iMac (Debian) の Fusion Drive SSD を swap にする

iMac 2015 の Fusion Drive は、HDD と小容量の SSD(ブレード NVMe)を組み合わせる構成である。macOS で Fusion Drive を解体して Debian に移行すると、HDD 側は OS 用に使える一方、SSD 側(約 24 GB)が「未使用のデバイス」として残ることがある。[1]

この SSD の使い道として最初に思いつくのは、root を SSD でキャッシュする(LVM cache)か、swap 専用として使うかの 2 択である。前回の記事では LVM cache を試したが、サーバー用途で最優先すべきは性能ではなく「起動経路の単純さ」と「障害時に手順が短いこと」だと結論づけた。LVM cache は root の成立条件に SSD を追加するため、SSD の認識遅延や欠落が「起動が止まる」という事故に直結しうる。[2][3]

したがって本稿の採用形は、Fusion Drive の SSD を swap 専用にし、root(OS 領域)は HDD 単独で完結させる構成である。さらに root が意図せず SSD にまたがり、pvmove が失敗して設計純度を壊した事故を踏まえ、「デバイスを完全にまたがせない」かつ「VG / PV の空き extents を 0 にする」手順と確認方法を、実用レベルで固定する。


前提とゴール

前提は「暗号化 LVM(LUKS + LVM)の上に ext4 の /(root)を置く」構成である。[4][5]

項目 方針
root HDD 側 PV のみで完結させる(SSD へ 1 extent も流さない)
swap SSD 側 PV のみで完結させる(HDD へ 1 extent も流さない)
空き extents VG / 各 PV ともに Free PE = 0 にする(「空きが残っていて事故る」を防ぐ)
障害時 SSD を失っても OS は起動できる。必要なのは swap の無効化だけにする

ここで言う「事故」とは、VG に HDD と SSD の 2 PV がある状態で、lvextend などを PV 指定なしで実行してしまい、LVM が空き extents のある PV に自動割当を行って root LV がデバイスをまたぐ状態になった、というものだ。LVM は「またがない」保証を暗黙には提供しない。よって、手順と確認を固定しない限り、同じ事故は再発しうる。


SSD の健康状態を確認する

Fusion Drive 由来の SSD は中古機体では消耗している可能性がある。まず smartctl で健康状態を見て、使う価値があるか判断する。[6]

見るべきポイントは、Critical Warning、Media/Data Integrity Errors、Error Information Log Entries、温度、Percentage Used(消耗率)である。NVMe のログ構造は NVMe 仕様(SMART / Health Information Log)に基づく。[7]

1
sudo smartctl -a /dev/nvme0n1

本用途(swap)では「データを長期保持しない」ため、寿命やエラーカウントが多少進んでいても、LVM cache や永続データ領域よりは許容しやすい。一方で、Critical Warning が立っている、Integrity Errors が増える、といった場合は swap にすら使わないほうがよい。


設計ルールを先に固定する

再発防止の要点は 2 つだけである。

1 つ目は「LV を作る/拡張する操作では、必ず PV を指定する」ことだ。lvcreate は PV を明示できる。[8] lvextend も同様に対象 PV を明示できる。[9] PV を指定しないと、LVM は VG 内の空き extents から最適化方針に従って自動割当を行い、結果として LV が複数 PV にまたがる可能性がある。

2 つ目は「空き extents を残さない」ことだ。空きが残ると、将来の lvextend で誤って PV 指定を忘れた場合に、空きのある側へ extents が流れて事故が再発する。空き extents を 0 にするのは、誤操作の余地を潰すための安全策である。

デバイスを完全分離する設計では、本来は HDD 用 VG と SSD 用 VG を分けるのが最も明快である。ただし「既に 1 VG に統合して運用している」「暗号化やブート手順を変えたくない」などの制約がある場合、本稿のように 1 VG のまま PV 指定を徹底しても、非またぎは実現できる。その代わり、確認を機械的に行う。


構築手順

1. SSD 側の署名を消す

Fusion Drive の名残で SSD 側に GPT 署名等が残っていることがある。そのまま pvcreate すると失敗したり、意図しない解釈が入る。wipefs で署名を確認し、必要なら削除する。[10] 反映のために partprobe で再読込する。[11]

1
2
3
sudo wipefs /dev/nvme0n1
sudo wipefs -a /dev/nvme0n1
sudo partprobe

2. SSD を PV 化して VG に追加する

SSD を PV として初期化し、HDD 側の VG に追加する。[12][13]

1
2
sudo pvcreate /dev/nvme0n1
sudo vgextend orion-vg /dev/nvme0n1

3. swap LV を SSD 側 PV のみで作成し、SSD 側を使い切る

swap は SSD 側 PV のみに閉じる。SSD 側の空き extents を 0 にするには、lvcreate -l 100%FREE を SSD 側 PV を指定して実行する。[8][14][15]

1
2
3
sudo lvcreate -l 100%FREE -n swap_nvme orion-vg /dev/nvme0n1
sudo mkswap /dev/orion-vg/swap_nvme
sudo swapon /dev/orion-vg/swap_nvme

4. root LV は HDD 側 PV のみで作り、HDD 側を使い切る

root は HDD 側 PV のみに閉じる。既に root がある場合も、拡張は必ず HDD 側 PV を指定して行う。lvextend の PV 指定を忘れた場合、swap を作った SSD 側へ root が流れ込む可能性があるので、ここが最重要ポイントである。[9]

1
2
sudo lvextend -l +100%FREE /dev/orion-vg/root /dev/mapper/sda3_crypt
sudo resize2fs /dev/orion-vg/root

resize2fs はオンライン拡張はできるが、オンライン縮小はできない。縮小が必要ならアンマウントして実施する。[16]

5. /etc/fstab は UUID 指定にする

swap は UUID 指定が安全である。fstab の記述仕様は fstab(5) を参照。[17] UUID は blkid で取得できる。[18]

1
sudo blkid /dev/orion-vg/swap_nvme
1
UUID=XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX none swap sw 0 0

確認

この段階で、確認は必ず機械的に行う。見るべき点は 3 つだけだ。

1. LV がデバイスをまたいでいないこと

lvs の devices 列で、root が HDD 側 PV のみ、swap が SSD 側 PV のみになっていることを確認する。[19]

1
sudo lvs -o lv_name,vg_name,lv_size,devices

期待値は次の形になる。

  • root: /dev/mapper/sda3_crypt(…) のみ
  • swap_nvme: /dev/nvme0n1(…) のみ

2. VG の空き extents が 0 であること

vgdisplay の Free PE / Size が 0 / 0 であることを確認する。[20]

1
sudo vgdisplay

3. PV ごとの空き extents が 0 であること

pvdisplay の Free PE が、HDD 側 PV と SSD 側 PV の両方で 0 であることを確認する。[21]

1
sudo pvdisplay

この 3 点が満たされていれば、少なくとも「root が SSD にまたがっている」「swap が HDD に流れている」「VG に空きが残っていて将来の誤操作でまたがる」という類の事故は、構成としては起きない。


障害対応(SSD が失われた場合)

SSD が認識不能になると、swap は有効化できない。しかし本稿の設計では root が HDD 側 PV のみで完結しているため、OS は起動できる。残る作業は swap を無効化するだけである。[15][22]

1
2
sudo swapoff -a
sudoedit /etc/fstab

/etc/fstab の swap 行をコメントアウトし、再起動すればよい。最悪の状況でも「起動が止まる」方向には行かないように設計している。

それでも rescue 環境が必要になるケース(HDD 側の暗号化解除や fsck が絡む等)はありうるため、Debian installer の rescue mode は常備しておく。[23] iMac 2015 では起動直後に Option (⌥) キー押しっぱなしにして EFI Boot を選択することで USB デバイスから起動できる。


まとめ

Fusion Drive 由来の SSD は、データ領域としては小さいが、swap 専用なら用途として成立する。性能目的で root をキャッシュ化する(LVM cache)よりも、起動経路に依存を増やさない swap のほうが、サーバー用途では設計純度が高い。

今回の事故(LV が意図せずデバイスをまたぐ)は、LVM の挙動として自然に起こりうる。再発防止の本質は「LV 操作時に PV を必ず指定する」ことと「空き extents を残さない」こと、そして「lvs/vgdisplay/pvdisplay で機械的に確認する」ことだけである。この 3 点を固定することがポイントである。


参考文献

  1. Fusion Drive の概要. https://support.apple.com/ja-jp/101390
  2. LVM cache(lvmcache(7)). https://man7.org/linux/man-pages/man7/lvmcache.7.html
  3. lvconvert(8)(cache / uncache). https://man7.org/linux/man-pages/man8/lvconvert.8.html
  4. Debian Wiki: Cryptsetup. https://wiki.debian.org/Cryptsetup
  5. Debian Wiki: LVM. https://wiki.debian.org/LVM
  6. smartmontools(smartctl). https://www.smartmontools.org/
  7. NVM Express: NVMe Base Specification(SMART / Health Information Log を含む). https://nvmexpress.org/specifications/
  8. lvcreate(8). https://manpages.debian.org/bookworm/lvm2/lvcreate.8.en.html
  9. lvextend(8). https://manpages.debian.org/bookworm/lvm2/lvextend.8.en.html
  10. wipefs(8). https://man7.org/linux/man-pages/man8/wipefs.8.html
  11. partprobe(8). https://man7.org/linux/man-pages/man8/partprobe.8.html
  12. pvcreate(8). https://manpages.debian.org/bookworm/lvm2/pvcreate.8.en.html
  13. vgextend(8). https://manpages.debian.org/bookworm/lvm2/vgextend.8.en.html
  14. mkswap(8). https://manpages.debian.org/bookworm/util-linux/mkswap.8.en.html
  15. swapon(8) / swapoff(8). https://manpages.debian.org/bookworm/util-linux/swapon.8.en.html
  16. resize2fs(8). https://manpages.debian.org/bookworm/e2fsprogs/resize2fs.8.en.html
  17. fstab(5). https://man7.org/linux/man-pages/man5/fstab.5.html
  18. blkid(8). https://manpages.debian.org/bookworm/util-linux/blkid.8.en.html
  19. lvs(8). https://manpages.debian.org/bookworm/lvm2/lvs.8.en.html
  20. vgdisplay(8). https://manpages.debian.org/bookworm/lvm2/vgdisplay.8.en.html
  21. pvdisplay(8). https://manpages.debian.org/bookworm/lvm2/pvdisplay.8.en.html
  22. swapoff(8). https://manpages.debian.org/bookworm/util-linux/swapoff.8.en.html
  23. Debian Installer: Rescue mode. https://www.debian.org/releases/stable/amd64/ch08s07.en.html
  24. iMac (Retina 5K, 27-inch, Late 2015) 技術仕様. https://support.apple.com/kb/SP731
  25. NVMe(概要). https://ja.wikipedia.org/wiki/NVM_Express

コメントする

日本語が含まれない投稿は無視されますのでご注意ください。(スパム対策)