neon
neon copied to clipboard
Add APIs that convert between `Context` and `napi_env`
Closes #611.
with_raw_env is useful when neon is not used as the "entry" of a native module, so after getting a raw napi_env we need the unsafe API to bootstrap a neon::Context.
@kjvalencik
My usage of with_raw_env is to pass Context across the ffi boundary. I am writing a native module that depends two static libraries, one targeting msvc and the other targeting mingw. Since they are two different ABIs I have to split the module into 2 shared libraries. Let's called them "a.node" and "b.dll".
- "a.node" is compiled with msvc so it can use the msvc library. Also it's the entry of the native module.
- "b.dll" is compiled with mingw so it can use the mingw library. It exports c functions which are called by "a.node".
I want to use neon in both the shared libraries. But "b.dll" isn't the entry point, so to create Context on its side I must pass a raw pointer from "a.node" and use with_raw_env the reconstruct the context.
I understand your concern about the entry point but for my case it's not a problem (neon is still used as the entry point in a.node). What do you think we remove the mentions of napi_env in the docs, and requires the ptr passed in with_raw_env (should rename to with_raw?) to be the one that returned from as_mut_ptr, not just any napi_env?
That's an interesting use case. Unfortunately, Context is more than a simple wrapper around napi_env. A good portion of that is unnecessary with the Node-API backend, but it would need to be removed before constructing a context across FFI could be safe. I also wouldn't want to overload TaskContext for this, but would want to create some type of FFI context dedicated to it where we can explicitly mark some guarantees. Ideally a user would only get &mut access to it.
In your example, it seems like one crate could own all Neon functions while the other exposes C FFI, but I'm sure the actual code is much more complicated.
Yeah it's not practical for my case to isolate neon in one crate :(
But I think I come up with a solution. The general idea is to represent napi_env with an FFI-safe opaque type RawEnv, and of course create contexts dedicate to FFI (RawContext). The bonus part is no more unsafe APIs, although callers would most definitely use unsafe.
I have pushed the commits. Let me know what you think :)