5

是否可以在尝试写入/读取之前检查管道是否损坏,所以我可以跳过它并继续程序?

我正在使用一个while循环来写入从父级到多个子级通信的管道。在循环过程中,几个孩子将关闭。当循环出现并尝试再次写入它们时,我的程序将关闭,因为它被 SIGPIPE 杀死,因为管道已损坏。我知道管道坏了,我给孩子们编程关闭管道并退出(必要)。我仍然想完成循环并继续执行程序。我希望它检查管道是否损坏,如果损坏则跳过它(没有错误输出),然后继续执行程序(其他孩子仍然需要写入)。

那么,有可能吗?c中的一个例子会很棒。

这是我要问的简单伪代码表示:

int i = 0;

while(i != 5)
{
    if (mypipe[WRITE] is BROKEN)
        //Do Nothing ---Basically Skip

    else if (some condition)
        write(mypipe[WRITE]);

    i++;
}

这个问题与我以前的帖子有关,尽管我的问题的上下文不同。您可以在那里查看实际程序的代码。

4

3 回答 3

5

我的程序关闭了,因为它被 SIGPIPE 杀死了

如果您安装忽略 SIGPIPE 的信号处理程序,则可以更改该行为,这样对管道的 write() 调用将返回错误而不是终止您的程序:

  signal(SIGPIPE, SIG_IGN);

然后你简单检查

ssize_t rc;
rc = write(...);
if (rc == -1) {
    if (errno == EPIPE) {
         //it's broken
    }
 //some other error occured.
}
于 2014-10-14T14:09:12.860 回答
5

您可以设置一个信号处理程序来忽略SIGPIPE,然后写入缓冲区并检查错误代码:

/* initialization */
signal(SIGPIPE, SIG_IGN);
...

/* try writing to pipe and detect broken pipe */
ssize_t written = write(mypipe[WRITE], buf, size);
if (written == -1 && errno == EPIPE)
  ... remove pipe from the list and continue processing
于 2014-10-14T14:10:39.003 回答
3

是的,您可以在读写之前使用像poll(2)这样的多路复用系统调用。这将告诉您哪些文件描述符是可读的(有一些东西read)和可写的(可以是主题write),在一系列文件描述符中检查可读性或可写性。

(您可以使用较旧的select(2)多路复用系统调用,但poll由于C10K 问题,我更喜欢)

请注意,其他线程可能会在您自己的线程之前执行某些操作。

你想要一些事件循环。另请参阅相关问题的答案。

于 2014-10-14T14:06:05.223 回答