#!/usr/bin/env fish
function foo
__parse_args $argv[1]
echo foo
end
function __parse_args --argument option
if test -z $option
return # No option to parse, return early
end
switch $option
case -h --help
echo "Shows this help and exits"
return 0 # How can we exit 0 instead of return?
case -\*
echo "Error: '$option' not a valid option"
return 1 # How can we exit 1 instead of return?
end
end
foo $argv
功能阻塞,直到信号到达。
假设进程得到一个信号并且返回了pause(),那么信号处理程序是否会在<{>} 调用pause()
之后的代码之前执行,或者结果是意外的?
示例:
pause()
void sigusr1_handler()
{
// .. handler code
}
void main()
{
// .. bind handler to SIGUSR1
pause(); // wait for SIGUSR1
// some more code
}
完成后是否会执行“更多代码”,或者是否存在竞争条件?如果是这样,解决方案是什么?
除了忙碌的等待之外我什么都想不到,但是根本不需要停顿......
答案 0 :(得分:8)
pause()仅在捕获到信号并返回信号捕获函数时返回。在这种情况下, pause()返回-1, errno 设置为 EINTR 。
您可以确定信号处理程序在some more code
之前运行。
答案 1 :(得分:3)
信号处理程序不会同时运行;它们会中断处理它们的线程,并且只有在信号处理程序返回时,中断的流才会继续。
但是,您的示例可能存在其他竞争条件;只是稀疏的伪代码而不是对你的使用案例的完整解释,很难说。例如,一个不同的信号可能会到达并在您的信号发生之前中断pause
,然后您的处理程序可能会比您预期的更晚运行。
有几种“正确的方法”可以做到这一点:
write
单个字节到信号处理程序中的pipe
,并且在主要执行流程中来自read
。sem_post
来自信号处理程序的信号量,以及主要执行流程中的sem_wait
。sigwaitinfo
或sigtimedwait
代替信号处理程序。仍在使用pause
,但是在循环中:
while(!signal_handler_finished) pause();
其中signal_handler_finished
的类型为volatile sig_atomic_t
,并且在信号处理程序中设置为非零值。