• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2022 The ChromiumOS Authors
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 //! A panic handler for better crash signatures for rust apps.
6 
7 use std::ffi::CString;
8 use std::io;
9 use std::mem;
10 use std::panic;
11 use std::process::abort;
12 
13 use super::SharedMemory;
14 
15 const PANIC_MEMFD_NAME: &str = "RUST_PANIC_SIG";
16 
17 /// Inserts a panic handler that writes the panic info to a memfd called
18 /// "RUST_PANIC_SIG" before calling the original panic handler. This
19 /// makes it possible for external crash handlers to recover the panic info.
install_memfd_handler()20 pub fn install_memfd_handler() {
21     let hook = panic::take_hook();
22     panic::set_hook(Box::new(move |p| {
23         let panic_info = format!("{}\n", &p);
24         let panic_bytes = panic_info.as_bytes();
25         // On failure, ignore the error and call the original handler.
26         if let Ok(mut panic_memfd) = SharedMemory::new(
27             &CString::new(PANIC_MEMFD_NAME).unwrap(),
28             panic_bytes.len() as u64,
29         ) {
30             io::Write::write_all(&mut panic_memfd, panic_bytes).ok();
31             // Intentionally leak panic_memfd so it is picked up by the crash handler.
32             mem::forget(panic_memfd);
33         }
34         hook(p);
35 
36         // If this is a multithreaded program, a panic in one thread will not kill the whole
37         // process. Abort so the entire process gets killed and produces a core dump.
38         abort();
39     }));
40 }
41