Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(192)

Side by Side Diff: runtime/vm/thread_interrupter_fuchsia.cc

Issue 2935483002: Update Fuchsia-specific code to use the new MX_ error names (Closed)
Patch Set: not windows tho Created 3 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « runtime/vm/os_thread_fuchsia.cc ('k') | runtime/vm/virtual_memory_fuchsia.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 #include "platform/globals.h" 5 #include "platform/globals.h"
6 #if defined(HOST_OS_FUCHSIA) 6 #if defined(HOST_OS_FUCHSIA)
7 7
8 #include "vm/thread_interrupter.h" 8 #include "vm/thread_interrupter.h"
9 9
10 #include <magenta/process.h> 10 #include <magenta/process.h>
(...skipping 22 matching lines...) Expand all
33 // feature is added for it. 33 // feature is added for it.
34 34
35 // A scope within which a target thread is suspended. When the scope is exited, 35 // A scope within which a target thread is suspended. When the scope is exited,
36 // the thread is resumed and its handle is closed. 36 // the thread is resumed and its handle is closed.
37 class ThreadSuspendScope { 37 class ThreadSuspendScope {
38 public: 38 public:
39 explicit ThreadSuspendScope(mx_handle_t thread_handle) 39 explicit ThreadSuspendScope(mx_handle_t thread_handle)
40 : thread_handle_(thread_handle), suspended_(true) { 40 : thread_handle_(thread_handle), suspended_(true) {
41 mx_status_t status = mx_task_suspend(thread_handle); 41 mx_status_t status = mx_task_suspend(thread_handle);
42 // If a thread is somewhere where suspend is impossible, mx_task_suspend() 42 // If a thread is somewhere where suspend is impossible, mx_task_suspend()
43 // can return ERR_NOT_SUPPORTED. 43 // can return MX_ERR_NOT_SUPPORTED.
44 if (status != NO_ERROR) { 44 if (status != MX_OK) {
45 if (FLAG_trace_thread_interrupter) { 45 if (FLAG_trace_thread_interrupter) {
46 OS::PrintErr("ThreadInterrupter: mx_task_suspend failed: %s\n", 46 OS::PrintErr("ThreadInterrupter: mx_task_suspend failed: %s\n",
47 mx_status_get_string(status)); 47 mx_status_get_string(status));
48 } 48 }
49 suspended_ = false; 49 suspended_ = false;
50 } 50 }
51 } 51 }
52 52
53 ~ThreadSuspendScope() { 53 ~ThreadSuspendScope() {
54 if (suspended_) { 54 if (suspended_) {
55 mx_status_t status = mx_task_resume(thread_handle_, 0); 55 mx_status_t status = mx_task_resume(thread_handle_, 0);
56 if (status != NO_ERROR) { 56 if (status != MX_OK) {
57 // If we fail to resume a thread, then it's likely the program will 57 // If we fail to resume a thread, then it's likely the program will
58 // hang. Crash instead. 58 // hang. Crash instead.
59 FATAL1("mx_task_resume failed: %s", mx_status_get_string(status)); 59 FATAL1("mx_task_resume failed: %s", mx_status_get_string(status));
60 } 60 }
61 } 61 }
62 mx_handle_close(thread_handle_); 62 mx_handle_close(thread_handle_);
63 } 63 }
64 64
65 bool suspended() const { return suspended_; } 65 bool suspended() const { return suspended_; }
66 66
67 private: 67 private:
68 mx_handle_t thread_handle_; 68 mx_handle_t thread_handle_;
69 bool suspended_; 69 bool suspended_;
70 70
71 DISALLOW_ALLOCATION(); 71 DISALLOW_ALLOCATION();
72 DISALLOW_COPY_AND_ASSIGN(ThreadSuspendScope); 72 DISALLOW_COPY_AND_ASSIGN(ThreadSuspendScope);
73 }; 73 };
74 74
75 class ThreadInterrupterFuchsia : public AllStatic { 75 class ThreadInterrupterFuchsia : public AllStatic {
76 public: 76 public:
77 #if defined(TARGET_ARCH_X64) 77 #if defined(TARGET_ARCH_X64)
78 static bool GrabRegisters(mx_handle_t thread, InterruptedThreadState* state) { 78 static bool GrabRegisters(mx_handle_t thread, InterruptedThreadState* state) {
79 mx_x86_64_general_regs_t regs; 79 mx_x86_64_general_regs_t regs;
80 uint32_t regset_size; 80 uint32_t regset_size;
81 mx_status_t status = mx_thread_read_state( 81 mx_status_t status = mx_thread_read_state(
82 thread, MX_THREAD_STATE_REGSET0, &regs, sizeof(regs), &regset_size); 82 thread, MX_THREAD_STATE_REGSET0, &regs, sizeof(regs), &regset_size);
83 if (status != NO_ERROR) { 83 if (status != MX_OK) {
84 if (FLAG_trace_thread_interrupter) { 84 if (FLAG_trace_thread_interrupter) {
85 OS::PrintErr("ThreadInterrupter failed to get registers: %s\n", 85 OS::PrintErr("ThreadInterrupter failed to get registers: %s\n",
86 mx_status_get_string(status)); 86 mx_status_get_string(status));
87 } 87 }
88 return false; 88 return false;
89 } 89 }
90 state->pc = static_cast<uintptr_t>(regs.rip); 90 state->pc = static_cast<uintptr_t>(regs.rip);
91 state->fp = static_cast<uintptr_t>(regs.rbp); 91 state->fp = static_cast<uintptr_t>(regs.rbp);
92 state->csp = static_cast<uintptr_t>(regs.rsp); 92 state->csp = static_cast<uintptr_t>(regs.rsp);
93 state->dsp = static_cast<uintptr_t>(regs.rsp); 93 state->dsp = static_cast<uintptr_t>(regs.rsp);
94 return true; 94 return true;
95 } 95 }
96 #elif defined(TARGET_ARCH_ARM64) 96 #elif defined(TARGET_ARCH_ARM64)
97 static bool GrabRegisters(mx_handle_t thread, InterruptedThreadState* state) { 97 static bool GrabRegisters(mx_handle_t thread, InterruptedThreadState* state) {
98 mx_arm64_general_regs_t regs; 98 mx_arm64_general_regs_t regs;
99 uint32_t regset_size; 99 uint32_t regset_size;
100 mx_status_t status = mx_thread_read_state( 100 mx_status_t status = mx_thread_read_state(
101 thread, MX_THREAD_STATE_REGSET0, &regs, sizeof(regs), &regset_size); 101 thread, MX_THREAD_STATE_REGSET0, &regs, sizeof(regs), &regset_size);
102 if (status != NO_ERROR) { 102 if (status != MX_OK) {
103 if (FLAG_trace_thread_interrupter) { 103 if (FLAG_trace_thread_interrupter) {
104 OS::PrintErr("ThreadInterrupter failed to get registers: %s\n", 104 OS::PrintErr("ThreadInterrupter failed to get registers: %s\n",
105 mx_status_get_string(status)); 105 mx_status_get_string(status));
106 } 106 }
107 return false; 107 return false;
108 } 108 }
109 state->pc = static_cast<uintptr_t>(regs.pc); 109 state->pc = static_cast<uintptr_t>(regs.pc);
110 state->fp = static_cast<uintptr_t>(regs.r[FPREG]); 110 state->fp = static_cast<uintptr_t>(regs.r[FPREG]);
111 state->csp = static_cast<uintptr_t>(regs.sp); 111 state->csp = static_cast<uintptr_t>(regs.sp);
112 state->dsp = static_cast<uintptr_t>(regs.r[SPREG]); 112 state->dsp = static_cast<uintptr_t>(regs.r[SPREG]);
(...skipping 11 matching lines...) Expand all
124 124
125 // Get a handle on the target thread. 125 // Get a handle on the target thread.
126 const mx_koid_t target_thread_koid = os_thread->id(); 126 const mx_koid_t target_thread_koid = os_thread->id();
127 if (FLAG_trace_thread_interrupter) { 127 if (FLAG_trace_thread_interrupter) {
128 OS::PrintErr("ThreadInterrupter: interrupting thread with koid=%d\n", 128 OS::PrintErr("ThreadInterrupter: interrupting thread with koid=%d\n",
129 target_thread_koid); 129 target_thread_koid);
130 } 130 }
131 mx_handle_t target_thread_handle; 131 mx_handle_t target_thread_handle;
132 status = mx_object_get_child(mx_process_self(), target_thread_koid, 132 status = mx_object_get_child(mx_process_self(), target_thread_koid,
133 MX_RIGHT_SAME_RIGHTS, &target_thread_handle); 133 MX_RIGHT_SAME_RIGHTS, &target_thread_handle);
134 if (status != NO_ERROR) { 134 if (status != MX_OK) {
135 if (FLAG_trace_thread_interrupter) { 135 if (FLAG_trace_thread_interrupter) {
136 OS::PrintErr("ThreadInterrupter: mx_object_get_child failed: %s\n", 136 OS::PrintErr("ThreadInterrupter: mx_object_get_child failed: %s\n",
137 mx_status_get_string(status)); 137 mx_status_get_string(status));
138 } 138 }
139 return; 139 return;
140 } 140 }
141 if (target_thread_handle == MX_HANDLE_INVALID) { 141 if (target_thread_handle == MX_HANDLE_INVALID) {
142 if (FLAG_trace_thread_interrupter) { 142 if (FLAG_trace_thread_interrupter) {
143 OS::PrintErr( 143 OS::PrintErr(
144 "ThreadInterrupter: mx_object_get_child gave an invalid " 144 "ThreadInterrupter: mx_object_get_child gave an invalid "
145 "thread handle!"); 145 "thread handle!");
146 } 146 }
147 return; 147 return;
148 } 148 }
149 149
150 // This scope suspends the thread. When we exit the scope, the thread is 150 // This scope suspends the thread. When we exit the scope, the thread is
151 // resumed, and the thread handle is closed. 151 // resumed, and the thread handle is closed.
152 ThreadSuspendScope tss(target_thread_handle); 152 ThreadSuspendScope tss(target_thread_handle);
153 if (!tss.suspended()) { 153 if (!tss.suspended()) {
154 return; 154 return;
155 } 155 }
156 156
157 // Check that the thread is suspended. 157 // Check that the thread is suspended.
158 status = PollThreadUntilSuspended(target_thread_handle); 158 status = PollThreadUntilSuspended(target_thread_handle);
159 if (status != NO_ERROR) { 159 if (status != MX_OK) {
160 return; 160 return;
161 } 161 }
162 162
163 // Grab the target thread's registers. 163 // Grab the target thread's registers.
164 InterruptedThreadState its; 164 InterruptedThreadState its;
165 if (!GrabRegisters(target_thread_handle, &its)) { 165 if (!GrabRegisters(target_thread_handle, &its)) {
166 return; 166 return;
167 } 167 }
168 // Currently we sample only threads that are associated 168 // Currently we sample only threads that are associated
169 // with an isolate. It is safe to call 'os_thread->thread()' 169 // with an isolate. It is safe to call 'os_thread->thread()'
(...skipping 26 matching lines...) Expand all
196 196
197 static mx_status_t PollThreadUntilSuspended(mx_handle_t thread_handle) { 197 static mx_status_t PollThreadUntilSuspended(mx_handle_t thread_handle) {
198 const intptr_t kMaxPollAttempts = 10; 198 const intptr_t kMaxPollAttempts = 10;
199 intptr_t poll_tries = 0; 199 intptr_t poll_tries = 0;
200 while (poll_tries < kMaxPollAttempts) { 200 while (poll_tries < kMaxPollAttempts) {
201 mx_info_thread_t thread_info; 201 mx_info_thread_t thread_info;
202 mx_status_t status = 202 mx_status_t status =
203 mx_object_get_info(thread_handle, MX_INFO_THREAD, &thread_info, 203 mx_object_get_info(thread_handle, MX_INFO_THREAD, &thread_info,
204 sizeof(thread_info), NULL, NULL); 204 sizeof(thread_info), NULL, NULL);
205 poll_tries++; 205 poll_tries++;
206 if (status != NO_ERROR) { 206 if (status != MX_OK) {
207 if (FLAG_trace_thread_interrupter) { 207 if (FLAG_trace_thread_interrupter) {
208 OS::PrintErr("ThreadInterrupter: mx_object_get_info failed: %s\n", 208 OS::PrintErr("ThreadInterrupter: mx_object_get_info failed: %s\n",
209 mx_status_get_string(status)); 209 mx_status_get_string(status));
210 } 210 }
211 return status; 211 return status;
212 } 212 }
213 if (thread_info.state == MX_THREAD_STATE_SUSPENDED) { 213 if (thread_info.state == MX_THREAD_STATE_SUSPENDED) {
214 // Success. 214 // Success.
215 return NO_ERROR; 215 return MX_OK;
216 } 216 }
217 if (thread_info.state == MX_THREAD_STATE_RUNNING) { 217 if (thread_info.state == MX_THREAD_STATE_RUNNING) {
218 // Poll. 218 // Poll.
219 continue; 219 continue;
220 } 220 }
221 if (FLAG_trace_thread_interrupter) { 221 if (FLAG_trace_thread_interrupter) {
222 OS::PrintErr("ThreadInterrupter: Thread is not suspended: %s\n", 222 OS::PrintErr("ThreadInterrupter: Thread is not suspended: %s\n",
223 ThreadStateGetString(thread_info.state)); 223 ThreadStateGetString(thread_info.state));
224 } 224 }
225 return ERR_BAD_STATE; 225 return MX_ERR_BAD_STATE;
226 } 226 }
227 if (FLAG_trace_thread_interrupter) { 227 if (FLAG_trace_thread_interrupter) {
228 OS::PrintErr("ThreadInterrupter: Exceeded max suspend poll tries\n"); 228 OS::PrintErr("ThreadInterrupter: Exceeded max suspend poll tries\n");
229 } 229 }
230 return ERR_BAD_STATE; 230 return MX_ERR_BAD_STATE;
231 } 231 }
232 }; 232 };
233 233
234 234
235 bool ThreadInterrupter::IsDebuggerAttached() { 235 bool ThreadInterrupter::IsDebuggerAttached() {
236 return false; 236 return false;
237 } 237 }
238 238
239 239
240 void ThreadInterrupter::InterruptThread(OSThread* thread) { 240 void ThreadInterrupter::InterruptThread(OSThread* thread) {
(...skipping 16 matching lines...) Expand all
257 257
258 void ThreadInterrupter::RemoveSignalHandler() { 258 void ThreadInterrupter::RemoveSignalHandler() {
259 // Nothing to do on Fuchsia. 259 // Nothing to do on Fuchsia.
260 } 260 }
261 261
262 #endif // !PRODUCT 262 #endif // !PRODUCT
263 263
264 } // namespace dart 264 } // namespace dart
265 265
266 #endif // defined(HOST_OS_FUCHSIA) 266 #endif // defined(HOST_OS_FUCHSIA)
OLDNEW
« no previous file with comments | « runtime/vm/os_thread_fuchsia.cc ('k') | runtime/vm/virtual_memory_fuchsia.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698