@@ -93,6 +93,32 @@ pub unsafe fn trace(cb: &mut FnMut(&super::Frame) -> bool) {
93
93
Err ( ( ) ) => return , // oh well...
94
94
} ;
95
95
96
+ // On x86_64 (and probably ARM64? need to verify at some point) we opt to
97
+ // not use the default `Sym*` functions from dbghelp for getting the
98
+ // function table and module base. Instead we use the
99
+ // `RtlLookupFunctionEntry` function in kernel32 which will account for JIT
100
+ // compiler frames as well. These should be equivalent, but using `Rtl*`
101
+ // allows us to backtrace through JIT frames.
102
+ cfg_if:: cfg_if! {
103
+ if #[ cfg( target_arch = "x86_64" ) ] {
104
+ use core:: ptr;
105
+
106
+ unsafe extern "system" fn function_table_access( _process: HANDLE , addr: DWORD64 ) -> PVOID {
107
+ let mut base = 0 ;
108
+ RtlLookupFunctionEntry ( addr, & mut base, ptr:: null_mut( ) ) . cast( )
109
+ }
110
+
111
+ unsafe extern "system" fn get_module_base( _process: HANDLE , addr: DWORD64 ) -> DWORD64 {
112
+ let mut base = 0 ;
113
+ RtlLookupFunctionEntry ( addr, & mut base, ptr:: null_mut( ) ) ;
114
+ base
115
+ }
116
+ } else {
117
+ let function_table_access = dbghelp. SymFunctionTableAccess64 ( ) ;
118
+ let get_module_base = dbghelp. SymGetModuleBase64 ( ) ;
119
+ }
120
+ }
121
+
96
122
// Attempt to use `StackWalkEx` if we can, but fall back to `StackWalk64`
97
123
// since it's in theory supported on more systems.
98
124
match ( * dbghelp. dbghelp ( ) ) . StackWalkEx ( ) {
@@ -113,8 +139,8 @@ pub unsafe fn trace(cb: &mut FnMut(&super::Frame) -> bool) {
113
139
frame_ptr,
114
140
& mut context. 0 as * mut CONTEXT as * mut _ ,
115
141
None ,
116
- Some ( dbghelp . SymFunctionTableAccess64 ( ) ) ,
117
- Some ( dbghelp . SymGetModuleBase64 ( ) ) ,
142
+ Some ( function_table_access ) ,
143
+ Some ( get_module_base ) ,
118
144
None ,
119
145
0 ,
120
146
) == TRUE
@@ -141,8 +167,8 @@ pub unsafe fn trace(cb: &mut FnMut(&super::Frame) -> bool) {
141
167
frame_ptr,
142
168
& mut context. 0 as * mut CONTEXT as * mut _ ,
143
169
None ,
144
- Some ( dbghelp . SymFunctionTableAccess64 ( ) ) ,
145
- Some ( dbghelp . SymGetModuleBase64 ( ) ) ,
170
+ Some ( function_table_access ) ,
171
+ Some ( get_module_base ) ,
146
172
None ,
147
173
) == TRUE
148
174
{
0 commit comments