* tracepoint.c (trace_actions_command): Update.
[deliverable/binutils-gdb.git] / gdb / breakpoint.c
index 785155c5a0c837e3c739d5ed0a7e4bc1e35cf4a1..8d9926c11d78af6a444b80812ade2fc4a8d9f68b 100644 (file)
@@ -62,6 +62,7 @@
 #include "jit.h"
 #include "xml-syscall.h"
 #include "parser-defs.h"
+#include "cli/cli-utils.h"
 
 /* readline include files */
 #include "readline/readline.h"
@@ -98,7 +99,7 @@ static void clear_command (char *, int);
 
 static void catch_command (char *, int);
 
-static int can_use_hardware_watchpoint (struct value *);
+static int can_use_hardware_watchpoint (struct value *, int);
 
 static void break_command_1 (char *, int, int);
 
@@ -132,7 +133,8 @@ static void breakpoints_info (char *, int);
 
 static void watchpoints_info (char *, int);
 
-static int breakpoint_1 (int, int, int (*) (const struct breakpoint *));
+static int breakpoint_1 (char *, int, 
+                        int (*) (const struct breakpoint *));
 
 static int breakpoint_cond_eval (void *);
 
@@ -142,8 +144,6 @@ static void commands_command (char *, int);
 
 static void condition_command (char *, int);
 
-static int get_number_trailer (char **, int);
-
 typedef enum
   {
     mark_inserted,
@@ -185,8 +185,6 @@ static void catch_exception_command_1 (enum exception_event_kind ex_event,
 
 static void tcatch_command (char *arg, int from_tty);
 
-static void ep_skip_leading_whitespace (char **s);
-
 static void detach_single_step_breakpoints (void);
 
 static int single_step_breakpoint_inserted_here_p (struct address_space *,
@@ -268,8 +266,9 @@ show_can_use_hw_watchpoints (struct ui_file *file, int from_tty,
                             struct cmd_list_element *c,
                             const char *value)
 {
-  fprintf_filtered (file, _("\
-Debugger's willingness to use watchpoint hardware is %s.\n"),
+  fprintf_filtered (file,
+                   _("Debugger's willingness to use "
+                     "watchpoint hardware is %s.\n"),
                    value);
 }
 
@@ -283,8 +282,9 @@ show_pending_break_support (struct ui_file *file, int from_tty,
                            struct cmd_list_element *c,
                            const char *value)
 {
-  fprintf_filtered (file, _("\
-Debugger's behavior regarding pending breakpoints is %s.\n"),
+  fprintf_filtered (file,
+                   _("Debugger's behavior regarding "
+                     "pending breakpoints is %s.\n"),
                    value);
 }
 
@@ -298,8 +298,8 @@ show_automatic_hardware_breakpoints (struct ui_file *file, int from_tty,
                                     struct cmd_list_element *c,
                                     const char *value)
 {
-  fprintf_filtered (file, _("\
-Automatic usage of hardware breakpoints is %s.\n"),
+  fprintf_filtered (file,
+                   _("Automatic usage of hardware breakpoints is %s.\n"),
                    value);
 }
 
@@ -324,12 +324,14 @@ show_always_inserted_mode (struct ui_file *file, int from_tty,
                     struct cmd_list_element *c, const char *value)
 {
   if (always_inserted_mode == always_inserted_auto)
-    fprintf_filtered (file, _("\
-Always inserted breakpoint mode is %s (currently %s).\n"),
+    fprintf_filtered (file,
+                     _("Always inserted breakpoint "
+                       "mode is %s (currently %s).\n"),
                      value,
                      breakpoints_always_inserted_mode () ? "on" : "off");
   else
-    fprintf_filtered (file, _("Always inserted breakpoint mode is %s.\n"), value);
+    fprintf_filtered (file, _("Always inserted breakpoint mode is %s.\n"),
+                     value);
 }
 
 int
@@ -347,6 +349,9 @@ static int executing_breakpoint_commands;
 /* Are overlay event breakpoints enabled? */
 static int overlay_events_enabled;
 
+/* See description in breakpoint.h. */
+int target_exact_watchpoints = 0;
+
 /* Walk the following statement or block through all breakpoints.
    ALL_BREAKPOINTS_SAFE does so even if the statment deletes the
    current breakpoint.  */
@@ -546,163 +551,6 @@ int default_breakpoint_line;
 struct program_space *default_breakpoint_pspace;
 
 \f
-/* *PP is a string denoting a breakpoint.  Get the number of the
-   breakpoint.  Advance *PP after the string and any trailing
-   whitespace.
-
-   Currently the string can either be a number or "$" followed by the
-   name of a convenience variable.  Making it an expression wouldn't
-   work well for map_breakpoint_numbers (e.g. "4 + 5 + 6").
-
-   If the string is a NULL pointer, that denotes the last breakpoint.
-   
-   TRAILER is a character which can be found after the number; most
-   commonly this is `-'.  If you don't want a trailer, use \0.  */
-
-static int
-get_number_trailer (char **pp, int trailer)
-{
-  int retval = 0;      /* default */
-  char *p = *pp;
-
-  if (p == NULL)
-    /* Empty line means refer to the last breakpoint.  */
-    return breakpoint_count;
-  else if (*p == '$')
-    {
-      /* Make a copy of the name, so we can null-terminate it
-         to pass to lookup_internalvar().  */
-      char *varname;
-      char *start = ++p;
-      LONGEST val;
-
-      while (isalnum (*p) || *p == '_')
-       p++;
-      varname = (char *) alloca (p - start + 1);
-      strncpy (varname, start, p - start);
-      varname[p - start] = '\0';
-      if (get_internalvar_integer (lookup_internalvar (varname), &val))
-       retval = (int) val;
-      else
-       {
-         printf_filtered (_("Convenience variable must have integer value.\n"));
-         retval = 0;
-       }
-    }
-  else
-    {
-      if (*p == '-')
-       ++p;
-      while (*p >= '0' && *p <= '9')
-       ++p;
-      if (p == *pp)
-       /* There is no number here.  (e.g. "cond a == b").  */
-       {
-         /* Skip non-numeric token.  */
-         while (*p && !isspace((int) *p))
-           ++p;
-         /* Return zero, which caller must interpret as error.  */
-         retval = 0;
-       }
-      else
-       retval = atoi (*pp);
-    }
-  if (!(isspace (*p) || *p == '\0' || *p == trailer))
-    {
-      /* Trailing junk: return 0 and let caller print error msg.  */
-      while (!(isspace (*p) || *p == '\0' || *p == trailer))
-       ++p;
-      retval = 0;
-    }
-  while (isspace (*p))
-    p++;
-  *pp = p;
-  return retval;
-}
-
-
-/* Like get_number_trailer, but don't allow a trailer.  */
-int
-get_number (char **pp)
-{
-  return get_number_trailer (pp, '\0');
-}
-
-/* Parse a number or a range.
-   A number will be of the form handled by get_number.
-   A range will be of the form <number1> - <number2>, and 
-   will represent all the integers between number1 and number2,
-   inclusive.
-
-   While processing a range, this fuction is called iteratively;
-   At each call it will return the next value in the range.
-
-   At the beginning of parsing a range, the char pointer PP will
-   be advanced past <number1> and left pointing at the '-' token.
-   Subsequent calls will not advance the pointer until the range
-   is completed.  The call that completes the range will advance
-   pointer PP past <number2>.  */
-
-int 
-get_number_or_range (char **pp)
-{
-  static int last_retval, end_value;
-  static char *end_ptr;
-  static int in_range = 0;
-
-  if (**pp != '-')
-    {
-      /* Default case: pp is pointing either to a solo number, 
-        or to the first number of a range.  */
-      last_retval = get_number_trailer (pp, '-');
-      if (**pp == '-')
-       {
-         char **temp;
-
-         /* This is the start of a range (<number1> - <number2>).
-            Skip the '-', parse and remember the second number,
-            and also remember the end of the final token.  */
-
-         temp = &end_ptr; 
-         end_ptr = *pp + 1; 
-         while (isspace ((int) *end_ptr))
-           end_ptr++;  /* skip white space */
-         end_value = get_number (temp);
-         if (end_value < last_retval) 
-           {
-             error (_("inverted range"));
-           }
-         else if (end_value == last_retval)
-           {
-             /* Degenerate range (number1 == number2).  Advance the
-                token pointer so that the range will be treated as a
-                single number.  */ 
-             *pp = end_ptr;
-           }
-         else
-           in_range = 1;
-       }
-    }
-  else if (! in_range)
-    error (_("negative value"));
-  else
-    {
-      /* pp points to the '-' that betokens a range.  All
-        number-parsing has already been done.  Return the next
-        integer value (one greater than the saved previous value).
-        Do not advance the token pointer 'pp' until the end of range
-        is reached.  */
-
-      if (++last_retval == end_value)
-       {
-         /* End of range reached; advance token pointer.  */
-         *pp = end_ptr;
-         in_range = 0;
-       }
-    }
-  return last_retval;
-}
-
 /* Return the breakpoint with the specified number, or NULL
    if the number does not refer to an existing breakpoint.  */
 
@@ -816,7 +664,8 @@ check_no_tracepoint_commands (struct command_line *commands)
       int i;
 
       if (c->control_type == while_stepping_control)
-       error (_("The 'while-stepping' command can only be used for tracepoints"));
+       error (_("The 'while-stepping' command can "
+                "only be used for tracepoints"));
 
       for (i = 0; i < c->body_count; ++i)
        check_no_tracepoint_commands ((c->body_list)[i]);
@@ -863,14 +712,15 @@ validate_commands_for_breakpoint (struct breakpoint *b,
          if (c->control_type == while_stepping_control)
            {
              if (b->type == bp_fast_tracepoint)
-               error (_("\
-The 'while-stepping' command cannot be used for fast tracepoint"));
+               error (_("The 'while-stepping' command "
+                        "cannot be used for fast tracepoint"));
              else if (b->type == bp_static_tracepoint)
-               error (_("\
-The 'while-stepping' command cannot be used for static tracepoint"));
+               error (_("The 'while-stepping' command "
+                        "cannot be used for static tracepoint"));
 
              if (while_stepping)
-               error (_("The 'while-stepping' command can be used only once"));
+               error (_("The 'while-stepping' command "
+                        "can be used only once"));
              else
                while_stepping = c;
            }
@@ -930,6 +780,46 @@ breakpoint_set_commands (struct breakpoint *b,
   observer_notify_breakpoint_modified (b->number);
 }
 
+/* Set the internal `silent' flag on the breakpoint.  Note that this
+   is not the same as the "silent" that may appear in the breakpoint's
+   commands.  */
+
+void
+breakpoint_set_silent (struct breakpoint *b, int silent)
+{
+  int old_silent = b->silent;
+
+  b->silent = silent;
+  if (old_silent != silent)
+    observer_notify_breakpoint_modified (b->number);
+}
+
+/* Set the thread for this breakpoint.  If THREAD is -1, make the
+   breakpoint work for any thread.  */
+
+void
+breakpoint_set_thread (struct breakpoint *b, int thread)
+{
+  int old_thread = b->thread;
+
+  b->thread = thread;
+  if (old_thread != thread)
+    observer_notify_breakpoint_modified (b->number);
+}
+
+/* Set the task for this breakpoint.  If TASK is 0, make the
+   breakpoint work for any task.  */
+
+void
+breakpoint_set_task (struct breakpoint *b, int task)
+{
+  int old_task = b->task;
+
+  b->task = task;
+  if (old_task != task)
+    observer_notify_breakpoint_modified (b->number);
+}
+
 void
 check_tracepoint_command (char *line, void *closure)
 {
@@ -977,7 +867,8 @@ do_map_commands_command (struct breakpoint *b, void *data)
          struct cleanup *old_chain;
          char *str;
 
-         str = xstrprintf (_("Type commands for breakpoint(s) %s, one per line."),
+         str = xstrprintf (_("Type commands for breakpoint(s) "
+                             "%s, one per line."),
                            info->arg);
 
          old_chain = make_cleanup (xfree, str);
@@ -1220,18 +1111,6 @@ breakpoint_restore_shadows (gdb_byte *buf, ULONGEST memaddr, LONGEST len)
 }
 \f
 
-/* A wrapper function for inserting catchpoints.  */
-static void
-insert_catchpoint (struct ui_out *uo, void *args)
-{
-  struct breakpoint *b = (struct breakpoint *) args;
-
-  gdb_assert (b->type == bp_catchpoint);
-  gdb_assert (b->ops != NULL && b->ops->insert != NULL);
-
-  b->ops->insert (b);
-}
-
 /* Return true if BPT is of any hardware watchpoint kind.  */
 
 static int
@@ -1335,11 +1214,6 @@ update_watchpoint (struct breakpoint *b, int reparse)
   if (!watchpoint_in_thread_scope (b))
     return;
 
-  /* We don't free locations.  They are stored in bp_location array
-     and update_global_locations will eventually delete them and
-     remove breakpoints if needed.  */
-  b->loc = NULL;
-
   if (b->disposition == disp_del_at_next_stop)
     return;
  
@@ -1350,7 +1224,15 @@ update_watchpoint (struct breakpoint *b, int reparse)
     within_current_scope = 1;
   else
     {
-      struct frame_info *fi;
+      struct frame_info *fi = get_current_frame ();
+      struct gdbarch *frame_arch = get_frame_arch (fi);
+      CORE_ADDR frame_pc = get_frame_pc (fi);
+
+      /* If we're in a function epilogue, unwinding may not work
+        properly, so do not attempt to recreate locations at this
+        point.  See similar comments in watchpoint_check.  */
+      if (gdbarch_in_function_epilogue_p (frame_arch, frame_pc))
+       return;
 
       /* Save the current frame's ID so we can restore it after
          evaluating the watchpoint expression on its own frame.  */
@@ -1366,6 +1248,11 @@ update_watchpoint (struct breakpoint *b, int reparse)
        select_frame (fi);
     }
 
+  /* We don't free locations.  They are stored in the bp_location array
+     and update_global_location_list will eventually delete them and
+     remove breakpoints if needed.  */
+  b->loc = NULL;
+
   if (within_current_scope && reparse)
     {
       char *s;
@@ -1430,43 +1317,10 @@ update_watchpoint (struct breakpoint *b, int reparse)
          b->val_valid = 1;
        }
 
-       /* Change the type of breakpoint between hardware assisted or
-          an ordinary watchpoint depending on the hardware support
-          and free hardware slots.  REPARSE is set when the inferior
-          is started.  */
-       if ((b->type == bp_watchpoint || b->type == bp_hardware_watchpoint)
-           && reparse)
-         {
-           int i, mem_cnt, other_type_used;
-
-           /* We need to determine how many resources are already
-              used for all other hardware watchpoints to see if we
-              still have enough resources to also fit this watchpoint
-              in as well.  To avoid the hw_watchpoint_used_count call
-              below from counting this watchpoint, make sure that it
-              is marked as a software watchpoint.  */
-           b->type = bp_watchpoint;
-           i = hw_watchpoint_used_count (bp_hardware_watchpoint,
-                                         &other_type_used);
-           mem_cnt = can_use_hardware_watchpoint (val_chain);
-
-           if (!mem_cnt)
-             b->type = bp_watchpoint;
-           else
-             {
-               int target_resources_ok = target_can_use_hardware_watchpoint
-                 (bp_hardware_watchpoint, i + mem_cnt, other_type_used);
-               if (target_resources_ok <= 0)
-                 b->type = bp_watchpoint;
-               else
-                 b->type = bp_hardware_watchpoint;
-             }
-         }
-
       frame_pspace = get_frame_program_space (get_selected_frame (NULL));
 
       /* Look at each value on the value chain.  */
-      for (v = val_chain; v; v = next)
+      for (v = val_chain; v; v = value_next (v))
        {
          /* If it's a memory location, and GDB actually needed
             its contents to evaluate the expression, then we
@@ -1509,7 +1363,62 @@ update_watchpoint (struct breakpoint *b, int reparse)
                  loc->watchpoint_type = type;
                }
            }
+       }
+
+      /* Change the type of breakpoint between hardware assisted or
+        an ordinary watchpoint depending on the hardware support
+        and free hardware slots.  REPARSE is set when the inferior
+        is started.  */
+      if ((b->type == bp_watchpoint || b->type == bp_hardware_watchpoint)
+         && reparse)
+       {
+         int reg_cnt;
+         enum bp_loc_type loc_type;
+         struct bp_location *bl;
+
+         reg_cnt = can_use_hardware_watchpoint (val_chain, b->exact);
+
+         if (reg_cnt)
+           {
+             int i, target_resources_ok, other_type_used;
+             enum enable_state orig_enable_state;
+
+             /* We need to determine how many resources are already
+                used for all other hardware watchpoints plus this one
+                to see if we still have enough resources to also fit
+                this watchpoint in as well.  To guarantee the
+                hw_watchpoint_used_count call below counts this
+                watchpoint, make sure that it is marked as a hardware
+                watchpoint.  */
+             b->type = bp_hardware_watchpoint;
+
+             /* hw_watchpoint_used_count ignores disabled watchpoints,
+                and b might be disabled if we're being called from
+                do_enable_breakpoint.  */
+             orig_enable_state = b->enable_state;
+             b->enable_state = bp_enabled;
+
+             i = hw_watchpoint_used_count (bp_hardware_watchpoint,
+                                           &other_type_used);
+
+             b->enable_state = orig_enable_state;
+
+             target_resources_ok = target_can_use_hardware_watchpoint
+                   (bp_hardware_watchpoint, i, other_type_used);
+             if (target_resources_ok <= 0)
+               b->type = bp_watchpoint;
+           }
+         else
+           b->type = bp_watchpoint;
+
+         loc_type = (b->type == bp_watchpoint? bp_loc_other
+                     : bp_loc_hardware_watchpoint);
+         for (bl = b->loc; bl; bl = bl->next)
+           bl->loc_type = loc_type;
+       }
 
+      for (v = val_chain; v; v = next)
+       {
          next = value_next (v);
          if (v != b->val)
            value_free (v);
@@ -1648,15 +1557,18 @@ insert_bp_location (struct bp_location *bl,
                      bl->loc_type = new_type;
                      if (!said)
                        {
-                         fprintf_filtered (gdb_stdout, _("\
-Note: automatically using hardware breakpoints for read-only addresses.\n"));
+                         fprintf_filtered (gdb_stdout,
+                                           _("Note: automatically using "
+                                             "hardware breakpoints for "
+                                             "read-only addresses.\n"));
                          said = 1;
                        }
                    }
                }
              else if (bl->loc_type == bp_loc_software_breakpoint
                       && mr->attrib.mode != MEM_RW)        
-               warning (_("cannot set software breakpoint at readonly address %s"),
+               warning (_("cannot set software breakpoint "
+                          "at readonly address %s"),
                         paddress (bl->gdbarch, bl->address));
            }
        }
@@ -1698,7 +1610,8 @@ Note: automatically using hardware breakpoints for read-only addresses.\n"));
                                                  &bl->overlay_target_info);
                  if (val != 0)
                    fprintf_unfiltered (tmp_error_stream,
-                                       "Overlay breakpoint %d failed: in ROM?\n",
+                                       "Overlay breakpoint %d "
+                                       "failed: in ROM?\n",
                                        bl->owner->number);
                }
            }
@@ -1735,7 +1648,8 @@ Note: automatically using hardware breakpoints for read-only addresses.\n"));
                                      "Cannot insert breakpoint %d.\n", 
                                      bl->owner->number);
                  fprintf_unfiltered (tmp_error_stream, 
-                                     "Temporarily disabling shared library breakpoints:\n");
+                                     "Temporarily disabling shared "
+                                     "library breakpoints:\n");
                }
              *disabled_breaks = 1;
              fprintf_unfiltered (tmp_error_stream,
@@ -1746,8 +1660,9 @@ Note: automatically using hardware breakpoints for read-only addresses.\n"));
              if (bl->loc_type == bp_loc_hardware_breakpoint)
                {
                  *hw_breakpoint_error = 1;
-                 fprintf_unfiltered (tmp_error_stream, 
-                                     "Cannot insert hardware breakpoint %d.\n",
+                 fprintf_unfiltered (tmp_error_stream,
+                                     "Cannot insert hardware "
+                                     "breakpoint %d.\n",
                                      bl->owner->number);
                }
              else
@@ -1776,10 +1691,10 @@ Note: automatically using hardware breakpoints for read-only addresses.\n"));
              watchpoints.  It's not clear that it's necessary...  */
           && bl->owner->disposition != disp_del_at_next_stop)
     {
-      val = target_insert_watchpoint (bl->address,
-                                     bl->length,
-                                     bl->watchpoint_type,
-                                     bl->owner->cond_exp);
+      gdb_assert (bl->owner->ops != NULL
+                 && bl->owner->ops->insert_location != NULL);
+
+      val = bl->owner->ops->insert_location (bl);
 
       /* If trying to set a read-watchpoint, and it turns out it's not
         supported, try emulating one with an access watchpoint.  */
@@ -1805,12 +1720,12 @@ Note: automatically using hardware breakpoints for read-only addresses.\n"));
 
          if (val == 1)
            {
-             val = target_insert_watchpoint (bl->address,
-                                             bl->length,
-                                             hw_access,
-                                             bl->owner->cond_exp);
-             if (val == 0)
-               bl->watchpoint_type = hw_access;
+             bl->watchpoint_type = hw_access;
+             val = bl->owner->ops->insert_location (bl);
+
+             if (val)
+               /* Back to the original value.  */
+               bl->watchpoint_type = hw_read;
            }
        }
 
@@ -1819,14 +1734,23 @@ Note: automatically using hardware breakpoints for read-only addresses.\n"));
 
   else if (bl->owner->type == bp_catchpoint)
     {
-      struct gdb_exception e = catch_exception (uiout, insert_catchpoint,
-                                               bl->owner, RETURN_MASK_ERROR);
-      exception_fprintf (gdb_stderr, e, "warning: inserting catchpoint %d: ",
-                        bl->owner->number);
-      if (e.reason < 0)
-       bl->owner->enable_state = bp_disabled;
-      else
-       bl->inserted = 1;
+      gdb_assert (bl->owner->ops != NULL
+                 && bl->owner->ops->insert_location != NULL);
+
+      val = bl->owner->ops->insert_location (bl);
+      if (val)
+       {
+         bl->owner->enable_state = bp_disabled;
+
+         if (val == 1)
+           warning (_("\
+Error inserting catchpoint %d: Your system does not support this type\n\
+of catchpoint."), bl->owner->number);
+         else
+           warning (_("Error inserting catchpoint %d."), bl->owner->number);
+       }
+
+      bl->inserted = (val == 0);
 
       /* We've already printed an error message if there was a problem
         inserting this catchpoint, and we've disabled the catchpoint,
@@ -2065,7 +1989,7 @@ reattach_breakpoints (int pid)
   struct cleanup *old_chain;
   struct bp_location *bl, **blp_tmp;
   int val;
-  struct ui_file *tmp_error_stream = mem_fileopen ();
+  struct ui_file *tmp_error_stream;
   int dummy1 = 0, dummy2 = 0;
   struct inferior *inf;
   struct thread_info *tp;
@@ -2079,6 +2003,7 @@ reattach_breakpoints (int pid)
 
   inferior_ptid = tp->ptid;
 
+  tmp_error_stream = mem_fileopen ();
   make_cleanup_ui_file_delete (tmp_error_stream);
 
   ALL_BP_LOCATIONS (bl, blp_tmp)
@@ -2141,22 +2066,94 @@ create_internal_breakpoint (struct gdbarch *gdbarch,
   return b;
 }
 
+static const char *const longjmp_names[] =
+  {
+    "longjmp", "_longjmp", "siglongjmp", "_siglongjmp"
+  };
+#define NUM_LONGJMP_NAMES ARRAY_SIZE(longjmp_names)
+
+/* Per-objfile data private to breakpoint.c.  */
+struct breakpoint_objfile_data
+{
+  /* Minimal symbol for "_ovly_debug_event" (if any).  */
+  struct minimal_symbol *overlay_msym;
+
+  /* Minimal symbol(s) for "longjmp", "siglongjmp", etc. (if any).  */
+  struct minimal_symbol *longjmp_msym[NUM_LONGJMP_NAMES];
+
+  /* Minimal symbol for "std::terminate()" (if any).  */
+  struct minimal_symbol *terminate_msym;
+
+  /* Minimal symbol for "_Unwind_DebugHook" (if any).  */
+  struct minimal_symbol *exception_msym;
+};
+
+static const struct objfile_data *breakpoint_objfile_key;
+
+/* Minimal symbol not found sentinel.  */
+static struct minimal_symbol msym_not_found;
+
+/* Returns TRUE if MSYM point to the "not found" sentinel.  */
+
+static int
+msym_not_found_p (const struct minimal_symbol *msym)
+{
+  return msym == &msym_not_found;
+}
+
+/* Return per-objfile data needed by breakpoint.c.
+   Allocate the data if necessary.  */
+
+static struct breakpoint_objfile_data *
+get_breakpoint_objfile_data (struct objfile *objfile)
+{
+  struct breakpoint_objfile_data *bp_objfile_data;
+
+  bp_objfile_data = objfile_data (objfile, breakpoint_objfile_key);
+  if (bp_objfile_data == NULL)
+    {
+      bp_objfile_data = obstack_alloc (&objfile->objfile_obstack,
+                                      sizeof (*bp_objfile_data));
+
+      memset (bp_objfile_data, 0, sizeof (*bp_objfile_data));
+      set_objfile_data (objfile, breakpoint_objfile_key, bp_objfile_data);
+    }
+  return bp_objfile_data;
+}
+
 static void
-create_overlay_event_breakpoint (char *func_name)
+create_overlay_event_breakpoint (void)
 {
   struct objfile *objfile;
+  const char *const func_name = "_ovly_debug_event";
 
   ALL_OBJFILES (objfile)
     {
       struct breakpoint *b;
-      struct minimal_symbol *m;
+      struct breakpoint_objfile_data *bp_objfile_data;
+      CORE_ADDR addr;
 
-      m = lookup_minimal_symbol_text (func_name, objfile);
-      if (m == NULL)
-        continue;
+      bp_objfile_data = get_breakpoint_objfile_data (objfile);
+
+      if (msym_not_found_p (bp_objfile_data->overlay_msym))
+       continue;
+
+      if (bp_objfile_data->overlay_msym == NULL)
+       {
+         struct minimal_symbol *m;
+
+         m = lookup_minimal_symbol_text (func_name, objfile);
+         if (m == NULL)
+           {
+             /* Avoid future lookups in this objfile.  */
+             bp_objfile_data->overlay_msym = &msym_not_found;
+             continue;
+           }
+         bp_objfile_data->overlay_msym = m;
+       }
 
-      b = create_internal_breakpoint (get_objfile_arch (objfile),
-                                     SYMBOL_VALUE_ADDRESS (m),
+      addr = SYMBOL_VALUE_ADDRESS (bp_objfile_data->overlay_msym);
+      b = create_internal_breakpoint (get_objfile_arch (objfile), addr,
                                       bp_overlay_event);
       b->addr_string = xstrdup (func_name);
 
@@ -2175,70 +2172,117 @@ create_overlay_event_breakpoint (char *func_name)
 }
 
 static void
-create_longjmp_master_breakpoint (char *func_name)
+create_longjmp_master_breakpoint (void)
 {
   struct program_space *pspace;
-  struct objfile *objfile;
   struct cleanup *old_chain;
 
   old_chain = save_current_program_space ();
 
   ALL_PSPACES (pspace)
-  ALL_OBJFILES (objfile)
+  {
+    struct objfile *objfile;
+
+    set_current_program_space (pspace);
+
+    ALL_OBJFILES (objfile)
     {
-      struct breakpoint *b;
-      struct minimal_symbol *m;
+      int i;
+      struct gdbarch *gdbarch;
+      struct breakpoint_objfile_data *bp_objfile_data;
 
-      if (!gdbarch_get_longjmp_target_p (get_objfile_arch (objfile)))
+      gdbarch = get_objfile_arch (objfile);
+      if (!gdbarch_get_longjmp_target_p (gdbarch))
        continue;
 
-      set_current_program_space (pspace);
+      bp_objfile_data = get_breakpoint_objfile_data (objfile);
 
-      m = lookup_minimal_symbol_text (func_name, objfile);
-      if (m == NULL)
-        continue;
+      for (i = 0; i < NUM_LONGJMP_NAMES; i++)
+       {
+         struct breakpoint *b;
+         const char *func_name;
+         CORE_ADDR addr;
 
-      b = create_internal_breakpoint (get_objfile_arch (objfile),
-                                     SYMBOL_VALUE_ADDRESS (m),
-                                      bp_longjmp_master);
-      b->addr_string = xstrdup (func_name);
-      b->enable_state = bp_disabled;
+         if (msym_not_found_p (bp_objfile_data->longjmp_msym[i]))
+           continue;
+
+         func_name = longjmp_names[i];
+         if (bp_objfile_data->longjmp_msym[i] == NULL)
+           {
+             struct minimal_symbol *m;
+
+             m = lookup_minimal_symbol_text (func_name, objfile);
+             if (m == NULL)
+               {
+                 /* Prevent future lookups in this objfile.  */
+                 bp_objfile_data->longjmp_msym[i] = &msym_not_found;
+                 continue;
+               }
+             bp_objfile_data->longjmp_msym[i] = m;
+           }
+
+         addr = SYMBOL_VALUE_ADDRESS (bp_objfile_data->longjmp_msym[i]);
+         b = create_internal_breakpoint (gdbarch, addr, bp_longjmp_master);
+         b->addr_string = xstrdup (func_name);
+         b->enable_state = bp_disabled;
+       }
     }
+  }
   update_global_location_list (1);
 
   do_cleanups (old_chain);
 }
 
-/* Create a master std::terminate breakpoint.  The actual function
-   looked for is named FUNC_NAME.  */
+/* Create a master std::terminate breakpoint.  */
 static void
-create_std_terminate_master_breakpoint (const char *func_name)
+create_std_terminate_master_breakpoint (void)
 {
   struct program_space *pspace;
-  struct objfile *objfile;
   struct cleanup *old_chain;
+  const char *const func_name = "std::terminate()";
 
   old_chain = save_current_program_space ();
 
   ALL_PSPACES (pspace)
+  {
+    struct objfile *objfile;
+    CORE_ADDR addr;
+
+    set_current_program_space (pspace);
+
     ALL_OBJFILES (objfile)
     {
       struct breakpoint *b;
-      struct minimal_symbol *m;
+      struct breakpoint_objfile_data *bp_objfile_data;
 
-      set_current_program_space (pspace);
+      bp_objfile_data = get_breakpoint_objfile_data (objfile);
 
-      m = lookup_minimal_symbol (func_name, NULL, objfile);
-      if (m == NULL || (MSYMBOL_TYPE (m) != mst_text
-                       && MSYMBOL_TYPE (m) != mst_file_text))
-        continue;
+      if (msym_not_found_p (bp_objfile_data->terminate_msym))
+       continue;
 
-      b = create_internal_breakpoint (get_objfile_arch (objfile),
-                                     SYMBOL_VALUE_ADDRESS (m),
+      if (bp_objfile_data->terminate_msym == NULL)
+       {
+         struct minimal_symbol *m;
+
+         m = lookup_minimal_symbol (func_name, NULL, objfile);
+         if (m == NULL || (MSYMBOL_TYPE (m) != mst_text
+                           && MSYMBOL_TYPE (m) != mst_file_text))
+           {
+             /* Prevent future lookups in this objfile.  */
+             bp_objfile_data->terminate_msym = &msym_not_found;
+             continue;
+           }
+         bp_objfile_data->terminate_msym = m;
+       }
+
+      addr = SYMBOL_VALUE_ADDRESS (bp_objfile_data->terminate_msym);
+      b = create_internal_breakpoint (get_objfile_arch (objfile), addr,
                                       bp_std_terminate_master);
       b->addr_string = xstrdup (func_name);
       b->enable_state = bp_disabled;
     }
+  }
+
   update_global_location_list (1);
 
   do_cleanups (old_chain);
@@ -2250,24 +2294,42 @@ void
 create_exception_master_breakpoint (void)
 {
   struct objfile *objfile;
+  const char *const func_name = "_Unwind_DebugHook";
 
   ALL_OBJFILES (objfile)
     {
-      struct minimal_symbol *debug_hook;
+      struct breakpoint *b;
+      struct gdbarch *gdbarch;
+      struct breakpoint_objfile_data *bp_objfile_data;
+      CORE_ADDR addr;
 
-      debug_hook = lookup_minimal_symbol ("_Unwind_DebugHook", NULL, objfile);
-      if (debug_hook != NULL)
+      bp_objfile_data = get_breakpoint_objfile_data (objfile);
+
+      if (msym_not_found_p (bp_objfile_data->exception_msym))
+       continue;
+
+      gdbarch = get_objfile_arch (objfile);
+
+      if (bp_objfile_data->exception_msym == NULL)
        {
-         struct breakpoint *b;
-         CORE_ADDR addr = SYMBOL_VALUE_ADDRESS (debug_hook);
-         struct gdbarch *gdbarch = get_objfile_arch (objfile);
+         struct minimal_symbol *debug_hook;
 
-         addr = gdbarch_convert_from_func_ptr_addr (gdbarch, addr,
-                                                    &current_target);
-         b = create_internal_breakpoint (gdbarch, addr, bp_exception_master);
-         b->addr_string = xstrdup ("_Unwind_DebugHook");
-         b->enable_state = bp_disabled;
+         debug_hook = lookup_minimal_symbol (func_name, NULL, objfile);
+         if (debug_hook == NULL)
+           {
+             bp_objfile_data->exception_msym = &msym_not_found;
+             continue;
+           }
+
+         bp_objfile_data->exception_msym = debug_hook;
        }
+
+      addr = SYMBOL_VALUE_ADDRESS (bp_objfile_data->exception_msym);
+      addr = gdbarch_convert_from_func_ptr_addr (gdbarch, addr,
+                                                &current_target);
+      b = create_internal_breakpoint (gdbarch, addr, bp_exception_master);
+      b->addr_string = xstrdup (func_name);
+      b->enable_state = bp_disabled;
     }
 
   update_global_location_list (1);
@@ -2386,12 +2448,9 @@ update_breakpoints_after_exec (void)
       }
   }
   /* FIXME what about longjmp breakpoints?  Re-create them here?  */
-  create_overlay_event_breakpoint ("_ovly_debug_event");
-  create_longjmp_master_breakpoint ("longjmp");
-  create_longjmp_master_breakpoint ("_longjmp");
-  create_longjmp_master_breakpoint ("siglongjmp");
-  create_longjmp_master_breakpoint ("_siglongjmp");
-  create_std_terminate_master_breakpoint ("std::terminate()");
+  create_overlay_event_breakpoint ();
+  create_longjmp_master_breakpoint ();
+  create_std_terminate_master_breakpoint ();
   create_exception_master_breakpoint ();
 }
 
@@ -2523,10 +2582,11 @@ remove_breakpoint_1 (struct bp_location *bl, insertion_state_t is)
     }
   else if (bl->loc_type == bp_loc_hardware_watchpoint)
     {
+      gdb_assert (bl->owner->ops != NULL
+                 && bl->owner->ops->remove_location != NULL);
+
       bl->inserted = (is == mark_inserted);
-      val = target_remove_watchpoint (bl->address, bl->length,
-                                     bl->watchpoint_type, 
-                                     bl->owner->cond_exp);
+      bl->owner->ops->remove_location (bl);
 
       /* Failure to remove any of the hardware watchpoints comes here.  */
       if ((is == mark_uninserted) && (bl->inserted))
@@ -2537,11 +2597,13 @@ remove_breakpoint_1 (struct bp_location *bl, insertion_state_t is)
            && breakpoint_enabled (bl->owner)
            && !bl->duplicate)
     {
-      gdb_assert (bl->owner->ops != NULL && bl->owner->ops->remove != NULL);
+      gdb_assert (bl->owner->ops != NULL
+                 && bl->owner->ops->remove_location != NULL);
 
-      val = bl->owner->ops->remove (bl->owner);
+      val = bl->owner->ops->remove_location (bl);
       if (val)
        return val;
+
       bl->inserted = (is == mark_inserted);
     }
 
@@ -2799,7 +2861,8 @@ breakpoint_inserted_here_p (struct address_space *aspace, CORE_ADDR pc)
    inserted at PC.  */
 
 int
-software_breakpoint_inserted_here_p (struct address_space *aspace, CORE_ADDR pc)
+software_breakpoint_inserted_here_p (struct address_space *aspace,
+                                    CORE_ADDR pc)
 {
   struct bp_location *bl, **blp_tmp;
 
@@ -3246,11 +3309,6 @@ print_it_typical (bpstat bs)
   int bp_temp = 0;
   enum print_stop_action result;
 
-  /* bs->breakpoint_at can be NULL if it was a momentary breakpoint
-     which has since been deleted.  */
-  if (bs->breakpoint_at == NULL)
-    return PRINT_UNKNOWN;
-
   gdb_assert (bs->bp_location_at != NULL);
 
   bl = bs->bp_location_at;
@@ -3313,13 +3371,15 @@ print_it_typical (bpstat bs)
 
     case bp_std_terminate_master:
       /* These should never be enabled.  */
-      printf_filtered (_("std::terminate Master Breakpoint: gdb should not stop!\n"));
+      printf_filtered (_("std::terminate Master Breakpoint: "
+                        "gdb should not stop!\n"));
       result = PRINT_NOTHING;
       break;
 
     case bp_exception_master:
       /* These should never be enabled.  */
-      printf_filtered (_("Exception Master Breakpoint: gdb should not stop!\n"));
+      printf_filtered (_("Exception Master Breakpoint: "
+                        "gdb should not stop!\n"));
       result = PRINT_NOTHING;
       break;
 
@@ -3454,10 +3514,14 @@ print_bp_stop_message (bpstat bs)
       {
        struct breakpoint *b = bs->breakpoint_at;
 
+       /* bs->breakpoint_at can be NULL if it was a momentary breakpoint
+          which has since been deleted.  */
+       if (b == NULL)
+         return PRINT_UNKNOWN;
+
        /* Normal case.  Call the breakpoint's print_it method, or
           print_it_typical.  */
-       /* FIXME: how breakpoint can ever be NULL here?  */
-       if (b != NULL && b->ops != NULL && b->ops->print_it != NULL)
+       if (b->ops != NULL && b->ops->print_it != NULL)
          return b->ops->print_it (b);
        else
          return print_it_typical (bs);
@@ -3745,7 +3809,8 @@ watchpoint_check (void *p)
          (uiout, "reason", async_reason_lookup (EXEC_ASYNC_WATCHPOINT_SCOPE));
       ui_out_text (uiout, "\nWatchpoint ");
       ui_out_field_int (uiout, "wpnum", b->number);
-      ui_out_text (uiout, " deleted because the program has left the block in\n\
+      ui_out_text (uiout,
+                  " deleted because the program has left the block in\n\
 which its expression is valid.\n");     
 
       if (b->related_breakpoint)
@@ -3859,8 +3924,9 @@ bpstat_check_watchpoint (bpstat bs)
       
       if (must_check_value)
        {
-         char *message = xstrprintf ("Error evaluating expression for watchpoint %d\n",
-                                     b->number);
+         char *message
+           = xstrprintf ("Error evaluating expression for watchpoint %d\n",
+                         b->number);
          struct cleanup *cleanups = make_cleanup (xfree, message);
          int e = catch_errors (watchpoint_check, bs, message,
                                RETURN_MASK_ALL);
@@ -4498,12 +4564,40 @@ bpstat_causes_stop (bpstat bs)
 
 \f
 
+/* Compute a string of spaces suitable to indent the next line
+   so it starts at the position corresponding to the table column
+   named COL_NAME in the currently active table of UIOUT.  */
+
+static char *
+wrap_indent_at_field (struct ui_out *uiout, const char *col_name)
+{
+  static char wrap_indent[80];
+  int i, total_width, width, align;
+  char *text;
+
+  total_width = 0;
+  for (i = 1; ui_out_query_field (uiout, i, &width, &align, &text); i++)
+    {
+      if (strcmp (text, col_name) == 0)
+       {
+         gdb_assert (total_width < sizeof wrap_indent);
+         memset (wrap_indent, ' ', total_width);
+         wrap_indent[total_width] = 0;
+
+         return wrap_indent;
+       }
+
+      total_width += width + 1;
+    }
+
+  return NULL;
+}
+
 /* Print the LOC location out of the list of B->LOC locations.  */
 
-static void print_breakpoint_location (struct breakpoint *b,
-                                      struct bp_location *loc,
-                                      char *wrap_indent,
-                                      struct ui_stream *stb)
+static void
+print_breakpoint_location (struct breakpoint *b,
+                          struct bp_location *loc)
 {
   struct cleanup *old_chain = save_current_program_space ();
 
@@ -4522,8 +4616,9 @@ static void print_breakpoint_location (struct breakpoint *b,
          ui_out_text (uiout, "in ");
          ui_out_field_string (uiout, "func",
                               SYMBOL_PRINT_NAME (sym));
-         ui_out_wrap_hint (uiout, wrap_indent);
-         ui_out_text (uiout, " at ");
+         ui_out_text (uiout, " ");
+         ui_out_wrap_hint (uiout, wrap_indent_at_field (uiout, "what"));
+         ui_out_text (uiout, "at ");
        }
       ui_out_field_string (uiout, "file", b->source_file);
       ui_out_text (uiout, ":");
@@ -4541,9 +4636,14 @@ static void print_breakpoint_location (struct breakpoint *b,
     }
   else if (loc)
     {
+      struct ui_stream *stb = ui_out_stream_new (uiout);
+      struct cleanup *stb_chain = make_cleanup_ui_out_stream_delete (stb);
+
       print_address_symbolic (loc->gdbarch, loc->address, stb->stream,
                              demangle, "");
       ui_out_field_stream (uiout, "at", stb);
+
+      do_cleanups (stb_chain);
     }
   else
     ui_out_field_string (uiout, "pending", b->addr_string);
@@ -4607,14 +4707,10 @@ print_one_breakpoint_location (struct breakpoint *b,
                               struct bp_location *loc,
                               int loc_number,
                               struct bp_location **last_loc,
-                              int print_address_bits,
                               int allflag)
 {
   struct command_line *l;
   static char bpenables[] = "nynny";
-  char wrap_indent[80];
-  struct ui_stream *stb = ui_out_stream_new (uiout);
-  struct cleanup *old_chain = make_cleanup_ui_out_stream_delete (stb);
   struct cleanup *bkpt_chain;
 
   int header_of_multiple = 0;
@@ -4676,15 +4772,6 @@ print_one_breakpoint_location (struct breakpoint *b,
 
   
   /* 5 and 6 */
-  strcpy (wrap_indent, "                           ");
-  if (opts.addressprint)
-    {
-      if (print_address_bits <= 32)
-       strcat (wrap_indent, "           ");
-      else
-       strcat (wrap_indent, "                   ");
-    }
-
   if (b->ops != NULL && b->ops->print_one != NULL)
     {
       /* Although the print_one can possibly print all locations,
@@ -4749,7 +4836,7 @@ print_one_breakpoint_location (struct breakpoint *b,
          }
        annotate_field (5);
        if (!header_of_multiple)
-         print_breakpoint_location (b, loc, wrap_indent, stb);
+         print_breakpoint_location (b, loc);
        if (b->loc)
          *last_loc = b->loc;
        break;
@@ -4905,17 +4992,14 @@ print_one_breakpoint_location (struct breakpoint *b,
     }
        
   do_cleanups (bkpt_chain);
-  do_cleanups (old_chain);
 }
 
 static void
 print_one_breakpoint (struct breakpoint *b,
                      struct bp_location **last_loc, 
-                     int print_address_bits,
                      int allflag)
 {
-  print_one_breakpoint_location (b, NULL, 0, last_loc,
-                                print_address_bits, allflag);
+  print_one_breakpoint_location (b, NULL, 0, last_loc, allflag);
 
   /* If this breakpoint has custom print function,
      it's already printed.  Otherwise, print individual
@@ -4928,7 +5012,7 @@ print_one_breakpoint (struct breakpoint *b,
         situation.
 
         Note that while hardware watchpoints have several locations
-        internally, that's no a property exposed to user.  */
+        internally, that's not a property exposed to user.  */
       if (b->loc 
          && !is_hardware_watchpoint (b)
          && (b->loc->next || !b->loc->enabled)
@@ -4937,8 +5021,7 @@ print_one_breakpoint (struct breakpoint *b,
          struct bp_location *loc;
          int n = 1;
          for (loc = b->loc; loc; loc = loc->next, ++n)
-           print_one_breakpoint_location (b, loc, n, last_loc,
-                                          print_address_bits, allflag);
+           print_one_breakpoint_location (b, loc, n, last_loc, allflag);
        }
     }
 }
@@ -4982,9 +5065,7 @@ do_captured_breakpoint_query (struct ui_out *uiout, void *data)
     {
       if (args->bnum == b->number)
        {
-         int print_address_bits = breakpoint_address_bits (b);
-
-         print_one_breakpoint (b, &dummy_loc, print_address_bits, 0);
+         print_one_breakpoint (b, &dummy_loc, 0);
          return GDB_RC_OK;
        }
     }
@@ -5020,6 +5101,15 @@ user_settable_breakpoint (const struct breakpoint *b)
          || is_watchpoint (b));
 }
 
+/* Return true if this breakpoint was set by the user, false if it is
+   internal or momentary.  */
+
+int
+user_breakpoint_p (struct breakpoint *b)
+{
+  return user_settable_breakpoint (b) && b->number > 0;
+}
+
 /* Print information on user settable breakpoint (watchpoint, etc)
    number BNUM.  If BNUM is -1 print all user-settable breakpoints.
    If ALLFLAG is non-zero, include non-user-settable breakpoints.  If
@@ -5028,7 +5118,7 @@ user_settable_breakpoint (const struct breakpoint *b)
    breakpoints listed.  */
 
 static int
-breakpoint_1 (int bnum, int allflag, 
+breakpoint_1 (char *args, int allflag, 
              int (*filter) (const struct breakpoint *))
 {
   struct breakpoint *b;
@@ -5045,37 +5135,46 @@ breakpoint_1 (int bnum, int allflag,
      required for address fields.  */
   nr_printable_breakpoints = 0;
   ALL_BREAKPOINTS (b)
-    if (bnum == -1
-       || bnum == b->number)
-      {
-       /* If we have a filter, only list the breakpoints it accepts.  */
-       if (filter && !filter (b))
-         continue;
-       
-       if (allflag || (user_settable_breakpoint (b)
-                       && b->number > 0))
-         {
-           int addr_bit, type_len;
+    {
+      /* If we have a filter, only list the breakpoints it accepts.  */
+      if (filter && !filter (b))
+       continue;
 
-           addr_bit = breakpoint_address_bits (b);
-           if (addr_bit > print_address_bits)
-             print_address_bits = addr_bit;
+      /* If we have an "args" string, it is a list of breakpoints to 
+        accept.  Skip the others.  */
+      if (args != NULL && *args != '\0')
+       {
+         if (allflag && parse_and_eval_long (args) != b->number)
+           continue;
+         if (!allflag && !number_is_in_list (args, b->number))
+           continue;
+       }
 
-           type_len = strlen (bptype_string (b->type));
-           if (type_len > print_type_col_width)
-             print_type_col_width = type_len;
+      if (allflag || user_breakpoint_p (b))
+       {
+         int addr_bit, type_len;
 
-           nr_printable_breakpoints++;
-         }
-      }
+         addr_bit = breakpoint_address_bits (b);
+         if (addr_bit > print_address_bits)
+           print_address_bits = addr_bit;
+
+         type_len = strlen (bptype_string (b->type));
+         if (type_len > print_type_col_width)
+           print_type_col_width = type_len;
+
+         nr_printable_breakpoints++;
+       }
+    }
 
   if (opts.addressprint)
     bkpttbl_chain 
-      = make_cleanup_ui_out_table_begin_end (uiout, 6, nr_printable_breakpoints,
+      = make_cleanup_ui_out_table_begin_end (uiout, 6,
+                                            nr_printable_breakpoints,
                                              "BreakpointTable");
   else
     bkpttbl_chain 
-      = make_cleanup_ui_out_table_begin_end (uiout, 5, nr_printable_breakpoints,
+      = make_cleanup_ui_out_table_begin_end (uiout, 5,
+                                            nr_printable_breakpoints,
                                              "BreakpointTable");
 
   if (nr_printable_breakpoints > 0)
@@ -5094,16 +5193,16 @@ breakpoint_1 (int bnum, int allflag,
     annotate_field (3);
   ui_out_table_header (uiout, 3, ui_left, "enabled", "Enb");   /* 4 */
   if (opts.addressprint)
-       {
-         if (nr_printable_breakpoints > 0)
-           annotate_field (4);
-         if (print_address_bits <= 32)
-           ui_out_table_header (uiout, 10, ui_left, 
-                                "addr", "Address");            /* 5 */
-         else
-           ui_out_table_header (uiout, 18, ui_left, 
-                                "addr", "Address");            /* 5 */
-       }
+    {
+      if (nr_printable_breakpoints > 0)
+       annotate_field (4);
+      if (print_address_bits <= 32)
+       ui_out_table_header (uiout, 10, ui_left, 
+                            "addr", "Address");                /* 5 */
+      else
+       ui_out_table_header (uiout, 18, ui_left, 
+                            "addr", "Address");                /* 5 */
+    }
   if (nr_printable_breakpoints > 0)
     annotate_field (5);
   ui_out_table_header (uiout, 40, ui_noalign, "what", "What"); /* 6 */
@@ -5112,23 +5211,34 @@ breakpoint_1 (int bnum, int allflag,
     annotate_breakpoints_table ();
 
   ALL_BREAKPOINTS (b)
-  {
-    QUIT;
-    if (bnum == -1
-       || bnum == b->number)
-      {
-       /* If we have a filter, only list the breakpoints it accepts.  */
-       if (filter && !filter (b))
-         continue;
-       
-       /* We only print out user settable breakpoints unless the
-          allflag is set.  */
-       if (allflag || (user_settable_breakpoint (b)
-                       && b->number > 0))
-         print_one_breakpoint (b, &last_loc, print_address_bits, allflag);
-      }
-  }
-  
+    {
+      QUIT;
+      /* If we have a filter, only list the breakpoints it accepts.  */
+      if (filter && !filter (b))
+       continue;
+
+      /* If we have an "args" string, it is a list of breakpoints to 
+        accept.  Skip the others.  */
+
+      if (args != NULL && *args != '\0')
+       {
+         if (allflag)  /* maintenance info breakpoint */
+           {
+             if (parse_and_eval_long (args) != b->number)
+               continue;
+           }
+         else          /* all others */
+           {
+             if (!number_is_in_list (args, b->number))
+               continue;
+           }
+       }
+      /* We only print out user settable breakpoints unless the
+        allflag is set.  */
+      if (allflag || user_breakpoint_p (b))
+       print_one_breakpoint (b, &last_loc, allflag);
+    }
+
   do_cleanups (bkpttbl_chain);
 
   if (nr_printable_breakpoints == 0)
@@ -5137,12 +5247,12 @@ breakpoint_1 (int bnum, int allflag,
         empty list.  */
       if (!filter)
        {
-         if (bnum == -1)
+         if (args == NULL || *args == '\0')
            ui_out_message (uiout, 0, "No breakpoints or watchpoints.\n");
          else
            ui_out_message (uiout, 0, 
-                           "No breakpoint or watchpoint number %d.\n",
-                           bnum);
+                           "No breakpoint or watchpoint matching '%s'.\n",
+                           args);
        }
     }
   else
@@ -5178,46 +5288,31 @@ default_collect_info (void)
 }
   
 static void
-breakpoints_info (char *bnum_exp, int from_tty)
+breakpoints_info (char *args, int from_tty)
 {
-  int bnum = -1;
-
-  if (bnum_exp)
-    bnum = parse_and_eval_long (bnum_exp);
-
-  breakpoint_1 (bnum, 0, NULL);
+  breakpoint_1 (args, 0, NULL);
 
   default_collect_info ();
 }
 
 static void
-watchpoints_info (char *wpnum_exp, int from_tty)
+watchpoints_info (char *args, int from_tty)
 {
-  int wpnum = -1, num_printed;
-
-  if (wpnum_exp)
-    wpnum = parse_and_eval_long (wpnum_exp);
-
-  num_printed = breakpoint_1 (wpnum, 0, is_watchpoint);
+  int num_printed = breakpoint_1 (args, 0, is_watchpoint);
 
   if (num_printed == 0)
     {
-      if (wpnum == -1)
+      if (args == NULL || *args == '\0')
        ui_out_message (uiout, 0, "No watchpoints.\n");
       else
-       ui_out_message (uiout, 0, "No watchpoint number %d.\n", wpnum);
+       ui_out_message (uiout, 0, "No watchpoint matching '%s'.\n", args);
     }
 }
 
 static void
-maintenance_info_breakpoints (char *bnum_exp, int from_tty)
+maintenance_info_breakpoints (char *args, int from_tty)
 {
-  int bnum = -1;
-
-  if (bnum_exp)
-    bnum = parse_and_eval_long (bnum_exp);
-
-  breakpoint_1 (bnum, 1, NULL);
+  breakpoint_1 (args, 1, NULL);
 
   default_collect_info ();
 }
@@ -5408,8 +5503,10 @@ static void
 breakpoint_adjustment_warning (CORE_ADDR from_addr, CORE_ADDR to_addr,
                                int bnum, int have_bnum)
 {
-  char astr1[40];
-  char astr2[40];
+  /* The longest string possibly returned by hex_string_custom
+     is 50 chars.  These must be at least that big for safety.  */
+  char astr1[64];
+  char astr2[64];
 
   strcpy (astr1, hex_string_custom ((unsigned long) from_addr, 8));
   strcpy (astr2, hex_string_custom ((unsigned long) to_addr, 8));
@@ -5865,6 +5962,19 @@ create_jit_event_breakpoint (struct gdbarch *gdbarch, CORE_ADDR address)
   return b;
 }
 
+/* Remove JIT code registration and unregistration breakpoint(s).  */
+
+void
+remove_jit_event_breakpoints (void)
+{
+  struct breakpoint *b, *b_tmp;
+
+  ALL_BREAKPOINTS_SAFE (b, b_tmp)
+    if (b->type == bp_jit_event
+       && b->loc->pspace == current_program_space)
+      delete_breakpoint (b);
+}
+
 void
 remove_solib_event_breakpoints (void)
 {
@@ -5962,7 +6072,8 @@ disable_breakpoints_in_unloaded_shlib (struct so_list *solib)
        if (!disabled_shlib_breaks)
          {
            target_terminal_ours_for_output ();
-           warning (_("Temporarily disabling breakpoints for unloaded shared library \"%s\""),
+           warning (_("Temporarily disabling breakpoints "
+                      "for unloaded shared library \"%s\""),
                     solib->so_name);
          }
        disabled_shlib_breaks = 1;
@@ -5975,17 +6086,17 @@ disable_breakpoints_in_unloaded_shlib (struct so_list *solib)
 /* Implement the "insert" breakpoint_ops method for fork
    catchpoints.  */
 
-static void
-insert_catch_fork (struct breakpoint *b)
+static int
+insert_catch_fork (struct bp_location *bl)
 {
-  target_insert_fork_catchpoint (PIDGET (inferior_ptid));
+  return target_insert_fork_catchpoint (PIDGET (inferior_ptid));
 }
 
 /* Implement the "remove" breakpoint_ops method for fork
    catchpoints.  */
 
 static int
-remove_catch_fork (struct breakpoint *b)
+remove_catch_fork (struct bp_location *bl)
 {
   return target_remove_fork_catchpoint (PIDGET (inferior_ptid));
 }
@@ -6062,6 +6173,7 @@ static struct breakpoint_ops catch_fork_breakpoint_ops =
   insert_catch_fork,
   remove_catch_fork,
   breakpoint_hit_catch_fork,
+  NULL, /* resources_needed */
   print_it_catch_fork,
   print_one_catch_fork,
   print_mention_catch_fork,
@@ -6071,17 +6183,17 @@ static struct breakpoint_ops catch_fork_breakpoint_ops =
 /* Implement the "insert" breakpoint_ops method for vfork
    catchpoints.  */
 
-static void
-insert_catch_vfork (struct breakpoint *b)
+static int
+insert_catch_vfork (struct bp_location *bl)
 {
-  target_insert_vfork_catchpoint (PIDGET (inferior_ptid));
+  return target_insert_vfork_catchpoint (PIDGET (inferior_ptid));
 }
 
 /* Implement the "remove" breakpoint_ops method for vfork
    catchpoints.  */
 
 static int
-remove_catch_vfork (struct breakpoint *b)
+remove_catch_vfork (struct bp_location *bl)
 {
   return target_remove_vfork_catchpoint (PIDGET (inferior_ptid));
 }
@@ -6157,6 +6269,7 @@ static struct breakpoint_ops catch_vfork_breakpoint_ops =
   insert_catch_vfork,
   remove_catch_vfork,
   breakpoint_hit_catch_vfork,
+  NULL, /* resources_needed */
   print_it_catch_vfork,
   print_one_catch_vfork,
   print_mention_catch_vfork,
@@ -6166,20 +6279,20 @@ static struct breakpoint_ops catch_vfork_breakpoint_ops =
 /* Implement the "insert" breakpoint_ops method for syscall
    catchpoints.  */
 
-static void
-insert_catch_syscall (struct breakpoint *b)
+static int
+insert_catch_syscall (struct bp_location *bl)
 {
   struct inferior *inf = current_inferior ();
 
   ++inf->total_syscalls_count;
-  if (!b->syscalls_to_be_caught)
+  if (!bl->owner->syscalls_to_be_caught)
     ++inf->any_syscall_count;
   else
     {
       int i, iter;
 
       for (i = 0;
-           VEC_iterate (int, b->syscalls_to_be_caught, i, iter);
+           VEC_iterate (int, bl->owner->syscalls_to_be_caught, i, iter);
            i++)
        {
           int elem;
@@ -6187,7 +6300,8 @@ insert_catch_syscall (struct breakpoint *b)
          if (iter >= VEC_length (int, inf->syscalls_counts))
            {
               int old_size = VEC_length (int, inf->syscalls_counts);
-              uintptr_t vec_addr_offset = old_size * ((uintptr_t) sizeof (int));
+              uintptr_t vec_addr_offset
+               = old_size * ((uintptr_t) sizeof (int));
               uintptr_t vec_addr;
               VEC_safe_grow (int, inf->syscalls_counts, iter + 1);
               vec_addr = (uintptr_t) VEC_address (int, inf->syscalls_counts) +
@@ -6200,30 +6314,30 @@ insert_catch_syscall (struct breakpoint *b)
        }
     }
 
-  target_set_syscall_catchpoint (PIDGET (inferior_ptid),
-                                inf->total_syscalls_count != 0,
-                                inf->any_syscall_count,
-                                VEC_length (int, inf->syscalls_counts),
-                                VEC_address (int, inf->syscalls_counts));
+  return target_set_syscall_catchpoint (PIDGET (inferior_ptid),
+                                       inf->total_syscalls_count != 0,
+                                       inf->any_syscall_count,
+                                       VEC_length (int, inf->syscalls_counts),
+                                       VEC_address (int, inf->syscalls_counts));
 }
 
 /* Implement the "remove" breakpoint_ops method for syscall
    catchpoints.  */
 
 static int
-remove_catch_syscall (struct breakpoint *b)
+remove_catch_syscall (struct bp_location *bl)
 {
   struct inferior *inf = current_inferior ();
 
   --inf->total_syscalls_count;
-  if (!b->syscalls_to_be_caught)
+  if (!bl->owner->syscalls_to_be_caught)
     --inf->any_syscall_count;
   else
     {
       int i, iter;
 
       for (i = 0;
-           VEC_iterate (int, b->syscalls_to_be_caught, i, iter);
+           VEC_iterate (int, bl->owner->syscalls_to_be_caught, i, iter);
            i++)
        {
           int elem;
@@ -6239,7 +6353,8 @@ remove_catch_syscall (struct breakpoint *b)
                                        inf->total_syscalls_count != 0,
                                        inf->any_syscall_count,
                                        VEC_length (int, inf->syscalls_counts),
-                                       VEC_address (int, inf->syscalls_counts));
+                                       VEC_address (int,
+                                                    inf->syscalls_counts));
 }
 
 /* Implement the "breakpoint_hit" breakpoint_ops method for syscall
@@ -6438,6 +6553,7 @@ static struct breakpoint_ops catch_syscall_breakpoint_ops =
   insert_catch_syscall,
   remove_catch_syscall,
   breakpoint_hit_catch_syscall,
+  NULL, /* resources_needed */
   print_it_catch_syscall,
   print_one_catch_syscall,
   print_mention_catch_syscall,
@@ -6522,14 +6638,14 @@ create_fork_vfork_event_catchpoint (struct gdbarch *gdbarch,
 
 /* Exec catchpoints.  */
 
-static void
-insert_catch_exec (struct breakpoint *b)
+static int
+insert_catch_exec (struct bp_location *bl)
 {
-  target_insert_exec_catchpoint (PIDGET (inferior_ptid));
+  return target_insert_exec_catchpoint (PIDGET (inferior_ptid));
 }
 
 static int
-remove_catch_exec (struct breakpoint *b)
+remove_catch_exec (struct bp_location *bl)
 {
   return target_remove_exec_catchpoint (PIDGET (inferior_ptid));
 }
@@ -6591,6 +6707,7 @@ static struct breakpoint_ops catch_exec_breakpoint_ops =
   insert_catch_exec,
   remove_catch_exec,
   breakpoint_hit_catch_exec,
+  NULL, /* resources_needed */
   print_it_catch_exec,
   print_one_catch_exec,
   print_mention_catch_exec,
@@ -6631,20 +6748,30 @@ hw_breakpoint_used_count (void)
 static int
 hw_watchpoint_used_count (enum bptype type, int *other_type_used)
 {
-  struct breakpoint *b;
   int i = 0;
+  struct breakpoint *b;
+  struct bp_location *bl;
 
   *other_type_used = 0;
   ALL_BREAKPOINTS (b)
-  {
-    if (breakpoint_enabled (b))
-      {
+    {
+      if (!breakpoint_enabled (b))
+       continue;
+
        if (b->type == type)
-         i++;
+         for (bl = b->loc; bl; bl = bl->next)
+           {
+             /* Special types of hardware watchpoints may use more than
+                one register.  */
+             if (b->ops && b->ops->resources_needed)
+               i += b->ops->resources_needed (bl);
+             else
+               i++;
+           }
        else if (is_hardware_watchpoint (b))
          *other_type_used = 1;
-      }
-  }
+    }
+
   return i;
 }
 
@@ -6839,7 +6966,8 @@ mention (struct breakpoint *b)
     switch (b->type)
       {
       case bp_none:
-       printf_filtered (_("(apparently deleted?) Eventpoint %d: "), b->number);
+       printf_filtered (_("(apparently deleted?) Eventpoint %d: "),
+                        b->number);
        break;
       case bp_watchpoint:
        ui_out_text (uiout, "Watchpoint ");
@@ -7122,17 +7250,15 @@ create_breakpoint_sal (struct gdbarch *gdbarch,
                  char *marker_str;
                  int i;
 
-                 while (*p == ' ' || *p == '\t')
-                   p++;
+                 p = skip_spaces (p);
 
-                 endp = p;
-                 while (*endp != ' ' && *endp != '\t' && *endp != '\0')
-                   endp++;
+                 endp = skip_to_space (p);
 
                  marker_str = savestring (p, endp - p);
                  b->static_trace_marker_id = marker_str;
 
-                 printf_filtered (_("Probed static tracepoint marker \"%s\"\n"),
+                 printf_filtered (_("Probed static tracepoint "
+                                    "marker \"%s\"\n"),
                                   b->static_trace_marker_id);
                }
              else if (target_static_tracepoint_marker_at (sal.pc, &marker))
@@ -7140,12 +7266,13 @@ create_breakpoint_sal (struct gdbarch *gdbarch,
                  b->static_trace_marker_id = xstrdup (marker.str_id);
                  release_static_tracepoint_marker (&marker);
 
-                 printf_filtered (_("Probed static tracepoint marker \"%s\"\n"),
+                 printf_filtered (_("Probed static tracepoint "
+                                    "marker \"%s\"\n"),
                                   b->static_trace_marker_id);
                }
              else
-               warning (_("\
-Couldn't determine the static tracepoint marker to probe"));
+               warning (_("Couldn't determine the static "
+                          "tracepoint marker to probe"));
            }
 
          if (enabled && b->pspace->executing_startup
@@ -7359,10 +7486,13 @@ create_breakpoints_sal (struct gdbarch *gdbarch,
     }
 }
 
-/* Parse ARG which is assumed to be a SAL specification possibly
+/* Parse ADDRESS which is assumed to be a SAL specification possibly
    followed by conditionals.  On return, SALS contains an array of SAL
    addresses found.  ADDR_STRING contains a vector of (canonical)
-   address strings.  ARG points to the end of the SAL.  */
+   address strings.  ADDRESS points to the end of the SAL.
+
+   The array and the line spec strings are allocated on the heap, it is
+   the caller's responsibility to free them.  */
 
 static void
 parse_breakpoint_sals (char **address,
@@ -7517,13 +7647,9 @@ find_condition_and_thread (char *tok, CORE_ADDR pc,
       char *cond_start = NULL;
       char *cond_end = NULL;
 
-      while (*tok == ' ' || *tok == '\t')
-       tok++;
+      tok = skip_spaces (tok);
       
-      end_tok = tok;
-      
-      while (*end_tok != ' ' && *end_tok != '\t' && *end_tok != '\000')
-       end_tok++;
+      end_tok = skip_to_space (tok);
       
       toklen = end_tok - tok;
       
@@ -7582,12 +7708,9 @@ decode_static_tracepoint_spec (char **arg_p)
   char *marker_str;
   int i;
 
-  while (*p == ' ' || *p == '\t')
-    p++;
+  p = skip_spaces (p);
 
-  endp = p;
-  while (*endp != ' ' && *endp != '\t' && *endp != '\0')
-    endp++;
+  endp = skip_to_space (p);
 
   marker_str = savestring (p, endp - p);
   old_chain = make_cleanup (xfree, marker_str);
@@ -7701,7 +7824,8 @@ create_breakpoint (struct gdbarch *gdbarch,
           /* If pending breakpoint support is auto query and the user
             selects no, then simply return the error code.  */
          if (pending_break_support == AUTO_BOOLEAN_AUTO
-             && !nquery (_("Make breakpoint pending on future shared library load? ")))
+             && !nquery (_("Make breakpoint pending on "
+                           "future shared library load? ")))
            return 0;
 
          /* At this point, either the user was queried about setting
@@ -7718,6 +7842,7 @@ create_breakpoint (struct gdbarch *gdbarch,
        default:
          throw_exception (e);
        }
+      break;
     default:
       if (!sals.nelts)
        return 0;
@@ -7836,7 +7961,8 @@ create_breakpoint (struct gdbarch *gdbarch,
        }
       else
        create_breakpoints_sal (gdbarch, sals, addr_string, cond_string,
-                               type_wanted, tempflag ? disp_del : disp_donttouch,
+                               type_wanted,
+                               tempflag ? disp_del : disp_donttouch,
                                thread, task, ignore_count, ops, from_tty,
                                enabled, internal);
     }
@@ -7874,8 +8000,8 @@ create_breakpoint (struct gdbarch *gdbarch,
   
   if (sals.nelts > 1)
     {
-      warning (_("Multiple breakpoints were set.\n"
-                "Use the \"delete\" command to delete unwanted breakpoints."));
+      warning (_("Multiple breakpoints were set.\nUse the "
+                "\"delete\" command to delete unwanted breakpoints."));
       prev_breakpoint_count = prev_bkpt_count;
     }
 
@@ -8182,6 +8308,53 @@ watchpoint_exp_is_const (const struct expression *exp)
   return 1;
 }
 
+/* Implement the "insert" breakpoint_ops method for hardware watchpoints.  */
+
+static int
+insert_watchpoint (struct bp_location *bl)
+{
+  int length = bl->owner->exact? 1 : bl->length;
+
+  return target_insert_watchpoint (bl->address, length, bl->watchpoint_type,
+                                  bl->owner->cond_exp);
+}
+
+/* Implement the "remove" breakpoint_ops method for hardware watchpoints.  */
+
+static int
+remove_watchpoint (struct bp_location *bl)
+{
+  int length = bl->owner->exact? 1 : bl->length;
+
+  return target_remove_watchpoint (bl->address, length, bl->watchpoint_type,
+                                  bl->owner->cond_exp);
+}
+
+/* Implement the "resources_needed" breakpoint_ops method for
+   hardware watchpoints.  */
+
+static int
+resources_needed_watchpoint (const struct bp_location *bl)
+{
+  int length = bl->owner->exact? 1 : bl->length;
+
+  return target_region_ok_for_hw_watchpoint (bl->address, length);
+}
+
+/* The breakpoint_ops structure to be used in hardware watchpoints.  */
+
+static struct breakpoint_ops watchpoint_breakpoint_ops =
+{
+  insert_watchpoint,
+  remove_watchpoint,
+  NULL, /* breakpoint_hit */
+  resources_needed_watchpoint,
+  NULL, /* print_it */
+  NULL, /* print_one */
+  NULL, /* print_mention */
+  NULL  /* print_recreate */
+};
+
 /* accessflag:  hw_write:  watch write, 
                 hw_read:   watch read, 
                hw_access: watch access (read or write) */
@@ -8202,7 +8375,7 @@ watch_command_1 (char *arg, int accessflag, int from_tty,
   char *cond_end = NULL;
   int i, other_type_used, target_resources_ok = 0;
   enum bptype bp_type;
-  int mem_cnt = 0;
+  int reg_cnt = 0;
   int thread = -1;
   int pc = 0;
 
@@ -8303,13 +8476,8 @@ watch_command_1 (char *arg, int accessflag, int from_tty,
   else if (val != NULL)
     release_value (val);
 
-  tok = arg;
-  while (*tok == ' ' || *tok == '\t')
-    tok++;
-  end_tok = tok;
-
-  while (*end_tok != ' ' && *end_tok != '\t' && *end_tok != '\000')
-    end_tok++;
+  tok = skip_spaces (arg);
+  end_tok = skip_to_space (tok);
 
   toklen = end_tok - tok;
   if (toklen >= 1 && strncmp (tok, "if", toklen) == 0)
@@ -8337,25 +8505,26 @@ watch_command_1 (char *arg, int accessflag, int from_tty,
   else
     bp_type = bp_hardware_watchpoint;
 
-  mem_cnt = can_use_hardware_watchpoint (val);
-  if (mem_cnt == 0 && bp_type != bp_hardware_watchpoint)
+  reg_cnt = can_use_hardware_watchpoint (val, target_exact_watchpoints);
+  if (reg_cnt == 0 && bp_type != bp_hardware_watchpoint)
     error (_("Expression cannot be implemented with read/access watchpoint."));
-  if (mem_cnt != 0)
+  if (reg_cnt != 0)
     {
       i = hw_watchpoint_used_count (bp_type, &other_type_used);
       target_resources_ok = 
-       target_can_use_hardware_watchpoint (bp_type, i + mem_cnt, 
+       target_can_use_hardware_watchpoint (bp_type, i + reg_cnt,
                                            other_type_used);
       if (target_resources_ok == 0 && bp_type != bp_hardware_watchpoint)
        error (_("Target does not support this type of hardware watchpoint."));
 
       if (target_resources_ok < 0 && bp_type != bp_hardware_watchpoint)
-       error (_("Target can only support one kind of HW watchpoint at a time."));
+       error (_("Target can only support one kind "
+                "of HW watchpoint at a time."));
     }
 
   /* Change the type of breakpoint to an ordinary watchpoint if a
      hardware watchpoint could not be set.  */
-  if (!mem_cnt || target_resources_ok <= 0)
+  if (!reg_cnt || target_resources_ok <= 0)
     bp_type = bp_watchpoint;
 
   frame = block_innermost_frame (exp_valid_block);
@@ -8424,6 +8593,12 @@ watch_command_1 (char *arg, int accessflag, int from_tty,
     b->exp_string = savestring (exp_start, exp_end - exp_start);
   b->val = val;
   b->val_valid = 1;
+  b->ops = &watchpoint_breakpoint_ops;
+
+  /* Use an exact watchpoint when there's only one memory region to be
+     watched, and only one debug register is needed to watch it.  */
+  b->exact = target_exact_watchpoints && reg_cnt == 1;
+
   if (cond_start)
     b->cond_string = savestring (cond_start, cond_end - cond_start);
   else
@@ -8463,12 +8638,15 @@ watch_command_1 (char *arg, int accessflag, int from_tty,
   update_global_location_list (1);
 }
 
-/* Return count of locations need to be watched and can be handled in
-   hardware.  If the watchpoint can not be handled in hardware return
-   zero.  */
+/* Return count of debug registers needed to watch the given expression.
+   If EXACT_WATCHPOINTS is 1, then consider that only the address of
+   the start of the watched region will be monitored (i.e., all accesses
+   will be aligned).  This uses less debug registers on some targets.
+
+   If the watchpoint cannot be handled in hardware return zero.  */
 
 static int
-can_use_hardware_watchpoint (struct value *v)
+can_use_hardware_watchpoint (struct value *v, int exact_watchpoints)
 {
   int found_memory_cnt = 0;
   struct value *head = v;
@@ -8521,12 +8699,18 @@ can_use_hardware_watchpoint (struct value *v)
                      && TYPE_CODE (vtype) != TYPE_CODE_ARRAY))
                {
                  CORE_ADDR vaddr = value_address (v);
-                 int       len   = TYPE_LENGTH (value_type (v));
+                 int len;
+                 int num_regs;
+
+                 len = (exact_watchpoints
+                        && is_scalar_type_recursive (vtype))?
+                   1 : TYPE_LENGTH (value_type (v));
 
-                 if (!target_region_ok_for_hw_watchpoint (vaddr, len))
+                 num_regs = target_region_ok_for_hw_watchpoint (vaddr, len);
+                 if (!num_regs)
                    return 0;
                  else
-                   found_memory_cnt++;
+                   found_memory_cnt += num_regs;
                }
            }
        }
@@ -8577,7 +8761,7 @@ watch_maybe_just_location (char *arg, int accessflag, int from_tty)
       && (check_for_argument (&arg, "-location", sizeof ("-location") - 1)
          || check_for_argument (&arg, "-l", sizeof ("-l") - 1)))
     {
-      ep_skip_leading_whitespace (&arg);
+      arg = skip_spaces (arg);
       just_location = 1;
     }
 
@@ -8734,15 +8918,6 @@ until_break_command (char *arg, int from_tty, int anywhere)
     do_cleanups (old_chain);
 }
 
-static void
-ep_skip_leading_whitespace (char **s)
-{
-  if ((s == NULL) || (*s == NULL))
-    return;
-  while (isspace (**s))
-    *s += 1;
-}
-
 /* This function attempts to parse an optional "if <cond>" clause
    from the arg string.  If one is not found, it returns NULL.
 
@@ -8764,7 +8939,7 @@ ep_parse_optional_if_clause (char **arg)
 
   /* Skip any extra leading whitespace, and record the start of the
      condition string.  */
-  ep_skip_leading_whitespace (arg);
+  *arg = skip_spaces (*arg);
   cond_string = *arg;
 
   /* Assume that the condition occupies the remainder of the arg
@@ -8799,7 +8974,7 @@ catch_fork_command_1 (char *arg, int from_tty,
 
   if (!arg)
     arg = "";
-  ep_skip_leading_whitespace (&arg);
+  arg = skip_spaces (arg);
 
   /* The allowed syntax is:
      catch [v]fork
@@ -8843,7 +9018,7 @@ catch_exec_command_1 (char *arg, int from_tty,
 
   if (!arg)
     arg = "";
-  ep_skip_leading_whitespace (&arg);
+  arg = skip_spaces (arg);
 
   /* The allowed syntax is:
      catch exec
@@ -8952,6 +9127,7 @@ static struct breakpoint_ops gnu_v3_exception_catchpoint_ops = {
   NULL, /* insert */
   NULL, /* remove */
   NULL, /* breakpoint_hit */
+  NULL, /* resources_needed */
   print_exception_catchpoint,
   print_one_exception_catchpoint,
   print_mention_exception_catchpoint,
@@ -8992,7 +9168,7 @@ catch_exception_command_1 (enum exception_event_kind ex_event, char *arg,
 
   if (!arg)
     arg = "";
-  ep_skip_leading_whitespace (&arg);
+  arg = skip_spaces (arg);
 
   cond_string = ep_parse_optional_if_clause (&arg);
 
@@ -9178,11 +9354,11 @@ catch_syscall_command_1 (char *arg, int from_tty,
   /* Checking if the feature if supported.  */
   if (gdbarch_get_syscall_number_p (gdbarch) == 0)
     error (_("The feature 'catch syscall' is not supported on \
-this architeture yet."));
+this architecture yet."));
 
   tempflag = get_cmd_context (command) == CATCH_TEMPORARY;
 
-  ep_skip_leading_whitespace (&arg);
+  arg = skip_spaces (arg);
 
   /* We need to do this first "dummy" translation in order
      to get the syscall XML file loaded or, most important,
@@ -9208,7 +9384,8 @@ this architeture yet."));
 /* Implement the "catch assert" command.  */
 
 static void
-catch_assert_command (char *arg, int from_tty, struct cmd_list_element *command)
+catch_assert_command (char *arg, int from_tty,
+                     struct cmd_list_element *command)
 {
   struct gdbarch *gdbarch = get_current_arch ();
   int tempflag;
@@ -9333,7 +9510,8 @@ clear_command (char *arg, int from_tty)
                                    && b->source_file != NULL
                                    && sal.symtab != NULL
                                    && sal.pspace == loc->pspace
-                                   && strcmp (b->source_file, sal.symtab->filename) == 0
+                                   && strcmp (b->source_file,
+                                              sal.symtab->filename) == 0
                                    && b->line_number == sal.line);
                  if (pc_match || line_match)
                    {
@@ -9642,7 +9820,8 @@ update_global_location_list (int should_insert)
                     Note that at this point, old_loc->owner is still
                     valid, as delete_breakpoint frees the breakpoint
                     only after calling us.  */
-                 printf_filtered (_("warning: Error removing breakpoint %d\n"), 
+                 printf_filtered (_("warning: Error removing "
+                                    "breakpoint %d\n"), 
                                   old_loc->owner->number);
                }
              removed = 1;
@@ -10221,7 +10400,8 @@ update_breakpoint_locations (struct breakpoint *b,
            }
          if (e.reason < 0)
            {
-             warning (_("failed to reevaluate condition for breakpoint %d: %s"), 
+             warning (_("failed to reevaluate condition "
+                        "for breakpoint %d: %s"), 
                       b->number, e.message);
              new_loc->enabled = 0;
            }
@@ -10348,8 +10528,8 @@ breakpoint_re_set_one (void *bint)
                error (_("marker %s not found"), b->static_trace_marker_id);
            }
          else
-           sals = decode_line_1 (&s, 1, (struct symtab *) NULL, 0, (char ***) NULL,
-                                 not_found_ptr);
+           sals = decode_line_1 (&s, 1, (struct symtab *) NULL, 0,
+                                 (char ***) NULL, not_found_ptr);
        }
       if (e.reason < 0)
        {
@@ -10520,12 +10700,9 @@ breakpoint_re_set (void)
 
   do_cleanups (old_chain);
 
-  create_overlay_event_breakpoint ("_ovly_debug_event");
-  create_longjmp_master_breakpoint ("longjmp");
-  create_longjmp_master_breakpoint ("_longjmp");
-  create_longjmp_master_breakpoint ("siglongjmp");
-  create_longjmp_master_breakpoint ("_siglongjmp");
-  create_std_terminate_master_breakpoint ("std::terminate()");
+  create_overlay_event_breakpoint ();
+  create_longjmp_master_breakpoint ();
+  create_std_terminate_master_breakpoint ();
   create_exception_master_breakpoint ();
 }
 \f
@@ -10576,13 +10753,15 @@ set_ignore_count (int bptnum, int count, int from_tty)
       if (from_tty)
        {
          if (count == 0)
-           printf_filtered (_("Will stop next time breakpoint %d is reached."),
+           printf_filtered (_("Will stop next time "
+                              "breakpoint %d is reached."),
                             bptnum);
          else if (count == 1)
            printf_filtered (_("Will ignore next crossing of breakpoint %d."),
                             bptnum);
          else
-           printf_filtered (_("Will ignore next %d crossings of breakpoint %d."),
+           printf_filtered (_("Will ignore next %d "
+                              "crossings of breakpoint %d."),
                             count, bptnum);
        }
       breakpoints_changed ();
@@ -10593,13 +10772,6 @@ set_ignore_count (int bptnum, int count, int from_tty)
   error (_("No breakpoint number %d."), bptnum);
 }
 
-void
-make_breakpoint_silent (struct breakpoint *b)
-{
-  /* Silence the breakpoint.  */
-  b->silent = 1;
-}
-
 /* Command to set ignore-count of breakpoint N to COUNT.  */
 
 static void
@@ -10632,21 +10804,23 @@ map_breakpoint_numbers (char *args, void (*function) (struct breakpoint *,
                                                      void *),
                        void *data)
 {
-  char *p = args;
-  char *p1;
   int num;
   struct breakpoint *b, *tmp;
   int match;
+  struct get_number_or_range_state state;
 
-  if (p == 0)
+  if (args == 0)
     error_no_arg (_("one or more breakpoint numbers"));
 
-  while (*p)
+  init_number_or_range (&state, args);
+
+  while (!state.finished)
     {
+      char *p = state.string;
+
       match = 0;
-      p1 = p;
 
-      num = get_number_or_range (&p1);
+      num = get_number_or_range (&state);
       if (num == 0)
        {
          warning (_("bad breakpoint number at or near '%s'"), p);
@@ -10666,7 +10840,6 @@ map_breakpoint_numbers (char *args, void (*function) (struct breakpoint *,
          if (match == 0)
            printf_unfiltered (_("No breakpoint number %d.\n"), num);
        }
-      p = p1;
     }
 }
 
@@ -10683,7 +10856,7 @@ find_location_by_number (char *number)
   *dot = '\0';
 
   p1 = number;
-  bp_num = get_number_or_range (&p1);
+  bp_num = get_number (&p1);
   if (bp_num == 0)
     error (_("Bad breakpoint number '%s'"), number);
 
@@ -10697,7 +10870,7 @@ find_location_by_number (char *number)
     error (_("Bad breakpoint number '%s'"), number);
   
   p1 = dot+1;
-  loc_num = get_number_or_range (&p1);
+  loc_num = get_number (&p1);
   if (loc_num == 0)
     error (_("Bad breakpoint location number '%s'"), number);
 
@@ -10757,7 +10930,7 @@ disable_command (char *args, int from_tty)
       case bp_none:
        warning (_("attempted to disable apparently deleted breakpoint #%d?"),
                 bpt->number);
-       continue;
+       break;
       case bp_breakpoint:
       case bp_tracepoint:
       case bp_fast_tracepoint:
@@ -10769,8 +10942,9 @@ disable_command (char *args, int from_tty)
       case bp_read_watchpoint:
       case bp_access_watchpoint:
        disable_breakpoint (bpt);
+       break;
       default:
-       continue;
+       break;
       }
   else if (strchr (args, '.'))
     {
@@ -10858,7 +11032,7 @@ enable_command (char *args, int from_tty)
       case bp_none:
        warning (_("attempted to enable apparently deleted breakpoint #%d?"),
                 bpt->number);
-       continue;
+       break;
       case bp_breakpoint:
       case bp_tracepoint:
       case bp_fast_tracepoint:
@@ -10870,8 +11044,9 @@ enable_command (char *args, int from_tty)
       case bp_read_watchpoint:
       case bp_access_watchpoint:
        enable_breakpoint (bpt);
+       break;
       default:
-       continue;
+       break;
       }
   else if (strchr (args, '.'))
     {
@@ -11190,8 +11365,11 @@ catch_syscall_completer (struct cmd_list_element *cmd,
                          char *text, char *word)
 {
   const char **list = get_syscall_names ();
+  char **retlist
+    = (list == NULL) ? NULL : complete_on_enum (list, text, word);
 
-  return (list == NULL) ? NULL : complete_on_enum (list, text, word);
+  xfree (list);
+  return retlist;
 }
 
 /* Tracepoint-specific operations.  */
@@ -11295,7 +11473,8 @@ create_tracepoint_from_upload (struct uploaded_tp *utp)
         address.  Since there is no way to confirm that the address
         means the same thing as when the trace was started, warn the
         user.  */
-      warning (_("Uploaded tracepoint %d has no source location, using raw address"),
+      warning (_("Uploaded tracepoint %d has no "
+                "source location, using raw address"),
               utp->number);
       sprintf (small_buf, "*%s", hex_string (utp->addr));
       addr_str = small_buf;
@@ -11303,7 +11482,8 @@ create_tracepoint_from_upload (struct uploaded_tp *utp)
 
   /* There's not much we can do with a sequence of bytecodes.  */
   if (utp->cond && !utp->cond_string)
-    warning (_("Uploaded tracepoint %d condition has no source form, ignoring it"),
+    warning (_("Uploaded tracepoint %d condition "
+              "has no source form, ignoring it"),
             utp->number);
 
   if (!create_breakpoint (get_current_arch (),
@@ -11349,7 +11529,8 @@ create_tracepoint_from_upload (struct uploaded_tp *utp)
     }
   else if (!VEC_empty (char_ptr, utp->actions)
           || !VEC_empty (char_ptr, utp->step_actions))
-    warning (_("Uploaded tracepoint %d actions have no source form, ignoring them"),
+    warning (_("Uploaded tracepoint %d actions "
+              "have no source form, ignoring them"),
             utp->number);
 
   return tp;
@@ -11359,21 +11540,18 @@ create_tracepoint_from_upload (struct uploaded_tp *utp)
    omitted.  */
 
 static void
-tracepoints_info (char *tpnum_exp, int from_tty)
+tracepoints_info (char *args, int from_tty)
 {
-  int tpnum = -1, num_printed;
+  int num_printed;
 
-  if (tpnum_exp)
-    tpnum = parse_and_eval_long (tpnum_exp);
-
-  num_printed = breakpoint_1 (tpnum, 0, is_tracepoint);
+  num_printed = breakpoint_1 (args, 0, is_tracepoint);
 
   if (num_printed == 0)
     {
-      if (tpnum == -1)
+      if (args == NULL || *args == '\0')
        ui_out_message (uiout, 0, "No tracepoints.\n");
       else
-       ui_out_message (uiout, 0, "No tracepoint number %d.\n", tpnum);
+       ui_out_message (uiout, 0, "No tracepoint matching '%s'.\n", args);
     }
 
   default_collect_info ();
@@ -11436,6 +11614,18 @@ delete_trace_command (char *arg, int from_tty)
     map_breakpoint_numbers (arg, do_delete_breakpoint, NULL);
 }
 
+/* Helper function for trace_pass_command.  */
+
+static void
+trace_pass_set_count (struct breakpoint *bp, int count, int from_tty)
+{
+  bp->pass_count = count;
+  observer_notify_tracepoint_modified (bp->number);
+  if (from_tty)
+    printf_filtered (_("Setting tracepoint %d's passcount to %d\n"),
+                    bp->number, count);
+}
+
 /* Set passcount for tracepoint.
 
    First command argument is passcount, second is tracepoint number.
@@ -11445,12 +11635,12 @@ delete_trace_command (char *arg, int from_tty)
 static void
 trace_pass_command (char *args, int from_tty)
 {
-  struct breakpoint *t1 = (struct breakpoint *) -1, *t2;
+  struct breakpoint *t1;
   unsigned int count;
-  int all = 0;
 
   if (args == 0 || *args == 0)
-    error (_("passcount command requires an argument (count + optional TP num)"));
+    error (_("passcount command requires an "
+            "argument (count + optional TP num)"));
 
   count = strtoul (args, &args, 10);   /* Count comes first, then TP num.  */
 
@@ -11460,31 +11650,32 @@ trace_pass_command (char *args, int from_tty)
   if (*args && strncasecmp (args, "all", 3) == 0)
     {
       args += 3;                       /* Skip special argument "all".  */
-      all = 1;
       if (*args)
        error (_("Junk at end of arguments."));
-    }
-  else
-    t1 = get_tracepoint_by_number (&args, 1, 1);
 
-  do
+      ALL_TRACEPOINTS (t1)
+      {
+       trace_pass_set_count (t1, count, from_tty);
+      }
+    }
+  else if (*args == '\0')
     {
+      t1 = get_tracepoint_by_number (&args, NULL, 1);
       if (t1)
+       trace_pass_set_count (t1, count, from_tty);
+    }
+  else
+    {
+      struct get_number_or_range_state state;
+
+      init_number_or_range (&state, args);
+      while (!state.finished)
        {
-         ALL_TRACEPOINTS (t2)
-           if (t1 == (struct breakpoint *) -1 || t1 == t2)
-             {
-               t2->pass_count = count;
-               observer_notify_tracepoint_modified (t2->number);
-               if (from_tty)
-                 printf_filtered (_("Setting tracepoint %d's passcount to %d\n"),
-                                  t2->number, count);
-             }
-         if (! all && *args)
-           t1 = get_tracepoint_by_number (&args, 1, 0);
+         t1 = get_tracepoint_by_number (&args, &state, 1);
+         if (t1)
+           trace_pass_set_count (t1, count, from_tty);
        }
     }
-  while (*args);
 }
 
 struct breakpoint *
@@ -11516,18 +11707,25 @@ get_tracepoint_by_number_on_target (int num)
 }
 
 /* Utility: parse a tracepoint number and look it up in the list.
-   If MULTI_P is true, there might be a range of tracepoints in ARG.
-   if OPTIONAL_P is true, then if the argument is missing, the most
+   If STATE is not NULL, use, get_number_or_range_state and ignore ARG.
+   If OPTIONAL_P is true, then if the argument is missing, the most
    recent tracepoint (tracepoint_count) is returned.  */
 struct breakpoint *
-get_tracepoint_by_number (char **arg, int multi_p, int optional_p)
+get_tracepoint_by_number (char **arg,
+                         struct get_number_or_range_state *state,
+                         int optional_p)
 {
   extern int tracepoint_count;
   struct breakpoint *t;
   int tpnum;
   char *instring = arg == NULL ? NULL : *arg;
 
-  if (arg == NULL || *arg == NULL || ! **arg)
+  if (state)
+    {
+      gdb_assert (!state->finished);
+      tpnum = get_number_or_range (state);
+    }
+  else if (arg == NULL || *arg == NULL || ! **arg)
     {
       if (optional_p)
        tpnum = tracepoint_count;
@@ -11535,7 +11733,7 @@ get_tracepoint_by_number (char **arg, int multi_p, int optional_p)
        error_no_arg (_("tracepoint number"));
     }
   else
-    tpnum = multi_p ? get_number_or_range (arg) : get_number (arg);
+    tpnum = get_number (arg);
 
   if (tpnum <= 0)
     {
@@ -11543,7 +11741,8 @@ get_tracepoint_by_number (char **arg, int multi_p, int optional_p)
        printf_filtered (_("bad tracepoint number at or near '%s'\n"), 
                         instring);
       else
-       printf_filtered (_("Tracepoint argument missing and no previous tracepoint\n"));
+       printf_filtered (_("Tracepoint argument missing "
+                          "and no previous tracepoint\n"));
       return NULL;
     }
 
@@ -11553,9 +11752,6 @@ get_tracepoint_by_number (char **arg, int multi_p, int optional_p)
       return t;
     }
 
-  /* FIXME: if we are in the middle of a range we don't want to give
-     a message.  The current interface to get_number_or_range doesn't
-     allow us to discover this.  */
   printf_unfiltered ("No tracepoint number %d.\n", tpnum);
   return NULL;
 }
@@ -11583,7 +11779,7 @@ save_breakpoints (char *filename, int from_tty,
   ALL_BREAKPOINTS (tp)
   {
     /* Skip internal and momentary breakpoints.  */
-    if (!user_settable_breakpoint (tp) || tp->number < 0)
+    if (!user_breakpoint_p (tp))
       continue;
 
     /* If we have a filter, only save the breakpoints it accepts.  */
@@ -11621,7 +11817,7 @@ save_breakpoints (char *filename, int from_tty,
   ALL_BREAKPOINTS (tp)
   {
     /* Skip internal and momentary breakpoints.  */
-    if (!user_settable_breakpoint (tp) || tp->number < 0)
+    if (!user_breakpoint_p (tp))
       continue;
 
     /* If we have a filter, only save the breakpoints it accepts.  */
@@ -11834,8 +12030,8 @@ clear_syscall_counts (struct inferior *inf)
 static void
 save_command (char *arg, int from_tty)
 {
-  printf_unfiltered (_("\
-\"save\" must be followed by the name of a save subcommand.\n"));
+  printf_unfiltered (_("\"save\" must be followed by "
+                      "the name of a save subcommand.\n"));
   help_list (save_cmdlist, "save ", -1, gdb_stdout);
 }
 
@@ -11863,6 +12059,8 @@ _initialize_breakpoint (void)
   observer_attach_inferior_exit (clear_syscall_counts);
   observer_attach_memory_changed (invalidate_bp_value_on_memory_change);
 
+  breakpoint_objfile_key = register_objfile_data ();
+
   breakpoint_chain = 0;
   /* Don't bother to call set_breakpoint_count.  $bpnum isn't useful
      before a breakpoint is set.  */
@@ -11900,7 +12098,7 @@ BREAK_ARGS_HELP ("tbreak")));
   set_cmd_completer (c, location_completer);
 
   c = add_com ("hbreak", class_breakpoint, hbreak_command, _("\
-Set a hardware assisted  breakpoint.\n\
+Set a hardware assisted breakpoint.\n\
 Like \"break\" except the breakpoint requires hardware support,\n\
 some target hardware may not have this support.\n\
 \n"
@@ -12058,7 +12256,7 @@ breakpoint set."));
     }
 
   add_info ("breakpoints", breakpoints_info, _("\
-Status of user-settable breakpoints, or breakpoint number NUMBER.\n\
+Status of specified breakpoints (all user-settable breakpoints if no argument).\n\
 The \"Type\" column indicates one of:\n\
 \tbreakpoint     - normal breakpoint\n\
 \twatchpoint     - watchpoint\n\
@@ -12206,9 +12404,7 @@ the memory to which it refers."));
   set_cmd_completer (c, expression_completer);
 
   add_info ("watchpoints", watchpoints_info, _("\
-Status of watchpoints, or watchpoint number NUMBER."));
-
-
+Status of specified watchpoints (all watchpoints if no argument)."));
 
   /* XXX: cagney/2005-02-23: This should be a boolean, and should
      respond to changes - contrary to the description.  */
@@ -12274,7 +12470,7 @@ Do \"help tracepoints\" for info on other tracepoint commands."));
   set_cmd_completer (c, location_completer);
 
   add_info ("tracepoints", tracepoints_info, _("\
-Status of tracepoints, or tracepoint number NUMBER.\n\
+Status of specified tracepoints (all tracepoints if no argument).\n\
 Convenience variable \"$tpnum\" contains the number of the\n\
 last tracepoint set."));
 
This page took 0.107867 seconds and 4 git commands to generate.