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

Side by Side Diff: base/process_util_posix.cc

Issue 39185: Make CrashAwareSleep more accurate on POSIX (checking if the process exists). (Closed)
Patch Set: wrap success Created 11 years, 9 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 | « no previous file | no next file » | 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) 2006-2008 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include <dirent.h> 5 #include <dirent.h>
6 #include <errno.h> 6 #include <errno.h>
7 #include <fcntl.h> 7 #include <fcntl.h>
8 #include <signal.h> 8 #include <signal.h>
9 #include <stdlib.h> 9 #include <stdlib.h>
10 #include <sys/resource.h> 10 #include <sys/resource.h>
(...skipping 166 matching lines...) Expand 10 before | Expand all | Expand 10 after
177 return true; 177 return true;
178 } 178 }
179 179
180 // If it didn't exit cleanly, it must have been signaled. 180 // If it didn't exit cleanly, it must have been signaled.
181 DCHECK(WIFSIGNALED(status)); 181 DCHECK(WIFSIGNALED(status));
182 return false; 182 return false;
183 } 183 }
184 184
185 namespace { 185 namespace {
186 186
187 int WaitpidWithTimeout(ProcessHandle handle, int wait_milliseconds) { 187 int WaitpidWithTimeout(ProcessHandle handle, int wait_milliseconds,
188 bool* success) {
188 // This POSIX version of this function only guarantees that we wait no less 189 // This POSIX version of this function only guarantees that we wait no less
189 // than |wait_milliseconds| for the proces to exit. The child process may 190 // than |wait_milliseconds| for the proces to exit. The child process may
190 // exit sometime before the timeout has ended but we may still block for 191 // exit sometime before the timeout has ended but we may still block for
191 // up to 0.25 seconds after the fact. 192 // up to 0.25 seconds after the fact.
192 // 193 //
193 // waitpid() has no direct support on POSIX for specifying a timeout, you can 194 // waitpid() has no direct support on POSIX for specifying a timeout, you can
194 // either ask it to block indefinitely or return immediately (WNOHANG). 195 // either ask it to block indefinitely or return immediately (WNOHANG).
195 // When a child process terminates a SIGCHLD signal is sent to the parent. 196 // When a child process terminates a SIGCHLD signal is sent to the parent.
196 // Catching this signal would involve installing a signal handler which may 197 // Catching this signal would involve installing a signal handler which may
197 // affect other parts of the application and would be difficult to debug. 198 // affect other parts of the application and would be difficult to debug.
(...skipping 25 matching lines...) Expand all
223 if (sleep_time_usecs > kQuarterSecondInMicroseconds) { 224 if (sleep_time_usecs > kQuarterSecondInMicroseconds) {
224 sleep_time_usecs = kQuarterSecondInMicroseconds; 225 sleep_time_usecs = kQuarterSecondInMicroseconds;
225 } 226 }
226 227
227 // usleep() will return 0 and set errno to EINTR on receipt of a signal 228 // usleep() will return 0 and set errno to EINTR on receipt of a signal
228 // such as SIGCHLD. 229 // such as SIGCHLD.
229 usleep(sleep_time_usecs); 230 usleep(sleep_time_usecs);
230 ret_pid = waitpid(handle, &status, WNOHANG); 231 ret_pid = waitpid(handle, &status, WNOHANG);
231 } 232 }
232 233
234 if (success)
235 *success = (ret_pid != -1);
236
233 return status; 237 return status;
234 } 238 }
235 239
236 } // namespace 240 } // namespace
237 241
238 bool WaitForSingleProcess(ProcessHandle handle, int wait_milliseconds) { 242 bool WaitForSingleProcess(ProcessHandle handle, int wait_milliseconds) {
239 int status = WaitpidWithTimeout(handle, wait_milliseconds); 243 bool waitpid_success;
240 if (status != -1) 244 int status = WaitpidWithTimeout(handle, wait_milliseconds, &waitpid_success);
245 if (status != -1) {
246 DCHECK(waitpid_success);
241 return WIFEXITED(status); 247 return WIFEXITED(status);
242 else 248 } else {
243 return false; 249 return false;
250 }
244 } 251 }
245 252
246 bool CrashAwareSleep(ProcessHandle handle, int wait_milliseconds) { 253 bool CrashAwareSleep(ProcessHandle handle, int wait_milliseconds) {
247 int status = WaitpidWithTimeout(handle, wait_milliseconds); 254 bool waitpid_success;
248 if (status != -1) 255 int status = WaitpidWithTimeout(handle, wait_milliseconds, &waitpid_success);
256 if (status != -1) {
257 DCHECK(waitpid_success);
249 return !(WIFEXITED(status) || WIFSIGNALED(status)); 258 return !(WIFEXITED(status) || WIFSIGNALED(status));
250 else 259 } else {
251 return true; 260 // If waitpid returned with an error, then the process doesn't exist
261 // (which most probably means it didn't exist before our call).
262 return waitpid_success;
263 }
252 } 264 }
253 265
254 namespace { 266 namespace {
255 267
256 int64 TimeValToMicroseconds(const struct timeval& tv) { 268 int64 TimeValToMicroseconds(const struct timeval& tv) {
257 return tv.tv_sec * kMicrosecondsPerSecond + tv.tv_usec; 269 return tv.tv_sec * kMicrosecondsPerSecond + tv.tv_usec;
258 } 270 }
259 271
260 } 272 }
261 273
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after
348 const ProcessFilter* filter) { 360 const ProcessFilter* filter) {
349 bool exited_cleanly = 361 bool exited_cleanly =
350 WaitForProcessesToExit(executable_name, wait_milliseconds, 362 WaitForProcessesToExit(executable_name, wait_milliseconds,
351 filter); 363 filter);
352 if (!exited_cleanly) 364 if (!exited_cleanly)
353 KillProcesses(executable_name, exit_code, filter); 365 KillProcesses(executable_name, exit_code, filter);
354 return exited_cleanly; 366 return exited_cleanly;
355 } 367 }
356 368
357 } // namespace base 369 } // namespace base
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698