Debugging With Visual Studio 2010
Debugging With Visual Studio 2010
Overview
To start debugging an application, you have a few options:
Open the project with the source code in Visual Studio, select the Debug
configuration, press Play to start debugging.
Open the project with the source code in Visual Studio, launch the application
externally, then attach to it from Visual Studio
Launch the application externally, then attach to it from Visual Studio. In this case if
you have the source code, an exception may load it correctly. However, this method is
useful if you just need to know the details of the exception being raised, or the list of
modules loaded, inspect memory, pause the code etc.
Use gflags to tell Windows to use a debugger whenever the application launches e.g.
use the vsjitdebugger.exe, which allows you to launch or select an instance of Visual
Studio to attach to the application. This method is particularly useful when debugging
services since you can't start a service from inside Visual Studio.
Use the CDB debugger, or WinDBG to debug your code, or to analyse memory
dumps.
Breakpoints
Press F9 to add a breakpoint at the current line in your code. Press F9 again to remove the
breakpoint (toggle).
When you run your code, the debugger will break at that line before it is executed.
The choice of location for a breakpoint requires some consideration. If you break too early,
you will need to step over many lines of code, but if you break too late, you may miss a
critical event in your code.
You can also press the Pause button in Visual Studio at any point to stop the execution of
code and break at the current line. However, your user code may not be executing at the time,
or the current line may show a different thread than expected.
Context
When your code stops at a breakpoint, the context cursor, a yellow cursor in the code margin
indicates the line of code to be executed next.
If you press F10 or click the Step Over option on the Toolbar in Visual Studio, the current
line of code is executed and the context moves to the next line.
A few shortcuts can help you execute your code
continue (F5)
Continues execution of your code until the next breakpoint is hit.
step over (F10)
Execute the current line, and move the context to the next line.
run to cursor (Ctrl+F10)
If your cursor (edit cursor in the code) is a few lines below, code is executed and stops
at your cursor.
step into (F11)
If the context is at a line of code that is a function/property or some other compound
code, then the context moves into the function/property i.e. the code you see is
changed to the function/property
step out (Shift+F11)
Executes all of the code in the current function/property and returns the context to the
calling function.
step into specific (native C++ only)
Same as F11 but allows you to select which function you would like to step into
set next statement (Ctrl+Shift+F10)
Allows you to skip code. Place your cursor on a line of code and press Ctrl+Shift+F10
to skip other lines and move the context to the line selected.
You may find it easier to drag the context cursor to the line you wish to execute next.
most of these options also apply to the disassembly window
Data Tooltips
As you are executing lines of code, the values of variables will change. To view the current
value of a variable hover over it with your mouse.
A data tooltip shows the current value. For some variable types, a data visualization window
appears allowing you to view the value easier e.g. if you hover over a DataTable, you can
view each cell in a table format.
Most data tooltips also allow you to change the value of the variable. Click on the tooltip and
type in a new value.
Watch window
Use the watch windows when data tooltips become too tedious, or when you want to view the
same variables continuously.
memory, m
e.g. 0x24BC, m cd represents global memory that has not been initialised. cc shows
un-initialised local memory. dd is free memory while fd is memory that you cannot
access.
pointer, size
e.g. pArr, 10
&MyVar
returns the memory address of the variable
@Err
Calls getlasterror and shows the result
Registers
e.g. EAX
Formatters
e.g. d (format as signed decimal), c (char), s (string)
e.g. MyVar,d
Uninitialised global shown with value 0xCDCDCDCD
Uninitialised locals shown with value 0xCCCCCCCC
Freed memory shown with value 0xDDDDDDDD
Memory out of the process/inaccessible shown with value 0xFDFDFDFD
Output Window
Exceptions
Navigating
double click to switch to different frame.
Used with watch window
Shows parameters types and parameter values
Set breakpoints
Command window
Run Visual Studio Commands, similar to when writing a macro e.g.
Edit.Find m_bMyBool
File.Open C:\pagefile.sys
Immediate window
Breakpoints
Once a breakpoint has been set, advanced options can be configured. Right clicking a
breakpoint brings up a property window where conditions for the breakpoint can be set.
Hit Count
Useful for long loops
Try setting the condition to a huge number to find when a problem occurs. Then when
the exception etc. is encountered, take a look at the hit count for the breakpoint. Now
you know when to break
Testing a variable
You may also check the value of a variable and break when it matches a condition
Data Breakpoints
In C++ data breakpoints allow you to break whenever a variable/memory location is
modified.
Memory Allocation Breakpoint
Set a breakpoint in the watch window by adding a variable with the name
_crtBreakAlloc to break whenever memory is allocated
Set the value of the _crtBreakAlloc variable e.g. to 24 to break on the 24th allocation
use {,,msvcr71d.dll}_crtBreakAlloc when using multithreaded dll version of CRT
(which is the default option for new projects)
Can also be done in code _crtBreakAlloc = 24
Lastly, while breakpoints are useful, too many breakpoints slows debugging. Use the
Breakpoints window to selectively enable/disable breakpoints. This window is also useful for
navigation, if you quickly want to jump around your code to known breakpoints.
Memory Window
Find which location a pointer is referencing, or the memory location of a variable and
type that into the address textbox.
Format as Ansi/Unicode string
Can also view the data as various integral or double types
Disassembly Window
Modules Window
Threads
Switch contexts
Switch context to a different thread by double clicking on it. Then when you press
F10, this thread will execute.
Freeze/thaw threads
When multiple threads are running, the execution context may jump between threads.
Freeze the thread temporarily to prevent its execution.
Set breakpoint per named thread
Task Window
The Task window can be used to show custom tasks by right clicking on the pane and
selecting Show All from the pop-up menu.
Comments specifically starting with // TODO: will then be listed. Use //TODO: //HACK:
//UNDONE: or custom tags
The options tab can also be used to add your own custom tasks.
The task window only shows tasks for the current project unless it is a bookmark task (added
from the Edit menu)
gflags
Global Flags configures registry entries that tell Windows to treat applications differently.
For example, you can tell windows to enable heap checking for your application.
Usage
Debugger
You can use Global Flags to configure an alternative debugger for your application.
Heap checking
If the debugger in step 1 does not detect your problem, you may need to turn on heap
checking which validates heap memory e.g. buffer overruns etc.
In the Debugging Tools for Windows directory run gflags.exe with no arguments.
Since we are interested in a user module ignore the settings for System Registry and
Kernel Mode. Type in dllhost.exe for the Image File Name. Then either select the
Image File Options radio button or Press the Tab key.
gflags sets registry keys for applications that you want Windows to analyze, once they
have been set, they will always be active (even after rebooting) unless you turn them
off.
If youre interested, you can have a look at the registry key:
HKLM\Software\Microsoft\Windows NT\Current Version\Image File Execution
Options\You Application.exe (e.g. dllhost.exe)
Place a check next to the following options for dllhost.exe in gflags.
1.
2.
3.
4.
5.
6.
7.
Installation
Install the Platform SDK for your version of Windows. The current version is available here:
\\mntksrv006\MAC\Software\Development\Microsoft Windows Platform SDK\Windows 7
SDK The default install will create a new folder C:\Program Files\Debugging Tools for
Windows (x64)
ADPlus
ADPlus can be used to analyse a program that's crashing often, or to analyse a program that
has hung.
The main purpose of ADPlus is to "take a dump" (mind the language). It does this by
attaching a debugger (CDB) to your processes and watching for exceptions or hangs etc.
Set Environment Variables
Right click on My Computer and select Properties.
Go to the Advanced tab and select Environment Variables
Select New under System Variables and set
_NT_SYMBOL_PATH =
SRV*C:\Symbols*http://msdl.microsoft.com/download/
symbols
(where C:\Symbols is the location of a local
folder to cache symbols)
Also add
_NT_EXECUTABLE_IMAGE_PATH =
C:\Windows;C:\Windows\System32;C:\Mintek\StarCS\Se
rver;C:\Mintek\StarCS\Server\Modules;
(or an equivalent location of your dll files)
Run ADPlus in crash mode
Open a command prompt and navigate to the Debugging Tools for Windows folder.
Also open Task Manager and find the PID of the StarCS Slave.exe process (or dllhost.exe for
older versions of StarCS).
Type the following in the command prompt
<ADPlus>
<Settings>
<RunMode> CRASH </RunMode>
AllExceptions
<Actions1>Log;MiniDump</Actions1>
<Actions2>Stack;FullDump;Log;EventLog</Actions2>
</Config>
<Config>
av
<Actions1>Log;MiniDump</Actions1>
<Actions2>Stack;FullDump;Log;EventLog</Actions2>
</Config>
</Exceptions>
</ADPlus>
Copy the text into notepad and save as C:\Program Files\Debugging Tools for
Windows\Adplus.cfg.
Then change the command to:
In order to properly analyse a dump file, it is necessary to have the correct version of
the dlls and their corresponding pdb (symbol files).
In this case, the dlls that were installed on the PC on which the dump was created
Verify that _NT_EXECUTABLE_IMAGE_PATH and _NT_SYMBOL_PATH point
to locations where the dlls and pdb files respectively reside
Other pdb files that relate to windows dlls may also be required.
Ensure that you have a valid internet connection. WinDBG will use the Symbol server
to download the pdbs are required (hence the url,
http://msdl.microsoft.com/download/symbols NB: you cannot browse to this url, only
a symbol server can download symbols from this location.)
Now type windbg.exe -v -n Q at a command prompt.
The options just specify verbose messages and strict symbol matching
Open your dump file by selecting File\Open Crash Dump. and browsing to your
,dmp file