LinuxSir.cn,穿越时空的Linuxsir!

 找回密码
 注册
搜索
热搜: shell linux mysql
查看: 786|回复: 5

关于定时器的问题?

[复制链接]
发表于 2005-11-1 23:04:24 | 显示全部楼层 |阅读模式
大家看看这段代码有什么问题,运行起来时定时器并没起作用,而是一直不断的打印出“settimer.....................”,怎么设置itv.it_interval.tv_sec 都没有用,一样的效果,总是很快的打印,感觉是进了死循环。

#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <string.h>
#include <sys/time.h>
#include <sys/wait.h>
#include <pthread.h>
#include <semaphore.h>
#include <unistd.h>
#include <signal.h>

void set_timer(void)
{
    struct itimerval itv,oldtv;

    itv.it_interval.tv_sec = 5;
    itv.it_interval.tv_usec = 0;
    itv.it_value.tv_sec = 5;
    itv.it_value.tv_usec = 0;
   
    setitimer(ITIMER_REAL, &itv, &oldtv);
}

void sigalrm_handler(void)
{
    printf("settimer.....................\n");
}

void *run_thread_function(void *arg)
{
    int i = 0, res ;
    struct sigaction sigact;
   
    //######## 设置线程为可取消 ###############//
    res = pthread_setcancelstate (PTHREAD_CANCEL_ENABLE , NULL);
    if (res != 0)
    {
                perror ("Thread_run pthread_setcancelstate failed");
                close (hCom1);
                exit (EXIT_FAILURE) ;
    }
   
    //######## 取消前先执行 pthread_join ###############//
    res = pthread_setcanceltype(PTHREAD_CANCEL_DEFERRED , NULL);
    if (res != 0)
    {
                perror ("Thread_run pthread_setcanceltype failed");
                close (hCom1);
                exit (EXIT_FAILURE) ;
    }
   
    sigact.sa_flags = SA_RESTART;
    sigact.sa_handler =(void (*)(int))sigalrm_handler;   
    sigemptyset(&sigact.sa_mask);
    sigaction(SIGALRM, &sigact, NULL);

    set_timer();   
   
    while (1)
    {
        //send_data();
        //sleep(3);
    }
   
    pthread_exit (0);
}

void send_data(void)
{                
    write(hCom1,"0123456789",10);
    printf("send data: 0123456789\n");
}


其中,把setitimer(ITIMER_REAL, &itv, &oldtv);改为:setitimer(ITIMER_REAL, &itv, NULL);
以及把sigact.sa_flags = SA_RESTART;改为:sigact.sa_flags = 0;
也是一样的效果,究竟该怎么做呀?
发表于 2005-11-2 09:25:50 | 显示全部楼层
Timers  decrement  from  it_value to zero, generate a signal, and
       reset to it_interval.  A timer which is set to zero (it_value  is
       zero or the timer expires and it_interval is zero) stops.
回复 支持 反对

使用道具 举报

发表于 2005-11-2 13:27:34 | 显示全部楼层
我的代码和你的基本一至,运行正常啊,每5秒触发一次啊。

  1. #include <stdio.h>
  2. #include <time.h>
  3. #include <sys/time.h>
  4. #include <stdlib.h>
  5. #include <signal.h>

  6. void set_timer()
  7. {
  8.         struct itimerval itv, oldtv;
  9.         itv.it_interval.tv_sec = 5;
  10.         itv.it_interval.tv_usec = 0;
  11.         itv.it_value.tv_sec = 5;
  12.         itv.it_value.tv_usec = 0;

  13.         setitimer(ITIMER_REAL, &itv, &oldtv);
  14. }

  15. void sigalrm_handler(int sig)
  16. {
  17.         printf("settimer.....\n");
  18. }

  19. int main()
  20. {
  21.         signal(SIGALRM, sigalrm_handler);
  22.         set_timer();
  23.         while (1)
  24.         {}
  25.         exit(0);
  26. }

复制代码
回复 支持 反对

使用道具 举报

发表于 2005-11-2 16:34:54 | 显示全部楼层
哦,理解错误,我还以为是给setitimer的参数有误,我试了下
[PHP]
#include <stdio.h>
#include <time.h>
#include <sys/time.h>
#include <stdlib.h>
#include <signal.h>

void set_timer()
{
    struct itimerval itv, oldtv;
    itv.it_interval.tv_sec = 5;
    itv.it_interval.tv_usec = 0;
    itv.it_value.tv_sec = 5;
    itv.it_value.tv_usec = 0;

    setitimer(ITIMER_REAL, &itv, &oldtv);
}

void sigalrm_handler(int sig)
{
    printf("settimer.....\n");
}

int main()
{
    struct sigaction sigact;
    sigact.sa_flags = SA_RESTART;
    sigact.sa_handler =(void (*)(int))sigalrm_handler;
    sigemptyset(&sigact.sa_mask);
    sigaction(SIGALRM, &sigact, NULL);

    //signal(SIGALRM, sigalrm_handler);

    set_timer();
    while (1)
    {}
    exit(0);
}


[/PHP]
运行也正常
回复 支持 反对

使用道具 举报

发表于 2005-11-2 17:21:59 | 显示全部楼层
楼主是不是想触发一次就可以了,把itv.it_interval.tv_sec 改为= 0;就行了。
回复 支持 反对

使用道具 举报

 楼主| 发表于 2005-11-2 23:49:09 | 显示全部楼层
哦,因为我是用在MINIGUI里面的,看来MINIGUI对它有影响,不过把setitimer(ITIMER_REAL, &itv, &oldtv);改为setitimer(ITIMER_PROF, &itv, &oldtv);就正常了,只可惜要单独开一个线程来运行,而且计时好像不怎么精确,仔细看了看,竟然计时时间多了一倍,不知道是怎么回事,晕
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则

快速回复 返回顶部 返回列表