linux时间和定时器zz

时间:2021-10-25 02:41:26

https://www.cnblogs.com/cobbliu/p/3627061.html

Linux 的计时函数,用于获得当前时间:

  • time(2) / time_t (秒)
  • ftime(3) / struct timeb (毫秒)
  • gettimeofday(2) / struct timeval (微秒)
  • clock_gettime(2) / struct timespec (纳秒)
  • gmtime / localtime / timegm / mktime / strftime / struct tm (这些与当前时间无关)

定时函数,用于让程序等待一段时间或安排计划任务:

  • sleep
  • alarm
  • getitimer / setitimer
  • timer_create / timer_settime / timer_gettime / timer_delete
  • timerfd_create / timerfd_gettime / timerfd_settime
  • 条件变量pthread_cond_timedwait实现
  • IO多路复用select, epoll实现

一般情况下,获取当前时间常用gettimerofday,因为它的精度是1us,并且在x86平台上它是用户态实现的,没有系统调用和上下文切换的开销。

定时函数中:

  1. sleep / alarm在实现时有可能用了信号 SIGALRM,在多线程程序中处理信号是个相当麻烦的事情,应当尽量避免。
  2. nanosleep 和 clock_nanosleep 是线程安全的,但是在非阻塞网络编程中,绝对不能用让线程挂起的方式来等待一段时间,程序会失去响应。正确的做法是注册一个时间回调函数。
  3. getitimer 和 timer_create 也是用信号来 deliver 超时,在多线程程序中也会有麻烦。timer_create 可以指定信号的接收方是进程还是线程,算是一个进步,不过在信号处理函数(signal handler)能做的事情实在很受限。
  4. timerfd_create 把时间变成了一个文件描述符,该“文件”在定时器超时的那一刻变得可读,这样就能很方便地融入到 select/poll 框架中,用统一的方式来处理 IO 事件和超时事件。
  5. 利用select, epoll的timeout实现定时功能,它们的缺点是定时精度只有毫秒,远低于 timerfd_settime 的定时精度。