日本综合一区二区|亚洲中文天堂综合|日韩欧美自拍一区|男女精品天堂一区|欧美自拍第6页亚洲成人精品一区|亚洲黄色天堂一区二区成人|超碰91偷拍第一页|日韩av夜夜嗨中文字幕|久久蜜综合视频官网|精美人妻一区二区三区

RELATEED CONSULTING
相關(guān)咨詢
選擇下列產(chǎn)品馬上在線溝通
服務(wù)時(shí)間:8:30-17:00
你可能遇到了下面的問題
關(guān)閉右側(cè)工具欄

新聞中心

這里有您想知道的互聯(lián)網(wǎng)營銷解決方案
解決Linux進(jìn)程占用IO的問題 (linux 進(jìn)程占用了io)

在Linux系統(tǒng)中,進(jìn)程占用IO的問題是很常見的。當(dāng)進(jìn)程占用了過多的IO資源時(shí),會導(dǎo)致系統(tǒng)變慢,甚至崩潰。因此,是非常重要的。本文將介紹常見的解決方法。

專業(yè)成都網(wǎng)站建設(shè)公司,做排名好的好網(wǎng)站,排在同行前面,為您帶來客戶和效益!成都創(chuàng)新互聯(lián)公司為您提供成都網(wǎng)站建設(shè),五站合一網(wǎng)站設(shè)計(jì)制作,服務(wù)好的網(wǎng)站設(shè)計(jì)公司,成都網(wǎng)站制作、做網(wǎng)站負(fù)責(zé)任的成都網(wǎng)站制作公司!

1. 使用iostat分析IO情況

iostat是一個(gè)常用的IO性能分析工具,它可以分析IO吞吐量、IO延遲和IO負(fù)載等指標(biāo)。使用iostat可以幫助我們了解系統(tǒng)的IO使用情況,從而判斷是否存在進(jìn)程占用IO的問題。

使用iostat需要安裝sysstat包。在Ubuntu系統(tǒng)中,可以通過以下命令安裝:

“`

sudo apt-get update

sudo apt-get install sysstat

“`

安裝完成后,可以使用以下命令查看IO情況:

“`

iostat -x 1

“`

該命令會每隔1秒輸出一次IO情況??梢杂^察每個(gè)設(shè)備的平均IO響應(yīng)時(shí)間(awt)、IO利用率(util)等指標(biāo),判斷是否存在進(jìn)程占用IO的問題。

2. 使用lsof查找占用文件的進(jìn)程

lsof是一個(gè)常用的文件列表命令,可以列出系統(tǒng)中打開的文件和進(jìn)程信息。使用lsof可以查找哪個(gè)進(jìn)程占用了某個(gè)文件或目錄。

例如,以下命令可以查找占用/dev/sda1文件系統(tǒng)的進(jìn)程:

“`

sudo lsof /dev/sda1

“`

如果該命令返回結(jié)果,則說明存在占用/dev/sda1的進(jìn)程。通過查找占用文件的進(jìn)程,我們可以定位占用IO資源的進(jìn)程,從而采取相應(yīng)的措施。

3. 使用ionice限制進(jìn)程IO優(yōu)先級

ionice是一個(gè)用于限制進(jìn)程IO優(yōu)先級的工具。使用ionice可以調(diào)整進(jìn)程對IO資源的使用權(quán),從而避免某個(gè)進(jìn)程占用過多的IO資源導(dǎo)致系統(tǒng)變慢。

ionice有三個(gè)命令:-c、-n和-p。其中,-c指定調(diào)度策略,可以是idle、batch、best-effort或realtime;-n指定IO優(yōu)先級,可以是0到7的整數(shù);-p指定進(jìn)程ID。

例如,以下命令可以將進(jìn)程ID為1234的進(jìn)程的IO優(yōu)先級調(diào)整為3:

“`

sudo ionice -c3 -p1234

“`

通過調(diào)整進(jìn)程IO優(yōu)先級,我們可以控制進(jìn)程對IO資源的使用權(quán),從而避免占用過多的IO資源。

4. 使用cgroups限制進(jìn)程IO資源

cgroups是Linux內(nèi)核提供的一種資源限制機(jī)制,可以限制進(jìn)程的CPU、內(nèi)存、IO等資源使用。使用cgroups可以限制某個(gè)進(jìn)程的IO資源使用,避免進(jìn)程占用過多的IO資源導(dǎo)致系統(tǒng)變慢。

在Ubuntu系統(tǒng)中,可以通過以下命令安裝cgroups:

“`

sudo apt-get update

sudo apt-get install cgroup-tools

“`

安裝完成后,可以使用以下命令創(chuàng)建一個(gè)名為test的cgroup,并限制該cgroup中的進(jìn)程IO速率為50M/s:

“`

sudo cgcreate -g blkio:test

sudo cgset -r blkio.throttle.read_bps_device=/dev/sda1 50M test

“`

該命令會創(chuàng)建一個(gè)名為test的cgroup,并限制該cgroup中的進(jìn)程在/dev/sda1設(shè)備上的讀IO速率為50M/s。如果某個(gè)進(jìn)程被加入到test cgroup,則其IO速率將被限制。

通過使用cgroups,我們可以靈活地限制進(jìn)程的IO資源使用,從而避免進(jìn)程占用過多的IO資源導(dǎo)致系統(tǒng)變慢。

是非常重要的。本文介紹了常見的解決方法,包括使用iostat分析IO情況、使用lsof查找占用文件的進(jìn)程、使用ionice限制進(jìn)程IO優(yōu)先級和使用cgroups限制進(jìn)程IO資源。通過采取合適的措施,我們可以避免進(jìn)程占用過多的IO資源,保證系統(tǒng)的穩(wěn)定性和可靠性。

相關(guān)問題拓展閱讀:

  • linux查看磁盤io的幾種方法
  • 如何提高Linux下塊設(shè)備IO的整體性能

linux查看磁盤io的幾種方法

linux查看磁盤io的幾種方法

怎樣才能快速的定位到并發(fā)高是由于磁盤io開銷大呢?可以通過三種方式:

  之一種:用 top 命令 中的cpu 信息觀察

  Top可以看到的cpu信息有:

  Tasks: 29 total, 1 running, 28 sleeping, 0 stopped, 0 zombie

  Cpu(s): 0.3% us, 1.0% sy, 0.0% ni, 98.7% id, 0.0% wa, 0.0% hi, 0.0% si

  具體的解釋如下:

  Tasks: 29 total 進(jìn)程總數(shù)

  1 running 正在運(yùn)行的進(jìn)程數(shù)

  28 sleeping 睡眠的進(jìn)程數(shù)

  0 stopped 停止的進(jìn)程數(shù)

  0 zombie 僵尸進(jìn)程數(shù)

  Cpu(s):

  0.3% us 用戶空間占用CPU百分比

  1.0% sy 內(nèi)核空間占用CPU百分比

  0.0% ni 用戶進(jìn)程空間內(nèi)改變過優(yōu)先級的進(jìn)程占用CPU百分比

  98.7% id 空閑CPU百分比

  0.0% wa 等待輸入輸出的CPU時(shí)間百分比

  0.0% hi

  0.0% si

  0.0% wa 的百分比可以大致的體現(xiàn)出當(dāng)前的磁盤io請求是否頻繁。如果 wa的數(shù)量比較大,說明等待輸入輸出的的io比較多。

  第二種:用vmstat

  vmstat 命令報(bào)告關(guān)于線程、

虛擬內(nèi)存

、磁盤、陷阱和 CPU 活動的統(tǒng)計(jì)信息。由 vmstat 命令生成的報(bào)告可以用于平衡系統(tǒng)負(fù)載活動。系統(tǒng)范圍內(nèi)的這些統(tǒng)計(jì)信息(所有的處理器中)都計(jì)算出以百分比表示的

平均值

,或者計(jì)算其總和。

  輸入命令:

  vmstat 2 5

  如果發(fā)現(xiàn)等待的進(jìn)程和處在非中斷睡眠狀態(tài)的進(jìn)程數(shù)非常多,并且發(fā)送到塊設(shè)備的塊數(shù)和從塊設(shè)備接收到的塊數(shù)非常大,那就說明磁盤隱緩io比較多。

  vmstat參數(shù)解釋:

  Procs

  r: 等待運(yùn)行的進(jìn)程數(shù) b: 處在非中斷睡眠狀態(tài)的進(jìn)程數(shù) w: 被交換出去的可運(yùn)行的進(jìn)程慧信數(shù)。此數(shù)由 linux 計(jì)算得出,但 linux 并不耗盡交換空間

  Memory

  swpd: 虛擬內(nèi)存使用情況,單位:KB

  free: 空閑的內(nèi)存,單位KB

  buff: 被用來做為緩存的內(nèi)存數(shù),單位:KB

  Swap

  si: 從磁盤交換到內(nèi)存的交換頁數(shù)量,單位:KB/秒

  so: 從內(nèi)存交換到磁盤的灶碧模交換頁數(shù)量,單位:KB/秒

  IO

  bi: 發(fā)送到塊設(shè)備的塊數(shù),單位:塊/秒

  bo: 從塊設(shè)備接收到的塊數(shù),單位:塊/秒

  System

  in: 每秒的中斷數(shù),包括時(shí)鐘中斷

  cs: 每秒的環(huán)境(上下文)切換次數(shù)

  CPU

  按 CPU 的總使用百分比來顯示

  us: CPU 使用時(shí)間

  sy: CPU 系統(tǒng)使用時(shí)間

  id: 閑置時(shí)間

  準(zhǔn)測

  更多vmstat使用信息

  第二種:用iostat

  安裝:

  Iostat 是 sysstat 工具集的一個(gè)工具,需要安裝。

  Centos的安裝方式是:

  yum install sysstat

  Ubuntu的安裝方式是:

  aptitude install sysstat

  使用:

  iostat -dx 顯示磁盤擴(kuò)展信息

  root@fileapp:~# iostat -dx

  r/s 和 w/s 分別是每秒的讀操作和寫操作,而rKB/s 和wKB/s 列以每秒千字節(jié)為單位顯示了讀和寫的數(shù)據(jù)量

  如果這兩對數(shù)據(jù)值都很高的話說明磁盤io操作是很頻繁。

+++++++++++++++++++++++++++++++++++++

linux wa%過高,iostat查看io狀況

1, 安裝  iostat

  yum install sysstat

之后就可以使用 iostat 命令了,

2,入門使用

  iostat -d -k 2

參數(shù) -d 表示,顯示設(shè)備(磁盤)使用狀態(tài);-k某些使用block為單位的列強(qiáng)制使用Kilobytes為單位;2表示,數(shù)據(jù)顯示每隔2秒刷新一次。

tps:該設(shè)備每秒的傳輸次數(shù)(Indicate the number of transfers per second that were issued to the device.)?!币淮蝹鬏敗币馑际恰币淮蜪/O請求”。多個(gè)邏輯請求可能會被合并為”一次I/O請求”?!币淮蝹鬏敗闭埱蟮拇笮∈俏粗?。kB_read/s:每秒從設(shè)備(drive expressed)讀取的數(shù)據(jù)量;

kB_wrtn/s:每秒向設(shè)備(drive expressed)寫入的數(shù)據(jù)量;

kB_read:讀取的總數(shù)據(jù)量;kB_wrtn:寫入的總數(shù)量數(shù)據(jù)量;這些單位都為Kilobytes。

指定監(jiān)控的設(shè)備名稱為sda,該命令的輸出結(jié)果和上面命令完全相同。

iostat -d sda 2

默認(rèn)監(jiān)控所有的硬盤設(shè)備,現(xiàn)在指定只監(jiān)控sda。

3, -x 參數(shù)

iostat還有一個(gè)比較常用的選項(xiàng) -x ,該選項(xiàng)將用于顯示和io相關(guān)的擴(kuò)展數(shù)據(jù)。

iostat -d -x -k 1 10

輸出信息的含義

4, 常見用法

iostat -d -k#查看TPS和

吞吐量

信息(磁盤讀寫速度單位為KB)

iostat -d -m#查看TPS和吞吐量信息(磁盤讀寫速度單位為MB)

iostat -d -x -k#查看設(shè)備使用率(%util)、響應(yīng)時(shí)間(await) iostat -c 1 10 #查看cpu狀態(tài)

5, 實(shí)例分析

iostat -d -k 1 | grep vda

Device:tps    kB_read/s    kB_wrtn/s    kB_read    kB_wrtn

sda60…

sda99…

sda83…

sda18…

sda46…

sda27…

上面看到,磁盤每秒傳輸次數(shù)平均約400;每秒磁盤讀取約5MB,寫入約1MB。

iostat -d -x -k 1

Device:    rrqm/s wrqm/s  r/s  w/s  rsec/s  wsec/s    rkB/s    wkB/s avgrq-sz avgqu-sz  await  svctm  %util

sda.56  28.31  7.84 31……..80  2.61  10.29

sda.98  24.75 419.80  6……..70  2.00  85.25

sda.06  41.84 444.90 54……..21  1.85  92.24

可以看到磁盤的平均響應(yīng)時(shí)間80。磁盤響應(yīng)正常,但是已經(jīng)很繁忙了。

可以看到磁盤的平均響應(yīng)時(shí)間90。磁盤響應(yīng)正常,但是已經(jīng)很繁忙了。

await:  每一個(gè)IO請求的處理的平均時(shí)間(單位是微秒毫秒)。這里可以理解為IO的響應(yīng)時(shí)間,一般地系統(tǒng)IO響應(yīng)時(shí)間應(yīng)該低于5ms,如果大于10ms就比較大了

svctm    表示平均每次設(shè)備I/O操作的服務(wù)時(shí)間(以毫秒為單位)。如果svctm的值與await很接近,表示幾乎沒有I/O等待,磁盤性能很好,

如果await的值遠(yuǎn)高于svctm的值,則表示I/O隊(duì)列等待太長,  系統(tǒng)上運(yùn)行的

應(yīng)用程序

將變慢。

%util: 在統(tǒng)計(jì)時(shí)間內(nèi)所有處理IO時(shí)間,除以總共統(tǒng)計(jì)時(shí)間

所以該參數(shù)暗示了設(shè)備的繁忙程度

。一般地,如果該參數(shù)是100%表示設(shè)備已經(jīng)接近滿負(fù)荷運(yùn)行了(當(dāng)然如果是多磁盤,即使%util是100%,因?yàn)榇疟P的并發(fā)能力,所以磁盤使用未必就到了瓶頸)。

也可以使用下面的命令,同時(shí)顯示cpu和磁盤的使用情況

等待時(shí)間超過5ms, 磁盤io有問題

如何提高Linux下塊設(shè)備IO的整體性能

前言:本文主要講解Linux IO調(diào)度層的三種模式:cfp、deadline和noop,并給出各自的優(yōu)化和適用場景建議掘歷。

IO調(diào)度發(fā)生在Linux內(nèi)核的IO調(diào)度層。租檔這個(gè)層次是針對Linux的整體IO層次體系來說的。從read()或者write()系統(tǒng)調(diào)用的角度來說,Linux整體IO體系可以分為七層,它們分別是:

VFS層: 虛擬文件系統(tǒng)層。由于內(nèi)核要跟多種文件系統(tǒng)打交道,而每一種文件系統(tǒng)所實(shí)現(xiàn)的數(shù)據(jù)結(jié)構(gòu)和相關(guān)方法都可能不盡相同,所以,內(nèi)核抽象了這一層,專門用來適配各種文件系統(tǒng),并對外提供統(tǒng)一操作接口。

文件系統(tǒng)層: 不同的文件系統(tǒng)實(shí)現(xiàn)自己的操作過程,提供自己特有的特征,具體不多說了,大家愿意的話自己去看代碼即可。

頁緩存層: 負(fù)責(zé)真對page的緩存。

通用塊層: 由于絕大多數(shù)情況的io操作是跟塊設(shè)備打交道,所以Linux在此提供了一個(gè)類似vfs層的塊設(shè)備操作抽象層。下層對接各種不同屬性的塊設(shè)備,對上提供統(tǒng)一的Block IO請求標(biāo)準(zhǔn)。

IO調(diào)度層 :因?yàn)榻^大多數(shù)的塊設(shè)備都是類似磁盤這樣的設(shè)備,所以有必要根據(jù)這類設(shè)備的特點(diǎn)以及應(yīng)用的不同特點(diǎn)來設(shè)置一些不同的調(diào)度算法和隊(duì)列。以便在不同的應(yīng)用環(huán)境下有針對性的提高磁盤的讀寫效率,這里就是大名鼎鼎的Linux電梯所起作用的地方。針對機(jī)械硬盤的各種調(diào)度方法就是在這實(shí)現(xiàn)的。

塊設(shè)備驅(qū)動層: 驅(qū)動層對外提供相對比較高級的設(shè)備操作接口,往往是C語言的,而下層對接設(shè)備本身的操作方法和規(guī)范。

塊設(shè)備層: 這層就是具體的物理設(shè)備了,定義了各種真對設(shè)備操作方法和規(guī)范。

有一個(gè)已經(jīng)整理好的,非常經(jīng)典,一圖勝千言:

我們今天要研究的內(nèi)容主要在IO調(diào)度這一層。

它要解決的核心問題是,如何提高塊設(shè)備IO的整體性能?這一層也主要是針對機(jī)械硬盤結(jié)構(gòu)而設(shè)計(jì)的。

眾所周知,機(jī)械硬盤的存儲介質(zhì)是磁盤,磁頭在盤片上移動進(jìn)行磁道尋址,行為類似播放一張唱片。

這種結(jié)構(gòu)的特點(diǎn)是,順序訪問時(shí)吞吐量較高,但是如果一旦對盤片有隨機(jī)訪問,那么大量的時(shí)間都會浪費(fèi)在磁頭的移動上,這時(shí)候就會導(dǎo)致每次IO的響應(yīng)時(shí)間變長,極大的降低IO的響應(yīng)速度。

磁頭在盤片上尋道的操作,類似電梯調(diào)度,實(shí)際上在最開始的時(shí)期,Linux把這個(gè)算法命名為Linux電梯算法,即:

如果在尋道的過程中,能把順序路過的相關(guān)磁道的數(shù)據(jù)請求都“順便”處理掉,那么就可以在比較小影響響應(yīng)速度的前提下,提高整體IO的吞吐量。

這就是我們?yōu)槭裁匆O(shè)計(jì)IO調(diào)度算法的原因。

目前在內(nèi)核中默認(rèn)開啟了三種算法/模式:noop,cfq和deadline。嚴(yán)格算應(yīng)該是兩種:

因?yàn)橹环N叫做noop,就是空操作調(diào)度算法,也就是沒有任何調(diào)度操作,并不對io請求進(jìn)行排序,僅僅做適當(dāng)?shù)膇o合并的一個(gè)fifo隊(duì)列。

目前內(nèi)核中默認(rèn)的調(diào)度算法應(yīng)該是cfq,叫做完全公平隊(duì)列調(diào)度。這個(gè)調(diào)度算法人如其名,它試圖給所有進(jìn)程提供一個(gè)完全公平的IO操作環(huán)境。

注:請大家一定記住這個(gè)詞語,cfq,完全公平隊(duì)列調(diào)度,不然下文就沒法看了。

cfq為每個(gè)進(jìn)程創(chuàng)建一個(gè)同步IO調(diào)度隊(duì)列,并默認(rèn)以時(shí)間片和請求數(shù)限定的方式分配IO資源,以此保證每個(gè)進(jìn)程的IO資源占用是公平的,cfq還實(shí)現(xiàn)了針對進(jìn)程級別的優(yōu)先級調(diào)度,這個(gè)我們后面會詳細(xì)解釋。

查看和修改IO調(diào)度算法的方法是:

cfq是通用服務(wù)器比較好的IO調(diào)度算法選擇,對桌面用戶也是比較好的選擇。

但是對于很多IO壓力較大的場景就并不是判型搜很適應(yīng),尤其是IO壓力集中在某些進(jìn)程上的場景。

因?yàn)檫@種場景我們需要更多的滿足某個(gè)或者某幾個(gè)進(jìn)程的IO響應(yīng)速度,而不是讓所有的進(jìn)程公平的使用IO,比如數(shù)據(jù)庫應(yīng)用。

deadline調(diào)度(最終期限調(diào)度)就是更適合上述場景的解決方案。deadline實(shí)現(xiàn)了四個(gè)隊(duì)列:

其中兩個(gè)分別處理正常read和write,按扇區(qū)號排序,進(jìn)行正常io的合并處理以提高吞吐量。因?yàn)镮O請求可能會集中在某些磁盤位置,這樣會導(dǎo)致新來的請求一直被合并,可能會有其他磁盤位置的io請求被餓死。

另外兩個(gè)處理超時(shí)read和write的隊(duì)列,按請求創(chuàng)建時(shí)間排序,如果有超時(shí)的請求出現(xiàn),就放進(jìn)這兩個(gè)隊(duì)列,調(diào)度算法保證超時(shí)(達(dá)到最終期限時(shí)間)的隊(duì)列中的請求會優(yōu)先被處理,防止請求被餓死。

不久前,內(nèi)核還是默認(rèn)標(biāo)配四種算法,還有一種叫做as的算法(Anticipatory scheduler),預(yù)測調(diào)度算法。一個(gè)高大上的名字,搞得我一度認(rèn)為Linux內(nèi)核都會算命了。

結(jié)果發(fā)現(xiàn),無非是在基于deadline算法做io調(diào)度的之前等一小會時(shí)間,如果這段時(shí)間內(nèi)有可以合并的io請求到來,就可以合并處理,提高deadline調(diào)度的在順序讀寫情況下的數(shù)據(jù)吞吐量。

其實(shí)這根本不是啥預(yù)測,我覺得不如叫撞大運(yùn)調(diào)度算法,當(dāng)然這種策略在某些特定場景差效果不錯(cuò)。

但是在大多數(shù)場景下,這個(gè)調(diào)度不僅沒有提高吞吐量,還降低了響應(yīng)速度,所以內(nèi)核干脆把它從默認(rèn)配置里刪除了。畢竟Linux的宗旨是實(shí)用,而我們也就不再這個(gè)調(diào)度算法上多費(fèi)口舌了。

1、cfq:完全公平隊(duì)列調(diào)度

cfq是內(nèi)核默認(rèn)選擇的IO調(diào)度隊(duì)列,它在桌面應(yīng)用場景以及大多數(shù)常見應(yīng)用場景下都是很好的選擇。

如何實(shí)現(xiàn)一個(gè)所謂的完全公平隊(duì)列(Completely Fair Queueing)?

首先我們要理解所謂的公平是對誰的公平?從操作系統(tǒng)的角度來說,產(chǎn)生操作行為的主體都是進(jìn)程,所以這里的公平是針對每個(gè)進(jìn)程而言的,我們要試圖讓進(jìn)程可以公平的占用IO資源。

那么如何讓進(jìn)程公平的占用IO資源?我們需要先理解什么是IO資源。當(dāng)我們衡量一個(gè)IO資源的時(shí)候,一般喜歡用的是兩個(gè)單位,一個(gè)是數(shù)據(jù)讀寫的帶寬,另一個(gè)是數(shù)據(jù)讀寫的IOPS。

帶寬就是以時(shí)間為單位的讀寫數(shù)據(jù)量,比如,100Mbyte/s。而IOPS是以時(shí)間為單位的讀寫次數(shù)。在不同的讀寫情境下,這兩個(gè)單位的表現(xiàn)可能不一樣,但是可以確定的是,兩個(gè)單位的任何一個(gè)達(dá)到了性能上限,都會成為IO的瓶頸。

從機(jī)械硬盤的結(jié)構(gòu)考慮,如果讀寫是順序讀寫,那么IO的表現(xiàn)是可以通過比較少的IOPS達(dá)到較大的帶寬,因?yàn)榭梢院喜⒑芏郔O,也可以通過預(yù)讀等方式加速數(shù)據(jù)讀取效率。

當(dāng)IO的表現(xiàn)是偏向于隨機(jī)讀寫的時(shí)候,那么IOPS就會變得更大,IO的請求的合并可能性下降,當(dāng)每次io請求數(shù)據(jù)越少的時(shí)候,帶寬表現(xiàn)就會越低。

從這里我們可以理解,針對進(jìn)程的IO資源的主要表現(xiàn)形式有兩個(gè): 進(jìn)程在單位時(shí)間內(nèi)提交的IO請求個(gè)數(shù)和進(jìn)程占用IO的帶寬。

其實(shí)無論哪個(gè),都是跟進(jìn)程分配的IO處理時(shí)間長度緊密相關(guān)的。

有時(shí)業(yè)務(wù)可以在較少IOPS的情況下占用較大帶寬,另外一些則可能在較大IOPS的情況下占用較少帶寬,所以對進(jìn)程占用IO的時(shí)間進(jìn)行調(diào)度才是相對最公平的。

即,我不管你是IOPS高還是帶寬占用高,到了時(shí)間咱就換下一個(gè)進(jìn)程處理,你愛咋樣咋樣。

所以,cfq就是試圖給所有進(jìn)程分配等同的塊設(shè)備使用的時(shí)間片,進(jìn)程在時(shí)間片內(nèi),可以將產(chǎn)生的IO請求提交給塊設(shè)備進(jìn)行處理,時(shí)間片結(jié)束,進(jìn)程的請求將排進(jìn)它自己的隊(duì)列,等待下次調(diào)度的時(shí)候進(jìn)行處理。這就是cfq的基本原理。

當(dāng)然,現(xiàn)實(shí)生活中不可能有真正的“公平”,常見的應(yīng)用場景下,我們很肯能需要人為的對進(jìn)程的IO占用進(jìn)行人為指定優(yōu)先級,這就像對進(jìn)程的CPU占用設(shè)置優(yōu)先級的概念一樣。

所以,除了針對時(shí)間片進(jìn)行公平隊(duì)列調(diào)度外,cfq還提供了優(yōu)先級支持。每個(gè)進(jìn)程都可以設(shè)置一個(gè)IO優(yōu)先級,cfq會根據(jù)這個(gè)優(yōu)先級的設(shè)置情況作為調(diào)度時(shí)的重要參考因素。

優(yōu)先級首先分成三大類:RT、BE、IDLE,它們分別是實(shí)時(shí)(Real Time)、更佳效果(Best Try)和閑置(Idle)三個(gè)類別,對每個(gè)類別的IO,cfq都使用不同的策略進(jìn)行處理。另外,RT和BE類別中,分別又再劃分了8個(gè)子優(yōu)先級實(shí)現(xiàn)更細(xì)節(jié)的QOS需求,而IDLE只有一個(gè)子優(yōu)先級。

另外,我們都知道內(nèi)核默認(rèn)對存儲的讀寫都是經(jīng)過緩存(buffer/cache)的,在這種情況下,cfq是無法區(qū)分當(dāng)前處理的請求是來自哪一個(gè)進(jìn)程的。

只有在進(jìn)程使用同步方式(sync read或者sync wirte)或者直接IO(Direct IO)方式進(jìn)行讀寫的時(shí)候,cfq才能區(qū)分出IO請求來自哪個(gè)進(jìn)程。

所以,除了針對每個(gè)進(jìn)程實(shí)現(xiàn)的IO隊(duì)列以外,還實(shí)現(xiàn)了一個(gè)公共的隊(duì)列用來處理異步請求。

當(dāng)前內(nèi)核已經(jīng)實(shí)現(xiàn)了針對IO資源的cgroup資源隔離,所以在以上體系的基礎(chǔ)上,cfq也實(shí)現(xiàn)了針對cgroup的調(diào)度支持。

總的來說,cfq用了一系列的數(shù)據(jù)結(jié)構(gòu)實(shí)現(xiàn)了以上所有復(fù)雜功能的支持,大家可以通過源代碼看到其相關(guān)實(shí)現(xiàn),文件在源代碼目錄下的block/cfq-iosched.c。

1.1 cfq設(shè)計(jì)原理

在此,我們對整體數(shù)據(jù)結(jié)構(gòu)做一個(gè)簡要描述:首先,cfq通過一個(gè)叫做cfq_data的數(shù)據(jù)結(jié)構(gòu)維護(hù)了整個(gè)調(diào)度器流程。在一個(gè)支持了cgroup功能的cfq中,全部進(jìn)程被分成了若干個(gè)contral group進(jìn)行管理。

每個(gè)cgroup在cfq中都有一個(gè)cfq_group的結(jié)構(gòu)進(jìn)行描述,所有的cgroup都被作為一個(gè)調(diào)度對象放進(jìn)一個(gè)紅黑樹中,并以vdisktime為key進(jìn)行排序。

vdisktime這個(gè)時(shí)間紀(jì)錄的是當(dāng)前cgroup所占用的io時(shí)間,每次對cgroup進(jìn)行調(diào)度時(shí),總是通過紅黑樹選擇當(dāng)前vdisktime時(shí)間最少的cgroup進(jìn)行處理,以保證所有cgroups之間的IO資源占用“公平”。

當(dāng)然我們知道,cgroup是可以對blkio進(jìn)行資源比例分配的,其作用原理就是,分配比例大的cgroup占用vdisktime時(shí)間增長較慢,分配比例小的vdisktime時(shí)間增長較快,快慢與分配比例成正比。

這樣就做到了不同的cgroup分配的IO比例不一樣,并且在cfq的角度看來依然是“公平“的。

選擇好了需要處理的cgroup(cfq_group)之后,調(diào)度器需要決策選擇下一步的service_tree。

service_tree這個(gè)數(shù)據(jù)結(jié)構(gòu)對應(yīng)的都是一系列的紅黑樹,主要目的是用來實(shí)現(xiàn)請求優(yōu)先級分類的,就是RT、BE、IDLE的分類。每一個(gè)cfq_group都維護(hù)了7個(gè)service_trees,其定義如下:

其中service_tree_idle就是用來給IDLE類型的請求進(jìn)行排隊(duì)用的紅黑樹。

而上面二維數(shù)組,首先之一個(gè)維度針對RT和BE分別各實(shí)現(xiàn)了一個(gè)數(shù)組,每一個(gè)數(shù)組中都維護(hù)了三個(gè)紅黑樹,分別對應(yīng)三種不同子類型的請求,分別是:SYNC、SYNC_NOIDLE以及ASYNC。

我們可以認(rèn)為SYNC相當(dāng)于SYNC_IDLE并與SYNC_NOIDLE對應(yīng)。idling是cfq在設(shè)計(jì)上為了盡量合并連續(xù)的IO請求以達(dá)到提高吞吐量的目的而加入的機(jī)制,我們可以理解為是一種“空轉(zhuǎn)”等待機(jī)制。

空轉(zhuǎn)是指,當(dāng)一個(gè)隊(duì)列處理一個(gè)請求結(jié)束后,會在發(fā)生調(diào)度之前空等一小會時(shí)間,如果下一個(gè)請求到來,則可以減少磁頭尋址,繼續(xù)處理順序的IO請求。

為了實(shí)現(xiàn)這個(gè)功能,cfq在service_tree這層數(shù)據(jù)結(jié)構(gòu)這實(shí)現(xiàn)了SYNC隊(duì)列,如果請求是同步順序請求,就入隊(duì)這個(gè)service tree,如果請求是同步隨機(jī)請求,則入隊(duì)SYNC_NOIDLE隊(duì)列,以判斷下一個(gè)請求是否是順序請求。

所有的異步寫操作請求將入隊(duì)ASYNC的service tree,并且針對這個(gè)隊(duì)列沒有空轉(zhuǎn)等待機(jī)制。

此外,cfq還對SSD這樣的硬盤有特殊調(diào)整,當(dāng)cfq發(fā)現(xiàn)存儲設(shè)備是一個(gè)ssd硬盤這樣的隊(duì)列深度更大的設(shè)備時(shí),所有針對單獨(dú)隊(duì)列的空轉(zhuǎn)都將不生效,所有的IO請求都將入隊(duì)SYNC_NOIDLE這個(gè)service tree。

每一個(gè)service tree都對應(yīng)了若干個(gè)cfq_queue隊(duì)列,每個(gè)cfq_queue隊(duì)列對應(yīng)一個(gè)進(jìn)程,這個(gè)我們后續(xù)再詳細(xì)說明。

cfq_group還維護(hù)了一個(gè)在cgroup內(nèi)部所有進(jìn)程公用的異步IO請求隊(duì)列,其結(jié)構(gòu)如下:

異步請求也分成了RT、BE、IDLE這三類進(jìn)行處理,每一類對應(yīng)一個(gè)cfq_queue進(jìn)行排隊(duì)。

BE和RT也實(shí)現(xiàn)了優(yōu)先級的支持,每一個(gè)類型有IOPRIO_BE_NR這么多個(gè)優(yōu)先級,這個(gè)值定義為8,數(shù)組下標(biāo)為0-7。

我們目前分析的內(nèi)核代碼版本為Linux 4.4,可以看出,從cfq的角度來說,已經(jīng)可以實(shí)現(xiàn)異步IO的cgroup支持了,我們需要定義一下這里所謂異步IO的含義,它僅僅表示從內(nèi)存的buffer/cache中的數(shù)據(jù)同步到硬盤的IO請求,而不是aio(man 7 aio)或者linux的native異步io以及l(fā)ibaio機(jī)制,實(shí)際上這些所謂的“異步”IO機(jī)制,在內(nèi)核中都是同步實(shí)現(xiàn)的(本質(zhì)上馮諾伊曼計(jì)算機(jī)沒有真正的“異步”機(jī)制)。

我們在上面已經(jīng)說明過,由于進(jìn)程正常情況下都是將數(shù)據(jù)先寫入buffer/cache,所以這種異步IO都是統(tǒng)一由cfq_group中的async請求隊(duì)列處理的。

那么為什么在上面的service_tree中還要實(shí)現(xiàn)和一個(gè)ASYNC的類型呢?

這當(dāng)然是為了支持區(qū)分進(jìn)程的異步IO并使之可以“完全公平”做準(zhǔn)備嘍。

實(shí)際上在最新的cgroup v2的blkio體系中,內(nèi)核已經(jīng)支持了針對buffer IO的cgroup限速支持,而以上這些可能容易混淆的一堆類型,都是在新的體系下需要用到的類型標(biāo)記。

新體系的復(fù)雜度更高了,功能也更加強(qiáng)大,但是大家先不要著急,正式的cgroup v2體系,在Linux 4.5發(fā)布的時(shí)候會正式跟大家見面。

我們繼續(xù)選擇service_tree的過程,三種優(yōu)先級類型的service_tree的選擇就是根據(jù)類型的優(yōu)先級來做選擇的,RT優(yōu)先級更高,BE其次,IDLE更低。就是說,RT里有,就會一直處理RT,RT沒了再處理BE。

每個(gè)service_tree對應(yīng)一個(gè)元素為cfq_queue排隊(duì)的紅黑樹,而每個(gè)cfq_queue就是內(nèi)核為進(jìn)程(線程)創(chuàng)建的請求隊(duì)列。

每一個(gè)cfq_queue都會維護(hù)一個(gè)rb_key的變量,這個(gè)變量實(shí)際上就是這個(gè)隊(duì)列的IO服務(wù)時(shí)間(service time)。

這里還是通過紅黑樹找到service time時(shí)間最短的那個(gè)cfq_queue進(jìn)行服務(wù),以保證“完全公平”。

選擇好了cfq_queue之后,就要開始處理這個(gè)隊(duì)列里的IO請求了。這里的調(diào)度方式基本跟deadline類似。

cfq_queue會對進(jìn)入隊(duì)列的每一個(gè)請求進(jìn)行兩次入隊(duì),一個(gè)放進(jìn)fifo中,另一個(gè)放進(jìn)按訪問扇區(qū)順序作為key的紅黑樹中。

默認(rèn)從紅黑樹中取請求進(jìn)行處理,當(dāng)請求的延時(shí)時(shí)間達(dá)到deadline時(shí),就從紅黑樹中取等待時(shí)間最長的進(jìn)行處理,以保證請求不被餓死。

這就是整個(gè)cfq的調(diào)度流程,當(dāng)然其中還有很多細(xì)枝末節(jié)沒有交代,比如合并處理以及順序處理等等。

1.2 cfq的參數(shù)調(diào)整

理解整個(gè)調(diào)度流程有助于我們決策如何調(diào)整cfq的相關(guān)參數(shù)。所有cfq的可調(diào)參數(shù)都可以在/sys/class/block/sda/queue/iosched/目錄下找到,當(dāng)然,在你的系統(tǒng)上,請將sda替換為相應(yīng)的磁盤名稱。我們來看一下都有什么:

這些參數(shù)部分是跟機(jī)械硬盤磁頭尋道方式有關(guān)的,如果其說明你看不懂,請先補(bǔ)充相關(guān)知識:

back_seek_max:磁頭可以向后尋址的更大范圍,默認(rèn)值為16M。

back_seek_penalty:向后尋址的懲罰系數(shù)。這個(gè)值是跟向前尋址進(jìn)行比較的。

以上兩個(gè)是為了防止磁頭尋道發(fā)生抖動而導(dǎo)致尋址過慢而設(shè)置的?;舅悸肥沁@樣,一個(gè)io請求到來的時(shí)候,cfq會根據(jù)其尋址位置預(yù)估一下其磁頭尋道成本。

設(shè)置一個(gè)更大值back_seek_max,對于請求所訪問的扇區(qū)號在磁頭后方的請求,只要尋址范圍沒有超過這個(gè)值,cfq會像向前尋址的請求一樣處理它。

再設(shè)置一個(gè)評估成本的系數(shù)back_seek_penalty,相對于磁頭向前尋址,向后尋址的距離為1/2(1/back_seek_penalty)時(shí),cfq認(rèn)為這兩個(gè)請求尋址的代價(jià)是相同。

這兩個(gè)參數(shù)實(shí)際上是cfq判斷請求合并處理的條件限制,凡事復(fù)合這個(gè)條件的請求,都會盡量在本次請求處理的時(shí)候一起合并處理。

fifo_expire_async:設(shè)置異步請求的超時(shí)時(shí)間。

同步請求和異步請求是區(qū)分不同隊(duì)列處理的,cfq在調(diào)度的時(shí)候一般情況都會優(yōu)先處理同步請求,之后再處理異步請求,除非異步請求符合上述合并處理的條件限制范圍內(nèi)。

當(dāng)本進(jìn)程的隊(duì)列被調(diào)度時(shí),cfq會優(yōu)先檢查是否有異步請求超時(shí),就是超過fifo_expire_async參數(shù)的限制。如果有,則優(yōu)先發(fā)送一個(gè)超時(shí)的請求,其余請求仍然按照優(yōu)先級以及扇區(qū)編號大小來處理。

fifo_expire_sync:這個(gè)參數(shù)跟上面的類似,區(qū)別是用來設(shè)置同步請求的超時(shí)時(shí)間。

slice_idle:參數(shù)設(shè)置了一個(gè)等待時(shí)間。這讓cfq在切換cfq_queue或service tree的時(shí)候等待一段時(shí)間,目的是提高機(jī)械硬盤的吞吐量。

一般情況下,來自同一個(gè)cfq_queue或者service tree的IO請求的尋址局部性更好,所以這樣可以減少磁盤的尋址次數(shù)。這個(gè)值在機(jī)械硬盤上默認(rèn)為非零。

當(dāng)然在固態(tài)硬盤或者硬RAID設(shè)備上設(shè)置這個(gè)值為非零會降低存儲的效率,因?yàn)楣虘B(tài)硬盤沒有磁頭尋址這個(gè)概念,所以在這樣的設(shè)備上應(yīng)該設(shè)置為0,關(guān)閉此功能。

group_idle:這個(gè)參數(shù)也跟上一個(gè)參數(shù)類似,區(qū)別是當(dāng)cfq要切換cfq_group的時(shí)候會等待一段時(shí)間。

在cgroup的場景下,如果我們沿用slice_idle的方式,那么空轉(zhuǎn)等待可能會在cgroup組內(nèi)每個(gè)進(jìn)程的cfq_queue切換時(shí)發(fā)生。

這樣會如果這個(gè)進(jìn)程一直有請求要處理的話,那么直到這個(gè)cgroup的配額被耗盡,同組中的其它進(jìn)程也可能無法被調(diào)度到。這樣會導(dǎo)致同組中的其它進(jìn)程餓死而產(chǎn)生IO性能瓶頸。

在這種情況下,我們可以將slice_idle = 0而group_idle = 8。這樣空轉(zhuǎn)等待就是以cgroup為單位進(jìn)行的,而不是以cfq_queue的進(jìn)程為單位進(jìn)行,以防止上述問題產(chǎn)生。

low_latency:這個(gè)是用來開啟或關(guān)閉cfq的低延時(shí)(low latency)模式的開關(guān)。

當(dāng)這個(gè)開關(guān)打開時(shí),cfq將會根據(jù)target_latency的參數(shù)設(shè)置來對每一個(gè)進(jìn)程的分片時(shí)間(slice time)進(jìn)行重新計(jì)算。

這將有利于對吞吐量的公平(默認(rèn)是對時(shí)間片分配的公平)。

關(guān)閉這個(gè)參數(shù)(設(shè)置為0)將忽略target_latency的值。這將使系統(tǒng)中的進(jìn)程完全按照時(shí)間片方式進(jìn)行IO資源分配。這個(gè)開關(guān)默認(rèn)是打開的。

我們已經(jīng)知道cfq設(shè)計(jì)上有“空轉(zhuǎn)”(idling)這個(gè)概念,目的是為了可以讓連續(xù)的讀寫操作盡可能多的合并處理,減少磁頭的尋址操作以便增大吞吐量。

如果有進(jìn)程總是很快的進(jìn)行順序讀寫,那么它將因?yàn)閏fq的空轉(zhuǎn)等待命中率很高而導(dǎo)致其它需要處理IO的進(jìn)程響應(yīng)速度下降,如果另一個(gè)需要調(diào)度的進(jìn)程不會發(fā)出大量順序IO行為的話,系統(tǒng)中不同進(jìn)程IO吞吐量的表現(xiàn)就會很不均衡。

就比如,系統(tǒng)內(nèi)存的cache中有很多臟頁要寫回時(shí),桌面又要打開一個(gè)瀏覽器進(jìn)行操作,這時(shí)臟頁寫回的后臺行為就很可能會大量命中空轉(zhuǎn)時(shí)間,而導(dǎo)致瀏覽器的小量IO一直等待,讓用戶感覺瀏覽器運(yùn)行響應(yīng)速度變慢。

這個(gè)low_latency主要是對這種情況進(jìn)行優(yōu)化的選項(xiàng),當(dāng)其打開時(shí),系統(tǒng)會根據(jù)target_latency的配置對因?yàn)槊锌辙D(zhuǎn)而大量占用IO吞吐量的進(jìn)程進(jìn)行限制,以達(dá)到不同進(jìn)程IO占用的吞吐量的相對均衡。這個(gè)開關(guān)比較合適在類似桌面應(yīng)用的場景下打開。

target_latency:當(dāng)low_latency的值為開啟狀態(tài)時(shí),cfq將根據(jù)這個(gè)值重新計(jì)算每個(gè)進(jìn)程分配的IO時(shí)間片長度。

quantum:這個(gè)參數(shù)用來設(shè)置每次從cfq_queue中處理多少個(gè)IO請求。在一個(gè)隊(duì)列處理事件周期中,超過這個(gè)數(shù)字的IO請求將不會被處理。這個(gè)參數(shù)只對同步的請求有效。

slice_sync:當(dāng)一個(gè)cfq_queue隊(duì)列被調(diào)度處理時(shí),它可以被分配的處理總時(shí)間是通過這個(gè)值來作為一個(gè)計(jì)算參數(shù)指定的。公式為:time_slice = slice_sync + (slice_sync/5 * (4 – prio))。這個(gè)參數(shù)對同步請求有效。

slice_async:這個(gè)值跟上一個(gè)類似,區(qū)別是對異步請求有效。

slice_async_rq:這個(gè)參數(shù)用來限制在一個(gè)slice的時(shí)間范圍內(nèi),一個(gè)隊(duì)列最多可以處理的異步請求個(gè)數(shù)。請求被處理的更大個(gè)數(shù)還跟相關(guān)進(jìn)程被設(shè)置的io優(yōu)先級有關(guān)。

1.3 cfq的IOPS模式

我們已經(jīng)知道,默認(rèn)情況下cfq是以時(shí)間片方式支持的帶優(yōu)先級的調(diào)度來保證IO資源占用的公平。

高優(yōu)先級的進(jìn)程將得到更多的時(shí)間片長度,而低優(yōu)先級的進(jìn)程時(shí)間片相對較小。

當(dāng)我們的存儲是一個(gè)高速并且支持NCQ(原生指令隊(duì)列)的設(shè)備的時(shí)候,我們更好可以讓其可以從多個(gè)cfq隊(duì)列中處理多路的請求,以便提升NCQ的利用率。

此時(shí)使用時(shí)間片的分配方式分配資源就顯得不合時(shí)宜了,因?yàn)榛跁r(shí)間片的分配,同一時(shí)刻最多能處理的請求隊(duì)列只有一個(gè)。

這時(shí),我們需要切換cfq的模式為IOPS模式。切換方式很簡單,就是將slice_idle=0即可。內(nèi)核會自動檢測你的存儲設(shè)備是否支持NCQ,如果支持的話cfq會自動切換為IOPS模式。

另外,在默認(rèn)的基于優(yōu)先級的時(shí)間片方式下,我們可以使用ionice命令來調(diào)整進(jìn)程的IO優(yōu)先級。進(jìn)程默認(rèn)分配的IO優(yōu)先級是根據(jù)進(jìn)程的nice值計(jì)算而來的,計(jì)算方法可以在man ionice中看到,這里不再廢話。

2、deadline:最終期限調(diào)度

deadline調(diào)度算法相對cfq要簡單很多。其設(shè)計(jì)目標(biāo)是:

在保證請求按照設(shè)備扇區(qū)的順序進(jìn)行訪問的同時(shí),兼顧其它請求不被餓死,要在一個(gè)最終期限前被調(diào)度到。

我們知道磁頭對磁盤的尋道是可以進(jìn)行順序訪問和隨機(jī)訪問的,因?yàn)閷さ姥訒r(shí)時(shí)間的關(guān)系,順序訪問時(shí)IO的吞吐量更大,隨機(jī)訪問的吞吐量小。

如果我們想為一個(gè)機(jī)械硬盤進(jìn)行吞吐量優(yōu)化的話,那么就可以讓調(diào)度器按照盡量復(fù)合順序訪問的IO請求進(jìn)行排序,之后請求以這樣的順序發(fā)送給硬盤,就可以使IO的吞吐量更大。

但是這樣做也有另一個(gè)問題,就是如果此時(shí)出現(xiàn)了一個(gè)請求,它要訪問的磁道離目前磁頭所在磁道很遠(yuǎn),應(yīng)用的請求又大量集中在目前磁道附近。

導(dǎo)致大量請求一直會被合并和插隊(duì)處理,而那個(gè)要訪問比較遠(yuǎn)磁道的請求將因?yàn)橐恢辈荒鼙徽{(diào)度而餓死。

linux 進(jìn)程占用了io的介紹就聊到這里吧,感謝你花時(shí)間閱讀本站內(nèi)容,更多關(guān)于linux 進(jìn)程占用了io,解決Linux進(jìn)程占用IO的問題,linux查看磁盤io的幾種方法,如何提高Linux下塊設(shè)備IO的整體性能的信息別忘了在本站進(jìn)行查找喔。

成都網(wǎng)站推廣找創(chuàng)新互聯(lián),老牌網(wǎng)站營銷公司
成都網(wǎng)站建設(shè)公司創(chuàng)新互聯(lián)(www.cdcxhl.com)專注高端網(wǎng)站建設(shè),網(wǎng)頁設(shè)計(jì)制作,網(wǎng)站維護(hù),網(wǎng)絡(luò)營銷,SEO優(yōu)化推廣,快速提升企業(yè)網(wǎng)站排名等一站式服務(wù)。IDC基礎(chǔ)服務(wù):云服務(wù)器、虛擬主機(jī)、網(wǎng)站系統(tǒng)開發(fā)經(jīng)驗(yàn)、服務(wù)器租用、服務(wù)器托管提供四川、成都、綿陽、雅安、重慶、貴州、昆明、鄭州、湖北十堰機(jī)房互聯(lián)網(wǎng)數(shù)據(jù)中心業(yè)務(wù)。


網(wǎng)頁名稱:解決Linux進(jìn)程占用IO的問題 (linux 進(jìn)程占用了io)
URL鏈接:http://www.dlmjj.cn/article/cdgpghc.html