在哪里为SIGPIPE声明sig_t信号
我目前正在使用kqueue来处理Serverprocess中每个线程的多个客户端,因此我不希望在Signal SIGPIPE出现时终止该线程,我只想从kqueue中删除相应的socked id。 所以我的问题是:有没有办法在Signalhandle中获取相应的socketid并将其解析回Process以从事件kqueue中删除它,或者我将jsut转换为SIGPIPE的SIG_IGN并通过返回-1来处理删除发送? 并且它会在超时时间后返回-1值还是立即返回-1?
最后,如果信号忽略是我的解决方案:其中id必须放置声明
typedef void (*sig_t) (int); sig_t signal(int sig, sig_t func);
它必须在主要function? 还是在相应线程的开头? 还是作为全球元素?
我想不出一个简单的方法让信号处理程序知道当前正在处理的套接字,除非你每次进行套接字操作时都设置一些全局状态。
您可以忽略来自main的SIGPIPE
。 您没有定义自己的处理程序,而是使用SIG_IGN
。
signal(SIGPIPE, SIG_IGN);
或者,如果您正在使用sigaction
:
struct sigaction act; act.sa_handler = SIG_IGN; sigemptyset(&act.sa_mask); act.sa_flags = 0; sigaction(SIGPIPE, &act, NULL);
或者,您可以在调用send时发出MSG_NOSIGNAL
标志。 这将抑制SIGPIPE
的生成,而是生成EPIPE
错误(如果忽略SIGPIPE
会发生这种情况):
ssize_t sent = send(sock, buf, sizeof(buf), MSG_NOSIGNAL); if (sent > 0) { /* ... */ } else { assert(sent < 0); swtich (errno) { case EPIPE: /* ...handle sending on a closed socket */ /* ...handle other error cases */ } }
‘signal(……’代码应该在’main’中。