use std::mem;
pub(crate) unsafe fn install_abort_handler() -> Result<libc::sigaction, std::io::Error> {
unsafe {
let mut sa: libc::sigaction = mem::zeroed();
libc::sigemptyset(&mut sa.sa_mask);
libc::sigaddset(&mut sa.sa_mask, libc::SIGABRT);
sa.sa_sigaction = signal_handler as usize;
sa.sa_flags = libc::SA_SIGINFO;
let mut old_action = mem::MaybeUninit::uninit();
if libc::sigaction(libc::SIGABRT, &sa, old_action.as_mut_ptr()) != -1 {
Ok(old_action.assume_init())
} else {
Err(std::io::Error::last_os_error())
}
}
}
#[inline]
pub(crate) unsafe fn restore_abort_handler(handler: libc::sigaction) {
unsafe { libc::sigaction(libc::SIGABRT, &handler, std::ptr::null_mut()) };
}
unsafe extern "C" fn signal_handler(
signal: i32,
_info: *mut libc::siginfo_t,
_uc: *mut std::ffi::c_void,
) {
use super::ffi;
assert_eq!(signal, libc::SIGABRT);
super::state::simulate_exception(Some(crash_context::ExceptionInfo {
kind: ffi::et::EXC_SOFTWARE,
code: ffi::EXC_SOFT_SIGNAL as u64, subcode: Some(signal as _),
}));
}