Call function declared in crate but defined in other crate


#1

Hello,

I am working on a C library wrapper in rust. The library is a plugin SDK with which you can write plugins for an application (obviously). I create a static wrapper (“rlib”) and the actual rust plugin (in my case the example plugin) is a dynamic system library (“dylib”) which can be directly called by the application. The wrapping works great so far, but I have a (conceptual) problem with the plugin’s setup function. It is called by the application for every plugin and I have implemented it, the function is called in the static wrapper, all good so far. But here comes the problem:

I don’t know how I can provide a way the user of the wrapper (again the example plugin in my case) can provide a custom setup function. I don’t want the user to implement the extern native function directly (and I also need to do some wrapper there), so I need some way to register the setup function the user provides, but since it all is inside of libraries I don’t have any main function to register any events or something else.

Call stack: Application -> Native C Function -?> Custom rust function

So: Is there anyway I can call a function or register a function to be called from within the wrapper crate without this function being defined inside the wrapper crate (but inside the custom plugin)?

In C I can easily do this by declaring the function but not defining it and then when the C SDK is static linked define the function in the custom C plugin.

I hope my explanation is understandable, otherwise I’ll provide you with more information.

Thank you in advance,
MarkAtk


#2

For “declare but not define” Rust has only the C FFI extern "C" { fn … }.

You could call Rust native functions by pointer:

extern "C" {
   fn init(f: fn());
}

and in another crate:

#[no_mangle]
pub extern "C" fn init(f: fn()) {
   f();
}

#3

Thank you, this seems to work. I am still unhappy about the extern way, I think it should be possible to do such a thing without “leaving” rust but for the moment it’s okay.


#4

Unfortunately, Rust hasn’t declared its ABI as stable yet, so Rust-native calls between libraries are not really supported.