性能测试中,Tester程序由start.sh脚本来启动。现在的需求是:用户按下ctrl-c,程序能graceful退出,从而不用重启板子。问题 是:ctrl-c产生信号SIGINT,但是这个信号是传递给脚本进程的,不是传递给Tester进程的。所以这里就存在一个信号传递的问题。解决办法如 下:
1. 在脚本中加入代码:
这 样ctrl-c按下后,函数forward_sigint得到执行。然后这个函数取出tester程序的pid,利用kill命令发送SIGINT信号给 tester,从而使tester程序graceful退出。注意,这里的kill命令是shell自带的一个命令,不是/bin/kill程序。也可以 使用/bin/kill程序来发送信号,效果一样的。
2. 在Tester程序中添加代码:
首先在main函数中添加:
OK,就是这样了。关键点就是当程序通过脚本启动时,信号是传递给脚本进程的,不是传递给正在执行的程序进程的。所以信号需要传递一下方可。
1. 在脚本中加入代码:
-
Code:
Select all
-
forward_sigint()
{
# check out the tester's pid
testerpid=$(cat /tmp/tester.pid)
kill -2 $testerpid
# call analyser and quit
echo "Calling analyser..."
./Analyser/analyser
echo "Test finished. Thanks."
rm -f /tmp/tester.pid
exit 0
}
......
# trap control-c signal and forwards it to tester
trap forward_sigint SIGINT
这 样ctrl-c按下后,函数forward_sigint得到执行。然后这个函数取出tester程序的pid,利用kill命令发送SIGINT信号给 tester,从而使tester程序graceful退出。注意,这里的kill命令是shell自带的一个命令,不是/bin/kill程序。也可以 使用/bin/kill程序来发送信号,效果一样的。
2. 在Tester程序中添加代码:
首先在main函数中添加:
-
Code:
Select all
-
// catch SIGINT interrupt
signal(SIGINT, stop_playing);
// write pid into /tmp/tester to make test script knows our pid
write_pid_to_temp_file();
然后是这两个函数的实现:
/*
* Write our pid to file /tmp/tester.pid
* This makes start script knows our pid and send SIGINT to us
* when the user pressed ctrl-c
*/
void write_pid_to_temp_file()
{
FILE *pidfile = fopen("/tmp/tester.pid", "wb");
char content[10];
sprintf(content, "%d", getpid());
fputs(content, pidfile);
fclose(pidfile);
}
/*
* Stop playing and quit
*/
void stop_playing(int sig)
{
DEBUG_OUTPUT("Ctrl-C caught, stop playing and quit...");
// restore the SIGINT handler
signal(SIGINT, SIG_DFL);
// make sure the glib mainloop is running
while (!g_main_loop_is_running(loop))
wait_seconds(1);
g_main_loop_quit(loop);
}
OK,就是这样了。关键点就是当程序通过脚本启动时,信号是传递给脚本进程的,不是传递给正在执行的程序进程的。所以信号需要传递一下方可。