diff options
author | Pedro Alves <palves@redhat.com> | 2017-09-27 23:37:48 +0100 |
---|---|---|
committer | Pedro Alves <palves@redhat.com> | 2017-09-27 23:37:48 +0100 |
commit | 2a015c47e1a4a9b117d54f357dc3540326811748 (patch) | |
tree | aa62d83c6770702191ff1b038f0183824bcec639 | |
parent | bea0a5aeece991b2f4f20a746ce655283607d9a6 (diff) | |
download | gdb-users/palves/catch_exceptions.zip gdb-users/palves/catch_exceptions.tar.gz gdb-users/palves/catch_exceptions.tar.bz2 |
zap catch_exceptionsusers/palves/catch_exceptions
-rw-r--r-- | gdb/breakpoint.c | 35 | ||||
-rw-r--r-- | gdb/breakpoint.h | 3 | ||||
-rw-r--r-- | gdb/exceptions.c | 81 | ||||
-rw-r--r-- | gdb/gdb.h | 58 | ||||
-rw-r--r-- | gdb/gdbthread.h | 2 | ||||
-rw-r--r-- | gdb/mi/mi-cmd-break.c | 13 | ||||
-rw-r--r-- | gdb/mi/mi-cmd-catch.c | 1 | ||||
-rw-r--r-- | gdb/mi/mi-interp.c | 72 | ||||
-rw-r--r-- | gdb/mi/mi-main.c | 49 | ||||
-rw-r--r-- | gdb/remote-fileio.c | 37 | ||||
-rw-r--r-- | gdb/symfile-mem.c | 61 | ||||
-rw-r--r-- | gdb/thread.c | 88 |
12 files changed, 115 insertions, 385 deletions
diff --git a/gdb/breakpoint.c b/gdb/breakpoint.c index 02e028c..a7915fb 100644 --- a/gdb/breakpoint.c +++ b/gdb/breakpoint.c @@ -44,7 +44,6 @@ #include "source.h" #include "linespec.h" #include "completer.h" -#include "gdb.h" #include "ui-out.h" #include "cli/cli-script.h" #include "block.h" @@ -6596,39 +6595,11 @@ breakpoint_address_bits (struct breakpoint *b) return print_address_bits; } -static int -do_captured_breakpoint_query (int bnum) +void +print_breakpoint (breakpoint *b) { - struct breakpoint *b; struct bp_location *dummy_loc = NULL; - - ALL_BREAKPOINTS (b) - { - if (bnum == b->number) - { - print_one_breakpoint (b, &dummy_loc, 0); - return GDB_RC_OK; - } - } - return GDB_RC_NONE; -} - -enum gdb_rc -gdb_breakpoint_query (struct ui_out *uiout, int bnum, - char **error_message) -{ - /* For the moment we don't trust print_one_breakpoint() to not throw - an error. */ - if (catch_exceptions_with_msg - (uiout, - [&] (struct ui_out *) - { - return do_captured_breakpoint_query (bnum); - }, - error_message, RETURN_MASK_ALL) < 0) - return GDB_RC_FAIL; - else - return GDB_RC_OK; + print_one_breakpoint (b, &dummy_loc, 0); } /* Return true if this breakpoint was set by the user, false if it is diff --git a/gdb/breakpoint.h b/gdb/breakpoint.h index ff49cd2..143eae3 100644 --- a/gdb/breakpoint.h +++ b/gdb/breakpoint.h @@ -1644,4 +1644,7 @@ extern const char *ep_parse_optional_if_clause (const char **arg); UIOUT iff debugging multiple threads. */ extern void maybe_print_thread_hit_breakpoint (struct ui_out *uiout); +/* Print the specified breakpoint. */ +extern void print_breakpoint (breakpoint *bp); + #endif /* !defined (BREAKPOINT_H) */ diff --git a/gdb/exceptions.c b/gdb/exceptions.c index 97a56e6..0fc2de5 100644 --- a/gdb/exceptions.c +++ b/gdb/exceptions.c @@ -134,87 +134,6 @@ exception_fprintf (struct ui_file *file, struct gdb_exception e, } } -/* Call FUNC(UIOUT, FUNC_ARGS) but wrapped within an exception - handler. If an exception (enum return_reason) is thrown using - throw_exception() than all cleanups installed since - catch_exceptions() was entered are invoked, the (-ve) exception - value is then returned by catch_exceptions. If FUNC() returns - normally (with a positive or zero return value) then that value is - returned by catch_exceptions(). It is an internal_error() for - FUNC() to return a negative value. - - See exceptions.h for further usage details. */ - -/* MAYBE: cagney/1999-11-05: catch_errors() in conjunction with - error() et al. could maintain a set of flags that indicate the - current state of each of the longjmp buffers. This would give the - longjmp code the chance to detect a longjmp botch (before it gets - to longjmperror()). Prior to 1999-11-05 this wasn't possible as - code also randomly used a SET_TOP_LEVEL macro that directly - initialized the longjmp buffers. */ - -int -catch_exceptions (struct ui_out *uiout, - gdb::function_view<catch_exceptions_ftype> func, - return_mask mask) -{ - return catch_exceptions_with_msg (uiout, func, NULL, mask); -} - -int -catch_exceptions_with_msg (struct ui_out *func_uiout, - gdb::function_view<catch_exceptions_ftype> func, - char **gdberrmsg, - return_mask mask) -{ - struct gdb_exception exception = exception_none; - volatile int val = 0; - struct ui_out *saved_uiout; - - /* Save and override the global ``struct ui_out'' builder. */ - saved_uiout = current_uiout; - current_uiout = func_uiout; - - TRY - { - val = func (current_uiout); - } - CATCH (ex, RETURN_MASK_ALL) - { - exception = ex; - } - END_CATCH - - /* Restore the global builder. */ - current_uiout = saved_uiout; - - if (exception.reason < 0 && (mask & RETURN_MASK (exception.reason)) == 0) - { - /* The caller didn't request that the event be caught. - Rethrow. */ - throw_exception (exception); - } - - exception_print (gdb_stderr, exception); - gdb_assert (val >= 0); - gdb_assert (exception.reason <= 0); - if (exception.reason < 0) - { - /* If caller wants a copy of the low-level error message, make - one. This is used in the case of a silent error whereby the - caller may optionally want to issue the message. */ - if (gdberrmsg != NULL) - { - if (exception.message != NULL) - *gdberrmsg = xstrdup (exception.message); - else - *gdberrmsg = NULL; - } - return exception.reason; - } - return val; -} - /* See exceptions.h. */ int diff --git a/gdb/gdb.h b/gdb/gdb.h deleted file mode 100644 index ac1e683..0000000 --- a/gdb/gdb.h +++ /dev/null @@ -1,58 +0,0 @@ -/* Library interface into GDB. - Copyright (C) 1999-2017 Free Software Foundation, Inc. - - This file is part of GDB. - - 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/>. */ - -#ifndef GDB_H -#define GDB_H - -struct ui_out; - -/* Return-code (RC) from a gdb library call. (The abreviation RC is - taken from the sim/common directory.) */ - -enum gdb_rc { - /* The operation failed. The failure message can be fetched by - calling ``char *error_last_message(void)''. The value is - determined by the catch_errors() interface. The MSG parameter is - set to a freshly allocated copy of the error message. */ - /* NOTE: Since ``defs.h:catch_errors()'' does not return an error / - internal / quit indication it is not possible to return that - here. */ - GDB_RC_FAIL = 0, - /* No error occured but nothing happened. Due to the catch_errors() - interface, this must be non-zero. */ - GDB_RC_NONE = 1, - /* The operation was successful. Due to the catch_errors() - interface, this must be non-zero. */ - GDB_RC_OK = 2 -}; - - -/* Print the specified breakpoint on GDB_STDOUT. (Eventually this - function will ``print'' the object on ``output''). */ -enum gdb_rc gdb_breakpoint_query (struct ui_out *uiout, int bnum, - char **error_message); - -/* Switch thread and print notification. */ -enum gdb_rc gdb_thread_select (struct ui_out *uiout, char *tidstr, - char **error_message); - -/* Print a list of known thread ids. */ -enum gdb_rc gdb_list_thread_ids (struct ui_out *uiout, - char **error_message); - -#endif diff --git a/gdb/gdbthread.h b/gdb/gdbthread.h index d5101ab..9720993 100644 --- a/gdb/gdbthread.h +++ b/gdb/gdbthread.h @@ -679,6 +679,8 @@ extern int show_thread_that_caused_stop (void); extern void print_selected_thread_frame (struct ui_out *uiout, user_selected_what selection); +extern void thread_select (const char *tidstr, thread_info *thr); + extern struct thread_info *thread_list; #endif /* GDBTHREAD_H */ diff --git a/gdb/mi/mi-cmd-break.c b/gdb/mi/mi-cmd-break.c index 188e4e2..c313c03 100644 --- a/gdb/mi/mi-cmd-break.c +++ b/gdb/mi/mi-cmd-break.c @@ -24,7 +24,6 @@ #include "mi-out.h" #include "breakpoint.h" #include "mi-getopt.h" -#include "gdb.h" #include "observer.h" #include "mi-main.h" #include "mi-cmd-break.h" @@ -53,7 +52,17 @@ static void breakpoint_notify (struct breakpoint *b) { if (mi_can_breakpoint_notify) - gdb_breakpoint_query (current_uiout, b->number, NULL); + { + TRY + { + print_breakpoint (b); + } + CATCH (ex, RETURN_MASK_ALL) + { + exception_print (gdb_stdout, ex); + } + END_CATCH + } } enum bp_type diff --git a/gdb/mi/mi-cmd-catch.c b/gdb/mi/mi-cmd-catch.c index 0e1fb7e..9c103d2 100644 --- a/gdb/mi/mi-cmd-catch.c +++ b/gdb/mi/mi-cmd-catch.c @@ -21,7 +21,6 @@ #include "defs.h" #include "arch-utils.h" #include "breakpoint.h" -#include "gdb.h" #include "ada-lang.h" #include "mi-cmds.h" #include "mi-getopt.h" diff --git a/gdb/mi/mi-interp.c b/gdb/mi/mi-interp.c index 714bb4b..20b5a71 100644 --- a/gdb/mi/mi-interp.c +++ b/gdb/mi/mi-interp.c @@ -33,7 +33,6 @@ #include "observer.h" #include "gdbthread.h" #include "solist.h" -#include "gdb.h" #include "objfiles.h" #include "tracepoint.h" #include "cli-out.h" @@ -828,6 +827,36 @@ mi_tsv_modified (const struct trace_state_variable *tsv) } } +static void +mi_print_breakpoint (struct mi_interp *mi, breakpoint *bp) +{ + ui_out *mi_uiout = interp_ui_out (mi); + + /* We want the output from print_breakpoint to go to + mi->event_channel. One approach would be to just call + print_breakpoint, and then use mi_out_put to send the current + content of mi_uiout into mi->event_channel. However, that will + break if anything is output to mi_uiout prior to calling the + breakpoint_created notifications. So, we use + ui_out_redirect. */ + mi_uiout->redirect (mi->event_channel); + + TRY + { + scoped_restore restore_uiout + = make_scoped_restore (¤t_uiout, mi_uiout); + + print_breakpoint (bp); + } + CATCH (ex, RETURN_MASK_ALL) + { + exception_print (gdb_stderr, ex); + } + END_CATCH + + mi_uiout->redirect (NULL); +} + /* Emit notification about a created breakpoint. */ static void @@ -842,36 +871,16 @@ mi_breakpoint_created (struct breakpoint *b) SWITCH_THRU_ALL_UIS () { struct mi_interp *mi = as_mi_interp (top_level_interpreter ()); - struct ui_out *mi_uiout; if (mi == NULL) continue; - mi_uiout = interp_ui_out (top_level_interpreter ()); - target_terminal::scoped_restore_terminal_state term_state; target_terminal::ours_for_output (); fprintf_unfiltered (mi->event_channel, "breakpoint-created"); - /* We want the output from gdb_breakpoint_query to go to - mi->event_channel. One approach would be to just call - gdb_breakpoint_query, and then use mi_out_put to send the current - content of mi_uiout into mi->event_channel. However, that will - break if anything is output to mi_uiout prior to calling the - breakpoint_created notifications. So, we use - ui_out_redirect. */ - mi_uiout->redirect (mi->event_channel); - TRY - { - gdb_breakpoint_query (mi_uiout, b->number, NULL); - } - CATCH (e, RETURN_MASK_ERROR) - { - } - END_CATCH - - mi_uiout->redirect (NULL); + mi_print_breakpoint (mi, b); gdb_flush (mi->event_channel); } @@ -927,24 +936,7 @@ mi_breakpoint_modified (struct breakpoint *b) target_terminal::ours_for_output (); fprintf_unfiltered (mi->event_channel, "breakpoint-modified"); - /* We want the output from gdb_breakpoint_query to go to - mi->event_channel. One approach would be to just call - gdb_breakpoint_query, and then use mi_out_put to send the current - content of mi_uiout into mi->event_channel. However, that will - break if anything is output to mi_uiout prior to calling the - breakpoint_created notifications. So, we use - ui_out_redirect. */ - mi->mi_uiout->redirect (mi->event_channel); - TRY - { - gdb_breakpoint_query (mi->mi_uiout, b->number, NULL); - } - CATCH (e, RETURN_MASK_ERROR) - { - } - END_CATCH - - mi->mi_uiout->redirect (NULL); + mi_print_breakpoint (mi, b); gdb_flush (mi->event_channel); } diff --git a/gdb/mi/mi-main.c b/gdb/mi/mi-main.c index 5e71949..1cf3b7f 100644 --- a/gdb/mi/mi-main.c +++ b/gdb/mi/mi-main.c @@ -38,7 +38,6 @@ #include "gdbcore.h" /* For write_memory(). */ #include "value.h" #include "regcache.h" -#include "gdb.h" #include "frame.h" #include "mi-main.h" #include "mi-common.h" @@ -553,21 +552,17 @@ mi_cmd_target_flash_erase (const char *command, char **argv, int argc) void mi_cmd_thread_select (const char *command, char **argv, int argc) { - enum gdb_rc rc; - char *mi_error_message; - ptid_t previous_ptid = inferior_ptid; - if (argc != 1) error (_("-thread-select: USAGE: threadnum.")); - rc = gdb_thread_select (current_uiout, argv[0], &mi_error_message); + int num = value_as_long (parse_and_eval (argv[0])); + thread_info *thr = find_thread_global_id (num); + if (thr == NULL) + error (_("Thread ID %d not known."), num); - /* If thread switch did not succeed don't notify or print. */ - if (rc == GDB_RC_FAIL) - { - make_cleanup (xfree, mi_error_message); - error ("%s", mi_error_message); - } + ptid_t previous_ptid = inferior_ptid; + + thread_select (argv[0], thr); print_selected_thread_frame (current_uiout, USER_SELECTED_THREAD | USER_SELECTED_FRAME); @@ -583,19 +578,31 @@ mi_cmd_thread_select (const char *command, char **argv, int argc) void mi_cmd_thread_list_ids (const char *command, char **argv, int argc) { - enum gdb_rc rc; - char *mi_error_message; - if (argc != 0) error (_("-thread-list-ids: No arguments required.")); - rc = gdb_list_thread_ids (current_uiout, &mi_error_message); + int num = 0; + int current_thread = -1; - if (rc == GDB_RC_FAIL) - { - make_cleanup (xfree, mi_error_message); - error ("%s", mi_error_message); - } + update_thread_list (); + + { + ui_out_emit_tuple tuple_emitter (current_uiout, "thread-ids"); + + struct thread_info *tp; + ALL_NON_EXITED_THREADS (tp) + { + if (tp->ptid == inferior_ptid) + current_thread = tp->global_num; + + num++; + current_uiout->field_int ("thread-id", tp->global_num); + } + } + + if (current_thread != -1) + current_uiout->field_int ("current-thread-id", current_thread); + current_uiout->field_int ("number-of-threads", num); } void diff --git a/gdb/remote-fileio.c b/gdb/remote-fileio.c index f3e33ec..9d1a923 100644 --- a/gdb/remote-fileio.c +++ b/gdb/remote-fileio.c @@ -1118,10 +1118,9 @@ static struct { { NULL, NULL } }; -static int -do_remote_fileio_request (struct ui_out *uiout, void *buf_arg) +static void +do_remote_fileio_request (char *buf) { - char *buf = (char *) buf_arg; char *c; int idx; @@ -1135,10 +1134,10 @@ do_remote_fileio_request (struct ui_out *uiout, void *buf_arg) for (idx = 0; remote_fio_func_map[idx].name; ++idx) if (!strcmp (remote_fio_func_map[idx].name, buf)) break; - if (!remote_fio_func_map[idx].name) /* ERROR: No such function. */ - return RETURN_ERROR; - remote_fio_func_map[idx].func (c); - return 0; + if (!remote_fio_func_map[idx].name) + remote_fileio_reply (-1, FILEIO_ENOSYS); + else + remote_fio_func_map[idx].func (c); } /* Close any open descriptors, and reinitialize the file mapping. */ @@ -1188,22 +1187,16 @@ remote_fileio_request (char *buf, int ctrlc_pending_p) } else { - ex = catch_exceptions (current_uiout, - [&] (ui_out *uiout) - { - return do_remote_fileio_request (uiout, buf); - }, - RETURN_MASK_ALL); - switch (ex) + TRY { - case RETURN_ERROR: - remote_fileio_reply (-1, FILEIO_ENOSYS); - break; - case RETURN_QUIT: - remote_fileio_reply (-1, FILEIO_EINTR); - break; - default: - break; + do_remote_fileio_request (buf); + } + CATCH (ex, RETURN_MASK_ALL) + { + if (ex.reason == RETURN_QUIT) + remote_fileio_reply (-1, FILEIO_EINTR); + else + remote_fileio_reply (-1, FILEIO_EIO); } } diff --git a/gdb/symfile-mem.c b/gdb/symfile-mem.c index 5cefbc9..c7ef013 100644 --- a/gdb/symfile-mem.c +++ b/gdb/symfile-mem.c @@ -167,31 +167,6 @@ add_symbol_file_from_memory_command (const char *args, int from_tty) symbol_file_add_from_memory (templ, addr, 0, NULL, from_tty); } -/* Arguments for symbol_file_add_from_memory_wrapper. */ - -struct symbol_file_add_from_memory_args -{ - struct bfd *bfd; - CORE_ADDR sysinfo_ehdr; - size_t size; - char *name; - int from_tty; -}; - -/* Wrapper function for symbol_file_add_from_memory, for - catch_exceptions. */ - -static int -symbol_file_add_from_memory_wrapper (struct ui_out *uiout, void *data) -{ - struct symbol_file_add_from_memory_args *args - = (struct symbol_file_add_from_memory_args *) data; - - symbol_file_add_from_memory (args->bfd, args->sysinfo_ehdr, args->size, - args->name, args->from_tty); - return 0; -} - /* Try to add the symbols for the vsyscall page, if there is one. This function is called via the inferior_created observer. */ @@ -203,7 +178,6 @@ add_vsyscall_page (struct target_ops *target, int from_tty) if (gdbarch_vsyscall_range (target_gdbarch (), &vsyscall_range)) { struct bfd *bfd; - struct symbol_file_add_from_memory_args args; if (core_bfd != NULL) bfd = core_bfd; @@ -221,23 +195,24 @@ add_vsyscall_page (struct target_ops *target, int from_tty) "because no executable was specified")); return; } - args.bfd = bfd; - args.sysinfo_ehdr = vsyscall_range.start; - args.size = vsyscall_range.length; - - args.name = xstrprintf ("system-supplied DSO at %s", - paddress (target_gdbarch (), vsyscall_range.start)); - /* Pass zero for FROM_TTY, because the action of loading the - vsyscall DSO was not triggered by the user, even if the user - typed "run" at the TTY. */ - args.from_tty = 0; - catch_exceptions (current_uiout, - [&] (ui_out *uiout) - { - return symbol_file_add_from_memory_wrapper (uiout, - &args); - }, - RETURN_MASK_ALL); + + char *name = xstrprintf ("system-supplied DSO at %s", + paddress (target_gdbarch (), vsyscall_range.start)); + TRY + { + /* Pass zero for FROM_TTY, because the action of loading the + vsyscall DSO was not triggered by the user, even if the + user typed "run" at the TTY. */ + symbol_file_add_from_memory (bfd, + vsyscall_range.start, + vsyscall_range.length, + name, + 0 /* from_tty */); + } + CATCH (ex, RETURN_MASK_ALL) + { + exception_print (gdb_stderr, ex); + } } } diff --git a/gdb/thread.c b/gdb/thread.c index 7deebf2..33c98e4 100644 --- a/gdb/thread.c +++ b/gdb/thread.c @@ -30,7 +30,6 @@ #include "command.h" #include "gdbcmd.h" #include "regcache.h" -#include "gdb.h" #include "btrace.h" #include <ctype.h> @@ -720,50 +719,6 @@ any_live_thread_of_process (int pid) return tp_executing; } -/* Print a list of thread ids currently known, and the total number of - threads. To be used from within catch_errors. */ -static int -do_captured_list_thread_ids (struct ui_out *uiout) -{ - struct thread_info *tp; - int num = 0; - int current_thread = -1; - - update_thread_list (); - - { - ui_out_emit_tuple tuple_emitter (uiout, "thread-ids"); - - for (tp = thread_list; tp; tp = tp->next) - { - if (tp->state == THREAD_EXITED) - continue; - - if (tp->ptid == inferior_ptid) - current_thread = tp->global_num; - - num++; - uiout->field_int ("thread-id", tp->global_num); - } - } - - if (current_thread != -1) - uiout->field_int ("current-thread-id", current_thread); - uiout->field_int ("number-of-threads", num); - return GDB_RC_OK; -} - -/* Official gdblib interface function to get a list of thread ids and - the total number. */ -enum gdb_rc -gdb_list_thread_ids (struct ui_out *uiout, char **error_message) -{ - if (catch_exceptions_with_msg (uiout, do_captured_list_thread_ids, - error_message, RETURN_MASK_ALL) < 0) - return GDB_RC_FAIL; - return GDB_RC_OK; -} - /* Return true if TP is an active thread. */ static int thread_alive (struct thread_info *tp) @@ -1885,13 +1840,8 @@ thread_command (char *tidstr, int from_tty) else { ptid_t previous_ptid = inferior_ptid; - enum gdb_rc result; - - result = gdb_thread_select (current_uiout, tidstr, NULL); - /* If thread switch did not succeed don't notify or print. */ - if (result == GDB_RC_FAIL) - return; + thread_select (tidstr, parse_thread_id (tidstr, NULL)); /* Print if the thread has not changed, otherwise an event will be sent. */ @@ -1991,25 +1941,9 @@ show_print_thread_events (struct ui_file *file, int from_tty, value); } -static int -do_captured_thread_select (struct ui_out *uiout, const char *tidstr) +void +thread_select (const char *tidstr, thread_info *tp) { - struct thread_info *tp; - - if (uiout->is_mi_like_p ()) - { - int num = value_as_long (parse_and_eval (tidstr)); - - tp = find_thread_global_id (num); - if (tp == NULL) - error (_("Thread ID %d not known."), num); - } - else - { - tp = parse_thread_id (tidstr, NULL); - gdb_assert (tp != NULL); - } - if (!thread_alive (tp)) error (_("Thread ID %s has terminated."), tidstr); @@ -2020,8 +1954,6 @@ do_captured_thread_select (struct ui_out *uiout, const char *tidstr) /* Since the current thread may have changed, see if there is any exited thread we can now delete. */ prune_threads (); - - return GDB_RC_OK; } /* Print thread and frame switch command response. */ @@ -2066,20 +1998,6 @@ print_selected_thread_frame (struct ui_out *uiout, } } -enum gdb_rc -gdb_thread_select (struct ui_out *uiout, char *tidstr, char **error_message) -{ - if (catch_exceptions_with_msg - (uiout, - [&] (struct ui_out *inner_uiout) - { - return do_captured_thread_select (inner_uiout, tidstr); - }, - error_message, RETURN_MASK_ALL) < 0) - return GDB_RC_FAIL; - return GDB_RC_OK; -} - /* Update the 'threads_executing' global based on the threads we know about right now. */ |