1
/* -----------------------------------------------------------------------
2
ffi.c - Copyright (c) 2002-2008, 2012 Kaz Kojima
3
Copyright (c) 2008 Red Hat, Inc.
5
SuperH Foreign Function Interface
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:
15
The above copyright notice and this permission notice shall be included
16
in all copies or substantial portions of the Software.
18
THE SOFTWARE IS PROVIDED ``AS IS'', WITHOUT WARRANTY OF ANY KIND,
19
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
21
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
22
HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
23
WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
24
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
25
DEALINGS IN THE SOFTWARE.
26
----------------------------------------------------------------------- */
29
#include <ffi_common.h>
38
#if defined(__HITACHI__)
39
#define STRUCT_VALUE_ADDRESS_WITH_ARG 1
41
#define STRUCT_VALUE_ADDRESS_WITH_ARG 0
44
/* If the structure has essentialy an unique element, return its type. */
46
simple_type (ffi_type *arg)
48
if (arg->type != FFI_TYPE_STRUCT)
50
else if (arg->elements[1])
51
return FFI_TYPE_STRUCT;
53
return simple_type (arg->elements[0]);
57
return_type (ffi_type *arg)
61
if (arg->type != FFI_TYPE_STRUCT)
64
type = simple_type (arg->elements[0]);
65
if (! arg->elements[1])
82
/* gcc uses r0/r1 pair for some kind of structures. */
83
if (arg->size <= 2 * sizeof (int))
88
while ((e = arg->elements[i++]))
90
type = simple_type (e);
97
return FFI_TYPE_UINT64;
105
return FFI_TYPE_STRUCT;
108
/* ffi_prep_args is called by the assembly routine once stack space
109
has been allocated for the function's arguments */
111
void ffi_prep_args(char *stack, extended_cif *ecif)
113
register unsigned int i;
115
register unsigned int avn;
116
register void **p_argv;
118
register ffi_type **p_arg;
127
if (return_type (ecif->cif->rtype) == FFI_TYPE_STRUCT)
129
*(void **) argp = ecif->rvalue;
131
ireg = STRUCT_VALUE_ADDRESS_WITH_ARG ? 1 : 0;
136
/* Set arguments for registers. */
138
avn = ecif->cif->nargs;
139
p_argv = ecif->avalue;
141
for (i = 0, p_arg = ecif->cif->arg_types; i < avn; i++, p_arg++, p_argv++)
148
if (greg++ >= NGREGARG)
152
switch ((*p_arg)->type)
155
*(signed int *) argp = (signed int)*(SINT8 *)(* p_argv);
159
*(unsigned int *) argp = (unsigned int)*(UINT8 *)(* p_argv);
162
case FFI_TYPE_SINT16:
163
*(signed int *) argp = (signed int)*(SINT16 *)(* p_argv);
166
case FFI_TYPE_UINT16:
167
*(unsigned int *) argp = (unsigned int)*(UINT16 *)(* p_argv);
170
case FFI_TYPE_STRUCT:
171
*(unsigned int *) argp = (unsigned int)*(UINT32 *)(* p_argv);
179
else if (z == sizeof(int))
182
if ((*p_arg)->type == FFI_TYPE_FLOAT)
184
if (freg++ >= NFREGARG)
190
if (greg++ >= NGREGARG)
193
*(unsigned int *) argp = (unsigned int)*(UINT32 *)(* p_argv);
197
else if ((*p_arg)->type == FFI_TYPE_DOUBLE)
199
if (freg + 1 >= NFREGARG)
201
freg = (freg + 1) & ~1;
203
memcpy (argp, *p_argv, z);
209
int n = (z + sizeof (int) - 1) / sizeof (int);
211
if (greg + n - 1 >= NGREGARG)
214
if (greg >= NGREGARG)
218
memcpy (argp, *p_argv, z);
219
argp += n * sizeof (int);
223
/* Set arguments on stack. */
228
p_argv = ecif->avalue;
230
for (i = 0, p_arg = ecif->cif->arg_types; i < avn; i++, p_arg++, p_argv++)
237
if (greg++ < NGREGARG)
241
switch ((*p_arg)->type)
244
*(signed int *) argp = (signed int)*(SINT8 *)(* p_argv);
248
*(unsigned int *) argp = (unsigned int)*(UINT8 *)(* p_argv);
251
case FFI_TYPE_SINT16:
252
*(signed int *) argp = (signed int)*(SINT16 *)(* p_argv);
255
case FFI_TYPE_UINT16:
256
*(unsigned int *) argp = (unsigned int)*(UINT16 *)(* p_argv);
259
case FFI_TYPE_STRUCT:
260
*(unsigned int *) argp = (unsigned int)*(UINT32 *)(* p_argv);
268
else if (z == sizeof(int))
271
if ((*p_arg)->type == FFI_TYPE_FLOAT)
273
if (freg++ < NFREGARG)
279
if (greg++ < NGREGARG)
282
*(unsigned int *) argp = (unsigned int)*(UINT32 *)(* p_argv);
286
else if ((*p_arg)->type == FFI_TYPE_DOUBLE)
288
if (freg + 1 < NFREGARG)
290
freg = (freg + 1) & ~1;
294
memcpy (argp, *p_argv, z);
300
int n = (z + sizeof (int) - 1) / sizeof (int);
301
if (greg + n - 1 < NGREGARG)
306
#if (! defined(__SH4__))
307
else if (greg < NGREGARG)
313
memcpy (argp, *p_argv, z);
314
argp += n * sizeof (int);
321
/* Perform machine dependent cif processing */
322
ffi_status ffi_prep_cif_machdep(ffi_cif *cif)
334
greg = ((return_type (cif->rtype) == FFI_TYPE_STRUCT) &&
335
STRUCT_VALUE_ADDRESS_WITH_ARG) ? 1 : 0;
338
for (i = j = 0; i < cif->nargs && j < 12; i++)
340
type = (cif->arg_types)[i]->type;
344
if (freg >= NFREGARG)
347
cif->flags += ((cif->arg_types)[i]->type) << (2 * j);
351
case FFI_TYPE_DOUBLE:
352
if ((freg + 1) >= NFREGARG)
354
freg = (freg + 1) & ~1;
356
cif->flags += ((cif->arg_types)[i]->type) << (2 * j);
361
size = (cif->arg_types)[i]->size;
362
n = (size + sizeof (int) - 1) / sizeof (int);
363
if (greg + n - 1 >= NGREGARG)
366
for (m = 0; m < n; m++)
367
cif->flags += FFI_TYPE_INT << (2 * j++);
372
for (i = j = 0; i < cif->nargs && j < 4; i++)
374
size = (cif->arg_types)[i]->size;
375
n = (size + sizeof (int) - 1) / sizeof (int);
376
if (greg >= NGREGARG)
378
else if (greg + n - 1 >= NGREGARG)
381
for (m = 0; m < n; m++)
382
cif->flags += FFI_TYPE_INT << (2 * j++);
386
/* Set the return type flag */
387
switch (cif->rtype->type)
389
case FFI_TYPE_STRUCT:
390
cif->flags += (unsigned) (return_type (cif->rtype)) << 24;
395
case FFI_TYPE_DOUBLE:
396
case FFI_TYPE_SINT64:
397
case FFI_TYPE_UINT64:
398
cif->flags += (unsigned) cif->rtype->type << 24;
402
cif->flags += FFI_TYPE_INT << 24;
409
extern void ffi_call_SYSV(void (*)(char *, extended_cif *), extended_cif *,
410
unsigned, unsigned, unsigned *, void (*fn)(void));
412
void ffi_call(ffi_cif *cif, void (*fn)(void), void *rvalue, void **avalue)
418
ecif.avalue = avalue;
420
/* If the return value is a struct and we don't have a return */
421
/* value address then we need to make one */
423
if (cif->rtype->type == FFI_TYPE_STRUCT
424
&& return_type (cif->rtype) != FFI_TYPE_STRUCT)
425
ecif.rvalue = &trvalue;
426
else if ((rvalue == NULL) &&
427
(cif->rtype->type == FFI_TYPE_STRUCT))
429
ecif.rvalue = alloca(cif->rtype->size);
432
ecif.rvalue = rvalue;
437
ffi_call_SYSV(ffi_prep_args, &ecif, cif->bytes, cif->flags, ecif.rvalue,
446
&& cif->rtype->type == FFI_TYPE_STRUCT
447
&& return_type (cif->rtype) != FFI_TYPE_STRUCT)
448
memcpy (rvalue, &trvalue, cif->rtype->size);
451
extern void ffi_closure_SYSV (void);
453
extern void __ic_invalidate (void *line);
457
ffi_prep_closure_loc (ffi_closure* closure,
459
void (*fun)(ffi_cif*, void*, void**, void*),
466
if (cif->abi != FFI_SYSV)
469
tramp = (unsigned int *) &closure->tramp[0];
470
/* Set T bit if the function returns a struct pointed with R2. */
471
insn = (return_type (cif->rtype) == FFI_TYPE_STRUCT
473
: 0x0008 /* clrt */);
475
#ifdef __LITTLE_ENDIAN__
476
tramp[0] = 0xd301d102;
477
tramp[1] = 0x0000412b | (insn << 16);
479
tramp[0] = 0xd102d301;
480
tramp[1] = 0x412b0000 | insn;
482
*(void **) &tramp[2] = (void *)codeloc; /* ctx */
483
*(void **) &tramp[3] = (void *)ffi_closure_SYSV; /* funaddr */
487
closure->user_data = user_data;
490
/* Flush the icache. */
491
__ic_invalidate(codeloc);
497
/* Basically the trampoline invokes ffi_closure_SYSV, and on
498
* entry, r3 holds the address of the closure.
499
* After storing the registers that could possibly contain
500
* parameters to be passed into the stack frame and setting
501
* up space for a return value, ffi_closure_SYSV invokes the
502
* following helper function to do most of the work.
505
#ifdef __LITTLE_ENDIAN__
514
ffi_closure_helper_SYSV (ffi_closure *closure, void *rvalue,
515
unsigned long *pgr, unsigned long *pfr,
528
avalue = alloca(cif->nargs * sizeof(void *));
530
/* Copy the caller's structure return value address so that the closure
531
returns the data directly to the caller. */
532
if (cif->rtype->type == FFI_TYPE_STRUCT && STRUCT_VALUE_ADDRESS_WITH_ARG)
534
rvalue = (void *) *pgr++;
544
/* Grab the addresses of the arguments from the stack frame. */
545
for (i = 0, p_arg = cif->arg_types; i < avn; i++, p_arg++)
552
if (greg++ >= NGREGARG)
556
switch ((*p_arg)->type)
560
avalue[i] = (((char *)pgr) + OFS_INT8);
563
case FFI_TYPE_SINT16:
564
case FFI_TYPE_UINT16:
565
avalue[i] = (((char *)pgr) + OFS_INT16);
568
case FFI_TYPE_STRUCT:
577
else if (z == sizeof(int))
580
if ((*p_arg)->type == FFI_TYPE_FLOAT)
582
if (freg++ >= NFREGARG)
590
if (greg++ >= NGREGARG)
597
else if ((*p_arg)->type == FFI_TYPE_DOUBLE)
599
if (freg + 1 >= NFREGARG)
603
freg = (freg + 1) & ~1;
611
int n = (z + sizeof (int) - 1) / sizeof (int);
613
if (greg + n - 1 >= NGREGARG)
616
if (greg >= NGREGARG)
630
for (i = 0, p_arg = cif->arg_types; i < avn; i++, p_arg++)
637
if (greg++ < NGREGARG)
641
switch ((*p_arg)->type)
645
avalue[i] = (((char *)pst) + OFS_INT8);
648
case FFI_TYPE_SINT16:
649
case FFI_TYPE_UINT16:
650
avalue[i] = (((char *)pst) + OFS_INT16);
653
case FFI_TYPE_STRUCT:
662
else if (z == sizeof(int))
665
if ((*p_arg)->type == FFI_TYPE_FLOAT)
667
if (freg++ < NFREGARG)
673
if (greg++ < NGREGARG)
680
else if ((*p_arg)->type == FFI_TYPE_DOUBLE)
682
if (freg + 1 < NFREGARG)
684
freg = (freg + 1) & ~1;
694
int n = (z + sizeof (int) - 1) / sizeof (int);
695
if (greg + n - 1 < NGREGARG)
700
#if (! defined(__SH4__))
701
else if (greg < NGREGARG)
704
pst += greg - NGREGARG;
713
(closure->fun) (cif, rvalue, avalue, closure->user_data);
715
/* Tell ffi_closure_SYSV how to perform return type promotions. */
716
return return_type (cif->rtype);