Special Command—Unassembling code with u, ub and uf


When debugging sooner or later you will need to disassemble code to get a better understanding of that code.


By disassembling the code, you get the mnemonics translated from the 0s and 1s that constitute the binary code. It is a low level view of the code, but a higher level than seeing just numbers.


 


The commands syntaxes are:


 


u[b] [address]


u[b] [range]


u[b]


 


uf [options] <address>


 


Where options are:


 


/c – Displays only the call instructions in a routine.


/D – Creates linked callee names for navigation of the call graph.


/o – Sorts the display by address instead of by function offset.


/O – Creates linked call lines for accessing call information and creating breakpoints.


/i – Displays the number of instructions in a routine.


 


 


To demonstrate this command, let’s use this simple Visual C++ application that recursively calculates the Fibonacci from a specific number:


 


#include “stdafx.h”


 


using namespace std;


 


// Recursive function.


unsigned FiboRecursive(unsigned n, int nNum = 0)


{       


          if(n <= 1)


          {


                    return n;


          }


                   


          return FiboRecursive(n – 1, 1) + FiboRecursive(n – 2, 2);


}


 


int _tmain(int argc, _TCHAR* argv[])


{


          cout << FiboRecursive(5) << endl;


 


          return 0;


}


 


Let’s break the execution when the line from main() only is being executed, using a breakpoint for that.


 


Now let’s disassemble the eip register.


 


0:000> u @eip


Fibo!wmain+0x1e [c:\development\my tools\fibo\fibo\fibo.cpp @ 21]:


00a7145e 8bf4            mov     esi,esp


00a71460 a19882a700      mov     eax,dword ptr [Fibo!_imp_?endlstdYAAAV?$basic_ostreamDU?$char_traitsDstd (00a78298)]


00a71465 50              push    eax


00a71466 6a00            push    0


00a71468 6a05            push    5


00a7146a e89bfbffff      call    Fibo!ILT+5(?FiboRecursiveYAIIHZ) (00a7100a)


00a7146f 83c408          add     esp,8


00a71472 8bfc            mov     edi,esp


 


Using this approach we see the disassembled code starting from eip.


We can see the disassembled code that comes before eip using this approach:


 


0:000> ub @eip L8


Fibo!wmain+0x3 [c:\development\my tools\fibo\fibo\fibo.cpp @ 20]:


00a71443 81ecc0000000    sub     esp,0C0h


00a71449 53              push    ebx


00a7144a 56              push    esi


00a7144b 57              push    edi


00a7144c 8dbd40ffffff    lea     edi,[ebp-0C0h]


00a71452 b930000000      mov     ecx,30h


00a71457 b8cccccccc      mov     eax,0CCCCCCCCh


00a7145c f3ab            rep stos dword ptr es:[edi]


 


Keep in mind that b is for backward.


 


Let’s suppose you want to disassemble the entire function without having the work of finding the beginning of the function.


To accomplish that you use uf, and it automatically does that for you:


 


0:000> uf @eip


Fibo!wmain [c:\development\my tools\fibo\fibo\fibo.cpp @ 20]:


   20 00a71440 55              push    ebp


   20 00a71441 8bec            mov     ebp,esp


   20 00a71443 81ecc0000000    sub     esp,0C0h


   20 00a71449 53              push    ebx


   20 00a7144a 56              push    esi


   20 00a7144b 57              push    edi


   20 00a7144c 8dbd40ffffff    lea     edi,[ebp-0C0h]


   20 00a71452 b930000000      mov     ecx,30h


   20 00a71457 b8cccccccc      mov     eax,0CCCCCCCCh


   20 00a7145c f3ab            rep stos dword ptr es:[edi]


   21 00a7145e 8bf4            mov     esi,esp


   21 00a71460 a19882a700      mov     eax,dword ptr [Fibo!_imp_?endlstdYAAAV?$basic_ostreamDU?$char_traitsDstd (00a78298)]


   21 00a71465 50              push    eax


   21 00a71466 6a00            push    0


   21 00a71468 6a05            push    5


   21 00a7146a e89bfbffff      call    Fibo!ILT+5(?FiboRecursiveYAIIHZ) (00a7100a)


   21 00a7146f 83c408          add     esp,8


   21 00a71472 8bfc            mov     edi,esp


   21 00a71474 50              push    eax


   21 00a71475 8b0d9082a700    mov     ecx,dword ptr [Fibo!_imp_?coutstd (00a78290)]


   21 00a7147b ff159482a700    call    dword ptr [Fibo!_imp_??6?$basic_ostreamDU?$char_traitsDstdstdQAEAAV01IZ (00a78294)]


   21 00a71481 3bfc            cmp     edi,esp


   21 00a71483 e8d1fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   21 00a71488 8bc8            mov     ecx,eax


   21 00a7148a ff159c82a700    call    dword ptr [Fibo!_imp_??6?$basic_ostreamDU?$char_traitsDstdstdQAEAAV01P6AAAV01AAV01ZZ (00a7829c)]


   21 00a71490 3bf4            cmp     esi,esp


   21 00a71492 e8c2fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   23 00a71497 33c0            xor     eax,eax


   24 00a71499 5f              pop     edi


   24 00a7149a 5e              pop     esi


   24 00a7149b 5b              pop     ebx


   24 00a7149c 81c4c0000000    add     esp,0C0h


   24 00a714a2 3bec            cmp     ebp,esp


   24 00a714a4 e8b0fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   24 00a714a9 8be5            mov     esp,ebp


   24 00a714ab 5d              pop     ebp


   24 00a714ac c3              ret


 


Let’s see just the calls made by this function:


 


0:000> uf /c @eip


Fibo!wmain (00a71440) [c:\development\my tools\fibo\fibo\fibo.cpp @ 20]


  Fibo!wmain+0x2a (00a7146a) [c:\development\my tools\fibo\fibo\fibo.cpp @ 21]:


    call to Fibo!ILT+5(?FiboRecursiveYAIIHZ) (00a7100a)


  Fibo!wmain+0x3b (00a7147b) [c:\development\my tools\fibo\fibo\fibo.cpp @ 21]:


    call to MSVCP90D!std::basic_ostream<char,std::char_traits<char> >::operator<< (690fa700) [f:\dd\vctools\crt_bld\self_x86\crt\src\ostream @ 289]


  Fibo!wmain+0x43 (00a71483) [c:\development\my tools\fibo\fibo\fibo.cpp @ 21]:


    call to Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


  Fibo!wmain+0x4a (00a7148a) [c:\development\my tools\fibo\fibo\fibo.cpp @ 21]:


    call to MSVCP90D!std::basic_ostream<char,std::char_traits<char> >::operator<< (690f9f60) [f:\dd\vctools\crt_bld\self_x86\crt\src\ostream @ 171]


  Fibo!wmain+0x52 (00a71492) [c:\development\my tools\fibo\fibo\fibo.cpp @ 21]:


    call to Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


  Fibo!wmain+0x64 (00a714a4) [c:\development\my tools\fibo\fibo\fibo.cpp @ 24]:


    call to Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


 


 


Creates linked callee names from the same function:


 


0:000> uf /D @eip


Fibo!wmain [c:\development\my tools\fibo\fibo\fibo.cpp @ 20]:


   20 00a71440 55              push    ebp


   20 00a71441 8bec            mov     ebp,esp


   20 00a71443 81ecc0000000    sub     esp,0C0h


   20 00a71449 53              push    ebx


   20 00a7144a 56              push    esi


   20 00a7144b 57              push    edi


   20 00a7144c 8dbd40ffffff    lea     edi,[ebp-0C0h]


   20 00a71452 b930000000      mov     ecx,30h


   20 00a71457 b8cccccccc      mov     eax,0CCCCCCCCh


   20 00a7145c f3ab            rep stos dword ptr es:[edi]


   21 00a7145e 8bf4            mov     esi,esp


   21 00a71460 a19882a700      mov     eax,dword ptr [Fibo!_imp_?endlstdYAAAV?$basic_ostreamDU?$char_traitsDstd (00a78298)]


   21 00a71465 50              push    eax


   21 00a71466 6a00            push    0


   21 00a71468 6a05            push    5


   21 00a7146a e89bfbffff      call    Fibo!ILT+5(?FiboRecursiveYAIIHZ) (00a7100a)


   21 00a7146f 83c408          add     esp,8


   21 00a71472 8bfc            mov     edi,esp


   21 00a71474 50              push    eax


   21 00a71475 8b0d9082a700    mov     ecx,dword ptr [Fibo!_imp_?coutstd (00a78290)]


   21 00a7147b ff159482a700    call    dword ptr [Fibo!_imp_??6?$basic_ostreamDU?$char_traitsDstdstdQAEAAV01IZ (00a78294)]


   21 00a71481 3bfc            cmp     edi,esp


   21 00a71483 e8d1fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   21 00a71488 8bc8            mov     ecx,eax


   21 00a7148a ff159c82a700    call    dword ptr [Fibo!_imp_??6?$basic_ostreamDU?$char_traitsDstdstdQAEAAV01P6AAAV01AAV01ZZ (00a7829c)]


   21 00a71490 3bf4            cmp     esi,esp


   21 00a71492 e8c2fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   23 00a71497 33c0            xor     eax,eax


   24 00a71499 5f              pop     edi


   24 00a7149a 5e              pop     esi


   24 00a7149b 5b              pop     ebx


   24 00a7149c 81c4c0000000    add     esp,0C0h


   24 00a714a2 3bec            cmp     ebp,esp


   24 00a714a4 e8b0fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   24 00a714a9 8be5            mov     esp,ebp


   24 00a714ab 5d              pop     ebp


   24 00a714ac c3              ret


 


 


Sorts the output by address:


 


0:000> uf /o @eip


Fibo!wmain [c:\development\my tools\fibo\fibo\fibo.cpp @ 20]:


   20 00a71440 55              push    ebp


   20 00a71441 8bec            mov     ebp,esp


   20 00a71443 81ecc0000000    sub     esp,0C0h


   20 00a71449 53              push    ebx


   20 00a7144a 56              push    esi


   20 00a7144b 57              push    edi


   20 00a7144c 8dbd40ffffff    lea     edi,[ebp-0C0h]


   20 00a71452 b930000000      mov     ecx,30h


   20 00a71457 b8cccccccc      mov     eax,0CCCCCCCCh


   20 00a7145c f3ab            rep stos dword ptr es:[edi]


   21 00a7145e 8bf4            mov     esi,esp


   21 00a71460 a19882a700      mov     eax,dword ptr [Fibo!_imp_?endlstdYAAAV?$basic_ostreamDU?$char_traitsDstd (00a78298)]


   21 00a71465 50              push    eax


   21 00a71466 6a00            push    0


   21 00a71468 6a05            push    5


   21 00a7146a e89bfbffff      call    Fibo!ILT+5(?FiboRecursiveYAIIHZ) (00a7100a)


   21 00a7146f 83c408          add     esp,8


   21 00a71472 8bfc            mov     edi,esp


   21 00a71474 50              push    eax


   21 00a71475 8b0d9082a700    mov     ecx,dword ptr [Fibo!_imp_?coutstd (00a78290)]


   21 00a7147b ff159482a700    call    dword ptr [Fibo!_imp_??6?$basic_ostreamDU?$char_traitsDstdstdQAEAAV01IZ (00a78294)]


   21 00a71481 3bfc            cmp     edi,esp


   21 00a71483 e8d1fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   21 00a71488 8bc8            mov     ecx,eax


   21 00a7148a ff159c82a700    call    dword ptr [Fibo!_imp_??6?$basic_ostreamDU?$char_traitsDstdstdQAEAAV01P6AAAV01AAV01ZZ (00a7829c)]


   21 00a71490 3bf4            cmp     esi,esp


   21 00a71492 e8c2fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   23 00a71497 33c0            xor     eax,eax


   24 00a71499 5f              pop     edi


   24 00a7149a 5e              pop     esi


   24 00a7149b 5b              pop     ebx


   24 00a7149c 81c4c0000000    add     esp,0C0h


   24 00a714a2 3bec            cmp     ebp,esp


   24 00a714a4 e8b0fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   24 00a714a9 8be5            mov     esp,ebp


   24 00a714ab 5d              pop     ebp


   24 00a714ac c3              ret


 


 


Creates linked call lines for accessing call information and creating breakpoints:


 


0:000> uf /O @eip


Fibo!wmain [c:\development\my tools\fibo\fibo\fibo.cpp @ 20]:


   20 00a71440 55              push    ebp


   20 00a71441 8bec            mov     ebp,esp


   20 00a71443 81ecc0000000    sub     esp,0C0h


   20 00a71449 53              push    ebx


   20 00a7144a 56              push    esi


   20 00a7144b 57              push    edi


   20 00a7144c 8dbd40ffffff    lea     edi,[ebp-0C0h]


   20 00a71452 b930000000      mov     ecx,30h


   20 00a71457 b8cccccccc      mov     eax,0CCCCCCCCh


   20 00a7145c f3ab            rep stos dword ptr es:[edi]


   21 00a7145e 8bf4            mov     esi,esp


   21 00a71460 a19882a700      mov     eax,dword ptr [Fibo!_imp_?endlstdYAAAV?$basic_ostreamDU?$char_traitsDstd (00a78298)]


   21 00a71465 50              push    eax


   21 00a71466 6a00            push    0


   21 00a71468 6a05            push    5


   21 00a7146a e89bfbffff      call    Fibo!ILT+5(?FiboRecursiveYAIIHZ) (00a7100a)


   21 00a7146f 83c408          add     esp,8


   21 00a71472 8bfc            mov     edi,esp


   21 00a71474 50              push    eax


   21 00a71475 8b0d9082a700    mov     ecx,dword ptr [Fibo!_imp_?coutstd (00a78290)]


   21 00a7147b ff159482a700    call    dword ptr [Fibo!_imp_??6?$basic_ostreamDU?$char_traitsDstdstdQAEAAV01IZ (00a78294)]


   21 00a71481 3bfc            cmp     edi,esp


   21 00a71483 e8d1fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   21 00a71488 8bc8            mov     ecx,eax


   21 00a7148a ff159c82a700    call    dword ptr [Fibo!_imp_??6?$basic_ostreamDU?$char_traitsDstdstdQAEAAV01P6AAAV01AAV01ZZ (00a7829c)]


   21 00a71490 3bf4            cmp     esi,esp


   21 00a71492 e8c2fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   23 00a71497 33c0            xor     eax,eax


   24 00a71499 5f              pop     edi


   24 00a7149a 5e              pop     esi


   24 00a7149b 5b              pop     ebx


   24 00a7149c 81c4c0000000    add     esp,0C0h


   24 00a714a2 3bec            cmp     ebp,esp


   24 00a714a4 e8b0fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   24 00a714a9 8be5            mov     esp,ebp


   24 00a714ab 5d              pop     ebp


   24 00a714ac c3              ret


 


 


Displays the number of instructions in a routine:


 


0:000> uf /i @eip


37 instructions scanned


 


Fibo!wmain [c:\development\my tools\fibo\fibo\fibo.cpp @ 20]:


   20 00a71440 55              push    ebp


   20 00a71441 8bec            mov     ebp,esp


   20 00a71443 81ecc0000000    sub     esp,0C0h


   20 00a71449 53              push    ebx


   20 00a7144a 56              push    esi


   20 00a7144b 57              push    edi


   20 00a7144c 8dbd40ffffff    lea     edi,[ebp-0C0h]


   20 00a71452 b930000000      mov     ecx,30h


   20 00a71457 b8cccccccc      mov     eax,0CCCCCCCCh


   20 00a7145c f3ab            rep stos dword ptr es:[edi]


   21 00a7145e 8bf4            mov     esi,esp


   21 00a71460 a19882a700      mov     eax,dword ptr [Fibo!_imp_?endlstdYAAAV?$basic_ostreamDU?$char_traitsDstd (00a78298)]


   21 00a71465 50              push    eax


   21 00a71466 6a00            push    0


   21 00a71468 6a05            push    5


   21 00a7146a e89bfbffff      call    Fibo!ILT+5(?FiboRecursiveYAIIHZ) (00a7100a)


   21 00a7146f 83c408          add     esp,8


   21 00a71472 8bfc            mov     edi,esp


   21 00a71474 50              push    eax


   21 00a71475 8b0d9082a700    mov     ecx,dword ptr [Fibo!_imp_?coutstd (00a78290)]


   21 00a7147b ff159482a700    call    dword ptr [Fibo!_imp_??6?$basic_ostreamDU?$char_traitsDstdstdQAEAAV01IZ (00a78294)]


   21 00a71481 3bfc            cmp     edi,esp


   21 00a71483 e8d1fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   21 00a71488 8bc8            mov     ecx,eax


   21 00a7148a ff159c82a700    call    dword ptr [Fibo!_imp_??6?$basic_ostreamDU?$char_traitsDstdstdQAEAAV01P6AAAV01AAV01ZZ (00a7829c)]


   21 00a71490 3bf4            cmp     esi,esp


   21 00a71492 e8c2fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   23 00a71497 33c0            xor     eax,eax


   24 00a71499 5f              pop     edi


   24 00a7149a 5e              pop     esi


   24 00a7149b 5b              pop     ebx


   24 00a7149c 81c4c0000000    add     esp,0C0h


   24 00a714a2 3bec            cmp     ebp,esp


   24 00a714a4 e8b0fcffff      call    Fibo!ILT+340(__RTC_CheckEsp) (00a71159)


   24 00a714a9 8be5            mov     esp,ebp


   24 00a714ab 5d              pop     ebp


   24 00a714ac c3              ret


 


 


 

Comments (2)

  1. Marc Sherman says:

    Hi,

    The call stacks for

    uf @eip

    uf /D @eip

    uf /O @eip

    all look identical to me (I’m too lazy to do actual diffs). Am I missing something?

    thanks,

    Marc

  2. rafarah says:

    Marc you’re right and thanks for mentioning this! The problem is that the output has hyperlinks (DML) so when I copied and pasted it, it didn’t work! If you try the commands you’re going to see that some of them use hyperlinks.

Skip to main content