execve grep进程永远不会退出

时间:2015-09-21 09:00:24

标签: c grep pipe

以下代码通过分叉过程和使用execve系统调用来模拟管道和grep操作。输出似乎很好,但是,grep进程似乎永远不会退出(仍然在后面运行),直到整个过程结束。有什么问题?它是异常的,因为在shell中使用grep总是退出。

#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/wait.h>
#include <fcntl.h>
int main(int argc, char *argv[], char *env[]) {
char ch[32];
while (1) {
    scanf("%s", ch);
    int pd[2];
    if (pipe(pd) == -1) {
        perror("Pipe failed");
        exit(1);
    }

    int childPid, pid;
    if ((childPid = fork()) < 0) {
        perror("fork failed\n");
        exit(1);
    } else {
        // parent process
        if (childPid) {
            int status;
            wait(&status);
            // print exit code of child process
            printf("Exit code %d\n", status);
        }
        // child process, execute command
        else {
            // fork a child
            if ((pid = fork()) < 0) {
                perror("fork failed\n");
                exit(1);
            }
            if (pid) {   // parent as pipe WRITER
                close(pd[0]);
                close(1);
                // replace input with pipe
                dup(pd[1]);
                char* cmds[] = { "/bin/cat", "aa", 0 };
                execve(cmds[0], cmds, env);

                exit(0);
            } else {   // child as pipe READER
                close(pd[1]);
                close(0); // close its READ end
                dup(pd[0]);

                char* cmds[] = { "/bin/grep", "rw", 0 };
                execve(cmds[0], cmds, env);
                exit(0); // never been here
            }
        }
    }
}
return 0;
}

以下是我在运行此程序之前和之后监视进程的输出。

hengstar@ubuntu:~$ ps -ef | grep "grep"
hengstar 58073 58038  0 01:43 pts/26   00:00:00 grep --color=auto grep
hengstar@ubuntu:~$ ps -ef | grep "grep"
hengstar 58075  1886  0 01:43 pts/11   00:00:00 /bin/grep drw
hengstar 58077 58038  0 01:43 pts/26   00:00:00 grep --color=auto grep

2 个答案:

答案 0 :(得分:3)

exec family of functions 从不 返回。它们的目的是加载一个新程序,以替换当前正在运行的程序。

如果exec函数返回,则表示存在错误。

答案 1 :(得分:2)

当我发现这个时,我自己也笑得很开心!你注意到上面的if else if了吗?好吧,一切都还好,除了那个!没有它,你的程序就像你描述的那样工作。

BTW :如果某个进程的父级已经死亡,则该子进程将被while(1) a.k.a init 采用。您的代码使用(pid_t)1发生了这种情况。