linux驱动中时间相关问题
来源:互联网 发布:德州软件开发 编辑:程序博客网 时间:2024/04/30 13:59
内核代码能一直获取一个当前时间的表示, 通过查看 jifies 的值. 常常地, 这个值只代表从最后一次启动以来的时间, 这个事实对驱动来说无关, 因为它的生命周期受限于系统的 uptime. 如所示, 驱动可以使用 jiffies 的当前值来计算事件之间的时间间隔(例如, 在输入驱动中从单击中区分双击或者计算超时). 简单地讲, 查看 jiffies 几乎一直是足够的, 当你需要测量时间间隔. 如果你需要对短时间流失的非常精确的测量, 处理器特定的寄存器来帮忙了( 尽管它们带来严重的移植性问题 ).
它是非常不可能一个驱动会需要知道墙上时钟时间, 以月, 天, 和小时来表达的; 这个信息常常只对用户程序需要, 例如 cron 和 syslogd. 处理真实世界的时间常常最好留给用户空间, 那里的 C 库提供了更好的支持; 另外, 这样的代码常常太策略相关以至于不属于内核. 有一个内核函数转变一个墙上时钟时间到一个 jiffies 值, 但是:
#include <linux/time.h> unsigned long mktime (unsigned int year, unsigned int mon, unsigned int day, unsigned int hour, unsigned int min, unsigned int sec);
重复:直接在驱动中处理墙上时钟时间往往是一个在实现策略的信号, 并且应当因此而被置疑.
虽然你不会一定处理人可读的时间表示, 有时你需要甚至在内核空间中处理绝对时间. 为此, <linux/time.h> 输出了 do_gettimeofday 函数. 当被调用时, 它填充一个 struct timeval 指针 -- 和在 gettimeofday 系统调用中使用的相同 -- 使用类似的秒和毫秒值. do_gettimeofday 的原型是:
#include <linux/time.h> void do_gettimeofday(struct timeval *tv);
这段源代码声明 do_gettimeofday 有" 接近毫秒的精度", 因为它询问时间硬件当前 jiffy 多大比例已经流失. 这个精度每个体系都不同, 但是, 因为它依赖实际使用中的硬件机制. 例如, 一些 m68knommu 处理器, Sun3 系统, 和其他 m68k 系统不能提供大于 jiffy 的精度. Pentium 系统, 另一方面, 提供了非常快速和精确的小于嘀哒的测量, 通过读取本章前面描述的时戳计数器.
当前时间也可用( 尽管使用 jiffy 的粒度 )来自 xtime 变量, 一个 struct timespec 值. 不鼓励这个变量的直接使用, 因为难以原子地同时存取这 2 个字段. 因此, 内核提供了实用函数 current_kernel_time:
#include <linux/time.h>struct timespec current_kernel_time(void);
用来以各种方式获取当前时间的代码, 可以从由 O' Reilly 提供的 FTP 网站上的源码文件的 jit ("just in time") 模块获得. jit 创建了一个文件称为 /proc/currentime, 当读取时, 它以 ASCII 码返回下列项:
当前的 jiffies 和 jiffies_64 值, 以 16 进制数的形式.
如同 do_gettimeofday 返回的相同的当前时间.
由 current_kernel_time 返回的 timespec.
我们选择使用一个动态的 /proc 文件来保持样板代码为最小 -- 它不值得创建一整个设备只是返回一点儿文本信息.
这个文件连续返回文本行只要这个模块加载着; 每次 read 系统调用收集和返回一套数据, 为更好阅读而组织为 2 行. 无论何时你在少于一个时钟嘀哒内读多个数据集, 你将看到 do_gettimeofday 之间的差别, 它询问硬件, 并且其他值仅在时钟嘀哒时被更新.
phon% head -8 /proc/currentime0x00bdbc1f 0x0000000100bdbc1f 1062370899.630126 1062370899.6291614880x00bdbc1f 0x0000000100bdbc1f 1062370899.630150 1062370899.6291614880x00bdbc20 0x0000000100bdbc20 1062370899.630208 1062370899.6301613360x00bdbc20 0x0000000100bdbc20 1062370899.630233 1062370899.630161336
在上面的屏幕快照中, 由 2 件有趣的事情要注意. 首先, 这个 current_kernel_time 值, 尽管以纳秒来表示, 只有时钟嘀哒的粒度; do_gettimeofday 持续报告一个稍晚的时间但是不晚于下一个时钟嘀哒. 第二, 这个 64-位的 jiffies 计数器有 高 32-位字集合的最低有效位. 这是由于 INITIAL_JIFFIES 的缺省值, 在启动时间用来初始化计数器, 在启动时间后几分钟内强加一个低字溢出来帮助探测与这个刚好溢出相关的问题. 这个在计数器中的初始化偏好没有效果, 因为 jiffies 与墙上时钟时间无关. 在 /proc/uptime 中, 这里内核从计数器中抽取 uptime, 初始化偏好在转换前被去除.
3.容易混淆LINUX时钟的xtime和jiffies http://linux.chinaitlab.com/administer/757250.html
LINUX的时钟中断中涉及至二个全局变量一个是xtime,它是timeval数据结构变量,另一个则是jiffies,首先看timeval结构
struct timeval
{
time_t tv_sec; /***second***/
susecond_t tv_usec;/***microsecond***/
}
这个地方一直有很多人容易混淆,到底microsecond是毫秒还是微秒,我也经常犯这个错误,也被搞的糊涂了很久,我们理清一下吧,1秒=1000毫秒(3个零),1秒=1000 000微秒(6个零),1秒=1000 000 000纳秒(9个零),1秒=1000 000 000 000皮秒(12个零)。秒用s表现,毫秒用ms,微秒用μs表示,纳秒用ns表示,皮秒用ps表示,他们的分级单位是千,即每次3个零。混淆的原因找到了,由于毫秒用ms表示,所以我老是以为microsecond是毫秒,所以就把tv_usec理解错了。microsecond查词霸也是微秒的意思,看来单位的表示迷惑了我,也迷惑了大多数人,请朋友们牢记这里,非常重要。
那么xtime是从cmos电路中取得的时间,一般是从某一历史时刻开始到现在的时间,也就是为了取得我们操作系统上显示的日期。这个就是所谓的“实时时钟”,它的精确度是微秒。
jiffies是记录着从电脑开机到现在总共的时钟中断次数。在linux内核中jiffies远比xtime重要,那么他取决于系统的频率,单位是Hz,这里不得不说一下频率的单位,1MHz=1000,000Hz(6个零), 1KHz=1000Hz(3个零).频率是周期的倒数,一般是一秒钟中断产生的次数,所以,假如我们需要知道系统的精确的时间单位时,需要换算了,假如我们系统的频率是200Mhz,那么一次中断的间隔是1秒/200,000,000Hz=0.000 000 005秒看一下上面我们的时间单位,对照一下小数点后面是9个零,所以理论上我们系统的精确度是5纳秒。LINUX系统时钟频率是一个常数HZ来决定的,通常HZ=100,那么他的精度度就是10ms(毫秒)。也就是说每10ms一次中断。所以一般来说Linux的精确度是10毫秒。
- linux驱动中时间相关问题
- linux驱动中时间相关问题
- linux驱动中时间相关问题
- linux编程中与时间相关的问题总结
- linux时间配置相关问题
- Linux驱动中相关函数查询
- linux驱动中request_mem_region()相关函数
- Linux驱动设计中相关知识点记录
- 程序中涉及到时间的相关问题
- linux中时间相关的函数介绍
- 驱动相关问题
- Linux 驱动相关文件系统
- 编译Linux驱动相关
- Linux USB驱动相关
- linux驱动调试相关
- linux驱动相关命令
- linux驱动相关文章
- linux GPIO驱动相关
- android 广播大全(转)
- 理解GBDT算法(一)——理论
- Swing表格列宽自适应
- Android Studio多渠道打包(以友盟为例)
- 网站在架构时要考虑的事情
- linux驱动中时间相关问题
- 五种类型的程序员
- linux下svn服务搭建
- Python 正则表达式改变csv文件的分隔符
- 对于程序员说的话,项目经理们是这样理解的
- VOIP
- ulimit -c unlimited
- Ajax&Json<2>Ajax核心
- 第十六周上机项目二1