~ubuntu-branches/ubuntu/lucid/gauche-c-wrapper/lucid

« back to all changes in this revision

Viewing changes to libffi/src/sh64/sysv.S

  • Committer: Bazaar Package Importer
  • Author(s): NIIBE Yutaka
  • Date: 2008-04-07 09:15:03 UTC
  • Revision ID: james.westby@ubuntu.com-20080407091503-wu0h414koe95kj4i
Tags: upstream-0.5.2
ImportĀ upstreamĀ versionĀ 0.5.2

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/* -----------------------------------------------------------------------
 
2
   sysv.S - Copyright (c) 2003, 2004 Kaz Kojima
 
3
   
 
4
   SuperH SHmedia Foreign Function Interface 
 
5
 
 
6
   Permission is hereby granted, free of charge, to any person obtaining
 
7
   a copy of this software and associated documentation files (the
 
8
   ``Software''), to deal in the Software without restriction, including
 
9
   without limitation the rights to use, copy, modify, merge, publish,
 
10
   distribute, sublicense, and/or sell copies of the Software, and to
 
11
   permit persons to whom the Software is furnished to do so, subject to
 
12
   the following conditions:
 
13
 
 
14
   The above copyright notice and this permission notice shall be included
 
15
   in all copies or substantial portions of the Software.
 
16
 
 
17
   THE SOFTWARE IS PROVIDED ``AS IS'', WITHOUT WARRANTY OF ANY KIND, EXPRESS
 
18
   OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
 
19
   MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
 
20
   IN NO EVENT SHALL CYGNUS SOLUTIONS BE LIABLE FOR ANY CLAIM, DAMAGES OR
 
21
   OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
 
22
   ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
 
23
   OTHER DEALINGS IN THE SOFTWARE.
 
24
   ----------------------------------------------------------------------- */
 
25
 
 
26
#define LIBFFI_ASM      
 
27
#include <fficonfig.h>
 
28
#include <ffi.h>
 
29
#ifdef HAVE_MACHINE_ASM_H
 
30
#include <machine/asm.h>
 
31
#else
 
32
/* XXX these lose for some platforms, I'm sure. */
 
33
#define CNAME(x) x
 
34
#define ENTRY(x) .globl CNAME(x); .type CNAME(x),%function; CNAME(x):
 
35
#endif
 
36
 
 
37
#ifdef __LITTLE_ENDIAN__
 
38
#define OFS_FLT 0
 
39
#else
 
40
#define OFS_FLT 4
 
41
#endif
 
42
 
 
43
        .section        .text..SHmedia32,"ax"
 
44
 
 
45
        # r2:   ffi_prep_args
 
46
        # r3:   &ecif
 
47
        # r4:   bytes
 
48
        # r5:   flags
 
49
        # r6:   flags2
 
50
        # r7:   rvalue
 
51
        # r8:   fn
 
52
 
 
53
        # This assumes we are using gas.
 
54
        .align  5
 
55
ENTRY(ffi_call_SYSV)
 
56
        # Save registers
 
57
.LFB1:
 
58
        addi.l  r15, -48, r15
 
59
.LCFI0:
 
60
        st.q    r15, 40, r32
 
61
        st.q    r15, 32, r31
 
62
        st.q    r15, 24, r30
 
63
        st.q    r15, 16, r29
 
64
        st.q    r15, 8, r28
 
65
        st.l    r15, 4, r18
 
66
        st.l    r15, 0, r14
 
67
.LCFI1:
 
68
        add.l   r15, r63, r14
 
69
.LCFI2:
 
70
#       add     r4, r63, r28
 
71
        add     r5, r63, r29
 
72
        add     r6, r63, r30
 
73
        add     r7, r63, r31
 
74
        add     r8, r63, r32
 
75
 
 
76
        addi    r4, (64 + 7), r4
 
77
        andi    r4, ~7, r4
 
78
        sub.l   r15, r4, r15
 
79
 
 
80
        ptabs/l r2, tr0
 
81
        add     r15, r63, r2
 
82
        blink   tr0, r18
 
83
 
 
84
        addi    r15, 64, r22
 
85
        movi    0, r0
 
86
        movi    0, r1
 
87
 
 
88
        pt/l    1f, tr1
 
89
        bnei/l  r29, FFI_TYPE_STRUCT, tr1
 
90
        ld.l    r15, 0, r19
 
91
        addi    r15, 8, r15
 
92
        addi    r0, 1, r0
 
93
1:
 
94
 
 
95
.L_pass:
 
96
        andi    r30, 3, r20
 
97
        shlri   r30, 2, r30
 
98
 
 
99
        pt/l    .L_call_it, tr0
 
100
        pt/l    .L_pass_i, tr1
 
101
        pt/l    .L_pass_f, tr2
 
102
 
 
103
        beqi/l  r20, FFI_TYPE_VOID, tr0
 
104
        beqi/l  r20, FFI_TYPE_INT, tr1
 
105
        beqi/l  r20, FFI_TYPE_FLOAT, tr2
 
106
 
 
107
.L_pass_d:
 
108
        addi    r0, 1, r0
 
109
        addi    r1, 1, r1
 
110
        andi    r1, ~1, r1
 
111
 
 
112
        pt/l    3f, tr0
 
113
        movi    12, r20
 
114
        bge/l   r1, r20, tr0
 
115
 
 
116
        pt/l    .L_pop_d, tr1
 
117
        pt/l    2f, tr0
 
118
        blink   tr1, r63
 
119
2:
 
120
        addi.l  r15, 8, r15
 
121
3:
 
122
        pt/l    .L_pass, tr0
 
123
        addi    r1, 2, r1
 
124
        blink   tr0, r63
 
125
 
 
126
.L_pop_d:
 
127
        pt/l    .L_pop_d_tbl, tr1
 
128
        gettr   tr1, r20
 
129
        shlli   r1, 2, r21
 
130
        add     r20, r21, r20
 
131
        ptabs/l r20, tr1
 
132
        blink   tr1, r63
 
133
 
 
134
.L_pop_d_tbl:
 
135
        fld.d   r15, 0, dr0
 
136
        blink   tr0, r63
 
137
        fld.d   r15, 0, dr2
 
138
        blink   tr0, r63
 
139
        fld.d   r15, 0, dr4
 
140
        blink   tr0, r63
 
141
        fld.d   r15, 0, dr6
 
142
        blink   tr0, r63
 
143
        fld.d   r15, 0, dr8
 
144
        blink   tr0, r63
 
145
        fld.d   r15, 0, dr10
 
146
        blink   tr0, r63
 
147
 
 
148
.L_pass_f:
 
149
        addi    r0, 1, r0
 
150
        pt/l    3f, tr0
 
151
        movi    12, r20
 
152
        bge/l   r1, r20, tr0
 
153
 
 
154
        pt/l    .L_pop_f, tr1
 
155
        pt/l    2f, tr0
 
156
        blink   tr1, r63
 
157
2:
 
158
        addi.l  r15, 8, r15
 
159
3:
 
160
        pt/l    .L_pass, tr0
 
161
        addi    r1, 1, r1
 
162
        blink   tr0, r63
 
163
 
 
164
.L_pop_f:
 
165
        pt/l    .L_pop_f_tbl, tr1
 
166
        gettr   tr1, r20
 
167
        shlli   r1, 3, r21
 
168
        add     r20, r21, r20
 
169
        ptabs/l r20, tr1
 
170
        blink   tr1, r63
 
171
 
 
172
.L_pop_f_tbl:
 
173
        fld.s   r15, OFS_FLT, fr0
 
174
        blink   tr0, r63
 
175
        fld.s   r15, OFS_FLT, fr1
 
176
        blink   tr0, r63
 
177
        fld.s   r15, OFS_FLT, fr2
 
178
        blink   tr0, r63
 
179
        fld.s   r15, OFS_FLT, fr3
 
180
        blink   tr0, r63
 
181
        fld.s   r15, OFS_FLT, fr4
 
182
        blink   tr0, r63
 
183
        fld.s   r15, OFS_FLT, fr5
 
184
        blink   tr0, r63
 
185
        fld.s   r15, OFS_FLT, fr6
 
186
        blink   tr0, r63
 
187
        fld.s   r15, OFS_FLT, fr7
 
188
        blink   tr0, r63
 
189
        fld.s   r15, OFS_FLT, fr8
 
190
        blink   tr0, r63
 
191
        fld.s   r15, OFS_FLT, fr9
 
192
        blink   tr0, r63
 
193
        fld.s   r15, OFS_FLT, fr10
 
194
        blink   tr0, r63
 
195
        fld.s   r15, OFS_FLT, fr11
 
196
        blink   tr0, r63
 
197
 
 
198
.L_pass_i:
 
199
        pt/l    3f, tr0
 
200
        movi    8, r20
 
201
        bge/l   r0, r20, tr0
 
202
 
 
203
        pt/l    .L_pop_i, tr1
 
204
        pt/l    2f, tr0
 
205
        blink   tr1, r63
 
206
2:
 
207
        addi.l  r15, 8, r15
 
208
3:
 
209
        pt/l    .L_pass, tr0
 
210
        addi    r0, 1, r0
 
211
        blink   tr0, r63
 
212
 
 
213
.L_pop_i:
 
214
        pt/l    .L_pop_i_tbl, tr1
 
215
        gettr   tr1, r20
 
216
        shlli   r0, 3, r21
 
217
        add     r20, r21, r20
 
218
        ptabs/l r20, tr1
 
219
        blink   tr1, r63
 
220
 
 
221
.L_pop_i_tbl:
 
222
        ld.q    r15, 0, r2
 
223
        blink   tr0, r63
 
224
        ld.q    r15, 0, r3
 
225
        blink   tr0, r63
 
226
        ld.q    r15, 0, r4
 
227
        blink   tr0, r63
 
228
        ld.q    r15, 0, r5
 
229
        blink   tr0, r63
 
230
        ld.q    r15, 0, r6
 
231
        blink   tr0, r63
 
232
        ld.q    r15, 0, r7
 
233
        blink   tr0, r63
 
234
        ld.q    r15, 0, r8
 
235
        blink   tr0, r63
 
236
        ld.q    r15, 0, r9
 
237
        blink   tr0, r63
 
238
 
 
239
.L_call_it:
 
240
        # call function
 
241
        pt/l    1f, tr1
 
242
        bnei/l  r29, FFI_TYPE_STRUCT, tr1
 
243
        add     r19, r63, r2
 
244
1:
 
245
        add     r22, r63, r15
 
246
        ptabs/l r32, tr0
 
247
        blink   tr0, r18
 
248
 
 
249
        pt/l    .L_ret_i, tr0
 
250
        pt/l    .L_ret_ll, tr1
 
251
        pt/l    .L_ret_d, tr2
 
252
        pt/l    .L_ret_f, tr3
 
253
        pt/l    .L_epilogue, tr4
 
254
 
 
255
        beqi/l  r29, FFI_TYPE_INT, tr0
 
256
        beqi/l  r29, FFI_TYPE_UINT32, tr0
 
257
        beqi/l  r29, FFI_TYPE_SINT64, tr1
 
258
        beqi/l  r29, FFI_TYPE_UINT64, tr1
 
259
        beqi/l  r29, FFI_TYPE_DOUBLE, tr2
 
260
        beqi/l  r29, FFI_TYPE_FLOAT, tr3
 
261
 
 
262
        pt/l    .L_ret_q, tr0
 
263
        pt/l    .L_ret_h, tr1
 
264
 
 
265
        beqi/l  r29, FFI_TYPE_UINT8, tr0
 
266
        beqi/l  r29, FFI_TYPE_UINT16, tr1
 
267
        blink   tr4, r63
 
268
 
 
269
.L_ret_d:
 
270
        fst.d   r31, 0, dr0
 
271
        blink   tr4, r63
 
272
 
 
273
.L_ret_ll:
 
274
        st.q    r31, 0, r2
 
275
        blink   tr4, r63
 
276
 
 
277
.L_ret_f:
 
278
        fst.s   r31, OFS_FLT, fr0
 
279
        blink   tr4, r63
 
280
 
 
281
.L_ret_q:
 
282
        st.b    r31, 0, r2
 
283
        blink   tr4, r63
 
284
 
 
285
.L_ret_h:
 
286
        st.w    r31, 0, r2
 
287
        blink   tr4, r63
 
288
 
 
289
.L_ret_i:
 
290
        st.l    r31, 0, r2
 
291
        # Fall
 
292
 
 
293
.L_epilogue:
 
294
        # Remove the space we pushed for the args
 
295
        add     r14, r63, r15
 
296
 
 
297
        ld.l    r15, 0, r14
 
298
        ld.l    r15, 4, r18
 
299
        ld.q    r15, 8, r28
 
300
        ld.q    r15, 16, r29
 
301
        ld.q    r15, 24, r30
 
302
        ld.q    r15, 32, r31
 
303
        ld.q    r15, 40, r32
 
304
        addi.l  r15, 48, r15
 
305
        ptabs   r18, tr0
 
306
        blink   tr0, r63
 
307
 
 
308
.LFE1:
 
309
.ffi_call_SYSV_end:
 
310
        .size    CNAME(ffi_call_SYSV),.ffi_call_SYSV_end-CNAME(ffi_call_SYSV)
 
311
 
 
312
        .align  5
 
313
ENTRY(ffi_closure_SYSV)
 
314
.LFB2:
 
315
        addi.l  r15, -136, r15
 
316
.LCFI3:
 
317
        st.l    r15, 12, r18
 
318
        st.l    r15, 8, r14
 
319
        st.l    r15, 4, r12
 
320
.LCFI4:
 
321
        add     r15, r63, r14
 
322
.LCFI5:
 
323
        /* Stack layout:        
 
324
           ...
 
325
           64 bytes (register parameters)
 
326
           48 bytes (floating register parameters)
 
327
            8 bytes (result)
 
328
            4 bytes (r18)
 
329
            4 bytes (r14)
 
330
            4 bytes (r12)
 
331
            4 bytes (for align)
 
332
           <- new stack pointer
 
333
        */
 
334
        fst.d   r14, 24, dr0
 
335
        fst.d   r14, 32, dr2
 
336
        fst.d   r14, 40, dr4
 
337
        fst.d   r14, 48, dr6
 
338
        fst.d   r14, 56, dr8
 
339
        fst.d   r14, 64, dr10
 
340
        st.q    r14, 72, r2
 
341
        st.q    r14, 80, r3
 
342
        st.q    r14, 88, r4
 
343
        st.q    r14, 96, r5
 
344
        st.q    r14, 104, r6
 
345
        st.q    r14, 112, r7
 
346
        st.q    r14, 120, r8
 
347
        st.q    r14, 128, r9
 
348
 
 
349
        add     r1, r63, r2
 
350
        addi    r14, 16, r3
 
351
        addi    r14, 72, r4
 
352
        addi    r14, 24, r5
 
353
        addi    r14, 136, r6
 
354
#ifdef PIC
 
355
        movi    (((datalabel _GLOBAL_OFFSET_TABLE_-(.LPCS0-.)) >> 16) & 65535), r12
 
356
        shori   ((datalabel _GLOBAL_OFFSET_TABLE_-(.LPCS0-.)) & 65535), r12
 
357
.LPCS0: ptrel/u r12, tr0
 
358
        movi    ((ffi_closure_helper_SYSV@GOTPLT) & 65535), r1
 
359
        gettr   tr0, r12
 
360
        ldx.l   r1, r12, r1
 
361
        ptabs   r1, tr0
 
362
#else
 
363
        pt/l    ffi_closure_helper_SYSV, tr0
 
364
#endif
 
365
        blink   tr0, r18
 
366
 
 
367
        shlli   r2, 1, r1
 
368
        movi    (((datalabel .L_table) >> 16) & 65535), r2
 
369
        shori   ((datalabel .L_table) & 65535), r2
 
370
        ldx.w   r2, r1, r1
 
371
        add     r1, r2, r1
 
372
        pt/l    .L_case_v, tr1
 
373
        ptabs   r1, tr0
 
374
        blink   tr0, r63
 
375
 
 
376
        .align 2
 
377
.L_table:
 
378
        .word   .L_case_v - datalabel .L_table  /* FFI_TYPE_VOID */
 
379
        .word   .L_case_i - datalabel .L_table  /* FFI_TYPE_INT */
 
380
        .word   .L_case_f - datalabel .L_table  /* FFI_TYPE_FLOAT */
 
381
        .word   .L_case_d - datalabel .L_table  /* FFI_TYPE_DOUBLE */
 
382
        .word   .L_case_d - datalabel .L_table  /* FFI_TYPE_LONGDOUBLE */
 
383
        .word   .L_case_uq - datalabel .L_table /* FFI_TYPE_UINT8 */
 
384
        .word   .L_case_q - datalabel .L_table  /* FFI_TYPE_SINT8 */
 
385
        .word   .L_case_uh - datalabel .L_table /* FFI_TYPE_UINT16 */
 
386
        .word   .L_case_h - datalabel .L_table  /* FFI_TYPE_SINT16 */
 
387
        .word   .L_case_i - datalabel .L_table  /* FFI_TYPE_UINT32 */
 
388
        .word   .L_case_i - datalabel .L_table  /* FFI_TYPE_SINT32 */
 
389
        .word   .L_case_ll - datalabel .L_table /* FFI_TYPE_UINT64 */
 
390
        .word   .L_case_ll - datalabel .L_table /* FFI_TYPE_SINT64 */
 
391
        .word   .L_case_v - datalabel .L_table  /* FFI_TYPE_STRUCT */
 
392
        .word   .L_case_i - datalabel .L_table  /* FFI_TYPE_POINTER */
 
393
 
 
394
        .align 2
 
395
.L_case_d:
 
396
        fld.d   r14, 16, dr0
 
397
        blink   tr1, r63
 
398
.L_case_f:
 
399
        fld.s   r14, 16, fr0
 
400
        blink   tr1, r63
 
401
.L_case_ll:
 
402
        ld.q    r14, 16, r2
 
403
        blink   tr1, r63
 
404
.L_case_i:
 
405
        ld.l    r14, 16, r2
 
406
        blink   tr1, r63
 
407
.L_case_q:
 
408
        ld.b    r14, 16, r2
 
409
        blink   tr1, r63
 
410
.L_case_uq:
 
411
        ld.ub   r14, 16, r2
 
412
        blink   tr1, r63
 
413
.L_case_h:
 
414
        ld.w    r14, 16, r2
 
415
        blink   tr1, r63
 
416
.L_case_uh:
 
417
        ld.uw   r14, 16, r2
 
418
        blink   tr1, r63
 
419
.L_case_v:
 
420
        add.l   r14, r63, r15
 
421
        ld.l    r15, 4, r12
 
422
        ld.l    r15, 8, r14
 
423
        ld.l    r15, 12, r18
 
424
        addi.l  r15, 136, r15
 
425
        ptabs   r18, tr0
 
426
        blink   tr0, r63
 
427
 
 
428
.LFE2:
 
429
.ffi_closure_SYSV_end:
 
430
        .size    CNAME(ffi_closure_SYSV),.ffi_closure_SYSV_end-CNAME(ffi_closure_SYSV)
 
431
 
 
432
        .section        ".eh_frame","aw",@progbits
 
433
__FRAME_BEGIN__:
 
434
        .4byte  .LECIE1-.LSCIE1 /* Length of Common Information Entry */
 
435
.LSCIE1:
 
436
        .4byte  0x0     /* CIE Identifier Tag */
 
437
        .byte   0x1     /* CIE Version */
 
438
#ifdef PIC
 
439
        .ascii "zR\0"   /* CIE Augmentation */
 
440
#else
 
441
        .byte   0x0     /* CIE Augmentation */
 
442
#endif
 
443
        .uleb128 0x1    /* CIE Code Alignment Factor */
 
444
        .sleb128 -4     /* CIE Data Alignment Factor */
 
445
        .byte   0x12    /* CIE RA Column */
 
446
#ifdef PIC
 
447
        .uleb128 0x1    /* Augmentation size */
 
448
        .byte   0x10    /* FDE Encoding (pcrel) */
 
449
#endif
 
450
        .byte   0xc     /* DW_CFA_def_cfa */
 
451
        .uleb128 0xf
 
452
        .uleb128 0x0
 
453
        .align  2
 
454
.LECIE1:
 
455
.LSFDE1:
 
456
        .4byte  datalabel .LEFDE1-datalabel .LASFDE1    /* FDE Length */
 
457
.LASFDE1:
 
458
        .4byte  datalabel .LASFDE1-datalabel __FRAME_BEGIN__
 
459
#ifdef PIC
 
460
        .4byte  .LFB1-. /* FDE initial location */
 
461
#else
 
462
        .4byte  .LFB1   /* FDE initial location */
 
463
#endif
 
464
        .4byte  datalabel .LFE1-datalabel .LFB1 /* FDE address range */
 
465
#ifdef PIC
 
466
        .uleb128 0x0    /* Augmentation size */
 
467
#endif
 
468
        .byte   0x4     /* DW_CFA_advance_loc4 */
 
469
        .4byte  datalabel .LCFI0-datalabel .LFB1
 
470
        .byte   0xe     /* DW_CFA_def_cfa_offset */
 
471
        .uleb128 0x30
 
472
        .byte   0x4     /* DW_CFA_advance_loc4 */
 
473
        .4byte  datalabel .LCFI1-datalabel .LCFI0
 
474
        .byte   0x8e    /* DW_CFA_offset, column 0xe */
 
475
        .uleb128 0xc
 
476
        .byte   0x92    /* DW_CFA_offset, column 0x12 */
 
477
        .uleb128 0xb
 
478
        .byte   0x9c    /* DW_CFA_offset, column 0x1c */
 
479
        .uleb128 0xa
 
480
        .byte   0x9d    /* DW_CFA_offset, column 0x1d */
 
481
        .uleb128 0x8
 
482
        .byte   0x9e    /* DW_CFA_offset, column 0x1e */
 
483
        .uleb128 0x6
 
484
        .byte   0x9f    /* DW_CFA_offset, column 0x1f */
 
485
        .uleb128 0x4
 
486
        .byte   0xa0    /* DW_CFA_offset, column 0x20 */
 
487
        .uleb128 0x2
 
488
        .byte   0x4     /* DW_CFA_advance_loc4 */
 
489
        .4byte  datalabel .LCFI2-datalabel .LCFI1
 
490
        .byte   0xd     /* DW_CFA_def_cfa_register */
 
491
        .uleb128 0xe
 
492
        .align  2
 
493
.LEFDE1:
 
494
 
 
495
.LSFDE3:
 
496
        .4byte  datalabel .LEFDE3-datalabel .LASFDE3    /* FDE Length */
 
497
.LASFDE3:
 
498
        .4byte  datalabel .LASFDE3-datalabel __FRAME_BEGIN__
 
499
#ifdef PIC
 
500
        .4byte  .LFB2-. /* FDE initial location */
 
501
#else
 
502
        .4byte  .LFB2   /* FDE initial location */
 
503
#endif
 
504
        .4byte  datalabel .LFE2-datalabel .LFB2 /* FDE address range */
 
505
#ifdef PIC
 
506
        .uleb128 0x0    /* Augmentation size */
 
507
#endif
 
508
        .byte   0x4     /* DW_CFA_advance_loc4 */
 
509
        .4byte  datalabel .LCFI3-datalabel .LFB2
 
510
        .byte   0xe     /* DW_CFA_def_cfa_offset */
 
511
        .uleb128 0x88
 
512
        .byte   0x4     /* DW_CFA_advance_loc4 */
 
513
        .4byte  datalabel .LCFI4-datalabel .LCFI3
 
514
        .byte   0x8c    /* DW_CFA_offset, column 0xc */
 
515
        .uleb128 0x21
 
516
        .byte   0x8e    /* DW_CFA_offset, column 0xe */
 
517
        .uleb128 0x20
 
518
        .byte   0x92    /* DW_CFA_offset, column 0x12 */
 
519
        .uleb128 0x1f
 
520
        .byte   0x4     /* DW_CFA_advance_loc4 */
 
521
        .4byte  datalabel .LCFI5-datalabel .LCFI4
 
522
        .byte   0xd     /* DW_CFA_def_cfa_register */
 
523
        .uleb128 0xe
 
524
        .align  2
 
525
.LEFDE3: