uf Command and Symbol Resolution

Is this broken or it it just me…

Symbols match:
0: kd> lml
start end module name
0000000077ec0000 0000000077ffb000 ntdll (pdb symbols) c:\symbols\ntdll.pdb\7ECDDF018BEF40068136BF66574633B32\ntdll.pdb
fffff80001000000 fffff80001496000 nt (pdb symbols) c:\symbols\ntkrnlmp.pdb\295F2F2B8EF54B51BEF2AF1556FB67942\ntkrnlmp.pdb

ln command shows function at fffff800010c4902 0: kd\> ln IoWriteCrashDump (fffff800010c4902) nt!IoWriteCrashDump | (fffff800010c52b0) nt!string’
Exact matches:
nt!IoWriteCrashDump =

u command agrees with ln:
0: kd> u IoWriteCrashDump
nt!IoWriteCrashDump:
fffff800010c4902 9c pushfq<br>fffff800010c4903 488bc4 mov rax,rsp
fffff800010c4906 4881ecb0010000 sub rsp,1B0h<br>fffff800010c490d 488958f8 mov qword ptr [rax-8],rbx
fffff800010c4911 488968f0 mov qword ptr [rax-10h],rbp<br>fffff800010c4915 488970e8 mov qword ptr [rax-18h],rsi
fffff800010c4919 488978e0 mov qword ptr [rax-20h],rdi<br>fffff800010c491d 4c8960d8 mov qword ptr [rax-28h],r12

uf command shows different address:
0: kd> uf IoWriteCrashDump
nt!IoWriteCrashDump:
fffff800010c4900 8bc0 mov eax,eax<br>fffff800010c4902 9c pushfq
fffff800010c4903 488bc4 mov rax,rsp<br>fffff800010c4906 4881ecb0010000 sub rsp,1B0h
fffff800010c490d 488958f8 mov qword ptr [rax-8],rbx<br>fffff800010c4911 488968f0 mov qword ptr [rax-10h],rbp
fffff800010c4915 488970e8 mov qword ptr [rax-18h],rsi<br>fffff800010c4919 488978e0 mov qword ptr [rax-20h],rdi
fffff800010c491d 4c8960d8 mov qword ptr [rax-28h],r12<br>fffff800010c4921 4c8968d0 mov qword ptr [rax-30h],r13
fffff800010c4925 33f6 xor esi,esi<br>fffff800010c4927 4c8978c0 mov qword ptr [rax-40h],r15
fffff800010c492b 498be9 mov rbp,r9<br>fffff800010c492e 403835fb751100 cmp byte ptr [nt!KdDebuggerEnabled (fffff800`011dbf30)],sil
fffff800`010c4935 4d8be0 mov r12,r8
fffff800`010c4938 4c8bea mov r13,rdx
fffff800`010c493b 448bf9 mov r15d,ecx
fffff800`010c493e 0f848c000000 je nt!IoWriteCrashDump+0xcf (fffff800`010c49d0)

nt!IoWriteCrashDump+0x43:
fffff800`010c4944 32db xor bl,bl
fffff800`010c4946 fa cli
fffff800`010c4947 8bbc24b0010000 mov edi,dword ptr [rsp+1B0h]
fffff800`010c494e c1ef09 shr edi,9
fffff800`010c4951 4080e701 and dil,1
fffff800`010c4955 381de1751100 cmp byte ptr [nt!KdpContext+0x4 (fffff800`011dbf3c)],bl
fffff800`010c495b 7412 je nt!IoWriteCrashDump+0x6e (fffff800`010c496f)

nt!IoWriteCrashDump+0x5c:
fffff800`010c495d c60546b10f0001 mov byte ptr [nt!KdpControlCPressed (fffff800`011bfaaa)],1

…etc…

Notice that the offset shown, above is inconsisten with both opinions about the function base:
nt!IoWriteCrashDump+0x43:
fffff800`010c4944 32db xor bl,bl

That is fffff800`010c4944 - fffff800`010c4902 = 42
and fffff800`010c4944 - fffff800`010c4900 = 44

And if you try to use it to set a breakpoint, it ends up at the wrong place:

0: kd> bp nt!IoWriteCrashDump+0x43
0: kd> bl
0 e fffff800`010c4945 0001 (0001) nt!IoWriteCrashDump+0x44

I first hit this a few releases back and I figured it would get fixed pretty quickily since the uf command is otherwise so useful. But here it is in 6.11.1.404.

Am I missing sometrhing?

Thanks,
Rex

Those uf output labels have nothing to do with the actual offsets in memory.
Try doing a uf of win32k!xxxSendBSMtoDesktop on XP, you’ll get positive
offsets for labels that are actually lower in memory:

win32k!xxxSendBSMtoDesktop+0x199:
bf8873af mov eax,dword ptr [ebx+18h]
bf8873b2 cmp eax,dword ptr [ebp-6Ch]
bf8873b5 je win32k!xxxSendBSMtoDesktop+0x1a5 (bf88749c)

win32k!xxxSendBSMtoDesktop+0x1a5:
bf8873bb jmp win32k!xxxSendBSMtoDesktop+0x326 (bf887519)

win32k!xxxSendBSMtoDesktop:
bf8873c5 mov edi,edi
bf8873c7 push ebp
bf8873c8 mov ebp,esp

It would be nice if the WinDBG folks documented what the algorithm was for
generating the labels (or used a different value), but I suspect it’s just
some artifact of the flow analysis.

I have no explanation whatsoever as for why uf is starting two bytes before
the symbol address though…

-scott


Scott Noone
Consulting Associate
OSR Open Systems Resources, Inc.
http://www.osronline.com

wrote in message news:xxxxx@windbg…
> Is this broken or it it just me…
>
> Symbols match:
> 0: kd> lml
> start end module name
> 0000000077ec0000 0000000077ffb000 ntdll (pdb symbols)
> c:\symbols\ntdll.pdb\7ECDDF018BEF40068136BF66574633B32\ntdll.pdb
> fffff80001000000 fffff80001496000 nt (pdb symbols)
> c:\symbols\ntkrnlmp.pdb\295F2F2B8EF54B51BEF2AF1556FB67942\ntkrnlmp.pdb
>
> ln command shows function at fffff800010c4902<br>&gt; 0: kd&gt; ln IoWriteCrashDump<br>&gt; (fffff800010c4902) nt!IoWriteCrashDump | (fffff800010c52b0) <br>&gt; nt!string’
> Exact matches:
> nt!IoWriteCrashDump =
>
> u command agrees with ln:
> 0: kd> u IoWriteCrashDump
> nt!IoWriteCrashDump:
> fffff800010c4902 9c pushfq<br>&gt; fffff800010c4903 488bc4 mov rax,rsp
> fffff800010c4906 4881ecb0010000 sub rsp,1B0h<br>&gt; fffff800010c490d 488958f8 mov qword ptr [rax-8],rbx
> fffff800010c4911 488968f0 mov qword ptr [rax-10h],rbp<br>&gt; fffff800010c4915 488970e8 mov qword ptr [rax-18h],rsi
> fffff800010c4919 488978e0 mov qword ptr [rax-20h],rdi<br>&gt; fffff800010c491d 4c8960d8 mov qword ptr [rax-28h],r12
>
> uf command shows different address:
> 0: kd> uf IoWriteCrashDump
> nt!IoWriteCrashDump:
> fffff800010c4900 8bc0 mov eax,eax<br>&gt; fffff800010c4902 9c pushfq
> fffff800010c4903 488bc4 mov rax,rsp<br>&gt; fffff800010c4906 4881ecb0010000 sub rsp,1B0h
> fffff800010c490d 488958f8 mov qword ptr [rax-8],rbx<br>&gt; fffff800010c4911 488968f0 mov qword ptr [rax-10h],rbp
> fffff800010c4915 488970e8 mov qword ptr [rax-18h],rsi<br>&gt; fffff800010c4919 488978e0 mov qword ptr [rax-20h],rdi
> fffff800010c491d 4c8960d8 mov qword ptr [rax-28h],r12<br>&gt; fffff800010c4921 4c8968d0 mov qword ptr [rax-30h],r13
> fffff800010c4925 33f6 xor esi,esi<br>&gt; fffff800010c4927 4c8978c0 mov qword ptr [rax-40h],r15
> fffff800010c492b 498be9 mov rbp,r9<br>&gt; fffff800010c492e 403835fb751100 cmp byte ptr [nt!KdDebuggerEnabled
> (fffff800`011dbf30)],sil
> fffff800`010c4935 4d8be0 mov r12,r8
> fffff800`010c4938 4c8bea mov r13,rdx
> fffff800`010c493b 448bf9 mov r15d,ecx
> fffff800`010c493e 0f848c000000 je nt!IoWriteCrashDump+0xcf
> (fffff800`010c49d0)
>
> nt!IoWriteCrashDump+0x43:
> fffff800`010c4944 32db xor bl,bl
> fffff800`010c4946 fa cli
> fffff800`010c4947 8bbc24b0010000 mov edi,dword ptr [rsp+1B0h]
> fffff800`010c494e c1ef09 shr edi,9
> fffff800`010c4951 4080e701 and dil,1
> fffff800`010c4955 381de1751100 cmp byte ptr [nt!KdpContext+0x4
> (fffff800`011dbf3c)],bl
> fffff800`010c495b 7412 je nt!IoWriteCrashDump+0x6e
> (fffff800`010c496f)
>
> nt!IoWriteCrashDump+0x5c:
> fffff800`010c495d c60546b10f0001 mov byte ptr [nt!KdpControlCPressed
> (fffff800`011bfaaa)],1
>
> …etc…
>
>
> Notice that the offset shown, above is inconsisten with both opinions
> about the function base:
> nt!IoWriteCrashDump+0x43:
> fffff800`010c4944 32db xor bl,bl
>
> That is fffff800`010c4944 - fffff800`010c4902 = 42
> and fffff800`010c4944 - fffff800`010c4900 = 44
>
>
> And if you try to use it to set a breakpoint, it ends up at the wrong
> place:
>
> 0: kd> bp nt!IoWriteCrashDump+0x43
> 0: kd> bl
> 0 e fffff800`010c4945 0001 (0001) nt!IoWriteCrashDump+0x44
>
> I first hit this a few releases back and I figured it would get fixed
> pretty quickily since the uf command is otherwise so useful. But here it
> is in 6.11.1.404.
>
> Am I missing sometrhing?
>
> Thanks,
> Rex
>

Scott Noone wrote:

Those uf output labels have nothing to do with the actual offsets in memory.
Try doing a uf of win32k!xxxSendBSMtoDesktop on XP, you’ll get positive
offsets for labels that are actually lower in memory:

It would be nice if the WinDBG folks documented what the algorithm was for
generating the labels (or used a different value), but I suspect it’s just
some artifact of the flow analysis.

We had an extensive discussion about this last year. The basic cause
for this is that the linker, the system loader, and some other
optimization tools will reorganize the code in an executable, in an
attempt to improve paging behavior and locality of reference. WinDbg is
still trying to use the symbolic information that the original compiler
produced. So, the code labeled Xxx+0x100 did start out from the
compiler at 0x100 bytes past the Xxx label, but by the time it was
loaded, it might be at a different address.

There was much debate at the time over whether WinDbg should be showing
us the compiler-relative addresses, or the live-in-memory addresses,
with no final resolution.


Tim Roberts, xxxxx@probo.com
Providenza & Boekelheide, Inc.

This is documented in debugger help. Please check http://msdn.microsoft.com/en-us/library/cc266465.aspx

-----Original Message-----
From: xxxxx@lists.osr.com [mailto:xxxxx@lists.osr.com] On Behalf Of Tim Roberts
Sent: Thursday, July 09, 2009 03:48 PM
To: Kernel Debugging Interest List
Subject: Re: [windbg] uf Command and Symbol Resolution

Scott Noone wrote:

Those uf output labels have nothing to do with the actual offsets in memory.
Try doing a uf of win32k!xxxSendBSMtoDesktop on XP, you’ll get positive
offsets for labels that are actually lower in memory:

It would be nice if the WinDBG folks documented what the algorithm was for
generating the labels (or used a different value), but I suspect it’s just
some artifact of the flow analysis.

We had an extensive discussion about this last year. The basic cause
for this is that the linker, the system loader, and some other
optimization tools will reorganize the code in an executable, in an
attempt to improve paging behavior and locality of reference. WinDbg is
still trying to use the symbolic information that the original compiler
produced. So, the code labeled Xxx+0x100 did start out from the
compiler at 0x100 bytes past the Xxx label, but by the time it was
loaded, it might be at a different address.

There was much debate at the time over whether WinDbg should be showing
us the compiler-relative addresses, or the live-in-memory addresses,
with no final resolution.


Tim Roberts, xxxxx@probo.com
Providenza & Boekelheide, Inc.


WINDBG is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at http://www.osronline.com/page.cfm?name=ListServer

I was hoping to find that discussion and post it with my reply, but couldn’t
find it with some casual googling.

The problem and confusion is that you get different results based on the
command you use (which I suspect is what is messing up the OP). The link
posted by Jen-Lung actually explains this nicely (thanks Jen-Lung!).

My personal preference would be to have the results be consistent so that
you could feed a lab from uf to the u command and get the same result. It
would save future generations from having to worry about this.

-scott


Scott Noone
Consulting Associate
OSR Open Systems Resources, Inc.
http://www.osronline.com

“Tim Roberts” wrote in message news:xxxxx@windbg…
> Scott Noone wrote:
>> Those uf output labels have nothing to do with the actual offsets in
>> memory.
>> Try doing a uf of win32k!xxxSendBSMtoDesktop on XP, you’ll get positive
>> offsets for labels that are actually lower in memory:
>> …
>> It would be nice if the WinDBG folks documented what the algorithm was
>> for
>> generating the labels (or used a different value), but I suspect it’s
>> just
>> some artifact of the flow analysis.
>>
>
> We had an extensive discussion about this last year. The basic cause
> for this is that the linker, the system loader, and some other
> optimization tools will reorganize the code in an executable, in an
> attempt to improve paging behavior and locality of reference. WinDbg is
> still trying to use the symbolic information that the original compiler
> produced. So, the code labeled Xxx+0x100 did start out from the
> compiler at 0x100 bytes past the Xxx label, but by the time it was
> loaded, it might be at a different address.
>
> There was much debate at the time over whether WinDbg should be showing
> us the compiler-relative addresses, or the live-in-memory addresses,
> with no final resolution.
>
> –
> Tim Roberts, xxxxx@probo.com
> Providenza & Boekelheide, Inc.
>
>

This is actually a limitation of the symbol data not accounting for optimizations that reorder functions to not be contiguous in memory.

Ignore the offset from function start as it is not kept up to date for “chunked” functions like that.

  • S

-----Original Message-----
From: Scott Noone
Sent: Thursday, July 09, 2009 15:21
To: Kernel Debugging Interest List
Subject: Re:[windbg] uf Command and Symbol Resolution

Those uf output labels have nothing to do with the actual offsets in memory.
Try doing a uf of win32k!xxxSendBSMtoDesktop on XP, you’ll get positive
offsets for labels that are actually lower in memory:

win32k!xxxSendBSMtoDesktop+0x199:
bf8873af mov eax,dword ptr [ebx+18h]
bf8873b2 cmp eax,dword ptr [ebp-6Ch]
bf8873b5 je win32k!xxxSendBSMtoDesktop+0x1a5 (bf88749c)

win32k!xxxSendBSMtoDesktop+0x1a5:
bf8873bb jmp win32k!xxxSendBSMtoDesktop+0x326 (bf887519)

win32k!xxxSendBSMtoDesktop:
bf8873c5 mov edi,edi
bf8873c7 push ebp
bf8873c8 mov ebp,esp

It would be nice if the WinDBG folks documented what the algorithm was for
generating the labels (or used a different value), but I suspect it’s just
some artifact of the flow analysis.

I have no explanation whatsoever as for why uf is starting two bytes before
the symbol address though…

-scott


Scott Noone
Consulting Associate
OSR Open Systems Resources, Inc.
http://www.osronline.com

wrote in message news:xxxxx@windbg…
> Is this broken or it it just me…
>
> Symbols match:
> 0: kd> lml
> start end module name
> 0000000077ec0000 0000000077ffb000 ntdll (pdb symbols)
> c:\symbols\ntdll.pdb\7ECDDF018BEF40068136BF66574633B32\ntdll.pdb
> fffff80001000000 fffff80001496000 nt (pdb symbols)
> c:\symbols\ntkrnlmp.pdb\295F2F2B8EF54B51BEF2AF1556FB67942\ntkrnlmp.pdb
>
> ln command shows function at fffff800010c4902<br>&gt; 0: kd&gt; ln IoWriteCrashDump<br>&gt; (fffff800010c4902) nt!IoWriteCrashDump | (fffff800010c52b0)<br>&gt; nt!string’
> Exact matches:
> nt!IoWriteCrashDump =
>
> u command agrees with ln:
> 0: kd> u IoWriteCrashDump
> nt!IoWriteCrashDump:
> fffff800010c4902 9c pushfq<br>&gt; fffff800010c4903 488bc4 mov rax,rsp
> fffff800010c4906 4881ecb0010000 sub rsp,1B0h<br>&gt; fffff800010c490d 488958f8 mov qword ptr [rax-8],rbx
> fffff800010c4911 488968f0 mov qword ptr [rax-10h],rbp<br>&gt; fffff800010c4915 488970e8 mov qword ptr [rax-18h],rsi
> fffff800010c4919 488978e0 mov qword ptr [rax-20h],rdi<br>&gt; fffff800010c491d 4c8960d8 mov qword ptr [rax-28h],r12
>
> uf command shows different address:
> 0: kd> uf IoWriteCrashDump
> nt!IoWriteCrashDump:
> fffff800010c4900 8bc0 mov eax,eax<br>&gt; fffff800010c4902 9c pushfq
> fffff800010c4903 488bc4 mov rax,rsp<br>&gt; fffff800010c4906 4881ecb0010000 sub rsp,1B0h
> fffff800010c490d 488958f8 mov qword ptr [rax-8],rbx<br>&gt; fffff800010c4911 488968f0 mov qword ptr [rax-10h],rbp
> fffff800010c4915 488970e8 mov qword ptr [rax-18h],rsi<br>&gt; fffff800010c4919 488978e0 mov qword ptr [rax-20h],rdi
> fffff800010c491d 4c8960d8 mov qword ptr [rax-28h],r12<br>&gt; fffff800010c4921 4c8968d0 mov qword ptr [rax-30h],r13
> fffff800010c4925 33f6 xor esi,esi<br>&gt; fffff800010c4927 4c8978c0 mov qword ptr [rax-40h],r15
> fffff800010c492b 498be9 mov rbp,r9<br>&gt; fffff800010c492e 403835fb751100 cmp byte ptr [nt!KdDebuggerEnabled
> (fffff800`011dbf30)],sil
> fffff800`010c4935 4d8be0 mov r12,r8
> fffff800`010c4938 4c8bea mov r13,rdx
> fffff800`010c493b 448bf9 mov r15d,ecx
> fffff800`010c493e 0f848c000000 je nt!IoWriteCrashDump+0xcf
> (fffff800`010c49d0)
>
> nt!IoWriteCrashDump+0x43:
> fffff800`010c4944 32db xor bl,bl
> fffff800`010c4946 fa cli
> fffff800`010c4947 8bbc24b0010000 mov edi,dword ptr [rsp+1B0h]
> fffff800`010c494e c1ef09 shr edi,9
> fffff800`010c4951 4080e701 and dil,1
> fffff800`010c4955 381de1751100 cmp byte ptr [nt!KdpContext+0x4
> (fffff800`011dbf3c)],bl
> fffff800`010c495b 7412 je nt!IoWriteCrashDump+0x6e
> (fffff800`010c496f)
>
> nt!IoWriteCrashDump+0x5c:
> fffff800`010c495d c60546b10f0001 mov byte ptr [nt!KdpControlCPressed
> (fffff800`011bfaaa)],1
>
> …etc…
>
>
> Notice that the offset shown, above is inconsisten with both opinions
> about the function base:
> nt!IoWriteCrashDump+0x43:
> fffff800`010c4944 32db xor bl,bl
>
> That is fffff800`010c4944 - fffff800`010c4902 = 42
> and fffff800`010c4944 - fffff800`010c4900 = 44
>
>
> And if you try to use it to set a breakpoint, it ends up at the wrong
> place:
>
> 0: kd> bp nt!IoWriteCrashDump+0x43
> 0: kd> bl
> 0 e fffff800`010c4945 0001 (0001) nt!IoWriteCrashDump+0x44
>
> I first hit this a few releases back and I figured it would get fixed
> pretty quickily since the uf command is otherwise so useful. But here it
> is in 6.11.1.404.
>
> Am I missing sometrhing?
>
> Thanks,
> Rex
>


WINDBG is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at http://www.osronline.com/page.cfm?name=ListServer

If you feed the raw virtual address back in, and not a symbol reference in the form of “function+offset”, you will get consistent results. That is what I recommend.

  • S

-----Original Message-----
From: Scott Noone
Sent: Thursday, July 09, 2009 16:15
To: Kernel Debugging Interest List
Subject: Re:[windbg] uf Command and Symbol Resolution

I was hoping to find that discussion and post it with my reply, but couldn’t
find it with some casual googling.

The problem and confusion is that you get different results based on the
command you use (which I suspect is what is messing up the OP). The link
posted by Jen-Lung actually explains this nicely (thanks Jen-Lung!).

My personal preference would be to have the results be consistent so that
you could feed a lab from uf to the u command and get the same result. It
would save future generations from having to worry about this.

-scott


Scott Noone
Consulting Associate
OSR Open Systems Resources, Inc.
http://www.osronline.com

“Tim Roberts” wrote in message news:xxxxx@windbg…
> Scott Noone wrote:
>> Those uf output labels have nothing to do with the actual offsets in
>> memory.
>> Try doing a uf of win32k!xxxSendBSMtoDesktop on XP, you’ll get positive
>> offsets for labels that are actually lower in memory:
>> …
>> It would be nice if the WinDBG folks documented what the algorithm was
>> for
>> generating the labels (or used a different value), but I suspect it’s
>> just
>> some artifact of the flow analysis.
>>
>
> We had an extensive discussion about this last year. The basic cause
> for this is that the linker, the system loader, and some other
> optimization tools will reorganize the code in an executable, in an
> attempt to improve paging behavior and locality of reference. WinDbg is
> still trying to use the symbolic information that the original compiler
> produced. So, the code labeled Xxx+0x100 did start out from the
> compiler at 0x100 bytes past the Xxx label, but by the time it was
> loaded, it might be at a different address.
>
> There was much debate at the time over whether WinDbg should be showing
> us the compiler-relative addresses, or the live-in-memory addresses,
> with no final resolution.
>
> –
> Tim Roberts, xxxxx@probo.com
> Providenza & Boekelheide, Inc.
>
>


WINDBG is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at http://www.osronline.com/page.cfm?name=ListServer

Thanks, everyone. I guess this sums it up:

“Since the debugger will try to stay close to the original code, you might see some amusing results.”

Rex