日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 >

Linux文件预读对系统的影响

發(fā)布時間:2025/1/21 47 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Linux文件预读对系统的影响 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

Linux系統(tǒng)很重要的一個性能提升點就是它的Pagecache, 因為內(nèi)存比IO快太多了,所以大家都想進辦法來利用這個cache。 文件系統(tǒng)也不例外,為了達(dá)到高性能,文件讀取通常采用預(yù)讀來預(yù)測用戶的行為,把用戶可能需要的數(shù)據(jù)預(yù)先讀取到cache去,達(dá)到高性能的目的。

Linux各個發(fā)行版readahead的實現(xiàn)差異很大,我們這里重點討論2.6.18, RHEL 5U4發(fā)行版的行為.文件預(yù)讀的實現(xiàn)主要在mm/readahead.c中,代碼才603行。 預(yù)讀的流程大概是這樣的,用戶需要文件頁面的時候入口函數(shù)do_generic_mapping_read會委托 page_cache_readahead來進行處理。它首先判斷用戶的IO是順序的還是隨機的,如果是隨機的就沒啥好預(yù)讀. 如果是順序的話,那么預(yù)讀算法會根據(jù)用戶上一次讀取的頁面的使用情況評估出預(yù)讀的窗口,決定要讀多少頁面。讀頁面的模塊會先檢查要讀取頁面在 pagecache里面是否已經(jīng)存在,如果不存在的話就需要發(fā)起IO請求,讀取相應(yīng)的頁面。

這個預(yù)讀的關(guān)鍵參數(shù)有3個: 用戶的req_size, 預(yù)讀算法評估出來的nr_to_read,以及實際上IO讀取的頁面數(shù)actual。

接下來我們就是要查看系統(tǒng)是如何運作的,所以我首先寫了個systemtap腳本叫做ratop.stp來獲取這些數(shù)據(jù):

perl"> $ uname -r 2.6.18-164.el5 $ rpm -i kernel-debuginfo-common-2.6.18-164.el5.x86_64.rpm $ rpm -i kernel-debuginfo-2.6.18-164.el5.x86_64.rpm $ cat > ratop.stp #!/usr/bin/stap -DMAXMAPENTRIES=10240 global total, skip global req, to_read, actual global __inode_filename probe kernel.function("page_cache_readahead") { ino = __file_ino($filp) req[ino]+=$req_size; total++; if($ra->flags & 0x2) skip++; } probe kernel.function("__do_page_cache_readahead").return { ino = __file_ino($filp) to_read[ino]+= $nr_to_read; if($return>0) actual[ino]+=$return; } probe timer.ms(5000) { if(total) { foreach( ino in req-) { s0+= req[ino]; s1+= to_read[ino] s2+= actual[ino]; } printf("\\n%25s, %5s%6d, %5s%6d, %5s%8d, %5s%8d, %5s%8d\\n\\n", ctime(gettimeofday_s()), "TOTAL:", total, "SKIP:", skip, "REQ:",s0, "TO_RD:",s1, "NR_RD:",s2 ) /* print header */ printf("%25s %8s %8s %8s\\n", "FILENAME","REQ","TO_RD","NR_RD") foreach( ino in req- limit 20) printf("%25s %8d %8d %8d\\n", find_filename(ino), req[ino], to_read[ino], actual[ino]); } delete total; delete skip; delete req; delete to_read; delete actual; } probe generic.fop.open { __inode_filename[ino]= filename } function find_filename(ino) { return __inode_filename[ino]==""?sprint(ino):__inode_filename[ino]; } probe begin { println("::"); } CTRL +D $ chmod +x ratop.stp $ sudo ./ratop.stp :: Tue May 31 05:41:37 2011, TOTAL: 2321, SKIP: 0, REQ: 6308, TO_RD: 6308, NR_RD: 1424 FILENAME REQ TO_RD NR_RD 056878.sst 15 15 0 062889.sst 13 13 6 .. 其中各個參數(shù)含義解釋如下: TOTAL: 系統(tǒng)共調(diào)用了多少次預(yù)讀 SKIP: 由于頁面在PAGECACHE中存在,略過多少次預(yù)讀 REQ: 用戶準(zhǔn)備讀取的頁面數(shù) TO_RD:預(yù)讀算法告訴我們要讀取的頁面數(shù) NR_RD:實際IO系統(tǒng)讀取的頁面數(shù) 這個腳本每5秒打印下系統(tǒng)目前的預(yù)讀情況。

好吧,有了這個工具我們就可以做實驗了。

先在一個終端下運行我們的腳本:

$ sudo ./ratop.stp ::#等著出數(shù)據(jù)...

然后在另外一個終端下做實驗:

#準(zhǔn)備個數(shù)據(jù)文件 $ dd if=/dev/zero of=test count=1024 bs=4096 1024+0 records in 1024+0 records out 4194304 bytes (4.2 MB) copied, 0.008544 seconds, 491 MB/s #清空pagecache $ sudo sysctl vm.drop_caches=3 vm.drop_caches = 3 #第一次拷貝 $ cp test junk && sleep 5 #第二次拷貝 $ cp test junk

我們就可以在之前的腳本窗口里看到下面的信息:

#第一次拷貝test,我們可以看到 用戶要1025個頁面,預(yù)讀決定讀1084,但是實際IO讀了1024,很合理,因為當(dāng)時pagecache是空的Tue May 31 05:50:21 2011, TOTAL: 1038, SKIP: 0, REQ: 1039, TO_RD: 1320, NR_RD: 1109 FILENAME REQ TO_RD NR_RD test 1025 1084 1024 cp 3 36 18 ... #第二次拷貝test,我們可以看到 用戶要1025個頁面,預(yù)讀決定讀284,但是實際IO讀了0,很合理,因為所有的頁面在pagecache里面都已經(jīng)存在 Tue May 31 05:50:46 2011, TOTAL: 1038, SKIP: 804, REQ: 1039, TO_RD: 328, NR_RD: 0 FILENAME REQ TO_RD NR_RD test 1025 284 0 cp 3 4 0 ...

Linux系統(tǒng)不僅為文件的讀取提供自動預(yù)讀,還提供了readahead這樣的系統(tǒng)調(diào)用和工具,幫助用戶主動預(yù)加載數(shù)據(jù),我們演示下:

$ readahead junk Preloaded 0 files (0 KB) in 5 ms

另外一個窗口說:

Tue May 31 05:57:45 2011, TOTAL: 1044, SKIP: 805, REQ: 1045, TO_RD: 348, NR_RD: 0 FILENAME REQ TO_RD NR_RD junk 1026 284 0 readahead 3 4 0

Linux還支持對每個設(shè)備設(shè)定預(yù)讀的默認(rèn)大小,不同的大小可以用來控制預(yù)讀的力度,用戶可以自行改變:

$ pwd /sys/block/sda/queue $ cat read_ahead_kb 128 $ echo 256 |sudo tee read_ahead_kb 256

后續(xù)我會用這個工具分析leveldb數(shù)據(jù)庫的行為,歡迎關(guān)注!

總結(jié): 如果actual讀比用戶req的要多很多, 那么我們的很多預(yù)讀就浪費了,可以考慮減少預(yù)讀的大小。

  • 本文來自:Linux學(xué)習(xí)

轉(zhuǎn)載于:https://www.cnblogs.com/www886/p/4323670.html

總結(jié)

以上是生活随笔為你收集整理的Linux文件预读对系统的影响的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。