C++ e不是很重要:他们只是告诉你管道(这里是插座)不再可用

C++ e不是很重要:他们只是告诉你管道(这里是插座)不再可用,c++,sockets,networking,C++,Sockets,Networking,那么,在我的主要职能中 信号(信号管、信号灯)我的应用程序中有很多SIGPIPE。这些并不重要:它们只是告诉您管道(这里是插座)不再可用 那么,在我的主要职能中 信号(信号管、信号灯)另一个选项是使用MSG_NOSIGNAL标志进行send,例如send(…,MSG_NOSIGNAL)。在这种情况下,SIGPIPE未发送,调用返回-1和errno==EPIPE另一个选项是使用MSG_NOSIGNAL标志进行send,例如send(…,MSG_NOSIGNAL)。在这种情况下,如果未发送SIGPI

那么,在我的主要职能中


信号(信号管、信号灯)

我的应用程序中有很多SIGPIPE。这些并不重要:它们只是告诉您管道(这里是插座)不再可用

那么,在我的主要职能中


信号(信号管、信号灯)

另一个选项是使用
MSG_NOSIGNAL
标志进行
send
,例如
send(…,MSG_NOSIGNAL)。在这种情况下,
SIGPIPE
未发送,调用返回
-1
errno==EPIPE

另一个选项是使用
MSG_NOSIGNAL
标志进行
send
,例如
send(…,MSG_NOSIGNAL)。在这种情况下,如果未发送
SIGPIPE
,调用将返回
-1
errno==EPIPE

如果套接字在另一个线程中关闭了套接字,那么原始线程将非常混乱。当然,细致的错误处理应该可以防止,但是让主线程超时发送更简单。忽略
SIGPIPE
信号,
send
应返回
-1
errno
设置为
EPIPE
。关闭另一个线程中的套接字的问题是,如果套接字也可能被网络线程关闭,这可能导致两个线程都使用相同的值调用
close()
,这通常只会导致第二个
close()
调用出错,但如果在这两个
close()
调用之间有第三个线程调用了
socket()
,并被赋予了相同的描述符值,则会出现争用情况(由于已关闭(),该fd值可重复使用)然后,你就有了一个真正有趣的bug来追踪——一个完全无关的线程,偶尔会因为“没有理由”而出错。@ JeremyFriesner好点。我只有一个接收线程和一个在我的应用程序中触摸套接字的发送线程,所以我希望我相信没有第三线程会介入。考虑使用<代码>关闭>代码>系统调用。比
close
。这可以防止所提到的特定竞赛@JeremyFriesner,因为它可以确保
send
“完成时出错”,而不会使套接字文件描述符无效。然后,实际的
close
可以由发送线程执行。(请记住,如果您没有适当地同步对保存文件描述符值的变量的访问,则仍然可能存在其他争用。)如果套接字关闭了另一个线程中的套接字,那么原始线程将变得非常混乱。当然,仔细的错误处理应该可以防止这种情况发生,但只让主线程超时发送更简单。忽略
SIGPIPE
信号,
send
应返回
-1
errno
设置到
EPIPE
。关闭另一个线程中的套接字的问题是,如果该套接字也可能被网络线程关闭,则可能会导致争用状态,其中两个线程使用相同的值调用
close()
,通常这只会导致第二个
close()
调用以出错,但如果有第三个线程在这两个
close()
调用之间调用了
socket()
,并被传递到相同的描述符值(因为已经关闭(),该fd值可供重用)然后,你就有了一个真正有趣的bug来追踪——一个完全无关的线程,偶尔会因为“没有理由”而出错。@ JeremyFriesner好点。我只有一个接收线程和一个在我的应用程序中触摸套接字的发送线程,所以我希望我相信没有第三线程会介入。考虑使用<代码>关闭>代码>系统调用。比
close
。这可以防止所提到的特定竞赛@JeremyFriesner,因为它可以确保
send
“完成时出错”,而不会使套接字文件描述符无效。然后,实际的
close
可以由发送线程执行。(请记住,如果您没有适当地同步对保存文件描述符值的变量的访问,还有其他争用可能。)这可以很好地去除SIGPIPE。此外,如果我确保句柄有效,我可以调用close()。我在套接字上有两层。我可以使用getSocket()->getRawSocketHandle(),检查它是否有效,然后对它调用close(),这似乎有效,同时如您所示抑制SIGPIPE。这可以很好地去除SIGPIPE。此外,如果我确保句柄有效,我可以调用close()。我在套接字上有两层。我可以使用getSocket()->getRawSocketHandle(),检查它是否有效,然后对其调用close(),这似乎有效,并按指示抑制SIGPIPE。