如何使用 execv 运行 另一个 C 程序

How to run another C program using execv

我想 运行 使用 execv 将一个单独的 C 程序作为子进程。下面的代码没有产生我需要的结果(write.c 没有被编译和执行)。不知道哪里出了问题。

int buffered_child;
int native_child = fork();
if(native_child == 0){
  printf("\nnative child\n");
  execv("gcc -o /abc/write.o /abc/write.c; /abc/./write.o",argv);
  exit(1);
}

execv 不进行 PATH 插值,因此,在您的情况下,gcc 需要与您正在执行的程序位于同一目录中。尝试使用 execvp,这将使用您当前的 PATH,以查找您尝试 运行 的可执行文件,或者在您的 execv 调用中指定 gcc 的完整路径。

http://www.gnu.org/software/libc/manual/html_node/Executing-a-File.html

execv() 系统调用需要在第一个参数中包含可执行文件的路径名,在第二个参数中包含该函数的参数列表。它不搜索 $PATH 上的命令;为此,您需要 execvp()

要实现你想要的,你需要更像这样的代码:

char *argv[] = { "gcc", "-c", "-o", "/abc/write.o", "/abc/write.c", 0 };
execvp(argv[0], argv);

仔细检查原始命令行,您正在创建一个后缀为 .o 的可执行文件,然后 运行ning 它。 (这是一个奇怪的后缀选择;最令人困惑——强烈不推荐。)为此,您需要调用 shell:

char *argv[] = { "sh", "-c", "gcc -o /abc/write.o /abc/write.c; /abc/./write.o", 0 };
execvp(argv[0], argv);

执行路径中的.也是不需要的。或者,更简单(无需显式 fork()):

system("gcc -o /abc/write.o /abc/write.c; /abc/write.o");

或者您需要安排子进程 fork 和孙进程 运行 编译器,然后当孙进程完成时,子进程可以 运行 程序;这可以使用 fork() 和上述 exec* 函数之一来完成。

您需要构造要发送的argv数组,并使用完整路径作为第一个参数。例如:

char *gcc_argv[] = {"gcc",
                    "-o",
                    "/abc/write.o",
                    "-c",
                    "/abc/write.c",
                    NULL};

execv("/usr/bin/gcc", gcc_argv);

请注意,gcc_argv 中的 gcc 条目是作为其 argv 传递给 gcc 的第一个元素。然而,execv 的第一个参数是用于调用它的路径。