Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, 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(TARGET_OS_LINUX) | 6 #if defined(TARGET_OS_LINUX) |
| 7 | 7 |
| 8 #include "bin/process.h" | 8 #include "bin/process.h" |
| 9 | 9 |
| 10 #include <errno.h> // NOLINT | 10 #include <errno.h> // NOLINT |
| (...skipping 460 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 471 execvp(path, const_cast<char* const*>(program_arguments))); | 471 execvp(path, const_cast<char* const*>(program_arguments))); |
| 472 | 472 |
| 473 ReportChildError(exec_control[1]); | 473 ReportChildError(exec_control[1]); |
| 474 } | 474 } |
| 475 | 475 |
| 476 // The arguments and environment for the spawned process are not needed | 476 // The arguments and environment for the spawned process are not needed |
| 477 // any longer. | 477 // any longer. |
| 478 delete[] program_arguments; | 478 delete[] program_arguments; |
| 479 delete[] program_environment; | 479 delete[] program_environment; |
| 480 | 480 |
| 481 int event_fds[2]; | |
| 482 result = TEMP_FAILURE_RETRY(pipe(event_fds)); | |
| 483 if (result < 0) { | |
| 484 SetChildOsErrorMessage(os_error_message); | |
| 485 TEMP_FAILURE_RETRY(close(read_in[0])); | |
| 486 TEMP_FAILURE_RETRY(close(read_in[1])); | |
| 487 TEMP_FAILURE_RETRY(close(read_err[0])); | |
| 488 TEMP_FAILURE_RETRY(close(read_err[1])); | |
| 489 TEMP_FAILURE_RETRY(close(write_out[0])); | |
| 490 TEMP_FAILURE_RETRY(close(write_out[1])); | |
| 491 Log::PrintErr("Error pipe creation failed: %s\n", *os_error_message); | |
| 492 return errno; | |
| 493 } | |
| 494 FDUtils::SetCloseOnExec(event_fds[0]); | |
| 495 FDUtils::SetCloseOnExec(event_fds[1]); | |
| 496 | |
| 497 ProcessInfoList::AddProcess(pid, event_fds[1]); | |
| 498 *exit_event = event_fds[0]; | |
| 499 FDUtils::SetNonBlocking(event_fds[0]); | |
| 500 | |
| 501 // Notify child process to start. | 481 // Notify child process to start. |
| 502 char msg = '1'; | 482 char msg = '1'; |
| 503 result = FDUtils::WriteToBlocking(read_in[1], &msg, sizeof(msg)); | 483 result = FDUtils::WriteToBlocking(read_in[1], &msg, sizeof(msg)); |
| 504 if (result != sizeof(msg)) { | 484 if (result != sizeof(msg)) { |
| 505 perror("Failed sending notification message"); | 485 perror("Failed sending notification message"); |
| 506 } | 486 } |
| 507 | 487 |
| 508 // Read exec result from child. If no data is returned the exec was | 488 // Read exec result from child. If no data is returned the exec was |
| 509 // successful and the exec call closed the pipe. Otherwise the errno | 489 // successful and the exec call closed the pipe. Otherwise the errno |
| 510 // is written to the pipe. | 490 // is written to the pipe. |
| (...skipping 20 matching lines...) Expand all Loading... | |
| 531 TEMP_FAILURE_RETRY(close(read_in[0])); | 511 TEMP_FAILURE_RETRY(close(read_in[0])); |
| 532 TEMP_FAILURE_RETRY(close(read_in[1])); | 512 TEMP_FAILURE_RETRY(close(read_in[1])); |
| 533 TEMP_FAILURE_RETRY(close(read_err[0])); | 513 TEMP_FAILURE_RETRY(close(read_err[0])); |
| 534 TEMP_FAILURE_RETRY(close(read_err[1])); | 514 TEMP_FAILURE_RETRY(close(read_err[1])); |
| 535 TEMP_FAILURE_RETRY(close(write_out[0])); | 515 TEMP_FAILURE_RETRY(close(write_out[0])); |
| 536 TEMP_FAILURE_RETRY(close(write_out[1])); | 516 TEMP_FAILURE_RETRY(close(write_out[1])); |
| 537 if (bytes_read == -1) { | 517 if (bytes_read == -1) { |
| 538 return errno; // Read failed. | 518 return errno; // Read failed. |
| 539 } else { | 519 } else { |
| 540 return child_errno; // Exec failed. | 520 return child_errno; // Exec failed. |
| 541 } | 521 } |
|
kustermann
2013/06/03 07:30:27
In these two cases, we return a nonzero value. The
| |
| 542 } | 522 } |
| 543 | 523 |
| 544 FDUtils::SetNonBlocking(read_in[0]); | 524 FDUtils::SetNonBlocking(read_in[0]); |
| 545 *in = read_in[0]; | 525 *in = read_in[0]; |
| 546 TEMP_FAILURE_RETRY(close(read_in[1])); | 526 TEMP_FAILURE_RETRY(close(read_in[1])); |
| 547 FDUtils::SetNonBlocking(write_out[1]); | 527 FDUtils::SetNonBlocking(write_out[1]); |
| 548 *out = write_out[1]; | 528 *out = write_out[1]; |
| 549 TEMP_FAILURE_RETRY(close(write_out[0])); | 529 TEMP_FAILURE_RETRY(close(write_out[0])); |
| 550 FDUtils::SetNonBlocking(read_err[0]); | 530 FDUtils::SetNonBlocking(read_err[0]); |
| 551 *err = read_err[0]; | 531 *err = read_err[0]; |
| 552 TEMP_FAILURE_RETRY(close(read_err[1])); | 532 TEMP_FAILURE_RETRY(close(read_err[1])); |
| 553 | 533 |
| 534 // Everything went well, so we can listen for the exitcode of our child | |
| 535 // process. | |
| 536 int event_fds[2]; | |
| 537 result = TEMP_FAILURE_RETRY(pipe(event_fds)); | |
| 538 if (result < 0) { | |
| 539 SetChildOsErrorMessage(os_error_message); | |
| 540 TEMP_FAILURE_RETRY(close(read_in[0])); | |
| 541 TEMP_FAILURE_RETRY(close(read_in[1])); | |
| 542 TEMP_FAILURE_RETRY(close(read_err[0])); | |
| 543 TEMP_FAILURE_RETRY(close(read_err[1])); | |
| 544 TEMP_FAILURE_RETRY(close(write_out[0])); | |
| 545 TEMP_FAILURE_RETRY(close(write_out[1])); | |
| 546 Log::PrintErr("Error pipe creation failed: %s\n", *os_error_message); | |
| 547 return errno; | |
| 548 } | |
| 549 FDUtils::SetCloseOnExec(event_fds[0]); | |
| 550 FDUtils::SetCloseOnExec(event_fds[1]); | |
| 551 | |
| 552 ProcessInfoList::AddProcess(pid, event_fds[1]); | |
| 553 *exit_event = event_fds[0]; | |
| 554 FDUtils::SetNonBlocking(event_fds[0]); | |
| 555 | |
| 554 *id = pid; | 556 *id = pid; |
| 555 return 0; | 557 return 0; |
| 556 } | 558 } |
| 557 | 559 |
| 558 | 560 |
| 559 bool Process::Kill(intptr_t id, int signal) { | 561 bool Process::Kill(intptr_t id, int signal) { |
| 560 return (TEMP_FAILURE_RETRY(kill(id, signal)) != -1); | 562 return (TEMP_FAILURE_RETRY(kill(id, signal)) != -1); |
| 561 } | 563 } |
| 562 | 564 |
| 563 | 565 |
| 564 void Process::TerminateExitCodeHandler() { | 566 void Process::TerminateExitCodeHandler() { |
| 565 ExitCodeHandler::TerminateExitCodeThread(); | 567 ExitCodeHandler::TerminateExitCodeThread(); |
| 566 } | 568 } |
| 567 | 569 |
| 568 | 570 |
| 569 intptr_t Process::CurrentProcessId() { | 571 intptr_t Process::CurrentProcessId() { |
| 570 return static_cast<intptr_t>(getpid()); | 572 return static_cast<intptr_t>(getpid()); |
| 571 } | 573 } |
| 572 | 574 |
| 573 } // namespace bin | 575 } // namespace bin |
| 574 } // namespace dart | 576 } // namespace dart |
| 575 | 577 |
| 576 #endif // defined(TARGET_OS_LINUX) | 578 #endif // defined(TARGET_OS_LINUX) |
| OLD | NEW |