diff --git a/gdb/ChangeLog b/gdb/ChangeLog
index 0ec71d4..0b9e140 100644
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -1,3 +1,27 @@
+2014-09-12  Pedro Alves  <palves@redhat.com>
+
+	* breakpoint.c (remove_solib_event_breakpoints_at_next_stop)
+	(create_and_insert_solib_event_breakpoint): New functions.
+	* breakpoint.h (create_and_insert_solib_event_breakpoint)
+	(remove_solib_event_breakpoints_at_next_stop): New declarations.
+	* procfs.c (dbx_link_bpt_addr, dbx_link_bpt): Delete globals.
+	(remove_dbx_link_breakpoint): Delete function.
+	(insert_dbx_link_bpt_in_file): Use
+	create_and_insert_solib_event_breakpoint instead of
+	deprecated_insert_raw_breakpoint.
+	(procfs_wait): Don't check whether we hit __dbx_link here.
+	(procfs_mourn_inferior): Don't delete the __dbx_link breakpoint
+	here.
+	* solib-irix.c (base_breakpoint): Delete global.
+	(disable_break): Delete function.
+	(enable_break): Use create_solib_event_breakpoint
+	instead of deprecated_insert_raw_breakpoint.
+	(irix_solib_handle_event): New function.
+	(irix_solib_create_inferior_hook): Don't run the target or disable
+	the mapping-complete breakpoint here.
+	(_initialize_irix_solib): Install irix_solib_handle_event as
+	so_ops->handle_event hook.
+
 2014-09-12  Edjunior Barbosa Machado  <emachado@linux.vnet.ibm.com>
 	    Ulrich Weigand  <uweigand@de.ibm.com>

diff --git a/gdb/breakpoint.c b/gdb/breakpoint.c
index 683ed2b..f990d97 100644
--- a/gdb/breakpoint.c
+++ b/gdb/breakpoint.c
@@ -7620,6 +7620,19 @@ remove_solib_event_breakpoints (void)
       delete_breakpoint (b);
 }

+/* See breakpoint.h.  */
+
+void
+remove_solib_event_breakpoints_at_next_stop (void)
+{
+  struct breakpoint *b, *b_tmp;
+
+  ALL_BREAKPOINTS_SAFE (b, b_tmp)
+    if (b->type == bp_shlib_event
+	&& b->loc->pspace == current_program_space)
+      b->disposition = disp_del_at_next_stop;
+}
+
 struct breakpoint *
 create_solib_event_breakpoint (struct gdbarch *gdbarch, CORE_ADDR address)
 {
@@ -7631,6 +7644,24 @@ create_solib_event_breakpoint (struct gdbarch *gdbarch, CORE_ADDR address)
   return b;
 }

+/* See breakpoint.h.  */
+
+struct breakpoint *
+create_and_insert_solib_event_breakpoint (struct gdbarch *gdbarch, CORE_ADDR address)
+{
+  struct breakpoint *b;
+
+  b = create_solib_event_breakpoint (gdbarch, address);
+  if (!breakpoints_always_inserted_mode ())
+    insert_breakpoint_locations ();
+  if (!b->loc->inserted)
+    {
+      delete_breakpoint (b);
+      return NULL;
+    }
+  return b;
+}
+
 /* Disable any breakpoints that are on code in shared libraries.  Only
    apply to enabled breakpoints, disabled ones can just stay disabled.  */

diff --git a/gdb/breakpoint.h b/gdb/breakpoint.h
index f6d06ce..8abb5ea 100644
--- a/gdb/breakpoint.h
+++ b/gdb/breakpoint.h
@@ -1419,6 +1419,13 @@ extern struct breakpoint *create_jit_event_breakpoint (struct gdbarch *,
 extern struct breakpoint *create_solib_event_breakpoint (struct gdbarch *,
 							 CORE_ADDR);

+/* Create an solib event breakpoint at ADDRESS in the current program
+   space, and immediately try to insert it.  Returns a pointer to the
+   breakpoint on success.  Deletes the new breakpoint and returns NULL
+   if inserting the breakpoint fails.  */
+extern struct breakpoint *create_and_insert_solib_event_breakpoint
+  (struct gdbarch *gdbarch, CORE_ADDR address);
+
 extern struct breakpoint *create_thread_event_breakpoint (struct gdbarch *,
 							  CORE_ADDR);

@@ -1426,6 +1433,10 @@ extern void remove_jit_event_breakpoints (void);

 extern void remove_solib_event_breakpoints (void);

+/* Mark solib event breakpoints of the current program space with
+   delete at next stop disposition.  */
+extern void remove_solib_event_breakpoints_at_next_stop (void);
+
 extern void remove_thread_event_breakpoints (void);

 extern void disable_breakpoints_in_shlibs (void);
diff --git a/gdb/procfs.c b/gdb/procfs.c
index 3465bc5..699fcd9 100644
--- a/gdb/procfs.c
+++ b/gdb/procfs.c
@@ -2902,13 +2902,6 @@ static void do_detach (int signo);
 static void proc_trace_syscalls_1 (procinfo *pi, int syscallnum,
 				   int entry_or_exit, int mode, int from_tty);

-/* On mips-irix, we need to insert a breakpoint at __dbx_link during
-   the startup phase.  The following two variables are used to record
-   the address of the breakpoint, and the code that was replaced by
-   a breakpoint.  */
-static int dbx_link_bpt_addr = 0;
-static void *dbx_link_bpt;
-
 /* Sets up the inferior to be debugged.  Registers to trace signals,
    hardware faults, and syscalls.  Note: does not set RLC flag: caller
    may want to customize that.  Returns zero for success (note!
@@ -3380,23 +3373,6 @@ syscall_is_lwp_create (procinfo *pi, int scall)
   return 0;
 }

-/* Remove the breakpoint that we inserted in __dbx_link().
-   Does nothing if the breakpoint hasn't been inserted or has already
-   been removed.  */
-
-static void
-remove_dbx_link_breakpoint (void)
-{
-  if (dbx_link_bpt_addr == 0)
-    return;
-
-  if (deprecated_remove_raw_breakpoint (target_gdbarch (), dbx_link_bpt) != 0)
-    warning (_("Unable to remove __dbx_link breakpoint."));
-
-  dbx_link_bpt_addr = 0;
-  dbx_link_bpt = NULL;
-}
-
 #ifdef SYS_syssgi
 /* Return the address of the __dbx_link() function in the file
    refernced by ABFD by scanning its symbol table.  Return 0 if
@@ -3461,10 +3437,12 @@ insert_dbx_link_bpt_in_file (int fd, CORE_ADDR ignored)
   sym_addr = dbx_link_addr (abfd);
   if (sym_addr != 0)
     {
+      struct breakpoint *dbx_link_bpt;
+
       /* Insert the breakpoint.  */
-      dbx_link_bpt_addr = sym_addr;
-      dbx_link_bpt = deprecated_insert_raw_breakpoint (target_gdbarch (), NULL,
-						       sym_addr);
+      dbx_link_bpt
+	= create_and_insert_solib_event_breakpoint (target_gdbarch (),
+						    sym_addr);
       if (dbx_link_bpt == NULL)
 	{
 	  warning (_("Failed to insert dbx_link breakpoint."));
@@ -3894,14 +3872,6 @@ wait_again:
 #if (FLTTRACE != FLTBPT)	/* Avoid "duplicate case" error.  */
 		case FLTTRACE:
 #endif
-		  /* If we hit our __dbx_link() internal breakpoint,
-		     then remove it.  See comments in procfs_init_inferior()
-		     for more details.	*/
-		  if (dbx_link_bpt_addr != 0
-		      && dbx_link_bpt_addr
-			 == regcache_read_pc (get_current_regcache ()))
-		    remove_dbx_link_breakpoint ();
-
 		  wstat = (SIGTRAP << 8) | 0177;
 		  break;
 		case FLTSTACK:
@@ -4340,13 +4310,6 @@ procfs_mourn_inferior (struct target_ops *ops)

   generic_mourn_inferior ();

-  if (dbx_link_bpt != NULL)
-    {
-      deprecated_remove_raw_breakpoint (target_gdbarch (), dbx_link_bpt);
-      dbx_link_bpt_addr = 0;
-      dbx_link_bpt = NULL;
-    }
-
   inf_child_maybe_unpush_target (ops);
 }

diff --git a/gdb/solib-irix.c b/gdb/solib-irix.c
index 12ed766..00236bf 100644
--- a/gdb/solib-irix.c
+++ b/gdb/solib-irix.c
@@ -240,8 +240,6 @@ fetch_lm_info (CORE_ADDR addr)
 /* The symbol which starts off the list of shared libraries.  */
 #define DEBUG_BASE "__rld_obj_head"

-static void *base_breakpoint;
-
 static CORE_ADDR debug_base;	/* Base of dynamic linker structures.  */

 /* Locate the base address of dynamic linker structs.
@@ -293,34 +291,6 @@ locate_base (void)
   return (address);
 }

-/* Remove the "mapping changed" breakpoint.
-
-   Removes the breakpoint that gets hit when the dynamic linker
-   completes a mapping change.  */
-
-static int
-disable_break (void)
-{
-  int status = 1;
-
-  /* Note that breakpoint address and original contents are in our address
-     space, so we just need to write the original contents back.  */
-
-  if (deprecated_remove_raw_breakpoint (target_gdbarch (), base_breakpoint) != 0)
-    {
-      status = 0;
-    }
-
-  base_breakpoint = NULL;
-
-  /* Note that it is possible that we have stopped at a location that
-     is different from the location where we inserted our breakpoint.
-     On mips-irix, we can actually land in __dbx_init(), so we should
-     not check the PC against our breakpoint address here.  See procfs.c
-     for more details.  */
-
-  return (status);
-}

 /* Arrange for dynamic linker to hit breakpoint.

@@ -332,23 +302,39 @@ enable_break (void)
 {
   if (symfile_objfile != NULL && has_stack_frames ())
     {
-      struct frame_info *frame = get_current_frame ();
-      struct address_space *aspace = get_frame_address_space (frame);
       CORE_ADDR entry_point;

-      if (!entry_point_address_query (&entry_point))
-	return 0;
-
-      base_breakpoint = deprecated_insert_raw_breakpoint (target_gdbarch (),
-							  aspace, entry_point);
-
-      if (base_breakpoint != NULL)
-	return 1;
+      if (entry_point_address_query (&entry_point))
+	{
+	  create_solib_event_breakpoint (target_gdbarch (), entry_point);
+	  return 1;
+	}
     }

   return 0;
 }

+/* Implement the "handle_event" target_solib_ops method.  */
+
+static void
+irix_solib_handle_event (void)
+{
+  /* We are now at the "mapping complete" breakpoint, we no longer
+     need it.  Note that it is possible that we have stopped at a
+     location that is different from the location where we inserted
+     our breakpoint: On mips-irix, we can actually land in
+     __dbx_link(), so we should not check the PC against our
+     breakpoint address here.  See procfs.c for more details.  Note
+     we're being called by the bpstat handling code, and so can't
+     delete the breakpoint immediately.  Mark it for later deletion,
+     which has the same effect (it'll be removed before we next resume
+     or if we're stopping).  */
+  remove_solib_event_breakpoints_at_next_stop ();
+
+  /* The caller calls solib_add, which will add any shared libraries
+     that were mapped in.  */
+}
+
 /* Implement the "create_inferior_hook" target_solib_ops method.

    For SunOS executables, this first instruction is typically the
@@ -409,43 +395,10 @@ irix_solib_create_inferior_hook (int from_tty)
       return;
     }

-  /* Now run the target.  It will eventually hit the breakpoint, at
-     which point all of the libraries will have been mapped in and we
-     can go groveling around in the dynamic linker structures to find
-     out what we need to know about them.  */
-
-  tp = inferior_thread ();
-
-  clear_proceed_status (0);
-
-  inf->control.stop_soon = STOP_QUIETLY;
-  tp->suspend.stop_signal = GDB_SIGNAL_0;
-
-  do
-    {
-      target_resume (pid_to_ptid (-1), 0, tp->suspend.stop_signal);
-      wait_for_inferior ();
-    }
-  while (tp->suspend.stop_signal != GDB_SIGNAL_TRAP);
-
-  /* We are now either at the "mapping complete" breakpoint (or somewhere
-     else, a condition we aren't prepared to deal with anyway), so adjust
-     the PC as necessary after a breakpoint, disable the breakpoint, and
-     add any shared libraries that were mapped in.  */
-
-  if (!disable_break ())
-    {
-      warning (_("shared library handler failed to disable breakpoint"));
-    }
-
-  /* solib_add will call reinit_frame_cache.
-     But we are stopped in the startup code and we might not have symbols
-     for the startup code, so heuristic_proc_start could be called
-     and will put out an annoying warning.
-     Delaying the resetting of stop_soon until after symbol loading
-     suppresses the warning.  */
-  solib_add ((char *) 0, 0, (struct target_ops *) 0, auto_solib_add);
-  inf->control.stop_soon = NO_STOP_QUIETLY;
+  /* The target will eventually hit the breakpoint, at which point all
+     of the libraries will have been mapped in and we can go groveling
+     around in the dynamic linker structures to find out what we need
+     to know about them.  */
 }

 /* Implement the "current_sos" target_so_ops method.  */
@@ -653,4 +606,5 @@ _initialize_irix_solib (void)
   irix_so_ops.open_symbol_file_object = irix_open_symbol_file_object;
   irix_so_ops.in_dynsym_resolve_code = irix_in_dynsym_resolve_code;
   irix_so_ops.bfd_open = solib_bfd_open;
+  irix_so_ops.handle_event = irix_solib_handle_event;
 }
