Show how to call a function in a shared library (without dynamically linking to it at compile-time). In particular, show how to call the shared library function if the library is available, otherwise use an internal equivalent function.

This is a special case of calling a foreign language function where the focus is close to the ABI level and not at the normal API level.



Related task

 OpenGL -- OpenGL is usually maintained as a shared library.


/* call_shared_library_function.wren */
 
var RTLD_LAZY = 1
 
foreign class DL {
    construct open(file, mode) {}
 
    foreign call(symbol, arg)
 
    foreign close()
}
 
class My {
    static openimage(s) {
        System.print("internal openimage opens %(s)...")
        if (!__handle) __handle = 0
        __handle = __handle + 1
        return __handle - 1
    }
}
 
var file = "fake.img"
var imglib = DL.open("./fakeimglib.so", RTLD_LAZY)
var imghandle = (imglib != null) ? imglib.call("openimage", file) : My.openimage(file)
System.print("opened with handle %(imghandle)")
if (imglib != null) imglib.close()