Contents

Practical Reverse Engineering Exercise Solutions: Windows Kernel Routines

Contents

I am currently developing my reverse engineering skills and want to keep some important parts of this journey as well in this blog.

The first step of this series relates to disassembling Windows kernel routines, in my case Windows 7.

What are the prerequisites for this exercise?

  • Ideally, install Windows inside a virtual machine
  • From Windows Vista onwards, the Kernel debugging mode has to be enabled with: bcdedit /debug on
  • Install Debugging Tools for Windows (for example, as part of the Windows SDK - https://www.microsoft.com/en-us/download/details.aspx?id=3138 for Windows 7, which contains the Kernel Debugger (KD))
  • Install LiveKD from the SysInternals Suite 
    • IMPORTANT: the livekd.exe file should be placed in the system32 folder

Notice that since we use LiveKD, we are essentially debugging the Kernel locally without a second system. With this approach, functions cannot be debugged as LiveKD uses a Kernel read-only memory dump as a basis.

If you have any questions to the usage of KD, the best resource available to my knowledge is the Windows help file included with the Windows SDK, debugger.chm. It contains a plethora of information and is especially helpful for the command line usage. Searching is possible by using the command .hh and the command you are interested in as an argument. For example, .hh uf would display the help menu for the uf command.

In order to start the Kernel Debugger, open a command line prompt with administrative privileges and start the LiveKd executable, which will invoke the KD.exe included in the Windows SDK:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
LiveKd v5.40 - Execute kd/windbg on a live system
Sysinternals - www.sysinternals.com
Copyright (C) 2000-2015 Mark Russinovich and Ken Johnson

Launching c:\Program Files\Debugging Tools for Windows (x86)\kd.exe:

Microsoft (R) Windows Debugger Version 6.12.0002.633 X86
Copyright (c) Microsoft Corporation. All rights reserved.


Loading Dump File [C:\Windows\livekd.dmp]
Kernel Complete Dump File: Full address space is available

Comment: 'LiveKD live system view'
Symbol search path is: srv*c:\Symbols*http://msdl.microsoft.com/download/symbo

Executable search path is:
Windows 7 Kernel Version 7601 (Service Pack 1) MP (4 procs) Free x86 compatibl
Product: WinNt, suite: TerminalServer SingleUserTS
Built by: 7601.19110.x86fre.win7sp1_gdr.151230-0600
Machine Name:
Kernel base = 0x8283c000 PsLoadedModuleList = 0x82987e30
Debug session time: Fri Jun 16 23:49:45.112 2017 (UTC - 7:00)
System Uptime: 0 days 2:01:39.545
WARNING: Process directory table base 00185000 doesn't match CR3 DF654620
WARNING: Process directory table base 00185000 doesn't match CR3 DF654620
Loading Kernel Symbols
...............................................................
................................................................
...................
Loading User Symbols

Loading unloaded module list
............
0: kd>

The Kernel Debugger has started successfully and we can proceed with our experiments.

Initially, we will disassemble the KeInitializeDpc Windows kernel routine, which is described in detail at: https://msdn.microsoft.com/en-us/library/windows/hardware/ff552130(v=vs.85).aspx

For obtaining the disassembly of this function, we will use the uf (unassemble function) command of the Kernel Debugger:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
0: kd> uf keinitializedpc
nt!KeInitializeDpc:
828ddc4e 8bff            mov     edi,edi
828ddc50 55              push    ebp
828ddc51 8bec            mov     ebp,esp
828ddc53 8b4508          mov     eax,dword ptr [ebp+8]
828ddc56 33c9            xor     ecx,ecx
828ddc58 83601c00        and     dword ptr [eax+1Ch],0
828ddc5c c60013          mov     byte ptr [eax],13h
828ddc5f c6400101        mov     byte ptr [eax+1],1
828ddc63 66894802        mov     word ptr [eax+2],cx
828ddc67 8b4d0c          mov     ecx,dword ptr [ebp+0Ch]
828ddc6a 89480c          mov     dword ptr [eax+0Ch],ecx
828ddc6d 8b4d10          mov     ecx,dword ptr [ebp+10h]
828ddc70 894810          mov     dword ptr [eax+10h],ecx
828ddc73 5d              pop     ebp
828ddc74 c20c00          ret     0Ch

As mentioned on  MSDN, the function transforms a (K)DPC object, which is defined in the Windows kernel. The command for analyzing datatypes in KD is the dt (display type).

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
0: kd> dt nt!_kdpc
   +0x000 Type             : UChar
   +0x001 Importance       : UChar
   +0x002 Number           : Uint2B
   +0x004 DpcListEntry     : _LIST_ENTRY
   +0x00c DeferredRoutine  : Ptr32     void
   +0x010 DeferredContext  : Ptr32 Void
   +0x014 SystemArgument1  : Ptr32 Void
   +0x018 SystemArgument2  : Ptr32 Void
   +0x01c DpcData          : Ptr32 Void

I found two other blogs on the Internet that published their results as well. You should definitely have a look at them likewise:

https://zerosum0x0.blogspot.de
https://johannesbader.ch/