【问题标题】:Incorrect pid of calling process when handling signal in C在 C 中处理信号时调用进程的 pid 不正确
【发布时间】:2016-03-27 21:08:20
【问题描述】:

我真的不知道我在这里到底做错了什么。我想从传入信号中提取调用者的 pid,但我得到的值完全不正确。

这是我的“捕手”代码:

#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <unistd.h>

int SIGNALS_RECEIVED = 0;
pid_t CALLING_PID;

void signal_received(int sig, siginfo_t *info, void *context) {
    SIGNALS_RECEIVED++;

    if(SIGNALS_RECEIVED == 1) {
        CALLING_PID = info->si_pid;
        printf("%ld\n", (long) CALLING_PID);
    }
}

int main() {
    struct sigaction act;
    act.sa_sigaction = &signal_received;

    sigaction(SIGUSR1, &act, NULL);

    while(1) {

    }

    return 0;
}

和“发件人”:

#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <unistd.h>

int main(int argc, char **argv) {

    char line[10];
    FILE *cmd = popen("pidof -s catcher", "r");

    fgets(line, 10, cmd);
    pid_t pid = strtoul(line, NULL, 10);

    pclose(cmd);

    int i;
    for(i = 0; i < 400; i++) {
        kill(pid, SIGUSR1);
    }

    kill(pid, SIGUSR2);

    return 0;
}

结果,当第一个 catcher 和 sender 运行时,我得到:

./catcher 
398533948
SIGNALS_RECEIVED: 24

虽然发件人的 pid 是:

ps aux | grep *sender
maciej    4704  100  0.0   4328  1268 pts/13   R+   22:46   0:15 ./sender

我的 Linux 版本:

Linux version 4.2.0-34-generic (buildd@lgw01-55) (gcc version 4.8.2 (Ubuntu 4.8.2-19ubuntu1) ) #39~14.04.1-Ubuntu SMP Fri Mar 11 11:38:02 UTC 2016

【问题讨论】:

    标签: c linux signals pid


    【解决方案1】:

    阅读sigaction() 的手册页:

    sa_handler 指定要与signum 关联的操作...此函数接收信号编号作为其唯一参数。

    这不是你想要的。你想要这个:

    如果在sa_flags 中指定了SA_SIGINFO,则sa_sigaction(而不是sa_handler)指定signum 的信号处理函数。这个函数接收信号编号作为它的第一个参数,一个指向siginfo_t的指针作为它的第二个参数......

    您在安装处理程序时没有设置SA_SIGINFOflag。

    在调用sigaction之前将以下行添加到您的代码中:

    act.sa_flags = SA_SIGINFO;
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多