3

我正在开发一个通过 TCP 连接到服务器的应用程序。

如果由于某种原因关闭了套接字,我最终会进入 SIGPIPE 处理程序。

我该怎么做才能使 recv 和 send 只在断开/关闭的套接字上返回错误?

谢谢

4

6 回答 6

3

我发现在 OS X 上忽略 SIGPIPE 无效。请改用 SO_NOSIGPIPE。请注意,这是在套接字上设置一次,而不是在每次调用 send() 时请求的 MSG_NOSIGNAL。

int socket = accept (...); /* (or however you're getting the socket) */
int option_value = 1; /* Set NOSIGPIPE to ON */
if (setsockopt (socket, SOL_SOCKET, SO_NOSIGPIPE, &option_value, sizeof (option_value)) < 0) {
    perror ("setsockopt(,,SO_NOSIGPIPE)");
}
于 2016-04-26T03:42:38.973 回答
2

要忽略信号,请将信号处理程序设置为SIG_IGN这样做:

struct sigaction sa;
memset(&sa, 0, sizeof(sa));

sa.sa_handler = SIG_IGN;

if (-1 == sigaction(SIGPIPE, &sa, NULL))
{
  perror("sigaction() failed");
}
于 2013-10-22T06:53:31.080 回答
2

SIG_IGN信号而不是处理它。 send将返回 -1 并且 errno 将设置为 EPIPE。

于 2013-10-22T05:18:14.470 回答
2

忽略其他答案(即)中描述的 SIGPIPEsignal(SIGPIPE, SIG_IGN);在 OS X 上对我有用。此外,请务必在调试器之外进行测试,如本评论中所述。我正在调试,lldb它的信号处理正在用 SIGPIPE 终止我的程序,即使我忽略了那个信号。在外面进行测试lldb工作正常。

于 2017-05-07T20:35:25.530 回答
0

使用信号处理程序或忽略它

#include <signal.h>
signal(SIGPIPE, SIG_IGN);

在写入套接字时,首先检查套接字 fd 是否在程序中为正。在外部,您应该检查您是否正在发送有效套接字的指针

于 2013-10-22T05:31:46.423 回答
0

你可以无视SIGPIPE

 #include <signal.h>

signal(SIGPIPE, SIG_IGN);

或者您可以使用信号处理程序。

signal(SIGPIPE, handler);
void handler(int signal)
{   
    //("Signal caught");

}
于 2013-10-22T06:21:08.810 回答