Skip to content

ffi

This content is for v1.0. Switch to the latest version for up-to-date documentation.

The ffi module provides foreign function interface capabilities, allowing RayQuiro programs to load native shared libraries and invoke C functions directly with automatic conversion of primitives, strings, and byte buffers.


FunctionSignatureReturn TypeDescription
ffi.loadffi.load(path)FFILibraryLoads a dynamic shared library (.dll on Windows, .so on POSIX).
ffi.symffi.sym(lib, name)boolChecks whether a exported symbol exists in the loaded library.
ffi.callffi.call(lib, name, ...args)numberInvokes an exported C function with up to 6 arguments.
ffi.closeffi.close(lib)voidUnloads the dynamic library handle.

var k32 = ffi.load("kernel32.dll")
if (ffi.sym(k32, "GetCurrentProcessId")) {
var pid = ffi.call(k32, "GetCurrentProcessId")
print("Process ID: " + pid)
}
ffi.close(k32)

Calling Standard C Library (libc / msvcrt)

Section titled “Calling Standard C Library (libc / msvcrt)”
var lib = ffi.load("msvcrt.dll")
ffi.call(lib, "puts", "Hello from C puts!")
ffi.close(lib)

When passing a Buffer object (created via buffer.alloc or buffer.from_string) as an argument to ffi.call, the raw memory pointer (uint8_t*) is automatically passed to the C function:

var buf = buffer.from_string("Hello C library")
var lib = ffi.load("mylib.dll")
ffi.call(lib, "process_data", buf, buffer.size(buf))
ffi.close(lib)