Commit 56faec5e by Andrew Haley Committed by Andrew Haley

ffitarget.h, ffi.c: Merge stdcall changes from libffi.

2009-06-05  Andrew Haley  <aph@redhat.com>

        * src/x86/ffitarget.h, src/x86/ffi.c: Merge stdcall changes from
        libffi.

From-SVN: r148207
parent 47d1f191
2009-06-05 Andrew Haley <aph@redhat.com>
* src/x86/ffitarget.h, src/x86/ffi.c: Merge stdcall changes from
libffi.
2009-06-04 Andrew Haley <aph@redhat.com> 2009-06-04 Andrew Haley <aph@redhat.com>
* src/x86/ffitarget.h, src/x86/win32.S, src/x86/ffi.c: Back out * src/x86/ffitarget.h, src/x86/win32.S, src/x86/ffi.c: Back out
......
/* ----------------------------------------------------------------------- /* -----------------------------------------------------------------------
ffi.c - Copyright (c) 1996, 1998, 1999, 2001, 2007 Red Hat, Inc. ffi.c - Copyright (c) 1996, 1998, 1999, 2001, 2007, 2008 Red Hat, Inc.
Copyright (c) 2002 Ranjit Mathew Copyright (c) 2002 Ranjit Mathew
Copyright (c) 2002 Bo Thorsen Copyright (c) 2002 Bo Thorsen
Copyright (c) 2002 Roger Sayle Copyright (c) 2002 Roger Sayle
...@@ -236,6 +236,10 @@ unsigned int FFI_HIDDEN ffi_closure_SYSV_inner (ffi_closure *, void **, void *) ...@@ -236,6 +236,10 @@ unsigned int FFI_HIDDEN ffi_closure_SYSV_inner (ffi_closure *, void **, void *)
__attribute__ ((regparm(1))); __attribute__ ((regparm(1)));
void FFI_HIDDEN ffi_closure_raw_SYSV (ffi_raw_closure *) void FFI_HIDDEN ffi_closure_raw_SYSV (ffi_raw_closure *)
__attribute__ ((regparm(1))); __attribute__ ((regparm(1)));
#ifdef X86_WIN32
void FFI_HIDDEN ffi_closure_STDCALL (ffi_closure *)
__attribute__ ((regparm(1)));
#endif
/* This function is jumped to by the trampoline */ /* This function is jumped to by the trampoline */
...@@ -245,7 +249,7 @@ ffi_closure_SYSV_inner (closure, respp, args) ...@@ -245,7 +249,7 @@ ffi_closure_SYSV_inner (closure, respp, args)
void **respp; void **respp;
void *args; void *args;
{ {
// our various things... /* our various things... */
ffi_cif *cif; ffi_cif *cif;
void **arg_area; void **arg_area;
...@@ -311,13 +315,26 @@ ffi_prep_incoming_args_SYSV(char *stack, void **rvalue, void **avalue, ...@@ -311,13 +315,26 @@ ffi_prep_incoming_args_SYSV(char *stack, void **rvalue, void **avalue,
({ unsigned char *__tramp = (unsigned char*)(TRAMP); \ ({ unsigned char *__tramp = (unsigned char*)(TRAMP); \
unsigned int __fun = (unsigned int)(FUN); \ unsigned int __fun = (unsigned int)(FUN); \
unsigned int __ctx = (unsigned int)(CTX); \ unsigned int __ctx = (unsigned int)(CTX); \
unsigned int __dis = __fun - (__ctx + FFI_TRAMPOLINE_SIZE); \ unsigned int __dis = __fun - (__ctx + 10); \
*(unsigned char*) &__tramp[0] = 0xb8; \ *(unsigned char*) &__tramp[0] = 0xb8; \
*(unsigned int*) &__tramp[1] = __ctx; /* movl __ctx, %eax */ \ *(unsigned int*) &__tramp[1] = __ctx; /* movl __ctx, %eax */ \
*(unsigned char *) &__tramp[5] = 0xe9; \ *(unsigned char *) &__tramp[5] = 0xe9; \
*(unsigned int*) &__tramp[6] = __dis; /* jmp __fun */ \ *(unsigned int*) &__tramp[6] = __dis; /* jmp __fun */ \
}) })
#define FFI_INIT_TRAMPOLINE_STDCALL(TRAMP,FUN,CTX,SIZE) \
({ unsigned char *__tramp = (unsigned char*)(TRAMP); \
unsigned int __fun = (unsigned int)(FUN); \
unsigned int __ctx = (unsigned int)(CTX); \
unsigned int __dis = __fun - (__ctx + 10); \
unsigned short __size = (unsigned short)(SIZE); \
*(unsigned char*) &__tramp[0] = 0xb8; \
*(unsigned int*) &__tramp[1] = __ctx; /* movl __ctx, %eax */ \
*(unsigned char *) &__tramp[5] = 0xe8; \
*(unsigned int*) &__tramp[6] = __dis; /* call __fun */ \
*(unsigned char *) &__tramp[10] = 0xc2; \
*(unsigned short*) &__tramp[11] = __size; /* ret __size */ \
})
/* the cif must already be prep'ed */ /* the cif must already be prep'ed */
...@@ -328,11 +345,24 @@ ffi_prep_closure_loc (ffi_closure* closure, ...@@ -328,11 +345,24 @@ ffi_prep_closure_loc (ffi_closure* closure,
void *user_data, void *user_data,
void *codeloc) void *codeloc)
{ {
FFI_ASSERT (cif->abi == FFI_SYSV); if (cif->abi == FFI_SYSV)
{
FFI_INIT_TRAMPOLINE (&closure->tramp[0], \ FFI_INIT_TRAMPOLINE (&closure->tramp[0],
&ffi_closure_SYSV, \ &ffi_closure_SYSV,
codeloc); (void*)codeloc);
}
#ifdef X86_WIN32
else if (cif->abi == FFI_STDCALL)
{
FFI_INIT_TRAMPOLINE_STDCALL (&closure->tramp[0],
&ffi_closure_STDCALL,
(void*)codeloc, cif->bytes);
}
#endif
else
{
return FFI_BAD_ABI;
}
closure->cif = cif; closure->cif = cif;
closure->user_data = user_data; closure->user_data = user_data;
...@@ -354,7 +384,9 @@ ffi_prep_raw_closure_loc (ffi_raw_closure* closure, ...@@ -354,7 +384,9 @@ ffi_prep_raw_closure_loc (ffi_raw_closure* closure,
{ {
int i; int i;
FFI_ASSERT (cif->abi == FFI_SYSV); if (cif->abi != FFI_SYSV) {
return FFI_BAD_ABI;
}
// we currently don't support certain kinds of arguments for raw // we currently don't support certain kinds of arguments for raw
// closures. This should be implemented by a separate assembly language // closures. This should be implemented by a separate assembly language
......
...@@ -78,7 +78,11 @@ typedef enum ffi_abi { ...@@ -78,7 +78,11 @@ typedef enum ffi_abi {
#define FFI_TRAMPOLINE_SIZE 24 #define FFI_TRAMPOLINE_SIZE 24
#define FFI_NATIVE_RAW_API 0 #define FFI_NATIVE_RAW_API 0
#else #else
#ifdef X86_WIN32
#define FFI_TRAMPOLINE_SIZE 13
#else
#define FFI_TRAMPOLINE_SIZE 10 #define FFI_TRAMPOLINE_SIZE 10
#endif
#define FFI_NATIVE_RAW_API 1 /* x86 has native raw api support */ #define FFI_NATIVE_RAW_API 1 /* x86 has native raw api support */
#endif #endif
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment