New GDB/MI commands to catch Ada exceptions
authorJoel Brobecker <brobecker@gnat.com>
Fri, 11 Oct 2013 13:48:19 +0000 (13:48 +0000)
committerJoel Brobecker <brobecker@gnat.com>
Fri, 11 Oct 2013 13:48:19 +0000 (13:48 +0000)
This patch introduces two new GDB/MI commands implementing the equivalent
of the "catch exception" and  "catch assert" GDB/CLI commands.

gdb/ChangeLog:

        * breakpoint.h (init_ada_exception_breakpoint): Add parameter
        "enabled".
        * breakpoint.c (init_ada_exception_breakpoint): Add parameter
        "enabled".  Set B->ENABLE_STATE accordingly.
        * ada-lang.h (ada_exception_catchpoint_kind): Move here from
        ada-lang.c.
        (create_ada_exception_catchpoint): Add declaration.
        * ada-lang.c (ada_exception_catchpoint_kind): Move to ada-lang.h.
        (create_ada_exception_catchpoint): Make non-static. Add new
        parameter "disabled". Use it in call to
        init_ada_exception_breakpoint.
        (catch_ada_exception_command): Add parameter "enabled" in call
        to create_ada_exception_catchpoint.
        (catch_assert_command): Likewise.

        * mi/mi-cmds.h (mi_cmd_catch_assert, mi_cmd_catch_exception):
        Add declarations.
        * mi/mi-cmds.c (mi_cmds): Add the "catch-assert" and
        "catch-exception" commands.
        * mi/mi-cmd-catch.c: Add #include "ada-lang.h".
        (mi_cmd_catch_assert, mi_cmd_catch_exception): New functions.

gdb/ChangeLog
gdb/ada-lang.c
gdb/ada-lang.h
gdb/breakpoint.c
gdb/breakpoint.h
gdb/mi/mi-cmd-catch.c
gdb/mi/mi-cmds.c
gdb/mi/mi-cmds.h

index b07f1c5f478c011f9389360f3d97121f457ecafd..b8f01c2547c4675cf42077f8fd73d72b7845e033 100644 (file)
@@ -1,3 +1,27 @@
+2013-10-11  Joel Brobecker  <brobecker@adacore.com>
+
+       * breakpoint.h (init_ada_exception_breakpoint): Add parameter
+       "enabled".
+       * breakpoint.c (init_ada_exception_breakpoint): Add parameter
+       "enabled".  Set B->ENABLE_STATE accordingly.
+       * ada-lang.h (ada_exception_catchpoint_kind): Move here from
+       ada-lang.c.
+       (create_ada_exception_catchpoint): Add declaration.
+       * ada-lang.c (ada_exception_catchpoint_kind): Move to ada-lang.h.
+       (create_ada_exception_catchpoint): Make non-static. Add new
+       parameter "disabled". Use it in call to
+       init_ada_exception_breakpoint.
+       (catch_ada_exception_command): Add parameter "enabled" in call
+       to create_ada_exception_catchpoint.
+       (catch_assert_command): Likewise.
+
+       * mi/mi-cmds.h (mi_cmd_catch_assert, mi_cmd_catch_exception):
+       Add declarations.
+       * mi/mi-cmds.c (mi_cmds): Add the "catch-assert" and
+       "catch-exception" commands.
+       * mi/mi-cmd-catch.c: Add #include "ada-lang.h".
+       (mi_cmd_catch_assert, mi_cmd_catch_exception): New functions.
+
 2013-10-11  Joel Brobecker  <brobecker@adacore.com>
 
        * ada-lang.c (enum ada_exception_catchpoint_kind): Renames
index 3c7e4cfe9bc7483cbc5c539fea73d00a5e20a829..9ff3ab91f015d7a64732cb72eba8d913264715bb 100644 (file)
@@ -10981,16 +10981,6 @@ ada_modulus (struct type *type)
    variants of the runtime, we use a sniffer that will determine
    the runtime variant used by the program being debugged.  */
 
-/* The different types of catchpoints that we introduced for catching
-   Ada exceptions.  */
-
-enum ada_exception_catchpoint_kind
-{
-  ada_catch_exception,
-  ada_catch_exception_unhandled,
-  ada_catch_assert
-};
-
 /* Ada's standard exceptions.  */
 
 static char *standard_exc[] = {
@@ -12190,12 +12180,13 @@ ada_exception_sal (enum ada_exception_catchpoint_kind ex, char *excep_string,
 
    FROM_TTY is the usual argument passed to all commands implementations.  */
 
-static void
+void
 create_ada_exception_catchpoint (struct gdbarch *gdbarch,
                                 enum ada_exception_catchpoint_kind ex_kind,
                                 char *excep_string,
                                 char *cond_string,
                                 int tempflag,
+                                int disabled,
                                 int from_tty)
 {
   struct ada_catchpoint *c;
@@ -12206,7 +12197,7 @@ create_ada_exception_catchpoint (struct gdbarch *gdbarch,
 
   c = XNEW (struct ada_catchpoint);
   init_ada_exception_breakpoint (&c->base, gdbarch, sal, addr_string,
-                                ops, tempflag, from_tty);
+                                ops, tempflag, disabled, from_tty);
   c->excep_string = excep_string;
   create_excep_cond_exprs (c);
   if (cond_string != NULL)
@@ -12234,7 +12225,8 @@ catch_ada_exception_command (char *arg, int from_tty,
                                     &cond_string);
   create_ada_exception_catchpoint (gdbarch, ex_kind,
                                   excep_string, cond_string,
-                                  tempflag, from_tty);
+                                  tempflag, 1 /* enabled */,
+                                  from_tty);
 }
 
 /* Split the arguments specified in a "catch assert" command.
@@ -12284,7 +12276,8 @@ catch_assert_command (char *arg, int from_tty,
   catch_ada_assert_command_split (arg, &cond_string);
   create_ada_exception_catchpoint (gdbarch, ada_catch_assert,
                                   NULL, cond_string,
-                                  tempflag, from_tty);
+                                  tempflag, 1 /* enabled */,
+                                  from_tty);
 }
                                 /* Operators */
 /* Information about operators given special treatment in functions
index 4ea25b80ba9f051f7a738bf2b2ac291182983a1a..151ced8bef13058713a682adb0539510e3184805 100644 (file)
@@ -114,6 +114,16 @@ enum ada_renaming_category
     ADA_SUBPROGRAM_RENAMING
   };
 
+/* The different types of catchpoints that we introduced for catching
+   Ada exceptions.  */
+
+enum ada_exception_catchpoint_kind
+{
+  ada_catch_exception,
+  ada_catch_exception_unhandled,
+  ada_catch_assert
+};
+
 /* Ada task structures.  */
 
 struct ada_task_info
@@ -374,6 +384,11 @@ extern char *ada_main_name (void);
 
 extern char *ada_name_for_lookup (const char *name);
 
+extern void create_ada_exception_catchpoint
+  (struct gdbarch *gdbarch, enum ada_exception_catchpoint_kind ex_kind,
+   char *excep_string, char *cond_string, int tempflag, int disabled,
+   int from_tty);
+
 /* Tasking-related: ada-tasks.c */
 
 extern int valid_task_id (int);
index f0da90a5ce76364e7355180d69db09c50073d201..5ce50defc11076d70f633e155427fd26db60ef09 100644 (file)
@@ -11621,6 +11621,7 @@ init_ada_exception_breakpoint (struct breakpoint *b,
                               char *addr_string,
                               const struct breakpoint_ops *ops,
                               int tempflag,
+                              int enabled,
                               int from_tty)
 {
   if (from_tty)
@@ -11643,7 +11644,7 @@ init_ada_exception_breakpoint (struct breakpoint *b,
 
   init_raw_breakpoint (b, gdbarch, sal, bp_breakpoint, ops);
 
-  b->enable_state = bp_enabled;
+  b->enable_state = enabled ? bp_enabled : bp_disabled;
   b->disposition = tempflag ? disp_del : disp_donttouch;
   b->addr_string = addr_string;
   b->language = language_ada;
index faedb4a7eae0c06c20e98f39f6e6abc3f393ee6d..4a25fb7b80d8ced0ba3c862967e79e736d745244 100644 (file)
@@ -1238,6 +1238,7 @@ extern void
                                 char *addr_string,
                                 const struct breakpoint_ops *ops,
                                 int tempflag,
+                                int enabled,
                                 int from_tty);
 
 extern void init_catchpoint (struct breakpoint *b,
index cd932fe999fab1938972206d5805d962d8311054..23e30d086e0f8cf4ae74dd2c2c11f9cd5356aa94 100644 (file)
 #include "breakpoint.h"
 #include "gdb.h"
 #include "libiberty.h"
+#include "ada-lang.h"
 #include "mi-cmds.h"
 #include "mi-getopt.h"
 #include "mi-cmd-break.h"
 
+/* Handler for the -catch-assert command.  */
+
+void
+mi_cmd_catch_assert (char *cmd, char *argv[], int argc)
+{
+  struct gdbarch *gdbarch = get_current_arch();
+  char *condition = NULL;
+  int enabled = 1;
+  int temp = 0;
+
+  int oind = 0;
+  char *oarg;
+
+  enum opt
+    {
+      OPT_CONDITION, OPT_DISABLED, OPT_TEMP,
+    };
+  static const struct mi_opt opts[] =
+    {
+      { "c", OPT_CONDITION, 1},
+      { "d", OPT_DISABLED, 0 },
+      { "t", OPT_TEMP, 0 },
+      { 0, 0, 0 }
+    };
+
+  for (;;)
+    {
+      int opt = mi_getopt ("-catch-assert", argc, argv, opts,
+                          &oind, &oarg);
+
+      if (opt < 0)
+        break;
+
+      switch ((enum opt) opt)
+        {
+       case OPT_CONDITION:
+         condition = oarg;
+         break;
+       case OPT_DISABLED:
+         enabled = 0;
+         break;
+       case OPT_TEMP:
+         temp = 1;
+         break;
+        }
+    }
+
+  /* This command does not accept any argument.  Make sure the user
+     did not provide any.  */
+  if (oind != argc)
+    error (_("Invalid argument: %s"), argv[oind]);
+
+  setup_breakpoint_reporting ();
+  create_ada_exception_catchpoint (gdbarch, ada_catch_assert,
+                                  NULL, condition, temp, enabled, 0);
+}
+
+/* Handler for the -catch-exception command.  */
+
+void
+mi_cmd_catch_exception (char *cmd, char *argv[], int argc)
+{
+  struct gdbarch *gdbarch = get_current_arch();
+  char *condition = NULL;
+  int enabled = 1;
+  char *exception_name = NULL;
+  int temp = 0;
+  enum ada_exception_catchpoint_kind ex_kind = ada_catch_exception;
+
+  int oind = 0;
+  char *oarg;
+
+  enum opt
+    {
+      OPT_CONDITION, OPT_DISABLED, OPT_EXCEPTION_NAME, OPT_TEMP,
+      OPT_UNHANDLED,
+    };
+  static const struct mi_opt opts[] =
+    {
+      { "c", OPT_CONDITION, 1},
+      { "d", OPT_DISABLED, 0 },
+      { "e", OPT_EXCEPTION_NAME, 1 },
+      { "t", OPT_TEMP, 0 },
+      { "u", OPT_UNHANDLED, 0},
+      { 0, 0, 0 }
+    };
+
+  for (;;)
+    {
+      int opt = mi_getopt ("-catch-exception", argc, argv, opts,
+                          &oind, &oarg);
+
+      if (opt < 0)
+        break;
+
+      switch ((enum opt) opt)
+        {
+       case OPT_CONDITION:
+         condition = oarg;
+         break;
+       case OPT_DISABLED:
+         enabled = 0;
+         break;
+       case OPT_EXCEPTION_NAME:
+         exception_name = oarg;
+         break;
+       case OPT_TEMP:
+         temp = 1;
+         break;
+       case OPT_UNHANDLED:
+         ex_kind = ada_catch_exception_unhandled;
+         break;
+        }
+    }
+
+  /* This command does not accept any argument.  Make sure the user
+     did not provide any.  */
+  if (oind != argc)
+    error (_("Invalid argument: %s"), argv[oind]);
+
+  /* Specifying an exception name does not make sense when requesting
+     an unhandled exception breakpoint.  */
+  if (ex_kind == ada_catch_exception_unhandled && exception_name != NULL)
+    error (_("\"-e\" and \"-u\" are mutually exclusive"));
+
+  setup_breakpoint_reporting ();
+  create_ada_exception_catchpoint (gdbarch, ex_kind,
+                                  exception_name, condition,
+                                  temp, enabled, 0);
+}
 
 /* Common path for the -catch-load and -catch-unload.  */
 
index 0768b2a135c56c0d1baed9916917ab5c8c27db38..1b8ec9279ed0abdaa9dbf395046984f330d8d4b3 100644 (file)
@@ -68,6 +68,10 @@ static struct mi_cmd mi_cmds[] =
                   &mi_suppress_notification.breakpoint),
   DEF_MI_CMD_MI_1 ("break-watch", mi_cmd_break_watch,
                   &mi_suppress_notification.breakpoint),
+  DEF_MI_CMD_MI_1 ("catch-assert", mi_cmd_catch_assert,
+                   &mi_suppress_notification.breakpoint),
+  DEF_MI_CMD_MI_1 ("catch-exception", mi_cmd_catch_exception,
+                   &mi_suppress_notification.breakpoint),
   DEF_MI_CMD_MI_1 ("catch-load", mi_cmd_catch_load,
                    &mi_suppress_notification.breakpoint),
   DEF_MI_CMD_MI_1 ("catch-unload", mi_cmd_catch_unload,
index a472582f12533ec05841639ceb88ce3a7cd9b5b7..bbca54db7ba7f4d6d588a62e2d0b43be967120e7 100644 (file)
@@ -39,6 +39,8 @@ extern mi_cmd_argv_ftype mi_cmd_dprintf_insert;
 extern mi_cmd_argv_ftype mi_cmd_break_commands;
 extern mi_cmd_argv_ftype mi_cmd_break_passcount;
 extern mi_cmd_argv_ftype mi_cmd_break_watch;
+extern mi_cmd_argv_ftype mi_cmd_catch_assert;
+extern mi_cmd_argv_ftype mi_cmd_catch_exception;
 extern mi_cmd_argv_ftype mi_cmd_catch_load;
 extern mi_cmd_argv_ftype mi_cmd_catch_unload;
 extern mi_cmd_argv_ftype mi_cmd_disassemble;