1pub type UnwContext = libc::ucontext_t;
5
6pub type UnwWord = u64;
7
8#[repr(C)]
10#[derive(Debug, Copy, Clone)]
11pub struct UnwCursor {
12 pub opaque: [UnwWord; 250],
13}
14
15pub type UnwAddrSpaceT = *mut libc::c_void;
17
18#[repr(C)]
20pub struct UnwAccessors;
21
22extern "C" {
23 #[link_name = "_ULaarch64_init_local2"]
24 pub fn unw_init_local2(cursor: *mut UnwCursor, context: *mut UnwContext, flag: i32) -> i32;
25 #[link_name = "_ULaarch64_step"]
26 pub fn unw_step(cursor: *mut UnwCursor) -> i32;
27 #[link_name = "_ULaarch64_get_reg"]
28 pub fn unw_get_reg(cursor: *mut UnwCursor, reg: i32, valp: *mut UnwWord) -> i32;
29 #[link_name = "_ULaarch64_get_proc_name"]
30 pub fn unw_get_proc_name(
31 cursor: *mut UnwCursor,
32 name: *mut libc::c_char,
33 len: usize,
34 offset: *mut u64,
35 ) -> i32;
36 #[link_name = "unw_backtrace2"]
37 pub fn unw_backtrace2(
38 buffer: *mut *mut ::std::os::raw::c_void,
39 size: i32,
40 context: *mut UnwContext,
41 flag: i32,
42 ) -> i32;
43}
44
45#[allow(improper_ctypes)]
48extern "C" {
49 #[link_name = "_Uaarch64_init_remote"]
50 pub fn unw_init_remote(
51 cursor: *mut UnwCursor,
52 addr_space: UnwAddrSpaceT,
53 arg: *mut libc::c_void,
54 ) -> i32;
55 #[link_name = "_Uaarch64_step"]
56 pub fn unw_step_remote(cursor: *mut UnwCursor) -> i32;
57 #[link_name = "_Uaarch64_get_reg"]
58 pub fn unw_get_reg_remote(cursor: *mut UnwCursor, reg: i32, valp: *mut UnwWord) -> i32;
59 #[link_name = "_Uaarch64_get_proc_name"]
60 pub fn unw_get_proc_name_remote(
61 cursor: *mut UnwCursor,
62 name: *mut libc::c_char,
63 len: usize,
64 offset: *mut UnwWord,
65 ) -> i32;
66 #[link_name = "_Uaarch64_create_addr_space"]
67 pub fn unw_create_addr_space(accessors: *mut UnwAccessors, byteorder: i32) -> UnwAddrSpaceT;
68 #[link_name = "_Uaarch64_destroy_addr_space"]
69 pub fn unw_destroy_addr_space(addr_space: UnwAddrSpaceT);
70 pub fn _UPT_create(pid: libc::pid_t) -> *mut libc::c_void;
71 pub fn _UPT_destroy(upt_info: *mut libc::c_void);
72 pub static _UPT_accessors: UnwAccessors;
73}
74
75pub const UNW_REG_IP: i32 = 30; pub const UNW_REG_SP: i32 = 31; pub const UNW_REG_FP: i32 = 29; pub const UNW_INIT_LOCAL_ONLY_IP: i32 = 1;
79
80#[cfg(test)]
89#[inline(always)]
90pub unsafe fn getcontext(context: *mut UnwContext) -> i32 {
91 let base = core::ptr::addr_of_mut!((*context).uc_mcontext.regs) as u64;
92 let ret: u64;
93 core::arch::asm!(
94 "stp x0, x1, [x0, #0]",
95 "stp x2, x3, [x0, #16]",
96 "stp x4, x5, [x0, #32]",
97 "stp x6, x7, [x0, #48]",
98 "stp x8, x9, [x0, #64]",
99 "stp x10, x11, [x0, #80]",
100 "stp x12, x13, [x0, #96]",
101 "stp x14, x15, [x0, #112]",
102 "stp x16, x17, [x0, #128]",
103 "stp x18, x19, [x0, #144]",
104 "stp x20, x21, [x0, #160]",
105 "stp x22, x23, [x0, #176]",
106 "stp x24, x25, [x0, #192]",
107 "stp x26, x27, [x0, #208]",
108 "stp x28, x29, [x0, #224]",
109 "mov x1, sp",
110 "stp x30, x1, [x0, #240]",
111 "adr x1, 2f",
112 "str x1, [x0, #256]",
113 "mov x0, #0",
114 "2:",
115 inout("x0") base => ret,
116 out("x1") _,
117 options(nostack, preserves_flags),
118 );
119 ret as i32
120}