#[macro_use]
mod assert;
use std::{
panic,
sync::{Arc, Mutex},
};
use lazy_static::lazy_static;
use crate::errors::*;
pub const TEST_TEMP_DIR: &str = "tests/temp";
lazy_static! {
static ref USE_PANIC_HANDLER: Arc<Mutex<usize>> = Arc::new(Mutex::new(0));
}
pub fn capture_panic(f: impl FnOnce() + panic::UnwindSafe) -> RvResult<()> {
{
let arc = USE_PANIC_HANDLER.clone();
let mut count = arc.lock().map_err(|_| CoreError::PanicCaptureFailure)?;
*count += 1;
panic::set_hook(Box::new(|_| {}));
}
let result = panic::catch_unwind(f);
let arc = USE_PANIC_HANDLER.clone();
let mut count = arc.lock().map_err(|_| CoreError::PanicCaptureFailure)?;
if *count != 0 {
*count -= 1;
}
if *count == 0 {
let _ = panic::take_hook();
}
if let Err(err) = result {
if let Some(x) = err.downcast_ref::<&str>() {
return Err(CoreError::panic_capture(x).into());
} else if let Some(x) = err.downcast_ref::<String>() {
return Err(CoreError::panic_capture(x).into());
}
}
Ok(())
}