/Modules/_ctypes/libffi/src/m68k/sysv.S

http://unladen-swallow.googlecode.com/ · Assembly · 234 lines · 179 code · 29 blank · 26 comment · 5 complexity · 9de0630e99a0b634afe5519c60c2be86 MD5 · raw file

  1. /* -----------------------------------------------------------------------
  2. sysv.S - Copyright (c) 1998 Andreas Schwab
  3. Copyright (c) 2008 Red Hat, Inc.
  4. m68k Foreign Function Interface
  5. Permission is hereby granted, free of charge, to any person obtaining
  6. a copy of this software and associated documentation files (the
  7. ``Software''), to deal in the Software without restriction, including
  8. without limitation the rights to use, copy, modify, merge, publish,
  9. distribute, sublicense, and/or sell copies of the Software, and to
  10. permit persons to whom the Software is furnished to do so, subject to
  11. the following conditions:
  12. The above copyright notice and this permission notice shall be included
  13. in all copies or substantial portions of the Software.
  14. THE SOFTWARE IS PROVIDED ``AS IS'', WITHOUT WARRANTY OF ANY KIND,
  15. EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
  16. MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  17. NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
  18. HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
  19. WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  20. OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
  21. DEALINGS IN THE SOFTWARE.
  22. ----------------------------------------------------------------------- */
  23. #define LIBFFI_ASM
  24. #include <fficonfig.h>
  25. #include <ffi.h>
  26. #ifdef HAVE_AS_CFI_PSEUDO_OP
  27. #define CFI_STARTPROC() .cfi_startproc
  28. #define CFI_OFFSET(reg,off) .cfi_offset reg,off
  29. #define CFI_DEF_CFA(reg,off) .cfi_def_cfa reg,off
  30. #define CFI_ENDPROC() .cfi_endproc
  31. #else
  32. #define CFI_STARTPROC()
  33. #define CFI_OFFSET(reg,off)
  34. #define CFI_DEF_CFA(reg,off)
  35. #define CFI_ENDPROC()
  36. #endif
  37. .text
  38. .globl ffi_call_SYSV
  39. .type ffi_call_SYSV,@function
  40. .align 4
  41. ffi_call_SYSV:
  42. CFI_STARTPROC()
  43. link %fp,#0
  44. CFI_OFFSET(14,-8)
  45. CFI_DEF_CFA(14,8)
  46. move.l %d2,-(%sp)
  47. CFI_OFFSET(2,-12)
  48. | Make room for all of the new args.
  49. sub.l 12(%fp),%sp
  50. | Call ffi_prep_args
  51. move.l 8(%fp),-(%sp)
  52. pea 4(%sp)
  53. #if !defined __PIC__
  54. jsr ffi_prep_args
  55. #else
  56. bsr.l ffi_prep_args@PLTPC
  57. #endif
  58. addq.l #8,%sp
  59. | Pass pointer to struct value, if any
  60. move.l %a0,%a1
  61. | Call the function
  62. move.l 24(%fp),%a0
  63. jsr (%a0)
  64. | Remove the space we pushed for the args
  65. add.l 12(%fp),%sp
  66. | Load the pointer to storage for the return value
  67. move.l 20(%fp),%a1
  68. | Load the return type code
  69. move.l 16(%fp),%d2
  70. | If the return value pointer is NULL, assume no return value.
  71. tst.l %a1
  72. jbeq noretval
  73. btst #0,%d2
  74. jbeq retlongint
  75. move.l %d0,(%a1)
  76. jbra epilogue
  77. retlongint:
  78. btst #1,%d2
  79. jbeq retfloat
  80. move.l %d0,(%a1)
  81. move.l %d1,4(%a1)
  82. jbra epilogue
  83. retfloat:
  84. btst #2,%d2
  85. jbeq retdouble
  86. fmove.s %fp0,(%a1)
  87. jbra epilogue
  88. retdouble:
  89. btst #3,%d2
  90. jbeq retlongdouble
  91. fmove.d %fp0,(%a1)
  92. jbra epilogue
  93. retlongdouble:
  94. btst #4,%d2
  95. jbeq retpointer
  96. fmove.x %fp0,(%a1)
  97. jbra epilogue
  98. retpointer:
  99. btst #5,%d2
  100. jbeq retstruct1
  101. move.l %a0,(%a1)
  102. jbra epilogue
  103. retstruct1:
  104. btst #6,%d2
  105. jbeq retstruct2
  106. move.b %d0,(%a1)
  107. jbra epilogue
  108. retstruct2:
  109. btst #7,%d2
  110. jbeq noretval
  111. move.w %d0,(%a1)
  112. noretval:
  113. epilogue:
  114. move.l (%sp)+,%d2
  115. unlk %fp
  116. rts
  117. CFI_ENDPROC()
  118. .size ffi_call_SYSV,.-ffi_call_SYSV
  119. .globl ffi_closure_SYSV
  120. .type ffi_closure_SYSV, @function
  121. .align 4
  122. ffi_closure_SYSV:
  123. CFI_STARTPROC()
  124. link %fp,#-12
  125. CFI_OFFSET(14,-8)
  126. CFI_DEF_CFA(14,8)
  127. move.l %sp,-12(%fp)
  128. pea 8(%fp)
  129. pea -12(%fp)
  130. move.l %a0,-(%sp)
  131. #if !defined __PIC__
  132. jsr ffi_closure_SYSV_inner
  133. #else
  134. bsr.l ffi_closure_SYSV_inner@PLTPC
  135. #endif
  136. lsr.l #1,%d0
  137. jne 1f
  138. jcc .Lcls_epilogue
  139. move.l -12(%fp),%d0
  140. .Lcls_epilogue:
  141. unlk %fp
  142. rts
  143. 1:
  144. lea -12(%fp),%a0
  145. lsr.l #2,%d0
  146. jne 1f
  147. jcs .Lcls_ret_float
  148. move.l (%a0)+,%d0
  149. move.l (%a0),%d1
  150. jra .Lcls_epilogue
  151. .Lcls_ret_float:
  152. fmove.s (%a0),%fp0
  153. jra .Lcls_epilogue
  154. 1:
  155. lsr.l #2,%d0
  156. jne 1f
  157. jcs .Lcls_ret_ldouble
  158. fmove.d (%a0),%fp0
  159. jra .Lcls_epilogue
  160. .Lcls_ret_ldouble:
  161. fmove.x (%a0),%fp0
  162. jra .Lcls_epilogue
  163. 1:
  164. lsr.l #2,%d0
  165. jne .Lcls_ret_struct2
  166. jcs .Lcls_ret_struct1
  167. move.l (%a0),%a0
  168. move.l %a0,%d0
  169. jra .Lcls_epilogue
  170. .Lcls_ret_struct1:
  171. move.b (%a0),%d0
  172. jra .Lcls_epilogue
  173. .Lcls_ret_struct2:
  174. move.w (%a0),%d0
  175. jra .Lcls_epilogue
  176. CFI_ENDPROC()
  177. .size ffi_closure_SYSV,.-ffi_closure_SYSV
  178. .globl ffi_closure_struct_SYSV
  179. .type ffi_closure_struct_SYSV, @function
  180. .align 4
  181. ffi_closure_struct_SYSV:
  182. CFI_STARTPROC()
  183. link %fp,#0
  184. CFI_OFFSET(14,-8)
  185. CFI_DEF_CFA(14,8)
  186. move.l %sp,-12(%fp)
  187. pea 8(%fp)
  188. move.l %a1,-(%sp)
  189. move.l %a0,-(%sp)
  190. #if !defined __PIC__
  191. jsr ffi_closure_SYSV_inner
  192. #else
  193. bsr.l ffi_closure_SYSV_inner@PLTPC
  194. #endif
  195. unlk %fp
  196. rts
  197. CFI_ENDPROC()
  198. .size ffi_closure_struct_SYSV,.-ffi_closure_struct_SYSV
  199. #if defined __ELF__ && defined __linux__
  200. .section .note.GNU-stack,"",@progbits
  201. #endif