setrlimit不可靠?
我正在尝试使用setrlimit()
来限制进程所需的时间。 但是,当我执行某些操作(如printf()
时,它似乎不起作用。
这是一个说明问题的测试程序:
#include #include int main(void) { int i; struct rlimit limit; limit.rlim_cur = 3; limit.rlim_max = 3; // send SIGKILL after 3 seconds setrlimit(RLIMIT_CPU, &limit); // doesn't get killed for(i=0; i<1000000; i++) printf("%d",i); return 0; }
但是,如果我用一个不同的例程替换for循环,比如天真的斐波那契:
int fib(int n) { if(n<=1) return 1; return fib(n-1)+fib(n-2); } int main(void) { ... fib(100); ... }
它完美地运作。 这里发生了什么? setrlimit()
根本不可靠吗?
CPU限制是CPU秒数的限制,而不是经过的时间。 CPU秒基本上是CPU使用的秒数,并不一定与经过的时间直接相关。
当您执行fib
调用时,您将锤击CPU以使经过的时间和CPU时间都关闭(大部分处理时间都是使用CPU完成的)。 打印时并非如此,因为大部分时间都花在I / O上。
因此,在您的特定情况下发生的事情是rlimit
已设置,但您只是在流程完成之前没有使用三秒的CPU时间。
按如下方式更改main
信号会导致信号在我的系统上传送:
int main(void) { int i; struct rlimit limit; limit.rlim_cur = 3; limit.rlim_max = 3; // send SIGKILL after 3 seconds setrlimit(RLIMIT_CPU, &limit); while (1) { // Run "forever". for(i=0; i<100000; i++) { printf("%d\n",i); } fib(30); // some CPU-intensive work. } return 0; }
当您在Linux下进行time
,您会看到:
: (much looping). 52670 52671 52672 52673 52674 Killed real 0m18.719s user 0m0.944s sys 0m2.416s
在这种情况下,它花了将近20秒的时间,但CPU只使用了3.36秒(用户+ sys)。
rlimit放在CPU时间,而不是墙上时间。 根据输出的去向,您的程序可能会花费大部分时间在输出设备上等待。 虽然它正在这样做,但它不消耗CPU时间。 因此程序运行时间可能超过3秒,但如果检查其CPU使用率( ps up $PID
并查看TIME
),则显示使用的时间少于3秒。