linux内核中测量时间的方法,Linux内核中获取时间函数do_gettimeofday
內核代碼能一直獲取一個當前時間的表示, 通過查看 jifies 的值. 常常地, 這個值只代表從最后一次啟動以來的時間, 這個事實對驅動來說無關, 因為它的生命周期受限于系統的 uptime. 如所示, 驅動可以使用 jiffies 的當前值來計算事件之間的時間間隔(例如, 在輸入驅動中從單擊中區分雙擊或者計算超時). 簡單地講, 查看 jiffies 幾乎一直是足夠的, 當你需要測量時間間隔. 如果你需要對短時間流失的非常精確的測量, 處理器特定的寄存器來幫忙了( 盡管它們帶來嚴重的移植性問題 ).
它是非常不可能一個驅動會需要知道墻上時鐘時間, 以月, 天, 和小時來表達的; 這個信息常常只對用戶程序需要, 例如 cron 和 syslogd. 處理真實世界的時間常常最好留給用戶空間, 那里的 C 庫提供了更好的支持; 另外, 這樣的代碼常常太策略相關以至于不屬于內核. 有一個內核函數轉變一個墻上時鐘時間到一個 jiffies 值, 但是:
#include
unsigned long mktime (unsigned int year, unsigned int mon, unsigned int day, unsigned int hour, unsigned int min, unsigned int sec);
重復:直接在驅動中處理墻上時鐘時間往往是一個在實現策略的信號, 并且應當因此而被置疑.
雖然你不會一定處理人可讀的時間表示, 有時你需要甚至在內核空間中處理絕對時間. 為此, 輸出了 do_gettimeofday 函數. 當被調用時, 它填充一個 struct timeval 指針 -- 和在 gettimeofday 系統調用中使用的相同 -- 使用類似的秒和毫秒值. do_gettimeofday 的原型是:
#include
void do_gettimeofday(struct timeval *tv);
這段源代碼聲明 do_gettimeofday 有" 接近毫秒的精度", 因為它詢問時間硬件當前 jiffy 多大比例已經流失. 這個精度每個體系都不同, 但是, 因為它依賴實際使用中的硬件機制. 例如, 一些 m68knommu 處理器, Sun3 系統, 和其他 m68k 系統不能提供大于 jiffy 的精度. Pentium 系統, 另一方面, 提供了非??焖俸途_的小于嘀噠的測量, 通過讀取本章前面描述的時戳計數器.
當前時間也可用( 盡管使用 jiffy 的粒度 )來自 xtime 變量, 一個 struct timespec 值. 不鼓勵這個變量的直接使用, 因為難以原子地同時存取這 2 個字段. 因此, 內核提供了實用函數 current_kernel_time:
#include
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 之間的差別, 它詢問硬件, 并且其他值僅在時鐘嘀噠時被更新. 1、使用rtc設備,這個時鐘可以用于各種模式? 2、借鑒系統調用adjtimex? 這里使用第二種方式 系統調用adjtimex 一直跟下去,會發現最后調用? void do_gettimeofday(struct timeval *tv) 那么直接使用do_gettimeofday,能夠得到struct timeval struct timeval {? time_t tv_sec; /* seconds */? suseconds_t tv_usec; /* microseconds */? }; 那么就需要將這個tv_sec,即1970年開始至今的秒數轉換為年月日時分秒? 其實內核已經有這樣的函數? /*? * Convert seconds since 01-01-1970 00:00:00 to Gregorian date.? */? void rtc_time_to_tm(unsigned long time, struct rtc_time *tm) 唯一的不足是轉換得到的是UTC時間,同北京時間差8小時。要想達到用戶態localtime()的效果,必須獲得/etc/localtime 中的時區信息。 示例代碼: #include ? #include ? #include /*添加到合適位置*/ struct timex ?txc;? struct rtc_time tm;? do_gettimeofday(&(txc.time));? rtc_time_to_tm(txc.time.tv_sec,&tm);? printk(“UTC time :%d-%d-%d %d:%d:%d /n”,tm.tm_year+1900,tm.tm_mon, tm.tm_mday,tm.tm_hour,tm.tm_min,tm.tm_sec);
總結
以上是生活随笔為你收集整理的linux内核中测量时间的方法,Linux内核中获取时间函数do_gettimeofday的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Argus
- 下一篇: linux 内核空间占用cpu百分比过高