Add generated source files and fix thinko in aarch64-asm.c
[binutils-gdb.git] / gdb / process-stratum-target.c
blob8737938e3b493416a535734292db0f7e04d0d1df
1 /* Abstract base class inherited by all process_stratum targets
3 Copyright (C) 2018-2024 Free Software Foundation, Inc.
5 This file is part of GDB.
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
20 #include "defs.h"
21 #include "process-stratum-target.h"
22 #include "inferior.h"
23 #include <algorithm>
25 process_stratum_target::~process_stratum_target ()
29 struct gdbarch *
30 process_stratum_target::thread_architecture (ptid_t ptid)
32 inferior *inf = find_inferior_ptid (this, ptid);
33 gdb_assert (inf != NULL);
34 return inf->arch ();
37 bool
38 process_stratum_target::has_all_memory ()
40 /* If no inferior selected, then we can't read memory here. */
41 return inferior_ptid != null_ptid;
44 bool
45 process_stratum_target::has_memory ()
47 /* If no inferior selected, then we can't read memory here. */
48 return inferior_ptid != null_ptid;
51 bool
52 process_stratum_target::has_stack ()
54 /* If no inferior selected, there's no stack. */
55 return inferior_ptid != null_ptid;
58 bool
59 process_stratum_target::has_registers ()
61 /* Can't read registers from no inferior. */
62 return inferior_ptid != null_ptid;
65 bool
66 process_stratum_target::has_execution (inferior *inf)
68 /* If there's a process running already, we can't make it run
69 through hoops. */
70 return inf->pid != 0;
73 /* See process-stratum-target.h. */
75 void
76 process_stratum_target::follow_exec (inferior *follow_inf, ptid_t ptid,
77 const char *execd_pathname)
79 inferior *orig_inf = current_inferior ();
81 if (orig_inf != follow_inf)
83 /* Execution continues in a new inferior, push the original inferior's
84 process target on the new inferior's target stack. The process target
85 may decide to unpush itself from the original inferior's target stack
86 after that, at its discretion. */
87 follow_inf->push_target (orig_inf->process_target ());
88 thread_info *t = add_thread (follow_inf->process_target (), ptid);
90 /* Leave the new inferior / thread as the current inferior / thread. */
91 switch_to_thread (t);
95 /* See process-stratum-target.h. */
97 void
98 process_stratum_target::follow_fork (inferior *child_inf, ptid_t child_ptid,
99 target_waitkind fork_kind,
100 bool follow_child,
101 bool detach_on_fork)
103 if (child_inf != nullptr)
105 child_inf->push_target (this);
106 add_thread_silent (this, child_ptid);
110 /* See process-stratum-target.h. */
112 void
113 process_stratum_target::maybe_add_resumed_with_pending_wait_status
114 (thread_info *thread)
116 gdb_assert (!thread->resumed_with_pending_wait_status_node.is_linked ());
118 if (thread->resumed () && thread->has_pending_waitstatus ())
120 infrun_debug_printf ("adding to resumed threads with event list: %s",
121 thread->ptid.to_string ().c_str ());
122 m_resumed_with_pending_wait_status.push_back (*thread);
126 /* See process-stratum-target.h. */
128 void
129 process_stratum_target::maybe_remove_resumed_with_pending_wait_status
130 (thread_info *thread)
132 if (thread->resumed () && thread->has_pending_waitstatus ())
134 infrun_debug_printf ("removing from resumed threads with event list: %s",
135 thread->ptid.to_string ().c_str ());
136 gdb_assert (thread->resumed_with_pending_wait_status_node.is_linked ());
137 auto it = m_resumed_with_pending_wait_status.iterator_to (*thread);
138 m_resumed_with_pending_wait_status.erase (it);
140 else
141 gdb_assert (!thread->resumed_with_pending_wait_status_node.is_linked ());
144 /* See process-stratum-target.h. */
146 thread_info *
147 process_stratum_target::random_resumed_with_pending_wait_status
148 (inferior *inf, ptid_t filter_ptid)
150 auto matches = [inf, filter_ptid] (const thread_info &thread)
152 return thread.inf == inf && thread.ptid.matches (filter_ptid);
155 /* First see how many matching events we have. */
156 const auto &l = m_resumed_with_pending_wait_status;
157 unsigned int count = std::count_if (l.begin (), l.end (), matches);
159 if (count == 0)
160 return nullptr;
162 /* Now randomly pick a thread out of those that match the criteria. */
163 int random_selector
164 = (int) ((count * (double) rand ()) / (RAND_MAX + 1.0));
166 if (count > 1)
167 infrun_debug_printf ("Found %u events, selecting #%d",
168 count, random_selector);
170 /* Select the Nth thread that matches. */
171 auto it = std::find_if (l.begin (), l.end (),
172 [&random_selector, &matches]
173 (const thread_info &thread)
175 if (!matches (thread))
176 return false;
178 return random_selector-- == 0;
181 gdb_assert (it != l.end ());
183 return &*it;
186 /* See process-stratum-target.h. */
188 thread_info *
189 process_stratum_target::find_thread (ptid_t ptid)
191 inferior *inf = find_inferior_ptid (this, ptid);
192 if (inf == NULL)
193 return NULL;
194 return inf->find_thread (ptid);
197 /* See process-stratum-target.h. */
199 std::set<process_stratum_target *>
200 all_non_exited_process_targets ()
202 /* Inferiors may share targets. To eliminate duplicates, use a set. */
203 std::set<process_stratum_target *> targets;
204 for (inferior *inf : all_non_exited_inferiors ())
205 targets.insert (inf->process_target ());
207 return targets;
210 /* See process-stratum-target.h. */
212 void
213 switch_to_target_no_thread (process_stratum_target *target)
215 for (inferior *inf : all_inferiors (target))
217 switch_to_inferior_no_thread (inf);
218 break;