why doesn't gdb like aliases

Aliases are a feature of the shell. Defining an alias creates a new shell command name. It's recognized only by the shell, and only when it appears as a command name.

For example, if you type

> ff

at a shell prompt, it will invoke your alias, but if you type

> echo ff

the ff is just an argument, not a command. (At least in bash, you can play some tricks if the alias definition ends with a space. See Stéphane Chazelas's answer for a possible solution if you're determined to use shell aliases.)

You typed

> gdb ff

so the shell invoked gdb, passing it the string ff as an argument.

You can pass arguments to the debugged program via the gdb command line, but you have to use the --args option. For example:

> gdb firefox --safe-mode

tries (and fails) to treat --safe-mode as an option to gdb. To run the command with an argument, you can do it manually:

> gdb firefox
...
(gdb) run --safe-mode

or, as thrig's answer reminds me, you can use --args:

> gdb --args firefox --safe-mode
...
(gdb) run

(The first argument following --args is the command name; all remaining arguments are passed to the invoked command.)

It's possible to extract the arguments from a shell alias, but I'd recommend just defining a separate alias:

alias ff='firefox --safe-mode'
alias gdbff='gdb --args firefox --safe-mode'

Or, better, use shell functions, which are much more versatile. The bash manual says:

For almost every purpose, shell functions are preferred over aliases.


Not directly but it is possible with some wrangling of ZSH shell aliases into a form suitable for gdb.

alias testtest='echo test test test'

function gdb-alias() {
   local cmdargs
   cmdargs=( ${(z)${aliases[$1]}} )
   gdb -q --args $cmdargs
}

This splits the alias (more robust code would check whether the first argument is indeed an alias, or even is set, etc) as ZSH would and then feeds those arguments to gdb via the handy --args flag (see info gdb invocation). If we then run gdb-alias testtest

% gdb-alias testtest
Reading symbols from echo...(no debugging symbols found)...done.
(gdb) r
Starting program: /Users/jhqdoe/usr/Darwin15.6.0-x86_64/bin/echo test test test
test test test
[Inferior 1 (process 93721) exited normally]
(gdb) 

which shows that echo (my assembly implementation of echo, anyways) was run by gdb with the arguments from the alias.

(This will probably break on global aliases, or any aliases with shell metacharacter foo, maybe, depending on whether gdb throws those argument through a shell compatible with anything that might be set in ZSH, but should be okay for simple x='y z' type stuff. Maybe.)


In POSIX shells, aliases are only expanded in command position (wherever a command is expected) or after aliases whose expansion ends in a blank character (in zsh, only a space, and in many other implementations, only space or tab)¹. You also need the --args option to gdb to be able to pass arguments to the program being debugged. So you can do:

alias gdba='gdb --args ' # note the trailing space which does mean
                         # that aliases are to be expanded after it
alias ff='firefox --safe-mode'
gdba ff

¹ zsh also supports global aliases (with alias -g) which are expanded in many more places, but you probably wouldn't want to use such an alias for your firefox --safe-mode here as you wouldn't want echo ff for instance to output anything other than ff.