Ddbg is a command-line tool with two CLIs.
The main CLI is described below, the other is a GDB emulation mode.
This mode is activated by the "-cli=gdb" command line option.
The GDB emulation is only used as a compatibility hack to enable integration into GDB frontends like Code::Blocks.
Ddbg currently works with DMD for Windows only. Executables created with GDC are not supported, yet.
Using Ddbg from the command line
The syntax to start Ddbg is: ddbg [-cli=<mode>] [-cmd=<commands>] <exe file> [arguments]
-cli
Selects the CLI to use. Available CLIs are "gdb" and "ddbg" (default)
-cmd
execute a string of Ddbg commands separated by semicolons,
e.g. ddbg -cmd="sp src; onex \"wmd ddbg.dmp; r\"; r" debuggee.exe
<exe file>
The name of the debuggee. If no extension is given, ".exe" is assumed.
[arguments]
Optional arguments that are passed to the debuggee.
In order to be able to debug a program it has to be compiled with DMD's "-g" switch.
This section describes the Ddbg CLI that is active by default.
Commands
Enter "?", "h" or "help" in Ddbg to get the list of supported commands:
Running
-----------------------------------------------------------------------------
in step into at source level
ov step over at source level
out step out at source level
r run/continue the program
Breakpoints
-----------------------------------------------------------------------------
bp [<file>:<line>[#<thrd>]] [ind] set breakpoint #index at given file:line
optionally only for the given thread id
optionally with the given breakpoint index
dbp [<file>:<line>|#index|*] delete breakpoint by index, line or all
lbp list breakpoints
ltbp list temporary breakpoints
Stack/Memory/Registers
-----------------------------------------------------------------------------
dm <start> <length> dump memory (start in hex, length in dec)
dr [cpu] [fpu] [mmx] [sse] dump registers [toggle register groups]
ds dump stack (last line is top)
lsv list variables in current scope
mi [free] [rsrv] memory information. lists blocks in state
commit and optionally free and reserve
us unwind stack, prints full stacktrace
Expressions
-----------------------------------------------------------------------------
= <expr> evaluate expression
ed <depth> set max depth of implicit evaluation of
recursive structures
el <length> set max number of array elements to print
er toggle between ed 0 and previous ed
f <number> select frame for evaluation.
default: current frame = 0
t <expression> type of expression
Source
-----------------------------------------------------------------------------
jkf toggle whether to switch to stack frame of
last known source location on exception
lsm [substring] list source modules
lsp list source search paths
ps [count] print count lines of source before
and after current location
sp <path> add source search path
Disassembly
-----------------------------------------------------------------------------
da [start] disassemble from start
(default = function start) to next ret
dal [#lines] disassemble to/from +/- source lines
Threads
-----------------------------------------------------------------------------
lt list threads
st <threadId> select thread to be evaluation context
Minidumps
-----------------------------------------------------------------------------
rmd <file> read minidump from file
wmd <file> write minidump to file
Miscellaneous
-----------------------------------------------------------------------------
arg <args> set command line arguments
ii print image information
ldll list loaded DLLs
lm [substring] list debug modules
ld [substring] list data symbols
lf [substring] list function symbols
lg [substring] list global symbols
lp [substring] list global publics
ls [substring] list all symbols
nc toggle new console for process
onex <cmd; cmd; ...> on exception execute list of commands
onterm <cmd; cmd; ...> on termination execute list of commands
q quit debugger
return repeats the last command
Some hints
Do not use absolute paths to set breakpoints.
Use the 'lsm' command instead to list the relative paths of the source files saved in the executable. These paths can be used with 'bp'.
If you want source lines to be printed (for breakpoints or disassembly) and the working directory is not the base path of the relative paths saved in the executable,
you need to add the base path to the source search paths using 'sp'.
Do not use stepping commands to start the debuggee. You have to use the "r" command or "Start" menu item in Code::Blocks first (will be fixed soon)
To examine exceptions or asserts, run the program until Ddbg breaks with an Unhandled exception message, then issue the "us" command to show the stacktrace.
Note that Code::Blocks will ask you whether it should display the stacktrace ("backtrace") in such a case. If you click "yes", the stacktrace window will appear, but it will not show the correct stacktrace.
You will have to close and reopen the window to refresh the stacktrace.
Use the "nc" command before starting the process (i.e. directly after starting Ddbg) to redirect the debuggee's console output to a new window
If stepping through your code doesn't work, set breakpoints at the locations you want to step to instead (and report the problem)
To display global variables, use expressions with it's full name (including packages), e.g. "mymodule.global_var"
You can check
Settings > Compiler and Debugger > Debugger settings > Display Debugger's log
to enable the message tab "Debugger (debug)" (not the same as "Debugger") which displays almost all of the communication between Code::Blocks and Ddbg.
There you may find more detailed information if you're experiencing any problems.
"dr" remembers the selected register groups from last time.
Ddbg expressions
Ddbg supports evaluation of versatile expressions in the debuggee's address space.
The syntax is a subset of D's expressions (except for register access) and should be intuitive for every D programmer.
Register names are prefixed by a # symbol, to distinguish them from symbol identifiers.
For static and dynamic arrays, Ddbg supports the "ptr" and "length" properties, for associative arrays the "length" property.
Evaluate an expression with the "=" command, print the type of an expression with the "t" command.
By default, expressions are evaluated one level deep. That means that if the result of an expression is a non-scalar data structure (struct, class, arrays),
the evaluation is stopped and "..." is printed instead. You can change the evaluation depth with the "ed" and "er" commands.
Usually it's fine to use depth 1, though, since that gives you a short listing of all scope variables ("lsv" command) and you can inspect variables deeper by issuing explicit "=" commands for single variables.
Ddbg supports Minidumps for post-mortem debugging.
You can use the wmd command to write a minidump of the current state of the debuggee to a file.
Later you can read that minidump with the rmd command. After reading a minidump, Ddbg is in post-mortem mode.
In that mode you can browse the data from the minidump, but cannot execute the debuggee. Therefore, some commands are not available in post-mortem mode.
Ddbg uses the DBGHELP API to support minidumps. It is available on every Windows XP Installation. For other Windows versions, the Platform SDK must be installed.
To run a debuggee such that it automatically creates a minidump file when it crashes, use the following command line:
To browse the minidump, you can start ddbg as usual:
ddbg debuggee.exe
and issue an rmd command to load the minidump file
->rmd ddbg.dmp
If the minidump was saved after an exception occured, you will now recieve the exception's message again.
Minidumps can be created at anytime, though. Therefore you can also examine problems that do not necessarily throw an exception.
OutputDebugString interface
You can issue commands to Ddbg from within your debuggee by calling the OutputDebugString function from the Win32 API.
To mark a debug string as a Ddbg command sequence, it has to be prefixed with "Ddbg:".
The following call triggers writing of a minidump and continues the debuggee afterwards: