Quick introduction to WinDbg

Gaurav yadav
RIXED_LABS
Published in
7 min readFeb 11, 2021

--

About WinDbg

Windbg is a debugger which used on Windows platform and as per my opinion is more powerful than other debuggers like Ollydbg because Windbg can work in both user mode and kernel mode which means that you can debug user mode applications like exe’s, and you can debug privileged kernel code of the OS too. If you have experience with command based debuggers or with GUI based debugger you can easily get hands on Windbg easily because Windbg allow the user to work with GUI as well as commands, but mostly it is a command driven debugger. It can also be used for analyzing crash dumps.

Let’s get started

If you want to install Windbg you can check out Microsoft official website, which leads you to the entire whole process to get it started on your machine. Now lets run Windbg and see what it offers to the reverse engineers.

First view

When you open Windbg this is the GUI you are going to see. There are 4 main windows which you are going to see by default which are command window, disassembly window, locals windows and stack window. Let’s get a brief introduction of these :

Command window : This window is used to type in the commands and to examine output of the commands.

Disassembly window: This window will show you the assembly code of the the binary that you are currently analyzing

Locals window : This window will show you all the local variable and their values for the current function

Stack window : This window shows the current call stack the function you are currently in is on the top and the next function is the function which called the current one.

We will see working of these windows with the help of examples. Now let’s open our executable in Windbg. When you will click on the file menu you will see these options.

Here you can see we have many options. We can open different kind of files like executables, dump file and trace file. We can even choose to attach Windbg to any running process. Windbg also give us the option to attach to kernel for kernel debugging which is one of the advantages of Windbg over other debuggers and indeed my favorite one. Now lets click on the option to launch executable and select the file to open in Windbg. If you are trying out WinDbg, I would suggest you to write a simple C program and try to debug it, keeping the source code handy of the executable and opening it on the side might help you to analyze the executable more easily but off course we may not have source code every time so let's just open executable now. I will be using an executable that I created, you can use the same for this tutorial.

After launching an executable in Windbg you will see that windbg will try to find the symbol file path since I have compiled my executable myself I have my symbol file so windbg will automatically consider it. If you want Windbg to use a symbol file which is present elsewhere you can use .sympath //file_path command. Symbol file is important for debugging but it is not necessary because it contains Global variables ,Local variables ,Function names and the addresses of their entry points ,Frame pointer omission (FPO) records and source-line numbers. After providing the path of symbol file I will attach the source file too for better debugging as said above. Now our windows should look like this.

Breakpoints

As you can observe in stack window that we are currently in ntdll we want to go to our main function, so we will have to set a breakpoint at main function we can do that either by typing a command bp Windbg_tuto!main where Windbg_tuto is my binary name and main is the function to which I want to set a breakpoint, they both are separated by a ! or you can just click on the specific line and press F9 to put a breakpoint either in assembly window or source window. You can check the position of breakpoint in source code by a red dot in front of that line or a red marked line in assembly. If you want to check all the breakpoints for the current binary you can check that in Breakpoints windows which you can toggle below stack window, or you can use a command bl which will get the work done for you.

If you see the output of command bl you can see that there is a number at the starting which tells the id of a breakpoint we can use it if we want to disable this breakpoint (note : disable doesn’t mean removing the breakpoint) the command will look like this bd 0 to enable that breakpoint you can use command be 0. If you want to remove a breakpoint permanently you can use bc (breakpoint clear)command with the breakpoint id for ex: bc 0 to remove 0th breakpoint and bc * to remove all the breakpoints. Now let's execute the binary till hit the breakpoint that we had set, we can do this either by clicking a green play button in Home tab or by command g.

Execution

Now if you observe you stack you can see that the first function there is Windbg_tuto!main now we know that we are in our main function. Locals window is also showing us the variable name and their data type present in main function you can also do that through command window using dv command. If you want to know about the type of particular variable/symbol you can use command dt for our case the command will be dt name to check the type of name variable.

Now let’s talk about how we can step through the code using commands or GUI there are three main stepping option explained below:

Step out : Allows you to execute instruction until the current function is complete. Command used : gu ,can also be done through Step out option in Home menu.

Step into : Allows you to execute one instruction and if that instruction is a function call then debugger will take you inside that function . Command used : t , can also be done through Step into option in Home menu .

Step over : Allows you to on instruction and if that instruction is a function call then debugger will execute it in single step (will not go inside the call). Command used : p, can also be done through Step over option in Home menu.

Executing of every single stepping command will also show you the values of registers after every execution if you want to see the value of registers without executing you can use command r to display the registers, and you can change the value of a register too for example if we want to change the value of eax to 0xff then we can use the r command like this : r eax=0xff.

Miscellaneous

If you don’t like to open a disassembly window side by side, or you don't have enough space on the screen for disassembly window you can also see the disassembly in the command window too with the help of the command u. For example command : u 0x006c5b11 0x006c5b27 will disassemble the instruction in the following range and command : uf Windbg_tuto!main will disassemble the whole main function.

If you want to know statistics about a function without tracing through the whole function yourself like number of function executed, number of function executed by a child process and depth of function on stack you can use a command : wt. This command will list the instructions that were executed throughout the function and their statistics.

Handy Cheat sheet

To put a breakpoint : bp <module_name!function_name>

To list all breakpoints : bl

To disable a breakpoint : bd <breakpoint_id>

To enable a breakpoint : be <breakpoint_id>

To clear all break point : bc *

To execute the instructions : g

To execute the instruction until current function ends : gu

Trace through instruction and to get in the CALL instruction : t

Step through instruction and to treat a CALL as a single instruction : p

To display the local variables : dv

To display the type of the symbol : dt

To display the value of registers : r

To change the value of the register : r <register_name>=<value>

To disassemble a function : uf <function name>

To see the stats of a function : wt

What’s more?

Commands that I have used above are all basic commands they have different variations too, to check out every command I would suggest you to refer Microsoft’s official website and the binary that I have used you can get that from my github . In my opinion Windbg is an excellent tool to start practicing reverse engineering because we can compare assembly with its source code side by side which allows us to write code and disassemble it to learn more. Till then keep practicing & debugging.

Blog by Nerd of AX1AL. Join us at our discord server.

--

--

Gaurav yadav
RIXED_LABS

I like to learn things which challenges me . I am a Developer ,reverse engineer and very much addicted to games.