1use num_derive::FromPrimitive;
2use num_traits::FromPrimitive;
3
4#[repr(u32)]
7#[derive(Copy, Clone, Debug, FromPrimitive, PartialEq)]
8pub enum TrapCode {
9 StackOverflow = 0,
10 HeapOutOfBounds = 1,
11 OutOfBounds = 2,
12 IndirectCallToNull = 3,
13 BadSignature = 4,
14 IntegerOverflow = 5,
15 IntegerDivByZero = 6,
16 BadConversionToInteger = 7,
17 Interrupt = 8,
18 TableOutOfBounds = 9,
19 Unreachable = 10,
20}
21
22impl TrapCode {
23 pub fn try_from_u32(v: u32) -> Option<TrapCode> {
24 Self::from_u32(v)
25 }
26}
27
28#[repr(C)]
35#[derive(Clone, Debug)]
36pub struct TrapSite {
37 pub offset: u32,
38 pub code: TrapCode,
39}
40
41#[repr(C)]
44#[derive(Clone, Debug)]
45pub struct TrapManifest<'a> {
46 pub traps: &'a [TrapSite],
47}
48
49impl<'a> TrapManifest<'a> {
50 pub fn new(traps: &'a [TrapSite]) -> TrapManifest<'_> {
51 TrapManifest { traps }
52 }
53 pub fn lookup_addr(&self, addr: u32) -> Option<TrapCode> {
54 let f = |ts: &TrapSite| ts.offset.cmp(&addr);
56
57 if let Ok(i) = self.traps.binary_search_by(f) {
58 Some(self.traps[i].code)
59 } else {
60 None
61 }
62 }
63}