jnr / jffi

Java Foreign Function Interface
Apache License 2.0
168 stars 78 forks source link

Varargs support via FFI functions #121

Closed headius closed 2 years ago

headius commented 2 years ago

This PR modifies variadic function call logic to use the ffi_prep_cif_var function provided by libffi for passing varargs. This primarily improves support on Apple Silicon, which (at least under Darwin) structures the call stack for varargs differently than other platforms (a mix of registers and stack).

This is the first part of fixes to better support Apple Silicon. Additional fixes are required in the upstream libraries like jnr-ffi and jnr-posix.

Note that at the time I submit this initial PR it still requires the native library to be rebuilt for each platform. Given the challenges of doing so right now, I hope to find a way to make the Java changes work with the older builds of the C library. We will address build and versioning issues in the future.

headius commented 2 years ago

As expected, the pre-built linux binaries failed. Will mark this as non-draft once I know they work with the changes, and we can incrementally get the non-Darwin binaries rebuilt.

headius commented 2 years ago

Most recent commit moves the fixed param count into the high word of the flags parameter passed into the native side of Foreign.newCallContext. These high bits are ignored by the older builds, which only mask off low-word bits for JFFI behavioral flags. I believe this is safe to release with only the Darwin binary rebuilt.

I fully acknowledge the slight hackiness of passing the fixed count in the flags field but any other solution would require changing the C stub and introducing fallbacks on platforms where it has not been rebuilt. That feels hackier to me. We will need to address the versioning of the native stub better (see #93).