* [RFC] info threads takes an argument
@ 2011-02-11 1:52 Michael Snyder
2011-02-11 6:09 ` Joel Brobecker
0 siblings, 1 reply; 15+ messages in thread
From: Michael Snyder @ 2011-02-11 1:52 UTC (permalink / raw)
To: gdb-patches
[-- Attachment #1: Type: text/plain, Size: 70 bytes --]
Seems like it should be possible to inquire about a specific thread.
[-- Attachment #2: thread.txt --]
[-- Type: text/plain, Size: 810 bytes --]
2011-02-10 Michael Snyder <msnyder@msnyder-server.eng.vmware.com>
* thread.c (info_threads_command): Process arg as thread id.
Index: thread.c
===================================================================
RCS file: /cvs/src/src/gdb/thread.c,v
retrieving revision 1.131
diff -u -p -u -p -r1.131 thread.c
--- thread.c 19 Jan 2011 17:21:36 -0000 1.131
+++ thread.c 11 Feb 2011 01:47:31 -0000
@@ -965,7 +965,16 @@ No selected thread. See `help thread'.\
static void
info_threads_command (char *arg, int from_tty)
{
- print_thread_info (uiout, -1, -1);
+ int tid = -1;
+
+ if (arg != NULL && *arg != '\0')
+ {
+ int tmp_tid = strtoul (arg, NULL, 0);
+ if (tmp_tid != 0)
+ tid = tmp_tid;
+ }
+
+ print_thread_info (uiout, tid, -1);
}
/* Switch from one thread to another. */
^ permalink raw reply [flat|nested] 15+ messages in thread* Re: [RFC] info threads takes an argument 2011-02-11 1:52 [RFC] info threads takes an argument Michael Snyder @ 2011-02-11 6:09 ` Joel Brobecker 2011-02-11 19:23 ` Michael Snyder 0 siblings, 1 reply; 15+ messages in thread From: Joel Brobecker @ 2011-02-11 6:09 UTC (permalink / raw) To: Michael Snyder; +Cc: gdb-patches > 2011-02-10 Michael Snyder <msnyder@msnyder-server.eng.vmware.com> > > * thread.c (info_threads_command): Process arg as thread id. This seems like a reasonable enhancement to me. We have the same sort of feature for Ada (except that we print a more detailed description of the given task). You will also need a documentation update... > + if (arg != NULL && *arg != '\0') > + { > + int tmp_tid = strtoul (arg, NULL, 0); > + if (tmp_tid != 0) Emtpy line after the variable declaration... -- Joel ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-11 6:09 ` Joel Brobecker @ 2011-02-11 19:23 ` Michael Snyder 2011-02-11 21:14 ` Tom Tromey 0 siblings, 1 reply; 15+ messages in thread From: Michael Snyder @ 2011-02-11 19:23 UTC (permalink / raw) To: Joel Brobecker; +Cc: gdb-patches [-- Attachment #1: Type: text/plain, Size: 607 bytes --] Joel Brobecker wrote: >> 2011-02-10 Michael Snyder <msnyder@msnyder-server.eng.vmware.com> >> >> * thread.c (info_threads_command): Process arg as thread id. > > This seems like a reasonable enhancement to me. We have the same sort > of feature for Ada (except that we print a more detailed description > of the given task). > > You will also need a documentation update... > >> + if (arg != NULL && *arg != '\0') >> + { >> + int tmp_tid = strtoul (arg, NULL, 0); >> + if (tmp_tid != 0) > > Emtpy line after the variable declaration... > OK, here's help, doc, and a newline. ;-) [-- Attachment #2: thread.txt --] [-- Type: text/plain, Size: 2219 bytes --] 2011-02-10 Michael Snyder <msnyder@msnyder-server.eng.vmware.com> * thread.c (info_threads_command): Process arg as thread id. (_initialize_thread): Document argument for info therads. Index: thread.c =================================================================== RCS file: /cvs/src/src/gdb/thread.c,v retrieving revision 1.131 diff -u -p -u -p -r1.131 thread.c --- thread.c 19 Jan 2011 17:21:36 -0000 1.131 +++ thread.c 11 Feb 2011 19:18:30 -0000 @@ -965,7 +965,17 @@ No selected thread. See `help thread'.\ static void info_threads_command (char *arg, int from_tty) { - print_thread_info (uiout, -1, -1); + int tid = -1; + + if (arg != NULL && *arg != '\0') + { + int tmp_tid = (int) parse_and_eval_long (arg); + + if (tmp_tid != 0) + tid = tmp_tid; + } + + print_thread_info (uiout, tid, -1); } /* Switch from one thread to another. */ @@ -1404,7 +1414,8 @@ _initialize_thread (void) static struct cmd_list_element *thread_apply_list = NULL; add_info ("threads", info_threads_command, - _("IDs of currently known threads.")); + _("IDs of currently known threads.\n\ +A single thread id may be given as the optional argument.")); add_prefix_cmd ("thread", class_run, thread_command, _("\ Use this command to switch between threads.\n\ 2011-02-11 Michael Snyder <msnyder@vmware.com> * gdb.texinfo (threads): Document argument for info threads cmd. Index: doc/gdb.texinfo =================================================================== RCS file: /cvs/src/src/gdb/doc/gdb.texinfo,v retrieving revision 1.797 diff -u -p -u -p -r1.797 gdb.texinfo --- doc/gdb.texinfo 4 Feb 2011 21:54:15 -0000 1.797 +++ doc/gdb.texinfo 11 Feb 2011 19:18:31 -0000 @@ -2706,9 +2706,10 @@ number---always a single integer---with @table @code @kindex info threads -@item info threads -Display a summary of all threads currently in your -program. @value{GDBN} displays for each thread (in this order): +@item info threads @r{[}@var{n}@r{]} +Display a summary of all threads currently in your program. Optional +argument @var{n} means print information only about the specified +thread. @value{GDBN} displays for each thread (in this order): @enumerate @item ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-11 19:23 ` Michael Snyder @ 2011-02-11 21:14 ` Tom Tromey [not found] ` <4D55B1ED.5020808@vmware.com> 0 siblings, 1 reply; 15+ messages in thread From: Tom Tromey @ 2011-02-11 21:14 UTC (permalink / raw) To: Michael Snyder; +Cc: Joel Brobecker, gdb-patches >>>>> "Michael" == Michael Snyder <msnyder@vmware.com> writes: Michael> OK, here's help, doc, and a newline. ;-) Michael> + _("IDs of currently known threads.\n\ Michael> +A single thread id may be given as the optional argument.")); How about a "usage" form instead? Usage: info threads [ID] If ID is given, it is the id of the sole thread to display. Otherwise, all threads are displayed. Tom ^ permalink raw reply [flat|nested] 15+ messages in thread
[parent not found: <4D55B1ED.5020808@vmware.com>]
[parent not found: <m3k4h2e6xu.fsf@fleche.redhat.com>]
* Re: [RFC] info threads takes an argument [not found] ` <m3k4h2e6xu.fsf@fleche.redhat.com> @ 2011-02-14 20:03 ` Michael Snyder 2011-02-14 20:40 ` Eli Zaretskii 2011-02-15 19:58 ` Tom Tromey 0 siblings, 2 replies; 15+ messages in thread From: Michael Snyder @ 2011-02-14 20:03 UTC (permalink / raw) To: Tom Tromey, gdb-patches [-- Attachment #1: Type: text/plain, Size: 635 bytes --] Tom Tromey wrote: > > Michael> add_info ("threads", info_threads_command, > Michael> _("Usage: info threads [ID]. Display currently known > Michael> threads.\n\ > Michael> If ID is given, display only that thread;\ > Michael> otherwise, all threads are displayed.")); > > I think I'd like it if the Usage was always on its own line. > How about: > > Display currently known threads. > Usage: info threads [ID] > If ID is given, it is the id of the sole thread to display. > Otherwise, all threads are displayed. OK, so modified, and combined with the new 'thread find' patch. Documentation and NEWS also attached. [-- Attachment #2: find.txt --] [-- Type: text/plain, Size: 7084 bytes --] 2011-02-14 Michael Snyder <msnyder@msnyder-server.eng.vmware.com> * thread.c (info_threads_command): Process arg as thread id, or list of thread ids. (thread_find_command): New command. (_initialize_thread): Document argument for info threads. Document 'thread find' command. * NEWS: Document new command "thread find". 2011-02-14 Michael Snyder <msnyder@vmware.com> * gdb.texinfo (threads): Document argument for "info threads" cmd. Document new command "thread find". Index: thread.c =================================================================== RCS file: /cvs/src/src/gdb/thread.c,v retrieving revision 1.131 diff -u -p -u -p -r1.131 thread.c --- thread.c 19 Jan 2011 17:21:36 -0000 1.131 +++ thread.c 14 Feb 2011 19:51:42 -0000 @@ -43,6 +43,7 @@ #include "observer.h" #include "annotate.h" #include "cli/cli-decode.h" +#include "gdb_regex.h" /* Definition of struct thread_info exported to gdbthread.h. */ @@ -957,15 +958,35 @@ No selected thread. See `help thread'.\ /* Print information about currently known threads - * Note: this has the drawback that it _really_ switches - * threads, which frees the frame cache. A no-side - * effects info-threads command would be nicer. - */ + Optional ARG is a thread id, or list of thread ids. + + Note: this has the drawback that it _really_ switches + threads, which frees the frame cache. A no-side + effects info-threads command would be nicer. */ static void info_threads_command (char *arg, int from_tty) { - print_thread_info (uiout, -1, -1); + int tid = -1; + + if (arg == NULL || *arg == '\0') + { + print_thread_info (uiout, -1, -1); + return; + } + + while (arg != NULL && *arg != '\0') + { + int tmp_tid + = (int) parse_and_eval_long (scan_expression_with_cleanup (&arg, + NULL)); + + if (tmp_tid != 0) + { + tid = tmp_tid; + print_thread_info (uiout, tid, -1); + } + } } /* Switch from one thread to another. */ @@ -1313,6 +1334,56 @@ thread_name_command (char *arg, int from info->name = arg ? xstrdup (arg) : NULL; } +/* Find thread ids with a name, target pid, or extra info matching ARG. */ + +static void +thread_find_command (char *arg, int from_tty) +{ + struct thread_info *tp; + char *tmp; + unsigned long match = 0; + + if (arg == NULL || *arg == '\0') + error (_("Command requires an argument.")); + + tmp = re_comp (arg); + if (tmp != 0) + error (_("Invalid regexp (%s): %s"), tmp, arg); + + update_thread_list (); + for (tp = thread_list; tp; tp = tp->next) + { + if (tp->name != NULL && re_exec (tp->name)) + { + printf_filtered ("Thread %d has name '%s'\n", tp->num, tp->name); + match++; + } + + tmp = target_thread_name (tp); + if (tmp != NULL && re_exec (tmp)) + { + printf_filtered ("Thread %d has target name '%s'\n", tp->num, tmp); + match++; + } + + tmp = target_pid_to_str (tp->ptid); + if (tmp != NULL && re_exec (tmp)) + { + printf_filtered ("Thread %d has target id '%s'\n", tp->num, tmp); + match++; + } + + tmp = target_extra_thread_info (tp); + if (tmp != NULL && re_exec (tmp)) + { + printf_filtered ("Thread %d has extra info '%s'\n", tp->num, tmp); + match++; + } + } + if (!match) + printf_filtered ("No threads match '%s'\n", arg); +} + /* Print notices when new threads are attached and detached. */ int print_thread_events = 1; static void @@ -1403,8 +1474,11 @@ _initialize_thread (void) { static struct cmd_list_element *thread_apply_list = NULL; - add_info ("threads", info_threads_command, - _("IDs of currently known threads.")); + add_info ("threads", info_threads_command, + _("Display currently known threads.\n\ +Usage: info threads [ID [ID]...]\n\ +If ID is given, display only that thread or those threads;\n\ +otherwise, all threads are displayed.")); add_prefix_cmd ("thread", class_run, thread_command, _("\ Use this command to switch between threads.\n\ @@ -1418,11 +1492,15 @@ The new thread ID must be currently know add_cmd ("all", class_run, thread_apply_all_command, _("Apply a command to all threads."), &thread_apply_list); - add_cmd ("name", class_run, thread_name_command, + add_cmd ("name", no_class, thread_name_command, _("Set the current thread's name.\n\ Usage: thread name [NAME]\n\ If NAME is not given, then any existing name is removed."), &thread_cmd_list); + add_cmd ("find", no_class, thread_find_command, _("\ +Find thread ids with a name, target pid, or extra info matching REGEXP."), + &thread_cmd_list); + if (!xdb_commands) add_com_alias ("t", "thread", class_run, 1); Index: NEWS =================================================================== RCS file: /cvs/src/src/gdb/NEWS,v retrieving revision 1.425 diff -u -p -u -p -r1.425 NEWS --- NEWS 5 Feb 2011 05:27:23 -0000 1.425 +++ NEWS 14 Feb 2011 19:51:42 -0000 @@ -3,6 +3,10 @@ *** Changes since GDB 7.2 +* GDB has a new command: "thread find [regexp]". + It finds the thread id whose name, target id, or thread extra info + matches the given regular expression. + * The "catch syscall" command now works on mips*-linux* targets. * The -data-disassemble MI command now supports modes 2 and 3 for Index: doc/gdb.texinfo =================================================================== RCS file: /cvs/src/src/gdb/doc/gdb.texinfo,v retrieving revision 1.797 diff -u -p -u -p -r1.797 gdb.texinfo --- doc/gdb.texinfo 4 Feb 2011 21:54:15 -0000 1.797 +++ doc/gdb.texinfo 14 Feb 2011 19:51:44 -0000 @@ -2706,9 +2706,10 @@ number---always a single integer---with @table @code @kindex info threads -@item info threads -Display a summary of all threads currently in your -program. @value{GDBN} displays for each thread (in this order): +@item info threads @r{[}@var{ids}@r{]} +Display a summary of all threads currently in your program. Optional +argument @var{ids} means print information only about the specified +thread or threads. @value{GDBN} displays for each thread (in this order): @enumerate @item @@ -2805,6 +2806,24 @@ systems, a name specified with @samp{thr system-give name, and removing the user-specified name will cause @value{GDBN} to once again display the system-specified name. +@kindex thread find +@cindex search for a thread +@item thread find [@var{regexp}] +Search for and display thread ids whose name, target thread id, or +target extra info matches the supplied regular expression. + +As well as being the complement to the @samp{thread name} command, +this command also allows you to identify a thread by its target thread +id. For instance, on Linux, the target thread id is the LWP id. + +@smallexample +(@value{GDBN}) thread find 26688 +Thread 4 has target id 'Thread 0x41e02940 (LWP 26688)' +(@value{GDBN}) info thread 4 + Id Target Id Frame + 4 Thread 0x41e02940 (LWP 26688) 0x00000031ca6cd372 in select () +@end smallexample + @kindex set print thread-events @cindex print messages on thread start and exit @item set print thread-events ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-14 20:03 ` Michael Snyder @ 2011-02-14 20:40 ` Eli Zaretskii 2011-02-15 19:58 ` Tom Tromey 1 sibling, 0 replies; 15+ messages in thread From: Eli Zaretskii @ 2011-02-14 20:40 UTC (permalink / raw) To: Michael Snyder; +Cc: tromey, gdb-patches > Date: Mon, 14 Feb 2011 11:54:11 -0800 > From: Michael Snyder <msnyder@vmware.com> > > Documentation and NEWS also attached. Thanks. > + printf_filtered ("Thread %d has name '%s'\n", tp->num, tp->name); No _() (here and elsewhere in this function)? > *** Changes since GDB 7.2 > > +* GDB has a new command: "thread find [regexp]". > + It finds the thread id whose name, target id, or thread extra info > + matches the given regular expression. > + This part is okay. > +@item info threads @r{[}@var{ids}@r{]} > +Display a summary of all threads currently in your program. Optional > +argument @var{ids} means print information only about the specified > +thread or threads. We should say what is the syntax if @var{ids}. IIUC, "@var{id}@dots{}" is a better way of expressing it (but still, something should be said about the valid syntax, e.g. can I use "23-32"?) > +Search for and display thread ids whose name, target thread id, or > +target extra info matches the supplied regular expression. What you call "extra info" and "target thread id" is described under different names just a few dozen lines above this text. Let's use a consistent terminology, to avoid confusion, okay? > +As well as being the complement to the @samp{thread name} command, > +this command also allows you to identify a thread by its target thread > +id. For instance, on Linux, the target thread id is the LWP id. ^^^^^ "GNU/Linux", right? Okay with those changes. ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-14 20:03 ` Michael Snyder 2011-02-14 20:40 ` Eli Zaretskii @ 2011-02-15 19:58 ` Tom Tromey 2011-02-15 21:44 ` Michael Snyder 1 sibling, 1 reply; 15+ messages in thread From: Tom Tromey @ 2011-02-15 19:58 UTC (permalink / raw) To: Michael Snyder; +Cc: gdb-patches >>>>> "Michael" == Michael Snyder <msnyder@vmware.com> writes: Michael> static void Michael> info_threads_command (char *arg, int from_tty) [...] Michael> + int tmp_tid Michael> + = (int) parse_and_eval_long (scan_expression_with_cleanup (&arg, Michael> + NULL)); parse_and_eval_long means that expressions will be accepted here. But then I think it will do the wrong thing if you actually pass multiple IDs -- I think it will syntax error instead of parsing each separately. I'd suggest just parsing out an integer and using atoi or the like. (I'm not sure if there is already a convenience function for this -- I'm always a little surprised at how few argument-parsing convenience functions there are for the CLI.) I like "thread find", it seems handy. Matching both the ID and the target PID means that using numbers here will be over-eager. Why match the ID? "info thread ID" seems good enough. Michael> + add_info ("threads", info_threads_command, Michael> + _("Display currently known threads.\n\ Michael> +Usage: info threads [ID [ID]...]\n\ I think it is more typical to write this as: Usage: info threads [ID]... Michael> + add_cmd ("find", no_class, thread_find_command, _("\ Michael> +Find thread ids with a name, target pid, or extra info matching REGEXP."), Michael> + &thread_cmd_list); How about a Usage here, too? Like: Find threads that match a regular expression. Usage: thread find REGEXP This command will display all the threads whose name, target PID, or extra info matches REGEXP. Michael> +* GDB has a new command: "thread find [regexp]". I'd make regexp all upper-case, in keeping with a GNU documentation convention. Tom ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-15 19:58 ` Tom Tromey @ 2011-02-15 21:44 ` Michael Snyder 2011-02-16 11:58 ` Pedro Alves 2011-02-21 18:45 ` Tom Tromey 0 siblings, 2 replies; 15+ messages in thread From: Michael Snyder @ 2011-02-15 21:44 UTC (permalink / raw) To: Tom Tromey; +Cc: gdb-patches [-- Attachment #1: Type: text/plain, Size: 1984 bytes --] Tom Tromey wrote: >>>>>> "Michael" == Michael Snyder <msnyder@vmware.com> writes: > > Michael> static void > Michael> info_threads_command (char *arg, int from_tty) > [...] > Michael> + int tmp_tid > Michael> + = (int) parse_and_eval_long (scan_expression_with_cleanup (&arg, > Michael> + NULL)); > > parse_and_eval_long means that expressions will be accepted here. But > then I think it will do the wrong thing if you actually pass multiple > IDs -- I think it will syntax error instead of parsing each separately. > > I'd suggest just parsing out an integer and using atoi or the like. > (I'm not sure if there is already a convenience function for this -- I'm > always a little surprised at how few argument-parsing convenience > functions there are for the CLI.) OK. > I like "thread find", it seems handy. > > Matching both the ID and the target PID means that using numbers here > will be over-eager. Why match the ID? "info thread ID" seems good > enough. "info thread" will only match the gdb thread id (small counting integer). "thread find" will match the PID. > Michael> + add_info ("threads", info_threads_command, > Michael> + _("Display currently known threads.\n\ > Michael> +Usage: info threads [ID [ID]...]\n\ > > I think it is more typical to write this as: > > Usage: info threads [ID]... > > Michael> + add_cmd ("find", no_class, thread_find_command, _("\ > Michael> +Find thread ids with a name, target pid, or extra info matching REGEXP."), > Michael> + &thread_cmd_list); > > How about a Usage here, too? Like: > > Find threads that match a regular expression. > Usage: thread find REGEXP > This command will display all the threads whose name, target PID, or > extra info matches REGEXP. > > Michael> +* GDB has a new command: "thread find [regexp]". > > I'd make regexp all upper-case, in keeping with a GNU documentation > convention. OK, changes made, and committed as below (with a new testsuite test). [-- Attachment #2: find.txt --] [-- Type: text/plain, Size: 22633 bytes --] 2011-02-15 Michael Snyder <msnyder@vmware.com> * command.h (enum command_class): New class 'no_set_class', for "show" commands without a corresponding "set" command. * value.c (_initialize_values): Use 'no_set_class' for "show values". * copying.c (_initialize_copying): Ditto for "show copying" and "show warranty". * cli/cli-cmds.c (init_cli_cmds): Ditto for "show commands" and "show version". * cli/cli-setshow.c (cmd_show_list): Skip "show" commands for which there is no corresponding "set" command (eg. "show copying"). 2011-02-14 Michael Snyder <msnyder@vmware.com> * gdb.texinfo (threads): Document argument for "info threads" cmd. Document new command "thread find". 2011-02-15 Michael Snyder <msnyder@vmware.com> * gdb.base/default.exp: Add tests for thread commands. * gdb.base/help.exp: Add tests for thread commands. * gdb.threads/thread-find.exp: New test for thread find command. Index: NEWS =================================================================== RCS file: /cvs/src/src/gdb/NEWS,v retrieving revision 1.425 diff -u -p -u -p -r1.425 NEWS --- NEWS 5 Feb 2011 05:27:23 -0000 1.425 +++ NEWS 15 Feb 2011 21:14:27 -0000 @@ -3,6 +3,10 @@ *** Changes since GDB 7.2 +* GDB has a new command: "thread find [REGEXP]". + It finds the thread id whose name, target id, or thread extra info + matches the given regular expression. + * The "catch syscall" command now works on mips*-linux* targets. * The -data-disassemble MI command now supports modes 2 and 3 for Index: thread.c =================================================================== RCS file: /cvs/src/src/gdb/thread.c,v retrieving revision 1.131 diff -u -p -u -p -r1.131 thread.c --- thread.c 19 Jan 2011 17:21:36 -0000 1.131 +++ thread.c 15 Feb 2011 21:14:27 -0000 @@ -43,6 +43,7 @@ #include "observer.h" #include "annotate.h" #include "cli/cli-decode.h" +#include "gdb_regex.h" /* Definition of struct thread_info exported to gdbthread.h. */ @@ -954,18 +955,54 @@ No selected thread. See `help thread'.\ } } - /* Print information about currently known threads - * Note: this has the drawback that it _really_ switches - * threads, which frees the frame cache. A no-side - * effects info-threads command would be nicer. - */ + Optional ARG is a thread id, or list of thread ids. + + Note: this has the drawback that it _really_ switches + threads, which frees the frame cache. A no-side + effects info-threads command would be nicer. */ static void info_threads_command (char *arg, int from_tty) { - print_thread_info (uiout, -1, -1); + int tid = -1; + + if (arg == NULL || *arg == '\0') + { + print_thread_info (uiout, -1, -1); + return; + } + + while (arg != NULL && *arg != '\0') + { + int tmp_tid = strtol (arg, &arg, 0); + unsigned int highrange; + + if (tmp_tid <= 0) + error ("invalid thread id %d\n", tmp_tid); + + tid = tmp_tid; + print_thread_info (uiout, tid, -1); + + while (*arg == ' ' || *arg == '\t') + ++arg; + + if (*arg == '-') + { + /* Do a range of threads. Must be in ascending order. */ + ++arg; /* Skip the hyphen. */ + highrange = strtoul (arg, &arg, 0); + if (highrange < tid) + error (_("inverted range")); + + /* Do the threads in the range (first one already done). */ + while (tid < highrange) + { + print_thread_info (uiout, ++tid, -1); + } + } + } } /* Switch from one thread to another. */ @@ -1313,6 +1350,60 @@ thread_name_command (char *arg, int from info->name = arg ? xstrdup (arg) : NULL; } +/* Find thread ids with a name, target pid, or extra info matching ARG. */ + +static void +thread_find_command (char *arg, int from_tty) +{ + struct thread_info *tp; + char *tmp; + unsigned long match = 0; + + if (arg == NULL || *arg == '\0') + error (_("Command requires an argument.")); + + tmp = re_comp (arg); + if (tmp != 0) + error (_("Invalid regexp (%s): %s"), tmp, arg); + + update_thread_list (); + for (tp = thread_list; tp; tp = tp->next) + { + if (tp->name != NULL && re_exec (tp->name)) + { + printf_filtered (_("Thread %d has name '%s'\n"), + tp->num, tp->name); + match++; + } + + tmp = target_thread_name (tp); + if (tmp != NULL && re_exec (tmp)) + { + printf_filtered (_("Thread %d has target name '%s'\n"), + tp->num, tmp); + match++; + } + + tmp = target_pid_to_str (tp->ptid); + if (tmp != NULL && re_exec (tmp)) + { + printf_filtered (_("Thread %d has target id '%s'\n"), + tp->num, tmp); + match++; + } + + tmp = target_extra_thread_info (tp); + if (tmp != NULL && re_exec (tmp)) + { + printf_filtered (_("Thread %d has extra info '%s'\n"), + tp->num, tmp); + match++; + } + } + if (!match) + printf_filtered (_("No threads match '%s'\n"), arg); +} + /* Print notices when new threads are attached and detached. */ int print_thread_events = 1; static void @@ -1403,8 +1494,11 @@ _initialize_thread (void) { static struct cmd_list_element *thread_apply_list = NULL; - add_info ("threads", info_threads_command, - _("IDs of currently known threads.")); + add_info ("threads", info_threads_command, + _("Display currently known threads.\n\ +Usage: info threads [ID]...\n\ +Optional arguments are thread IDs with spaces between.\n\ +If no arguments, all threads are displayed.")); add_prefix_cmd ("thread", class_run, thread_command, _("\ Use this command to switch between threads.\n\ @@ -1423,6 +1517,12 @@ The new thread ID must be currently know Usage: thread name [NAME]\n\ If NAME is not given, then any existing name is removed."), &thread_cmd_list); + add_cmd ("find", class_run, thread_find_command, _("\ +Find threads that match a regular expression.\n\ +Usage: thread find REGEXP\n\ +Will display thread ids whose name, target ID, or extra info matches REGEXP."), + &thread_cmd_list); + if (!xdb_commands) add_com_alias ("t", "thread", class_run, 1); Index: doc/gdb.texinfo =================================================================== RCS file: /cvs/src/src/gdb/doc/gdb.texinfo,v retrieving revision 1.799 diff -u -p -u -p -r1.799 gdb.texinfo --- doc/gdb.texinfo 14 Feb 2011 23:14:35 -0000 1.799 +++ doc/gdb.texinfo 15 Feb 2011 21:14:27 -0000 @@ -2706,9 +2706,11 @@ number---always a single integer---with @table @code @kindex info threads -@item info threads -Display a summary of all threads currently in your -program. @value{GDBN} displays for each thread (in this order): +@item info threads @r{[}@var{id}@dots{}@r{]} +Display a summary of all threads currently in your program. Optional +argument @var{id}@dots{} is one or more thread ids separated by spaces, and +means to print information only about the specified thread or threads. +@value{GDBN} displays for each thread (in this order): @enumerate @item @@ -2805,6 +2807,25 @@ systems, a name specified with @samp{thr system-give name, and removing the user-specified name will cause @value{GDBN} to once again display the system-specified name. +@kindex thread find +@cindex search for a thread +@item thread find [@var{regexp}] +Search for and display thread ids whose name or @var{systag} +matches the supplied regular expression. + +As well as being the complement to the @samp{thread name} command, +this command also allows you to identify a thread by its target +@var{systag}. For instance, on @sc{gnu}/Linux, the target @var{systag} +is the LWP id. + +@smallexample +(@value{GDBN}) thread find 26688 +Thread 4 has target id 'Thread 0x41e02940 (LWP 26688)' +(@value{GDBN}) info thread 4 + Id Target Id Frame + 4 Thread 0x41e02940 (LWP 26688) 0x00000031ca6cd372 in select () +@end smallexample + @kindex set print thread-events @cindex print messages on thread start and exit @item set print thread-events Index: testsuite/gdb.base/default.exp =================================================================== RCS file: /cvs/src/src/gdb/testsuite/gdb.base/default.exp,v retrieving revision 1.47 diff -u -p -u -p -r1.47 default.exp --- testsuite/gdb.base/default.exp 1 Jan 2011 15:33:41 -0000 1.47 +++ testsuite/gdb.base/default.exp 15 Feb 2011 21:14:27 -0000 @@ -356,6 +356,8 @@ gdb_test "info sources" "No symbol table gdb_test_no_output "info target" "info target" #test info terminal gdb_test "info terminal" "No saved terminal information." "info terminal" +# test info threads +gdb_test "info threads" "No threads." "info threads" #test info types gdb_test "info types" "All defined types:" "info types" #test info variables @@ -779,6 +781,14 @@ if ![istarget "*-*-udi*"] then { gdb_test "target" "Argument required .target name.*" "target" #test tbreak gdb_test "tbreak" "No default breakpoint address now." "tbreak" +#test thread +gdb_test "thread" "No thread selected" "thread" +#test thread apply +gdb_test "thread apply" "Please specify a thread ID list" "thread apply" +#test thread find +gdb_test "thread find" "Command requires an argument." "thread find" +#test thread name +gdb_test "thread name" "No thread selected" "thread name" #test tty gdb_test "tty" "Argument required .filename to set it to\..*" "tty" #test until "u" abbreviation Index: testsuite/gdb.base/help.exp =================================================================== RCS file: /cvs/src/src/gdb/testsuite/gdb.base/help.exp,v retrieving revision 1.48 diff -u -p -u -p -r1.48 help.exp --- testsuite/gdb.base/help.exp 1 Jan 2011 15:33:42 -0000 1.48 +++ testsuite/gdb.base/help.exp 15 Feb 2011 21:14:27 -0000 @@ -281,6 +281,8 @@ gdb_test "help info symbol" "Describe wh gdb_test "help info target" "Names of targets and files being debugged\.\[\r\n\]+Shows the entire stack of targets currently in use \\(including the exec-file,\[\r\n\]+core-file, and process, if any\\), as well as the symbol file name\." "help info target" # test help info terminal gdb_test "help info terminal" "Print inferior's saved terminal status\." "help info terminal" +# test help info threads +gdb_test "help info threads" "Display currently known threads.*" "help info threads" # test help info types gdb_test "help info types" "All type names, or those matching REGEXP\." "help info types" # test help info variables @@ -644,6 +646,14 @@ test_prefix_command_help "target" { } # test help tbreak gdb_test "help tbreak" "Set a temporary breakpoint.*" "help tbreak" +#test help thread +gdb_test "help thread" "Use this command to switch between threads.*" "help thread" +# test help thread apply +gdb_test "help thread apply" "Apply a command to a list of threads.*" "help thread apply" +# test help thread find +gdb_test "help thread find" "Find threads that match a regular.*" help thread find" +# test help thread name +gdb_test "help thread name" "Set the current thread's name.*" "help thread name" # test help tty gdb_test "help tty" "Set terminal for future runs of program being debugged\.\[\r\n\]+Usage: set inferior-tty /dev/pts/1" "help tty" # test help until "u" abbreviation Index: testsuite/gdb.threads/thread-find.exp =================================================================== RCS file: testsuite/gdb.threads/thread-find.exp diff -N testsuite/gdb.threads/thread-find.exp --- /dev/null 1 Jan 1970 00:00:00 -0000 +++ testsuite/gdb.threads/thread-find.exp 15 Feb 2011 21:14:27 -0000 @@ -0,0 +1,430 @@ +# Copyright 2011 +# Free Software Foundation, Inc. + +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see <http://www.gnu.org/licenses/>. + +# Please email any bugs, comments, and/or additions to this file to: +# bug-gdb@gnu.org + +if $tracelevel then { + strace $tracelevel +} + +set testfile "linux-dp" +set srcfile ${testfile}.c +set binfile ${objdir}/${subdir}/${testfile} +if {[gdb_compile_pthreads "${srcdir}/${subdir}/${srcfile}" "${binfile}" executable {debug}] != ""} { + return -1 +} + +gdb_start +gdb_reinitialize_dir $srcdir/$subdir +gdb_load ${binfile} +gdb_test_no_output "set print sevenbit-strings" +runto_main + +# Run until there are some threads. +gdb_breakpoint [gdb_get_line_number "linuxthreads.exp: info threads 2"] +gdb_continue_to_breakpoint "main thread's sleep" + +# Create thread names. +gdb_test "thread apply 1 thread name threadname_1" \ + "Thread 1 .*" \ + "name thread 1" + +gdb_test "thread apply 2 thread name threadname_2" \ + "Thread 2 .*" \ + "name thread 2" + +gdb_test "thread apply 3 thread name threadname_3" \ + "Thread 3 .*" \ + "name thread 3" + +gdb_test "thread apply 4 thread name threadname_4" \ + "Thread 4 .*" \ + "name thread 4" + +gdb_test "thread apply 5 thread name threadname_5" \ + "Thread 5 .*" \ + "name thread 5" + +gdb_test "thread apply 6 thread name threadname_6" \ + "Thread 6 .*" \ + "name thread 6" + +# Collect thread ids, if any. +gdb_test_multiple "info threads" "collect thread id" { + -re ". 6 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_6\" \[^\r\n\]*" { + set thread6 $expect_out(1,string) + exp_continue + } + -re ". 5 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_5\" \[^\r\n\]*" { + set thread5 $expect_out(1,string) + exp_continue + } + -re ". 4 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_4\" \[^\r\n\]*" { + set thread4 $expect_out(1,string) + exp_continue + } + -re ". 3 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_3\" \[^\r\n\]*" { + set thread3 $expect_out(1,string) + exp_continue + } + -re ". 2 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_2\" \[^\r\n\]*" { + set thread2 $expect_out(1,string) + exp_continue + } + -re ". 1 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_1\" \[^\r\n\]*" { + set thread1 $expect_out(1,string) + exp_continue + } + -re ".*$gdb_prompt $" { + pass "collect thread id" + } +} + +if { [info exists thread6] } then { + gdb_test "echo $thread6\\n" "$thread6" "got thread ids" +} + +# Collect process ids, if any. +gdb_test_multiple "info threads" "collect thread id" { + -re ". 6 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_6\" \[^\r\n\]*" { + set process6 $expect_out(1,string) + exp_continue + } + -re ". 5 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_5\" \[^\r\n\]*" { + set process5 $expect_out(1,string) + exp_continue + } + -re ". 4 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_4\" \[^\r\n\]*" { + set process4 $expect_out(1,string) + exp_continue + } + -re ". 3 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_3\" \[^\r\n\]*" { + set process3 $expect_out(1,string) + exp_continue + } + -re ". 2 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_2\" \[^\r\n\]*" { + set process2 $expect_out(1,string) + exp_continue + } + -re ". 1 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_1\" \[^\r\n\]*" { + set process1 $expect_out(1,string) + exp_continue + } + -re ".*$gdb_prompt $" { + pass "collect process id" + } +} + +if { [info exists process6] } then { + gdb_test "echo $process6\\n" "$process6" "got process ids" +} + +# Collect lwp ids, if any. +gdb_test_multiple "info threads" "collect thread id" { + -re ". 6 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_6\" \[^\r\n\]*" { + set lwp6 $expect_out(1,string) + exp_continue + } + -re ". 5 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_5\" \[^\r\n\]*" { + set lwp5 $expect_out(1,string) + exp_continue + } + -re ". 4 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_4\" \[^\r\n\]*" { + set lwp4 $expect_out(1,string) + exp_continue + } + -re ". 3 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_3\" \[^\r\n\]*" { + set lwp3 $expect_out(1,string) + exp_continue + } + -re ". 2 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_2\" \[^\r\n\]*" { + set lwp2 $expect_out(1,string) + exp_continue + } + -re ". 1 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_1\" \[^\r\n\]*" { + set lwp1 $expect_out(1,string) + exp_continue + } + -re ".*$gdb_prompt $" { + pass "collect lwp id" + } +} + +if { [info exists lwp6] } then { + gdb_test "echo $lwp6\\n" "$lwp6" "got lwp ids" +} + +# +# Now: test 'thread find' with names. +# + +gdb_test "thread find threadname_6" \ + "Thread 6 has name 'threadname_6'" "find thread name 6" +gdb_test "thread find threadname_5" \ + "Thread 5 has name 'threadname_5'" "find thread name 5" +gdb_test "thread find threadname_4" \ + "Thread 4 has name 'threadname_4'" "find thread name 4" +gdb_test "thread find threadname_3" \ + "Thread 3 has name 'threadname_3'" "find thread name 3" +gdb_test "thread find threadname_2" \ + "Thread 2 has name 'threadname_2'" "find thread name 2" +gdb_test "thread find threadname_1" \ + "Thread 1 has name 'threadname_1'" "find thread name 1" + +# +# Test 'thread find' with thread ids, if any. +# + +if { [info exists thread6] } then { + gdb_test "thread find $thread6" \ + "Thread 6 has .*$thread6.*" "find thread id 6" + gdb_test "thread find $thread5" \ + "Thread 5 has .*$thread5.*" "find thread id 5" + gdb_test "thread find $thread4" \ + "Thread 4 has .*$thread4.*" "find thread id 4" + gdb_test "thread find $thread3" \ + "Thread 3 has .*$thread3.*" "find thread id 3" + gdb_test "thread find $thread2" \ + "Thread 2 has .*$thread2.*" "find thread id 2" + gdb_test "thread find $thread1" \ + "Thread 1 has .*$thread1.*" "find thread id 1" +} + +# +# Test 'thread find' with process ids, if any. +# + +if { [info exists process6] } then { + gdb_test "thread find $process6" \ + "Thread 6 has .*$process6.*" "find process id 6" + gdb_test "thread find $process5" \ + "Thread 5 has .*$process5.*" "find process id 5" + gdb_test "thread find $process4" \ + "Thread 4 has .*$process4.*" "find process id 4" + gdb_test "thread find $process3" \ + "Thread 3 has .*$process3.*" "find process id 3" + gdb_test "thread find $process2" \ + "Thread 2 has .*$process2.*" "find process id 2" + gdb_test "thread find $process1" \ + "Thread 1 has .*$process1.*" "find process id 1" +} + +# +# Test 'thread find' with lwp ids, if any. +# + +if { [info exists lwp6] } then { + gdb_test "thread find $lwp6" \ + "Thread 6 has .*$lwp6.*" "find lwp id 6" + gdb_test "thread find $lwp5" \ + "Thread 5 has .*$lwp5.*" "find lwp id 5" + gdb_test "thread find $lwp4" \ + "Thread 4 has .*$lwp4.*" "find lwp id 4" + gdb_test "thread find $lwp3" \ + "Thread 3 has .*$lwp3.*" "find lwp id 3" + gdb_test "thread find $lwp2" \ + "Thread 2 has .*$lwp2.*" "find lwp id 2" + gdb_test "thread find $lwp1" \ + "Thread 1 has .*$lwp1.*" "find lwp id 1" +} + +# Test no match. + +gdb_test "thread find foobarbaz" "No threads match .*" "no thread" + +# +# Test regular expression +# + +set see1 0 +set see2 0 +set see3 0 +set see4 0 +set see5 0 +set see6 0 + +gdb_test_multiple "thread find threadname_\[345\]" "test regular exp" { + -re "Thread 6 has name \[^\r\n\]*" { + set see6 1 + exp_continue + } + -re "Thread 5 has name \[^\r\n\]*" { + set see5 1 + exp_continue + } + -re "Thread 4 has name \[^\r\n\]*" { + set see4 1 + exp_continue + } + -re "Thread 3 has name \[^\r\n\]*" { + set see3 1 + exp_continue + } + -re "Thread 2 has name \[^\r\n\]*" { + set see2 1 + exp_continue + } + -re "Thread 1 has name \[^\r\n\]*" { + set see1 1 + exp_continue + } + -re ".*$gdb_prompt $" { + if { $see3 && $see4 && $see5 && !$see1 && !$see2 && !$see6 } then { + pass "test regular exp" + } else { + fail "test regular exp" + } + } +} + +# +# Test info threads on a subset of threads +# + +set see1 0 +set see2 0 +set see3 0 +set see4 0 +set see5 0 +set see6 0 + +gdb_test_multiple "info threads 2 4 6" "info threads 2 4 6" { + -re ". 6 .*\"threadname_6.*\" \[\r\n\]*" { + set see6 1 + exp_continue + } + -re ". 5 .*\"threadname_5.*\" \[\r\n\]*" { + set see5 1 + exp_continue + } + -re ". 4 .*\"threadname_4.*\" \[\r\n\]*" { + set see4 1 + exp_continue + } + -re ". 3 .*\"threadname_3.*\" \[\r\n\]*" { + set see3 1 + exp_continue + } + -re ". 2 .*\"threadname_2.*\" \[\r\n\]*" { + set see2 1 + exp_continue + } + -re ". 1 .*\"threadname_1.*\" \[\r\n\]*" { + set see1 1 + exp_continue + } + -re ".*$gdb_prompt $" { + if { $see2 && $see4 && $see6 && !$see1 && !$see3 && !$see5 } then { + pass "info threads 2 4 6" + } else { + fail "info threads 2 4 6" + } + } +} + +# +# Test info threads on a range +# + +set see1 0 +set see2 0 +set see3 0 +set see4 0 +set see5 0 +set see6 0 + +gdb_test_multiple "info threads 3-5" "info threads 3-5" { + -re ". 6 .*\"threadname_6.*\" \[\r\n\]*" { + set see6 1 + exp_continue + } + -re ". 5 .*\"threadname_5.*\" \[\r\n\]*" { + set see5 1 + exp_continue + } + -re ". 4 .*\"threadname_4.*\" \[\r\n\]*" { + set see4 1 + exp_continue + } + -re ". 3 .*\"threadname_3.*\" \[\r\n\]*" { + set see3 1 + exp_continue + } + -re ". 2 .*\"threadname_2.*\" \[\r\n\]*" { + set see2 1 + exp_continue + } + -re ". 1 .*\"threadname_1.*\" \[\r\n\]*" { + set see1 1 + exp_continue + } + -re ".*$gdb_prompt $" { + if { $see3 && $see4 && $see5 && !$see1 && !$see2 && !$see6 } then { + pass "info threads 3-5" + } else { + fail "info threads 3-5" + } + } +} + +# Test inverted range + +gdb_test "info threads 5-3" "inverted range" "test inverted range" + +# Test degenerate range + +set see1 0 +set see2 0 +set see3 0 +set see4 0 +set see5 0 +set see6 0 + +gdb_test_multiple "info threads 3-3" "info threads 3-3" { + -re ". 6 .*\"threadname_6.*\" \[\r\n\]*" { + set see6 1 + exp_continue + } + -re ". 5 .*\"threadname_5.*\" \[\r\n\]*" { + set see5 1 + exp_continue + } + -re ". 4 .*\"threadname_4.*\" \[\r\n\]*" { + set see4 1 + exp_continue + } + -re ". 3 .*\"threadname_3.*\" \[\r\n\]*" { + set see3 1 + exp_continue + } + -re ". 2 .*\"threadname_2.*\" \[\r\n\]*" { + set see2 1 + exp_continue + } + -re ". 1 .*\"threadname_1.*\" \[\r\n\]*" { + set see1 1 + exp_continue + } + -re ".*$gdb_prompt $" { + if { $see3 && !$see1 && !$see2 && !$see4 && !$see5 && !$see6 } then { + pass "info threads 3-3" + } else { + fail "info threads 3-3" + } + } +} + ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-15 21:44 ` Michael Snyder @ 2011-02-16 11:58 ` Pedro Alves 2011-02-16 18:47 ` Michael Snyder 2011-02-21 18:45 ` Tom Tromey 1 sibling, 1 reply; 15+ messages in thread From: Pedro Alves @ 2011-02-16 11:58 UTC (permalink / raw) To: gdb-patches; +Cc: Michael Snyder, Tom Tromey On Tuesday 15 February 2011 21:18:31, Michael Snyder wrote: > > find.txt > 2011-02-15 Michael Snyder <msnyder@vmware.com> > > * command.h (enum command_class): New class 'no_set_class', for > "show" commands without a corresponding "set" command. > * value.c (_initialize_values): Use 'no_set_class' for "show values". > * copying.c (_initialize_copying): Ditto for "show copying" and > "show warranty". > * cli/cli-cmds.c (init_cli_cmds): Ditto for "show commands" and > "show version". > * cli/cli-setshow.c (cmd_show_list): Skip "show" commands for > which there is no corresponding "set" command (eg. "show copying"). Wrong changelog entry, btw. Here's the correct one, to ease code archaeology / web search in the future: 2011-02-15 Michael Snyder <msnyder@vmware.com> * thread.c (info_threads_command): Process arg as thread id, or list of thread ids. (thread_find_command): New command. (_initialize_thread): Document argument for info threads. Document 'thread find' command. * NEWS: Document new command "thread find". > Index: NEWS > =================================================================== > RCS file: /cvs/src/src/gdb/NEWS,v > retrieving revision 1.425 > diff -u -p -u -p -r1.425 NEWS > --- NEWS 5 Feb 2011 05:27:23 -0000 1.425 > +++ NEWS 15 Feb 2011 21:14:27 -0000 > @@ -3,6 +3,10 @@ > > *** Changes since GDB 7.2 > > +* GDB has a new command: "thread find [REGEXP]". > + It finds the thread id whose name, target id, or thread extra info > + matches the given regular expression. IMO, it'd be nice to mention the "info threads" change as well. Anyway, the reason I'm replying is that I noticed a couple of new FAILs in this test, and looking at the log, I noticed another issue: info threads 2 4 6 Id Target Id Frame 2 Thread 0x2aaaab6f4700 (LWP 335) "threadname_2" 0x00002aaaab24e2c3 in select () from /lib/libc.so.6 Id Target Id Frame 4 Thread 0x2aaaabaf7700 (LWP 337) "threadname_4" 0x00002aaaab24e2c3 in select () from /lib/libc.so.6 Id Target Id Frame 6 Thread 0x2aaaabef9700 (LWP 339) "threadname_6" 0x00002aaaab1f7050 in strchrnul () from /lib/libc.so.6 (gdb) FAIL: gdb.threads/thread-find.exp: info threads 2 4 6 info threads 3-5 Id Target Id Frame 3 Thread 0x2aaaab8f5700 (LWP 336) "threadname_3" 0x00002aaaab24e2c3 in select () from /lib/libc.so.6 Id Target Id Frame 4 Thread 0x2aaaabaf7700 (LWP 337) "threadname_4" 0x00002aaaab24e2c3 in select () from /lib/libc.so.6 Id Target Id Frame 5 Thread 0x2aaaabcf8700 (LWP 338) "threadname_5" 0x00002aaaab24e2c3 in select () from /lib/libc.so.6 (gdb) FAIL: gdb.threads/thread-find.exp: info threads 3-5 The header is printed once for each entry. Was that intended? It doesn't seem right to me. -- Pedro Alves ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-16 11:58 ` Pedro Alves @ 2011-02-16 18:47 ` Michael Snyder 2011-02-17 16:57 ` Jan Kratochvil 0 siblings, 1 reply; 15+ messages in thread From: Michael Snyder @ 2011-02-16 18:47 UTC (permalink / raw) To: Pedro Alves; +Cc: gdb-patches, Tom Tromey Pedro Alves wrote: > On Tuesday 15 February 2011 21:18:31, Michael Snyder wrote: >> find.txt >> 2011-02-15 Michael Snyder <msnyder@vmware.com> >> >> * command.h (enum command_class): New class 'no_set_class', for >> "show" commands without a corresponding "set" command. >> * value.c (_initialize_values): Use 'no_set_class' for "show values". >> * copying.c (_initialize_copying): Ditto for "show copying" and >> "show warranty". >> * cli/cli-cmds.c (init_cli_cmds): Ditto for "show commands" and >> "show version". >> * cli/cli-setshow.c (cmd_show_list): Skip "show" commands for >> which there is no corresponding "set" command (eg. "show copying"). > > Wrong changelog entry, btw. Here's the correct one, to ease > code archaeology / web search in the future: Sorry, fixed. > > 2011-02-15 Michael Snyder <msnyder@vmware.com> > > * thread.c (info_threads_command): Process arg as thread id, > or list of thread ids. > (thread_find_command): New command. > (_initialize_thread): Document argument for info threads. > Document 'thread find' command. > * NEWS: Document new command "thread find". > >> Index: NEWS >> =================================================================== >> RCS file: /cvs/src/src/gdb/NEWS,v >> retrieving revision 1.425 >> diff -u -p -u -p -r1.425 NEWS >> --- NEWS 5 Feb 2011 05:27:23 -0000 1.425 >> +++ NEWS 15 Feb 2011 21:14:27 -0000 >> @@ -3,6 +3,10 @@ >> >> *** Changes since GDB 7.2 >> >> +* GDB has a new command: "thread find [REGEXP]". >> + It finds the thread id whose name, target id, or thread extra info >> + matches the given regular expression. > > IMO, it'd be nice to mention the "info threads" change as well. > > Anyway, the reason I'm replying is that I noticed a couple > of new FAILs in this test, and looking at the log, I noticed > another issue: Urk. I did half my work on the 7.2 branch, where it doesn't do this. Let me fix it. > info threads 2 4 6 > Id Target Id Frame > 2 Thread 0x2aaaab6f4700 (LWP 335) "threadname_2" 0x00002aaaab24e2c3 in select () from /lib/libc.so.6 > Id Target Id Frame > 4 Thread 0x2aaaabaf7700 (LWP 337) "threadname_4" 0x00002aaaab24e2c3 in select () from /lib/libc.so.6 > Id Target Id Frame > 6 Thread 0x2aaaabef9700 (LWP 339) "threadname_6" 0x00002aaaab1f7050 in strchrnul () from /lib/libc.so.6 > (gdb) FAIL: gdb.threads/thread-find.exp: info threads 2 4 6 > info threads 3-5 > Id Target Id Frame > 3 Thread 0x2aaaab8f5700 (LWP 336) "threadname_3" 0x00002aaaab24e2c3 in select () from /lib/libc.so.6 > Id Target Id Frame > 4 Thread 0x2aaaabaf7700 (LWP 337) "threadname_4" 0x00002aaaab24e2c3 in select () from /lib/libc.so.6 > Id Target Id Frame > 5 Thread 0x2aaaabcf8700 (LWP 338) "threadname_5" 0x00002aaaab24e2c3 in select () from /lib/libc.so.6 > (gdb) FAIL: gdb.threads/thread-find.exp: info threads 3-5 > > The header is printed once for each entry. Was that > intended? It doesn't seem right to me. > ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-16 18:47 ` Michael Snyder @ 2011-02-17 16:57 ` Jan Kratochvil 2011-02-17 19:12 ` Michael Snyder 2011-02-17 20:11 ` Michael Snyder 0 siblings, 2 replies; 15+ messages in thread From: Jan Kratochvil @ 2011-02-17 16:57 UTC (permalink / raw) To: Michael Snyder; +Cc: Pedro Alves, gdb-patches, Tom Tromey On Wed, 16 Feb 2011 19:26:33 +0100, Michael Snyder wrote: > Pedro Alves wrote: > >Anyway, the reason I'm replying is that I noticed a couple > >of new FAILs in this test, and looking at the log, I noticed > >another issue: > > Urk. I did half my work on the 7.2 branch, where it doesn't do this. > Let me fix it. I also see the failure: info threads 2 4 6 Id Target Id Frame 2 Thread 0x7ffff759e700 (LWP 24773) "threadname_2" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 Id Target Id Frame 4 Thread 0x7ffff659c700 (LWP 24775) "threadname_4" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 Id Target Id Frame 6 Thread 0x7ffff559a700 (LWP 24777) "threadname_6" __lll_lock_wait () at ../nptl/sysdeps/unix/sysv/linux/x86_64/lowlevellock.S:136 (gdb) FAIL: gdb.threads/thread-find.exp: info threads 2 4 6 -re ". 6 .*\"threadname_6.*\" \[\r\n\]*" { set see6 1 exp_continue } -re ". 5 .*\"threadname_5.*\" \[\r\n\]*" { set see5 1 exp_continue } This is racy, * of the regexp is greedy by default and there can be multiple threadnames available during a single read/match, one match can swallow multiple entries. There should be some \[^\r\n\]* instead of any .* during such unanchored matching. One may also rather catch the whole output and regex-match by hand the caught output afterwards. Thanks, Jan ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-17 16:57 ` Jan Kratochvil @ 2011-02-17 19:12 ` Michael Snyder 2011-02-17 20:11 ` Michael Snyder 1 sibling, 0 replies; 15+ messages in thread From: Michael Snyder @ 2011-02-17 19:12 UTC (permalink / raw) To: Jan Kratochvil; +Cc: Pedro Alves, gdb-patches, Tom Tromey Jan Kratochvil wrote: > On Wed, 16 Feb 2011 19:26:33 +0100, Michael Snyder wrote: >> Pedro Alves wrote: >>> Anyway, the reason I'm replying is that I noticed a couple >>> of new FAILs in this test, and looking at the log, I noticed >>> another issue: >> Urk. I did half my work on the 7.2 branch, where it doesn't do this. >> Let me fix it. > > I also see the failure: > > info threads 2 4 6 > Id Target Id Frame > 2 Thread 0x7ffff759e700 (LWP 24773) "threadname_2" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 > Id Target Id Frame > 4 Thread 0x7ffff659c700 (LWP 24775) "threadname_4" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 > Id Target Id Frame > 6 Thread 0x7ffff559a700 (LWP 24777) "threadname_6" __lll_lock_wait () at ../nptl/sysdeps/unix/sysv/linux/x86_64/lowlevellock.S:136 > (gdb) FAIL: gdb.threads/thread-find.exp: info threads 2 4 6 > > -re ". 6 .*\"threadname_6.*\" \[\r\n\]*" { > set see6 1 > exp_continue > } > -re ". 5 .*\"threadname_5.*\" \[\r\n\]*" { > set see5 1 > exp_continue > } > > This is racy, * of the regexp is greedy by default and there can be multiple > threadnames available during a single read/match, one match can swallow > multiple entries. There should be some \[^\r\n\]* instead of any .* during > such unanchored matching. > > One may also rather catch the whole output and regex-match by hand the caught > output afterwards. I am not seeing these failures, even on the trunk. Would you guys please email me your gdb.log files for this test? Thanks, Michael ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-17 16:57 ` Jan Kratochvil 2011-02-17 19:12 ` Michael Snyder @ 2011-02-17 20:11 ` Michael Snyder 2011-02-17 21:22 ` Jan Kratochvil 1 sibling, 1 reply; 15+ messages in thread From: Michael Snyder @ 2011-02-17 20:11 UTC (permalink / raw) To: Jan Kratochvil; +Cc: Pedro Alves, gdb-patches, Tom Tromey [-- Attachment #1: Type: text/plain, Size: 1506 bytes --] Jan Kratochvil wrote: > On Wed, 16 Feb 2011 19:26:33 +0100, Michael Snyder wrote: >> Pedro Alves wrote: >>> Anyway, the reason I'm replying is that I noticed a couple >>> of new FAILs in this test, and looking at the log, I noticed >>> another issue: >> Urk. I did half my work on the 7.2 branch, where it doesn't do this. >> Let me fix it. > > I also see the failure: > > info threads 2 4 6 > Id Target Id Frame > 2 Thread 0x7ffff759e700 (LWP 24773) "threadname_2" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 > Id Target Id Frame > 4 Thread 0x7ffff659c700 (LWP 24775) "threadname_4" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 > Id Target Id Frame > 6 Thread 0x7ffff559a700 (LWP 24777) "threadname_6" __lll_lock_wait () at ../nptl/sysdeps/unix/sysv/linux/x86_64/lowlevellock.S:136 > (gdb) FAIL: gdb.threads/thread-find.exp: info threads 2 4 6 > > -re ". 6 .*\"threadname_6.*\" \[\r\n\]*" { > set see6 1 > exp_continue > } > -re ". 5 .*\"threadname_5.*\" \[\r\n\]*" { > set see5 1 > exp_continue > } > > This is racy, * of the regexp is greedy by default and there can be multiple > threadnames available during a single read/match, one match can swallow > multiple entries. There should be some \[^\r\n\]* instead of any .* during > such unanchored matching. You're right, there is an extra .* in there. Can you please try the attached? [-- Attachment #2: thread-find.exp --] [-- Type: text/plain, Size: 10755 bytes --] # Copyright 2011 # Free Software Foundation, Inc. # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 3 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see <http://www.gnu.org/licenses/>. # Please email any bugs, comments, and/or additions to this file to: # bug-gdb@gnu.org if $tracelevel then { strace $tracelevel } set testfile "linux-dp" set srcfile ${testfile}.c set binfile ${objdir}/${subdir}/${testfile} if {[gdb_compile_pthreads "${srcdir}/${subdir}/${srcfile}" "${binfile}" executable {debug}] != ""} { return -1 } gdb_start gdb_reinitialize_dir $srcdir/$subdir gdb_load ${binfile} gdb_test_no_output "set print sevenbit-strings" runto_main # Run until there are some threads. gdb_breakpoint [gdb_get_line_number "linuxthreads.exp: info threads 2"] gdb_continue_to_breakpoint "main thread's sleep" # Create thread names. gdb_test "thread apply 1 thread name threadname_1" \ "Thread 1 .*" \ "name thread 1" gdb_test "thread apply 2 thread name threadname_2" \ "Thread 2 .*" \ "name thread 2" gdb_test "thread apply 3 thread name threadname_3" \ "Thread 3 .*" \ "name thread 3" gdb_test "thread apply 4 thread name threadname_4" \ "Thread 4 .*" \ "name thread 4" gdb_test "thread apply 5 thread name threadname_5" \ "Thread 5 .*" \ "name thread 5" gdb_test "thread apply 6 thread name threadname_6" \ "Thread 6 .*" \ "name thread 6" # Collect thread ids, if any. gdb_test_multiple "info threads" "collect thread id" { -re ". 6 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_6\" \[^\r\n\]*" { set thread6 $expect_out(1,string) exp_continue } -re ". 5 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_5\" \[^\r\n\]*" { set thread5 $expect_out(1,string) exp_continue } -re ". 4 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_4\" \[^\r\n\]*" { set thread4 $expect_out(1,string) exp_continue } -re ". 3 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_3\" \[^\r\n\]*" { set thread3 $expect_out(1,string) exp_continue } -re ". 2 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_2\" \[^\r\n\]*" { set thread2 $expect_out(1,string) exp_continue } -re ". 1 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_1\" \[^\r\n\]*" { set thread1 $expect_out(1,string) exp_continue } -re ".*$gdb_prompt $" { pass "collect thread id" } } if { [info exists thread6] } then { gdb_test "echo $thread6\\n" "$thread6" "got thread ids" } # Collect process ids, if any. gdb_test_multiple "info threads" "collect thread id" { -re ". 6 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_6\" \[^\r\n\]*" { set process6 $expect_out(1,string) exp_continue } -re ". 5 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_5\" \[^\r\n\]*" { set process5 $expect_out(1,string) exp_continue } -re ". 4 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_4\" \[^\r\n\]*" { set process4 $expect_out(1,string) exp_continue } -re ". 3 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_3\" \[^\r\n\]*" { set process3 $expect_out(1,string) exp_continue } -re ". 2 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_2\" \[^\r\n\]*" { set process2 $expect_out(1,string) exp_continue } -re ". 1 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_1\" \[^\r\n\]*" { set process1 $expect_out(1,string) exp_continue } -re ".*$gdb_prompt $" { pass "collect process id" } } if { [info exists process6] } then { gdb_test "echo $process6\\n" "$process6" "got process ids" } # Collect lwp ids, if any. gdb_test_multiple "info threads" "collect thread id" { -re ". 6 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_6\" \[^\r\n\]*" { set lwp6 $expect_out(1,string) exp_continue } -re ". 5 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_5\" \[^\r\n\]*" { set lwp5 $expect_out(1,string) exp_continue } -re ". 4 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_4\" \[^\r\n\]*" { set lwp4 $expect_out(1,string) exp_continue } -re ". 3 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_3\" \[^\r\n\]*" { set lwp3 $expect_out(1,string) exp_continue } -re ". 2 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_2\" \[^\r\n\]*" { set lwp2 $expect_out(1,string) exp_continue } -re ". 1 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_1\" \[^\r\n\]*" { set lwp1 $expect_out(1,string) exp_continue } -re ".*$gdb_prompt $" { pass "collect lwp id" } } if { [info exists lwp6] } then { gdb_test "echo $lwp6\\n" "$lwp6" "got lwp ids" } # # Now: test 'thread find' with names. # gdb_test "thread find threadname_6" \ "Thread 6 has name 'threadname_6'" "find thread name 6" gdb_test "thread find threadname_5" \ "Thread 5 has name 'threadname_5'" "find thread name 5" gdb_test "thread find threadname_4" \ "Thread 4 has name 'threadname_4'" "find thread name 4" gdb_test "thread find threadname_3" \ "Thread 3 has name 'threadname_3'" "find thread name 3" gdb_test "thread find threadname_2" \ "Thread 2 has name 'threadname_2'" "find thread name 2" gdb_test "thread find threadname_1" \ "Thread 1 has name 'threadname_1'" "find thread name 1" # # Test 'thread find' with thread ids, if any. # if { [info exists thread6] } then { gdb_test "thread find $thread6" \ "Thread 6 has .*$thread6.*" "find thread id 6" gdb_test "thread find $thread5" \ "Thread 5 has .*$thread5.*" "find thread id 5" gdb_test "thread find $thread4" \ "Thread 4 has .*$thread4.*" "find thread id 4" gdb_test "thread find $thread3" \ "Thread 3 has .*$thread3.*" "find thread id 3" gdb_test "thread find $thread2" \ "Thread 2 has .*$thread2.*" "find thread id 2" gdb_test "thread find $thread1" \ "Thread 1 has .*$thread1.*" "find thread id 1" } # # Test 'thread find' with process ids, if any. # if { [info exists process6] } then { gdb_test "thread find $process6" \ "Thread 6 has .*$process6.*" "find process id 6" gdb_test "thread find $process5" \ "Thread 5 has .*$process5.*" "find process id 5" gdb_test "thread find $process4" \ "Thread 4 has .*$process4.*" "find process id 4" gdb_test "thread find $process3" \ "Thread 3 has .*$process3.*" "find process id 3" gdb_test "thread find $process2" \ "Thread 2 has .*$process2.*" "find process id 2" gdb_test "thread find $process1" \ "Thread 1 has .*$process1.*" "find process id 1" } # # Test 'thread find' with lwp ids, if any. # if { [info exists lwp6] } then { gdb_test "thread find $lwp6" \ "Thread 6 has .*$lwp6.*" "find lwp id 6" gdb_test "thread find $lwp5" \ "Thread 5 has .*$lwp5.*" "find lwp id 5" gdb_test "thread find $lwp4" \ "Thread 4 has .*$lwp4.*" "find lwp id 4" gdb_test "thread find $lwp3" \ "Thread 3 has .*$lwp3.*" "find lwp id 3" gdb_test "thread find $lwp2" \ "Thread 2 has .*$lwp2.*" "find lwp id 2" gdb_test "thread find $lwp1" \ "Thread 1 has .*$lwp1.*" "find lwp id 1" } # Test no match. gdb_test "thread find foobarbaz" "No threads match .*" "no thread" # # Test regular expression # set see1 0 set see2 0 set see3 0 set see4 0 set see5 0 set see6 0 gdb_test_multiple "thread find threadname_\[345\]" "test regular exp" { -re "Thread 6 has name \[^\r\n\]*" { set see6 1 exp_continue } -re "Thread 5 has name \[^\r\n\]*" { set see5 1 exp_continue } -re "Thread 4 has name \[^\r\n\]*" { set see4 1 exp_continue } -re "Thread 3 has name \[^\r\n\]*" { set see3 1 exp_continue } -re "Thread 2 has name \[^\r\n\]*" { set see2 1 exp_continue } -re "Thread 1 has name \[^\r\n\]*" { set see1 1 exp_continue } -re ".*$gdb_prompt $" { if { $see3 && $see4 && $see5 && !$see1 && !$see2 && !$see6 } then { pass "test regular exp" } else { fail "test regular exp" } } } # # Test info threads on a subset of threads # set see1 0 set see2 0 set see3 0 set see4 0 set see5 0 set see6 0 gdb_test_multiple "info threads 2 4 6" "info threads 2 4 6" { -re ". 6 .*\"threadname_6\" \[\r\n\]*" { set see6 1 exp_continue } -re ". 5 .*\"threadname_5\" \[\r\n\]*" { set see5 1 exp_continue } -re ". 4 .*\"threadname_4\" \[\r\n\]*" { set see4 1 exp_continue } -re ". 3 .*\"threadname_3\" \[\r\n\]*" { set see3 1 exp_continue } -re ". 2 .*\"threadname_2\" \[\r\n\]*" { set see2 1 exp_continue } -re ". 1 .*\"threadname_1\" \[\r\n\]*" { set see1 1 exp_continue } -re ".*$gdb_prompt $" { if { $see2 && $see4 && $see6 && !$see1 && !$see3 && !$see5 } then { pass "info threads 2 4 6" } else { fail "info threads 2 4 6" } } } # # Test info threads on a range # set see1 0 set see2 0 set see3 0 set see4 0 set see5 0 set see6 0 gdb_test_multiple "info threads 3-5" "info threads 3-5" { -re ". 6 .*\"threadname_6\" \[\r\n\]*" { set see6 1 exp_continue } -re ". 5 .*\"threadname_5\" \[\r\n\]*" { set see5 1 exp_continue } -re ". 4 .*\"threadname_4\" \[\r\n\]*" { set see4 1 exp_continue } -re ". 3 .*\"threadname_3\" \[\r\n\]*" { set see3 1 exp_continue } -re ". 2 .*\"threadname_2\" \[\r\n\]*" { set see2 1 exp_continue } -re ". 1 .*\"threadname_1\" \[\r\n\]*" { set see1 1 exp_continue } -re ".*$gdb_prompt $" { if { $see3 && $see4 && $see5 && !$see1 && !$see2 && !$see6 } then { pass "info threads 3-5" } else { fail "info threads 3-5" } } } # Test inverted range gdb_test "info threads 5-3" "inverted range" "test inverted range" # Test degenerate range set see1 0 set see2 0 set see3 0 set see4 0 set see5 0 set see6 0 gdb_test_multiple "info threads 3-3" "info threads 3-3" { -re ". 6 .*\"threadname_6\" \[\r\n\]*" { set see6 1 exp_continue } -re ". 5 .*\"threadname_5\" \[\r\n\]*" { set see5 1 exp_continue } -re ". 4 .*\"threadname_4\" \[\r\n\]*" { set see4 1 exp_continue } -re ". 3 .*\"threadname_3\" \[\r\n\]*" { set see3 1 exp_continue } -re ". 2 .*\"threadname_2\" \[\r\n\]*" { set see2 1 exp_continue } -re ". 1 .*\"threadname_1\" \[\r\n\]*" { set see1 1 exp_continue } -re ".*$gdb_prompt $" { if { $see3 && !$see1 && !$see2 && !$see4 && !$see5 && !$see6 } then { pass "info threads 3-3" } else { fail "info threads 3-3" } } } ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-17 20:11 ` Michael Snyder @ 2011-02-17 21:22 ` Jan Kratochvil 0 siblings, 0 replies; 15+ messages in thread From: Jan Kratochvil @ 2011-02-17 21:22 UTC (permalink / raw) To: Michael Snyder; +Cc: Pedro Alves, gdb-patches, Tom Tromey [-- Attachment #1: Type: text/plain, Size: 689 bytes --] On Thu, 17 Feb 2011 20:45:58 +0100, Michael Snyder wrote: > You're right, there is an extra .* in there. > Can you please try the attached? It still FAILs. Shouldn't there be \[^\r\n\]* instead of \[\r\n\]*? BTW i7-920 (4 cores + hyperthreading), Fedora 15 x86_64. Attaching also my attempt first today but I haven't finished it to a state to make it running as I have too much stuff to do here now. BTW I do not like any .* there in such unanchored regexes, it is still too fragile while it may not cause problems right now. The part ". 3 .*\"... can match almost anything, some random digit between 1 to 6 can possibly appear somewhere and it can eat some text again. Thanks, Jan [-- Attachment #2: gdb.log --] [-- Type: text/plain, Size: 12691 bytes --] Test Run By jkratoch on Thu Feb 17 21:49:51 2011 Native configuration is x86_64-unknown-linux-gnu === gdb tests === Schedule of variations: unix Running target unix Using /usr/share/dejagnu/baseboards/unix.exp as board description file for target. Using /usr/share/dejagnu/config/unix.exp as generic interface file for target. Using ./config/unix.exp as tool-and-target-specific interface file. Running ./gdb.threads/thread-find.exp ... Executing on host: gcc ./gdb.threads/linux-dp.c -g -lpthreads -lm -o /home/jkratoch/redhat/gdb-clean/gdb/testsuite/gdb.threads/linux-dp (timeout = 300) spawn -ignore SIGHUP gcc ./gdb.threads/linux-dp.c -g -lpthreads -lm -o /home/jkratoch/redhat/gdb-clean/gdb/testsuite/gdb.threads/linux-dp /usr/bin/ld: cannot find -lpthreads collect2: ld returned 1 exit status compiler exited with status 1 output is: /usr/bin/ld: cannot find -lpthreads collect2: ld returned 1 exit status Executing on host: gcc ./gdb.threads/linux-dp.c -g -lpthread -lm -o /home/jkratoch/redhat/gdb-clean/gdb/testsuite/gdb.threads/linux-dp (timeout = 300) spawn -ignore SIGHUP gcc ./gdb.threads/linux-dp.c -g -lpthread -lm -o /home/jkratoch/redhat/gdb-clean/gdb/testsuite/gdb.threads/linux-dp PASS: gdb.threads/thread-find.exp: successfully compiled posix threads test case spawn /home/jkratoch/redhat/gdb-clean/gdb/testsuite/../../gdb/gdb -nw -nx -data-directory /home/jkratoch/redhat/gdb-clean/gdb/testsuite/../data-directory GNU gdb (GDB) 7.2.50.20110217-cvs Copyright (C) 2011 Free Software Foundation, Inc. License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html> This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law. Type "show copying" and "show warranty" for details. This GDB was configured as "x86_64-unknown-linux-gnu". For bug reporting instructions, please see: <http://www.gnu.org/software/gdb/bugs/>. (gdb) set height 0 (gdb) set width 0 (gdb) dir Reinitialize source path to empty? (y or n) y Source directories searched: $cdir:$cwd (gdb) dir ./gdb.threads Source directories searched: /home/jkratoch/redhat/gdb-clean/gdb/testsuite/./gdb.threads:$cdir:$cwd (gdb) kill The program is not being run. (gdb) file /home/jkratoch/redhat/gdb-clean/gdb/testsuite/gdb.threads/linux-dp Reading symbols from /home/jkratoch/redhat/gdb-clean/gdb/testsuite/gdb.threads/linux-dp...done. (gdb) set print sevenbit-strings (gdb) PASS: gdb.threads/thread-find.exp: set print sevenbit-strings delete breakpoints (gdb) info breakpoints No breakpoints or watchpoints. (gdb) break main Breakpoint 1 at 0x400eb8: file ./gdb.threads/linux-dp.c, line 162. (gdb) run Starting program: /home/jkratoch/redhat/gdb-clean/gdb/testsuite/gdb.threads/linux-dp [Thread debugging using libthread_db enabled] Breakpoint 1, main (argc=1, argv=0x7fffffffe058) at ./gdb.threads/linux-dp.c:162 162 num_philosophers = 5; (gdb) break 198 Breakpoint 2 at 0x401017: file ./gdb.threads/linux-dp.c, line 198. (gdb) continue Continuing. [New Thread 0x7ffff759e700 (LWP 21313)] _ 0 _ ! 0 _ [New Thread 0x7ffff6d9d700 (LWP 21314)] _ 1 _ ! 1 _ [New Thread 0x7ffff659c700 (LWP 21315)] _ 2 _ ! 2 _ [New Thread 0x7ffff5d9b700 (LWP 21316)] _ 3 _ ! 3 _ [New Thread 0x7ffff559a700 (LWP 21317)] _ 4 _ Breakpoint 2, main (argc=1, argv=0x7fffffffe058) at ./gdb.threads/linux-dp.c:199 199 sleep (1000000); (gdb) PASS: gdb.threads/thread-find.exp: continue to breakpoint: main thread's sleep thread apply 1 thread name threadname_1 Thread 1 (Thread 0x7ffff7fe7720 (LWP 21310)): (gdb) PASS: gdb.threads/thread-find.exp: name thread 1 thread apply 2 thread name threadname_2 Thread 2 (Thread 0x7ffff759e700 (LWP 21313)): (gdb) PASS: gdb.threads/thread-find.exp: name thread 2 thread apply 3 thread name threadname_3 Thread 3 (Thread 0x7ffff6d9d700 (LWP 21314)): (gdb) PASS: gdb.threads/thread-find.exp: name thread 3 thread apply 4 thread name threadname_4 Thread 4 (Thread 0x7ffff659c700 (LWP 21315)): (gdb) PASS: gdb.threads/thread-find.exp: name thread 4 thread apply 5 thread name threadname_5 Thread 5 (Thread 0x7ffff5d9b700 (LWP 21316)): (gdb) PASS: gdb.threads/thread-find.exp: name thread 5 thread apply 6 thread name threadname_6 Thread 6 (Thread 0x7ffff559a700 (LWP 21317)): (gdb) PASS: gdb.threads/thread-find.exp: name thread 6 info threads Id Target Id Frame 6 Thread 0x7ffff559a700 (LWP 21317) "threadname_6" __lll_lock_wait () at ../nptl/sysdeps/unix/sysv/linux/x86_64/lowlevellock.S:136 5 Thread 0x7ffff5d9b700 (LWP 21316) "threadname_5" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 4 Thread 0x7ffff659c700 (LWP 21315) "threadname_4" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 3 Thread 0x7ffff6d9d700 (LWP 21314) "threadname_3" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 2 Thread 0x7ffff759e700 (LWP 21313) "threadname_2" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 * 1 Thread 0x7ffff7fe7720 (LWP 21310) "threadname_1" main (argc=1, argv=0x7fffffffe058) at ./gdb.threads/linux-dp.c:199 (gdb) PASS: gdb.threads/thread-find.exp: collect thread id echo 0x7ffff559a700\n 0x7ffff559a700 (gdb) PASS: gdb.threads/thread-find.exp: got thread ids info threads Id Target Id Frame 6 Thread 0x7ffff559a700 (LWP 21317) "threadname_6" __lll_lock_wait () at ../nptl/sysdeps/unix/sysv/linux/x86_64/lowlevellock.S:136 5 Thread 0x7ffff5d9b700 (LWP 21316) "threadname_5" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 4 Thread 0x7ffff659c700 (LWP 21315) "threadname_4" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 3 Thread 0x7ffff6d9d700 (LWP 21314) "threadname_3" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 2 Thread 0x7ffff759e700 (LWP 21313) "threadname_2" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 * 1 Thread 0x7ffff7fe7720 (LWP 21310) "threadname_1" main (argc=1, argv=0x7fffffffe058) at ./gdb.threads/linux-dp.c:199 (gdb) PASS: gdb.threads/thread-find.exp: collect process id info threads Id Target Id Frame 6 Thread 0x7ffff559a700 (LWP 21317) "threadname_6" __lll_lock_wait () at ../nptl/sysdeps/unix/sysv/linux/x86_64/lowlevellock.S:136 5 Thread 0x7ffff5d9b700 (LWP 21316) "threadname_5" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 4 Thread 0x7ffff659c700 (LWP 21315) "threadname_4" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 3 Thread 0x7ffff6d9d700 (LWP 21314) "threadname_3" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 2 Thread 0x7ffff759e700 (LWP 21313) "threadname_2" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 * 1 Thread 0x7ffff7fe7720 (LWP 21310) "threadname_1" main (argc=1, argv=0x7fffffffe058) at ./gdb.threads/linux-dp.c:199 (gdb) PASS: gdb.threads/thread-find.exp: collect lwp id echo 21317\n 21317 (gdb) PASS: gdb.threads/thread-find.exp: got lwp ids thread find threadname_6 Thread 6 has name 'threadname_6' (gdb) PASS: gdb.threads/thread-find.exp: find thread name 6 thread find threadname_5 Thread 5 has name 'threadname_5' (gdb) PASS: gdb.threads/thread-find.exp: find thread name 5 thread find threadname_4 Thread 4 has name 'threadname_4' (gdb) PASS: gdb.threads/thread-find.exp: find thread name 4 thread find threadname_3 Thread 3 has name 'threadname_3' (gdb) PASS: gdb.threads/thread-find.exp: find thread name 3 thread find threadname_2 Thread 2 has name 'threadname_2' (gdb) PASS: gdb.threads/thread-find.exp: find thread name 2 thread find threadname_1 Thread 1 has name 'threadname_1' (gdb) PASS: gdb.threads/thread-find.exp: find thread name 1 thread find 0x7ffff559a700 Thread 6 has target id 'Thread 0x7ffff559a700 (LWP 21317)' (gdb) PASS: gdb.threads/thread-find.exp: find thread id 6 thread find 0x7ffff5d9b700 Thread 5 has target id 'Thread 0x7ffff5d9b700 (LWP 21316)' (gdb) PASS: gdb.threads/thread-find.exp: find thread id 5 thread find 0x7ffff659c700 Thread 4 has target id 'Thread 0x7ffff659c700 (LWP 21315)' (gdb) PASS: gdb.threads/thread-find.exp: find thread id 4 thread find 0x7ffff6d9d700 Thread 3 has target id 'Thread 0x7ffff6d9d700 (LWP 21314)' (gdb) PASS: gdb.threads/thread-find.exp: find thread id 3 thread find 0x7ffff759e700 Thread 2 has target id 'Thread 0x7ffff759e700 (LWP 21313)' (gdb) PASS: gdb.threads/thread-find.exp: find thread id 2 thread find 0x7ffff7fe7720 Thread 1 has target id 'Thread 0x7ffff7fe7720 (LWP 21310)' (gdb) PASS: gdb.threads/thread-find.exp: find thread id 1 thread find 21317 Thread 6 has target id 'Thread 0x7ffff559a700 (LWP 21317)' (gdb) PASS: gdb.threads/thread-find.exp: find lwp id 6 thread find 21316 Thread 5 has target id 'Thread 0x7ffff5d9b700 (LWP 21316)' (gdb) PASS: gdb.threads/thread-find.exp: find lwp id 5 thread find 21315 Thread 4 has target id 'Thread 0x7ffff659c700 (LWP 21315)' (gdb) PASS: gdb.threads/thread-find.exp: find lwp id 4 thread find 21314 Thread 3 has target id 'Thread 0x7ffff6d9d700 (LWP 21314)' (gdb) PASS: gdb.threads/thread-find.exp: find lwp id 3 thread find 21313 Thread 2 has target id 'Thread 0x7ffff759e700 (LWP 21313)' (gdb) PASS: gdb.threads/thread-find.exp: find lwp id 2 thread find 21310 Thread 1 has target id 'Thread 0x7ffff7fe7720 (LWP 21310)' (gdb) PASS: gdb.threads/thread-find.exp: find lwp id 1 thread find foobarbaz No threads match 'foobarbaz' (gdb) PASS: gdb.threads/thread-find.exp: no thread thread find threadname_[345] Thread 5 has name 'threadname_5' Thread 4 has name 'threadname_4' Thread 3 has name 'threadname_3' (gdb) PASS: gdb.threads/thread-find.exp: test regular exp info threads 2 4 6 Id Target Id Frame 2 Thread 0x7ffff759e700 (LWP 21313) "threadname_2" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 Id Target Id Frame 4 Thread 0x7ffff659c700 (LWP 21315) "threadname_4" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 Id Target Id Frame 6 Thread 0x7ffff559a700 (LWP 21317) "threadname_6" __lll_lock_wait () at ../nptl/sysdeps/unix/sysv/linux/x86_64/lowlevellock.S:136 (gdb) PASS: gdb.threads/thread-find.exp: info threads 2 4 6 info threads 3-5 Id Target Id Frame 3 Thread 0x7ffff6d9d700 (LWP 21314) "threadname_3" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 Id Target Id Frame 4 Thread 0x7ffff659c700 (LWP 21315) "threadname_4" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 Id Target Id Frame 5 Thread 0x7ffff5d9b700 (LWP 21316) "threadname_5" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 (gdb) FAIL: gdb.threads/thread-find.exp: info threads 3-5 info threads 5-3 Id Target Id Frame 5 Thread 0x7ffff5d9b700 (LWP 21316) "threadname_5" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 inverted range (gdb) PASS: gdb.threads/thread-find.exp: test inverted range info threads 3-3 Id Target Id Frame 3 Thread 0x7ffff6d9d700 (LWP 21314) "threadname_3" 0x00007ffff7678213 in select () at ../sysdeps/unix/syscall-template.S:82 (gdb) PASS: gdb.threads/thread-find.exp: info threads 3-3 testcase ./gdb.threads/thread-find.exp completed in 1 seconds === gdb Summary === # of expected passes 37 # of unexpected failures 1 Executing on host: /home/jkratoch/redhat/gdb-clean/gdb/testsuite/../../gdb/gdb -nw -nx -data-directory /home/jkratoch/redhat/gdb-clean/gdb/testsuite/../data-directory --version (timeout = 300) spawn -ignore SIGHUP /home/jkratoch/redhat/gdb-clean/gdb/testsuite/../../gdb/gdb -nw -nx -data-directory /home/jkratoch/redhat/gdb-clean/gdb/testsuite/../data-directory --version GNU gdb (GDB) 7.2.50.20110217-cvs Copyright (C) 2011 Free Software Foundation, Inc. License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html> This is free software: you are free to change and redistribute it. There is NO WARRANTY, to the extent permitted by law. Type "show copying" and "show warranty" for details. This GDB was configured as "x86_64-unknown-linux-gnu". For bug reporting instructions, please see: <http://www.gnu.org/software/gdb/bugs/>. /home/jkratoch/redhat/gdb-clean/gdb/testsuite/../../gdb/gdb version 7.2.50.20110217-cvs -nw -nx -data-directory /home/jkratoch/redhat/gdb-clean/gdb/testsuite/../data-directory runtest completed at Thu Feb 17 21:49:52 2011 [-- Attachment #3: thread-find-jan.patch --] [-- Type: text/plain, Size: 3850 bytes --] diff --git a/gdb/testsuite/gdb.threads/thread-find.exp b/gdb/testsuite/gdb.threads/thread-find.exp index dd18a95..fb73963 100644 --- a/gdb/testsuite/gdb.threads/thread-find.exp +++ b/gdb/testsuite/gdb.threads/thread-find.exp @@ -65,31 +65,11 @@ gdb_test "thread apply 6 thread name threadname_6" \ # Collect thread ids, if any. gdb_test_multiple "info threads" "collect thread id" { - -re ". 6 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_6\" \[^\r\n\]*" { - set thread6 $expect_out(1,string) + -re "\r\n. (\d) +\[Tt\]hread (\[0-9a-fA-Fx\]+) \[^\r\n\]* \"threadname_\1\" \[^\r\n\]*" { + eval "set thread$expect_out(1,string) \\$expect_out(2,string)" exp_continue } - -re ". 5 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_5\" \[^\r\n\]*" { - set thread5 $expect_out(1,string) - exp_continue - } - -re ". 4 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_4\" \[^\r\n\]*" { - set thread4 $expect_out(1,string) - exp_continue - } - -re ". 3 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_3\" \[^\r\n\]*" { - set thread3 $expect_out(1,string) - exp_continue - } - -re ". 2 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_2\" \[^\r\n\]*" { - set thread2 $expect_out(1,string) - exp_continue - } - -re ". 1 .*\[Tt\]hread (\[0-9a-fA-Fx\]+).* \"threadname_1\" \[^\r\n\]*" { - set thread1 $expect_out(1,string) - exp_continue - } - -re ".*$gdb_prompt $" { + -re "\r\n$gdb_prompt $" { pass "collect thread id" } } @@ -100,31 +80,11 @@ if { [info exists thread6] } then { # Collect process ids, if any. gdb_test_multiple "info threads" "collect thread id" { - -re ". 6 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_6\" \[^\r\n\]*" { - set process6 $expect_out(1,string) - exp_continue - } - -re ". 5 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_5\" \[^\r\n\]*" { - set process5 $expect_out(1,string) - exp_continue - } - -re ". 4 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_4\" \[^\r\n\]*" { - set process4 $expect_out(1,string) - exp_continue - } - -re ". 3 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_3\" \[^\r\n\]*" { - set process3 $expect_out(1,string) + -re "\r\n. (\d) +\[Pp\]rocess (\[0-9a-fA-Fx\]+) \[^\r\n\]* \"threadname_\1\" \[^\r\n\]*" { + eval "set process$expect_out(1,string) \\$expect_out(2,string)" exp_continue } - -re ". 2 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_2\" \[^\r\n\]*" { - set process2 $expect_out(1,string) - exp_continue - } - -re ". 1 .*\[Pp\]rocess (\[0-9a-fA-Fx\]+).* \"threadname_1\" \[^\r\n\]*" { - set process1 $expect_out(1,string) - exp_continue - } - -re ".*$gdb_prompt $" { + -re "\r\n$gdb_prompt $" { pass "collect process id" } } @@ -135,31 +95,11 @@ if { [info exists process6] } then { # Collect lwp ids, if any. gdb_test_multiple "info threads" "collect thread id" { - -re ". 6 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_6\" \[^\r\n\]*" { - set lwp6 $expect_out(1,string) - exp_continue - } - -re ". 5 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_5\" \[^\r\n\]*" { - set lwp5 $expect_out(1,string) - exp_continue - } - -re ". 4 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_4\" \[^\r\n\]*" { - set lwp4 $expect_out(1,string) - exp_continue - } - -re ". 3 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_3\" \[^\r\n\]*" { - set lwp3 $expect_out(1,string) - exp_continue - } - -re ". 2 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_2\" \[^\r\n\]*" { - set lwp2 $expect_out(1,string) - exp_continue - } - -re ". 1 .*LWP (\[0-9a-fA-Fx\]+).* \"threadname_1\" \[^\r\n\]*" { - set lwp1 $expect_out(1,string) + -re "\r\n. (\d) +LWP (\[0-9a-fA-Fx\]+) \[^\r\n\]* \"threadname_\1\" \[^\r\n\]*" { + eval "set lwp$expect_out(1,string) \\$expect_out(2,string)" exp_continue } - -re ".*$gdb_prompt $" { + -re "\r\n$gdb_prompt $" { pass "collect lwp id" } } ^ permalink raw reply [flat|nested] 15+ messages in thread
* Re: [RFC] info threads takes an argument 2011-02-15 21:44 ` Michael Snyder 2011-02-16 11:58 ` Pedro Alves @ 2011-02-21 18:45 ` Tom Tromey 1 sibling, 0 replies; 15+ messages in thread From: Tom Tromey @ 2011-02-21 18:45 UTC (permalink / raw) To: Michael Snyder; +Cc: gdb-patches >>>>> "Michael" == Michael Snyder <msnyder@vmware.com> writes: Tom> Matching both the ID and the target PID means that using numbers here Tom> will be over-eager. Why match the ID? "info thread ID" seems good Tom> enough. Michael> "info thread" will only match the gdb thread id (small counting Michael> integer). "thread find" will match the PID. Yes, sorry -- I misunderstood the text and did not read the corresponding part of the code. Tom ^ permalink raw reply [flat|nested] 15+ messages in thread
end of thread, other threads:[~2011-02-21 18:43 UTC | newest]
Thread overview: 15+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-02-11 1:52 [RFC] info threads takes an argument Michael Snyder
2011-02-11 6:09 ` Joel Brobecker
2011-02-11 19:23 ` Michael Snyder
2011-02-11 21:14 ` Tom Tromey
[not found] ` <4D55B1ED.5020808@vmware.com>
[not found] ` <m3k4h2e6xu.fsf@fleche.redhat.com>
2011-02-14 20:03 ` Michael Snyder
2011-02-14 20:40 ` Eli Zaretskii
2011-02-15 19:58 ` Tom Tromey
2011-02-15 21:44 ` Michael Snyder
2011-02-16 11:58 ` Pedro Alves
2011-02-16 18:47 ` Michael Snyder
2011-02-17 16:57 ` Jan Kratochvil
2011-02-17 19:12 ` Michael Snyder
2011-02-17 20:11 ` Michael Snyder
2011-02-17 21:22 ` Jan Kratochvil
2011-02-21 18:45 ` Tom Tromey
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox