summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChase Douglas <chase.douglas@ubuntu.com>2011-12-08 15:00:25 -0800
committerChase Douglas <chase.douglas@ubuntu.com>2011-12-08 15:00:25 -0800
commit330dfc09ecc78cfd91a93ed5d41f31f0341e81a1 (patch)
tree638097808dda4ff57ec6749d39918b5e380a6cec
parent3eda6c1380ab4bdfaf891d6d20097dc83dac8e65 (diff)
Use std::vector to store process arguments passed to execvp
-rw-r--r--src/process.cpp46
1 files changed, 17 insertions, 29 deletions
diff --git a/src/process.cpp b/src/process.cpp
index d4a4216..e4cf021 100644
--- a/src/process.cpp
+++ b/src/process.cpp
@@ -4,12 +4,14 @@
#include <sys/wait.h>
#include <unistd.h>
+#include <algorithm>
#include <cerrno>
#include <csignal>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <stdexcept>
+#include <vector>
struct xorg::testing::Process::Private {
pid_t pid;
@@ -32,39 +34,25 @@ void xorg::testing::Process::Start(const std::string& program, va_list args) {
close(1);
close(2);
- char** argv = reinterpret_cast<char**>(malloc(sizeof(char*)));
- if (!argv)
- throw std::bad_alloc();
-
- int argv_size = 1;
-
- while (true) {
- char* arg = va_arg(args, char*);
- if (!arg)
- break;
-
- char** tmp = reinterpret_cast<char**>(
- realloc(argv, ++argv_size * sizeof(char*)));
- if (!tmp) {
- free(argv);
- throw std::bad_alloc();
+ std::vector<char*> argv;
+ char* arg;
+ do {
+ arg = va_arg(args, char*);
+
+ if (arg) {
+ arg = strdup(arg);
+ if (!arg) {
+ std::for_each(argv.begin(), argv.end(), free);
+ throw std::bad_alloc();
+ }
}
- argv = tmp;
- argv[argv_size - 2] = strdup(arg);
- if (!argv[argv_size - 2]) {
- free(argv);
- throw std::bad_alloc();
- }
- }
-
- argv[argv_size - 1] = NULL;
+ argv.push_back(arg);
+ } while (arg);
- execvp(program.c_str(), argv);
+ execvp(program.c_str(), &argv[0]);
- for (int i = 0; i < argv_size; ++i)
- free(argv[i]);
- free(argv);
+ std::for_each(argv.begin(), argv.end(), free);
throw std::runtime_error("Failed to start process");
}
}