fork多个子进程来运行其他程序

时间:2013-09-09 13:24:47

标签: c exec fork

我希望从父程序(称为守护程序)启动带有args的测试程序的5个子进程(所有5个并行,不等待完成)。

我有以下代码:

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>

int main(int argc,char* argv[]){

    //missing irrelevant part where argum is set

    int status,i;
    char cmd[512];
    pid_t process_id = 0;
    for (i=0; i<=5;i++)
    {
        process_id = fork();
        if (process_id < 0)
        {
            printf("fork failed - %d!\n",i);
            continue;
        }
        else if(process_id > 0) {
            printf("process_id of child process %d \n", process_id);
        }
        else
        {
            sprintf(cmd,"./test %s",argum);
            status = system(cmd);
            exit(0);
        }
    }
    return 0;
}

它启动它们但是当我运行ps -aux来查看进程时,除了好的进程(例如:./ test [args])之外还有一些重复项:sh -c ./test [args]

如何摆脱那些以“sh -c”开头的人?

2 个答案:

答案 0 :(得分:2)

不要从孩子那里调用system(),而是使用exec*()系列函数的成员。

execXYZ() ed off子进程调用fork()将通过从传递给execXYZ()调用的内容创建的新进程替换子进程。

请注意,如果execXYZ()成功,则会返回。


执行/bin/ls -alrt *.c的示例:

  • 该系列的execl*()成员期望每个空格分离命令行选项作为单个参数。

    execl("/bin/ls", "ls", "-alrt", "*.c", (char*) 0);
    execlp("ls", "ls", "-alrt", "*.c", (char*) 0);
    
  • 该系列的execv*()成员期望每个空格分隔命令行选项的方式参数传递给main()

    char * const argv[] = {
      "ls",
      "-alrt",
      "*.c",
      NULL,
    }
    
    execv("/bin/ls", argv);
    execvp("ls", argv);
    

exec*p()家庭成员利用环境的变量PATH来搜索要执行的二进制文件。因此,对于此示例(对于系统命令ls),需要指定路径。


在测试计划中:

#include <unistd.h>  
#include <stdio.h>

/* This should list the current working directory. */

int main(void)
{
  execl("/bin/ls", "ls", "-al", "-rt", (char*) 0);
  perror("execl() failed");
  return 0;  
}

答案 1 :(得分:1)

忽略sh -c条目的最简单方法是:

sprintf(cmd, "exec ./test %s", argum);

exec使用命令替换system()运行的shell,而不是让shell挂起,直到./test进程终止。

alkanswer概述了替代方案 - 使用exec*()系列函数(系统调用)。