IOPS(Input/Output Per Second)即每秒磁盤的讀寫次數,是衡量磁盤性能的主要名額之一。IOPS是指機關時間内系統能處理的I/O請求數量,一般以每秒處理的I/O請求數量為機關,I/O請求通常為讀或寫資料操作請求。
想要知道磁盤的IOPS有多高,可以使用fio工具測試!
FIO是測試IOPS的非常好的工具,用來對磁盤進行壓力測試和驗證。磁盤IO是檢查磁盤性能的重要名額,可以按照負載情況分成照順序讀寫,随機讀寫兩大類。FIO是一個可以産生很多線程或程序并執行使用者指定的特定類型I/O操作的工具,FIO的典型用途是編寫和模拟的I/O負載比對的作業檔案。也就是說FIO 是一個多線程io生成工具,可以生成多種IO模式,用來測試磁盤裝置的性能(也包含檔案系統:如針對網絡檔案系統 NFS 的IO測試)。
Fio(Flexible I/O Tester)是一款由Jens Axboe開發的用于測評和壓力/硬體驗證的自由開源的軟體。它支援[sync、mmap、libaio、posixaio、SG v3、splice、null、network、 syslet、guasi、solarisaio] 等19 種不同類型的 I/O 引擎測試。Fio 接受一種非常簡單易于了解的文本格式的任務描述。軟體預設包含了幾個示例任務檔案。 Fio 展示了所有類型的 I/O 性能資訊,包括完整的 IO 延遲和百分比。
磁盤測試工具 FIO 安裝和使用方法
fio可以通過源碼安裝、rpm包安裝以及yum安裝;
- 源碼安裝方式
官網位址:http://freecode.com/projects/fio/
github 位址:https://github.com/axboe/fio
wget https://github.com/axboe/fio/archive/refs/tags/fio-3.14.tar.gz
tar -zxvf fio-3.14.tar.gz
./configure
make
make install
- rpm包安裝
官網位址:https://pkgs.org/download/fio
rpm 包:http://mirror.centos.org/centos/7/os/x86_64/Packages/fio-3.7-2.el7.x86_64.rpm
wget http://mirror.centos.org/centos/7/os/x86_64/Packages/fio-3.7-2.el7.x86_64.rpm
yum install libaio-devel
yum install libibverbs -y
yum install libpmem -y
yum install librados2 -y
yum install librbd1
rpm -ivh fio-3.7-2.el7.x86_64.rpm
- yum安裝:
yum install fio
fio使用參數說明
-filename=/dev/sdb1 /*測試檔案名稱,通常選擇需要測試的盤的data目錄。*/
-filename /*定義測試檔案(裝置)的名稱。此處選擇檔案,則代表測試檔案系統的性能,
例如:- filename=/opt/fiotest/fiotest.txt;
此處選擇裝置名稱,則代表測試裸盤的性能,例:-filename=/dev/vdb1。
如果在已經分區、并建立檔案系統,且已寫入資料的磁盤上進行性能測試,
請注意filename選擇指定檔案,以避免覆寫檔案系統和原有資料。*/
-direct=1 /*定義是否使用direct IO,可選值如下:值為0,表示使用buffered IO;
值為1,表示使用 direct IO,測試過程繞過機器自帶的buffer。使測試結果更真實。*/
-ioengine=libaio /*libaio指的是異步模式,如果是同步就要用sync。
vsync - 使用 readv / writev,主要是會将相鄰的 I/O 進行合并
psync - 對應的 pread / pwrite,增量同步,一般sync是全量的
pvsync / pvsync2 - 對應的 preadv / pwritev,以及 preadv2 / p writev2
定義fio如何下發IO請求,通常有同步IO和異步IO:
同步IO一次隻能發出一個IO請求, 等待核心完成後才傳回。
這樣對于單個線程IO隊列深度總是小于1,但是可以透過多個線程并發執行來解決。
通常會用16~32個線程同時工作把IO隊列深度塞滿。
異步IO則通常使用libaio這樣的方式一次送出一批
IO 請求,然後等待一批的完成,減少互動的次數,會更有效率*/
-iodepth=64 /*定義測試時的IO隊列深度,預設為1。
此處定義的隊列深度是指每個線程的隊列深度,
如果有多個線程測試,意味着每個線程都是此處定義的隊列深度。
fio總的IO并發數 =iodepth * numjobs*/
-rw=randwrite /*定義測試時的讀寫政策,
可選值如下:
随機讀:randread,
随機寫:randwrite,
順序讀: read,
順序寫:write,
混合随機讀寫:randrw-bs=4k /*定義IO的塊大小(block size),
機關是k、K、m和M等,預設IO塊大小為4 KB*/
-size=100M /*定義測試IO操作的資料量,若未指定runtime這類參數,
fio會将指定大小的資料量全部 讀/寫完成,然後才停止測試。
該參數的值,可以是帶機關的數字,比如size=10G,
表示讀/寫的資料量為10GB;也可是百分數,比如size=20%,
表示讀/寫的資料量占該裝置總檔案的20%的空間。
建議測試資料量為記憶體兩倍大,盡量避免緩存影響。*/
-numjobs=4 /*每個job(任務)開1個線程,這裡用了幾,
後面每個用-name指定的任務就開幾個線程測試。
是以最終線程數=任務數(幾個name=jobx)* numjobs。 */
-runtime /*定義測試時間。如果未配置,則持續将size指定的檔案大小,
以每次bs值為分塊大小讀/ 寫完。*/
-group_reporting /*定義測試結果顯示模式,
group_reporting 表示彙總每個程序的統計資訊,而非以不同 job彙總展示資訊。*/
-thread /*使用pthread_create建立線程,另一種是fork建立程序。
程序的開銷比線程要大,一般都采用thread測試。*/
-name=job1 /*定義測試任務名稱。*/
–output TestResult.log /*日志輸出到TestResult.log。*/
-lockmem=1g /*隻使用1g記憶體進行測試。 */
-zero_buffers /*用0初始化系統buffer。*/
-nrfiles=8 /*每個程序生成檔案的數量。*/
-bs=4k /*單次io的塊檔案大小為4k*/
-numjobs=10 /*本次測試的線程數是10*/
-size=5G /*每個線程讀寫的資料量是5GB*/
常用指令
- 順序讀
fio -filename=/dev/sda -direct=1 -iodepth 1 -thread -rw=read
-ioengine=psync -bs=16k -size=200G -numjobs=30 -runtime=1000
-group_reporting -name=test001
- 順序寫
fio -filename=/dev/sda -direct=1 -iodepth 1 -thread -rw=write
-ioengine=psync -bs=16k -size=200G -numjobs=30 -runtime=1000
-group_reporting -name=test001
- 随機讀
fio -filename=/dev/sda -direct=1 -iodepth 1 -thread -rw=randread
-ioengine=psync -bs=16k -size=200G -numjobs=30 -runtime=1000
-group_reporting -name=test001
- 随機寫
fio -filename=/dev/sda -direct=1 -iodepth 1 -thread -rw=randwrite
-ioengine=psync -bs=16k -size=200G -numjobs=30 -runtime=1000
-group_reporting -name=test001
- 随機混合讀寫
fio -filename=/dev/sda -direct=1 -iodepth 1 -thread -rw=randrw -rwmixread=70
-ioengine=psync -bs=16k -size=200G -numjobs=30 -runtime=100
-group_reporting -name=mytest -ioscheduler=noop
- 磁盤讀寫常用測試點
1. Read=100% Ramdon=100% rw=randread (100%随機讀)
2. Read=100% Sequence=100% rw=read (100%順序讀)
3. Write=100% Sequence=100% rw=write (100%順序寫)
4. Write=100% Ramdon=100% rw=randwrite (100%随機寫)
5. Read=70% Sequence=100% rw=rw, rwmixread=70, rwmixwrite=30(70%順序讀,30%順序寫)
6. Read=70% Ramdon=100% rw=randrw, rwmixread=70, rwmixwrite=30(70%随機讀,30%随機寫)
8C16G虛拟機測試
4k随機讀寫,70%讀+30%寫,30個并發, 檔案系統測試
fio -direct=1 -iodepth=1 -thread -rw=randrw -rwmixread=70 -ioengine=libaio
-bs=4k -size=4G -numjobs=30 -runtime=60 -group_reporting
-filename=/data/test001.txt -name=test001
虛拟機磁盤IOPS讀為677,寫為277,無怪乎系統性能不高了,磁盤制約了系統響應!
24C64G實體機測試
4k随機讀寫,70%讀+30%寫,30個并發, 檔案系統測試
fio -direct=1 -iodepth=1 -thread -rw=randrw -rwmixread=70 -ioengine=libaio
-bs=4k -size=4G -numjobs=30 -runtime=60 -group_reporting
-filename=/data/test001.txt -name=test001
實體機磁盤IOPS讀為1097,寫為473,性能高出虛拟機一大截!
實體機測試裸盤性能結果
輸出報告分析
下面是每個執行的資料方向的I/O統計資料資訊的代表值含義
- read/write: 讀/寫的IO操作(還有一個trim沒用過)
- salt: 送出延遲,這是送出I/O所花費的時間(min:最小值,max:最大值,avg:平均值,stdev:标準偏差)
- chat: 完成延遲,表示從送出到完成I/O部分的時間
- lat: 相應時間,表示從fio建立I/O單元到完成I/O操作的時間
- bw: 帶寬統計
- iops: IOPS統計
- lat(nsec/usec/msec): I/O完成延遲的分布。這是從I/O離開fio到它完成的時間。與上面單獨的讀/寫/修剪部分不同,這裡和其餘部分的資料适用于報告組的所有I/ o。10=0.01%意味着0.01%的I/O在250us以下完成。250=0.02%意味着0.02%的I/O需要10到250us才能完成。
- cpu: cpu使用率
- IO depths: I/O深度在作業生命周期中的分布
- IO submit: 在一個送出調用中送出了多少個I/O。每一個分錄表示該數額及其以下,直到上一分錄為止——例如,4=100%意味着我們每次送出0到4個I/O調用
- IO complete: 和上邊的submit一樣,不過這個是完成了多少個
- IO issued rwt: 發出的read/write/trim請求的數量,以及其中有多少請求被縮短或删除
- IO latency: 滿足指定延遲目标所需的I/O深度
下面是Run status group 0 (all jobs) 全部任務彙總資訊的代表值含義:
- bw: 總帶寬以及最小和最大帶寬
- io: 該組中所有線程執行的累計I/O
- run: 這組線程中最小和最長的運作時。
最後是Linux中特有的磁盤狀态統計資訊的代表值含義:
- ios: 所有組的I/ o個數
- merge: I/O排程器執行的總合并數
- ticks: 使磁盤繁忙的滴答數(僅供參考,原文是Number of ticks we kept the disk busy)
- in_queue: 在磁盤隊列中花費的總時間
- util: 磁盤使用率。值為100%意味着我們保留了磁盤,如果一直很忙,那麼50%的時間磁盤就會閑置一半的時間。