summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author Treehugger Robot <treehugger-gerrit@google.com> 2022-02-18 12:48:42 +0000
committer Automerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com> 2022-02-18 12:48:42 +0000
commitc58ee1a3dbe61ef02e35b16f76a83357c6264fc5 (patch)
tree8584dd6a1c5c1f6cc7b43a9aaeb65b0d396d3832
parent85b328fd1081694e174da7970c4643472a3decdb (diff)
parent9848c17b9109cefdf3b366181a5f9ad2b8007e3e (diff)
Merge changes Ib202fd5c,I5d0fa5d5 am: bab6ddb6ad am: d35600ed13 am: ed593ec7a9 am: 9848c17b91
Original change: https://android-review.googlesource.com/c/platform/frameworks/native/+/1989127 Change-Id: Ifb07ded6a590531018d2f24fd7e74ce1e814ab30
-rw-r--r--cmds/dumpstate/DumpstateUtil.cpp25
1 files changed, 18 insertions, 7 deletions
diff --git a/cmds/dumpstate/DumpstateUtil.cpp b/cmds/dumpstate/DumpstateUtil.cpp
index c833d0e6bd..aa42541a66 100644
--- a/cmds/dumpstate/DumpstateUtil.cpp
+++ b/cmds/dumpstate/DumpstateUtil.cpp
@@ -48,11 +48,26 @@ static bool waitpid_with_timeout(pid_t pid, int timeout_ms, int* status) {
sigemptyset(&child_mask);
sigaddset(&child_mask, SIGCHLD);
+ // block SIGCHLD before we check if a process has exited
if (sigprocmask(SIG_BLOCK, &child_mask, &old_mask) == -1) {
printf("*** sigprocmask failed: %s\n", strerror(errno));
return false;
}
+ // if the child has exited already, handle and reset signals before leaving
+ pid_t child_pid = waitpid(pid, status, WNOHANG);
+ if (child_pid != pid) {
+ if (child_pid > 0) {
+ printf("*** Waiting for pid %d, got pid %d instead\n", pid, child_pid);
+ sigprocmask(SIG_SETMASK, &old_mask, nullptr);
+ return false;
+ }
+ } else {
+ sigprocmask(SIG_SETMASK, &old_mask, nullptr);
+ return true;
+ }
+
+ // wait for a SIGCHLD
timespec ts;
ts.tv_sec = MSEC_TO_SEC(timeout_ms);
ts.tv_nsec = (timeout_ms % 1000) * 1000000;
@@ -76,7 +91,7 @@ static bool waitpid_with_timeout(pid_t pid, int timeout_ms, int* status) {
return false;
}
- pid_t child_pid = waitpid(pid, status, WNOHANG);
+ child_pid = waitpid(pid, status, WNOHANG);
if (child_pid != pid) {
if (child_pid != -1) {
printf("*** Waiting for pid %d, got pid %d instead\n", pid, child_pid);
@@ -232,7 +247,6 @@ int DumpFileToFd(int out_fd, const std::string& title, const std::string& path)
dprintf(out_fd, "*** Error dumping %s (%s): %s\n", path.c_str(), title.c_str(),
strerror(err));
}
- fsync(out_fd);
return -1;
}
return DumpFileFromFdToFd(title, path, fd.get(), out_fd, PropertiesHelper::IsDryRun());
@@ -280,7 +294,6 @@ int RunCommandToFd(int fd, const std::string& title, const std::vector<std::stri
if (!title.empty()) {
dprintf(fd, "------ %s (%s) ------\n", title.c_str(), command);
- fsync(fd);
}
const std::string& logging_message = options.LoggingMessage();
@@ -299,14 +312,13 @@ int RunCommandToFd(int fd, const std::string& title, const std::vector<std::stri
// There is no title, but we should still print a dry-run message
dprintf(fd, "%s: skipped on dry run\n", command_string.c_str());
}
- fsync(fd);
return 0;
}
const char* path = args[0];
uint64_t start = Nanotime();
- pid_t pid = fork();
+ pid_t pid = vfork();
/* handle error case */
if (pid < 0) {
@@ -323,7 +335,7 @@ int RunCommandToFd(int fd, const std::string& title, const std::vector<std::stri
strerror(errno));
}
MYLOGE("*** could not drop root before running %s: %s\n", command, strerror(errno));
- return -1;
+ _exit(EXIT_FAILURE);
}
if (options.ShouldCloseAllFileDescriptorsOnExec()) {
@@ -376,7 +388,6 @@ int RunCommandToFd(int fd, const std::string& title, const std::vector<std::stri
/* handle parent case */
int status;
bool ret = waitpid_with_timeout(pid, options.TimeoutInMs(), &status);
- fsync(fd);
uint64_t elapsed = Nanotime() - start;
if (!ret) {