]>
Commit | Line | Data |
---|---|---|
2f4006f8 DE |
1 | /* ----------------------------------------------------------------------- |
2 | aix.S - Copyright (c) 2002 Free Software Foundation, Inc. | |
3 | based on darwin.S by John Hornkvist | |
3e86b595 | 4 | |
2f4006f8 DE |
5 | PowerPC Assembly glue. |
6 | ||
7 | Permission is hereby granted, free of charge, to any person obtaining | |
8 | a copy of this software and associated documentation files (the | |
9 | ``Software''), to deal in the Software without restriction, including | |
10 | without limitation the rights to use, copy, modify, merge, publish, | |
11 | distribute, sublicense, and/or sell copies of the Software, and to | |
12 | permit persons to whom the Software is furnished to do so, subject to | |
13 | the following conditions: | |
14 | ||
15 | The above copyright notice and this permission notice shall be included | |
16 | in all copies or substantial portions of the Software. | |
17 | ||
18 | THE SOFTWARE IS PROVIDED ``AS IS'', WITHOUT WARRANTY OF ANY KIND, EXPRESS | |
19 | OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF | |
20 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. | |
21 | IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY CLAIM, DAMAGES OR | |
22 | OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | |
23 | ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | |
24 | OTHER DEALINGS IN THE SOFTWARE. | |
25 | ----------------------------------------------------------------------- */ | |
26 | ||
16070e45 AT |
27 | .set r0,0 |
28 | .set r1,1 | |
29 | .set r2,2 | |
30 | .set r3,3 | |
31 | .set r4,4 | |
32 | .set r5,5 | |
33 | .set r6,6 | |
34 | .set r7,7 | |
35 | .set r8,8 | |
36 | .set r9,9 | |
37 | .set r10,10 | |
38 | .set r11,11 | |
39 | .set r12,12 | |
40 | .set r13,13 | |
41 | .set r14,14 | |
42 | .set r15,15 | |
43 | .set r16,16 | |
44 | .set r17,17 | |
45 | .set r18,18 | |
46 | .set r19,19 | |
47 | .set r20,20 | |
48 | .set r21,21 | |
49 | .set r22,22 | |
50 | .set r23,23 | |
51 | .set r24,24 | |
52 | .set r25,25 | |
53 | .set r26,26 | |
54 | .set r27,27 | |
55 | .set r28,28 | |
56 | .set r29,29 | |
57 | .set r30,30 | |
58 | .set r31,31 | |
59 | .set f0,0 | |
60 | .set f1,1 | |
61 | .set f2,2 | |
62 | .set f3,3 | |
63 | .set f4,4 | |
64 | .set f5,5 | |
65 | .set f6,6 | |
66 | .set f7,7 | |
67 | .set f8,8 | |
68 | .set f9,9 | |
69 | .set f10,10 | |
70 | .set f11,11 | |
71 | .set f12,12 | |
72 | .set f13,13 | |
73 | .set f14,14 | |
74 | .set f15,15 | |
75 | .set f16,16 | |
76 | .set f17,17 | |
77 | .set f18,18 | |
78 | .set f19,19 | |
79 | .set f20,20 | |
80 | .set f21,21 | |
81 | ||
82 | #define LIBFFI_ASM | |
1450eb7a | 83 | #include <fficonfig.h> |
2f4006f8 DE |
84 | #include <ffi.h> |
85 | #define JUMPTARGET(name) name | |
86 | #define L(x) x | |
87 | .file "aix.S" | |
88 | .toc | |
89 | .csect .text[PR] | |
90 | .align 2 | |
91 | .globl ffi_prep_args | |
92 | ||
93 | .csect .text[PR] | |
94 | .align 2 | |
95 | .globl ffi_call_AIX | |
96 | .globl .ffi_call_AIX | |
97 | .csect ffi_call_AIX[DS] | |
98 | ffi_call_AIX: | |
99 | .long .ffi_call_AIX, TOC[tc0], 0 | |
100 | .csect .text[PR] | |
101 | .ffi_call_AIX: | |
102 | mr r12,r8 // We only need r12 until the call, so it doesn't have to be saved... | |
103 | /* Save the old stack pointer as AP. */ | |
104 | mr r8,r1 | |
105 | ||
106 | /* Allocate the stack space we need. */ | |
16070e45 | 107 | stwux r1,r1,r4 |
2f4006f8 DE |
108 | |
109 | /* Save registers we use. */ | |
110 | mflr r9 | |
111 | ||
112 | stw r28,-16(r8) | |
113 | stw r29,-12(r8) | |
114 | stw r30, -8(r8) | |
115 | stw r31, -4(r8) | |
116 | ||
117 | stw r9, 8(r8) | |
118 | stw r2, 20(r1) | |
119 | ||
120 | /* Save arguments over call... */ | |
121 | mr r31,r5 /* flags, */ | |
122 | mr r30,r6 /* rvalue, */ | |
123 | mr r29,r7 /* function address, */ | |
124 | mr r28,r8 /* our AP. */ | |
3e86b595 | 125 | |
2f4006f8 DE |
126 | /* Call ffi_prep_args. */ |
127 | mr r4,r1 | |
128 | li r9,0 | |
129 | ||
130 | lwz r2,4(r12) | |
131 | lwz r12,0(r12) | |
132 | mtctr r12 // r12 holds address of _ffi_prep_args | |
16070e45 | 133 | bctrl |
2f4006f8 DE |
134 | lwz r2,20(r1) |
135 | ||
136 | /* Now do the call. */ | |
137 | lwz r12,0(r29) | |
138 | /* Set up cr1 with bits 4-7 of the flags. */ | |
139 | mtcrf 0x40,r31 | |
140 | stw r2,20(r1) | |
141 | mtctr r12 | |
142 | lwz r2,4(r29) | |
143 | /* Load all those argument registers. */ | |
3e86b595 DE |
144 | // We have set up a nice stack frame, just load it into registers. |
145 | lwz r3, 20+(1*4)(r1) | |
146 | lwz r4, 20+(2*4)(r1) | |
147 | lwz r5, 20+(3*4)(r1) | |
148 | lwz r6, 20+(4*4)(r1) | |
149 | nop | |
2f4006f8 | 150 | lwz r7, 20+(5*4)(r1) |
3e86b595 DE |
151 | lwz r8, 20+(6*4)(r1) |
152 | lwz r9, 20+(7*4)(r1) | |
153 | lwz r10,20+(8*4)(r1) | |
2f4006f8 DE |
154 | |
155 | L1: | |
156 | /* Load all the FP registers. */ | |
157 | bf 6,L2 // 2f + 0x18 | |
158 | lfd f1,-16-(13*8)(r28) | |
159 | lfd f2,-16-(12*8)(r28) | |
160 | lfd f3,-16-(11*8)(r28) | |
161 | lfd f4,-16-(10*8)(r28) | |
162 | nop | |
163 | lfd f5,-16-(9*8)(r28) | |
164 | lfd f6,-16-(8*8)(r28) | |
165 | lfd f7,-16-(7*8)(r28) | |
166 | lfd f8,-16-(6*8)(r28) | |
167 | nop | |
168 | lfd f9,-16-(5*8)(r28) | |
3e86b595 | 169 | lfd f10,-16-(4*8)(r28) |
2f4006f8 DE |
170 | lfd f11,-16-(3*8)(r28) |
171 | lfd f12,-16-(2*8)(r28) | |
172 | nop | |
173 | lfd f13,-16-(1*8)(r28) | |
174 | ||
3e86b595 | 175 | L2: |
2f4006f8 DE |
176 | /* Make the call. */ |
177 | bctrl | |
178 | lwz r2,20(r1) | |
3e86b595 | 179 | |
2f4006f8 DE |
180 | /* Now, deal with the return value. */ |
181 | mtcrf 0x01,r31 | |
182 | ||
183 | bt 30,L(done_return_value) | |
184 | bt 29,L(fp_return_value) | |
185 | stw r3,0(r30) | |
186 | bf 28,L(done_return_value) | |
187 | stw r4,4(r30) | |
188 | ||
189 | /* Fall through... */ | |
190 | ||
191 | L(done_return_value): | |
192 | /* Restore the registers we used and return. */ | |
193 | lwz r9, 8(r28) | |
194 | lwz r31, -4(r28) | |
195 | mtlr r9 | |
196 | lwz r30, -8(r28) | |
197 | lwz r29,-12(r28) | |
198 | lwz r28,-16(r28) | |
199 | lwz r1,0(r1) | |
200 | blr | |
201 | ||
202 | L(fp_return_value): | |
203 | bf 28,L(float_return_value) | |
204 | stfd f1,0(r30) | |
205 | b L(done_return_value) | |
206 | L(float_return_value): | |
207 | stfs f1,0(r30) | |
208 | b L(done_return_value) | |
1f7d5413 DE |
209 | .long 0 |
210 | .byte 0,0,0,1,128,4,0,0 | |
2f4006f8 DE |
211 | //END(ffi_call_AIX) |
212 | ||
1f7d5413 DE |
213 | .csect .text[PR] |
214 | .align 2 | |
215 | .globl ffi_call_DARWIN | |
216 | .globl .ffi_call_DARWIN | |
217 | .csect ffi_call_DARWIN[DS] | |
218 | ffi_call_DARWIN: | |
219 | .long .ffi_call_DARWIN, TOC[tc0], 0 | |
220 | .csect .text[PR] | |
221 | .ffi_call_DARWIN: | |
222 | blr | |
223 | .long 0 | |
224 | .byte 0,0,0,0,0,0,0,0 | |
225 | //END(ffi_call_DARWIN) |