Changeset 3593
- Timestamp:
- Sep 30, 2007, 11:41:15 PM (18 years ago)
- Location:
- trunk/kStuff/kProfiler2
- Files:
-
- 1 added
- 4 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/kStuff/kProfiler2/Makefile.kmk
r3591 r3593 142 142 $(PATH_kPrf2)/kPrf2.lib 143 143 144 PROGRAMS += tstlongjmp 145 tstlongjmp_TEMPLATE = kStuffEXE 146 tstlongjmp_CFLAGS.win = -GH -Gh -Zi 147 tstlongjmp_SOURCES = tstlongjmp.c 148 tstlongjmp_LIBS = \ 149 $(PATH_kPrf2)/kPrf2.lib 150 144 151 # Generate the rules 145 152 include $(PATH_KBUILD)/subfooter.kmk -
trunk/kStuff/kProfiler2/prfamd64msc.asm
r3592 r3593 91 91 or r8, rax ; param 3 - the timestamp 92 92 mov [rsp + 20h], r8 ; save the tsc for later use. 93 lea rdx, [rsp + 8*8 + 28h] ; Param 2 - frame pointer (pointer to the return address of the function calling us)93 lea rdx, [rsp + 8*8 + 28h] ; Param 2 - default frame pointer 94 94 mov rcx, [rdx] ; Param 1 - The function address 95 96 ; MSC seems to put the _penter both before and after the typical sub rsp, xxh 97 ; statement as if it cannot quite make up its mind. We'll try adjust for this 98 ; to make the unwinding a bit more accurate wrt to longjmp/throw. But since 99 ; there are also an uneven amount of push/pop around the _penter/_pexit we 100 ; can never really make a perfect job of it. sigh. 101 cmp word [rcx - 5 - 4], 08348h ; sub rsp, imm8 102 jne .not_byte_sub 103 cmp byte [rcx - 5 - 2], 0ech 104 jne .not_byte_sub 105 movzx eax, byte [rcx - 5 - 1] ; imm8 106 add rdx, rax 107 jmp .call_prf_enter 108 .not_byte_sub: 109 cmp word [rcx - 5 - 7], 08148h ; sub rsp, imm8 110 jne .not_dword_sub 111 cmp byte [rcx - 5 - 5], 0ech 112 jne .not_dword_sub 113 mov eax, [rcx - 5 - 4] ; imm32 114 add rdx, rax 115 ; jmp .call_prf_enter 116 .not_dword_sub: 117 .call_prf_enter: 95 118 call KPRF_ENTER 96 119 jmp common_return_path … … 135 158 or r8, rax ; param 3 - the timestamp 136 159 mov [rsp + 20h], r8 ; save the tsc for later use. 137 lea rdx, [rsp + 8*8 + 28h] ; Param 2 - frame pointer (pointer to the return address of the function calling us)160 lea rdx, [rsp + 8*8 + 28h] ; Param 2 - frame pointer. 138 161 mov rcx, [rdx] ; Param 1 - The function address 162 163 ; MSC some times put the _pexit before the add rsp, xxh. To try match up with 164 ; any adjustments made in _penter, we'll try detect this. 165 cmp word [rcx], 08348h ; add rsp, imm8 166 jne .not_byte_sub 167 cmp byte [rcx + 2], 0c4h 168 jne .not_byte_sub 169 movzx eax, byte [rcx + 3] ; imm8 170 add rdx, rax 171 jmp .call_prf_leave 172 .not_byte_sub: 173 cmp word [rcx], 08148h ; add rsp, imm32 174 jne .not_dword_sub 175 cmp byte [rcx + 2], 0c4h 176 jne .not_dword_sub 177 mov eax, [rcx + 3] ; imm32 178 add rdx, rax 179 ; jmp .call_prf_leave 180 .not_dword_sub: 181 .call_prf_leave: 139 182 call KPRF_LEAVE 140 183 jmp common_return_path -
trunk/kStuff/kProfiler2/prfcore.cpp.h
r3566 r3593 141 141 /** 142 142 * Unwinds the stack. 143 * 144 * On MSC+AMD64 we have to be very very careful here, because the uFramePtr cannot be trusted. 143 145 */ 144 146 static KU64* KPRF_NAME(UnwindInt)(KPRF_TYPE(P,HDR) pHdr, KPRF_TYPE(P,STACK) pStack, KPRF_TYPE(,UPTR) uPC, KPRF_TYPE(,UPTR) uFramePtr, KU64 TS) … … 151 153 KI32 iFrame = pStack->cFrames - 1; 152 154 KPRF_TYPE(P,FRAME) pFrame = &pStack->aFrames[iFrame]; 155 153 156 /* the most frequent case first. */ 157 #if K_OS == K_OS_WINDOWS && K_ARCH == K_ARCH_AMD64 158 if ( uFramePtr == pFrame->uFramePtr 159 || ( pFrame->uFramePtr < uFramePtr 160 && iFrame > 0 161 && pFrame[-1].uFramePtr > uFramePtr)) 162 return KPRF_NAME(UnwindOne)(pHdr, pStack, uPC, TS); 163 #else 154 164 if (uFramePtr == pFrame->uFramePtr) 155 165 return KPRF_NAME(UnwindOne)(pHdr, pStack, uPC, TS); 166 #endif 156 167 157 168 /* none? */ … … 161 172 /* one or more, possibly all */ 162 173 KU64 *pCurOverheadTicks = KPRF_NAME(UnwindOne)(pHdr, pStack, uPC, TS); 163 pFrame ++;174 pFrame--; 164 175 if ( iFrame > 0 176 #if K_OS == K_OS_WINDOWS && K_ARCH == K_ARCH_AMD64 177 && pFrame->uFramePtr <= uFramePtr 178 && pFrame[-1].uFramePtr > uFramePtr) 179 #else 165 180 && pFrame->uFramePtr <= uFramePtr) 181 #endif 166 182 { 167 183 KPRF_TYPE(P,THREAD) pThread = KPRF_OFF2PTR(P,THREAD, pStack->offThread, pHdr); … … 170 186 pCurOverheadTicks = KPRF_NAME(UnwindOne)(pHdr, pStack, uPC, TS); 171 187 iFrame -= 2; 172 pFrame++; 188 pFrame--; 189 #if K_OS == K_OS_WINDOWS && K_ARCH == K_ARCH_AMD64 190 while ( iFrame > 0 191 && pFrame->uFramePtr <= uFramePtr 192 && pFrame[-1].uFramePtr > uFramePtr) 193 #else 173 194 while ( iFrame >= 0 174 195 && pFrame->uFramePtr <= uFramePtr) 196 #endif 175 197 { 176 198 pCurOverheadTicks = KPRF_NAME(UnwindOne)(pHdr, pStack, uPC, TS); 177 199 iFrame--; 178 pFrame ++;200 pFrame--; 179 201 } 180 202 } … … 255 277 KPRF_TYPE(P,FRAME) pFrame = &pStack->aFrames[iFrame]; 256 278 if ( iFrame 279 #if K_OS == K_OS_WINDOWS && K_ARCH == K_ARCH_AMD64 280 && 0) /* don't bother her yet because of _penter/_pexit frame problems. */ 281 #else 257 282 && pThread->uStackBasePtr >= uFramePtr /* ASSUMES stack direction */ 258 283 && pFrame[-1].uFramePtr + (KPRF_BITS - 8) / 8 < uFramePtr) /* ASSUMES stack direction */ 284 #endif 259 285 { 260 286 KPRF_NAME(UnwindInt)(pHdr, pStack, uPC, uFramePtr, TS); -
trunk/kStuff/kProfiler2/prfcore.h.h
r3566 r3593 270 270 /** Stack address of this frame. 271 271 * This is used to detect throw and longjmp, and is also used to deal with overflow. (relative address) */ 272 KPRF_TYPE(,UPTR) uFramePtr;272 KPRF_TYPE(,UPTR) uFramePtr; 273 273 /** Offset (relative to the profiler header) to the function record. 274 274 * This is 0 if we're out of function space. */ … … 293 293 /** The stack frames. 294 294 * The actual size of this array is specified in the header. */ 295 KPRF_TYPE(,FRAME) aFrames[1];295 KPRF_TYPE(,FRAME) aFrames[1]; 296 296 } KPRF_TYPE(,STACK); 297 297 /** Pointer to a stack. */
Note:
See TracChangeset
for help on using the changeset viewer.