3

我正在学习进程间通信...这是困扰我的代码

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
int main(void)
{
   int pfds[2];
   pipe(pfds);
    if (!fork()) 
    {
       printf("I m the child process\n");
       close(1);  /* close normal stdout */
       dup(pfds[1]);  /* make stdout same as pfds[1] */


       close(pfds[0]); /* we don't need this */
       execlp("ls", "ls", NULL);
 } 
 else 
 {
    printf("I m the parent process\n");
    close(0);       /* close normal stdin */
    dup(pfds[0]);   /* make stdin same as pfds[0] */
    close(pfds[1]); /* we don't need this */
    execlp("wc", "wc", "-l", NULL);
 }
  return 0; 

}

这些是一些问题:- 1)我同意在 execlp() 之后,什么都没有被执行,但是我的 printf() 语句在 execlp() 之前,那么为什么它们没有被执行?

2)该程序在linux中充当管道命令,因此它像“ls | wc -l”一样执行,但是系统如何知道执行像“ls | wc -l”而不是“wc -l | ls”这样的程序.. ??

3) 我认为 2) 的问题是因为我已经关闭了标准输出并将其用作我的 pfds[1] 并关闭了标准输入并用作我的 pads[0] ..但是如果一个线程在另一个线程之前退出怎么办。 . ??

4)(我使用Xcode以及gcc),当在gcc中运行上述程序时,它运行良好,但是在Xcode中运行时它显示“SIGTRAP”并在控制台中返回“1”

LZ 帮助...

PS:如果有人告诉我如何在任何一般问题中查看单独线程的执行会更好!谢谢你 !!

4

1 回答 1

4
  1. printf的正在被处决。但是,它仅在您重定向标准输出后才会被刷新,因此其输出不会显示在终端上。fprintf(stderr, ...)如果您想在 stderr 上看到它,或者fflush(stdout)在开始弄乱文件描述符之前尝试一下。

  2. 您将管道的写入端附加到ls进程的标准输出,并将读取端附加到 stdin on wc,因此不会造成混淆。

  3. 我不确定你关心的是什么。该ls进程在完成列出目录后wc退出,并在输入用完并打印行数时退出。一旦拥有端点的两个进程都关闭了它(通过退出),管道就会自动清理。

  4. 很难说。调试器显示什么?不过,Xcode 调试环境主要用于开发和调试桌面/移动应用程序,因此它可能只是某种侥幸。

于 2013-01-10T07:17:37.520 回答