*** empty log message ***
[deliverable/binutils-gdb.git] / gdb / infrun.c
index b525edf64ffc2246c14fe766053dd39b891a93e0..c7fdd613af14cf0d61599d922d354d41a72b0e1f 100644 (file)
@@ -237,11 +237,6 @@ int stop_after_trap;
 
 enum stop_kind stop_soon;
 
-/* Nonzero if proceed is being used for a "finish" command or a similar
-   situation when stop_registers should be saved.  */
-
-int proceed_to_finish;
-
 /* Save register contents here when about to pop a stack dummy frame,
    if-and-only-if proceed_to_finish is set.
    Thus this contains the return value from the called function (assuming
@@ -1083,6 +1078,10 @@ a command like `return' or `jump' to continue execution."));
         }
 
       target_resume (resume_ptid, step, sig);
+
+      /* Avoid confusing the next resume, if the next stop/resume
+        happens to apply to another thread.  */
+      tp->stop_signal = TARGET_SIGNAL_0;
     }
 
   discard_cleanups (old_cleanups);
@@ -1104,12 +1103,19 @@ clear_proceed_status (void)
       tp->step_range_start = 0;
       tp->step_range_end = 0;
       tp->step_frame_id = null_frame_id;
+      tp->step_over_calls = STEP_OVER_UNDEBUGGABLE;
+
+      tp->stop_step = 0;
+
+      tp->proceed_to_finish = 0;
+
+      /* Discard any remaining commands or status from previous
+        stop.  */
+      bpstat_clear (&tp->stop_bpstat);
     }
 
-  step_over_calls = STEP_OVER_UNDEBUGGABLE;
   stop_after_trap = 0;
   stop_soon = NO_STOP_QUIETLY;
-  proceed_to_finish = 0;
   breakpoint_proceeded = 1;    /* We're about to proceed... */
 
   if (stop_registers)
@@ -1117,9 +1123,6 @@ clear_proceed_status (void)
       regcache_xfree (stop_registers);
       stop_registers = NULL;
     }
-
-  /* Discard any remaining commands or status from previous stop.  */
-  bpstat_clear (&stop_bpstat);
 }
 
 /* This should be suitable for any targets that support threads. */
@@ -1185,6 +1188,7 @@ proceed (CORE_ADDR addr, enum target_signal siggnal, int step)
   struct thread_info *tp;
   CORE_ADDR pc = regcache_read_pc (regcache);
   int oneproc = 0;
+  enum target_signal stop_signal;
 
   if (step > 0)
     step_start_function = find_pc_function (pc);
@@ -1259,12 +1263,37 @@ proceed (CORE_ADDR addr, enum target_signal siggnal, int step)
   if (! tp->trap_expected || use_displaced_stepping (gdbarch))
     insert_breakpoints ();
 
+  if (!non_stop)
+    {
+      /* Pass the last stop signal to the thread we're resuming,
+        irrespective of whether the current thread is the thread that
+        got the last event or not.  This was historically GDB's
+        behaviour before keeping a stop_signal per thread.  */
+
+      struct thread_info *last_thread;
+      ptid_t last_ptid;
+      struct target_waitstatus last_status;
+
+      get_last_target_status (&last_ptid, &last_status);
+      if (!ptid_equal (inferior_ptid, last_ptid)
+         && !ptid_equal (last_ptid, null_ptid)
+         && !ptid_equal (last_ptid, minus_one_ptid))
+       {
+         last_thread = find_thread_pid (last_ptid);
+         if (last_thread)
+           {
+             tp->stop_signal = last_thread->stop_signal;
+             last_thread->stop_signal = TARGET_SIGNAL_0;
+           }
+       }
+    }
+
   if (siggnal != TARGET_SIGNAL_DEFAULT)
-    stop_signal = siggnal;
+    tp->stop_signal = siggnal;
   /* If this signal should not be seen by program,
      give it zero.  Used for debugging signals.  */
-  else if (!signal_program[stop_signal])
-    stop_signal = TARGET_SIGNAL_0;
+  else if (!signal_program[tp->stop_signal])
+    tp->stop_signal = TARGET_SIGNAL_0;
 
   annotate_starting ();
 
@@ -1303,7 +1332,7 @@ proceed (CORE_ADDR addr, enum target_signal siggnal, int step)
   init_infwait_state ();
 
   /* Resume inferior.  */
-  resume (oneproc || step || bpstat_should_step (), stop_signal);
+  resume (oneproc || step || bpstat_should_step (), tp->stop_signal);
 
   /* Wait for it to stop (if not standalone)
      and in any case decode why it stopped, and act accordingly.  */
@@ -1358,9 +1387,6 @@ init_wait_for_inferior (void)
 
   breakpoint_init_inferior (inf_starting);
 
-  /* Don't confuse first call to proceed(). */
-  stop_signal = TARGET_SIGNAL_0;
-
   /* The first resume is not following a fork/vfork/exec. */
   pending_follow.kind = TARGET_WAITKIND_SPURIOUS;      /* I.e., none. */
 
@@ -1542,8 +1568,6 @@ wait_for_inferior (int treat_exec_as_sigtrap)
       else
        ecs->ptid = target_wait (waiton_ptid, &ecs->ws);
 
-      ecs->event_thread = find_thread_pid (ecs->ptid);
-
       if (treat_exec_as_sigtrap && ecs->ws.kind == TARGET_WAITKIND_EXECD)
         {
           xfree (ecs->ws.value.execd_pathname);
@@ -1619,8 +1643,6 @@ fetch_inferior_event (void *client_data)
        thread.  */
     context_switch (ecs->ptid);
 
-  ecs->event_thread = find_thread_pid (ecs->ptid);
-
   /* Now figure out what to do with the result of the result.  */
   handle_inferior_event (ecs);
 
@@ -1631,7 +1653,11 @@ fetch_inferior_event (void *client_data)
       if (stop_soon == NO_STOP_QUIETLY)
        normal_stop ();
 
-      if (step_multi && stop_step)
+      if (target_has_execution
+         && ecs->ws.kind != TARGET_WAITKIND_EXITED
+         && ecs->ws.kind != TARGET_WAITKIND_SIGNALLED
+         && ecs->event_thread->step_multi
+         && ecs->event_thread->stop_step)
        inferior_event_handler (INF_EXEC_CONTINUE, NULL);
       else
        inferior_event_handler (INF_EXEC_COMPLETE, NULL);
@@ -1690,17 +1716,11 @@ nullify_last_target_wait_ptid (void)
   target_last_wait_ptid = minus_one_ptid;
 }
 
-/* Switch thread contexts, maintaining "infrun state". */
+/* Switch thread contexts */
 
 static void
 context_switch (ptid_t ptid)
 {
-  /* Caution: it may happen that the new thread (or the old one!)
-     is not in the thread list.  In this case we must not attempt
-     to "switch context", or we run the risk that our context may
-     be lost.  This may happen as a result of the target module
-     mishandling thread creation.  */
-
   if (debug_infrun)
     {
       fprintf_unfiltered (gdb_stdlog, "infrun: Switching context from %s ",
@@ -1709,46 +1729,9 @@ context_switch (ptid_t ptid)
                          target_pid_to_str (ptid));
     }
 
-  if (in_thread_list (inferior_ptid) && in_thread_list (ptid))
-    {                          /* Perform infrun state context switch: */
-      /* Save infrun state for the old thread.  */
-      save_infrun_state (inferior_ptid,
-                        cmd_continuation, intermediate_continuation,
-                        proceed_to_finish,
-                        step_over_calls,
-                        stop_step,
-                        step_multi,
-                        stop_signal,
-                        stop_bpstat);
-
-      /* Load infrun state for the new thread.  */
-      load_infrun_state (ptid,
-                        &cmd_continuation, &intermediate_continuation,
-                        &proceed_to_finish,
-                        &step_over_calls,
-                        &stop_step,
-                        &step_multi,
-                        &stop_signal,
-                        &stop_bpstat);
-    }
-
   switch_to_thread (ptid);
 }
 
-/* Context switch to thread PTID.  */
-ptid_t
-context_switch_to (ptid_t ptid)
-{
-  ptid_t current_ptid = inferior_ptid;
-
-  /* Context switch to the new thread. */
-  if (!ptid_equal (ptid, inferior_ptid))
-    {
-      context_switch (ptid);
-    }
-  return current_ptid;
-}
-
 static void
 adjust_pc_after_break (struct execution_control_state *ecs)
 {
@@ -1867,10 +1850,6 @@ handle_inferior_event (struct execution_control_state *ecs)
   /* Always clear state belonging to the previous time we stopped.  */
   stop_stack_dummy = 0;
 
-  adjust_pc_after_break (ecs);
-
-  reinit_frame_cache ();
-
   /* If it's a new process, add it to the thread database */
 
   ecs->new_thread_event = (!ptid_equal (ecs->ptid, inferior_ptid)
@@ -1881,6 +1860,14 @@ handle_inferior_event (struct execution_control_state *ecs)
       && ecs->ws.kind != TARGET_WAITKIND_SIGNALLED && ecs->new_thread_event)
     add_thread (ecs->ptid);
 
+  ecs->event_thread = find_thread_pid (ecs->ptid);
+
+  /* Dependent on valid ECS->EVENT_THREAD.  */
+  adjust_pc_after_break (ecs);
+
+  /* Dependent on the current PC value modified by adjust_pc_after_break.  */
+  reinit_frame_cache ();
+
   if (ecs->ws.kind != TARGET_WAITKIND_IGNORE)
     {
       /* Mark the non-executing threads accordingly.  */
@@ -2019,7 +2006,7 @@ handle_inferior_event (struct execution_control_state *ecs)
       /* Record the exit code in the convenience variable $_exitcode, so
          that the user can inspect this again later.  */
       set_internalvar (lookup_internalvar ("_exitcode"),
-                      value_from_longest (builtin_type_int,
+                      value_from_longest (builtin_type_int32,
                                           (LONGEST) ecs->ws.value.integer));
       gdb_flush (gdb_stdout);
       target_mourn_inferior ();
@@ -2032,7 +2019,6 @@ handle_inferior_event (struct execution_control_state *ecs)
       if (debug_infrun)
         fprintf_unfiltered (gdb_stdlog, "infrun: TARGET_WAITKIND_SIGNALLED\n");
       stop_print_frame = 0;
-      stop_signal = ecs->ws.value.sig;
       target_terminal_ours (); /* Must do this before mourn anyway */
 
       /* Note: By definition of TARGET_WAITKIND_SIGNALLED, we shouldn't
@@ -2042,7 +2028,7 @@ handle_inferior_event (struct execution_control_state *ecs)
          may be needed. */
       target_mourn_inferior ();
 
-      print_stop_reason (SIGNAL_EXITED, stop_signal);
+      print_stop_reason (SIGNAL_EXITED, ecs->ws.value.sig);
       singlestep_breakpoints_inserted_p = 0;
       stop_stepping (ecs);
       return;
@@ -2053,7 +2039,6 @@ handle_inferior_event (struct execution_control_state *ecs)
     case TARGET_WAITKIND_VFORKED:
       if (debug_infrun)
         fprintf_unfiltered (gdb_stdlog, "infrun: TARGET_WAITKIND_FORKED\n");
-      stop_signal = TARGET_SIGNAL_TRAP;
       pending_follow.kind = ecs->ws.kind;
 
       pending_follow.fork_event.parent_pid = ecs->ptid;
@@ -2067,24 +2052,23 @@ handle_inferior_event (struct execution_control_state *ecs)
 
       stop_pc = read_pc ();
 
-      stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid);
+      ecs->event_thread->stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid);
 
-      ecs->random_signal = !bpstat_explains_signal (stop_bpstat);
+      ecs->random_signal = !bpstat_explains_signal (ecs->event_thread->stop_bpstat);
 
       /* If no catchpoint triggered for this, then keep going.  */
       if (ecs->random_signal)
        {
-         stop_signal = TARGET_SIGNAL_0;
+         ecs->event_thread->stop_signal = TARGET_SIGNAL_0;
          keep_going (ecs);
          return;
        }
+      ecs->event_thread->stop_signal = TARGET_SIGNAL_TRAP;
       goto process_event_stop_test;
 
     case TARGET_WAITKIND_EXECD:
       if (debug_infrun)
         fprintf_unfiltered (gdb_stdlog, "infrun: TARGET_WAITKIND_EXECD\n");
-      stop_signal = TARGET_SIGNAL_TRAP;
-
       pending_follow.execd_pathname =
        savestring (ecs->ws.value.execd_pathname,
                    strlen (ecs->ws.value.execd_pathname));
@@ -2103,9 +2087,9 @@ handle_inferior_event (struct execution_control_state *ecs)
        ptid_t saved_inferior_ptid = inferior_ptid;
        inferior_ptid = ecs->ptid;
 
-       stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid);
+       ecs->event_thread->stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid);
 
-       ecs->random_signal = !bpstat_explains_signal (stop_bpstat);
+       ecs->random_signal = !bpstat_explains_signal (ecs->event_thread->stop_bpstat);
        inferior_ptid = saved_inferior_ptid;
       }
 
@@ -2118,10 +2102,11 @@ handle_inferior_event (struct execution_control_state *ecs)
       /* If no catchpoint triggered for this, then keep going.  */
       if (ecs->random_signal)
        {
-         stop_signal = TARGET_SIGNAL_0;
+         ecs->event_thread->stop_signal = TARGET_SIGNAL_0;
          keep_going (ecs);
          return;
        }
+      ecs->event_thread->stop_signal = TARGET_SIGNAL_TRAP;
       goto process_event_stop_test;
 
       /* Be careful not to try to gather much state about a thread
@@ -2148,7 +2133,7 @@ handle_inferior_event (struct execution_control_state *ecs)
     case TARGET_WAITKIND_STOPPED:
       if (debug_infrun)
         fprintf_unfiltered (gdb_stdlog, "infrun: TARGET_WAITKIND_STOPPED\n");
-      stop_signal = ecs->ws.value.sig;
+      ecs->event_thread->stop_signal = ecs->ws.value.sig;
       break;
 
       /* We had an event in the inferior, but we are not interested
@@ -2191,7 +2176,8 @@ targets should add new threads to the thread list themselves in non-stop mode.")
   /* Do we need to clean up the state of a thread that has completed a
      displaced single-step?  (Doing so usually affects the PC, so do
      it here, before we set stop_pc.)  */
-  displaced_step_fixup (ecs->ptid, stop_signal);
+  if (ecs->ws.kind == TARGET_WAITKIND_STOPPED)
+    displaced_step_fixup (ecs->ptid, ecs->event_thread->stop_signal);
 
   stop_pc = regcache_read_pc (get_thread_regcache (ecs->ptid));
 
@@ -2225,7 +2211,7 @@ targets should add new threads to the thread list themselves in non-stop mode.")
       /* We've either finished single-stepping past the single-step
          breakpoint, or stopped for some other reason.  It would be nice if
          we could tell, but we can't reliably.  */
-      if (stop_signal == TARGET_SIGNAL_TRAP)
+      if (ecs->event_thread->stop_signal == TARGET_SIGNAL_TRAP)
        {
          if (debug_infrun)
            fprintf_unfiltered (gdb_stdlog, "infrun: stepping_past_singlestep_breakpoint\n");
@@ -2254,7 +2240,7 @@ targets should add new threads to the thread list themselves in non-stop mode.")
 
       /* If we stopped for some other reason than single-stepping, ignore
         the fact that we were supposed to switch back.  */
-      if (stop_signal == TARGET_SIGNAL_TRAP)
+      if (ecs->event_thread->stop_signal == TARGET_SIGNAL_TRAP)
        {
          struct thread_info *tp;
 
@@ -2288,7 +2274,7 @@ targets should add new threads to the thread list themselves in non-stop mode.")
      another thread.  If so, then step that thread past the breakpoint,
      and continue it.  */
 
-  if (stop_signal == TARGET_SIGNAL_TRAP)
+  if (ecs->event_thread->stop_signal == TARGET_SIGNAL_TRAP)
     {
       int thread_hop_needed = 0;
 
@@ -2342,6 +2328,8 @@ targets should add new threads to the thread list themselves in non-stop mode.")
 
             if (new_singlestep_pc != singlestep_pc)
               {
+                enum target_signal stop_signal;
+
                 if (debug_infrun)
                   fprintf_unfiltered (gdb_stdlog, "infrun: unexpected thread,"
                                       " but expected thread advanced also\n");
@@ -2350,8 +2338,11 @@ targets should add new threads to the thread list themselves in non-stop mode.")
                    singlestep_ptid.  Don't swap here, since that's
                    the context we want to use.  Just fudge our
                    state and continue.  */
+                 stop_signal = ecs->event_thread->stop_signal;
+                 ecs->event_thread->stop_signal = TARGET_SIGNAL_0;
                  ecs->ptid = singlestep_ptid;
                  ecs->event_thread = find_thread_pid (ecs->ptid);
+                 ecs->event_thread->stop_signal = stop_signal;
                  stop_pc = new_singlestep_pc;
                }
              else
@@ -2501,13 +2492,13 @@ targets should add new threads to the thread list themselves in non-stop mode.")
   ecs->stop_func_start
     += gdbarch_deprecated_function_start_offset (current_gdbarch);
   ecs->event_thread->stepping_over_breakpoint = 0;
-  bpstat_clear (&stop_bpstat);
-  stop_step = 0;
+  bpstat_clear (&ecs->event_thread->stop_bpstat);
+  ecs->event_thread->stop_step = 0;
   stop_print_frame = 1;
   ecs->random_signal = 0;
   stopped_by_random_signal = 0;
 
-  if (stop_signal == TARGET_SIGNAL_TRAP
+  if (ecs->event_thread->stop_signal == TARGET_SIGNAL_TRAP
       && ecs->event_thread->trap_expected
       && gdbarch_single_step_through_delay_p (current_gdbarch)
       && currently_stepping (ecs->event_thread))
@@ -2564,16 +2555,16 @@ targets should add new threads to the thread list themselves in non-stop mode.")
      If we're doing a displaced step past a breakpoint, then the
      breakpoint is always inserted at the original instruction;
      non-standard signals can't be explained by the breakpoint.  */
-  if (stop_signal == TARGET_SIGNAL_TRAP
+  if (ecs->event_thread->stop_signal == TARGET_SIGNAL_TRAP
       || (! ecs->event_thread->trap_expected
           && breakpoint_inserted_here_p (stop_pc)
-         && (stop_signal == TARGET_SIGNAL_ILL
-             || stop_signal == TARGET_SIGNAL_SEGV
-             || stop_signal == TARGET_SIGNAL_EMT))
+         && (ecs->event_thread->stop_signal == TARGET_SIGNAL_ILL
+             || ecs->event_thread->stop_signal == TARGET_SIGNAL_SEGV
+             || ecs->event_thread->stop_signal == TARGET_SIGNAL_EMT))
       || stop_soon == STOP_QUIETLY || stop_soon == STOP_QUIETLY_NO_SIGSTOP
       || stop_soon == STOP_QUIETLY_REMOTE)
     {
-      if (stop_signal == TARGET_SIGNAL_TRAP && stop_after_trap)
+      if (ecs->event_thread->stop_signal == TARGET_SIGNAL_TRAP && stop_after_trap)
        {
           if (debug_infrun)
            fprintf_unfiltered (gdb_stdlog, "infrun: stopped\n");
@@ -2605,16 +2596,16 @@ targets should add new threads to the thread list themselves in non-stop mode.")
         (e.g. gdbserver).  We already rely on SIGTRAP being our
         signal, so this is no exception.  */
       if (stop_soon == STOP_QUIETLY_NO_SIGSTOP
-         && (stop_signal == TARGET_SIGNAL_STOP
-             || stop_signal == TARGET_SIGNAL_TRAP))
+         && (ecs->event_thread->stop_signal == TARGET_SIGNAL_STOP
+             || ecs->event_thread->stop_signal == TARGET_SIGNAL_TRAP))
        {
          stop_stepping (ecs);
-         stop_signal = TARGET_SIGNAL_0;
+         ecs->event_thread->stop_signal = TARGET_SIGNAL_0;
          return;
        }
 
       /* See if there is a breakpoint at the current PC.  */
-      stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid);
+      ecs->event_thread->stop_bpstat = bpstat_stop_status (stop_pc, ecs->ptid);
       
       /* Following in case break condition called a
         function.  */
@@ -2640,17 +2631,17 @@ targets should add new threads to the thread list themselves in non-stop mode.")
          be necessary for call dummies on a non-executable stack on
          SPARC.  */
 
-      if (stop_signal == TARGET_SIGNAL_TRAP)
+      if (ecs->event_thread->stop_signal == TARGET_SIGNAL_TRAP)
        ecs->random_signal
-         = !(bpstat_explains_signal (stop_bpstat)
+         = !(bpstat_explains_signal (ecs->event_thread->stop_bpstat)
              || ecs->event_thread->trap_expected
              || (ecs->event_thread->step_range_end
                  && ecs->event_thread->step_resume_breakpoint == NULL));
       else
        {
-         ecs->random_signal = !bpstat_explains_signal (stop_bpstat);
+         ecs->random_signal = !bpstat_explains_signal (ecs->event_thread->stop_bpstat);
          if (!ecs->random_signal)
-           stop_signal = TARGET_SIGNAL_TRAP;
+           ecs->event_thread->stop_signal = TARGET_SIGNAL_TRAP;
        }
     }
 
@@ -2671,17 +2662,18 @@ process_event_stop_test:
       int printed = 0;
 
       if (debug_infrun)
-        fprintf_unfiltered (gdb_stdlog, "infrun: random signal %d\n", stop_signal);
+        fprintf_unfiltered (gdb_stdlog, "infrun: random signal %d\n",
+                            ecs->event_thread->stop_signal);
 
       stopped_by_random_signal = 1;
 
-      if (signal_print[stop_signal])
+      if (signal_print[ecs->event_thread->stop_signal])
        {
          printed = 1;
          target_terminal_ours_for_output ();
-         print_stop_reason (SIGNAL_RECEIVED, stop_signal);
+         print_stop_reason (SIGNAL_RECEIVED, ecs->event_thread->stop_signal);
        }
-      if (signal_stop_state (stop_signal))
+      if (signal_stop_state (ecs->event_thread->stop_signal))
        {
          stop_stepping (ecs);
          return;
@@ -2692,8 +2684,8 @@ process_event_stop_test:
        target_terminal_inferior ();
 
       /* Clear the signal if it should not be passed.  */
-      if (signal_program[stop_signal] == 0)
-       stop_signal = TARGET_SIGNAL_0;
+      if (signal_program[ecs->event_thread->stop_signal] == 0)
+       ecs->event_thread->stop_signal = TARGET_SIGNAL_0;
 
       if (ecs->event_thread->prev_pc == read_pc ()
          && ecs->event_thread->trap_expected
@@ -2721,7 +2713,7 @@ process_event_stop_test:
        }
 
       if (ecs->event_thread->step_range_end != 0
-         && stop_signal != TARGET_SIGNAL_0
+         && ecs->event_thread->stop_signal != TARGET_SIGNAL_0
          && (ecs->event_thread->step_range_start <= stop_pc
              && stop_pc < ecs->event_thread->step_range_end)
          && frame_id_eq (get_frame_id (get_current_frame ()),
@@ -2762,7 +2754,7 @@ process_event_stop_test:
     CORE_ADDR jmp_buf_pc;
     struct bpstat_what what;
 
-    what = bpstat_what (stop_bpstat);
+    what = bpstat_what (ecs->event_thread->stop_bpstat);
 
     if (what.call_dummy)
       {
@@ -2811,7 +2803,7 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
        gdb_assert (ecs->event_thread->step_resume_breakpoint != NULL);
        delete_step_resume_breakpoint (ecs->event_thread);
 
-       stop_step = 1;
+       ecs->event_thread->stop_step = 1;
        print_stop_reason (END_STEPPING_RANGE, 0);
        stop_stepping (ecs);
        return;
@@ -2931,7 +2923,7 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
                 code or stubs in libdld.sl, such as "shl_load" and
                 friends) until we reach non-dld code.  At that point,
                 we can stop stepping. */
-             bpstat_get_triggered_catchpoints (stop_bpstat,
+             bpstat_get_triggered_catchpoints (ecs->event_thread->stop_bpstat,
                                                &ecs->
                                                event_thread->
                                                stepping_through_solib_catchpoints);
@@ -2986,8 +2978,9 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
       /* Else, stop and report the catchpoint(s) whose triggering
          caused us to begin stepping. */
       ecs->event_thread->stepping_through_solib_after_catch = 0;
-      bpstat_clear (&stop_bpstat);
-      stop_bpstat = bpstat_copy (ecs->event_thread->stepping_through_solib_catchpoints);
+      bpstat_clear (&ecs->event_thread->stop_bpstat);
+      ecs->event_thread->stop_bpstat
+       = bpstat_copy (ecs->event_thread->stepping_through_solib_catchpoints);
       bpstat_clear (&ecs->event_thread->stepping_through_solib_catchpoints);
       stop_print_frame = 1;
       stop_stepping (ecs);
@@ -3038,7 +3031,7 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
      loader dynamic symbol resolution code, we keep on single stepping
      until we exit the run time loader code and reach the callee's
      address.  */
-  if (step_over_calls == STEP_OVER_UNDEBUGGABLE
+  if (ecs->event_thread->step_over_calls == STEP_OVER_UNDEBUGGABLE
       && in_solib_dynsym_resolve_code (stop_pc))
     {
       CORE_ADDR pc_after_resolver =
@@ -3063,8 +3056,8 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
     }
 
   if (ecs->event_thread->step_range_end != 1
-      && (step_over_calls == STEP_OVER_UNDEBUGGABLE
-         || step_over_calls == STEP_OVER_ALL)
+      && (ecs->event_thread->step_over_calls == STEP_OVER_UNDEBUGGABLE
+         || ecs->event_thread->step_over_calls == STEP_OVER_ALL)
       && get_frame_type (get_current_frame ()) == SIGTRAMP_FRAME)
     {
       if (debug_infrun)
@@ -3096,7 +3089,7 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
       if (debug_infrun)
         fprintf_unfiltered (gdb_stdlog, "infrun: stepped into subroutine\n");
 
-      if ((step_over_calls == STEP_OVER_NONE)
+      if ((ecs->event_thread->step_over_calls == STEP_OVER_NONE)
          || ((ecs->event_thread->step_range_end == 1)
              && in_prologue (ecs->event_thread->prev_pc,
                              ecs->stop_func_start)))
@@ -3107,13 +3100,13 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
          /* Also, maybe we just did a "nexti" inside a prolog, so we
             thought it was a subroutine call but it was not.  Stop as
             well.  FENN */
-         stop_step = 1;
+         ecs->event_thread->stop_step = 1;
          print_stop_reason (END_STEPPING_RANGE, 0);
          stop_stepping (ecs);
          return;
        }
 
-      if (step_over_calls == STEP_OVER_ALL)
+      if (ecs->event_thread->step_over_calls == STEP_OVER_ALL)
        {
          /* We're doing a "next", set a breakpoint at callee's return
             address (the address at which the caller will
@@ -3166,9 +3159,10 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
       /* If we have no line number and the step-stop-if-no-debug is
          set, we stop the step so that the user has a chance to switch
          in assembly mode.  */
-      if (step_over_calls == STEP_OVER_UNDEBUGGABLE && step_stop_if_no_debug)
+      if (ecs->event_thread->step_over_calls == STEP_OVER_UNDEBUGGABLE
+         && step_stop_if_no_debug)
        {
-         stop_step = 1;
+         ecs->event_thread->stop_step = 1;
          print_stop_reason (END_STEPPING_RANGE, 0);
          stop_stepping (ecs);
          return;
@@ -3221,7 +3215,7 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
   /* NOTE: tausq/2004-05-24: This if block used to be done before all
      the trampoline processing logic, however, there are some trampolines 
      that have no names, so we should do trampoline handling first.  */
-  if (step_over_calls == STEP_OVER_UNDEBUGGABLE
+  if (ecs->event_thread->step_over_calls == STEP_OVER_UNDEBUGGABLE
       && ecs->stop_func_name == NULL
       && stop_pc_sal.line == 0)
     {
@@ -3242,7 +3236,7 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
          /* If we have no line number and the step-stop-if-no-debug
             is set, we stop the step so that the user has a chance to
             switch in assembly mode.  */
-         stop_step = 1;
+         ecs->event_thread->stop_step = 1;
          print_stop_reason (END_STEPPING_RANGE, 0);
          stop_stepping (ecs);
          return;
@@ -3263,7 +3257,7 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
          one instruction.  */
       if (debug_infrun)
         fprintf_unfiltered (gdb_stdlog, "infrun: stepi/nexti\n");
-      stop_step = 1;
+      ecs->event_thread->stop_step = 1;
       print_stop_reason (END_STEPPING_RANGE, 0);
       stop_stepping (ecs);
       return;
@@ -3277,7 +3271,7 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
          or can this happen as a result of a return or longjmp?).  */
       if (debug_infrun)
         fprintf_unfiltered (gdb_stdlog, "infrun: no line number info\n");
-      stop_step = 1;
+      ecs->event_thread->stop_step = 1;
       print_stop_reason (END_STEPPING_RANGE, 0);
       stop_stepping (ecs);
       return;
@@ -3293,7 +3287,7 @@ infrun: BPSTAT_WHAT_SET_LONGJMP_RESUME (!gdbarch_get_longjmp_target)\n");
          better.  */
       if (debug_infrun)
         fprintf_unfiltered (gdb_stdlog, "infrun: stepped to a different line\n");
-      stop_step = 1;
+      ecs->event_thread->stop_step = 1;
       print_stop_reason (END_STEPPING_RANGE, 0);
       stop_stepping (ecs);
       return;
@@ -3380,7 +3374,7 @@ step_into_function (struct execution_control_state *ecs)
   if (ecs->stop_func_start == stop_pc)
     {
       /* We are already there: stop now.  */
-      stop_step = 1;
+      ecs->event_thread->stop_step = 1;
       print_stop_reason (END_STEPPING_RANGE, 0);
       stop_stepping (ecs);
       return;
@@ -3524,12 +3518,14 @@ keep_going (struct execution_control_state *ecs)
   /* If we did not do break;, it means we should keep running the
      inferior and not return to debugger.  */
 
-  if (ecs->event_thread->trap_expected && stop_signal != TARGET_SIGNAL_TRAP)
+  if (ecs->event_thread->trap_expected
+      && ecs->event_thread->stop_signal != TARGET_SIGNAL_TRAP)
     {
       /* We took a signal (which we are supposed to pass through to
         the inferior, else we'd not get here) and we haven't yet
         gotten our trap.  Simply continue.  */
-      resume (currently_stepping (ecs->event_thread), stop_signal);
+      resume (currently_stepping (ecs->event_thread),
+             ecs->event_thread->stop_signal);
     }
   else
     {
@@ -3584,11 +3580,12 @@ keep_going (struct execution_control_state *ecs)
          simulator; the simulator then delivers the hardware
          equivalent of a SIGNAL_TRAP to the program being debugged. */
 
-      if (stop_signal == TARGET_SIGNAL_TRAP && !signal_program[stop_signal])
-       stop_signal = TARGET_SIGNAL_0;
-
+      if (ecs->event_thread->stop_signal == TARGET_SIGNAL_TRAP
+         && !signal_program[ecs->event_thread->stop_signal])
+       ecs->event_thread->stop_signal = TARGET_SIGNAL_0;
 
-      resume (currently_stepping (ecs->event_thread), stop_signal);
+      resume (currently_stepping (ecs->event_thread),
+             ecs->event_thread->stop_signal);
     }
 
   prepare_to_wait (ecs);
@@ -3637,7 +3634,8 @@ print_stop_reason (enum inferior_stop_reason stop_reason, int stop_info)
       /* For now print nothing. */
       /* Print a message only if not in the middle of doing a "step n"
          operation for n > 1 */
-      if (!step_multi || !stop_step)
+      if (!inferior_thread ()->step_multi
+         || !inferior_thread ()->stop_step)
        if (ui_out_is_mi_like_p (uiout))
          ui_out_field_string
            (uiout, "reason",
@@ -3786,7 +3784,11 @@ Further execution is probably impossible.\n"));
 
   /* Don't print a message if in the middle of doing a "step n"
      operation for n > 1 */
-  if (step_multi && stop_step)
+  if (target_has_execution
+      && last.kind != TARGET_WAITKIND_SIGNALLED
+      && last.kind != TARGET_WAITKIND_EXITED
+      && inferior_thread ()->step_multi
+      && inferior_thread ()->stop_step)
     goto done;
 
   target_terminal_ours ();
@@ -3797,17 +3799,12 @@ Further execution is probably impossible.\n"));
   if (target_has_stack && !stop_stack_dummy)
     set_current_sal_from_frame (get_current_frame (), 1);
 
-  /* Look up the hook_stop and run it (CLI internally handles problem
-     of stop_command's pre-hook not existing).  */
-  if (stop_command)
-    catch_errors (hook_stop_stub, stop_command,
-                 "Error while running hook_stop:\n", RETURN_MASK_ALL);
-
   if (!target_has_stack)
-    {
+    goto done;
 
-      goto done;
-    }
+  if (last.kind == TARGET_WAITKIND_SIGNALLED
+      || last.kind == TARGET_WAITKIND_EXITED)
+    goto done;
 
   /* Select innermost stack frame - i.e., current frame is frame 0,
      and current location is based on that.
@@ -3832,8 +3829,9 @@ Further execution is probably impossible.\n"));
          int bpstat_ret;
          int source_flag;
          int do_frame_printing = 1;
+         struct thread_info *tp = inferior_thread ();
 
-         bpstat_ret = bpstat_print (stop_bpstat);
+         bpstat_ret = bpstat_print (tp->stop_bpstat);
          switch (bpstat_ret)
            {
            case PRINT_UNKNOWN:
@@ -3852,8 +3850,8 @@ Further execution is probably impossible.\n"));
              /* FIXME: cagney/2002-12-01: Given that a frame ID does
                 (or should) carry around the function and does (or
                 should) use that when doing a frame comparison.  */
-             if (stop_step
-                 && frame_id_eq (inferior_thread ()->step_frame_id,
+             if (tp->stop_step
+                 && frame_id_eq (tp->step_frame_id,
                                  get_frame_id (get_current_frame ()))
                  && step_start_function == find_pc_function (stop_pc))
                source_flag = SRC_LINE; /* finished step, just print source line */
@@ -3905,7 +3903,7 @@ Further execution is probably impossible.\n"));
 
   /* Save the function value return registers, if we care.
      We might be about to restore their previous contents.  */
-  if (proceed_to_finish)
+  if (inferior_thread ()->proceed_to_finish)
     {
       /* This should not be necessary.  */
       if (stop_registers)
@@ -3931,21 +3929,37 @@ Further execution is probably impossible.\n"));
 
 done:
   annotate_stopped ();
-  if (!suppress_stop_observer && !step_multi)
-    observer_notify_normal_stop (stop_bpstat);
-  /* Delete the breakpoint we stopped at, if it wants to be deleted.
-     Delete any breakpoint that is to be deleted at the next stop.  */
-  breakpoint_auto_delete (stop_bpstat);
-
+  if (!suppress_stop_observer
+      && !(target_has_execution
+          && last.kind != TARGET_WAITKIND_SIGNALLED
+          && last.kind != TARGET_WAITKIND_EXITED
+          && inferior_thread ()->step_multi))
+    {
+      if (!ptid_equal (inferior_ptid, null_ptid))
+       observer_notify_normal_stop (inferior_thread ()->stop_bpstat);
+      else
+       observer_notify_normal_stop (NULL);
+    }
   if (target_has_execution
       && last.kind != TARGET_WAITKIND_SIGNALLED
       && last.kind != TARGET_WAITKIND_EXITED)
     {
+      /* Delete the breakpoint we stopped at, if it wants to be deleted.
+        Delete any breakpoint that is to be deleted at the next stop.  */
+      breakpoint_auto_delete (inferior_thread ()->stop_bpstat);
+
       if (!non_stop)
        set_running (pid_to_ptid (-1), 0);
       else
        set_running (inferior_ptid, 0);
     }
+
+  /* Look up the hook_stop and run it (CLI internally handles problem
+     of stop_command's pre-hook not existing).  */
+  if (stop_command)
+    catch_errors (hook_stop_stub, stop_command,
+                 "Error while running hook_stop:\n", RETURN_MASK_ALL);
+
 }
 
 static int
@@ -4363,27 +4377,27 @@ save_inferior_status (int restore_stack_info)
   struct inferior_status *inf_status = XMALLOC (struct inferior_status);
   struct thread_info *tp = inferior_thread ();
 
-  inf_status->stop_signal = stop_signal;
+  inf_status->stop_signal = tp->stop_signal;
   inf_status->stop_pc = stop_pc;
-  inf_status->stop_step = stop_step;
+  inf_status->stop_step = tp->stop_step;
   inf_status->stop_stack_dummy = stop_stack_dummy;
   inf_status->stopped_by_random_signal = stopped_by_random_signal;
   inf_status->stepping_over_breakpoint = tp->trap_expected;
   inf_status->step_range_start = tp->step_range_start;
   inf_status->step_range_end = tp->step_range_end;
   inf_status->step_frame_id = tp->step_frame_id;
-  inf_status->step_over_calls = step_over_calls;
+  inf_status->step_over_calls = tp->step_over_calls;
   inf_status->stop_after_trap = stop_after_trap;
   inf_status->stop_soon = stop_soon;
   /* Save original bpstat chain here; replace it with copy of chain.
      If caller's caller is walking the chain, they'll be happier if we
      hand them back the original chain when restore_inferior_status is
      called.  */
-  inf_status->stop_bpstat = stop_bpstat;
-  stop_bpstat = bpstat_copy (stop_bpstat);
+  inf_status->stop_bpstat = tp->stop_bpstat;
+  tp->stop_bpstat = bpstat_copy (tp->stop_bpstat);
   inf_status->breakpoint_proceeded = breakpoint_proceeded;
   inf_status->restore_stack_info = restore_stack_info;
-  inf_status->proceed_to_finish = proceed_to_finish;
+  inf_status->proceed_to_finish = tp->proceed_to_finish;
 
   inf_status->registers = regcache_dup (get_current_regcache ());
 
@@ -4417,22 +4431,22 @@ restore_inferior_status (struct inferior_status *inf_status)
 {
   struct thread_info *tp = inferior_thread ();
 
-  stop_signal = inf_status->stop_signal;
+  tp->stop_signal = inf_status->stop_signal;
   stop_pc = inf_status->stop_pc;
-  stop_step = inf_status->stop_step;
+  tp->stop_step = inf_status->stop_step;
   stop_stack_dummy = inf_status->stop_stack_dummy;
   stopped_by_random_signal = inf_status->stopped_by_random_signal;
   tp->trap_expected = inf_status->stepping_over_breakpoint;
   tp->step_range_start = inf_status->step_range_start;
   tp->step_range_end = inf_status->step_range_end;
   tp->step_frame_id = inf_status->step_frame_id;
-  step_over_calls = inf_status->step_over_calls;
+  tp->step_over_calls = inf_status->step_over_calls;
   stop_after_trap = inf_status->stop_after_trap;
   stop_soon = inf_status->stop_soon;
-  bpstat_clear (&stop_bpstat);
-  stop_bpstat = inf_status->stop_bpstat;
+  bpstat_clear (&tp->stop_bpstat);
+  tp->stop_bpstat = inf_status->stop_bpstat;
   breakpoint_proceeded = inf_status->breakpoint_proceeded;
-  proceed_to_finish = inf_status->proceed_to_finish;
+  tp->proceed_to_finish = inf_status->proceed_to_finish;
 
   /* The inferior can be gone if the user types "print exit(0)"
      (and perhaps other times).  */
This page took 0.03648 seconds and 4 git commands to generate.