diff --git a/.gitattributes b/.gitattributes new file mode 100644 index 0000000..c9839d6 --- /dev/null +++ b/.gitattributes @@ -0,0 +1 @@ +*.a binary diff --git a/buildenv b/buildenv index 54e6b2f..ca4a527 100644 --- a/buildenv +++ b/buildenv @@ -17,7 +17,7 @@ export ZOPEN_BUILD_LINE="STABLE" ## Required IF ZOPEN_BUILD_LINE='STABLE' export ZOPEN_STABLE_URL="https://cache.ruby-lang.org/pub/ruby/${RUBY_MAJOR}/ruby-${RUBY_VERSION}.tar.gz" # Specify the stable build URL (either git or tarball) -export ZOPEN_STABLE_DEPS="openssl make zoslib libyaml" # Specify the stable build dependencies. +export ZOPEN_STABLE_DEPS="openssl make zoslib libyaml coreutils grep pkgconfig zlib gawk" # Specify the stable build dependencies. ## Required IF ZOPEN_BUILD_LINE='DEV' export ZOPEN_DEV_URL="" # Specify the dev build URL @@ -34,6 +34,8 @@ export ZOPEN_RUNTIME_DEPS="" ## Current available prerequisites: zos24 zos25 zos31 procfs (see https://github.com/zopencommunity/meta/blob/main/include/prereq.sh for a current list) export ZOPEN_SYSTEM_PREREQ="" +export LD="clang" +export ZOPEN_SKIP_ZOSLIB_ENV_HOOK="skip" ### ### Build stage control environment variables @@ -66,9 +68,7 @@ zopen_check_results() zopen_get_version() { - # Modify to echo the version of your tool/library - # Rather than hardcoding the version, obtain the version by running the tool/library - echo "1.0.0" + ./ruby --version | awk -F" " '{print $2}' } @@ -126,9 +126,10 @@ zopen_get_version() ## This function runs before the 'install' step of the build is run. #} -#zopen_post_install(){ +zopen_post_install(){ ## This function runs after the 'install' step of the build is run. -#} + chtag -b $1/bin/ruby +} #zopen_pre_patch(){ ## This function runs before the 'patch' step of the build is run. @@ -143,11 +144,11 @@ zopen_get_version() ### Optional build control variables ### -#export ZOPEN_EXTRA_CFLAGS="" ## C compiler flags to append to CFLAGS (defaults to ''). -#export ZOPEN_EXTRA_CPPFLAGS="" ## C,C++ pre-processor flags to append to CPPFLAGS (defaults to '') +export ZOPEN_EXTRA_CFLAGS="-mzos-target=zosv3r1 -I${ZOPEN_ROOT}/libffi_built/include/" ## C compiler flags to append to CFLAGS (defaults to ''). +export ZOPEN_EXTRA_CPPFLAGS="-D_POSIX_C_SOURCE=200809L -D__XPLAT=1 -D_OPEN_SYS_IF_EXT -D_OPEN_SYS_SOCK_EXT3 -D_OPEN_SYS_SOCK_IPV6" ## C,C++ pre-processor flags to append to CPPFLAGS (defaults to '') #export ZOPEN_EXTRA_CXXFLAGS="" ## C++ compiler flags to append to CXXFLAGS (defaults to '') -#export ZOPEN_EXTRA_LDFLAGS="" ## C,C++ linker flags to append to LDFLAGS (defaults to '') -#export ZOPEN_EXTRA_LIBS="" ## C,C++ libraries to append to LIBS (defaults to '') +export ZOPEN_EXTRA_LDFLAGS="-L${ZOPEN_ROOT}/libffi_built/lib" ## C,C++ linker flags to append to LDFLAGS (defaults to '') +export ZOPEN_EXTRA_LIBS="-lffi" ## C,C++ libraries to append to LIBS (defaults to '') #export ZOPEN_BOOTSTRAP_OPTS="" ## Options to pass to bootstrap program (defaults to '') #export ZOPEN_CHECK_MINIMAL="" ## Check program will not be passed CFLAGS, LDFLAGS, CPPFLAGS options but will get them from env vars. #export ZOPEN_CHECK_OPTS="" ## Options to pass to check program (defaults to 'check') @@ -155,9 +156,9 @@ zopen_get_version() #export ZOPEN_CLEAN_OPTS="" ## Options to pass to clean up program (defaults to 'clean') #export ZOPEN_CONFIGURE_MINIMAL="" ## Configuration program will not be passed CFLAGS, LDFLAGS, CPPFLAGS options but will get them from env vars. #export ZOPEN_CONFIGURE_OPTS="" ## Options to pass to configuration program (defaults to '--prefix=') -#export ZOPEN_EXTRA_CONFIGURE_OPTS="" ## Extra configure options to pass to configuration program. (defaults to '') +export ZOPEN_EXTRA_CONFIGURE_OPTS="--disable-shared --disable-dln --disable-yjit --disable-rjit --without-valgrind --with-static-linked-ext" ## Extra configure options to pass to configuration program. (defaults to '') #export ZOPEN_INSTALL_OPTS="" ## Options to pass to installation program (defaults to 'install') -#export ZOPEN_MAKE_MINIMAL="" ## Build program will not be passed CFLAGS, LDFLAGS, CPPFLAGS options but will get them from env vars. +export ZOPEN_MAKE_MINIMAL="yes" ## Build program will not be passed CFLAGS, LDFLAGS, CPPFLAGS options but will get them from env vars. #export ZOPEN_MAKE_OPTS="" ## Options to pass to build program (defaults to '-j') #export ZOPEN_PATCH_DIR="" ## Specify directory from which patches should be applied. diff --git a/libffi_built/include/ffi.h b/libffi_built/include/ffi.h new file mode 100644 index 0000000..cde9753 --- /dev/null +++ b/libffi_built/include/ffi.h @@ -0,0 +1,530 @@ +/* -----------------------------------------------------------------*-C-*- + libffi 3.4.5 + - Copyright (c) 2011, 2014, 2019, 2021, 2022 Anthony Green + - Copyright (c) 1996-2003, 2007, 2008 Red Hat, Inc. + + Permission is hereby granted, free of charge, to any person + obtaining a copy of this software and associated documentation + files (the ``Software''), to deal in the Software without + restriction, including without limitation the rights to use, copy, + modify, merge, publish, distribute, sublicense, and/or sell copies + of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: + + The above copyright notice and this permission notice shall be + included in all copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED ``AS IS'', WITHOUT WARRANTY OF ANY KIND, + EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + DEALINGS IN THE SOFTWARE. + + ----------------------------------------------------------------------- */ + +/* ------------------------------------------------------------------- + Most of the API is documented in doc/libffi.texi. + + The raw API is designed to bypass some of the argument packing and + unpacking on architectures for which it can be avoided. Routines + are provided to emulate the raw API if the underlying platform + doesn't allow faster implementation. + + More details on the raw API can be found in: + + http://gcc.gnu.org/ml/java/1999-q3/msg00138.html + + and + + http://gcc.gnu.org/ml/java/1999-q3/msg00174.html + -------------------------------------------------------------------- */ + +#ifndef LIBFFI_H +#define LIBFFI_H + +#ifdef __cplusplus +extern "C" { +#endif + +/* Specify which architecture libffi is configured for. */ +#ifndef ZOS +#define ZOS +#endif + +/* ---- System configuration information --------------------------------- */ + +/* If these change, update src/mips/ffitarget.h. */ +#define FFI_TYPE_VOID 0 +#define FFI_TYPE_INT 1 +#define FFI_TYPE_FLOAT 2 +#define FFI_TYPE_DOUBLE 3 +#if 1 +#define FFI_TYPE_LONGDOUBLE 4 +#else +#define FFI_TYPE_LONGDOUBLE FFI_TYPE_DOUBLE +#endif +#define FFI_TYPE_UINT8 5 +#define FFI_TYPE_SINT8 6 +#define FFI_TYPE_UINT16 7 +#define FFI_TYPE_SINT16 8 +#define FFI_TYPE_UINT32 9 +#define FFI_TYPE_SINT32 10 +#define FFI_TYPE_UINT64 11 +#define FFI_TYPE_SINT64 12 +#define FFI_TYPE_STRUCT 13 +#define FFI_TYPE_POINTER 14 +#define FFI_TYPE_COMPLEX 15 + +/* This should always refer to the last type code (for sanity checks). */ +#define FFI_TYPE_LAST FFI_TYPE_COMPLEX + +#include + +#ifndef LIBFFI_ASM + +#if defined(_MSC_VER) && !defined(__clang__) +#define __attribute__(X) +#endif + +#include +#include + +/* LONG_LONG_MAX is not always defined (not if STRICT_ANSI, for example). + But we can find it either under the correct ANSI name, or under GNU + C's internal name. */ + +#define FFI_64_BIT_MAX 9223372036854775807 + +#ifdef LONG_LONG_MAX +# define FFI_LONG_LONG_MAX LONG_LONG_MAX +#else +# ifdef LLONG_MAX +# define FFI_LONG_LONG_MAX LLONG_MAX +# ifdef _AIX52 /* or newer has C99 LLONG_MAX */ +# undef FFI_64_BIT_MAX +# define FFI_64_BIT_MAX 9223372036854775807LL +# endif /* _AIX52 or newer */ +# else +# ifdef __GNUC__ +# define FFI_LONG_LONG_MAX __LONG_LONG_MAX__ +# endif +# ifdef _AIX /* AIX 5.1 and earlier have LONGLONG_MAX */ +# ifndef __PPC64__ +# if defined (__IBMC__) || defined (__IBMCPP__) +# define FFI_LONG_LONG_MAX LONGLONG_MAX +# endif +# endif /* __PPC64__ */ +# undef FFI_64_BIT_MAX +# define FFI_64_BIT_MAX 9223372036854775807LL +# endif +# endif +#endif + +/* The closure code assumes that this works on pointers, i.e. a size_t + can hold a pointer. */ + +typedef struct _ffi_type +{ + size_t size; + unsigned short alignment; + unsigned short type; + struct _ffi_type **elements; +} ffi_type; + +/* Need minimal decorations for DLLs to work on Windows. GCC has + autoimport and autoexport. Always mark externally visible symbols + as dllimport for MSVC clients, even if it means an extra indirection + when using the static version of the library. + Besides, as a workaround, they can define FFI_BUILDING if they + *know* they are going to link with the static library. */ +#if defined _MSC_VER && !defined(FFI_STATIC_BUILD) +# if defined FFI_BUILDING_DLL /* Building libffi.DLL with msvcc.sh */ +# define FFI_API __declspec(dllexport) +# else /* Importing libffi.DLL */ +# define FFI_API __declspec(dllimport) +# endif +#else +# define FFI_API +#endif + +/* The externally visible type declarations also need the MSVC DLL + decorations, or they will not be exported from the object file. */ +#if defined LIBFFI_HIDE_BASIC_TYPES +# define FFI_EXTERN FFI_API +#else +# define FFI_EXTERN extern FFI_API +#endif + +#ifndef LIBFFI_HIDE_BASIC_TYPES +#if SCHAR_MAX == 127 +# define ffi_type_uchar ffi_type_uint8 +# define ffi_type_schar ffi_type_sint8 +#else + #error "char size not supported" +#endif + +#if SHRT_MAX == 32767 +# define ffi_type_ushort ffi_type_uint16 +# define ffi_type_sshort ffi_type_sint16 +#elif SHRT_MAX == 2147483647 +# define ffi_type_ushort ffi_type_uint32 +# define ffi_type_sshort ffi_type_sint32 +#else + #error "short size not supported" +#endif + +#if INT_MAX == 32767 +# define ffi_type_uint ffi_type_uint16 +# define ffi_type_sint ffi_type_sint16 +#elif INT_MAX == 2147483647 +# define ffi_type_uint ffi_type_uint32 +# define ffi_type_sint ffi_type_sint32 +#elif INT_MAX == 9223372036854775807 +# define ffi_type_uint ffi_type_uint64 +# define ffi_type_sint ffi_type_sint64 +#else + #error "int size not supported" +#endif + +#if LONG_MAX == 2147483647 +# if FFI_LONG_LONG_MAX != FFI_64_BIT_MAX + #error "no 64-bit data type supported" +# endif +#elif LONG_MAX != FFI_64_BIT_MAX + #error "long size not supported" +#endif + +#if LONG_MAX == 2147483647 +# define ffi_type_ulong ffi_type_uint32 +# define ffi_type_slong ffi_type_sint32 +#elif LONG_MAX == FFI_64_BIT_MAX +# define ffi_type_ulong ffi_type_uint64 +# define ffi_type_slong ffi_type_sint64 +#else + #error "long size not supported" +#endif + +/* These are defined in types.c. */ +FFI_EXTERN ffi_type ffi_type_void; +FFI_EXTERN ffi_type ffi_type_uint8; +FFI_EXTERN ffi_type ffi_type_sint8; +FFI_EXTERN ffi_type ffi_type_uint16; +FFI_EXTERN ffi_type ffi_type_sint16; +FFI_EXTERN ffi_type ffi_type_uint32; +FFI_EXTERN ffi_type ffi_type_sint32; +FFI_EXTERN ffi_type ffi_type_uint64; +FFI_EXTERN ffi_type ffi_type_sint64; +FFI_EXTERN ffi_type ffi_type_float; +FFI_EXTERN ffi_type ffi_type_double; +FFI_EXTERN ffi_type ffi_type_pointer; + +#if 1 +FFI_EXTERN ffi_type ffi_type_longdouble; +#else +#define ffi_type_longdouble ffi_type_double +#endif + +#ifdef FFI_TARGET_HAS_COMPLEX_TYPE +FFI_EXTERN ffi_type ffi_type_complex_float; +FFI_EXTERN ffi_type ffi_type_complex_double; +#if 1 +FFI_EXTERN ffi_type ffi_type_complex_longdouble; +#else +#define ffi_type_complex_longdouble ffi_type_complex_double +#endif +#endif +#endif /* LIBFFI_HIDE_BASIC_TYPES */ + +typedef enum { + FFI_OK = 0, + FFI_BAD_TYPEDEF, + FFI_BAD_ABI, + FFI_BAD_ARGTYPE +} ffi_status; + +typedef struct { + ffi_abi abi; + unsigned nargs; + ffi_type **arg_types; + ffi_type *rtype; + unsigned bytes; + unsigned flags; +#ifdef FFI_EXTRA_CIF_FIELDS + FFI_EXTRA_CIF_FIELDS; +#endif +} ffi_cif; + +/* ---- Definitions for the raw API -------------------------------------- */ + +#ifndef FFI_SIZEOF_ARG +# if LONG_MAX == 2147483647 +# define FFI_SIZEOF_ARG 4 +# elif LONG_MAX == FFI_64_BIT_MAX +# define FFI_SIZEOF_ARG 8 +# endif +#endif + +#ifndef FFI_SIZEOF_JAVA_RAW +# define FFI_SIZEOF_JAVA_RAW FFI_SIZEOF_ARG +#endif + +typedef union { + ffi_sarg sint; + ffi_arg uint; + float flt; + char data[FFI_SIZEOF_ARG]; + void* ptr; +} ffi_raw; + +#if FFI_SIZEOF_JAVA_RAW == 4 && FFI_SIZEOF_ARG == 8 +/* This is a special case for mips64/n32 ABI (and perhaps others) where + sizeof(void *) is 4 and FFI_SIZEOF_ARG is 8. */ +typedef union { + signed int sint; + unsigned int uint; + float flt; + char data[FFI_SIZEOF_JAVA_RAW]; + void* ptr; +} ffi_java_raw; +#else +typedef ffi_raw ffi_java_raw; +#endif + + +FFI_API +void ffi_raw_call (ffi_cif *cif, + void (*fn)(void), + void *rvalue, + ffi_raw *avalue); + +FFI_API void ffi_ptrarray_to_raw (ffi_cif *cif, void **args, ffi_raw *raw); +FFI_API void ffi_raw_to_ptrarray (ffi_cif *cif, ffi_raw *raw, void **args); +FFI_API size_t ffi_raw_size (ffi_cif *cif); + +/* This is analogous to the raw API, except it uses Java parameter + packing, even on 64-bit machines. I.e. on 64-bit machines longs + and doubles are followed by an empty 64-bit word. */ + +#if !FFI_NATIVE_RAW_API +FFI_API +void ffi_java_raw_call (ffi_cif *cif, + void (*fn)(void), + void *rvalue, + ffi_java_raw *avalue) __attribute__((deprecated)); +#endif + +FFI_API +void ffi_java_ptrarray_to_raw (ffi_cif *cif, void **args, ffi_java_raw *raw) __attribute__((deprecated)); +FFI_API +void ffi_java_raw_to_ptrarray (ffi_cif *cif, ffi_java_raw *raw, void **args) __attribute__((deprecated)); +FFI_API +size_t ffi_java_raw_size (ffi_cif *cif) __attribute__((deprecated)); + +/* ---- Definitions for closures ----------------------------------------- */ + +#if FFI_CLOSURES + +#ifdef _MSC_VER +__declspec(align(8)) +#endif +typedef struct { +#if 0 + void *trampoline_table; + void *trampoline_table_entry; +#else + union { + char tramp[FFI_TRAMPOLINE_SIZE]; + void *ftramp; + }; +#endif + ffi_cif *cif; + void (*fun)(ffi_cif*,void*,void**,void*); + void *user_data; +#if defined(_MSC_VER) && defined(_M_IX86) + void *padding; +#endif +#if defined(__MVS__) + struct ffi_reg_data reg; +#endif +} ffi_closure +#ifdef __GNUC__ + __attribute__((aligned (8))) +#endif + ; + +#ifndef __GNUC__ +# ifdef __sgi +# pragma pack 0 +# endif +#endif + +FFI_API void *ffi_closure_alloc (size_t size, void **code); +FFI_API void ffi_closure_free (void *); + +FFI_API ffi_status +ffi_prep_closure (ffi_closure*, + ffi_cif *, + void (*fun)(ffi_cif*,void*,void**,void*), + void *user_data) +#if defined(__GNUC__) && (((__GNUC__ * 100) + __GNUC_MINOR__) >= 405) + __attribute__((deprecated ("use ffi_prep_closure_loc instead"))) +#elif defined(__GNUC__) && __GNUC__ >= 3 + __attribute__((deprecated)) +#endif + ; + +FFI_API ffi_status +ffi_prep_closure_loc (ffi_closure*, + ffi_cif *, + void (*fun)(ffi_cif*,void*,void**,void*), + void *user_data, + void *codeloc); + +#ifdef __sgi +# pragma pack 8 +#endif +typedef struct { +#if 0 + void *trampoline_table; + void *trampoline_table_entry; +#else + char tramp[FFI_TRAMPOLINE_SIZE]; +#endif + ffi_cif *cif; + +#if !FFI_NATIVE_RAW_API + + /* If this is enabled, then a raw closure has the same layout + as a regular closure. We use this to install an intermediate + handler to do the translation, void** -> ffi_raw*. */ + + void (*translate_args)(ffi_cif*,void*,void**,void*); + void *this_closure; + +#endif + + void (*fun)(ffi_cif*,void*,ffi_raw*,void*); + void *user_data; + +} ffi_raw_closure; + +typedef struct { +#if 0 + void *trampoline_table; + void *trampoline_table_entry; +#else + char tramp[FFI_TRAMPOLINE_SIZE]; +#endif + + ffi_cif *cif; + +#if !FFI_NATIVE_RAW_API + + /* If this is enabled, then a raw closure has the same layout + as a regular closure. We use this to install an intermediate + handler to do the translation, void** -> ffi_raw*. */ + + void (*translate_args)(ffi_cif*,void*,void**,void*); + void *this_closure; + +#endif + + void (*fun)(ffi_cif*,void*,ffi_java_raw*,void*); + void *user_data; + +} ffi_java_raw_closure; + +FFI_API ffi_status +ffi_prep_raw_closure (ffi_raw_closure*, + ffi_cif *cif, + void (*fun)(ffi_cif*,void*,ffi_raw*,void*), + void *user_data); + +FFI_API ffi_status +ffi_prep_raw_closure_loc (ffi_raw_closure*, + ffi_cif *cif, + void (*fun)(ffi_cif*,void*,ffi_raw*,void*), + void *user_data, + void *codeloc); + +#if !FFI_NATIVE_RAW_API +FFI_API ffi_status +ffi_prep_java_raw_closure (ffi_java_raw_closure*, + ffi_cif *cif, + void (*fun)(ffi_cif*,void*,ffi_java_raw*,void*), + void *user_data) __attribute__((deprecated)); + +FFI_API ffi_status +ffi_prep_java_raw_closure_loc (ffi_java_raw_closure*, + ffi_cif *cif, + void (*fun)(ffi_cif*,void*,ffi_java_raw*,void*), + void *user_data, + void *codeloc) __attribute__((deprecated)); +#endif + +#endif /* FFI_CLOSURES */ + +#ifdef FFI_GO_CLOSURES + +typedef struct { + void *tramp; + ffi_cif *cif; + void (*fun)(ffi_cif*,void*,void**,void*); +} ffi_go_closure; + +FFI_API ffi_status ffi_prep_go_closure (ffi_go_closure*, ffi_cif *, + void (*fun)(ffi_cif*,void*,void**,void*)); + +FFI_API void ffi_call_go (ffi_cif *cif, void (*fn)(void), void *rvalue, + void **avalue, void *closure); + +#endif /* FFI_GO_CLOSURES */ + +/* ---- Public interface definition -------------------------------------- */ + +FFI_API +ffi_status ffi_prep_cif(ffi_cif *cif, + ffi_abi abi, + unsigned int nargs, + ffi_type *rtype, + ffi_type **atypes); + +FFI_API +ffi_status ffi_prep_cif_var(ffi_cif *cif, + ffi_abi abi, + unsigned int nfixedargs, + unsigned int ntotalargs, + ffi_type *rtype, + ffi_type **atypes); + +FFI_API +void ffi_call(ffi_cif *cif, + void (*fn)(void), + void *rvalue, + void **avalue); + +FFI_API +ffi_status ffi_get_struct_offsets (ffi_abi abi, ffi_type *struct_type, + size_t *offsets); + +/* Convert between closure and function pointers. */ +#if defined(PA_LINUX) || defined(PA_HPUX) +#define FFI_FN(f) ((void (*)(void))((unsigned int)(f) | 2)) +#define FFI_CL(f) ((void *)((unsigned int)(f) & ~3)) +#else +#define FFI_FN(f) ((void (*)(void))f) +#define FFI_CL(f) ((void *)(f)) +#endif + +/* ---- Definitions shared with assembly code ---------------------------- */ + +#endif + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/libffi_built/include/ffitarget.h b/libffi_built/include/ffitarget.h new file mode 100644 index 0000000..ef2652b --- /dev/null +++ b/libffi_built/include/ffitarget.h @@ -0,0 +1,116 @@ +/* -----------------------------------------------------------------*-C-*- + ffitarget.h - Copyright (c) 2012 Anthony Green + Copyright (c) 1996-2003 Red Hat, Inc. + Copyright IBM Corp. 2021 + Target configuration macros for S390. + + Permission is hereby granted, free of charge, to any person obtaining + a copy of this software and associated documentation files (the + ``Software''), to deal in the Software without restriction, including + without limitation the rights to use, copy, modify, merge, publish, + distribute, sublicense, and/or sell copies of the Software, and to + permit persons to whom the Software is furnished to do so, subject to + the following conditions: + + The above copyright notice and this permission notice shall be included + in all copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED ``AS IS'', WITHOUT WARRANTY OF ANY KIND, + EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND + NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT + HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, + WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + DEALINGS IN THE SOFTWARE. + + ----------------------------------------------------------------------- */ + +#ifndef LIBFFI_TARGET_H +#define LIBFFI_TARGET_H + + +#ifndef LIBFFI_H +#error "Please do not include ffitarget.h directly into your source. Use ffi.h instead." +#endif + +#if defined (__s390x__) +#ifndef S390X +#define S390X +#endif +#endif + +/* ---- System specific configurations ----------------------------------- */ + +#ifndef LIBFFI_ASM +typedef unsigned long ffi_arg; +typedef signed long ffi_sarg; + +typedef enum ffi_abi { + FFI_FIRST_ABI = 0, + FFI_SYSV, + FFI_LAST_ABI, + FFI_DEFAULT_ABI = FFI_SYSV +} ffi_abi; +#endif + +#define FFI_TARGET_SPECIFIC_STACK_SPACE_ALLOCATION +#define FFI_TARGET_HAS_COMPLEX_TYPE + +/* ---- Definitions for closures ----------------------------------------- */ + +#define FFI_CLOSURES 1 +#ifdef S390X +#define FFI_TRAMPOLINE_SIZE 64 +#else +#define FFI_TRAMPOLINE_SIZE 64 +#endif +#define FFI_NATIVE_RAW_API 0 + + +/* If these change, update src/mips/ffitarget.h. */ +/** +#define FFI_TYPE_VOID 0 +#define FFI_TYPE_INT 1 +#define FFI_TYPE_FLOAT 2 +#define FFI_TYPE_DOUBLE 3 +#if @HAVE_LONG_DOUBLE@ +#define FFI_TYPE_LONGDOUBLE 4 +#else +#define FFI_TYPE_LONGDOUBLE FFI_TYPE_DOUBLE +#endif +#define FFI_TYPE_UINT8 5 +#define FFI_TYPE_SINT8 6 +#define FFI_TYPE_UINT16 7 +#define FFI_TYPE_SINT16 8 +#define FFI_TYPE_UINT32 9 +#define FFI_TYPE_SINT32 10 +#define FFI_TYPE_UINT64 11 +#define FFI_TYPE_SINT64 12 +#define FFI_TYPE_STRUCT 13 +#define FFI_TYPE_POINTER 14 +#define FFI_TYPE_COMPLEX 15 +#define FFI_TYPE_STRUCT_FF 16 +#define FFI_TYPE_STRUCT_DD 17 +**/ + +#define FFI_TYPE_STRUCT_FF 16 +#define FFI_TYPE_STRUCT_DD 17 + +// HACK ALERT!!! (maybe fix this?) +#ifdef FFI_TYPE_LAST +#undef FFI_TYPE_LAST +/* This should always refer to the last type code (for sanity checks) */ +#define FFI_TYPE_LAST FFI_TYPE_STRUCT_DD +#endif + +/* struct data to save registers */ +struct ffi_reg_data { + long* gpr[16]; + double fpr[7]; +}; + +// #define FFI_EXTRA_CIF_FIELDS struct ffi_reg_data reg + +#endif + diff --git a/libffi_built/lib/libffi.a b/libffi_built/lib/libffi.a new file mode 100644 index 0000000..4ff011b Binary files /dev/null and b/libffi_built/lib/libffi.a differ diff --git a/patches/configure-ext.mk.tmpl.patch b/patches/configure-ext.mk.tmpl.patch new file mode 100644 index 0000000..355125f --- /dev/null +++ b/patches/configure-ext.mk.tmpl.patch @@ -0,0 +1,13 @@ +diff --git a/template/configure-ext.mk.tmpl b/template/configure-ext.mk.tmpl +index bc192a3..835cb4e 100644 +--- a/template/configure-ext.mk.tmpl ++++ b/template/configure-ext.mk.tmpl +@@ -17,7 +17,7 @@ srcdir ||= File.dirname(File.dirname(__FILE__)) + exts = {} + [ + ["exts", "ext", "--extstatic $(EXTSTATIC)"], +- ["gems", ".bundle/gems", "--no-extstatic"], ++ ["gems", ".bundle/gems", "--extstatic $(EXTSTATIC)"], + ].each do |t, d, o| + exts[t] = [o, Dir.glob("#{srcdir}/#{d}/*/").map {|n| n[(srcdir.size+1)..-2]}] + end diff --git a/patches/configure.patch b/patches/configure.patch new file mode 100644 index 0000000..2fbdcd0 --- /dev/null +++ b/patches/configure.patch @@ -0,0 +1,37 @@ +diff --git a/configure b/configure +index 7a391a2..02c7c41 100755 +--- a/configure ++++ b/configure +@@ -26423,6 +26423,7 @@ if test "x$ac_cv_func_fork_works" = xcross; then + printf "%s\n" "$as_me: WARNING: result $ac_cv_func_vfork_works guessed because of cross compilation" >&2;} + fi + ++ac_cv_func_vfork_works=no + if test "x$ac_cv_func_vfork_works" = xyes; then + + printf "%s\n" "#define HAVE_WORKING_VFORK 1" >>confdefs.h +@@ -26570,6 +26571,7 @@ then : + fi + + ac_fn_c_check_func "$LINENO" "dladdr" "ac_cv_func_dladdr" ++ac_cv_func_dladdr=no + if test "x$ac_cv_func_dladdr" = xyes + then : + printf "%s\n" "#define HAVE_DLADDR 1" >>confdefs.h +@@ -27116,6 +27118,7 @@ then : + fi + + ac_fn_c_check_func "$LINENO" "mmap" "ac_cv_func_mmap" ++ac_cv_func_mmap=no + if test "x$ac_cv_func_mmap" = xyes + then : + printf "%s\n" "#define HAVE_MMAP 1" >>confdefs.h +@@ -29838,7 +29841,7 @@ then : + else $as_nop + + case "$target_cpu" in #( +- m68*|x86*|x64|i?86|ppc*|sparc*|alpha*|arm*|aarch*) : ++ m68*|x86*|x64|i?86|ppc*|sparc*|alpha*|arm*|aarch*|i370) : + dir=-1 ;; #( + hppa*) : + dir=+1 ;; #( diff --git a/patches/ext_socket.patch b/patches/ext_socket.patch new file mode 100644 index 0000000..97f71eb --- /dev/null +++ b/patches/ext_socket.patch @@ -0,0 +1,149 @@ +diff --git a/ext/socket/extconf.rb b/ext/socket/extconf.rb +index d44ce31..f220d08 100644 +--- a/ext/socket/extconf.rb ++++ b/ext/socket/extconf.rb +@@ -1,6 +1,8 @@ + # frozen_string_literal: false + require 'mkmf' + ++$CFLAGS << " -Werror=implicit-function-declaration" ++ + AF_INET6_SOCKET_CREATION_TEST = < + #ifndef _WIN32 +diff --git a/ext/socket/ipsocket.c b/ext/socket/ipsocket.c +index cacacd3..08bdbbd 100644 +--- a/ext/socket/ipsocket.c ++++ b/ext/socket/ipsocket.c +@@ -996,7 +996,7 @@ init_fast_fallback_inetsock_internal(VALUE v) + resolution_store.v6.finished = true; + + if (arg->getaddrinfo_entries[IPV6_ENTRY_POS]->err && +- arg->getaddrinfo_entries[IPV6_ENTRY_POS]->err != EAI_ADDRFAMILY) { ++ arg->getaddrinfo_entries[IPV6_ENTRY_POS]->err != EAI_FAMILY) { + if (!resolution_store.v4.finished || resolution_store.v4.has_error) { + last_error.type = RESOLUTION_ERROR; + last_error.ecode = arg->getaddrinfo_entries[IPV6_ENTRY_POS]->err; +@@ -1202,8 +1202,8 @@ fast_fallback_inetsock_cleanup(VALUE v) + } + } + +- if (arg->readfds.fdset) rb_fd_term(&arg->readfds); +- if (arg->writefds.fdset) rb_fd_term(&arg->writefds); ++ //if (arg->readfds.fdset) rb_fd_term(&arg->readfds); ++ //if (arg->writefds.fdset) rb_fd_term(&arg->writefds); + + if (arg->connection_attempt_fds) { + free(arg->connection_attempt_fds); +diff --git a/ext/socket/rubysocket.h b/ext/socket/rubysocket.h +index b4dcd59..fa6966e 100644 +--- a/ext/socket/rubysocket.h ++++ b/ext/socket/rubysocket.h +@@ -4,7 +4,7 @@ + #include "ruby/config.h" + #include RUBY_EXTCONF_H + +-#if defined(__sun) || defined(_AIX) ++#if defined(__sun) || defined(_AIX) || defined(__MVS__) + /* (Recent?) Solaris' have conflicting definition of T_DATA. Let + * us honour system definition by undefining ours. + * +diff --git a/ext/socket/socket.c b/ext/socket/socket.c +index 8f593ca..886180b 100644 +--- a/ext/socket/socket.c ++++ b/ext/socket/socket.c +@@ -9,6 +9,9 @@ + ************************************************/ + + #include "rubysocket.h" ++#include ++#include ++#include "zos-base.h" + + static VALUE sym_wait_writable; + +@@ -1552,7 +1555,74 @@ rsock_sockaddr_obj(struct sockaddr *addr, socklen_t len) + static VALUE + socket_s_ip_address_list(VALUE self) + { +-#if defined(HAVE_GETIFADDRS) ++#if defined(__MVS__) ++ ++#ifndef MAX ++#define MAX(a,b) (((a)>(b))?(a):(b)) ++#endif ++#define ADDR_SIZE(p) MAX((p).sa_len, sizeof(p)) ++ ++ int fd = -1; ++ struct ifconf ifc; ++ struct ifreq *ifr, *p, flg; ++ char *buf = NULL; ++ int bufsize = 16384; /* Start with a reasonable size */ ++ VALUE list = Qnil; ++ const char *reason = NULL; ++ int save_errno; ++ ++ fd = socket(AF_INET, SOCK_DGRAM, 0); ++ if (fd == -1) ++ rb_sys_fail("socket(2)"); ++ ++ buf = xmalloc(bufsize); ++ ifc.ifc_req = (struct ifreq *)buf; ++ ifc.ifc_len = bufsize; ++ ++ if (ioctl(fd, SIOCGIFCONF, &ifc) == -1) { ++ reason = "SIOCGIFCONF"; ++ goto finish; ++ } ++ ++ list = rb_ary_new(); ++ ifr = ifc.ifc_req; ++ while ((char*)ifr < (char*)ifc.ifc_req + ifc.ifc_len) { ++ p = ifr; ++ ifr = (struct ifreq*)((char*)ifr + sizeof(ifr->ifr_name) + ADDR_SIZE(p->ifr_addr)); ++ ++ if (!IS_IP_FAMILY(p->ifr_addr.sa_family)) ++ continue; ++ ++ memcpy(flg.ifr_name, p->ifr_name, sizeof(flg.ifr_name)); ++ if (ioctl(fd, SIOCGIFFLAGS, &flg) == -1) { ++ /* Ignore errors, just skip this interface */ ++ continue; ++ } ++ ++ if (!(flg.ifr_flags & IFF_UP && flg.ifr_flags & IFF_RUNNING)) ++ continue; ++ ++ rb_ary_push(list, sockaddr_obj(&p->ifr_addr, sockaddr_len(&p->ifr_addr))); ++ } ++ ++finish: ++ save_errno = errno; ++ if (buf) ++ xfree(buf); ++ if (fd != -1) ++ close(fd); ++ errno = save_errno; ++ ++ if (reason) ++ rb_syserr_fail(save_errno, reason); ++ return list; ++ ++#undef ADDR_SIZE ++#ifdef MAX ++#undef MAX ++#endif ++ ++#elif defined(HAVE_GETIFADDRS) + struct ifaddrs *ifp = NULL; + struct ifaddrs *p; + int ret; +@@ -1594,6 +1664,8 @@ socket_s_ip_address_list(VALUE self) + freeifaddrs(ifp); + + return list; ++ ++ + #elif defined(SIOCGLIFCONF) && defined(SIOCGLIFNUM) + /* Solaris if_tcp(7P) */ + int fd = -1; diff --git a/patches/process.c.patch b/patches/process.c.patch new file mode 100644 index 0000000..0e7cdac --- /dev/null +++ b/patches/process.c.patch @@ -0,0 +1,28 @@ +diff --git a/process.c b/process.c +index 5fbc9be..90c24c4 100644 +--- a/process.c ++++ b/process.c +@@ -8594,7 +8594,7 @@ rb_clock_getres(int argc, VALUE *argv, VALUE _) + timetick_int_t denominators[2]; + int num_numerators = 0; + int num_denominators = 0; +-#ifdef HAVE_CLOCK_GETRES ++#if defined(HAVE_CLOCK_GETRES) || defined(__MVS__) + clockid_t c; + #endif + +@@ -8697,11 +8697,12 @@ rb_clock_getres(int argc, VALUE *argv, VALUE _) + #endif + } + else if (NUMERIC_CLOCKID) { +-#if defined(HAVE_CLOCK_GETRES) ++#if defined(HAVE_CLOCK_GETRES) || defined(__MVS__) + struct timespec ts; + c = NUM2CLOCKID(clk_id); + getres: +- ret = clock_getres(c, &ts); ++ // ret = clock_getres(c, &ts); ++ ret = -1; + if (ret == -1) + clock_failed("getres", errno, clk_id); + tt.count = (int32_t)ts.tv_nsec; diff --git a/patches/ruby_assert.h.patch b/patches/ruby_assert.h.patch new file mode 100644 index 0000000..9631631 --- /dev/null +++ b/patches/ruby_assert.h.patch @@ -0,0 +1,19 @@ +diff --git a/ruby_assert.h b/ruby_assert.h +index d8f7ddd..9f000cb 100644 +--- a/ruby_assert.h ++++ b/ruby_assert.h +@@ -7,8 +7,13 @@ + * modify this file, provided that the conditions mentioned in the + * file COPYING are met. Consult the file for details. + */ +-#include "ruby/assert.h" ++#ifdef assert ++# undef assert ++#endif ++#define assert assert_undefine ++#include + #undef assert ++#include "ruby/assert.h" + #define assert RUBY_ASSERT_NDEBUG + + #endif /* RUBY_TOPLEVEL_ASSERT_H */ diff --git a/patches/signal.c.patch b/patches/signal.c.patch new file mode 100644 index 0000000..0a30da8 --- /dev/null +++ b/patches/signal.c.patch @@ -0,0 +1,13 @@ +diff --git a/signal.c b/signal.c +index d644991..9e53c6f 100644 +--- a/signal.c ++++ b/signal.c +@@ -883,7 +883,7 @@ check_stack_overflow(int sig, const void *addr) + # define CHECK_STACK_OVERFLOW_() check_stack_overflow(sig, FAULT_ADDRESS) + # endif + # define MESSAGE_FAULT_ADDRESS " at %p", FAULT_ADDRESS +-# define SIGNAL_FROM_USER_P() ((info)->si_code == SI_USER) ++# define SIGNAL_FROM_USER_P() 0 + # define CHECK_STACK_OVERFLOW() (SIGNAL_FROM_USER_P() ? (void)0 : CHECK_STACK_OVERFLOW_()) + # endif + #else diff --git a/patches/thread_pthread.c.patch b/patches/thread_pthread.c.patch new file mode 100644 index 0000000..0273540 --- /dev/null +++ b/patches/thread_pthread.c.patch @@ -0,0 +1,13 @@ +diff --git a/thread_pthread.c b/thread_pthread.c +index 423814c..42992d5 100644 +--- a/thread_pthread.c ++++ b/thread_pthread.c +@@ -2022,7 +2022,7 @@ native_thread_init_stack(rb_thread_t *th, void *local_in_parent_frame) + th->ec->machine.asan_fake_stack_handle = asan_get_thread_fake_stack_handle(); + #endif + +- if (!native_main_thread.id) { ++ if (!native_main_thread.id.__) { + /* This thread is the first thread, must be the main thread - + * configure the native_main_thread object */ + native_thread_init_main_thread_stack(local_in_parent_frame); diff --git a/patches/vm.c.patch b/patches/vm.c.patch new file mode 100644 index 0000000..caad2d3 --- /dev/null +++ b/patches/vm.c.patch @@ -0,0 +1,21 @@ +diff --git a/vm.c b/vm.c +index 21e0d6f..8745e5b 100644 +--- a/vm.c ++++ b/vm.c +@@ -50,6 +50,7 @@ + + #include "probes.h" + #include "probes_helper.h" ++#include + + #ifdef RUBY_ASSERT_CRITICAL_SECTION + int ruby_assert_critical_section_entered = 0; +@@ -3811,7 +3812,7 @@ nsdr(VALUE self) + { + VALUE ary = rb_ary_new(); + #ifdef HAVE_BACKTRACE +-#include ++//#include + #define MAX_NATIVE_TRACE 1024 + static void *trace[MAX_NATIVE_TRACE]; + int n = (int)backtrace(trace, MAX_NATIVE_TRACE); diff --git a/patches/vm_eval.c.patch b/patches/vm_eval.c.patch new file mode 100644 index 0000000..c2e2f1a --- /dev/null +++ b/patches/vm_eval.c.patch @@ -0,0 +1,13 @@ +diff --git a/vm_eval.c b/vm_eval.c +index 74dfd40..c3e3759 100644 +--- a/vm_eval.c ++++ b/vm_eval.c +@@ -389,7 +389,7 @@ void + rb_check_stack_overflow(void) + { + #ifndef RB_THREAD_LOCAL_SPECIFIER +- if (!ruby_current_ec_key) return; ++ if (ruby_current_ec_key.__ == 0) return; + #endif + rb_execution_context_t *ec = GET_EC(); + if (ec) stack_check(ec);