在sigaction
联机帮助页中写道:
sa_sigaction
还指定与signum
关联的操作。
该函数接收信号编号作为其第一个参数a
指向siginfo_t
作为其第二个参数的指针和指向ucon-的指针
text_t(强制转换为void*
)作为其第三个参数。
所以我们可以将参数传递给信号处理程序(通过void*
),但是我
找不到方法。
有没有办法把它放在任何地方?
示例:
struct ping_val
{
int data1;
int data2;
};
void ping(int sig, siginfo_t *siginf, void *ptr)
{
// ....
}
int main()
{
struct sigaction sa_ping;
ping_val foo;
foo.data1 = 3;
foo.data2 = 4;
sa_ping.sa_sigaction = ping;
sigemptyset(&sa_ping.sa_mask);
sa_ping.sa_flags = 0;
sigaction(SIGALRM, &sa_ping, NULL);
// ....
}
我可以在ping中的参数中传递foo
结构值(在struct *
中使用强制转换)???
答案 0 :(得分:0)
您不能将任何参数传递给信号处理程序,因为您自己从不调用它。操作系统调用信号处理程序,它不了解您的参数。
使信号处理程序与主程序通信的标准方法是通过全局(或文件范围)变量。
答案 1 :(得分:0)
信号处理程序接收的siginfo_t
结构包含union sigval si_value
成员:
union sigval {
int sival_int; // Integer signal value
void *sival_ptr; // Pointer signal value
}
因此,如果您在单个进程中(或在某些情况下,在某些情况下,我认为是forks)中发送信号,您可以发送指向某些数据的指针。
我知道有两种方法可以将sigval
值发送给信号处理程序:
如果您使用timer_create
创建计时器,则会向其传递sigevent
结构,其中包含union sigval sigev_value
成员。按照惯例,用户代码将sigev_value.sival_ptr
设置为计时器ID,以便信号处理程序可以在必要时区分多个计时器,但您可以将其设置为任何void *
值。
如果您使用sigqueue(而不是kill
,raise
,错误等)来发送信号,则会给它一个union sigval
作为参数。
答案 2 :(得分:0)
你写道:
所以我们可以将参数传递给信号处理程序[通过void * ucontext_t参数],但我找不到方法。
没有找到这样的方法 - ucontext_t
参数由系统本身设置并引用 "the receiving thread's context that was interrupted when the signal was delivered."
(具体来说,by spec它至少包含对该中断上下文的引用,以及该上下文的机器特定表示,以及当前上下文的堆栈及其阻塞信号集。)
你可能不需要这些。如果您希望程序在收到信号时采取某些操作和/或修改其状态,那么您可以在信号处理程序(volatile sigatomic_t
flags, self-pipes,
platform-specific interfaces)中安全地使用有限数量的策略,但是循环当然可以根据SIGFOO刚收到的知识做任何你想做的事。