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

Unified Diff: base/process_util_posix.cc

Issue 67226: Add GetAppOutput function, a better replacement for popen. (Closed)
Patch Set: fixes Created 11 years, 8 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « base/process_util.h ('k') | base/process_util_unittest.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: base/process_util_posix.cc
diff --git a/base/process_util_posix.cc b/base/process_util_posix.cc
index d55f65d77ba58fb7fb2647d613760c180d28fa3a..75c9b9623a39fb6c4273b9b78d75f5873a1a09d2 100644
--- a/base/process_util_posix.cc
+++ b/base/process_util_posix.cc
@@ -312,6 +312,74 @@ int ProcessMetrics::GetCPUUsage() {
return cpu;
}
+bool GetAppOutput(const CommandLine& cl, std::string* output) {
+ int pipe_fd[2];
+ pid_t pid;
+
+ if (pipe(pipe_fd) < 0)
+ return false;
+
+ switch (pid = fork()) {
+ case -1: // error
+ close(pipe_fd[0]);
+ close(pipe_fd[1]);
+ return false;
+ case 0: // child
+ {
+ int rv;
+ do {
+ rv = dup2(pipe_fd[1], STDOUT_FILENO);
+ } while (rv == -1 && errno == EINTR);
+ do {
+ rv = dup2(pipe_fd[1], STDERR_FILENO);
+ } while (rv == -1 && errno == EINTR);
+ if (pipe_fd[0] != STDOUT_FILENO && pipe_fd[0] != STDERR_FILENO)
+ close(pipe_fd[0]);
+ if (pipe_fd[1] != STDOUT_FILENO && pipe_fd[1] != STDERR_FILENO)
+ close(pipe_fd[1]);
+
+ const std::vector<std::string> argv = cl.argv();
+ char* argv_cstr[argv.size() + 1];
+ for (size_t i = 0; i < argv.size(); i++)
+ argv_cstr[i] = const_cast<char*>(argv[i].c_str());
+ argv_cstr[argv.size()] = NULL;
+ execvp(argv_cstr[0], argv_cstr);
+ exit(127);
+ }
+ default: // parent
+ {
+ // Close our writing end of pipe now. Otherwise later read would not
+ // be able to detect end of child's output (in theory we could still
+ // write to the pipe).
+ close(pipe_fd[1]);
+
+ int exit_code = EXIT_FAILURE;
+ bool success = WaitForExitCode(pid, &exit_code);
+ if (!success || exit_code != EXIT_SUCCESS) {
+ close(pipe_fd[0]);
+ return false;
+ }
+
+ char buffer[256];
+ std::string buf_output;
+ ssize_t bytes_read = 0;
+
+ while (true) {
+ bytes_read = read(pipe_fd[0], buffer, sizeof(buffer));
+ if (bytes_read == 0)
+ break;
+ if (bytes_read == -1 && errno != EINTR)
+ break;
+ if (bytes_read > 0)
+ buf_output.append(buffer, bytes_read);
+ }
+ output->assign(buf_output);
Scott Hess - ex-Googler 2009/04/16 21:20:25 Since process output is sort of open-ended, would
+ close(pipe_fd[0]);
+ return true;
+ }
+ }
+}
+
int GetProcessCount(const std::wstring& executable_name,
const ProcessFilter* filter) {
int count = 0;
« no previous file with comments | « base/process_util.h ('k') | base/process_util_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698