divmodhi4.S 1.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657
  1. //===------------- divmodhi4.S - sint16 div & mod -------------------------===//
  2. //
  3. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  4. // See https://llvm.org/LICENSE.txt for license information.
  5. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  6. //
  7. //===----------------------------------------------------------------------===//
  8. //
  9. // As described at
  10. // https://gcc.gnu.org/wiki/avr-gcc#Exceptions_to_the_Calling_Convention, the
  11. // prototype is `struct {sint16, sint16} __divmodhi4(sint16, sint16)`.
  12. // The sint16 quotient is returned via R23:R22, and the sint16 remainder is
  13. // returned via R25:R24, while registers R21/R26/27/Rtmp and bit T in SREG
  14. // are clobbered.
  15. //
  16. //===----------------------------------------------------------------------===//
  17. .text
  18. .align 2
  19. #ifdef __AVR_TINY__
  20. .set __tmp_reg__, 16
  21. #else
  22. .set __tmp_reg__, 0
  23. #endif
  24. .globl __divmodhi4
  25. .type __divmodhi4, @function
  26. __divmodhi4:
  27. bst r25, 7
  28. mov __tmp_reg__, r23
  29. brtc __divmodhi4_a
  30. com __tmp_reg__
  31. rcall __divmodhi4_b
  32. __divmodhi4_a:
  33. sbrc r23, 7
  34. rcall __divmodhi4_c
  35. rcall __udivmodhi4 ; Call __udivmodhi4 to do real calculation.
  36. sbrc __tmp_reg__, 7
  37. rcall __divmodhi4_c
  38. brtc __divmodhi4_exit
  39. __divmodhi4_b:
  40. com r25
  41. neg r24
  42. sbci r25, 255
  43. ret ; Return quotient via R23:R22 and remainder via R25:R24.
  44. __divmodhi4_c:
  45. com r23
  46. neg r22
  47. sbci r23, 255
  48. __divmodhi4_exit:
  49. ret ; Return quotient via R23:R22 and remainder via R25:r24.