#[no_mangle]
unsafe extern "C" fn Estore_Cancel(
rust: *mut ::std::os::raw::c_void,
data: sys::CancelData,
) -> *mut ::std::os::raw::c_void {
let api = unwrap_quote_spi(rust);
let mut result = RT.block_on(async { api.cancel(data).await });
let rsp = &mut result as *mut _ as *mut c_void;
std::mem::forget(result);
// if add this debug line, c++ not panic
// delete this debug line, c++ panic "has triggered a breakpoint"
// debug!("1");
rsp // CancelResult
}
rsp is a pointer to the local variable. Dereferencing it after the function returns is UB, means literally anything can happens including behaviors that doesn't make any sense.
If you haven't heard about what the UB is, try read this Wikipedia article.
Yes, which make it worse, since it's moved into the forget function's local variable. The original variable becomes the moved-out state, which means accessing here is UB.
This is one of the common symptoms of the UB. UB doesn't means it will crash or something predictable. It literally means the behavior is undefined - it may crash, work as you've imagined, silently corrupt some totally unrelated portion of memories, or mine some Bitcoin. It's the hole the language explicitly mentioned nothing guaranteed here. The Wikipedia article I mentioned contains more information why such thing even exist.
IOW, just because it happens not to panic doesn't mean it's correct. Your code should definitely be rewritten. If you need to return something complex through FFI, accept a pointer as an out parameter in which you write the results, or return a pointer pointing to a heap-allocated object. Returning a pointer to a stack-allocated object is never correct.
That's simply not possible. What you allocated in Rust must be destroyed by Rust. You'll need to write a destructor function that performs Box::from_raw and you must call it from C++.