1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77
/* ------------------------------------------ */
/* lib.rs - pretty-panic library source code. */
/* ------------------------------------------ */
// Set crate attributes.
#![deny(missing_docs)]
//!
//! # pretty-panic
//!
//! Provides a simple way to deliver prettier panic messages to the user.
//! Wraps around [`std::panic::set_hook()`](https://doc.rust-lang.org/std/panic/fn.set_hook.html), allowing you to easily change
//! the panic message for your release builds.
//!
//! ## Example
//! ```rust
//! use pretty_panic::pretty_panic;
//!
//! fn main() {
//! pretty_panic!();
//!
//! panic!("A panic message.");
//! }
//! ```
//! It's that simple! The `pretty_panic!()` macro can take a custom panic handler function as an argument.
//! If one isn't passed, it simply uses the default.
/// Sets the panic handler function to a function of your choosing.
/// **Example**:
/// ```rust
/// use pretty_panic::pretty_panic;
/// use std::panic::PanicInfo;
/// fn main() {
/// pretty_panic!(my_panic);
///
/// panic!("a panic message")
/// }
///
/// fn my_panic() -> ! {
/// loop { /* who needs to actually do something when they panic? }
/// }
/// ```
/// The panic handler MUST return the [`never`](https://doc.rust-lang.org/std/primitive.never.html) type, or the program will not compile!
#[macro_export]
macro_rules! pretty_panic {
() => {
use std::panic::{set_hook, PanicInfo};
fn default_handler(e: &PanicInfo) -> ! {
use std::thread;
let pkg_name: String = env!("CARGO_PKG_NAME").into();
let pkg_ver: String = env!("CARGO_PKG_VERSION").into();
let pkg_devs: String = env!("CARGO_PKG_AUTHORS").replace(":", ", ").into();
let pkg_home: String = env!("CARGO_PKG_HOMEPAGE").into();
let t = thread::current();
let t = match t.name() {
Some(name) => name,
None => "unknown",
};
eprintln!("Uh oh!\n");
eprintln!("The program experienced a fatal error, and has panicked. Recommend you contact one");
eprintln!("of the authors for assistance. See below for some additional information:\n");
eprintln!("(If you are going to submit a bug report, include the entirety of this message!)");
eprintln!("{} v{} ({}) - panic start", pkg_name, pkg_ver, pkg_home);
eprintln!(" panic from thread [{}]:\n {}\n", t, e);
eprintln!("Submit bug report to the authors: {}", pkg_devs);
eprintln!("{} v{} ({}) - panic end", pkg_name, pkg_ver, pkg_home);
std::process::exit(101);
}
set_hook(Box::new(|e| { default_handler(e) }));
};
($fname:ident) => {
use std::panic::{set_hook, PanicInfo};
set_hook(Box::new(|e| { $fname(e) }));
}
}