mGBA features a very basic embedded debugger. It has a help
command, but this command doesn't explain what arguments any of the commands accept (or require). One has to look at mGBA's source code to get that information.
Integers are decimal by default, but can be prefixed with 0x
or $
to allow hexadecimal. The 0b
prefix marks binary literals. Any command which takes a memory address expects to receive it in the form of an integer.
Literals of the form $01:23
have a segment of 01
and a non-segment value of 0x00000023
.
Register names (r0
through r15
, and cpsr
) can also be used, and will resolve to the registers' current values.
The following two-term operators are supported:
+ - * / % & | ^ << >> == != > < >= <= && ||
Parentheses are also supported for grouping sub-expressions.
The unary *
prefix operator will treat an integer value as a memory address, and read the byte at that address. This is treated as occurring within the context of the game (i.e. it will print [GAME ERROR] GBA Memory: Bad BIOS Load8
to the log if you read from an invalid address and have those messages enabled).
The unary !
prefix operator is supported, and is a logical "NOT" operator. It can be chained (e.g. !!5 == 1
).
The unary ~
prefix operator is a bitwise "NOT" operator.
break/t <address>
break/a <address>
Set a software breakpoint, to fire when execution reaches a given address. Breakpoints are specific to a CPU mode, with break/t
setting a THUMB breakpoint and break/a
setting an ARM breakpoint. Addresses are integer literals; if writing them in hex, they must be 0x
-prefixed.
listb
List all breakpoints.
delete <address>
d <address>
This command is supposed to delete a breakpoint. In my experience, it doesn't work at all. Your only option to unset a breakpoint is to completely restart mGBA.
next
Executes the next assembly instruction, and prints the registers and instruction.
trace <count>
Executes the next count assembly instructions, printing the registers and instructions.
continue
Continues execution.
watch <address> <condition>
watch/r <address> <condition>
watch/w <address> <condition>
watch/c <address> <condition>
Sets a watchpoint at the given address (an integer literal; if hexadecimal, it must be 0x
-prefixed). The suffix indicates the operation you're watching for:
- No suffix: reads or writes
r
: readsw
: writesc
: writes, but only if they change the value
mGBA will break into the debugger when the given operation occurs at the given address. The condition is optional and, if specified, controls whether mGBA breaks into the debugger. It must be an incomplete expression with no whitespace separation (e.g. watch 12345==3
is valid; watch 12345 == 3
and watch 12345 3 == 3
are invalid).
watch-range <address> <address>
watch-range/r <address> <address>
watch-range/w <address> <address>
watch-range/c <address> <address>
Same as the above, except that it watches a range of addresses. You provide a start and an end, and this adds a watchpoint for [start, end).
listw
Lists all extant watchpoints. Their conditions, if any, are not displayed.
disasm <address> <count>
The arguments are optional, and default to the current instruction pointer and to 1, respectively. Prints count many instructions starting at the given address. Addresses are integer literals; if writing them in hex, they must be 0x
-prefixed.
If you've loaded a symbol file, then any known symbols will be identified by name in the printed disassembly.
disasm/t <address> <count>
disasm/a <address> <count>
Same as the above, except that these forcibly interpret the instructions as THUMB or ARM, regardless of the current CPU mode.
stack <string>
Change the current stack tracing mode. The argument must be one of the following:
Value | Meaning |
---|---|
off |
Disables stack tracing. |
trace-only |
Enables stack tracing. |
break-call |
Break on function calls. |
break-return |
Break on function returns. |
break-all |
Break on function calls and returns. |
If you run the command without an argument, it prints the list of available options.
backtrace
Does nothing if stack tracing is not enabled.
If stack tracing is enabled, then this attempts to print a stack trace. It apparently can't see any stack frames that were passed through before tracing was enabled.
finish
Continues execution until the current stack frame returns.
load-symbols <filepath>
Attempts to load the .elf
file at the given path. If you're on Windows, you can use Windows or common path separators (i.e. \
or /
).
symbol <address>
Looks up the symbol name for the given address, if there is one.
print <expression>
print/t <expression>
print/x <expression>
Computes the result of the given expression, and prints it. The /t
specifier formats the output in base-2, while the /x
specifier formats the output in hex.
source <filepath>
Attempts to load and execute the given Lua script file, if scripting is enabled on your build of mGBA.