sys/time.h 定时器只运行一次

Posted

技术标签:

【中文标题】sys/time.h 定时器只运行一次【英文标题】:sys/time.h timer only runs once 【发布时间】:2019-03-07 18:53:46 【问题描述】:

我正在尝试实现一个计时器,该计时器在软件运行时连续计算一定的时间。我写了一个脏代码来尝试 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

提前感谢您的帮助!

【问题讨论】:

也许这与你到达那里的那个孤独和未使用的struct sigaction sa;有关。 糟糕,我应该删除它。目前它不在我的代码中。 @HumleBumble 实际上,您的问题的答案就在其中。 time.c:20:27: warning: comparison is always true due to limited range of data type [-Wtype-limits]有什么关系吗? @JL2210 嗯,虽然我的编译器设置启用了所有警告,但我没有收到该警告 :( 【参考方案1】:

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;

【讨论】:

尝试了代码,就像我想要的代码一样工作。非常感谢!

以上是关于sys/time.h 定时器只运行一次的主要内容,如果未能解决你的问题,请参考以下文章

优先队列实现定时器

间隔定时器不按指定的时间间隔触发信号

libevent:使计时器持久化

需要关于使用 libevent 动态更改计时器事件的建议

Linux系统编程-setitimer函数

iOS中定时器NSTimer的使用/开启与关闭