-
Notifications
You must be signed in to change notification settings - Fork 671
Description
Currently oneshot works well for converting Rust based callbacks into futures. Unfortunately it's less suited for converting C based callbacks into futures.
C based callbacks generally pass a void* from the setup call to the callback. Since that pointer needs to be stable, you can't simply pass a pointer to the Sender itself. You'd have to wrap it in a Box and call Box::into_raw on it. This is rather redundant, since oneshot::Sender is just a new-type wrapper around an Arc. Arc can already be converted into/from such a stable pointer via its into_raw / from_raw methods.
So I propose adding similar functions to Sender, which forward to the underlying functions on Arc. Something like:
#[repr(transparent)]
pub struct RawSender(c_void);
impl<T> Sender<T> {
pub fn into_raw(self) -> NonNull<RawSender>;
pub unsafe fn from_raw(ptr: NonNull<RawSender>) -> Sender<T>;
}
The type of pointer (NonNull vs *const vs *mut) and the type of pointee (() vs c_void vs RawSender vs RawSender<T>) needs to be figured out.
This feature does have one minor drawback: It prevents adding additional fields to Sender. For example Tokio's oneshot-channel puts tracing-span in the sender, which would need to be put inside the Arc to be compatible with this feature.
Inspired by a thread on the rust users forum: Bridging callbacks and futures