Using Windbg PyKD Python Extension to Print/Break at Only Call Instructions
Question: Using WinDBG's python extension I want to print only call instructions in
console. [A kind of one step debugging ]

**My Code:**

    
    
    from pykd import *
    pid = raw_input ('pid >>> ')
    id=attachProcess(int(pid))
    print id
    while 1:
        trace()
        r_o = dbgCommand('r')
        line = r_o.split('\n')[-2]
        sp_line = line.split()
        addr = int(sp_line[0],16)
        ins = sp_line[2]
        if ins == "call":
            print line
    

I tried above code and got below result.

**Output :**

    
    
    C:\Program Files (x86)\Debugging Tools for Windows (x86)\winext>db.py
    [+] Starting...
    pid >>> 3516
    0
    76ec000d c3              ret
    76f4f926 eb07            jmp     ntdll!DbgUiRemoteBreakin+0x45 (76f4f92f)
    76f4f92f c745fcfeffffff  mov     dword ptr [ebp-4],0FFFFFFFEh ss:002b:0029ff84=00000000
    76f4f936 6a00            push    0
    76f4f938 e8df86fbff      call    ntdll!RtlExitUserThread (76f0801c)
    76ed0096 83c404          add     esp,4
    

Here the problem seems to be, after the debugger breaks into the process, the
debug thread gets initiated and the debug thread is getting terminated after
sometime, because its the current thread [We can see last call is made to
ntdll!RtlExitUserThread]. Hence even if the debugee app runs I don't see any
thing in command line.

I've seen a script which uses winappdbg and does the similar operation. Here
is the script :

<https://github.com/MarioVilas/winappdbg/blob/master/tools/ptrace.py>

And I want to build something similar.


Answer: not a pykd answer but windbgs inbuilt pc/tc (step / trace to next call) will
print out all the calls

    
    
    0:000> .printf "%y\n" , @eip
    multithread!wmain (00411430)
    0:000> $ iam at start of winmain and i have disabled all output except disassembly via .prompt_allow
    0:000> $ i have set a breakpoint on winmains exit 
    0:000> $ code for demo is exact copy paste of msdn sample code for createthread documentation
    0:000> $lets roll and log all call instructions 
    

**0:000> tc 1000000**

    
    
    0041147c ff1530824100    call    dword ptr [multithread!_imp__GetProcessHeap (00418230)]
    00411484 e8e9fcffff      call    multithread!ILT+365(__RTC_CheckEsp) (00411172)
    0041148a ff152c824100    call    dword ptr [multithread!_imp__HeapAlloc (0041822c)]
    7c955264 e827ffffff      call    ntdll!LdrpTagAllocateHeap (7c955190)
    7c9551b0 e80faffbff      call    ntdll!RtlAllocateHeap (7c9100c4)
    7c9100ce e8f8e7ffff      call    ntdll!_SEH_prolog (7c90e8cb)
    removed =====================
    7c923b25 e80b000000      call    ntdll!LdrShutdownProcess+0x1e0 (7c923b35)
    7c923b3a e8a1d5fdff      call    ntdll!RtlLeaveCriticalSection (7c9010e0)
    7c923b2a e8d7adfeff      call    ntdll!_SEH_epilog (7c90e906)
    7c81cac3 ff153410807c    call    dword ptr [kernel32!_imp__CsrClientCallServer (7c801034)]
    7c912de3 e8f6acffff      call    ntdll!NtRequestWaitReplyPort (7c90dade)
    7c90dae8 ff12            call    dword ptr [edx]
    7c90e512 0f34            sysenter
    7c81cacc ffd6            call    esi
    7c90de78 ff12            call    dword ptr [edx]
    7c90e512 0f34            sysenter
    7c90e514 c3              ret
    

if you are following the code in the msdn sample and would want to trace the
thread calls a breakpoint ( hack but will work in most situations) can be used

`.prompt_allow` to disable everything except dis-assembly  
set a `conditional break-point` on `CreateThread`  
condition being `setting another break point on poi(@esp+c)`
`LpThreadStartRoutine` and `continuing`  
the `next three pc 1000000` are step until next calls and `one quit`  
we `know we have three threads` in the sample so we automated pc 10000000  
three times `if you don't know` how many threads prior to execution manually
`enter pc 1000000 manually on each thread exit` .

**:cdb -c ".prompt_allow -src -reg -sym -ea ;g wmain;bp kernel32!CreateThread \"ba e1 poi( @esp+c) \\\"? $tid ;pc 100000 \\\";gc\";pc 100000;pc 1000000;pc 1000000 ;pc 1000000;pc 10000000;pc 1000000; pc 10000000;q" multithread.exe | grep -iE "W rite|Eval"**
    
    
    Evaluate expression: 2148 = 00000864
    004011c6 ff1520204000    call    dword ptr [multithread!_imp__WriteConsoleW (004
    02020)]
    Evaluate expression: 2780 = 00000adc
    004011c6 ff1520204000    call    dword ptr [multithread!_imp__WriteConsoleW (004
    02020)]
    Evaluate expression: 3440 = 00000d70
    004011c6 ff1520204000    call    dword ptr [multithread!_imp__WriteConsoleW (004
    02020)]
    

