diff options
author | 2022-02-18 12:48:42 +0000 | |
---|---|---|
committer | 2022-02-18 12:48:42 +0000 | |
commit | c58ee1a3dbe61ef02e35b16f76a83357c6264fc5 (patch) | |
tree | 8584dd6a1c5c1f6cc7b43a9aaeb65b0d396d3832 | |
parent | 85b328fd1081694e174da7970c4643472a3decdb (diff) | |
parent | 9848c17b9109cefdf3b366181a5f9ad2b8007e3e (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.cpp | 25 |
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) { |