LinuxのIOスケジューラ
IOスケジューリングを紹介するにあたり、まず基本的な概念を理解する必要があります。
IOdb
I/Oデバイス、すなわち入出力デバイスは、データの入出力のためにコンピュータと通信できるハードウェアデバイスで、マウス、キーボード、スキャナ、デジタルカメラなどの一般的なものは入力デバイスに属し、モニタ、プリンタ、バーナーは出力デバイスに属します。異なる性質によって、IOデバイスは異なるカテゴリに分けることができます:
IOデバイスの分類
1.伝送速度による分類
低速機器:1秒間に数バイトから数百バイトの伝送速度の機器を指します。キーボード、マウス、音声入力などが代表的。
中速機器:毎秒数千バイトから数十キロバイトの機器の伝送速度を指します。代表的な機器は、ラインプリンター、レーザープリンターなど。
高速機器:数百キロバイトから数メガバイトの伝送速度の機器を指します。テープドライブ、ディスクドライブ、光ディスクドライブなどが代表的。
2.情報交換単位分類による
ブロック装置:データブロックを単位として、データ情報装置を組織し、伝送するもの。このタイプの装置は、情報を格納するために使用され、ディスクやテープがあります。 構造化装置に属します。典型的なブロックデバイスは、ディスク、512B〜4KBの各ディスクブロックのサイズは、ディスク装置の基本的な特性は次のとおりです。
DMAは、PIO(ディスクファイルをメモリに読み込み、データを保存してCPUを経由して転送する)に代わるもので、CPUを介さずにディスクとメモリ間で直接データをやり取りすることができます。DMAモードでは、CPUは、データの転送に対処するためにDMAコントローラができるように、DMAコントローラに命令を与える必要があり、データを転送するシステムバスを介してDMAコントローラは、転送が完了してから、主にCPUの占有率を低減し、CPUに通知され、システムリソースの大幅な削減!
キャラクタデバイス:これは、1文字の単位でデータ情報を送信するデバイスを指します。一般に、対話型端末やプリンタなど、データの入出力に使用されます。キャラクタデバイスの基本的な特徴は、①伝送速度が低い、②アドレス指定ができない、つまり入力元アドレスや出力先アドレスを指定できない、③キャラクタデバイスのI / Oは割り込み駆動モードを使用することが多い、などです。
3.資源配分の観点による分類
排他的デバイス:ユーザーが排他的デバイスにアクセスできる期間を指します。ユーザー端末、プリンターなどの低速I / Oデバイスのほとんどは、このタイプの機器に属しています。排他的装置は重要な資源なので、複数の同時プロセスが相互に排他的にアクセスする必要があります。
共有デバイス:一定期間に複数のプロセスが同時にアクセスできるデバイス。共有デバイスは、アドレス指定可能でランダムアクセス可能なデバイスである必要があります。典型的な共有デバイスはディスクです。共有デバイスは、デバイスをうまく利用できるだけでなく、ファイルシステムやデータベースシステムを実装するための物理的な基盤でもあります。
仮想デバイス:仮想化技術によって、排他的デバイスを複数のユーザーによって共有される複数の論理デバイスに変換すること。
ブロックデバイス
ブロックデバイスはすでに紹介しましたが、ブロックデバイスの基本的な特徴は、固定サイズのブロックにデータを格納することで、各ブロックはアドレス指定可能で互いに独立しており、他のブロックは読み書き可能です。ここでは、機械式ハードディスクドライブの例を示します。その構造とアドレス指定プロセスを分析するために、IOスケジューリングの目的をより深く理解するためのプロセスを理解するだけです:磁気ヘッドの動きを減らし、効率を向上させます。次の2つの写真は、ディスクの物理的な構造を示しています:
記憶容量=ヘッド数×トラック数×トラックあたりのセクタ数×セクタあたりのバイト数
上の図のように、ディスクには3枚のディスク、6個のヘッド、7個のシリンダー、1トラックあたり12個のセクタがあるので、このディスクの容量は6 * 7 * 12 * 512B = 258048Bとなります。
1トラックあたりのセクタ数は、古いハードディスクでは、外周リングの密度が小さく、内周リングの密度が大きく、各リングに格納できるデータ量は同じ、例えば512Bと言われています。新しいハードディスクでは、データ密度が同じなので、磁気トラックの外周が長くなるほどセクタ数が増え、格納できるデータ量も大きくなります。
ディスクの読み取り時間=シーク時間+スピン時間+転送時間
シーク時間:磁気ヘッドが先頭からデータのあるトラックまで移動するのにかかる時間。 シーク時間が短いほどI/O動作が速くなり、現在のディスクの平均シーク時間は通常3~15ms、通常は10ms前後です。
回転遅延:要求されたデータがあるセクタを読み取り/書き込みヘッドの下に移動させるためにディスクが回転するのに必要な時間で、回転遅延はディスク速度に依存します。通常のハードディスクは一般的に7200rpm、低速の5400rpmです。
データ転送時間:要求されたデータの転送を完了するのに必要な時間。
転送時間はディスクの性質に依存するため、ディスクのIO効率を向上させるために最適化できるのは、シーク時間と回転待ち時間です。これは後述する IO スケジューラで実現できます。
IOsdb
LinuxのIOアーキテクチャを以下に示します:
このように、IOシステム全体は7つの層に分けることができます:
- VFSの仮想ファイルシステム:カーネルは、ファイルシステムの様々な対処するために、カーネルは、特にファイルシステムの様々な適応するために使用されるこのVFSを抽象化し、統一された外部オペレーティングインターフェイスを提供します。
- ディスクキャッシュ:ディスクキャッシュは、RAMにディスク上のいくつかのデータを予約するソフトウェアのメカニズムであり、高速な応答は、このデータにアクセスすることができます。Linuxのディスク・キャッシュには、デントリー・キャッシュ、ページ・キャッシュ、バッファ・キャッシュの3種類があります。
- マッピング層:カーネルはブロック・デバイスからデータを読み込むため、そのデータが物理デバイス上のどこにあるかを特定する必要があります。
- 汎用ブロック・レイヤ:I/O操作のほとんどのケースでブロック・デバイスを扱うため、Linuxはvfsレイヤと同様のブロック・デバイス操作の抽象化レイヤを提供します。下位レイヤーは属性の異なるさまざまなブロックデバイスとのインターフェイスを提供し、上位レイヤーは統一されたブロックIOリクエスト標準を提供します。
- I/Oスケジューリング層:ほとんどのブロックデバイスはディスクデバイスであるため、そのようなデバイスの特性やアプリケーションの特性に基づいて、多くの異なるスケジューラを設定する必要があります。
- ブロック・デバイス・ドライバ:ブロック・デバイス・ドライバは、外部に対する高レ ベルのデバイス操作インタフェースを提供します。
- 物理ハードディスク:この層は具体的な物理デバイスです。
あるプロセスがシステムコールread()を使ってディスク上のファイルを読み込んだとします。プロセスからの読み取り要求に対してカーネルが実行するステップは次のとおりです:
- システムは read 関数を呼び出し、ファイル記述子やファイル・オフセットなどのパラメータを渡します。
- VFSは、要求されたデータがすでにメモリ・バッファ内にあるかどうかを判断し、ない場合は読み取り操作の実行方法を決定します。
- カーネルはブロック・デバイスからデータを読み取る必要があるため、データが物理デバイスのどこにあるかを判断する必要があります。これはマッピング層によって行われます。
- この時点で、カーネルは汎用ブロックデバイス層を通じてブロックデバイスの読み取り操作を実行し、要求されたデータを転送するためのI/O操作を開始します。
- 汎用ブロックデバイス層の下にはI/Oスケジューリング層があり、カーネルのスケジューリングポリシーに従ってI/O待ちキューをマージしてソートします。
- 最後に、ブロックデバイスドライバがディスクコントローラに適切なコマンドを送信して実際のデータ転送を実行します。
以上のように、IOスケジューリングがIOシステム全体のどこに位置づけられるかを明確にすることができます。
IOスケジューラの紹介
IOスケジューラは、オペレーティングシステムがブロックデバイス上でIOオペレーションを投入する順序を決定するために使用する方法です。その目的は2つあり、IOスループットの向上とIO応答時間の短縮です。しかし、IOスループットとIO応答時間はしばしば相反するものです。この2つのバランスを取ろうと、IOスケジューラはさまざまなIO要求シナリオに適応するために、さまざまなスケジューリングアルゴリズムを提供します。
Linuxは2.4カーネルからI/Oスケジューラをサポートしており、これまでにLinux 2.4カーネルのLinus Elevator、Linux 2.6カーネルのDeadline、Anticipatory、CFQ、Noopの5種類があります。AnticipatoryはLinux 2.6.33から削除されました。現在、主要なLinuxディストリビューションでは、Deadline、CFQ、NoopのI/Oスケジューラを使用しています。
NOOP
NoopとはNo Operationのことで、I/Oリクエストの順序付けやその他の最適化を行いません。Noopはリクエストのマージ以外の処理を行わず、FIFOのような順序でI/Oリクエストを送信します。
DeadLine
DeadLineは、4つのキューを実装しています。そのうちの2つは、セクタ番号でソートされた通常の読み取りと書き込みを処理し、スループットを向上させるために通常のIOマージ処理を実行します。IO リクエストは特定のディスク位置に集中する可能性があるため、 常に新しいリクエストがマージされることになり、IO リクエストに飢えている 他のディスク位置が存在する可能性があります。そのため、読み出しと書き込みのタイムアウトを処理するために、 他の2つのキューが実装されており、スケジューリングアルゴリズムによって、 タイムアウトキュー内の要求が最初に処理されるようにして、飢餓状態を防いでいます。
CFQ
CFQ (Completely Fair Queuing) アルゴリズムは、I/O要求をプロセスの対応する キューに入れます。各キュー内では、マージとソートの方法がまだ使用されますが、唯一の違いは、I/O要求を提出する各プロセスが、それ自身のI/Oキューを持つということです。
CFQの "公平性 "はプロセス固有であり、スケジューリングキューを回転させる 前提として、タイムスライスアルゴリズムを使用しています。 デフォルトでは、4つの要求が現在のキューから処理され、次に4つの要求が 次のキューから処理されます。これにより、各プロセスのI/Oリソースのバランスが保たれます。
Linux 2.6.18 以降、CFQ はデフォルトの IO スケジューリングアルゴリズムです。
異なるスケジューリング・アルゴリズムの適用シナリオ
Noop アルゴリズムは、その単純さゆえに、以下のシナリオに適しています:
- IOスケジューラの下には、よりスマートなIOスケジューリング・デバイスがあります。ブロック・デバイス・ドライバがRaidであったり、SANやNASなどのストレージ・デバイスであれば、IOスケジューラが余計なスケジューリング作業をしなくても、これらのデバイスがIOリクエストをうまく整理してくれます。
- 上位層のアプリケーションは、IOスケジューラよりも基礎となるデバイスをよく理解しています。あるいは、上位層のアプリケーションは、慎重に最適化されたIOリクエストでIOスケジューラに到達するので、IOスケジューラはそれに何も追加する必要がなく、上位層から伝達された順序でIOリクエストを実行するだけです。
- 一部の非回転ヘッドストレージデバイスでは、Noopを使った方がうまくいきます。なぜなら、回転ヘッドディスクの場合、IOスケジューラはリクエストを再編成するためにある程度のCPU時間を要しますが、SSDディスクの場合、SSDはカーネルがリクエストを引き出す必要のない、よりスマートなリクエストスケジューリングアルゴリズムを提供するため、IOリクエストを再編成するためのCPU時間を節約できるからです。
DeadLine はスループットとレスポンスタイムの面で優れたパフォーマンスを発揮し、データベースシナリオに適しています。
CFQは、汎用サーバーやデスクトップ・ユーザーに適した選択です。
High Performance MySQL の関連セクションを添付します:
Choosing a Disk Queue Scheduler
On GNU/Linux, the queue scheduler determines the order in which requests to a blockdevice are actually sent to the underlying device.
The default is Completely Fair Queueing, or cfq. It’s okay for casual use on laptops and desktops, where it helps preventI/O starvation, but it’s terrible for servers. It causes very poor response times under the types of workload that MySQL generates, because it stalls some requests in the queue needlessly.
The other two choices are suitable for server-class hardware, and in most cases they work about equally well. The noop scheduler is appropriate for devices that do their own scheduling behind the scenes, such as hardware RAID controllers and SANs, and deadline is fine both for RAID controllers and disks that are directly attached. Our benchmarks show very little difference between these two. The main thing is to use anything but cfq, which can cause severe performance problems.
LinuxのIOスケジューリングアルゴリズムの表示と変更
1.デバイスの現在のI/Oスケジューラをチェックします:
cat /sys/block/sda/queue/scheduler
異なるディスクのスケジューラは個別に設定できます。
2.デバイスの現在のI/Oスケジューラを変更します:
echo noop > /sys/block/sda/queue/scheduler
設定がすぐに反映されることがわかります。