From 8dd4f202ecf146ae7746e10277ddebedc43f42d4 Mon Sep 17 00:00:00 2001 From: Vladimir Prus Date: Mon, 17 Nov 2008 16:39:51 +0000 Subject: [PATCH] Implement continue/interrupt of thread groups. * mi/mi-main.c (proceed_thread_callback): New. (mi_cmd_exec_continue): If --thread-group is specified, resume all threads in that group. (interrupt_thread_callback): New. (mi_cmd_exec_interrupt): If --thread-group is specified, interrupt all threads in that group. --- gdb/ChangeLog | 11 ++++++++ gdb/mi/mi-main.c | 66 +++++++++++++++++++++++++++++++++++++++++++++--- 2 files changed, 74 insertions(+), 3 deletions(-) diff --git a/gdb/ChangeLog b/gdb/ChangeLog index 64e8eeeda5..03b066089e 100644 --- a/gdb/ChangeLog +++ b/gdb/ChangeLog @@ -1,3 +1,14 @@ +2008-11-17 Vladimir Prus + + Implement continue/interrupt of thread groups. + + * mi/mi-main.c (proceed_thread_callback): New. + (mi_cmd_exec_continue): If --thread-group is specified, resume all + threads in that group. + (interrupt_thread_callback): New. + (mi_cmd_exec_interrupt): If --thread-group is specified, interrupt + all threads in that group. + 2008-11-17 Vladimir Prus Implement '-target-detach pid'. diff --git a/gdb/mi/mi-main.c b/gdb/mi/mi-main.c index ad4ed0c268..6e5511fee9 100644 --- a/gdb/mi/mi-main.c +++ b/gdb/mi/mi-main.c @@ -162,6 +162,23 @@ mi_cmd_exec_return (char *command, char **argv, int argc) print_stack_frame (get_selected_frame (NULL), 1, LOC_AND_ADDRESS); } +static int +proceed_thread_callback (struct thread_info *thread, void *arg) +{ + int pid = *(int *)arg; + + if (!is_stopped (thread->ptid)) + return 0; + + if (PIDGET (thread->ptid) != pid) + return 0; + + switch_to_thread (thread->ptid); + clear_proceed_status (); + proceed ((CORE_ADDR) -1, TARGET_SIGNAL_DEFAULT, 0); + return 0; +} + void mi_cmd_exec_continue (char *command, char **argv, int argc) { @@ -169,8 +186,37 @@ mi_cmd_exec_continue (char *command, char **argv, int argc) continue_1 (0); else if (argc == 1 && strcmp (argv[0], "--all") == 0) continue_1 (1); + else if (argc == 2 && strcmp (argv[0], "--thread-group") == 0) + { + struct cleanup *old_chain; + int pid; + if (argv[1] == NULL || argv[1] == '\0') + error ("Thread group id not specified"); + pid = atoi (argv[1] + 1); + if (!in_inferior_list (pid)) + error ("Invalid thread group id '%s'", argv[1]); + + old_chain = make_cleanup_restore_current_thread (); + iterate_over_threads (proceed_thread_callback, &pid); + do_cleanups (old_chain); + } else - error ("Usage: -exec-continue [--all]"); + error ("Usage: -exec-continue [--all|--thread-group id]"); +} + +static int +interrupt_thread_callback (struct thread_info *thread, void *arg) +{ + int pid = *(int *)arg; + + if (!is_running (thread->ptid)) + return 0; + + if (PIDGET (thread->ptid) != pid) + return 0; + + target_stop (thread->ptid); + return 0; } /* Interrupt the execution of the target. Note how we must play around @@ -192,11 +238,25 @@ mi_cmd_exec_interrupt (char *command, char **argv, int argc) { if (!any_running ()) error ("Inferior not running."); - + interrupt_target_1 (1); } + else if (argc == 2 && strcmp (argv[0], "--thread-group") == 0) + { + struct cleanup *old_chain; + int pid; + if (argv[1] == NULL || argv[1] == '\0') + error ("Thread group id not specified"); + pid = atoi (argv[1] + 1); + if (!in_inferior_list (pid)) + error ("Invalid thread group id '%s'", argv[1]); + + old_chain = make_cleanup_restore_current_thread (); + iterate_over_threads (interrupt_thread_callback, &pid); + do_cleanups (old_chain); + } else - error ("Usage: -exec-interrupt [--all]"); + error ("Usage: -exec-interrupt [--all|--thread-group id]"); } static int