Tag: 信号

为什么timer_create在solaris 10中抛出SIGEV_THREAD错误?

我通过使用timer_create写了一块用于设置定时器来调用一个线程,其中我将sigev_notify设置为SIGEV_THREAD,它给我错误EINVAL(无效参数)但是当我设置sigev_notify时SIGEV_SIGNAL代码工作正常。 我的这段代码即使在solaris 11中也适用于所有操作系统,但对于solaris 10,我给出了错误。 代码如下: { int status =0; struct itimerspec ts; struct sigevent se; se.sigev_notify = SIGEV_THREAD; se.sigev_value.sival_int = val; se.sigev_notify_function = func; se.sigev_notify_attributes = NULL; status = timer_create(CLOCK_REALTIME, &se, timer_id); ts.it_value.tv_sec = abs(delay); ts.it_value.tv_nsec = (delay-abs(delay)) * 1e09; ts.it_interval.tv_sec = abs(interval); ts.it_interval.tv_nsec = (interval-abs(interval)) * 1e09; status = timer_settime(*timer_id, 0, &ts, 0); } […]

sighandler中的第二个信号呼叫 – 为什么?

最近我发现了一些使用signal代码: 286 static void sighandler( int signum ) 287 { 288 alarmed = 1; 289 signal( signum, sighandler ); 290 } 291 292 void set_alarm( int seconds ) 293 { 294 alarmed = 0; 295 signal( SIGALRM, sighandler ); 296 alarm( seconds ); 297 } 我有一些麻烦要弄清楚为什么我需要拨打2次signal ,尤其是为什么我需要在sighandler调用signal ? 我知道上面的代码做了什么,但不明白为什么我需要调用signal 2次。

检查是否错误!= EINTR:这是什么意思?

我发现这段代码多次使用(也是一个类似的代码,它使用的是open()而不是write() )。 int c = write(fd, &v, sizeof(v)); if (c == -1 && errno != EINTR) { perror(“Write to output file”); exit(EXIT_FAILURE); } 为什么检查&& errno != EINTR在这里? 寻找男人的 errno我发现了关于EINTR的以下文字,但即使我访问了man 7 signal ,也没有启发我。 EINTR中断函数调用(POSIX.1); 见信号(7)。

使用自管道,我怎样才能避免事件循环在read()上停止?

我正在尝试利用自管技巧来获得我的应用程序的可移植实现(跨Solaris,MacOSX,Linux,BSD)。 所以除了stderr和stdout的两个管道,我用它来获取分叉子的输出(我在子节点中不使用exec ,子节点执行与父节点相同的代码),我有信号管道( enum {SIG_PIPE, STDOUT_PIPE, STDERR_PIPE, MAX_PIPE}提供符号名称)。 在调用handle_child_output()之前,在管道上设置O_NONBLOCK 。 子进程具有stderr和stdout管道的写入端,并继续使用printf()和朋友,有效地写入每个相应的管道( setvbuf用于关闭子进程内的缓冲)。 接下来的代码有点冗长,一般的自管技巧也是如此。 它已经是浓缩forms。 因此,让我试着解释一下应该发生什么以及卡在哪里。 我需要收集退出状态,我必须能够找出孩子是通过信号终止还是通过退出终止。 在其他地方处理这些条件。 有意义的是handle_child_output()返回pstatus指向的int内的子pstatus的退出代码。 handle_child_output()的外部do – while循环将设置要在select调用中使用的FD_SET 。 它添加了信号管道读取端以及来自子节点的stderr和stdout管道的读取端。 然后if(FD_ISSET(fds[SIG_PIPE], &rd))检查信号管道是否包含任何新的并排出它,处理任何潜在的信号。 之后的for循环遍历剩余的文件描述符,以查看是否有任何stdio处理,然后通过parroting它在父对象的stdio通道上得到的内容进行处理。 第二个循环中的读取调用是停止的位置。 症状是父母卡在读取调用中: (gdb) bt 1 #0 0x00007f2daaa9e530 in __read_nocancel () from /lib64/libpthread.so.0 就好像在读取信号管和其他管道之间存在竞争条件。 当文件描述符被检查时,孩子似乎已经退出并因此最终成为僵尸,因为父母仍然停留在read()并且永远不会到达wait()调用。 我究竟做错了什么? 添加if(exitloop) break;合法if(exitloop) break; 在for循环之前突破外部do – while循环? 在我看来,这可能会在管道中留下未读的内容,不是吗? #define __MAX__(x,y) ((x) > (y) ? (x) […]

使用信号的进程同步如何工作?

我最近完成了“Unix环境下的高级编程”(第3版)的第10节(信号),我遇到了一段我不完全理解的代码: #include “apue.h” static volatile sig_atomic_t sigflag; /* set nonzero by sig handler */ static sigset_t newmask, oldmask, zeromask; static void sig_usr(int signo) /* one signal handler for SIGUSR1 and SIGUSR2 */ { sigflag = 1; } void TELL_WAIT(void) { if (signal(SIGUSR1, sig_usr) == SIG_ERR) err_sys(“signal(SIGUSR1) error”); if (signal(SIGUSR2, sig_usr) == SIG_ERR) err_sys(“signal(SIGUSR2) error”); sigemptyset(&zeromask); […]

SEGV_ACCERR是什么意思?

我正在研究一些碰撞信号为SIGSEGV的SEGV_ACCERR。 在搜索SEGV_ACCERR之后,我发现的最接近人类可读解释的是: 对象的无效权限 这在更一般意义上意味着什么? 何时出现SEGV_ACCERR? 关于这个原因有更具体的文件吗?

为多个信号设置单个信号处理器function的正确方法是什么?

Linux上用于设置可以处理具有相同function的多个POSIX信号的程序的最佳方法是什么? 例如,在我的代码中,我有一个处理程序函数,我希望在捕获信号时执行某些操作时通常会调用它: /* Exit handler function called by sigaction */ void exitHandler( int sig, siginfo_t *siginfo, void *ignore ) { printf(“*** Got %d signal from %d\n”, siginfo->si_signo, siginfo->si_pid); loopCounter=0; return; } 我已经设置了两个信号来捕获每个信号的单独sigaction调用: /* Set exit handler function for SIGUSR1 , SIGINT (ctrl+c) */ struct sigaction act; act.sa_flags = SA_SIGINFO; act.sa_sigaction = exitHandler; sigaction( SIGUSR1, &act, […]

使用信号和sigpipe

我正在进行一项任务,包括使用fork(进程),信号和选择编写程序来处理数据(计算pi)。 我现在正在处理信号,我想我想做的是使用SIGPIPE,所以如果程序捕获它,它会再次尝试写入管道(如果进程试图写入没有读取器的管道,它将被发送SIGPIPE)。 我在main()中使用fork()通过将每个进程发送到worker函数来为它们分配相同的工作。 void worker(int id) { …. (this piece of code is not relevant) if(write(pfd[id][1], &c, sizeof(c)) == -1) printf(“Error occurred: %s\n”,strerror(errno)); } 如何在此函数中实现信号以捕获SIGPIPE并使其再次写入管道? 谢谢!

用select()从管道读取信号

使用带管道的select() – 这就是我正在做的事情,现在我需要抓住SIGTERM 。 我该怎么做? 当select()返回错误(<0)时,我是否必须这样做?

如何在信号处理程序中使用“sigaltstack”?

有谁知道如何在真正的信号处理程序中使用sigaltstack ,一个简单但完整的代码可能对我很有帮助! 先感谢您!