Linux下的微秒级定时器: usleep, nanosleep, select, pselect

标签: linuxnulldelaystructdate
2012-02-07 23:29 4979人阅读 评论(0) 收藏 举报

 分类:
Linux 系统编程(26) 

版权声明:本文为博主原创文章,未经博主允许不得转载。

今天在公司代码中看到了使用select函数的超时功能作定时器的用法,便整理了如下几个Linux下的微秒级别的定时器。在我的Ubutu10.10 双核环境中,编译通过。

[cpp] view plaincopy
  1. /*
  2. * @FileName: test_sleep.c
  3. * @Author: wzj
  4. * @Brief:
  5. *
  6. *
  7. * @History:
  8. *
  9. * @Date: 2012年02月07日星期二22:20:00
  10. *
  11. */
  12. #include<stdio.h>
  13. #include<stdlib.h>
  14. #include<time.h>
  15. #include<sys/time.h>
  16. #include<errno.h>
  17. #include<string.h>
  18. #include<unistd.h>
  19. #include<sys/types.h>
  20. #include<sys/select.h>
  21. int main(int argc, char **argv)
  22. {
  23. unsigned int nTimeTestSec = 0;
  24. unsigned int nTimeTest = 0;
  25. struct timeval tvBegin;
  26. struct timeval tvNow;
  27. int ret = 0;
  28. unsigned int nDelay = 0;
  29. struct timeval tv;
  30. int fd = 1;
  31. int i = 0;
  32. struct timespec req;
  33. unsigned int delay[20] =
  34. {500000, 100000, 50000, 10000, 1000, 900, 500, 100, 10, 1, 0};
  35. int nReduce = 0; //误差
  36. fprintf(stderr, "%19s%12s%12s%12s\n", "fuction", "time(usec)", "realtime", "reduce");
  37. fprintf(stderr, "----------------------------------------------------\n");
  38. for (i = 0; i < 20; i++)
  39. {
  40. if (delay[i] <= 0)
  41. break;
  42. nDelay = delay[i];
  43. //test sleep
  44. gettimeofday(&tvBegin, NULL);
  45. ret = usleep(nDelay);
  46. if(ret == -1)
  47. {
  48. fprintf(stderr, "usleep error, errno=%d [%s]\n", errno, strerror(errno));
  49. }
  50. gettimeofday(&tvNow, NULL);
  51. nTimeTest = (tvNow.tv_sec - tvBegin.tv_sec) * 1000000 + tvNow.tv_usec - tvBegin.tv_usec;
  52. nReduce = nTimeTest - nDelay;
  53. fprintf (stderr, "\t usleep       %8u   %8u   %8d\n", nDelay, nTimeTest,nReduce);
  54. //test nanosleep
  55. req.tv_sec = nDelay/1000000;
  56. req.tv_nsec = (nDelay%1000000) * 1000;
  57. gettimeofday(&tvBegin, NULL);
  58. ret = nanosleep(&req, NULL);
  59. if (-1 == ret)
  60. {
  61. fprintf (stderr, "\t nanousleep   %8u   not support\n", nDelay);
  62. }
  63. gettimeofday(&tvNow, NULL);
  64. nTimeTest = (tvNow.tv_sec - tvBegin.tv_sec) * 1000000 + tvNow.tv_usec - tvBegin.tv_usec;
  65. nReduce = nTimeTest - nDelay;
  66. fprintf (stderr, "\t nanosleep    %8u   %8u   %8d\n", nDelay, nTimeTest,nReduce);
  67. //test select
  68. tv.tv_sec = 0;
  69. tv.tv_usec = nDelay;
  70. gettimeofday(&tvBegin, NULL);
  71. ret = select(0, NULL, NULL, NULL, &tv);
  72. if (-1 == ret)
  73. {
  74. fprintf(stderr, "select error. errno = %d [%s]\n", errno, strerror(errno));
  75. }
  76. gettimeofday(&tvNow, NULL);
  77. nTimeTest = (tvNow.tv_sec - tvBegin.tv_sec) * 1000000 + tvNow.tv_usec - tvBegin.tv_usec;
  78. nReduce = nTimeTest - nDelay;
  79. fprintf (stderr, "\t select       %8u   %8u   %8d\n", nDelay, nTimeTest,nReduce);
  80. //pselcet
  81. req.tv_sec = nDelay/1000000;
  82. req.tv_nsec = (nDelay%1000000) * 1000;
  83. gettimeofday(&tvBegin, NULL);
  84. ret = pselect(0, NULL, NULL, NULL, &req, NULL);
  85. if (-1 == ret)
  86. {
  87. fprintf(stderr, "select error. errno = %d [%s]\n", errno, strerror(errno));
  88. }
  89. gettimeofday(&tvNow, NULL);
  90. nTimeTest = (tvNow.tv_sec - tvBegin.tv_sec) * 1000000 + tvNow.tv_usec - tvBegin.tv_usec;
  91. nReduce = nTimeTest - nDelay;
  92. fprintf (stderr, "\t pselect      %8u   %8u   %8d\n", nDelay, nTimeTest,nReduce);
  93. fprintf (stderr, "--------------------------------\n");
  94. }
  95. return 0;
  96. }

老大建议我们在对精度要求较高的情况下使用select()作为定时器,最大的好处就是不会影响信号处理,线程安全,而且精度能得到保证。在这个实验中,当时间延时时间较长时,select和pselect表现较差,当时间小于1毫秒时,他们的精确度便提高了,表现与usleep、nanosleep不相上下,有时精度甚至超过后者

-------------------------------------------------------------------------------------------------------------------------------------------------

Linux下的微秒级定时器: usleep, nanosleep, select, pselect相关推荐

  1. linux 微秒级定时,Linux下的微秒级定时器: usleep, nanosleep, select, pselect

    /* * @FileName: test_sleep.c * @Author: wzj * @Brief: * * * @History: * * @Date: 2012年02月07日星期二22:20 ...

  2. linux下获取微秒级精度的时间【转】

    转自:https://blog.csdn.net/u011857683/article/details/81320052 使用C语言在linux环境下获得微秒级时间 1. 数据结构 int getti ...

  3. linux下获取微秒级精度的时间

    使用C语言在linux环境下获得微秒级时间 1. 数据结构 int gettimeofday(struct timeval*tv, struct timezone *tz); 其参数tv是保存获取时间 ...

  4. Linux中延时/暂停函数(sleep/usleep/nanosleep/select)的比较、底层实现说明

    本来只是要搞清楚Linux下如何实现延时和暂停,但无意中看到一篇文章介绍了其实现,帮自己窥得一点底层原理. 知其然还要知其所以然,但自己没有这个储备和能力来研究Linux内核实现,特地转载留存. 1. ...

  5. linux下usleep nanosleep select的比较经历

    sleep:单位为秒,1秒 usleep:单位为微秒,1/1000 秒 select:单位为微秒,1/1000 000 秒 nanosleep:单位为毫微秒,也就是纳秒,1/1000 000 000 ...

  6. Linux下获取毫秒级时间差

    Linux下获取毫秒级时间差 使用Linux的gettimeofday函数可以达到这个目的  其中t1=t_start.tv_sec是公元1970年至今的时间(换算为秒)  t2=t_start.tv ...

  7. c语言 linux系统 delay,Linux下实现秒级定时任务的两种方案

    Linux下实现秒级定时任务的两种方案(Crontab 每秒运行): 第一种方案,当然是写一个后台运行的脚本一直循环,然后每次循环sleep一段时间. while true ;do command s ...

  8. c#实现 微秒级定时器,高精度定时器

    c# 微秒级定时器,高精度定时器 整个代码,封装成类 using System; using System.Runtime.InteropServices;namespace winTest {/// ...

  9. 无需另配定时器在STM32 HAL下实现微秒级延时(兼容FreeRTOS)

    目录 前言 一.代码部分 二.使用和验证 1.引入头文件 2.初始化 3.使用和验证 三.可移植性 总结 前言 接触HAL库差不多两年了,一直苦于HAL库没有自带微秒级的延时,网上的前辈们给出的解决方 ...

最新文章

  1. 【 FPGA/IC 】addsub 的实现
  2. iOS 各种编译错误汇总
  3. 数据结构---多源最短路径
  4. portal认证 php,如何用PHP制作OSSH 免费版华为Portal系统认证前端页面
  5. 异常mongodb:Invalid BSON field name XXXXXX:YYYYY.zz
  6. linux中间人攻击工具,[web安全]使用ARPspoof进行中间人(MiTM)攻击
  7. vcpkg编译库位数总结
  8. 统计学常用的数据分析方法总结
  9. java代码压缩文件
  10. java实现评论功能_Java实现评论回复功能的完整步骤
  11. Golang 实现定时任务
  12. 分享一个超大文件编辑器(WINDOWS 文本编辑器)
  13. 未来的智能制造,或许会往这些方向推进
  14. 北京法院京牌小客车司法处置数据统计(Pandas)
  15. 徐直军:今年至少3亿设备用上鸿蒙,互联网又一领域暗藏“金矿“
  16. (二)企业微信消息推送
  17. 浅谈ThreadPoolExecute(JDK8)
  18. SQL 大厂面试真题篇
  19. 哪款微信群管理软件好用?
  20. 一次简单的路由器渗透

热门文章

  1. 怎么通过controller层退出登录_控制层访问拦截
  2. NodeJs局域网开启服务
  3. ftp 上传档案到主机 OMVS
  4. html5 中keygen用法,HTML5: keygen 标签
  5. linux usb全自动安装失败,关于使用universal usb installer 安装 archlinux 失败的问题
  6. 橱柜高度与身高对照表_170身高和橱柜高度对照表 详细解析
  7. 智能家居行业的数据传输保护
  8. VB将自定义资源中的文件释放出来
  9. 网易博客技巧(表格的高级样式)
  10. 智能一代云平台(三十一):mybatis加入分页