Convert vector<string> to char** for use in execvp

Viewed 73

I have a vector named tokens that holds the command in tokens[0] and args as the rest of the vector. I am trying to convert the vector so I can make the call to execvp(args[0], args); Currently args[0] and args just print as memory addresses.

  char **args = (char**)malloc(tokens.size() * sizeof(string));
  char *arg;

  int i;
  for(i = 0; i < tokens.size(); i++)
  {
    arg = &tokens[i][0];
    args[i] = arg;
  }
2 Answers

You don't have to resort to malloc to perform this since you are already using vectors of strings.

You could just create a std::vector<char*> before calling execvp:

std::vector<char*> pvec(tokens.size());
std::transform(tokens.begin(), tokens.end(), pvec.begin(), [](auto& str) {
  return &str[0];
});
pvec.data(); // This is a char**, pass it to `execvp`

I found that the answer lies with adding the NULL terminator to the end of the vector so that execvp knows where to end pvec.data(); This is thanks to Fatih above.

  std::vector<char*> pvec(tokens.size());
  std::transform(tokens.begin(), tokens.end(), pvec.begin(), [](auto& str) {
    return &str[0];
  });
  pvec.push_back(NULL);
  pvec.data();

  pid = fork();
  // if we enter child process
  if (pid == 0)
  {
    if (execvp(pvec.data()[0], pvec.data()) == -1)
    {
      printf("right here officer\n");
    }
    exit(EXIT_FAILURE);
  }```
Related