在 C 中处理信号时调用进程的 pid 不正确
Incorrect pid of calling process when handling signal in C
我真的不知道我到底做错了什么。我想从传入信号中提取调用者的 pid,但我得到的值完全不正确。
这是我的 "catcher" 代码:
#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;
}
和"sender":
#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
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
阅读 sigaction()
的手册页:
sa_handler
specifies the action to be associated with signum
... This function receives the signal number as its only argument.
那不是你想要的。你想要这个:
If SA_SIGINFO
is specified in sa_flags
, then sa_sigaction
(instead of sa_handler
) specifies the signal-handling function for signum
. This function receives the signal number as its first argument, a pointer to a siginfo_t
as its second argument ...
您在安装处理程序时没有设置 SA_SIGINFO
标志。
在调用 sigaction
之前将以下行添加到您的代码中:
act.sa_flags = SA_SIGINFO;
我真的不知道我到底做错了什么。我想从传入信号中提取调用者的 pid,但我得到的值完全不正确。
这是我的 "catcher" 代码:
#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;
}
和"sender":
#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
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
阅读 sigaction()
的手册页:
sa_handler
specifies the action to be associated withsignum
... This function receives the signal number as its only argument.
那不是你想要的。你想要这个:
If
SA_SIGINFO
is specified insa_flags
, thensa_sigaction
(instead ofsa_handler
) specifies the signal-handling function forsignum
. This function receives the signal number as its first argument, a pointer to asiginfo_t
as its second argument ...
您在安装处理程序时没有设置 SA_SIGINFO
标志。
在调用 sigaction
之前将以下行添加到您的代码中:
act.sa_flags = SA_SIGINFO;