Makefile.am (nodist_libffi_la_SOURCES): Add POWERPC_FREEBSD.
2005-07-19 Andreas Tobler <a.tobler@schweiz.ch> * Makefile.am (nodist_libffi_la_SOURCES): Add POWERPC_FREEBSD. * Makefile.in: Regenerate. * include/Makefile.in: Likewise. * testsuite/Makefile.in: Likewise. * configure.ac: Add POWERPC_FREEBSD rules. * configure: Regenerate. * src/powerpc/ffitarget.h: Add POWERPC_FREEBSD rules. (FFI_SYSV_TYPE_SMALL_STRUCT): Define. * src/powerpc/ffi.c: Add flags to handle small structure returns in ffi_call_SYSV. (ffi_prep_cif_machdep): Handle small structures for SYSV 4 ABI. Aka FFI_SYSV. (ffi_closure_helper_SYSV): Likewise. * src/powerpc/ppc_closure.S: Add return types for small structures. * src/powerpc/sysv.S: Add bits to handle small structures for final SYSV 4 ABI From-SVN: r102174
This commit is contained in:
parent
af62f6f9a4
commit
970676420b
10 changed files with 229 additions and 53 deletions
|
@ -117,6 +117,9 @@ endif
|
|||
if POWERPC_DARWIN
|
||||
nodist_libffi_la_SOURCES += src/powerpc/ffi_darwin.c src/powerpc/darwin.S src/powerpc/darwin_closure.S
|
||||
endif
|
||||
if POWERPC_FREEBSD
|
||||
nodist_libffi_la_SOURCES += src/powerpc/ffi.c src/powerpc/sysv.S src/powerpc/ppc_closure.S
|
||||
endif
|
||||
if ARM
|
||||
nodist_libffi_la_SOURCES += src/arm/sysv.S src/arm/ffi.c
|
||||
endif
|
||||
|
|
|
@ -51,14 +51,15 @@ target_triplet = @target@
|
|||
@POWERPC_TRUE@am__append_10 = src/powerpc/ffi.c src/powerpc/sysv.S src/powerpc/ppc_closure.S src/powerpc/linux64.S src/powerpc/linux64_closure.S
|
||||
@POWERPC_AIX_TRUE@am__append_11 = src/powerpc/ffi_darwin.c src/powerpc/aix.S src/powerpc/aix_closure.S
|
||||
@POWERPC_DARWIN_TRUE@am__append_12 = src/powerpc/ffi_darwin.c src/powerpc/darwin.S src/powerpc/darwin_closure.S
|
||||
@ARM_TRUE@am__append_13 = src/arm/sysv.S src/arm/ffi.c
|
||||
@LIBFFI_CRIS_TRUE@am__append_14 = src/cris/sysv.S src/cris/ffi.c
|
||||
@FRV_TRUE@am__append_15 = src/frv/eabi.S src/frv/ffi.c
|
||||
@S390_TRUE@am__append_16 = src/s390/sysv.S src/s390/ffi.c
|
||||
@X86_64_TRUE@am__append_17 = src/x86/ffi64.c src/x86/unix64.S src/x86/ffi.c src/x86/sysv.S
|
||||
@SH_TRUE@am__append_18 = src/sh/sysv.S src/sh/ffi.c
|
||||
@SH64_TRUE@am__append_19 = src/sh64/sysv.S src/sh64/ffi.c
|
||||
@PA_TRUE@am__append_20 = src/pa/linux.S src/pa/ffi.c
|
||||
@POWERPC_FREEBSD_TRUE@am__append_13 = src/powerpc/ffi.c src/powerpc/sysv.S src/powerpc/ppc_closure.S
|
||||
@ARM_TRUE@am__append_14 = src/arm/sysv.S src/arm/ffi.c
|
||||
@LIBFFI_CRIS_TRUE@am__append_15 = src/cris/sysv.S src/cris/ffi.c
|
||||
@FRV_TRUE@am__append_16 = src/frv/eabi.S src/frv/ffi.c
|
||||
@S390_TRUE@am__append_17 = src/s390/sysv.S src/s390/ffi.c
|
||||
@X86_64_TRUE@am__append_18 = src/x86/ffi64.c src/x86/unix64.S src/x86/ffi.c src/x86/sysv.S
|
||||
@SH_TRUE@am__append_19 = src/sh/sysv.S src/sh/ffi.c
|
||||
@SH64_TRUE@am__append_20 = src/sh64/sysv.S src/sh64/ffi.c
|
||||
@PA_TRUE@am__append_21 = src/pa/linux.S src/pa/ffi.c
|
||||
DIST_COMMON = README $(am__configure_deps) $(srcdir)/../compile \
|
||||
$(srcdir)/../config.guess $(srcdir)/../config.sub \
|
||||
$(srcdir)/../depcomp $(srcdir)/../install-sh \
|
||||
|
@ -111,36 +112,40 @@ am_libffi_la_OBJECTS = src/debug.lo src/prep_cif.lo src/types.lo \
|
|||
@POWERPC_DARWIN_TRUE@am__objects_12 = src/powerpc/ffi_darwin.lo \
|
||||
@POWERPC_DARWIN_TRUE@ src/powerpc/darwin.lo \
|
||||
@POWERPC_DARWIN_TRUE@ src/powerpc/darwin_closure.lo
|
||||
@ARM_TRUE@am__objects_13 = src/arm/sysv.lo src/arm/ffi.lo
|
||||
@LIBFFI_CRIS_TRUE@am__objects_14 = src/cris/sysv.lo src/cris/ffi.lo
|
||||
@FRV_TRUE@am__objects_15 = src/frv/eabi.lo src/frv/ffi.lo
|
||||
@S390_TRUE@am__objects_16 = src/s390/sysv.lo src/s390/ffi.lo
|
||||
@X86_64_TRUE@am__objects_17 = src/x86/ffi64.lo src/x86/unix64.lo \
|
||||
@POWERPC_FREEBSD_TRUE@am__objects_13 = src/powerpc/ffi.lo \
|
||||
@POWERPC_FREEBSD_TRUE@ src/powerpc/sysv.lo \
|
||||
@POWERPC_FREEBSD_TRUE@ src/powerpc/ppc_closure.lo
|
||||
@ARM_TRUE@am__objects_14 = src/arm/sysv.lo src/arm/ffi.lo
|
||||
@LIBFFI_CRIS_TRUE@am__objects_15 = src/cris/sysv.lo src/cris/ffi.lo
|
||||
@FRV_TRUE@am__objects_16 = src/frv/eabi.lo src/frv/ffi.lo
|
||||
@S390_TRUE@am__objects_17 = src/s390/sysv.lo src/s390/ffi.lo
|
||||
@X86_64_TRUE@am__objects_18 = src/x86/ffi64.lo src/x86/unix64.lo \
|
||||
@X86_64_TRUE@ src/x86/ffi.lo src/x86/sysv.lo
|
||||
@SH_TRUE@am__objects_18 = src/sh/sysv.lo src/sh/ffi.lo
|
||||
@SH64_TRUE@am__objects_19 = src/sh64/sysv.lo src/sh64/ffi.lo
|
||||
@PA_TRUE@am__objects_20 = src/pa/linux.lo src/pa/ffi.lo
|
||||
@SH_TRUE@am__objects_19 = src/sh/sysv.lo src/sh/ffi.lo
|
||||
@SH64_TRUE@am__objects_20 = src/sh64/sysv.lo src/sh64/ffi.lo
|
||||
@PA_TRUE@am__objects_21 = src/pa/linux.lo src/pa/ffi.lo
|
||||
nodist_libffi_la_OBJECTS = $(am__objects_1) $(am__objects_2) \
|
||||
$(am__objects_3) $(am__objects_4) $(am__objects_5) \
|
||||
$(am__objects_6) $(am__objects_7) $(am__objects_8) \
|
||||
$(am__objects_9) $(am__objects_10) $(am__objects_11) \
|
||||
$(am__objects_12) $(am__objects_13) $(am__objects_14) \
|
||||
$(am__objects_15) $(am__objects_16) $(am__objects_17) \
|
||||
$(am__objects_18) $(am__objects_19) $(am__objects_20)
|
||||
$(am__objects_18) $(am__objects_19) $(am__objects_20) \
|
||||
$(am__objects_21)
|
||||
libffi_la_OBJECTS = $(am_libffi_la_OBJECTS) \
|
||||
$(nodist_libffi_la_OBJECTS)
|
||||
libffi_convenience_la_LIBADD =
|
||||
am__objects_21 = src/debug.lo src/prep_cif.lo src/types.lo \
|
||||
am__objects_22 = src/debug.lo src/prep_cif.lo src/types.lo \
|
||||
src/raw_api.lo src/java_raw_api.lo
|
||||
am_libffi_convenience_la_OBJECTS = $(am__objects_21)
|
||||
am__objects_22 = $(am__objects_1) $(am__objects_2) $(am__objects_3) \
|
||||
am_libffi_convenience_la_OBJECTS = $(am__objects_22)
|
||||
am__objects_23 = $(am__objects_1) $(am__objects_2) $(am__objects_3) \
|
||||
$(am__objects_4) $(am__objects_5) $(am__objects_6) \
|
||||
$(am__objects_7) $(am__objects_8) $(am__objects_9) \
|
||||
$(am__objects_10) $(am__objects_11) $(am__objects_12) \
|
||||
$(am__objects_13) $(am__objects_14) $(am__objects_15) \
|
||||
$(am__objects_16) $(am__objects_17) $(am__objects_18) \
|
||||
$(am__objects_19) $(am__objects_20)
|
||||
nodist_libffi_convenience_la_OBJECTS = $(am__objects_22)
|
||||
$(am__objects_19) $(am__objects_20) $(am__objects_21)
|
||||
nodist_libffi_convenience_la_OBJECTS = $(am__objects_23)
|
||||
libffi_convenience_la_OBJECTS = $(am_libffi_convenience_la_OBJECTS) \
|
||||
$(nodist_libffi_convenience_la_OBJECTS)
|
||||
DEFAULT_INCLUDES = -I. -I$(srcdir) -I.
|
||||
|
@ -259,6 +264,8 @@ POWERPC_AIX_TRUE = @POWERPC_AIX_TRUE@
|
|||
POWERPC_DARWIN_FALSE = @POWERPC_DARWIN_FALSE@
|
||||
POWERPC_DARWIN_TRUE = @POWERPC_DARWIN_TRUE@
|
||||
POWERPC_FALSE = @POWERPC_FALSE@
|
||||
POWERPC_FREEBSD_FALSE = @POWERPC_FREEBSD_FALSE@
|
||||
POWERPC_FREEBSD_TRUE = @POWERPC_FREEBSD_TRUE@
|
||||
POWERPC_TRUE = @POWERPC_TRUE@
|
||||
RANLIB = @RANLIB@
|
||||
S390_FALSE = @S390_FALSE@
|
||||
|
@ -404,7 +411,8 @@ nodist_libffi_la_SOURCES = $(am__append_1) $(am__append_2) \
|
|||
$(am__append_9) $(am__append_10) $(am__append_11) \
|
||||
$(am__append_12) $(am__append_13) $(am__append_14) \
|
||||
$(am__append_15) $(am__append_16) $(am__append_17) \
|
||||
$(am__append_18) $(am__append_19) $(am__append_20)
|
||||
$(am__append_18) $(am__append_19) $(am__append_20) \
|
||||
$(am__append_21)
|
||||
libffi_convenience_la_SOURCES = $(libffi_la_SOURCES)
|
||||
nodist_libffi_convenience_la_SOURCES = $(nodist_libffi_la_SOURCES)
|
||||
AM_CFLAGS = -Wall -g -fexceptions
|
||||
|
|
22
libffi/configure
vendored
22
libffi/configure
vendored
|
@ -310,7 +310,7 @@ ac_includes_default="\
|
|||
# include <unistd.h>
|
||||
#endif"
|
||||
|
||||
ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS multi_basedir build build_cpu build_vendor build_os host host_cpu host_vendor host_os target target_cpu target_vendor target_os INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA CYGPATH_W PACKAGE VERSION ACLOCAL AUTOCONF AUTOMAKE AUTOHEADER MAKEINFO install_sh STRIP ac_ct_STRIP INSTALL_STRIP_PROGRAM mkdir_p AWK SET_MAKE am__leading_dot AMTAR am__tar am__untar CC ac_ct_CC EXEEXT OBJEXT DEPDIR am__include am__quote AMDEP_TRUE AMDEP_FALSE AMDEPBACKSLASH CCDEPMODE am__fastdepCC_TRUE am__fastdepCC_FALSE CFLAGS CCAS CCASFLAGS LN_S RANLIB ac_ct_RANLIB LIBTOOL MAINTAINER_MODE_TRUE MAINTAINER_MODE_FALSE MAINT CPP CPPFLAGS EGREP TESTSUBDIR_TRUE TESTSUBDIR_FALSE AM_RUNTESTFLAGS MIPS_IRIX_TRUE MIPS_IRIX_FALSE MIPS_LINUX_TRUE MIPS_LINUX_FALSE SPARC_TRUE SPARC_FALSE X86_TRUE X86_FALSE X86_WIN32_TRUE X86_WIN32_FALSE ALPHA_TRUE ALPHA_FALSE IA64_TRUE IA64_FALSE M32R_TRUE M32R_FALSE M68K_TRUE M68K_FALSE POWERPC_TRUE POWERPC_FALSE POWERPC_AIX_TRUE POWERPC_AIX_FALSE POWERPC_DARWIN_TRUE POWERPC_DARWIN_FALSE ARM_TRUE ARM_FALSE LIBFFI_CRIS_TRUE LIBFFI_CRIS_FALSE FRV_TRUE FRV_FALSE S390_TRUE S390_FALSE X86_64_TRUE X86_64_FALSE SH_TRUE SH_FALSE SH64_TRUE SH64_FALSE PA_TRUE PA_FALSE ALLOCA HAVE_LONG_DOUBLE TARGET TARGETDIR toolexecdir toolexeclibdir LIBOBJS LTLIBOBJS'
|
||||
ac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS multi_basedir build build_cpu build_vendor build_os host host_cpu host_vendor host_os target target_cpu target_vendor target_os INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA CYGPATH_W PACKAGE VERSION ACLOCAL AUTOCONF AUTOMAKE AUTOHEADER MAKEINFO install_sh STRIP ac_ct_STRIP INSTALL_STRIP_PROGRAM mkdir_p AWK SET_MAKE am__leading_dot AMTAR am__tar am__untar CC ac_ct_CC EXEEXT OBJEXT DEPDIR am__include am__quote AMDEP_TRUE AMDEP_FALSE AMDEPBACKSLASH CCDEPMODE am__fastdepCC_TRUE am__fastdepCC_FALSE CFLAGS CCAS CCASFLAGS LN_S RANLIB ac_ct_RANLIB LIBTOOL MAINTAINER_MODE_TRUE MAINTAINER_MODE_FALSE MAINT CPP CPPFLAGS EGREP TESTSUBDIR_TRUE TESTSUBDIR_FALSE AM_RUNTESTFLAGS MIPS_IRIX_TRUE MIPS_IRIX_FALSE MIPS_LINUX_TRUE MIPS_LINUX_FALSE SPARC_TRUE SPARC_FALSE X86_TRUE X86_FALSE X86_WIN32_TRUE X86_WIN32_FALSE ALPHA_TRUE ALPHA_FALSE IA64_TRUE IA64_FALSE M32R_TRUE M32R_FALSE M68K_TRUE M68K_FALSE POWERPC_TRUE POWERPC_FALSE POWERPC_AIX_TRUE POWERPC_AIX_FALSE POWERPC_DARWIN_TRUE POWERPC_DARWIN_FALSE POWERPC_FREEBSD_TRUE POWERPC_FREEBSD_FALSE ARM_TRUE ARM_FALSE LIBFFI_CRIS_TRUE LIBFFI_CRIS_FALSE FRV_TRUE FRV_FALSE S390_TRUE S390_FALSE X86_64_TRUE X86_64_FALSE SH_TRUE SH_FALSE SH64_TRUE SH64_FALSE PA_TRUE PA_FALSE ALLOCA HAVE_LONG_DOUBLE TARGET TARGETDIR toolexecdir toolexeclibdir LIBOBJS LTLIBOBJS'
|
||||
ac_subst_files=''
|
||||
|
||||
# Initialize some variables set by options.
|
||||
|
@ -5403,6 +5403,7 @@ powerpc*-*-linux* | powerpc-*-sysv*) TARGET=POWERPC; TARGETDIR=powerpc;;
|
|||
powerpc-*-beos*) TARGET=POWERPC; TARGETDIR=powerpc;;
|
||||
powerpc-*-darwin*) TARGET=POWERPC_DARWIN; TARGETDIR=powerpc;;
|
||||
powerpc-*-aix*) TARGET=POWERPC_AIX; TARGETDIR=powerpc;;
|
||||
powerpc-*-freebsd*) TARGET=POWERPC_FREEBSD; TARGETDIR=powerpc;;
|
||||
powerpc*-*-rtems*) TARGET=POWERPC; TARGETDIR=powerpc;;
|
||||
rs6000-*-aix*) TARGET=POWERPC_AIX; TARGETDIR=powerpc;;
|
||||
arm*-*-linux-*) TARGET=ARM; TARGETDIR=arm;;
|
||||
|
@ -5548,6 +5549,16 @@ fi
|
|||
|
||||
|
||||
|
||||
if test x$TARGET = xPOWERPC_FREEBSD; then
|
||||
POWERPC_FREEBSD_TRUE=
|
||||
POWERPC_FREEBSD_FALSE='#'
|
||||
else
|
||||
POWERPC_FREEBSD_TRUE='#'
|
||||
POWERPC_FREEBSD_FALSE=
|
||||
fi
|
||||
|
||||
|
||||
|
||||
if test x$TARGET = xARM; then
|
||||
ARM_TRUE=
|
||||
ARM_FALSE='#'
|
||||
|
@ -7799,6 +7810,13 @@ echo "$as_me: error: conditional \"POWERPC_DARWIN\" was never defined.
|
|||
Usually this means the macro was only invoked conditionally." >&2;}
|
||||
{ (exit 1); exit 1; }; }
|
||||
fi
|
||||
if test -z "${POWERPC_FREEBSD_TRUE}" && test -z "${POWERPC_FREEBSD_FALSE}"; then
|
||||
{ { echo "$as_me:$LINENO: error: conditional \"POWERPC_FREEBSD\" was never defined.
|
||||
Usually this means the macro was only invoked conditionally." >&5
|
||||
echo "$as_me: error: conditional \"POWERPC_FREEBSD\" was never defined.
|
||||
Usually this means the macro was only invoked conditionally." >&2;}
|
||||
{ (exit 1); exit 1; }; }
|
||||
fi
|
||||
if test -z "${ARM_TRUE}" && test -z "${ARM_FALSE}"; then
|
||||
{ { echo "$as_me:$LINENO: error: conditional \"ARM\" was never defined.
|
||||
Usually this means the macro was only invoked conditionally." >&5
|
||||
|
@ -8498,6 +8516,8 @@ s,@POWERPC_AIX_TRUE@,$POWERPC_AIX_TRUE,;t t
|
|||
s,@POWERPC_AIX_FALSE@,$POWERPC_AIX_FALSE,;t t
|
||||
s,@POWERPC_DARWIN_TRUE@,$POWERPC_DARWIN_TRUE,;t t
|
||||
s,@POWERPC_DARWIN_FALSE@,$POWERPC_DARWIN_FALSE,;t t
|
||||
s,@POWERPC_FREEBSD_TRUE@,$POWERPC_FREEBSD_TRUE,;t t
|
||||
s,@POWERPC_FREEBSD_FALSE@,$POWERPC_FREEBSD_FALSE,;t t
|
||||
s,@ARM_TRUE@,$ARM_TRUE,;t t
|
||||
s,@ARM_FALSE@,$ARM_FALSE,;t t
|
||||
s,@LIBFFI_CRIS_TRUE@,$LIBFFI_CRIS_TRUE,;t t
|
||||
|
|
|
@ -68,6 +68,7 @@ powerpc*-*-linux* | powerpc-*-sysv*) TARGET=POWERPC; TARGETDIR=powerpc;;
|
|||
powerpc-*-beos*) TARGET=POWERPC; TARGETDIR=powerpc;;
|
||||
powerpc-*-darwin*) TARGET=POWERPC_DARWIN; TARGETDIR=powerpc;;
|
||||
powerpc-*-aix*) TARGET=POWERPC_AIX; TARGETDIR=powerpc;;
|
||||
powerpc-*-freebsd*) TARGET=POWERPC_FREEBSD; TARGETDIR=powerpc;;
|
||||
powerpc*-*-rtems*) TARGET=POWERPC; TARGETDIR=powerpc;;
|
||||
rs6000-*-aix*) TARGET=POWERPC_AIX; TARGETDIR=powerpc;;
|
||||
arm*-*-linux-*) TARGET=ARM; TARGETDIR=arm;;
|
||||
|
@ -101,6 +102,7 @@ AM_CONDITIONAL(M68K, test x$TARGET = xM68K)
|
|||
AM_CONDITIONAL(POWERPC, test x$TARGET = xPOWERPC)
|
||||
AM_CONDITIONAL(POWERPC_AIX, test x$TARGET = xPOWERPC_AIX)
|
||||
AM_CONDITIONAL(POWERPC_DARWIN, test x$TARGET = xPOWERPC_DARWIN)
|
||||
AM_CONDITIONAL(POWERPC_FREEBSD, test x$TARGET = xPOWERPC_FREEBSD)
|
||||
AM_CONDITIONAL(ARM, test x$TARGET = xARM)
|
||||
AM_CONDITIONAL(LIBFFI_CRIS, test x$TARGET = xLIBFFI_CRIS)
|
||||
AM_CONDITIONAL(FRV, test x$TARGET = xFRV)
|
||||
|
|
|
@ -137,6 +137,8 @@ POWERPC_AIX_TRUE = @POWERPC_AIX_TRUE@
|
|||
POWERPC_DARWIN_FALSE = @POWERPC_DARWIN_FALSE@
|
||||
POWERPC_DARWIN_TRUE = @POWERPC_DARWIN_TRUE@
|
||||
POWERPC_FALSE = @POWERPC_FALSE@
|
||||
POWERPC_FREEBSD_FALSE = @POWERPC_FREEBSD_FALSE@
|
||||
POWERPC_FREEBSD_TRUE = @POWERPC_FREEBSD_TRUE@
|
||||
POWERPC_TRUE = @POWERPC_TRUE@
|
||||
RANLIB = @RANLIB@
|
||||
S390_FALSE = @S390_FALSE@
|
||||
|
|
|
@ -41,6 +41,7 @@ extern void hidden ffi_closure_LINUX64(void);
|
|||
|
||||
enum {
|
||||
/* The assembly depends on these exact flags. */
|
||||
FLAG_RETURNS_SMST = 1 << (31-31), /* Used for FFI_SYSV small structs. */
|
||||
FLAG_RETURNS_NOTHING = 1 << (31-30), /* These go in cr7 */
|
||||
FLAG_RETURNS_FP = 1 << (31-29),
|
||||
FLAG_RETURNS_64BITS = 1 << (31-28),
|
||||
|
@ -462,6 +463,7 @@ ffi_status ffi_prep_cif_machdep(ffi_cif *cif)
|
|||
unsigned flags = 0;
|
||||
unsigned struct_copy_size = 0;
|
||||
unsigned type = cif->rtype->type;
|
||||
unsigned size = cif->rtype->size;
|
||||
|
||||
if (cif->abi != FFI_LINUX64)
|
||||
{
|
||||
|
@ -518,15 +520,30 @@ ffi_status ffi_prep_cif_machdep(ffi_cif *cif)
|
|||
break;
|
||||
|
||||
case FFI_TYPE_STRUCT:
|
||||
if (cif->abi != FFI_GCC_SYSV && cif->abi != FFI_LINUX64)
|
||||
if (cif->abi == FFI_SYSV)
|
||||
{
|
||||
if (cif->rtype->size <= 4)
|
||||
break;
|
||||
else if (cif->rtype->size <= 8)
|
||||
{
|
||||
flags |= FLAG_RETURNS_64BITS;
|
||||
/* The final SYSV ABI says that structures smaller or equal 8 bytes
|
||||
are returned in r3/r4. The FFI_GCC_SYSV ABI instead returns them
|
||||
in memory. */
|
||||
|
||||
/* Treat structs with size <= 8 bytes. */
|
||||
if (size <= 8) {
|
||||
flags |= FLAG_RETURNS_SMST;
|
||||
/* These structs are returned in r3. We pack the type and the
|
||||
precalculated shift value (needed in the sysv.S) into flags.
|
||||
The same applies for the structs returned in r3/r4. */
|
||||
if (size <= 4) {
|
||||
flags |= 1 << (31 - FFI_SYSV_TYPE_SMALL_STRUCT - 1 )
|
||||
| (8 * (4 - size) << 4);
|
||||
break;
|
||||
}
|
||||
/* These structs are returned in r3 and r4. See above. */
|
||||
if (size <= 8) {
|
||||
flags |= 1 << (31 - FFI_SYSV_TYPE_SMALL_STRUCT - 2 )
|
||||
| (8 * (8 - size) << 4);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
/* else fall through. */
|
||||
#if FFI_TYPE_LONGDOUBLE != FFI_TYPE_DOUBLE
|
||||
|
@ -573,7 +590,7 @@ ffi_status ffi_prep_cif_machdep(ffi_cif *cif)
|
|||
/* 'long long' arguments are passed as two words, but
|
||||
either both words must fit in registers or both go
|
||||
on the stack. If they go on the stack, they must
|
||||
be 8-byte-aligned.
|
||||
be 8-byte-aligned.
|
||||
|
||||
Also, only certain register pairs can be used for
|
||||
passing long long int -- specifically (r3,r4), (r5,r6),
|
||||
|
@ -770,7 +787,7 @@ ffi_prep_closure (ffi_closure* closure,
|
|||
#else
|
||||
unsigned int *tramp;
|
||||
|
||||
FFI_ASSERT (cif->abi == FFI_GCC_SYSV);
|
||||
FFI_ASSERT (cif->abi == FFI_GCC_SYSV || cif->abi == FFI_SYSV);
|
||||
|
||||
tramp = (unsigned int *) &closure->tramp[0];
|
||||
tramp[0] = 0x7c0802a6; /* mflr r0 */
|
||||
|
@ -829,20 +846,27 @@ ffi_closure_helper_SYSV (ffi_closure* closure, void * rvalue,
|
|||
long ng; /* number of general registers already used */
|
||||
ffi_cif * cif;
|
||||
double temp;
|
||||
unsigned size;
|
||||
|
||||
cif = closure->cif;
|
||||
avalue = alloca(cif->nargs * sizeof(void *));
|
||||
size = cif->rtype->size;
|
||||
|
||||
nf = 0;
|
||||
ng = 0;
|
||||
|
||||
/* Copy the caller's structure return value address so that the closure
|
||||
returns the data directly to the caller. */
|
||||
returns the data directly to the caller.
|
||||
For FFI_SYSV the result is passed in r3/r4 if the struct size is less
|
||||
or equal 8 bytes. */
|
||||
|
||||
if (cif->rtype->type == FFI_TYPE_STRUCT)
|
||||
{
|
||||
rvalue = (void *) *pgr;
|
||||
ng++;
|
||||
pgr++;
|
||||
if (!((cif->abi == FFI_SYSV) && (size <= 8))) {
|
||||
rvalue = (void *) *pgr;
|
||||
ng++;
|
||||
pgr++;
|
||||
}
|
||||
}
|
||||
|
||||
i = 0;
|
||||
|
@ -986,7 +1010,12 @@ ffi_closure_helper_SYSV (ffi_closure* closure, void * rvalue,
|
|||
|
||||
(closure->fun) (cif, rvalue, avalue, closure->user_data);
|
||||
|
||||
/* Tell ffi_closure_SYSV how to perform return type promotions. */
|
||||
/* Tell ffi_closure_SYSV how to perform return type promotions.
|
||||
Because the FFI_SYSV ABI returns the structures <= 8 bytes in r3/r4
|
||||
we have to tell ffi_closure_SYSV how to treat them. */
|
||||
if (cif->abi == FFI_SYSV && cif->rtype->type == FFI_TYPE_STRUCT
|
||||
&& size <= 8)
|
||||
return FFI_SYSV_TYPE_SMALL_STRUCT + size;
|
||||
return cif->rtype->type;
|
||||
|
||||
}
|
||||
|
|
|
@ -62,6 +62,13 @@ typedef enum ffi_abi {
|
|||
FFI_DEFAULT_ABI = FFI_DARWIN,
|
||||
#endif
|
||||
|
||||
#ifdef POWERPC_FREEBSD
|
||||
FFI_SYSV,
|
||||
FFI_GCC_SYSV,
|
||||
FFI_LINUX64,
|
||||
FFI_DEFAULT_ABI = FFI_SYSV,
|
||||
#endif
|
||||
|
||||
FFI_LAST_ABI = FFI_DEFAULT_ABI + 1
|
||||
} ffi_abi;
|
||||
#endif
|
||||
|
@ -71,6 +78,9 @@ typedef enum ffi_abi {
|
|||
#define FFI_CLOSURES 1
|
||||
#define FFI_NATIVE_RAW_API 0
|
||||
|
||||
/* Needed for FFI_SYSV small structure returns. */
|
||||
#define FFI_SYSV_TYPE_SMALL_STRUCT (FFI_TYPE_LAST)
|
||||
|
||||
#if defined(POWERPC64) || defined(POWERPC_AIX)
|
||||
#define FFI_TRAMPOLINE_SIZE 24
|
||||
#else /* POWERPC || POWERPC_AIX */
|
||||
|
|
|
@ -63,9 +63,22 @@ ENTRY(ffi_closure_SYSV)
|
|||
# so use it to look up in a table
|
||||
# so we know how to deal with each type
|
||||
|
||||
# Extract the size of the return type for small structures.
|
||||
# Then calculate (4 - size) and multiply the result by 8.
|
||||
# This gives the value needed for the shift operation below.
|
||||
# This part is only needed for FFI_SYSV and small structures.
|
||||
addi %r5,%r3,-(FFI_SYSV_TYPE_SMALL_STRUCT)
|
||||
cmpwi cr0,%r5,4
|
||||
ble cr0,.Lnext
|
||||
addi %r5,%r5,-4
|
||||
.Lnext:
|
||||
addi %r5,%r5,-4
|
||||
neg %r5,%r5
|
||||
slwi %r5,%r5,3
|
||||
|
||||
# look up the proper starting point in table
|
||||
# by using return type as offset
|
||||
addi %r5,%r1,112 # get pointer to results area
|
||||
addi %r6,%r1,112 # get pointer to results area
|
||||
bl .Lget_ret_type0_addr # get pointer to .Lret_type0 into LR
|
||||
mflr %r4 # move to r4
|
||||
slwi %r3,%r3,4 # now multiply return type by 16
|
||||
|
@ -94,85 +107,85 @@ ENTRY(ffi_closure_SYSV)
|
|||
|
||||
# case FFI_TYPE_INT
|
||||
.Lret_type1:
|
||||
lwz %r3,0(%r5)
|
||||
lwz %r3,0(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_TYPE_FLOAT
|
||||
.Lret_type2:
|
||||
lfs %f1,0(%r5)
|
||||
lfs %f1,0(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_TYPE_DOUBLE
|
||||
.Lret_type3:
|
||||
lfd %f1,0(%r5)
|
||||
lfd %f1,0(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_TYPE_LONGDOUBLE
|
||||
.Lret_type4:
|
||||
lfd %f1,0(%r5)
|
||||
lfd %f1,0(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_TYPE_UINT8
|
||||
.Lret_type5:
|
||||
lbz %r3,3(%r5)
|
||||
lbz %r3,3(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_TYPE_SINT8
|
||||
.Lret_type6:
|
||||
lbz %r3,3(%r5)
|
||||
lbz %r3,3(%r6)
|
||||
extsb %r3,%r3
|
||||
b .Lfinish
|
||||
nop
|
||||
|
||||
# case FFI_TYPE_UINT16
|
||||
.Lret_type7:
|
||||
lhz %r3,2(%r5)
|
||||
lhz %r3,2(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_TYPE_SINT16
|
||||
.Lret_type8:
|
||||
lha %r3,2(%r5)
|
||||
lha %r3,2(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_TYPE_UINT32
|
||||
.Lret_type9:
|
||||
lwz %r3,0(%r5)
|
||||
lwz %r3,0(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_TYPE_SINT32
|
||||
.Lret_type10:
|
||||
lwz %r3,0(%r5)
|
||||
lwz %r3,0(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_TYPE_UINT64
|
||||
.Lret_type11:
|
||||
lwz %r3,0(%r5)
|
||||
lwz %r4,4(%r5)
|
||||
lwz %r3,0(%r6)
|
||||
lwz %r4,4(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
|
||||
# case FFI_TYPE_SINT64
|
||||
.Lret_type12:
|
||||
lwz %r3,0(%r5)
|
||||
lwz %r4,4(%r5)
|
||||
lwz %r3,0(%r6)
|
||||
lwz %r4,4(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
|
||||
|
@ -185,11 +198,76 @@ ENTRY(ffi_closure_SYSV)
|
|||
|
||||
# case FFI_TYPE_POINTER
|
||||
.Lret_type14:
|
||||
lwz %r3,0(%r5)
|
||||
lwz %r3,0(%r6)
|
||||
b .Lfinish
|
||||
nop
|
||||
nop
|
||||
|
||||
# The return types below are only used when the ABI type is FFI_SYSV.
|
||||
# case FFI_SYSV_TYPE_SMALL_STRUCT + 1. One byte struct.
|
||||
.Lret_type15:
|
||||
# fall through.
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_SYSV_TYPE_SMALL_STRUCT + 2. Two byte struct.
|
||||
.Lret_type16:
|
||||
# fall through.
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_SYSV_TYPE_SMALL_STRUCT + 3. Three byte struct.
|
||||
.Lret_type17:
|
||||
# fall through.
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_SYSV_TYPE_SMALL_STRUCT + 4. Four byte struct.
|
||||
.Lret_type18:
|
||||
# this one handles the structs from above too.
|
||||
lwz %r3,0(%r6)
|
||||
srw %r3,%r3,%r5
|
||||
b .Lfinish
|
||||
nop
|
||||
|
||||
# case FFI_SYSV_TYPE_SMALL_STRUCT + 5. Five byte struct.
|
||||
.Lret_type19:
|
||||
# fall through.
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_SYSV_TYPE_SMALL_STRUCT + 6. Six byte struct.
|
||||
.Lret_type20:
|
||||
# fall through.
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_SYSV_TYPE_SMALL_STRUCT + 7. Seven byte struct.
|
||||
.Lret_type21:
|
||||
# fall through.
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
nop
|
||||
|
||||
# case FFI_SYSV_TYPE_SMALL_STRUCT + 8. Eight byte struct.
|
||||
.Lret_type22:
|
||||
# this one handles the above unhandled structs.
|
||||
lwz %r3,0(%r6)
|
||||
lwz %r4,4(%r6)
|
||||
bl __lshrdi3 # libgcc function to shift r3/r4, shift value in r5.
|
||||
b .Lfinish
|
||||
|
||||
# case done
|
||||
.Lfinish:
|
||||
|
||||
|
|
|
@ -99,6 +99,7 @@ ENTRY(ffi_call_SYSV)
|
|||
|
||||
/* Now, deal with the return value. */
|
||||
mtcrf 0x01,%r31
|
||||
bt- 31,L(small_struct_return_value)
|
||||
bt- 30,L(done_return_value)
|
||||
bt- 29,L(fp_return_value)
|
||||
stw %r3,0(%r30)
|
||||
|
@ -124,6 +125,27 @@ L(fp_return_value):
|
|||
L(float_return_value):
|
||||
stfs %f1,0(%r30)
|
||||
b L(done_return_value)
|
||||
|
||||
L(small_struct_return_value):
|
||||
mtcrf 0x10,%r31 /* cr3 */
|
||||
bt- 15,L(smst_one_register)
|
||||
mtcrf 0x08,%r31 /* cr4 */
|
||||
bt- 16,L(smst_two_register)
|
||||
b L(done_return_value)
|
||||
|
||||
L(smst_one_register):
|
||||
rlwinm %r5,%r31,5+23,32-5,31 /* Extract the value to shift. */
|
||||
slw %r3,%r3,%r5
|
||||
stw %r3,0(%r30)
|
||||
b L(done_return_value)
|
||||
L(smst_two_register):
|
||||
rlwinm %r5,%r31,5+23,32-5,31 /* Extract the value to shift. */
|
||||
bl __ashldi3 /* libgcc function to shift r3/r4,
|
||||
shift value in r5. */
|
||||
stw %r3,0(%r30)
|
||||
stw %r4,4(%r30)
|
||||
b L(done_return_value)
|
||||
|
||||
.LFE1:
|
||||
END(ffi_call_SYSV)
|
||||
|
||||
|
|
|
@ -123,6 +123,8 @@ POWERPC_AIX_TRUE = @POWERPC_AIX_TRUE@
|
|||
POWERPC_DARWIN_FALSE = @POWERPC_DARWIN_FALSE@
|
||||
POWERPC_DARWIN_TRUE = @POWERPC_DARWIN_TRUE@
|
||||
POWERPC_FALSE = @POWERPC_FALSE@
|
||||
POWERPC_FREEBSD_FALSE = @POWERPC_FREEBSD_FALSE@
|
||||
POWERPC_FREEBSD_TRUE = @POWERPC_FREEBSD_TRUE@
|
||||
POWERPC_TRUE = @POWERPC_TRUE@
|
||||
RANLIB = @RANLIB@
|
||||
S390_FALSE = @S390_FALSE@
|
||||
|
|
Loading…
Add table
Reference in a new issue