轉:linux io排程深入分析
讀完這篇最好讀下,really great
轉自
一)I/O排程程式的總結:
1)當向裝置寫入資料塊或是從裝置讀出資料塊時,請求都被安置在一個佇列中等待完成.
2)每個塊裝置都有它自己的佇列.
3)I/O排程程式負責維護這些佇列的順序,以更有效地利用介質.I/O排程程式將無序的I/O操作變為有序的I/O操作.
4)核心必須首先確定佇列中一共有多少個請求,然後才開始進行排程.
二)I/O排程的4種演算法
1)CFQ(完全公平排隊I/O排程程式)
特點:
在最新的核心版本和發行版中,都選擇CFQ做為預設的I/O排程器,對於通用的伺服器也是最好的選擇.
CFQ試圖均勻地分佈對I/O頻寬的訪問,避免程式被餓死並實現較低的延遲,是deadline和as排程器的折中.
CFQ對於多媒體應用(video,audio)和桌面系統是最好的選擇.
CFQ賦予I/O請求一個優先順序,而I/O優先順序請求獨立於程式優先順序,高優先順序的程式的讀寫不能自動地繼承高的I/O優先順序.
工作原理:
CFQ為每個程式/執行緒,單獨建立一個佇列來管理該程式所產生的請求,也就是說每個程式一個佇列,各佇列之間的排程使用時間片來排程,
以此來保證每個程式都能被很好的分配到I/O頻寬.I/O排程器每次執行一個程式的4次請求.
2)NOOP(電梯式排程程式)
特點:
在Linux2.4或更早的版本的排程程式,那時只有這一種I/O排程演算法.
NOOP實現了一個簡單的FIFO佇列,它像電梯的工作主法一樣對I/O請求進行組織,當有一個新的請求到來時,它將請求合併到最近的請求之後,以此來保證請求同一介質.
NOOP傾向餓死讀而利於寫.
NOOP對於快閃記憶體裝置,RAM,嵌入式系統是最好的選擇.
電梯演算法餓死讀請求的解釋:
因為寫請求比讀請求更容易.
寫請求透過檔案系統cache,不需要等一次寫完成,就可以開始下一次寫操作,寫請求透過合併,堆積到I/O佇列中.
讀請求需要等到它前面所有的讀操作完成,才能進行下一次讀操作.在讀操作之間有幾毫秒時間,而寫請求在這之間就到來,餓死了後面的讀請求.
3)Deadline(截止時間排程程式)
特點:
透過時間以及硬碟區域進行分類,這個分類和合並要求類似於noop的排程程式.
Deadline確保了在一個截止時間內服務請求,這個截止時間是可調整的,而預設讀期限短於寫期限.這樣就防止了寫操作因為不能被讀取而餓死的現象.
Deadline對資料庫環境(ORACLE RAC,MYSQL等)是最好的選擇.
4)AS(預料I/O排程程式)
特點:
本質上與Deadline一樣,但在最後一次讀操作後,要等待6ms,才能繼續進行對其它I/O請求進行排程.
可以從應用程式中預訂一個新的讀請求,改進讀操作的執行,但以一些寫操作為代價.
它會在每個6ms中插入新的I/O操作,而會將一些小寫入流合併成一個大寫入流,用寫入延時換取最大的寫入吞吐量.
AS適合於寫入較多的環境,比如檔案伺服器
AS對資料庫環境表現很差.
三)I/O排程方法的檢視與設定
1)檢視當前系統的I/O排程方法:
[root@test1 tmp]# cat /sys/block/sda/queue/scheduler
noop anticipatory deadline [cfq]
2)臨地更改I/O排程方法:
例如:想更改到noop電梯排程演算法:
echo noop > /sys/block/sda/queue/scheduler
3)想永久的更改I/O排程方法:
修改核心引導引數,加入elevator=排程程式名
[root@test1 tmp]# vi /boot/grub/menu.lst
更改到如下內容:
kernel /boot/vmlinuz-2.6.18-8.el5 ro root=LABEL=/ elevator=deadline rhgb quiet
重啟之後,檢視排程方法:
[root@test1 ~]# cat /sys/block/sda/queue/scheduler
noop anticipatory [deadline] cfq
已經是deadline了
四)I/O排程程式的測試
本次測試分為只讀,只寫,讀寫同時進行.
分別對單個檔案600MB,每次讀寫2M,共讀寫300次.
1)測試磁碟讀:
[root@test1 tmp]# echo deadline > /sys/block/sda/queue/scheduler
[root@test1 tmp]# time dd if=/dev/sda1 f=/dev/null bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 6.81189 seconds, 92.4 MB/s
real 0m6.833s
user 0m0.001s
sys 0m4.556s
[root@test1 tmp]# echo noop > /sys/block/sda/queue/scheduler
[root@test1 tmp]# time dd if=/dev/sda1 f=/dev/null bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 6.61902 seconds, 95.1 MB/s
real 0m6.645s
user 0m0.002s
sys 0m4.540s
[root@test1 tmp]# echo anticipatory > /sys/block/sda/queue/scheduler
[root@test1 tmp]# time dd if=/dev/sda1 f=/dev/null bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 8.00389 seconds, 78.6 MB/s
real 0m8.021s
user 0m0.002s
sys 0m4.586s
[root@test1 tmp]# echo cfq > /sys/block/sda/queue/scheduler
[root@test1 tmp]# time dd if=/dev/sda1 f=/dev/null bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 29.8 seconds, 21.1 MB/s
real 0m29.826s
user 0m0.002s
sys 0m28.606s
結果:
第一 noop:用了6.61902秒,速度為95.1MB/s
第二 deadline:用了6.81189秒,速度為92.4MB/s
第三 anticipatory:用了8.00389秒,速度為78.6MB/s
第四 cfq:用了29.8秒,速度為21.1MB/s
2)測試寫磁碟:
[root@test1 tmp]# echo cfq > /sys/block/sda/queue/scheduler
[root@test1 tmp]# time dd if=/dev/zero f=/tmp/test bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 6.93058 seconds, 90.8 MB/s
real 0m7.002s
user 0m0.001s
sys 0m3.525s
[root@test1 tmp]# echo anticipatory > /sys/block/sda/queue/scheduler
[root@test1 tmp]# time dd if=/dev/zero f=/tmp/test bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 6.79441 seconds, 92.6 MB/s
real 0m6.964s
user 0m0.003s
sys 0m3.489s
[root@test1 tmp]# echo noop > /sys/block/sda/queue/scheduler
[root@test1 tmp]# time dd if=/dev/zero f=/tmp/test bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 9.49418 seconds, 66.3 MB/s
real 0m9.855s
user 0m0.002s
sys 0m4.075s
[root@test1 tmp]# echo deadline > /sys/block/sda/queue/scheduler
[root@test1 tmp]# time dd if=/dev/zero f=/tmp/test bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 6.84128 seconds, 92.0 MB/s
real 0m6.937s
user 0m0.002s
sys 0m3.447s
測試結果:
第一 anticipatory,用了6.79441秒,速度為92.6MB/s
第二 deadline,用了6.84128秒,速度為92.0MB/s
第三 cfq,用了6.93058秒,速度為90.8MB/s
第四 noop,用了9.49418秒,速度為66.3MB/s
3)測試同時讀/寫
[root@test1 tmp]# echo deadline > /sys/block/sda/queue/scheduler
[root@test1 tmp]# dd if=/dev/sda1 f=/tmp/test bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 15.1331 seconds, 41.6 MB/s
[root@test1 tmp]# echo cfq > /sys/block/sda/queue/scheduler
[root@test1 tmp]# dd if=/dev/sda1 f=/tmp/test bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 36.9544 seconds, 17.0 MB/s
[root@test1 tmp]# echo anticipatory > /sys/block/sda/queue/scheduler
[root@test1 tmp]# dd if=/dev/sda1 f=/tmp/test bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 23.3617 seconds, 26.9 MB/s
[root@test1 tmp]# echo noop > /sys/block/sda/queue/scheduler
[root@test1 tmp]# dd if=/dev/sda1 f=/tmp/test bs=2M count=300
300+0 records in
300+0 records out
629145600 bytes (629 MB) copied, 17.508 seconds, 35.9 MB/s
測試結果:
第一 deadline,用了15.1331秒,速度為41.6MB/s
第二 noop,用了17.508秒,速度為35.9MB/s
第三 anticipatory,用了23.3617秒,速度為26.9MS/s
第四 cfq,用了36.9544秒,速度為17.0MB/s
五)ionice
ionice可以更改任務的型別和優先順序,不過只有cfq排程程式可以用ionice.
有三個例子說明ionice的功能:
採用cfq的實時排程,優先順序為7
ionice -c1 -n7 -ptime dd if=/dev/sda1 f=/tmp/test bs=2M count=300&
採用預設的磁碟I/O排程,優先順序為3
ionice -c2 -n3 -ptime dd if=/dev/sda1 f=/tmp/test bs=2M count=300&
採用空閒的磁碟排程,優先順序為0
ionice -c3 -n0 -ptime dd if=/dev/sda1 f=/tmp/test bs=2M count=300&
ionice的三種排程方法,實時排程最高,其次是預設的I/O排程,最後是空閒的磁碟排程.
ionice的磁碟排程優先順序有8種,最高是0,最低是7.
注意,磁碟排程的優先順序與程式nice的優先順序沒有關係.
一個是針對程式I/O的優先順序,一個是針對程式CPU的優先順序.
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/7591490/viewspace-1033158/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- Linux IO排程方法Linux
- 如何選擇IO排程器
- linux程式排程Linux
- 排程器簡介,以及Linux的排程策略Linux
- linux搶佔式排程Linux
- Linux I/O排程器Linux
- MySQL優化--IO排程演算法優化MySql優化演算法
- Linux 定時任務排程Linux
- Flink排程之排程器、排程策略、排程模式模式
- 2.2.5排程演算法:時間片輪轉、優先順序排程、多級反饋排程演算法
- Linux程序排程器-CPU負載Linux負載
- Linux Shell指令碼時間排程Linux指令碼
- LInux實驗 : 程式排程模擬Linux
- linux之 修改磁碟排程演算法Linux演算法
- 如何更改Linux的I/O排程器Linux
- Linux排程器:程序優先順序Linux
- 網路io排詢
- Linux程式排程邏輯與原始碼分析Linux原始碼
- Linux 中 Laravel 任務排程不執行LinuxLaravel
- MySQL資料庫環境如何調整磁碟IO排程演算法MySql資料庫演算法
- linux基礎(四)——任務排程cron和anacronLinux
- Linux核心學習筆記(5)– 程式排程概述Linux筆記
- Linux之CPU排程策略和CPU親和性Linux
- 一文詳解 Linux Crontab 排程任務Linux
- Linux 核心排程器原始碼分析 - 初始化Linux原始碼
- kubernetes 排程
- Go排程器系列(3)圖解排程原理Go圖解
- Go語言排程器之主動排程(20)Go
- Go runtime 排程器精講(五):排程策略Go
- Spark中資源排程和任務排程Spark
- 高階Java工程師必備 ----- 深入分析 Java IO (三)Java工程師
- Go語言排程器之排程main goroutine(14)GoAI
- Go排程器系列(2)巨集觀看排程器Go
- Pod的排程是由排程器(kube-scheduler)
- async-await:協作排程 vs 搶佔排程AI
- python之IO併發-阻塞IO 非阻塞IO IO多路複用 非同步IO(協程)Python非同步
- 【IO】Linux下的五種IO模型Linux模型
- 任務排程
- 雲排程概述