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
#[derive(Debug, Clone)] pub struct Frame { rbp: u64, rsp: u64, rip: u64, } impl Frame { pub fn new(rbp: u64, rsp: u64, rip: u64) -> Frame { Frame { rbp: rbp, rsp: rsp, rip: rip, } } pub fn ip(&self) -> *mut u8 { (self.rip - 1) as *mut u8 } pub fn symbol_address(&self) -> *mut u8 { 0 as *mut u8 } } #[inline(always)] pub fn trace_from(mut curframe: Frame, cb: &mut dyn FnMut(&super::Frame) -> bool) { loop { let mut bomb = ::Bomb { enabled: true }; let ctxt = super::Frame { inner: curframe.clone(), }; let keep_going = cb(&ctxt); bomb.enabled = false; if keep_going { unsafe { curframe.rip = *((curframe.rbp + 8) as *mut u64); curframe.rsp = curframe.rbp; curframe.rbp = *(curframe.rbp as *mut u64); if curframe.rip == 0 || curframe.rbp <= 0xfff { break; } } } else { break; } } } #[inline(always)] pub fn trace(cb: &mut dyn FnMut(&super::Frame) -> bool) { use x86::current::registers; let curframe = Frame::new(registers::rbp(), registers::rsp(), registers::rip()); trace_from(curframe.clone(), cb); }