aboutsummaryrefslogtreecommitdiff
path: root/gdb/stack.c
diff options
context:
space:
mode:
authorTom Tromey <tom@tromey.com>2017-04-23 10:54:33 -0600
committerTom Tromey <tom@tromey.com>2018-03-26 21:57:09 -0600
commitea3b06874c8a1037bad4fd5b9396d196e6963ac6 (patch)
tree3992edee33959fb4062ff519bbea7ec663bcba4f /gdb/stack.c
parent07dca93f3bbc2426d89eba460c925863e4ebd636 (diff)
downloadgdb-ea3b06874c8a1037bad4fd5b9396d196e6963ac6.zip
gdb-ea3b06874c8a1037bad4fd5b9396d196e6963ac6.tar.gz
gdb-ea3b06874c8a1037bad4fd5b9396d196e6963ac6.tar.bz2
Rationalize "backtrace" command line parsing
The backtrace command has peculiar command-line parsing. In particular, it splits the command line, then loops over the arguments. If it sees a word it recognizes, like "full", it effectively drops this word from the argument vector. Then, it pastes together the remaining arguments, passing them on to backtrace_command_1, which in turn passes the resulting string to parse_and_eval_long. The documentation doesn't mention the parse_and_eval_long at all, so it is a bit of a hidden feature that you can "bt 3*2". The strange algorithm above also means you can "bt 3 * no-filters 2" and get 6 frames... This patch changes backtrace's command line parsing to be a bit more rational. Now, special words like "full" are only recognized at the start of the command. This also updates the documentation to describe the various bt options individually. gdb/ChangeLog 2018-03-26 Tom Tromey <tom@tromey.com> * stack.c (backtrace_command): Rewrite command line parsing. gdb/doc/ChangeLog 2018-03-26 Tom Tromey <tom@tromey.com> * gdb.texinfo (Backtrace): Describe options individually.
Diffstat (limited to 'gdb/stack.c')
-rw-r--r--gdb/stack.c62
1 files changed, 20 insertions, 42 deletions
diff --git a/gdb/stack.c b/gdb/stack.c
index aad8fcd..13af659 100644
--- a/gdb/stack.c
+++ b/gdb/stack.c
@@ -1850,61 +1850,39 @@ backtrace_command_1 (const char *count_exp, int show_locals, int no_filters,
static void
backtrace_command (const char *arg, int from_tty)
{
- int fulltrace_arg = -1, arglen = 0, argc = 0, no_filters = -1;
- int user_arg = 0;
+ bool fulltrace = false;
+ bool filters = true;
- std::string reconstructed_arg;
if (arg)
{
- char **argv;
- int i;
+ bool done = false;
- gdb_argv built_argv (arg);
- argv = built_argv.get ();
- argc = 0;
- for (i = 0; argv[i]; i++)
+ while (!done)
{
- unsigned int j;
+ const char *save_arg = arg;
+ std::string this_arg = extract_arg (&arg);
- for (j = 0; j < strlen (argv[i]); j++)
- argv[i][j] = TOLOWER (argv[i][j]);
+ if (this_arg.empty ())
+ break;
- if (no_filters < 0 && subset_compare (argv[i], "no-filters"))
- no_filters = argc;
+ if (subset_compare (this_arg.c_str (), "no-filters"))
+ filters = false;
+ else if (subset_compare (this_arg.c_str (), "full"))
+ fulltrace = true;
else
{
- if (fulltrace_arg < 0 && subset_compare (argv[i], "full"))
- fulltrace_arg = argc;
- else
- {
- user_arg++;
- arglen += strlen (argv[i]);
- }
- }
- argc++;
- }
- arglen += user_arg;
- if (fulltrace_arg >= 0 || no_filters >= 0)
- {
- if (arglen > 0)
- {
- for (i = 0; i < argc; i++)
- {
- if (i != fulltrace_arg && i != no_filters)
- {
- reconstructed_arg += argv[i];
- reconstructed_arg += " ";
- }
- }
- arg = reconstructed_arg.c_str ();
+ /* Not a recognized argument, so stop. */
+ arg = save_arg;
+ done = true;
}
- else
- arg = NULL;
}
+
+ if (*arg == '\0')
+ arg = NULL;
}
- backtrace_command_1 (arg, fulltrace_arg >= 0 /* show_locals */,
- no_filters >= 0 /* no frame-filters */, from_tty);
+ backtrace_command_1 (arg, fulltrace /* show_locals */,
+ !filters /* no frame-filters */, from_tty);
}
/* Iterate over the local variables of a block B, calling CB with