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
use crate::hw::{cop0, Register};
use crate::{dprintln, println, Framebuffer};
#[panic_handler]
fn panic(info: &core::panic::PanicInfo) -> ! {
cop0::Status::new().critical_section(|_| {
// SAFETY: We're in a critical section so no other threads can get a
// mutable reference. The previous (nested) call to panic, if any,
// that accesses IN_PANIC won't hold onto a reference since we drop
// them before calling display_panic.
static mut IN_PANIC: bool = false;
unsafe {
if IN_PANIC {
println!("Panicked in panic!");
}
IN_PANIC = true;
}
display_panic(info);
loop {}
})
}
fn display_panic(info: &core::panic::PanicInfo) {
// Print to stdout unless no_panic is set. This includes the default case since
// printing to the screen during a panic is not always reliable.
#[cfg(not(feature = "no_panic"))]
min_panic(info);
// In the default case print the panic message to the screen
#[cfg(not(any(feature = "min_panic", feature = "no_panic")))]
normal_panic(info);
}
fn min_panic(info: &core::panic::PanicInfo) {
match info.location() {
Some(location) => {
println!(
"Panicked at {}:{}:{}",
location.file(),
location.line(),
location.column()
)
},
None => {
println!("Panicked at unknown location")
},
}
println!("{}", info.message());
}
fn normal_panic(info: &core::panic::PanicInfo) {
// We have no idea what state the GPU was in when the panic happened, so reset
// it to a known state and reload the font into VRAM.
let mut fb = Framebuffer::default();
let mut txt = fb.load_default_font().new_text_box((0, 8), (320, 240));
loop {
txt.reset();
match info.location() {
Some(location) => {
dprintln!(
txt,
"Panicked at {}:{}:{}",
location.file(),
location.line(),
location.column()
);
},
None => {
dprintln!(txt, "Panicked at unknown location");
},
}
dprintln!(txt, "{}", info.message());
fb.draw_sync();
fb.wait_vblank();
fb.swap();
}
}