I'm implementing a "wrapper" (on Windows) for unsafe extern functions, the problem is that the wrapped functions are not safe (actually they're really unsafe). They may even throw exceptions, something like that:
Thank you, it may be possible to wrap them using __try {}...__except {} of Windows SEH (then passing wrapped functions into Rust). Is is possible to do that directly in Rust?
Thank you, but it's may not be what I'm looking for. Since the exception to capture is at a lower level than C++'s exception. On Windows x32, I've managed to do that by overwriting the exception handler chain, like that:
unsafe extern "system" fn exception_filter(
exception_record: *mut EXCEPTION_RECORD,
_establish_frame: PVOID,
_context_record: *mut CONTEXT,
_dispatcher_context: PVOID,
) -> EXCEPTION_DISPOSITION {
if (*exception_record).ExceptionCode == EXCEPTION_ILLEGAL_INSTRUCTION {
// capture it
println!("captured");
}
ExceptionContinueExecution
}
// overwrite the head of the exception handler chain
let tib = current_tib();
let mut registration = MaybeUninit::<EXCEPTION_REGISTRATION_RECORD>::uninit();
(*registration.as_mut_ptr()).Handler = Some(exception_filter);
(*registration.as_mut_ptr()).Next = (*tib).ExceptionList;
(*tib).ExceptionList = registration.as_mut_ptr();
// invoke an exception
asm!("ud2");
// restore the exception handler chain
(*tib).ExceptionList = (*(*tib).ExceptionList).Next;
Unfortunately, the technique doesn't work for the Windows x64 SEH since the handler table is now on the PE file itself, and built by the compiler. I'be heard that Rust compiler supports Windows x64 SEH, so it would be able to do that too. It may be possible to modify this table, but I'm don't know how to do it yet.
Thanks for the ping, @Yandros. @alice isccorrect that there's no well-defined way to catch C++ exceptions in Rust; technically, it is undefined for such an exception to enter a Rust stack frame at all, so the compiler currently emits LLVM's nounwind annotation for "C" function declarations and call sites.
Unfortunately, we don't plan to support catching C++ exceptions in the language proper or the standard library. But I don't know of any reason why a custom panic handler like the one you've defined couldn't do that (though of course that behavior could change out from under you if the target platform's implementation details change).