sys / time.h计时器仅运行一次

时间:2019-03-07 18:53:46

标签: c time timer

我正在尝试实现一个计时器,该计时器在软件运行时会连续计时一定的时间。我写了一个肮脏的代码来尝试sys / time.h的工作方式。
我的理解是,如果将我的it_interval结构设置为非零值,那么一旦完成对存储在it_value结构中的值的计数,计时器应该重新开始计数。
但是,我的代码停滞了。有人可以告诉我代码中缺少的内容吗?另外,我正在使用Linux。

#include <sys/time.h>
#include <stdio.h>
#include <stdint.h>

int main(void) {
    struct itimerval timer1;

    timer1.it_interval.tv_sec = 5;
    timer1.it_interval.tv_usec = 0;
    timer1.it_value.tv_sec = 5;
    timer1.it_value.tv_usec = 0 ;
    setitimer(ITIMER_REAL, &timer1, NULL);
    printf( "init interval counter: %ld.%ld\n", timer1.it_interval.tv_sec, 
    timer1.it_interval.tv_usec);
    printf( "init value counter: %ld.%ld\n\n", timer1.it_value.tv_sec, 
    timer1.it_value.tv_usec );

    while(1) {
        for (int i = 0; i < 100000000000000; i++){
            getitimer(ITIMER_REAL, &timer1);
            printf( "end interval counter: %ld.%ld\n", 
            timer1.it_interval.tv_sec, timer1.it_interval.tv_usec);
            printf( "end value counter: %ld.%ld\n\n", 
            timer1.it_value.tv_sec, timer1.it_value.tv_usec );
        }
    }
    return 0;
}

我的输出(当然是缩短了)是:
结束间隔计数器:5.0
终值计数器:0.8821

结束间隔计数器:5.0闹钟

进程返回142(0x8E)执行时间:5.033 s

提前感谢您的帮助!

1 个答案:

答案 0 :(得分:0)

setitimer(ITIMER_REAL,...)导致SIGALRM在计时器到期时发送到调用进程。 SIGALRM是通常致命的信号,其默认处置方式是终止进程。

如果要防止进程被该信号杀死,则需要以某种方式进行处理。

根据您的代码示例(每100毫秒从处理程序中打印一次EXPIRED):

#include <sys/time.h>
#include <stdio.h>
#include <stdint.h>
#include <signal.h>
#include <unistd.h>
void handler(int Sig)
{
    (void)Sig;
    char msg[]="EXPIRED\n";
    ssize_t nwr = write(1,msg,sizeof(msg)-1); (void)nwr;
}
int main(void) {
    struct itimerval timer1;
    struct sigaction sa;
    sa.sa_handler = handler;
    sa.sa_flags = 0;
    sigemptyset(&sa.sa_mask);
    sigaction(SIGALRM,&sa,0);

    timer1.it_interval.tv_sec = 0;
    timer1.it_interval.tv_usec = 100000;
    timer1.it_value.tv_sec = 0;
    timer1.it_value.tv_usec = 100000 ;
    setitimer(ITIMER_REAL, &timer1, NULL);
    printf( "init interval counter: %ld.%ld\n", timer1.it_interval.tv_sec, 
    timer1.it_interval.tv_usec);
    printf( "init value counter: %ld.%ld\n\n", timer1.it_value.tv_sec, 
    timer1.it_value.tv_usec );

    while(1) pause();
    return 0;
}