linux 读写时间变长,linux时钟变慢的原因分析【转】
今天發現現在使用的噪聲儀器時間不準,每天滿大約10幾分鐘,經過查找資料,發現以下一篇中提到的問題很可疑,轉載如下:
聽說有人抱怨他的Linux服務器或者嵌入式Linux開發板上的時間越來越慢,當時念頭一閃,沒有多在意
今天頓悟,果然是有道理的
用戶空間的延時和定時器,都是靠內核定時器實現的。內核定時器 struct timer_list 以及相關內核api,
init_timer()、add_timer、mod_timer 、del_timer,都依賴于jiffes
一個系統時鐘中斷,jiffes就加1,每秒將產生 1*HZ 個jiffes
可以說,這個jiffes,也可稱為滴答,等于是OS的心跳,靠著這個穩定長期的中斷,內核才能夠及時從一個時間片到期的進程手中奪回cpu的使用權,進行下一次調度。當然,每一
次中斷結束或者返回用戶空間都可能進入調度,所以這里用詞是及時。
2.6.21版本開始支持無滴答內核,據說能夠節能。不過我想沒有了滴答,內核定時器失效,很多軟件怕是要重寫了,所以大家都不大關注這個。
常見的計算機系統會帶有一個RTC,這個才是可靠的墻上時鐘源。
不過訪問rtc的速度比較慢,所以只是上電的時候,內核讀取一次rtc時間,之后在OS里看到的時間都是靠一個一個jiffes加上去的。
很多時候,為了保護臨界資源,不得不關閉所有中斷,這個在中斷處理函數中尤為常見。那么就有可能在關閉中斷后的臨界區,發生了系統時鐘中斷,這次時鐘中斷就被忽略了。
導致jiffies沒有增加,進而影響系統時鐘精度。這個概率我只能定性的分析。比如arm上HZ為100,pc上為1000,那么每隔10ms或者1ms就能有一次時鐘中斷。而10ms期間,200MHZ
的arm芯片大約能執行 0.5M
條指令,正好落在臨界區的幾百條指令的概率不是很大。但是計算機跑起來微小的誤差也是很容易積累的,所以如有必要,可以另開一個守護進程,定
時讀取rtc來修正系統時間。
手工驗證一下
spinlock_t lock;
unsigned long flags;
static int test_timer_init_module(void)
{
spin_lock_init(&lock);
printk( KERN_DEBUG "Module test_timer init\n" );
spin_lock_irqsave(&lock, flags);
printk( KERN_DEBUG "the jiffies is %ld\n" ,jiffies);
mdelay(2000);
printk( KERN_DEBUG "the jiffies is %ld\n" ,jiffies);
spin_unlock_irqrestore(&lock, flags);
return 0;
}
不加黑色代碼,兩個jiffes相差
20xx?,pc上HZ為1000,這個結果還是正常的
加上黑色代碼,關閉中斷2000ms,兩個jiffes沒有差別
所以寫驅動一定要自律,關閉中斷后的代碼一定要盡可能的簡潔迅速
所以需要在中斷響應時速度盡量快,處理終端時不能等待太長時間,否則很多其他中斷會被錯誤而導致意想不到的問題,以上時鐘不準就是一例。
總結
以上是生活随笔為你收集整理的linux 读写时间变长,linux时钟变慢的原因分析【转】的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: rufus linux开机密码,使用Ru
- 下一篇: Xp下的程序编译成linux,WinXP