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
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
use cortex_m::{self, Handler};
#[cfg(feature = "default-exception-handler")]
use cortex_m::StackFrame;
use r0;
#[derive(Debug)]
pub enum Exception {
ThreadMode,
Nmi,
HardFault,
MemoryManagementFault,
BusFault,
UsageFault,
SVCall,
PendSV,
Systick,
Interrupt(u8),
#[doc(hidden)]
Reserved,
}
impl Exception {
pub fn current() -> Exception {
match cortex_m::peripheral::scb().icsr.read() as u8 {
0 => Exception::ThreadMode,
2 => Exception::Nmi,
3 => Exception::HardFault,
4 => Exception::MemoryManagementFault,
5 => Exception::BusFault,
6 => Exception::UsageFault,
11 => Exception::SVCall,
14 => Exception::PendSV,
15 => Exception::Systick,
n if n >= 16 => Exception::Interrupt(n - 16),
_ => Exception::Reserved,
}
}
}
#[cfg(all(target_arch = "arm", feature = "default-exception-handler"))]
#[doc(hidden)]
#[export_name = "_default_exception_handler"]
#[naked]
pub unsafe extern "C" fn default_handler_entry_point() {
use core::intrinsics;
asm!("mrs r0, MSP
ldr r1, [r0, #20]
b _default_exception_handler_impl" :::: "volatile");
intrinsics::unreachable();
}
#[cfg(feature = "default-exception-handler")]
#[doc(hidden)]
#[export_name = "_default_exception_handler_impl"]
pub unsafe extern "C" fn default_handler(sf: &StackFrame) -> ! {
iprintln!("EXCEPTION {:?} @ PC=0x{:08x}", Exception::current(), sf.pc);
bkpt!();
loop {}
}
#[link_section = ".text.exceptions"]
#[no_mangle]
pub static EXCEPTIONS: [Option<Handler>; 14] = [Some(_nmi),
Some(_hard_fault),
Some(_memmanage_fault),
Some(_bus_fault),
Some(_usage_fault),
None,
None,
None,
None,
Some(_svcall),
None,
None,
Some(_pendsv),
Some(_systick)];
extern "C" {
pub fn _nmi();
pub fn _hard_fault();
pub fn _memmanage_fault();
pub fn _bus_fault();
pub fn _usage_fault();
pub fn _svcall();
pub fn _pendsv();
pub fn _systick();
}
#[export_name = "_reset"]
pub unsafe extern "C" fn reset() -> ! {
#[cfg(feature = "default-init")]
use ::_init;
extern "C" {
static _ebss: u32;
static _edata: u32;
static _sidata: u32;
static mut _sbss: u32;
static mut _sdata: u32;
#[cfg(not(feature = "default-init"))]
fn _init();
fn main();
}
if &_sbss as *const u32 as usize != &_ebss as *const u32 as usize {
r0::zero_bss(&mut _sbss, &_ebss);
}
if &_sdata as *const u32 as usize != &_edata as *const u32 as usize {
r0::init_data(&mut _sdata, &_edata, &_sidata);
}
_init();
main();
panic!("returned from main!")
}