I've pushed another update to libffidemo, adding the class DemoFFITypeMappedThing and tests. With Pharo v50647 image's UFFI enhancements, all DemoFFI tests pass.
DemoFFITypeMappedThing allows using the C typedef demo_thing in #ffiCall: function signatures:
The C and Smalltalk signatures match. The ability to specify #ffiCall: function signatures very much like the actual C function signatures should make it easier to create bindings for UFFI.
The magic of DemoFFITypeMappedThing lies in FFIOpaqueObject, and,
With the above, UFFI maps (a pointer to) demo_thing in #ffiCall: signature to FFIOpaqueObject.
Compare and contrast with the earlier versions of DemoFFI:
Notice "demo_thing**" in the C signature, and "DemoFFIExternalObject*" in the Smalltalk signature. Conceptually, DemoFFIExternalObject represents a pointer to demo_thing, hence "demo_thing**" == "DemoFFIExternalObject*". Still, the difference in number of asterisks can cause confusion or result in subtle typo's.
Sometimes, it may be worth creating subclasses of FFIOpaqueObject to represent pointers to different C structure types. One may think of FFIOpaqueObject as a generic "void*", and, say, DemoFFIExternalObject as "demo_thing*", or, NBSQLite3DatabaseExternalObject as "sqlite3*" and NBSQLite3StatementExternalObject as "sqlite3_stmt*".
I've pushed an update to libffidemo, adding the class DemoFFIAutoThing and tests.
DemoFFIAutoThing sends #autoRelease to its handle when said handle is filled by libffidemo with a proper pointer. To support auto-release, DemoFFIExternalObject implements the following class-side method:
Note the C function signature, which is different from DemoFFILibrary>>apiFree:'s:
DemoFFIAutoThing>>letGo becomes a no-op. Making it send "super letGo", which effectively calls DemoFFILibrary>>apiFree:, crashes the VM.
I've published libffidemo, a simple C source file meant to be built as a shared library, and DemoFFI, a Smalltalk package that calls libffidemo to, well, demonstrate Pharo's new Unified FFI. DemoFFI was originally published on Smalltalkhub; Damien Pollet kindly repackaged the Smalltalk code, wrote a Makefile for the C source, etc and now libffidemo is a single self-contained repository with all necessary source files. The unit tests serve as the examples. Known working on Linux and OS X.
Periodically, I build the CogVM from source on FreeBSD. I've prevously mentioned that I had encountered some oddity with FFI on that platform. Still there today.
The following code crashes the VM/image:
The oddity is that one particular version of the SqueakFFIPrims plugin works. Several other versions that I've built all fail. Overwriting the failed versions of the plugin with the known-working one allows that particular crashing VM's FFI to work.
The working one appears here three times. I'm running FreeBSD 8.3.