今更そんなの気にする必要ある?と言われそうだけど、調べていくうちにどんどん沼にはまったのでメモ。
※ATA は Trim で SCSI では UNMAP だとかその辺は今回は抜き。今回は SATA な一般のご家庭向けの SSD だけを対象とする。
■Linux Kernel のバージョン確認
Linux Kernel 2.6.33 以降ならば、基本的に ATA でも Trim コマンドの送出が可能になっている。
Red Hat Enterprise Linux 6 以降ならば、基本的に Trim 対応しているっぽい。
次のコマンドで 0 や Not Found が返ってくる場合は、対応していないとみていいらしい。
# cat /sys/block/[disk]/queue/discard_max_bytes
詳しくは、以下のサイトがわかりやすい。
Is there TRIM support for solid state drives (SSD) in RHEL6?
RHEL6 でソリッドステートドライブ (SSD) の TRIM はサポートされていますか?
もし、それ以外の Kernel の場合、ソースコードを確認し、次のコミットが適用されていれば、たぶん対応していそう。
libata: add translation for SCSI WRITE SAME (aka TRIM support)
しかし、今回調べたいのは Software RAID で Trim が使えるかどうかである。
RAID1 Trim support は Kernel 3.6 で Release candidate らしい。
RAID4/5/6 の Trim Support は Kernel 3.7 で対応らしい。
コミット内容はこれ。
md: raid 1 supports TRIM
MD: raid5 trim support
■ディスクそのものの Trim 対応確認
次のコマンドで、Data Set Management TRIM supported が返ってくれば Trim 対応のようだ。
# hdparm -I /dev/sdd | grep TRIM
ただし、今回は RAID 1 以上で使用するので、Trim した後のデータに注意する必要がある。
過去の SSD は、Trim コマンドを送出した後に該当 LBA を Read すると、何が返ってくるかわからなかったらしい。
Trim フラグがついたブロックが Garbage Collection 処理されたり、LBA と PBA のマッピングが Wear Leveling 処理などにより変動した際に、Write していない LBA においてはその処理前後での内容が保証されてなかったとか。
普通にシングルドライブとして使う場合は問題はでないが、RAID 1 などによってデータ保護を有効にしている場合はデータが化けた結果、RAID の不整合という致命的な障害になってしまう。
特に RAID4/5/6/DP などパリティによって複数ディスクのデータを保護している場合、パリティデータが保存されたディスクのブロック内で Trim が走った後に次回 Write されるまで返ってくる内容が不確定となると、データが化けかねない。というか化けるだろう。
これは、Microsoft が提唱した OS からストレージに未使用のブロック情報を通達する方法(Trim)を標準化を行う団体(ATAの標準化を行なうINCITS(米国規格協会ANSIの諮問機関)のT13技術委員会 らしい)に提案した「Data Set Management Commands Proposal for ATA8-ACS2」の仕様らしい。
Data Set Management Commands Proposal for ATA8-ACS2
Data Set Management Commands Proposal for ATA8-ACS2
【Mirror】Data Set Management Commands Proposal for ATA8-ACS2
Page 7
Trim
When trim is set to one the data in the logical blocks specified by the DATA SET MANAGEMENT command’s output data becomes indeterminate.
この問題に対して、NetApp と EMC というエンタープライズストレージベンダーが異議を唱えたらしい。
TRIM: Behavior of Subsequent READs
TRIM: Behavior of Subsequent READs
【Mirror】TRIM: Behavior of Subsequent READs
それにより、Trim 後の Read データを確定させるために、機能が追加されたとのこと。それが次の2つ。
- Deterministic Read After Trim (DRAT)
- Deterministic Read Zero After Trim (RZAT)
●Deterministic Read After Trim (DRAT)
規格については、次のドキュメント。
Deterministic TRIM Proposal for ATA8-ACS2
Deterministic TRIM Proposal for ATA8-ACS2
【Mirror】Deterministic TRIM Proposal for ATA8-ACS2
Trim した後の動きについては、次のようなことが書いてあった。
When trim is set to one the data in the logical blocks specified by the DATA SET MANAGEMENT command’s output data then:
- a) If word 69 bit 14 of the IDENTIFY DEVICE data is set to one, then once a trimmed LBA has been read (e.g., a read command), the data in that logical block becomes determinate (i.e., all read commands to a logical block shall return the same data until a subsequent write command to that logical block successfully completes); or
- b) If word 69 bit 14 of the IDENTIFY DEVICE data is cleared to zero, then the data read is indeterminate.
日本語的にはたぶん、Trim を送出した後に該当 LBA を Write する前に Read した場合、何らかの確定したデータを返すようにする。というように読める。気がする。
●Deterministic Read Zero After Trim (RZAT)
規格については、次のドキュメント。
Read zero after TRIM Proposal for ATA8-ACS2
Read zero after TRIM Proposal for ATA8-ACS2
【Mirror】Read zero after TRIM Proposal for ATA8-ACS2
Trim した後の動きについては、次のようなことが書いてあった。
If Trim is set to one, then the data in the logical block ranges addressed by the DATA SET MANAGEMENT command’s output data shall:
- a) if word 69 bit 14 of the IDENTIFY DEVICE data is set to one, then:
- A. after a trimmed LBA has been read (e.g., a read command has been processed), the data in that logical block becomes determinate (i.e., all read commands to a logical block shall return the same data until a subsequent write command to that logical block successfully completes);
- B. if word xx bit yy of the IDENTIFY DEVICE data is set to one, then the data returned by a read command shall have all words cleared to zero; and
- C. if word xx bit yy of the IDENTIFY DEVICE data is cleared to zero, then the data returned by a read command may have words set to any value;
- or
- b) if word 69 bit 14 of the IDENTIFY DEVICE data is cleared to zero, then the data read is indeterminate.
日本語的にはたぶん、Trim を送出した後に該当 LBA を Write する前に Read した場合、0x00 を必ず返す。というように読める。気がする。
これらを踏まえ、RAID に使う場合は RZAT に対応している SSD を選択するのが正しい気がする。気がする。
●Linux 上で RZAT 対応確認方法
hdparm にて確認すれば行けると思われる。
# hdparm -I /dev/sdd | grep Deterministic
この返り値が
- 無い場合、DRAT / RZAT 未対応。
- Deterministic read data after TRIM の場合、DRAT 対応
- Deterministic read ZEROs after TRIM の場合、DRAT / RZAT 双方に対応
とみてよさそうである。
根拠は hdparm のソースコードにある identify.c の内容及び T13技術委員会のドキュメントによる裏付け。
・hdparm のソースコード identify.c より抜粋
static const char *feat_word69_str[16] = { "CFast specification support", /* word 69 bit 15 */ "Deterministic read data after TRIM", /* word 69 bit 14 */ "Long physical sector diagnostics", /* word 69 bit 13 */ "DEVICE CONFIGURATION SET/IDENTIFY DMA commands", /* word 69 bit 12 */ "READ BUFFER DMA command", /* word 69 bit 11 */ "WRITE BUFFER DMA command", /* word 69 bit 10 */ "SET MAX SETPASSWORD/UNLOCK DMA commands", /* word 69 bit 9 */ "DOWNLOAD MICROCODE DMA command", /* word 69 bit 8 */ "reserved 69[7]", /* word 69 bit 7 */ "reserved 69[6]", /* word 69 bit 6 */ "Deterministic read ZEROs after TRIM", /* word 69 bit 5 */ "reserved 69[4]", /* word 69 bit 4 */ "reserved 69[3]", /* word 69 bit 3 */ "reserved 69[2]", /* word 69 bit 2 */ "reserved 69[1]", /* word 69 bit 1 */ "reserved 69[0]", /* word 69 bit 0 */ };
if (like_std > 6) { const __u16 trimd = 1<<14; /* deterministic read data after TRIM */ const __u16 trimz = 1<<5; /* deterministic read ZEROs after TRIM */ __u16 word69 = val[69] & ~(trimz | trimd); /* TRIM bits require special interpretation */ print_features(word69, word69, feat_word69_str); if (val[169] & 1 && val[169] != 0xffff) { /* supports TRIM ? */ printf("\t *\tData Set Management TRIM supported"); if (val[105] && val[105] != 0xffff) printf(" (limit %u block%s)\n", val[105], val[105] > 1 ? "s" : ""); else printf(" (limit unknown)\n"); if (val[69] & trimd) { /* Deterministic TRIM support */ if (val[69] & trimz) print_features(trimz, trimz, feat_word69_str); else print_features(trimd, trimd, feat_word69_str); } } }
TRIM – DRAT / RZAT clarifications for ATA8-ACS2 から抜粋
TRIM – DRAT / RZAT clarifications for ATA8-ACS2 から抜粋
【Mirror】TRIM – DRAT / RZAT clarifications for ATA8-ACS2
Table X – TRIM related interactions
Word 169 bit 0 |
Word 69 bit 14 |
Word 69 bit 5 |
Meaning |
---|---|---|---|
0 | Reserved | Reserved | The Trim function of the DATA SET MANAGEMENT command (see 7.10.3.2) is not supported. |
1 | 1 | 1 | The Trim function of the DATA SET MANAGEMENT command (see 7.10.3.2) is supported with deterministic read after trim behavior with words set to zero. |
1 | 1 | 0 | The Trim function of the DATA SET MANAGEMENT command (see 7.10.3.2) is supported with deterministic read after trim behavior with words set to any value. |
1 | 0 | Reserved | The Trim function of the DATA SET MANAGEMENT command (see 7.10.3.2) is supported with indeterminate read after trim behavior. |
これらを見るに、やはり先ほどの確認方法でよさそう。
なお、Windows で確認する場合、TxBENCH のドライブ情報で確認すればわかりやすい。
■その他参考にした情報
The Linux Kernel Archives
Linux kernel source tree
■元麻布春男の週刊PCホットライン■:SSDの現状とチャンス
■元麻布春男の週刊PCホットライン■:SSDに関するWindows 7の3つの特徴
Wikipedia: Trim (computing)
忘却の彼方:Trimコマンドの送信を個人でチェックする方法
忘却の彼方:Deterministic Zeroing TRIMについて
ピンバック: 20181010 くもり | まこぴかっと
ピンバック: 20200831 くもり | まこぴかっと
ピンバック: Hyper-V のホストサーバ上に All Flash でインライン重複排除ができるストレージサーバを作る | まこぴかっと