Is there a difference between masking a signal using sigprocmask()
and ignoring a signal using signal(<signal>, SIG_IGN)
?
使用sigprocmask()屏蔽信号和使用信号忽略信号(
2 个解决方案
#1
16
Blocking is different from ignoring. You ignore a signal by installing SIG_IGN
with sigaction()
.
阻止与忽略不同。您可以通过使用sigaction()安装SIG_IGN来忽略信号。
After a signal is generated by the kernel or a process, the kernel makes it pending to some process(es). The signal is said to be delivered to a process once the process acts on the signal. A process may block a signal, which leaves the signal pending until it is unblocked. A signal which is not blocked will be delivered immediately. The signal mask specifies which signals are blocked. A process can determine which signals are pending.
在内核或进程生成信号之后,内核使其等待某些进程。一旦该过程作用于信号,就称该信号被传送到过程。进程可以阻止信号,该信号在信号被解除阻塞之前保持未决状态。未被阻止的信号将立即发送。信号掩码指定阻止哪些信号。进程可以确定哪些信号待处理。
Most UNIX's will not queue multiple instances of the same pending signal; only one instance of each signal can be pending.
大多数UNIX不会对同一待处理信号的多个实例进行排队;每个信号只有一个实例可以挂起。
Setting a signal action to SIG_IGN
for a signal that is pending will cause the pending signal to be discarded, whether or not it is blocked.
将信号操作设置为SIG_IGN以查找待处理信号将导致待处理信号被丢弃,无论是否被阻止。
And the process signal mask contains the set of signals that are currently blocked.
并且过程信号掩码包含当前被阻止的一组信号。
When a process blocks a signal, an occurrence of the signal is held until the signal is unblocked (blocked signals do not get lost, whereas ignored signals do get lost).
当一个过程阻塞一个信号时,信号的出现一直保持到信号被解锁(阻塞的信号不会丢失,而被忽略的信号确实丢失)。
#2
2
When you mask a signal it actually tells the kernel that this signal won't be delivered to the process till the mask is it.This doesn't means the signal wont occur ever again in the context of the process.Its just placed in a queue.This is usually done when you want to receive the signal but not during certain operation.A masked signal usually implies this signal can mean something to me but let it wait if it comes before I finish with this job. An ignored signal usually means that the signal is of no use to the process.
当你屏蔽一个信号时,它实际告诉内核这个信号不会传递到进程,直到掩码是它。这并不意味着信号不会再发生在进程的上下文中。它只是放在一个queue.This通常是在你想要接收信号时完成的,但是在某些操作期间不会这样做。一个屏蔽信号通常意味着这个信号对我来说意味着什么,但是如果它在我完成这项工作之前就让它等待。忽略的信号通常意味着信号对过程没用。
#include<stdio.h>
#include<signal.h>
#include<sys/types.h>
int main()
{
sigset_t test; //test signal set
alarm(1); //set alarm,SIGALRM generated after 1 second
sigemptyset(&test);
sigaddset(&test,SIGALRM);
sigprocmask(SIG_SETMASK,&test,NULL); //mask sigalrm
sleep(3); //sleep for 3 seconds ensuring the signal is generated and is waiting in the queue
sigprocmask(SIG_UNBLOCK,&test,NULL); //unblock
}
This refers to case 1.The signal is masked.But It lies there waiting and delivered as soon as you need it The strace output confirms this
这是指情况1.信号被掩盖了。但它在那里等待并在你需要时立即交付strace输出证实了这一点
alarm(1) = 0
rt_sigprocmask(SIG_SETMASK, [ALRM], NULL, 8) = 0
rt_sigprocmask(SIG_BLOCK, [CHLD], [ALRM], 8) = 0
rt_sigaction(SIGCHLD, NULL, {SIG_DFL, [], 0}, 8) = 0
rt_sigprocmask(SIG_SETMASK, [ALRM], NULL, 8) = 0
nanosleep({3, 0}, 0xbfee9ea4) = 0
rt_sigprocmask(SIG_UNBLOCK, [ALRM], NULL, 8) = 0
--- SIGALRM (Alarm clock) @ 0 (0) ---
+++ killed by SIGALRM +++
While for the second case
而对于第二种情况
#include<stdio.h>
#include<signal.h>
int main()
{
alarm(1);
signal(SIGALRM,SIG_IGN);
sleep(3);
signal(SIGALRM,SIG_DFL);
return 0;
}
The strace o/p suggest a different story
strace o / p暗示了一个不同的故事
alarm(1) = 0
rt_sigaction(SIGALRM, {SIG_IGN, [ALRM], SA_RESTART}, {SIG_DFL, [], 0}, 8) = 0
rt_sigprocmask(SIG_BLOCK, [CHLD], [], 8) = 0
rt_sigaction(SIGCHLD, NULL, {SIG_DFL, [], 0}, 8) = 0
rt_sigprocmask(SIG_SETMASK, [], NULL, 8) = 0
nanosleep({3, 0}, {2, 691998}) = ? ERESTART_RESTARTBLOCK (To be restarted)
--- SIGALRM (Alarm clock) @ 0 (0) ---
restart_syscall(<... resuming interrupted call ...>) = 0
rt_sigaction(SIGALRM, {SIG_DFL, [ALRM], SA_RESTART}, {SIG_IGN, [ALRM], SA_RESTART}, 8) = 0
exit_group(0) = ?
The signal did got delivered but nothing happened except interrupting(and restarting sleep).
信号确实已经发送但除了中断(并重新启动睡眠)之外没有任何事情发生。
#1
16
Blocking is different from ignoring. You ignore a signal by installing SIG_IGN
with sigaction()
.
阻止与忽略不同。您可以通过使用sigaction()安装SIG_IGN来忽略信号。
After a signal is generated by the kernel or a process, the kernel makes it pending to some process(es). The signal is said to be delivered to a process once the process acts on the signal. A process may block a signal, which leaves the signal pending until it is unblocked. A signal which is not blocked will be delivered immediately. The signal mask specifies which signals are blocked. A process can determine which signals are pending.
在内核或进程生成信号之后,内核使其等待某些进程。一旦该过程作用于信号,就称该信号被传送到过程。进程可以阻止信号,该信号在信号被解除阻塞之前保持未决状态。未被阻止的信号将立即发送。信号掩码指定阻止哪些信号。进程可以确定哪些信号待处理。
Most UNIX's will not queue multiple instances of the same pending signal; only one instance of each signal can be pending.
大多数UNIX不会对同一待处理信号的多个实例进行排队;每个信号只有一个实例可以挂起。
Setting a signal action to SIG_IGN
for a signal that is pending will cause the pending signal to be discarded, whether or not it is blocked.
将信号操作设置为SIG_IGN以查找待处理信号将导致待处理信号被丢弃,无论是否被阻止。
And the process signal mask contains the set of signals that are currently blocked.
并且过程信号掩码包含当前被阻止的一组信号。
When a process blocks a signal, an occurrence of the signal is held until the signal is unblocked (blocked signals do not get lost, whereas ignored signals do get lost).
当一个过程阻塞一个信号时,信号的出现一直保持到信号被解锁(阻塞的信号不会丢失,而被忽略的信号确实丢失)。
#2
2
When you mask a signal it actually tells the kernel that this signal won't be delivered to the process till the mask is it.This doesn't means the signal wont occur ever again in the context of the process.Its just placed in a queue.This is usually done when you want to receive the signal but not during certain operation.A masked signal usually implies this signal can mean something to me but let it wait if it comes before I finish with this job. An ignored signal usually means that the signal is of no use to the process.
当你屏蔽一个信号时,它实际告诉内核这个信号不会传递到进程,直到掩码是它。这并不意味着信号不会再发生在进程的上下文中。它只是放在一个queue.This通常是在你想要接收信号时完成的,但是在某些操作期间不会这样做。一个屏蔽信号通常意味着这个信号对我来说意味着什么,但是如果它在我完成这项工作之前就让它等待。忽略的信号通常意味着信号对过程没用。
#include<stdio.h>
#include<signal.h>
#include<sys/types.h>
int main()
{
sigset_t test; //test signal set
alarm(1); //set alarm,SIGALRM generated after 1 second
sigemptyset(&test);
sigaddset(&test,SIGALRM);
sigprocmask(SIG_SETMASK,&test,NULL); //mask sigalrm
sleep(3); //sleep for 3 seconds ensuring the signal is generated and is waiting in the queue
sigprocmask(SIG_UNBLOCK,&test,NULL); //unblock
}
This refers to case 1.The signal is masked.But It lies there waiting and delivered as soon as you need it The strace output confirms this
这是指情况1.信号被掩盖了。但它在那里等待并在你需要时立即交付strace输出证实了这一点
alarm(1) = 0
rt_sigprocmask(SIG_SETMASK, [ALRM], NULL, 8) = 0
rt_sigprocmask(SIG_BLOCK, [CHLD], [ALRM], 8) = 0
rt_sigaction(SIGCHLD, NULL, {SIG_DFL, [], 0}, 8) = 0
rt_sigprocmask(SIG_SETMASK, [ALRM], NULL, 8) = 0
nanosleep({3, 0}, 0xbfee9ea4) = 0
rt_sigprocmask(SIG_UNBLOCK, [ALRM], NULL, 8) = 0
--- SIGALRM (Alarm clock) @ 0 (0) ---
+++ killed by SIGALRM +++
While for the second case
而对于第二种情况
#include<stdio.h>
#include<signal.h>
int main()
{
alarm(1);
signal(SIGALRM,SIG_IGN);
sleep(3);
signal(SIGALRM,SIG_DFL);
return 0;
}
The strace o/p suggest a different story
strace o / p暗示了一个不同的故事
alarm(1) = 0
rt_sigaction(SIGALRM, {SIG_IGN, [ALRM], SA_RESTART}, {SIG_DFL, [], 0}, 8) = 0
rt_sigprocmask(SIG_BLOCK, [CHLD], [], 8) = 0
rt_sigaction(SIGCHLD, NULL, {SIG_DFL, [], 0}, 8) = 0
rt_sigprocmask(SIG_SETMASK, [], NULL, 8) = 0
nanosleep({3, 0}, {2, 691998}) = ? ERESTART_RESTARTBLOCK (To be restarted)
--- SIGALRM (Alarm clock) @ 0 (0) ---
restart_syscall(<... resuming interrupted call ...>) = 0
rt_sigaction(SIGALRM, {SIG_DFL, [ALRM], SA_RESTART}, {SIG_IGN, [ALRM], SA_RESTART}, 8) = 0
exit_group(0) = ?
The signal did got delivered but nothing happened except interrupting(and restarting sleep).
信号确实已经发送但除了中断(并重新启动睡眠)之外没有任何事情发生。