+ /* We try not to notify the observer if no thread has actually
+ changed the running state -- merely to reduce the number of
+ messages to the MI frontend. A frontend is supposed to handle
+ multiple *running notifications just fine. */
+ bool any_started = false;
+
+ for (thread_info *tp : all_non_exited_threads (targ, ptid))
+ if (set_running_thread (tp, running))
+ any_started = true;
+
+ if (any_started)
+ gdb::observers::target_resumed.notify (ptid);
+}
+
+
+/* Helper for set_executing. Set's the thread's 'executing' field
+ from EXECUTING, and if EXECUTING is true also clears the thread's
+ stop_pc. */
+
+static void
+set_executing_thread (thread_info *thr, bool executing)
+{
+ thr->executing = executing;
+ if (executing)
+ thr->suspend.stop_pc = ~(CORE_ADDR) 0;
+}
+
+void
+set_executing (process_stratum_target *targ, ptid_t ptid, bool executing)
+{
+ for (thread_info *tp : all_non_exited_threads (targ, ptid))
+ set_executing_thread (tp, executing);
+
+ /* It only takes one running thread to spawn more threads. */
+ if (executing)
+ targ->threads_executing = true;
+ /* Only clear the flag if the caller is telling us everything is
+ stopped. */
+ else if (minus_one_ptid == ptid)
+ targ->threads_executing = false;
+}
+
+/* See gdbthread.h. */
+
+bool
+threads_are_executing (process_stratum_target *target)
+{
+ return target->threads_executing;
+}
+
+void
+set_stop_requested (process_stratum_target *targ, ptid_t ptid, bool stop)
+{
+ for (thread_info *tp : all_non_exited_threads (targ, ptid))
+ tp->stop_requested = stop;
+
+ /* Call the stop requested observer so other components of GDB can
+ react to this request. */
+ if (stop)
+ gdb::observers::thread_stop_requested.notify (ptid);
+}
+
+void
+finish_thread_state (process_stratum_target *targ, ptid_t ptid)
+{
+ bool any_started = false;
+
+ for (thread_info *tp : all_non_exited_threads (targ, ptid))
+ if (set_running_thread (tp, tp->executing))
+ any_started = true;
+
+ if (any_started)
+ gdb::observers::target_resumed.notify (ptid);
+}
+
+/* See gdbthread.h. */
+
+void
+validate_registers_access (void)
+{
+ /* No selected thread, no registers. */
+ if (inferior_ptid == null_ptid)
+ error (_("No thread selected."));
+
+ thread_info *tp = inferior_thread ();
+
+ /* Don't try to read from a dead thread. */
+ if (tp->state == THREAD_EXITED)
+ error (_("The current thread has terminated"));
+
+ /* ... or from a spinning thread. FIXME: This isn't actually fully
+ correct. It'll allow an user-requested access (e.g., "print $pc"
+ at the prompt) when a thread is not executing for some internal
+ reason, but is marked running from the user's perspective. E.g.,
+ the thread is waiting for its turn in the step-over queue. */
+ if (tp->executing)
+ error (_("Selected thread is running."));
+}
+
+/* See gdbthread.h. */
+
+bool
+can_access_registers_thread (thread_info *thread)
+{
+ /* No thread, no registers. */
+ if (thread == NULL)
+ return false;
+
+ /* Don't try to read from a dead thread. */
+ if (thread->state == THREAD_EXITED)
+ return false;
+
+ /* ... or from a spinning thread. FIXME: see validate_registers_access. */
+ if (thread->executing)
+ return false;
+
+ return true;
+}
+
+int
+pc_in_thread_step_range (CORE_ADDR pc, struct thread_info *thread)
+{
+ return (pc >= thread->control.step_range_start
+ && pc < thread->control.step_range_end);
+}
+
+/* Helper for print_thread_info. Returns true if THR should be
+ printed. If REQUESTED_THREADS, a list of GDB ids/ranges, is not
+ NULL, only print THR if its ID is included in the list. GLOBAL_IDS
+ is true if REQUESTED_THREADS is list of global IDs, false if a list
+ of per-inferior thread ids. If PID is not -1, only print THR if it
+ is a thread from the process PID. Otherwise, threads from all
+ attached PIDs are printed. If both REQUESTED_THREADS is not NULL
+ and PID is not -1, then the thread is printed if it belongs to the
+ specified process. Otherwise, an error is raised. */