AWS の IOPS と I/O クレジットがよくわからなかったので整理した
最近 AWS を触り始めて、EBS を使っているのだが、どうも I/O 速度に制限がかかる仕様があるらしい。調べてみると IOPS やら I/O クレジットやらといった考え方が出てきた。ドキュメントを読んでもわかりづらかったので整理してみた。
- そもそもの前提
- 最初に結論
- I/O クレジットその1: 消費と補充のルール
- I/O クレジットその2: クレジットが枯渇したら
- I/O クレジットその3: IOPS には上限もある
- I/O クレジットその4: IOPS の I/O ってそもそも何?
- 参考
そもそもの前提
AWS のボリュームでは無尽蔵に I/O を発生させることはできず、AWS 側で帯域制限ならぬ I/O 制限が実施されている。
この制限が具体的にいつ、どのように、どれだけ働くのかという仕組みが I/O クレジット という考え方。この時に使う単位が IOPS(I/O per Second) で、読んで字の如く「1秒間のI/O数」を表す。
最初に結論
速度制限について1:
- I/O 回数は I/O クレジット残数(IOPSで表現される)が枯渇すると制限が加えられる
- 制限値は「ボリューム 1 GB あたり 3 IOPS まで」
- この制限は I/O クレジットが回復したら(またクレジットを使い切るまでは)緩和される
速度制限について2:
- ボリュームの種類毎に最大 IOPS が定められており、これを超える速度は出せない
- 例: 汎用 SSD (gp2) だと 10000 IOPS
I/O クレジットの補充/消費ルール:
- [減る] ボリュームで 1 秒間に n 回 I/O を行うと、n [IOPS] が消費される
- [増える] 初期状態では 540 万 IOPS が付与される
- [増える] ボリューム 1GB あたり 3 IOPS が、1 秒毎に補充される
I/O 1回カウントのルール:
- SSD は 256KiB 毎、HDD は 1024KiB 毎の読み書きが 1 I/O になる
- ただしランダムアクセス時は上記の 256 or 1024 毎が適用されない
- 以下 SSD の例:
- 連続アクセスの場合、読み書き量が n [KiB] なら I/O 数は
Ceiling(n/256)
- ランダムアクセスの場合、アクセス数が k 回、各アクセスにおける読み書き量が n [KiB] なら I/O 数は
k * Ceiling(n/256)
- 連続アクセスの場合、読み書き量が n [KiB] なら I/O 数は
上記を踏まえて心がけること:
- I/O クレジットが枯渇すると I/O 速度落ちるので、クレジット消費ペース等を事前に計算した上で、必要ボリューム数やサイズ等を設計しましょう
- 上限 IOPS も ボリュームの種類 毎に定まっているので、ユースケースに適した種類を選びましょう
- CloudWatch を使えば I/O クレジットの消費状況をウォッチできます。また必要なら「しきい値を超えた時にアラートを出す」ことも可能のようです(まだ使ってないのでよくわかりません)
以下各ルールや仕様の細かい話が続く。
I/O クレジットその1: 消費と補充のルール
出展: Amazon Web Services ブログ: 【AWS発表】新しいSSDベースのElastic Block Storage
わかりやすそうでよくわからない図だが、要するに IOPS の補充/消費ルール について以下のようなことを言っている。
- [減る] ボリュームで 1 秒間に n 回 I/O を行うと、n IOPS が消費される
- [増える] 初期状態では 540 万 IOPS が付与 される
- [増える] ボリューム 1GB あたり 3 IOPS が、1 秒毎に補充 される
要するに、普通は減る一方の I/O クレジットだが、最初に540万ほど付与される&毎秒少しだが補充されるという話。
I/O クレジットその2: クレジットが枯渇したら
続いて I/O クレジットが枯渇したら(ゼロになったら)どうなるかという話。
結論を言うと ベースラインパフォーマンス にまで I/O 速度が引き落とされる。ベースラインパフォーマンスとは、上記の 1 秒毎に補充されるペースと同じ値。つまり ボリューム 1GB あたり 3 IOPS。
一つ例を挙げる。
例1: 100 GB のボリュームを使っていて I/O クレジットが枯渇した場合
この時、1000 IOPS(秒間1000回のI/O) を発生させようとしても、ベースラインにまで落とされてしまうため、実際は 300 IOPS の速度となる。ベースラインにまで落とされたくなかったら、I/O クレジットが補充されるのを待つしかない。
I/O クレジットその3: IOPS には上限もある
ここでふと疑問が生じる。「じゃあ(I/Oクレジット使い切るまでは)めちゃくちゃバーストさせてもいいの?」と。たとえば 100 万 IOPS(1秒に100回のI/O)を発生させてもいいのか。
結論を言うと 別に構わないがバーストにも上限が定められている。
上限値は ボリュームによって異なる が、一例を挙げると 2018/06/25 時点で以下のようになっている。
ボリューム種類 | 上限(ボリューム毎) | 上限(インスタンス毎) |
---|---|---|
汎用 SSD (gp2) | 10000[IOPS] | 80000[IOPS] |
プロビジョンド IOPS SSD (io1) | 32000[IOPS] | 80000[IOPS] |
たとえば「汎用 SSD (gp2)」ボリュームを使った場合、たとえ I/O クレジットが十分であっても 1 ボリュームあたり 10000 IOPS(秒間1万回のI/O)以上の速度を出すことはできない。また、1 インスタンスに 10 個のボリュームを繋いでいたとしても、10 個それぞれで 10000 IOPS を出すことは叶わない(計 80000 IOPS 分までしか出ない)。
I/O クレジットその4: IOPS の I/O ってそもそも何?
IOPS は I/O per Second だと述べたが、そもそもここでいう I/O とは何を示しているのか。何をどうしたら 1 I/O とみなすのか。
詳しい話は I/O の特性とモニタリング - Amazon Elastic Compute Cloud に書いてあるが、要するに
- 「最大サイズ」分の I/O 操作1回分を 1 I/O とする
- 「最大サイズ」はボリューム種類によって異なる
- SSD: 256KiB
- HDD: 1024KiB
- 連続した読み書きはなるべく最大サイズになるまでマージされる
- 例1: SSD で 32 KiB の連続する 7 個のデータを書き込んだ → 1 I/O
- 例2: SSD で 32 KiB の連続する 8 個のデータを書き込んだ → 1 I/O
- 例3: SSD で 32 KiB の連続する 9 個のデータを書き込んだ → 2 I/O
- 連続しない(ランダムな)読み書きはマージされない
- 例1: SSD で 32 KiB のデータをランダムアクセスで 7 個読んだ → 7 I/O
つまり(SSDを例にすると) 256KiB 分の読み書き一つが 1 I/O になる ということ。連続した 1MB のデータなら 4 I/O、1GB のデータなら 4096 I/O、10GB なら 40960 I/O。
仮に 10 GB のデータを 40 分でコピーした場合、コピー元ボリューム(コピー先ボリューム)では 40960 / 60*40 = 40960 / 2400 ≒ 17 [IOPS]
17 IOPS の読み込み(書き込み)操作が発生したことになる。