最近在做一个有关AD数据采集的项目,需要用到定时器来控制采集频率。为此,在本文中将Linux中与定时器相关的函数进行一个总结。
1 alarm()
精度:秒
声明:
#include <unistd.h> unsigned int alarm(unsigned int seconds);
参考资料[1]指出,alarm()执行seconds秒后,向调用进程发送信号SIGALRM并执行其处理函数。参考资料[11]则指出,如果在定时未完成的时间内再次调用了alarm()函数,则后一次定时器设置将覆盖前面的设置,当seconds设置为0时,定时器将被取消。它返回上次定时器剩余时间,如果是第一次设置则返回0。
1.1 实例
参考资料[1]给出了alarm()的一个用例,这里再现如下:
#include <stdio.h> #include <unistd.h> #include <signal.h> void sigalrm_fn(int sig) { printf("alarm!\n"); alarm(2); return; } int main(void) { signal(SIGALRM, sigalrm_fn); alarm(1); while(1) pause(); }
2 setitimer()
精度:微秒
声明:
#include <sys/time.h> int getitimer(int which, struct itimerval *curr_value); int setitimer(int which, const struct itimerval *new_value, struct itimerval *old_value);
参数:
2.1 int which
ITIMER_REAL decrements in real time, and delivers SIGALRM upon expiration. ITIMER_VIRTUAL decrements only when the process is executing, and delivers SIGVTALRM upon expiration. ITIMER_PROF decrements both when the process executes and when the system is executing on behalf of the process. Coupled with ITIMER_VIRTUAL, this timer is usually used to profile the time spent by the application in user and kernel space. SIGPROF is delivered upon expiration.
2.2 struct itimerval *new_value / *old_value
struct itimerval { struct timeval it_interval; /* next value */ struct timeval it_value; /* current value */ }; struct timeval { time_t tv_sec; /* seconds */ suseconds_t tv_usec; /* microseconds */ };比较难理解的是struct itimerval结构的意思,参考资料[7]对其解析如下: it_interval指定间隔时间,it_value指定初始定时时间。如果只指定it_value,就是实现一次定时;如果同时指定 it_interval,则超时后,系统会重新初始化it_value为it_interval,实现重复定时;两者都清零,则会清除定时器。
2.3 实例
参考资料[7]。
3 总结
无论是alarm()还是使用setitimer()设定的ITIMER_REAL定时器,都是发送相同的信号SIGALARM,因此两者要避免在同一个进程中使用!参考资料[6]则指出,windows下的接口支持单进程中拥有多个定时器,而linux则只允许单进程拥有一个定时器!
参考资料
[1] linux定时器
[2]linux time和timer
[3]Linux时间结构体和函数整理
[4]linux下定时器的使用--timer_create等系列
[5]Linux下timer的使用介绍,例子
[6]linux下多定时器的实现(经典)
[7]setitimer_百度百科
[8]linux编程下signal()函数
[9]linux下该怎么取消用setitimer设置的定时器呢
[10]Linux 下定时器的实现方式分析
[11]Unix系统alarm函数详解