C 为什么先封锁信号,然后再解除封锁?
在阅读涉及v4l2 API的某些源代码时,我偶然发现了以下几部分: 第一:C 为什么先封锁信号,然后再解除封锁?,c,linux,signals,semaphore,C,Linux,Signals,Semaphore,在阅读涉及v4l2 API的某些源代码时,我偶然发现了以下几部分: 第一: sigemptyset(&set); sigaddset(&set, SIGCHLD); sigaddset(&set, SIGALRM); sigaddset(&set, SIGUSR1); sigaddset(&set, SIGTERM); sigaddset(&set, SIGHUP); pthread_sigmask(SIG_BLOCK, &set, &am
sigemptyset(&set);
sigaddset(&set, SIGCHLD);
sigaddset(&set, SIGALRM);
sigaddset(&set, SIGUSR1);
sigaddset(&set, SIGTERM);
sigaddset(&set, SIGHUP);
pthread_sigmask(SIG_BLOCK, &set, &old);
然后:
其间:
if (s->pframe >= 0) {
if (xioctl(s->fd, VIDIOC_QBUF, &s->buf) == -1) {
motion_log(LOG_ERR, 1, "%s: VIDIOC_QBUF", __FUNCTION__);
return -1;
}
}
memset(&s->buf, 0, sizeof(struct v4l2_buffer));
s->buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
s->buf.memory = V4L2_MEMORY_MMAP;
if (xioctl(s->fd, VIDIOC_DQBUF, &s->buf) == -1) {
/* some drivers return EIO when there is no signal,
driver might dequeue an (empty) buffer despite
returning an error, or even stop capturing.
*/
if (errno == EIO) {
s->pframe++;
if ((u32)s->pframe >= s->req.count) s->pframe = 0;
s->buf.index = s->pframe;
motion_log(LOG_ERR, 1, "%s: VIDIOC_DQBUF: EIO (s->pframe %d)", __FUNCTION__, s->pframe);
return 1;
}
motion_log(LOG_ERR, 1, "%s: VIDIOC_DQBUF", __FUNCTION__);
return -1;
}
s->pframe = s->buf.index;
s->buffers[s->buf.index].used = s->buf.bytesused;
s->buffers[s->buf.index].content_length = s->buf.bytesused;
我诚实的猜测是,在这种特殊情况下,阻塞信号可以防止设置过程被中断。但我完全不确定。请帮忙?
您的猜测是正确的,它应该可以防止线程中断。
上面的链接并不特定于pthreads,但其概念是相同的,我认为已经很好地解释了
编辑:
pthreads关于阻塞信号的解释
您的猜测是正确的,它应该可以防止线程中断。
上面的链接并不特定于pthreads,但其概念是相同的,我认为已经很好地解释了
编辑:
pthreads关于阻塞信号的解释
您能按实际顺序显示代码吗?把中间的代码放在另一个代码之后是令人困惑的。你的猜测在我看来是正确的。它会阻止这些信号,进行设置,然后将信号掩码恢复到以前的状态。我猜您不想让视频缓冲区处于中间状态,部分初始化。您能按实际顺序显示代码吗?把中间的代码放在另一个代码之后是令人困惑的。你的猜测在我看来是正确的。它会阻塞这些信号,进行设置,然后将信号掩码恢复到以前的状态。我猜您不希望视频缓冲区处于中间状态,部分初始化。
if (s->pframe >= 0) {
if (xioctl(s->fd, VIDIOC_QBUF, &s->buf) == -1) {
motion_log(LOG_ERR, 1, "%s: VIDIOC_QBUF", __FUNCTION__);
return -1;
}
}
memset(&s->buf, 0, sizeof(struct v4l2_buffer));
s->buf.type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
s->buf.memory = V4L2_MEMORY_MMAP;
if (xioctl(s->fd, VIDIOC_DQBUF, &s->buf) == -1) {
/* some drivers return EIO when there is no signal,
driver might dequeue an (empty) buffer despite
returning an error, or even stop capturing.
*/
if (errno == EIO) {
s->pframe++;
if ((u32)s->pframe >= s->req.count) s->pframe = 0;
s->buf.index = s->pframe;
motion_log(LOG_ERR, 1, "%s: VIDIOC_DQBUF: EIO (s->pframe %d)", __FUNCTION__, s->pframe);
return 1;
}
motion_log(LOG_ERR, 1, "%s: VIDIOC_DQBUF", __FUNCTION__);
return -1;
}
s->pframe = s->buf.index;
s->buffers[s->buf.index].used = s->buf.bytesused;
s->buffers[s->buf.index].content_length = s->buf.bytesused;