お伝えしたいこと
ディスク拡張方法は、利用しているストレージ、LVM2の利用有無、ファイルシステムによって変わります。
今回ご紹介する手順は、以下の環境を前提としています。
ディスク拡張を行う際は、必ずバックアップを取った上で作業してください。
本手順においても、#パーティション拡張の工程で「間違えるとデータが消える」部分があります。
fdiskの操作でyes/noを間違えてそのまま気づかずwriteしてしまい、更に対処を間違えると詰みます。
なお、記事の後半でパーティションテーブルやアラインメントなどの背景知識に触れていますので、興味のある方はぜひご覧ください。
作業の流れ
ディスク拡張ですが、基本的にファイルシステムを作成する時の流れに沿って作業します。
冒頭で述べたストレージ環境を構築する手順は、ざっくり以下の流れです。
- qcow2ファイルの作成 (ホストマシン上で実施)
- パーティション作成
- LVMの設定
- PV作成 (PVとパーティションを紐づけて登録)
- VG作成 (VGにPVを所属させる)
- LV作成 (VGの領域の一部を切り出してLV作成)
- LV上にファイルシステム作成
従って、ディスク拡張作業は以下の流れで進めることになります。
LVMを使っていない場合、「LVMの設定」は丸ごとスキップします。
また、ファイルシステムを拡張するコマンドが若干変わります。
今回の環境ではLVM2を使っているので、この設定についても触れていきます。
図解
#作業の流れと重なりますが、ディスク拡張前後の状態を図解しました。
まずは、ディスク拡張前の状態です。
今回の作業では、(1)〜(6)を順に拡張していきます。
ディスク拡張後は、以下の状態になります。
qcow2のサイズを5GiB増やし、その分ルートファイルシステムを拡張しています。
拡張によって、ルートファイルシステムのアドレスがSWAP用の領域を挟んで不連続になっているように表現していますが、LVM2の仮想化機能によりこれでも問題なく動作します。
次のセクションから、具体的なコマンドを紹介します。
qcow2ファイルの拡張
ここの説明は、KVMで作成したVMのディスク拡張をしたい方にのみ関係があります。
また、KVMのセットアップが完了していることが前提です。
KVMの設定については、過去の記事を参照してください。
さて、本題に入ります。
KVM仮想マシンのボリュームのリサイズにはvirsh
コマンドを使用します。
コマンドの書式は以下の通りです。
以下のコマンドをKVMのホストマシン上で実行します。
virsh vol-resize vol-name-or-path capacity [--pool pool-or-uuid] [--allocate] [--delta] [--shrink]
それぞれのキーワードの意味は、以下のとおりです。
詳細はman virshのvol-resize
の項や、Red Hat Virtualization Deployment and Administration Guide を参照してください。
キーワード | 意味 |
---|---|
vol-name-or-path | ボリューム名、またはファイルフルパス (*.qcow2) |
capacity | ボリュームのサイズ。 1GB (1000MB), 1GiB (1024MiB) など |
--pool pool-or-uuid | プール名、またはUUID。 vol-name-or-path にフルパスを指定した場合は省略可 |
--allocate | rawファイルにのみ対応。 qcow2ファイルに対して指定するとエラーになる。 基本使わない |
--delta | --deltaを指定しない場合、capacity には変更後のサイズを記載する。 --deltaを指定すると、代わりにサイズ拡張/縮小の差分の値を記載する。 |
--shrink | ボリュームを縮小する際に指定する。 拡張の際に指定するとエラーになる |
さて、ここでvolume名とpool名が必要であることがわかります。
それらを先に調べておきます。
以下のコマンドより、volume名はvm_name.qcow2
、pool名はdefault
と判明しました。
virsh pool-list # Name State Autostart # ---------------------------------------------- # default active yes virsh vol-list --pool default # Name Path # ----------------------------------------------------- # vm_name.qcow2 /home/shared/kvm_volumes/vm_name.qcow2
ついでに、現在のボリュームサイズも調べておきます。
virsh vol-info --pool default my_vm.qcow2 # Name: my_vm.qcow2 # Type: file # Capacity: 20.00 GiB # Allocation: 16.46 GiB
さて、情報が揃いました。
以下のコマンドにより、pool default
に存在するsize 20GiB
のvolume my_vm.qcow2
を、25GiB
に拡張します。
2種類のコマンドを提示していますが、どちらも同じ結果になります。
現在の容量を意識せずに済む分--delta
を使う方が検証用途ではお手軽ですが、間違えて2回同じコマンドを実行しても安全なのは--delta
を使わないコマンドですね。
# virsh vol-resize my_vm.qcow2 --pool default --delta 5GiB virsh vol-resize my_vm.qcow2 --pool default 25GiB
今回のケースとは関係ないですが、ご参考までに5GiB縮小する際のコマンドも記載しておきます。
ディスクサイズの縮小はデータを破壊するリスクがあるので、試す際は事前にデータバックアップを取っておきましょう。
# virsh vol-resize my_vm.qcow2 --pool default --delta -5GiB --shrink virsh vol-resize my_vm.qcow2 --pool default 15GiB --shrink
パーティション拡張
以降のコマンドはVMゲスト上で実行します。
今回はfdisk
コマンドでパーティションを拡張します。
fdisk
コマンドを実行するために、デバイスファイル名を確認します。
3行目の出力より、今回は/dev/vda
を見ればよいとわかります。
他にもdf -Th
やsudo blkid
などで確認できます。
なお、冒頭の2行に警告が出ていますが、こちらはあまり気にする必要はありません。
パーティションテーブルを書き換えないままディスクサイズ (qcow2のサイズ) が変わったことで、fdiskが不整合を検出したというメッセージです。
メッセージに書いてあるとおり、fdisk
でwriteすることでPMBRを含むパーティションテーブルの情報が上書きされてエラーは解消されます (本当に何もせず、wでwriteするだけでエラーは解消されます)。
エラーメッセージの意味については、#(参考) GPTとPMBRの概要にて考察するので、気になる方はこちらも読んでみてください。
sudo fdisk -l # GPT PMBR size mismatch (41943039 != 52428799) will be corrected by write. # The backup GPT table is not on the end of the device. This problem will be corrected by write. # Disk /dev/vda: 25 GiB, 26843545600 bytes, 52428800 sectors # Units: sectors of 1 * 512 = 512 bytes # Sector size (logical/physical): 512 bytes / 512 bytes # I/O size (minimum/optimal): 512 bytes / 512 bytes # Disklabel type: gpt # Disk identifier: 3AED67ED-0074-4379-987F-320ED57ED3CB # Device Start End Sectors Size Type # /dev/vda1 2048 1230847 1228800 600M EFI System # /dev/vda2 1230848 3327999 2097152 1G Linux filesystem # /dev/vda3 3328000 41940991 38612992 18.4G Linux LVM # Disk /dev/mapper/my_vm-root: 16.26 GiB, 17448304640 bytes, 34078720 sectors # Units: sectors of 1 * 512 = 512 bytes # Sector size (logical/physical): 512 bytes / 512 bytes # I/O size (minimum/optimal): 512 bytes / 512 bytes # Disk /dev/mapper/my_vm-swap: 2 GiB, 2147483648 bytes, 4194304 sectors # Units: sectors of 1 * 512 = 512 bytes # Sector size (logical/physical): 512 bytes / 512 bytes # I/O size (minimum/optimal): 512 bytes / 512 bytes
ついでに、LVM周りの情報とファイルシステムの情報を予め取得しておいてください。
fdisk -l
のログも含めて、取得した情報はホストPC上のテキストファイルなどゲストOS以外の場所に保存してください。
いざというときの復旧に役に立ちます。
# LVM Information pvdisplay vgdisplay lvdisplay cat /etc/lvm/backup/* # File System Information df -Th
では、fdiskによってパーティションサイズを20GiBから25GiBに拡張します。
手順は以下の流れです。
d
,3
:/dev/vda3
の削除n
,3
,(Enter)
x2,n
: 新しいサイズで/dev/vda3
の再作成w
: 変更の確定。パーティションテーブルに情報を書き込む
2番目の工程でパーティションを作成する際のパラメータ指定について補足です。
man fdiskに書いてあるように安全な方法でパラメータを指定します (Enter
x2)。
First sectorはデフォルト値で指定することで、Alignmentの問題を踏まないようにしています。
Last sectorは単位 (MiB/GiB) を付けてサイズで指定するのが一般的ですが、今回は最終セクタを指定したいのでここもデフォルト値を使っています。
また、「Do you want to remove the signature? [Y]es/[N]o:」と聞かれる箇所がありますが、ここでは絶対にNo
を選択してください。
間違えてYesを選択した場合は、writeをせず、落ち着いてq
から抜けてください。
もしYes
を選択した上でwriteしてしまうと、/dev/vda3
のパーティションタイプがLinux LVMであるという情報が消えてしまいます。
結果として、次のPV拡張の工程でpvdisplay
などを実行しても何も表示されず、pvresize
コマンドも失敗してしまいます。
※既存のデータを全て削除して問題ない場合はYesでも良いのですが...
LVMを間違えて削除してしまった時も復旧できますが、それでも対処を間違えると詰みます。
もしLVMを削除した場合は、ひとまずOSシャットダウンや再起動は絶対にしないでください。
その上で#(参考) LVMを削除した時の復旧方法を参考にしつつ、対処法をご検討ください。
ただ、上記の方法で復旧するぐらいなら作業前のバックアップからやり直したほうが楽でしょう。
fdiskの操作は、くれぐれもお気をつけください。
前置きが長くなりましたが、具体的なfdiskのコマンドを以下に記載します。
Command (m for help): p # Disk /dev/vda: 25 GiB, 26843545600 bytes, 52428800 sectors # Units: sectors of 1 * 512 = 512 bytes # Sector size (logical/physical): 512 bytes / 512 bytes # I/O size (minimum/optimal): 512 bytes / 512 bytes # Disklabel type: gpt # Disk identifier: 3AED67ED-0074-4379-987F-320ED57ED3CB # Device Start End Sectors Size Type # /dev/vda1 2048 1230847 1228800 600M EFI System # /dev/vda2 1230848 3327999 2097152 1G Linux filesystem # /dev/vda3 3328000 41940991 38612992 18.4G Linux LVM Command (m for help): d # Partition number (1-3, default 3): 3 # Partition 3 has been deleted. Command (m for help): p # Disk /dev/vda: 25 GiB, 26843545600 bytes, 52428800 sectors # Units: sectors of 1 * 512 = 512 bytes # Sector size (logical/physical): 512 bytes / 512 bytes # I/O size (minimum/optimal): 512 bytes / 512 bytes # Disklabel type: gpt # Disk identifier: 3AED67ED-0074-4379-987F-320ED57ED3CB # Device Start End Sectors Size Type # /dev/vda1 2048 1230847 1228800 600M EFI System # /dev/vda2 1230848 3327999 2097152 1G Linux filesystem Command (m for help): n Partition number (3-128, default 3): First sector (3328000-52428766, default 3328000): Last sector, +/-sectors or +/-size{K,M,G,T,P} (3328000-52428766, default 52428766): # Created a new partition 3 of type 'Linux filesystem' and of size 23.4 GiB. # Partition #3 contains a LVM2_member signature. Do you want to remove the signature? [Y]es/[N]o: n Command (m for help): p # Disk /dev/vda: 25 GiB, 26843545600 bytes, 52428800 sectors # Units: sectors of 1 * 512 = 512 bytes # Sector size (logical/physical): 512 bytes / 512 bytes # I/O size (minimum/optimal): 512 bytes / 512 bytes # Disklabel type: gpt # Disk identifier: 3AED67ED-0074-4379-987F-320ED57ED3CB # Device Start End Sectors Size Type # /dev/vda1 2048 1230847 1228800 600M EFI System # /dev/vda2 1230848 3327999 2097152 1G Linux filesystem # /dev/vda3 3328000 52428766 49100767 23.4G Linux filesystem Command (m for help): w # The partition table has been altered. # Syncing disks.
最後に、パーティションサイズが変更されたことを確認します。
sudo fdisk -l # (中略) # Device Start End Sectors Size Type # /dev/vda1 2048 1230847 1228800 600M EFI System # /dev/vda2 1230848 3327999 2097152 1G Linux filesystem # /dev/vda3 3328000 52428766 49100767 23.4G Linux filesystem # (中略)
最後の/dev/vda3
のSectorsが奇数になっていますが、Alignmentの観点では気にする必要はありません。
Alignmentが問題となるのはあくまで開始セクタの位置のみです。
もちろん、例えば/dev/vda1
の終了セクタは、次の/dev/vda2
の開始セクタのデフォルト値に影響するので、配慮した方が良いとは思います。
ここで言っているのは、最後のパーティションの最終セクタ位置は気にしなくても良いということです1。
(参考) LVMを削除した時の復旧方法
ここでは、上記のfdisk操作で誤ってLinux LVM
Partition Type を誤って削除し、そのままwriteしてしまった時の対処法を紹介します。
最初に補足しておきます。
今回の障害の契機は、fdisk
によるパーティションタイプの削除です。
fdisk
には、t
でパーティションタイプを作成することができ、30
(Linux LVM) を指定することで同様のパーティションタイプを作成することができます。
しかし、今回のケースはパーティションタイプの再作成では復旧できません。
fdisk
がパーティションテーブルを削除する際、どうやらLVMのPV、LV、VGなどのメタデータも全て削除してしまっているようです。
その証拠に、実際にパーティションタイプを再作成しても、pvdisplay
などのコマンドでPV、VG、LVは表示されませんでした。
さて、本題に入ります。
基本的には、Red Hat社のマニュアルにあるPVの復旧方法2 を参考に進めます。
具体的には、以下のような流れで進めます。
- LVMメタデータのバックアップ
- レスキューモードの起動
- (任意) キーボードの日本語化
- (任意) SSHサーバの有効化、バックアップファイル送付
- (任意) 非LVM領域のマウント
- PVの復旧
- VG,LVの復旧
具体的な内容をstep by stepで紹介します。
LVMメタデータのバックアップ
まずは、以下のパスにあるLVMメタデータを外部ストレージに退避してください。
/etc/lvm/backup
lvcreate
などの変更コマンドを実行する度にバックアップを自動保存するフォルダ- 最新の情報のみ保存されている
/etc/lvm/archive
- 過去のバックアップを世代管理しているフォルダ
archive
内の最新のファイルは、/etc/lvm/backup
と同じ中身
私の場合は、VMを動かしているホストPCにSCPでファイルコピーしておきました。
外部ストレージをどうしても用意できない場合は、/bootなどLVM外のパーティションにファイルコピーしておくのでも最悪OKです。
これらのバックアップファイルは、復旧時にレスキューモードで起動したVM上に送る必要があります。
ファイルの送り方はSCPと非LVM領域のマウントの2パターンがあります (他にもあるかもしれません)。
SCPの場合は、パスワード無しでrootログインされてしまうというセキュリティリスクがあります。
詳細は、#(任意) SSHサーバの有効化、バックアップファイル送付を参照してください。
非LVM領域のマウントは、レスキューモードでマウントできる構成か、事前に確認が必要です。
/boot
であれば簡単にマウントできます。
詳細は、#(任意) 非LVM領域のマウントを参照してください。
レスキューモードでの起動
この手順が必要か否かは状況によって変わります。
後続の手順でpvcreate
コマンドを実行する際、対象のパーティションはアンマウントされている必要があります。
そして、今回のケースではルートファイルシステムも復旧対象に含んでいます。
ルートファイルシステムをアンマウントするために、レスキューモードの起動が必要となります。
レスキューモードに入る前に、必ず上述の#LVMメタデータのバックアップが完了していることをご確認ください。
ここでOSシャットダウンすると、ルートファイルシステムが読み込めないため、次回以降通常のOS起動ができなくなってしまいます。
レスキューモードへの入り方は過去記事に書いてあるので、そちらを参照してください。
レスキューモードからの起動
ディスクのマウントができないので、最後の起動メニューは3) Skip to shell
を選択し、ディスクをマウントせずにシェルを起動してください。
KVMを使っている方向けに補足です。
KVMを使っている場合は、OS起動順序をCD Drive優先にして、CDにLinuxインストール用のISOファイルをセットすることでISOファイルから起動することができます。
KVMの操作方法については、以下のリンクを参考にしてください。
以降の作業は、レスキューモードに入った後のウィンドウで実行します。
(任意) キーボードの日本語化
こちらの作業は任意で実行してください。
レスキューモードでは、以下のようにキーボードの言語が英字配列 (us) になっています。
日本語キーボードに慣れている方は、まずはキーボードの言語を変更しましょう。
蛇足ですが、普段私はコンソールとデスクトップ環境のキーボード設定を両方変更可能なlocalectl set-x11-keymap
ばかりを使っています。
localectl # System Locale: LANG=C.UTF-8 # VC Keymap: us # X11 Layout: n/a localectl set-keymap jp localectl # System Locale: LANG=C.UTF-8 # VC Keymap: jp # X11 Layout: n/a
(任意) SSHサーバの有効化、バックアップファイル送付
SSHサーバの有効化、SCPによるファイル送付は、任意で実行してください。
SSHサーバの有効化により、SCPによるファイル転送やSSHログインが可能となります。
パスワード無しでrootユーザにログインできてしまうので、商用環境では辞めておいた方が良いかもしれません...。
最低限、ファイアウォールやNATでガチガチに守られたサブネットで作業するなどの検討をした方が良いと思います。
私の環境は手元の検証用VMなので、気にせず有効化します。
単純にサービス起動しようとすると、sshd_config
が無いとのエラーで起動失敗します。
systemctl start sshd # Job for sshd.service failed because the control process exited with error code. # See "systemctl status sshd.service" and "journalctl -xe" for details. journalctl -e # Nov 12 08:11:34 my-vm /etc/ssh/sshd_config: No such file or directory
これに対処するため、sshd_configを用意します。
cp /etc/ssh/sshd_config.anaconda /etc/ssh/sshd_config cat /etc/ssh/sshd_config
sshdサービスを起動します。
今度はうまくいきます。
systemctl start sshd
ホストPCにLVMのバックアップを取得していた方は、SCPでファイルを送ってしまいましょう。
バックアップファイルの選択ですが、最新のバックアップファイルの場合はbackup/
配下のファイルを使用します。
2世代以上前のファイルを使いたい場合は、archive/
配下のファイルから適切なものを選択してください。
バックアップファイル名がmy_vmだったとしたときのコマンドは、以下のようになります。
レスキューモードの場合はパスワード無しでSCPできます。
scp my_vm root@x.x.x.x:/
更に、そのままSSHログインします。
ssh root@x.x.x.x
cd /
以降の操作は、SSHログインして行います。
SSHを長時間有効化することに抵抗がある場合は、systemctl stop sshd
でsshdを停止しても結構です。
(任意) 非LVM領域のマウント
非LVM領域のマウントは、任意で実施してください。
前の手順でSSHを有効化しなかった場合、別の方法でファイルを送付する必要があります。
例えば、LVMを利用していない/boot
にファイルを配置していた場合は、以下のようなコマンドで/boot
をマウントします。
環境によっては/boot
ではなく、NFSストレージや、LVMを使っていない別パーティションの領域かもしれません。
そのあたりは、環境によってアレンジしてください。
/mnt/sysroot/
は、レスキューモードで1) Continue
を選択した時などにマウント先として自動で選択される領域です。
深い意味はありませんが、何となく合わせました。
mkdir -p /mnt/sysroot/boot mount /dev/vda2 /mnt/sysroot/boot
最後に、マウントしたディスク上に、予め配置しておいたバックアップファイルがあることを確認してください。
もし/bootを一時的なファイル置き場に指定する場合は、一連の復旧作業が終わった後にゴミファイルを削除するのを忘れずに...。
PVの復旧
次に、バックアップファイルを利用してPVを再作成します。
バックアップファイルを利用しなくてもPVの再作成は可能ですが、以下の観点でバックアップファイルを使ったほうが良いと思います。
- UUIDの保持 (ただし、
--uuid
,--norestorefile
オプションの組み合わせでも可能) --restorefile
を使った場合、安全に復旧するための追加ロジックが発動する (man pvcreate--restorefile
の説明より)
コマンド実行の前に、まずはバックアップファイルを開いてPVのUUIDを確認します。
以下の例では、PVのUUIDはBPTO1p-dz0e-gM36-37ls-nGY0-cUeD-Zcmt4b
であるとわかります。
また、PVの作成先が/dev/vda3
であると再確認できます。
※PVの作成先は、事前ログのdf -Th
からも確認できます
cat my_vm # (中略) # physical_volumes { # pv0 { # id = "BPTO1p-dz0e-gM36-37ls-nGY0-cUeD-Zcmt4b" # device = "/dev/vda3" # Hint only # status = ["ALLOCATABLE"] # flags = [] # dev_size = 38612992 # 18.4121 Gigabytes # pe_start = 2048 # pe_count = 4713 # 18.4102 Gigabytes # } # } # (中略)
では、pvcreate
コマンドによってPVを復旧させます。
復旧の前に、ステータス確認とテストモード実行をしてみます。
pvdisplay # (出力なし) pvcreate --uuid "BPTO1p-dz0e-gM36-37ls-nGY0-cUeD-Zcmt4b" --restorefile my_vm /dev/vda3 -t # TEST MODE: Metadata will NOT be updated and volumes will not be (de)activated. # WARNING: Couldn't find device with uuid BPTO1p-dz0e-gM36-37ls-nGY0-cUeD-Zcmt4b. # Physical volume "/dev/vda3" successfully created.
問題なく通ったので、今度は-t
オプションを外して実際に実行します。
pvcreate --uuid "BPTO1p-dz0e-gM36-37ls-nGY0-cUeD-Zcmt4b" --restorefile my_vm /dev/vda3 # WARNING: Couldn't find device with uuid BPTO1p-dz0e-gM36-37ls-nGY0-cUeD-Zcmt4b. # Physical volume "/dev/vda3" successfully created.
成功しました。
PVの状態を確認します。
PE Sizeなどが0になっていますが、これはVG作成前であるためなので気にしないで大丈夫です。
# "/dev/vda3" is a new physical volume of "18.41 GiB" # --- NEW Physical volume --- # PV Name /dev/vda3 # VG Name # PV Size 18.41 GiB # Allocatable NO # PE Size 0 # Total PE 0 # Free PE 0 # Allocated PE 0 # PV UUID BPTO1p-dz0e-gM36-37ls-nGY0-cUeD-Zcmt4b
最後に、pvcreateコマンドの構文を紹介します。
pvcreate pv-name [options...]
今回使ったものを中心に、構文の詳細を下表にまとめます。
バックアップファイルから復旧する際は、--uuid
と--restorefile
を使います。
キーワード | 説明 |
---|---|
pv-name | PVの名前。/dev/vda3 など。pvdisplayで確認可能 |
-t, --test |
テストモード実行。 実際にはメタデータを書き込まずに終了する |
-u uuid, --uuid uuid |
PVのUUIDを明示的に指定したい場合に記載する。 --uuidを指定した場合、 --restorefile string , または--norestorefile のどちらかが必須になる |
--restorefile string | --uuid uuid とセットで指定する。string にはvgcfgbackup で取得したバックアップファイルパスを指定する。--restorefile を指定することで、PEを書き込むディスクアドレスなどが復旧前と同一になるようにPVを作成し、新たに書き込んだメタデータが通常データを上書きしないよう制御する。※バックアップファイルに pe_start などのパラメータが記録されているvgcfgbackup は、pvcreate やvgcreate などのLVM変更コマンドを実行する度に内部的に実行されている |
--norestorefile | --uuid uuid とセットで指定する。UUIDを指定しつつも、バックアップファイルを使わずにPVを作成したい時に使う |
VG,LVの復旧
VG、LVは、バックアップファイルを用いて1コマンドで復旧できます。
復旧コマンドを実行する前に状態確認とテストモード実行をしてみます。
vgdisplay # (出力なし) lvdisplay # (出力なし) vgcfgrestore -f my_vm my_vm -t # TEST MODE: Metadata will NOT be updated and volumes will not be (de)activated. # Restored volume group my_vm.
テストモード実行は問題なく通りました。
-t
オプションを外して実行し、実際に復旧させます。
vgcfgrestore -f my_vm fedora_cinnamon # Restored volume group fedora_cinnamon.
確認コマンドを実行します。
PV, VG, LV共に無事作成されました。
これにて復旧完了です。
復旧を確認できたら、再度fdisk
によるパーティション拡張に挑戦してみてください。
よろしければ、再挑戦の前にVMクローンによるバックアップもご検討ください。
pvdisplay # --- Physical volume --- # PV Name /dev/vda3 # VG Name fedora_cinnamon # PV Size 18.41 GiB / not usable 2.00 MiB # Allocatable yes # PE Size 4.00 MiB # Total PE 4713 # Free PE 41 # Allocated PE 4672 # PV UUID BPTO1p-dz0e-gM36-37ls-nGY0-cUeD-Zcmt4b vgdisplay # --- Volume group --- # VG Name fedora_cinnamon # System ID # Format lvm2 # Metadata Areas 1 # Metadata Sequence No 4 # VG Access read/write # VG Status resizable # MAX LV 0 # Cur LV 2 # Open LV 0 # Max PV 0 # Cur PV 1 # Act PV 1 # VG Size 18.41 GiB # PE Size 4.00 MiB # Total PE 4713 # Alloc PE / Size 4672 / 18.25 GiB # Free PE / Size 41 / 164.00 MiB # VG UUID RTiZsE-pO7c-2rMe-O5So-h2FA-PcFk-gz3wSi lvdisplay # --- Logical volume --- # LV Path /dev/fedora_cinnamon/root # LV Name root # VG Name fedora_cinnamon # LV UUID geKCRT-Q1TN-rJBV-zP4F-jdjI-Sucm-eichFQ # LV Write Access read/write # LV Creation host, time fedora-cinnamon, 2020-09-11 02:31:26 +0000 # LV Status available # # open 0 # LV Size 16.25 GiB # Current LE 4160 # Segments 1 # Allocation inherit # Read ahead sectors auto # - currently set to 256 # Block device 253:2 # --- Logical volume --- # LV Path /dev/fedora_cinnamon/swap # LV Name swap # VG Name fedora_cinnamon # LV UUID ZyTqNg-8MTo-JuVE-JWTi-1kfy-ZxJU-7fe812 # LV Write Access read/write # LV Creation host, time fedora-cinnamon, 2020-09-11 02:31:26 +0000 # LV Status available # # open 0 # LV Size 2.00 GiB # Current LE 512 # Segments 1 # Allocation inherit # Read ahead sectors auto # - currently set to 256 # Block device 253:3
PV拡張 & VG拡張
PVを拡張すると、対応するVGも拡張された扱いになります。
PVの拡張には、pvresize
コマンドを使用します3。
pvresize
コマンドを実行するためにPV (Physical Volume) の名前を事前に調べておきます。
PVを表示するコマンドはpvdisplay
、pvscan
、pvs
の3種類がありますが、一番見やすいpvdisplay
で表示します4。
PV名は/dev/vda3
で、現時点のサイズは18.41 GiBと認識されていることがわかります。
sudo pvdisplay # --- Physical volume --- # PV Name /dev/vda3 # VG Name fedora_my_vm # PV Size 18.41 GiB / not usable 2.00 MiB # Allocatable yes # PE Size 4.00 MiB # Total PE 4713 # Free PE 41 # Allocated PE 4672 # PV UUID BPTO1p-dz0e-gM36-37ls-nGY0-cUeD-Zcmt4b
では、pvresizeでPVサイズを拡張します。
pvresizeのSyntaxは以下の構造です。
pvresize <pv-name> [options...]
オプションは多数ありますが、代表的なものは以下の通りです。
オプション | 意味 |
---|---|
-t, --test | 実際に変更を行わず、想定結果のみ返して終了する |
--setphysicalvolumesize Size | PVのサイズを指定する。 指定しない場合は自動認識する。 基本使わない |
まずは、テストモードで実行してみます。
"1 physical volume(s) resized or updated" と出ているので、テスト実行としては成功しています。
sudo pvresize -t /dev/vda3 # TEST MODE: Metadata will NOT be updated and volumes will not be (de)activated. # Physical volume "/dev/vda3" changed # 1 physical volume(s) resized or updated / 0 physical volume(s) not resized
次は実際に変更します。
sudo pvresize /dev/vda3 # TEST MODE: Metadata will NOT be updated and volumes will not be (de)activated. # Physical volume "/dev/vda3" changed # 1 physical volume(s) resized or updated / 0 physical volume(s) not resized
pvdisplay
で確認します。
変更前のサイズは18.41 GiBでしたが、正しく23.41 GiBに拡張されました。
sudo pvdisplay # --- Physical volume --- # PV Name /dev/vda3 # VG Name my_vm # PV Size 23.41 GiB / not usable 1.98 MiB # Allocatable yes # PE Size 4.00 MiB # Total PE 5993 # Free PE 1321 # Allocated PE 4672 # PV UUID BPTO1p-dz0e-gM36-37ls-nGY0-cUeD-Zcmt4b
VGのサイズも確認します。
PV拡張後、VG Sizeも23.41 GiBになっていることがわかります。
sudo vgdisplay # --- Volume group --- # VG Name my_vm # System ID # Format lvm2 # Metadata Areas 1 # Metadata Sequence No 4 # VG Access read/write # VG Status resizable # MAX LV 0 # Cur LV 2 # Open LV 2 # Max PV 0 # Cur PV 1 # Act PV 1 # VG Size 23.41 GiB # PE Size 4.00 MiB # Total PE 5993 # Alloc PE / Size 4672 / 18.25 GiB # Free PE / Size 1321 / 5.16 GiB # VG UUID RTiZsE-pO7c-2rMe-O5So-h2FA-PcFk-gz3wSi
LV拡張 & File System拡張
LV (Logical Volume) の拡張には、lvextend
コマンドを使います5。
lvextend
に--resizefs
オプションを付与することで、ファイルシステムの拡張も同時に行えます。
ファイルシステムの同時拡張は、ext2, ext3, ext4, ReiserFS, XFSに対応しているようです (※)。
(※)
man lvextendによると、--resizefs
は裏でfsadm resize
コマンドを実行することでファイルシステムのサイズ変更を行っています。
そしてman fsadmによると、fsadmは上述のファイルシステムに対応しているようでした。
なお、lvresize
というlvextend
(拡張)とlvreduce
(縮小) を両方行えるコマンドもあります。
今回は「サイズ指定を間違えて誤って縮小し、データが破損した...」といったミスを防ぐために、lvextend
を使います。
さて、LVを拡張するために、まずはlvdisplay
によってLVの名前を調べておきます。
他にもlvs
、lvscan
といった同様のコマンドがありますが、ほぼ見た目しか変わりません。
コマンド出力より、今回拡張したいLVの名前は、/dev/my_vm/root
であるとわかります。
また、拡張前のLV Sizeは16.25 GiBでした。
sudo lvdisplay # --- Logical volume --- # LV Path /dev/my_vm/root # LV Name root # VG Name my_vm # LV UUID geKCRT-Q1TN-rJBV-zP4F-jdjI-Sucm-eichFQ # LV Write Access read/write # LV Creation host, time my-vm, 2020-09-11 11:31:26 +0900 # LV Status available # # open 1 # LV Size 16.25 GiB # Current LE 4160 # Segments 1 # Allocation inherit # Read ahead sectors auto # - currently set to 256 # Block device 253:0 # --- Logical volume --- # LV Path /dev/my_vm/swap # LV Name swap # VG Name my_vm # LV UUID ZyTqNg-8MTo-JuVE-JWTi-1kfy-ZxJU-7fe812 # LV Write Access read/write # LV Creation host, time my-vm, 2020-09-11 11:31:26 +0900 # LV Status available # # open 2 # LV Size 2.00 GiB # Current LE 512 # Segments 1 # Allocation inherit # Read ahead sectors auto # - currently set to 256 # Block device 253:1
次に、LVを拡張します。
lvextend
の構文は、以下のとおりです。
lvextend [options...] LV-name [PV-name]
主なオプションの意味は、下表のとおりです。
LVのサイズは--extents
と--size
の2通りの指定方法がありますが、今回の場合は--extents +100%FREE
を使うことで、LVの空き容量を全てroot
LVに追加で割り当てます。
VGの空き領域などは、vgdisplay
で確認できます。
もちろん、vgdisplay
で確認したFREE PE / Size
の値を参考に、--size
で指定しても問題ありません。
PV-name
は、--extentsでPE (Physical Extent) を利用したサイズ指定を行う場合や、%PVS
を使う際にPE Sizeを特定する際に必要となります。
オプション | 意味 |
---|---|
-l size, --extents size |
拡張後のLVのサイズ。 数値のみ記載した場合、LE (Logical Extent) 数での指定となる。 他に % を後置した動的な指定も可能。・ %VG : VGの総容量・ %FREE : VGの空き容量・ %PVS : 指定したPVの空き容量・ %ORIGIN : スナップショット元 (Original) のVGの合計サイズ(LVM Snapshot領域のLVに対して使う) + か- を先頭に付けると、今のLV Sizeに対する相対値になる。-L, --size と併用すると、size が上限値となる例1: -l 100%FREE でVGの空き領域を全て割り当て例2: -l +100%FREE でVGの空き領域を現状のLV Sizeに上乗せして割り当て |
-L size, --size size |
拡張後のLVのサイズ。 単位としてbBsSkKmMgGtTpPeEが使える。 bBはByte, sSはセクタ, kKは1024Bといった意味。 +か-をつけると、今のLV Sizeに対する相対値になる。 -L, --size の代わりに-l ,--extents を使ってもよい |
-r, --resizefs |
ファイルシステムのサイズ変更も同時に行う。 ext2, ext3, ext4, ReiserFS, XFSに対応。 詳細はman fsadmを参照 |
-t, --test |
テストモード実行になる。 LVMのメタデータを書き込まずに成功扱いで終了する。 -rを指定すると、 fsadm --dry-run も内部的に実行してくれる。lvreduceの場合は fsadm --dry-run の実行は行わないので注意(参考) |
-v, --verbose |
より詳細な情報を画面出力する。 -vを複数指定するとより詳細に出力する (最大4回) |
-d, --debug |
syslogにも結果を出力する。 -dを複数指定するとより詳細に出力する (最大6回) |
まずはテストモードで実行してみます。
無事に21.41 GiBまで拡張できそうです。
sudo lvextend -t -r -l +100%FREE /dev/my_vm/root TEST MODE: Metadata will NOT be updated and volumes will not be (de)activated. Size of logical volume my_vm/root changed from 16.25 GiB (4160 extents) to 21.41 GiB (5481 extents). Logical volume my_vm/root successfully resized.
-v
オプション付きでテストモード実行してみます。
後半でfsadm --dry-run
が実行され、さらにfsadm
が内部的にresize2fs
コマンドを呼んでいるところまで読み取れます。
理解が深まりますね。
sudo lvextend -t -r -l +100%FREE /dev/my_vm/root -v TEST MODE: Metadata will NOT be updated and volumes will not be (de)activated. Converted 100%FREE into at most 1321 physical extents. Executing: /usr/sbin/fsadm --dry-run --verbose check /dev/my_vm/root fsadm: "ext4" filesystem found on "/dev/mapper/my_vm-root". fsadm: Skipping filesystem check for device "/dev/mapper/my_vm-root" as the filesystem is mounted on / /usr/sbin/fsadm failed: 3 Test mode: Skipping archiving of volume group. Extending logical volume my_vm/root to up to 21.41 GiB Size of logical volume my_vm/root changed from 16.25 GiB (4160 extents) to 21.41 GiB (5481 extents). Test mode: Skipping backup of volume group. Logical volume my_vm/root successfully resized. Executing: /usr/sbin/fsadm --dry-run --verbose resize /dev/my_vm/root 22450176K fsadm: "ext4" filesystem found on "/dev/mapper/my_vm-root". fsadm: Device "/dev/mapper/my_vm-root" size is 17448304640 bytes fsadm: Parsing tune2fs -l "/dev/mapper/my_vm-root" fsadm: Resizing filesystem on device "/dev/mapper/my_vm-root" to 22988980224 bytes (4259840 -> 5612544 blocks of 4096 bytes) fsadm: Dry execution resize2fs /dev/mapper/my_vm-root 5612544
さて、テスト実行に成功したので、実際にLVを拡張します。
テストモード実行時のコマンドから-t
オプションを外して実行します。
ログ出力を見るに、LV、ファイルシステム共に正しく拡張されたようです。
sudo lvextend -r -l +100%FREE /dev/my_vm/root # Size of logical volume my_vm/root changed from 16.25 GiB (4160 extents) to 21.41 GiB (5481 extents). # Logical volume my_vm/root successfully resized. # resize2fs 1.45.5 (07-Jan-2020) # Filesystem at /dev/mapper/my_vm-root is mounted on /; on-line resizing required # old_desc_blocks = 3, new_desc_blocks = 3 # The filesystem on /dev/mapper/my_vm-root is now 5612544 (4k) blocks long.
拡張後のLVとファイルシステムの状態をそれぞれ確認します。
いずれも21GiBに拡張されていることが読み取れました。
sudo lvdisplay /dev/my_vm/root # --- Logical volume --- # LV Path /dev/my_vm/root # LV Name root # VG Name my_vm # LV UUID geKCRT-Q1TN-rJBV-zP4F-jdjI-Sucm-eichFQ # LV Write Access read/write # LV Creation host, time my-vm, 2020-09-11 11:31:26 +0900 # LV Status available # # open 1 # LV Size 21.41 GiB # Current LE 5481 # Segments 2 # Allocation inherit # Read ahead sectors auto # - currently set to 256 # Block device 253:0 df -Th # Filesystem Type Size Used Avail Use% Mounted on # (中略) # /dev/mapper/my_vm-root ext4 21G 14G 6.7G 67% / # (中略)
以上でディスク拡張は無事完了です。
最後に補足ですが、lvextend
に-r, --resizefs
を指定しなかった場合、LV拡張後に手動でファイルシステムの拡張コマンドを実行する必要があります。
EXT4の場合、手動実行のコマンドは、以下のいずれかになります。
# sudo fsadm resize /dev/my_vm/root # sudo resize2fs /dev/my_vm/root
基本的には、lvextend -r
を使うのが簡単でおすすめです。
-r
を付けるのを忘れてしまった場合は、fsadm
がファイルシステムの違いを抽象化してくれる上に-n
でテスト実行もできるので良いと思います。
resize2fs
は、Fedoraにおいて使うことはあまりないかなと思います。
参考情報
ディスク拡張手順の説明では省略した、背景知識について補足します。
記事を書き始めた時点では私も知らず、もやもやした部分が対象です。
参考情報については、本題とは関係ないので読み飛ばしても問題ありません。
もし興味のあるトピックがあれば、拾い読みいただければと思います。
(参考) fdisk vs parted
今回はパーティション拡張にfdisk
を使いましたが、parted
を使っても良いと思います。
他にもファイルをInputとして動作する自動化向きのsfdisk
や、TUI (Table User Interface) のcfdisk
、partedのGUI版であるGPartedなどのバリエーションもあり、基本的にどれを使っても問題ないとは思います。
RHEL 8 Managing storage devicesによると、2021年11月現在においてはpartedよりもfdiskの方がサポートするパーティションタイプの種類が多いようです。
ただ、こういった情報は今後ソフトウェアがアップデートされるごとに変わっていきます。
その時々で気になった際にman
などの情報を確認し、要件にあっているか確認すると良いでしょう。
機能面で特に差がなければ、自分が慣れている方を使えば良いと思います。
fdiskもpartedのどちらも対話式のインターフェースを持ちつつも、スクリプトで自動化することも可能です6。
私はpartedとfdiskのどちらにも慣れていませんが、writeしない限り何も起こらないfdiskの方が気軽に色々試せて好みです。
使い捨てのVM上で作業しているとは言え、何度もクローンし直すのは手間ですから...。
(参考) GPTとPMBRの概要
Wikipedia - GUID Partition Tableの記事を参考に、GPTやPMBRといった用語について補足します。
GPT (GUID Partition Table) は、従来のMBR (Master Boot Record) を置き換えるものです。
GUID (Globally Unique Identifier) は、UUIDと同じ意味で、「絶対に被らない128bitの16進数」で、要するに"ID"です。
GPTは、BIOSの後継であるUEFIの仕様の一部として定義されています。
GPTとは、その名の通りPartition Tableであり、ディスク上でLVM2やファイルシステムなどを含むパーティションの前後に書き込まれたメタデータを表します。
GPTのフォーマットは、Wikipediaの図が参考になります。
図に出てくるLBA (Logical Block Address) とは、物理的なディスク上のアドレス (CHS: cylinder-head-sectorなど) を抽象化する論理アドレスです。
LBA0が先頭アドレス、LBA1が次のアドレス...といったように表記します。
(参考:Wikipedia - Logical Block Addressing)
ディスク先頭のLBA0 (ディスク製品によって512 Byteであったり、4096 Byteであったりします) にPMBR (Protective Master Boot Record) の領域が存在します。
PMBRは、従来のMBRを認識する古いプログラムが、GPTの先頭ディスク領域を上書きしてPartition Tableを破壊することを防ぐための仕組みです。
原理について補足すると、PMBRには、MBRと同様のフォーマットでデータが書き込まれています。
そして、PMBRのPartition IDには "EFI" を表すEEh
というデータを書き込まれています。
するとMBRしか認識できない古いプログラムは、後続のGPTの領域 (LBA1以降) を「不明なフォーマットの単一のパーティションが存在する」と認識し、データを書き込む前に大抵何らかの警告を出すようになります。
こうして、PMBRは古いプログラムの誤動作によるパーティションの破壊を防いでいます。
さて、ここでディスクサイズ拡張直後にfdisk -l
を実行した時のエラーメッセージについて振り返ります。
# GPT PMBR size mismatch (41943039 != 52428799) will be corrected by write. # The backup GPT table is not on the end of the device. This problem will be corrected by write.
このエラーメッセージが出る前に、ゲストOS側では何の操作もすることなく仮想ディスクファイル (qcow2) を5 GiB拡張しています。
この時、qcow2の中身は以下のようになっています。
qcow2の拡張操作は、GPTを含むディスク上のデータを一切書き換えることなく、単純にディスク容量が増えています。
これによって、以下の点で整合性が取れなくなっています。
- PMBRから読み取ったパーティションの最終セクタ番号 (=ディスクの最終セクタ) と実際のディスクの最終セクタ番号が異なっている7, 8
- Secondary GPT Headerはディスクの最後のアドレス (LBA-1) に書き込まれるのが正しいが、実際にはSecondary GPT Headerの後に空き領域がある (上述のWikipediaの図も参照)
fdiskでwriteすると、GPT (= パーティションテーブル = PMBR + Partition Header + Partition Entries) が再書き込みされます。
#パーティション拡張では、この操作によりエラーが解消されたというわけです。
(参考) 論理セクタと物理セクタ
ディスクのデータ読み書きの単位であるセクタは、物理と論理の2種類があります。
それぞれの意味は、以下のとおりです9。
- 物理セクタ: ディスクが一度のI/Oでデータを読み書きする最小単位 (atomic write)
- 論理セクタ: LBA 1ブロック分のサイズ。ディスクが受け付け可能なI/Oの最小単位
なお、LBA 1ブロックあたりのデータ容量は、論理セクタのサイズと同じです。
物理セクタと論理セクタのサイズは、ディスクが工場から出荷された段階で予めセットされています。
ディスク製品の多くは、出荷時の段階でセクタ境界にbit列を書き込み、物理セクタサイズを設定しています (LLF: Low-Level Format)。
論理セクタサイズがどのように決まるかは情報が見つかりませんでしたが、恐らく同様に製品出荷時に決まっています10。
ちなみに、製品によってはre-initialization といってユーザー側で再度フォーマットすることでセクタサイズを変更できるものもあるそうです11。
論理セクタサイズと物理セクタサイズは、fdisk
コマンドによって確認できます。
ホストマシンで実行した以下のログによると、論理セクタサイズ, 物理セクタサイズ共に512 Byte であることがわかります。
ただkernelのバージョンにも依りますが、この情報が必ずしも正しいとは限らないという話もあるようです12。
正確な情報が必要な場合は、製造メーカーのデータシートなどを参照することになりそうです。
ただセクタサイズを意識する場面はAlignmentを意識するときぐらいです (#後述)。
現時点で一番大きい4KiBやそれよりも大きい1MiB単位でAlignmentしていれば、実用上セクタサイズに対してそれほど神経質になる必要はないと思います。
sudo fdisk -l # Disk /dev/nvme0n1: 931.51 GiB, 1000204886016 bytes, 1953525168 sectors # Disk model: WDC WDS100T2B0C-00PXH0 # Units: sectors of 1 * 512 = 512 bytes # Sector size (logical/physical): 512 bytes / 512 bytes # I/O size (minimum/optimal): 512 bytes / 512 bytes
今どきのディスク製品のフォーマット (FMT) 形式は、論理セクタサイズと物理セクタサイズによって以下のように分類できます13, 14。
フォーマット名 | 論理 | 物理 |
---|---|---|
512n (512 Native) | 512 Bytes | 512 Bytes |
512e (AF, 512-byte Emulation) | 512 Bytes | 4096 Bytes |
4Kn (AF, 4KB Native) | 4096 Bytes | 4096 Bytes |
AFとはAdvanced Format の略で、物理セクタサイズを従来型の512 Bytesから4096 Bytesに増やし、ディスクの容量効率を向上させる技術のことです15。
AFに対応した製品は2010年から出荷され始めた関係で、4096 Bytesのセクタサイズに対応していないOSやプログラムが「昔は」あったようです。
2015年より前のWindows Server 2008、RHEL6、ESXi5.5などの時代の話です。
恐らく、今の段階で4K非対応を気にする必要はあまりないのではないかと思います16。
(参考) 4K Disk Alignment
概要
結論から言えば、パーティション開始位置をfdiskのデフォルトに任せつつ、パーティションサイズを1MiBの倍数で指定していれば基本問題ありません。
1MiBの倍数で指定する場合、1M Alignmentと呼ばれることもあります17。
ここでの説明だけを参照すると4KiBでも十分そうに見えるのですが、RAID5, RAID6を組んでいる場合は16KiB, 256KiBのデータストライプに合わせる必要があります。18
LVMにもAlignmentは関係します。
LVM2はデフォルトで1MiBでAlignmentを調整します。
詳しい内容は、man pvcreateに書かれています。
LVMを使う場合は、1MiB単位でAlignmentを揃えるのが良さそうです。
さらに別の話題としてSSDのErase Block Sizeに合わせると16KiB〜8MiB程度の粒度になってしまうのですが、本当にErase Block SizeとPartition開始点を合わせる必要があるのかははっきりとしていません。
業務用ストレージでSSDを使う場合は、恐らくメーカーのドキュメントなどを参照して推奨される設計を確認することになりそうですが、個人利用の範囲ではあまり気にしないようにします。
SSDについてはsuperuser - Is partition alignment to SSD erase block size pointless?にて興味深い議論がされていますので、興味のある方は読んでみてください。
上記を総合すると、「パソコン用途では基本1MiBでAlignmentを調整し、エンタープライズ用途のSSDストレージやRAID構成であればメーカーの仕様に沿って検討するのが良さそう」というのが私なりの結論です。
さて、本題の「Alignmentの理解」に入ります。
パーティションを作成する際、セクター開始位置には注意を払う必要があります。
セクター開始位置のアドレス (LBA: Logical Block Address) が4KiBの倍数でない場合、I/Oのパフォーマンスが低下する可能性があります。
2021年現在においては、ディスクのフォーマット形式が512e (物理セクタサイズ=4KiB、論理セクタサイズ=512B) の場合のみ、この問題が発生する可能性があると理解しています。
512eについては、#(参考) 論理セクタと物理セクタに記載があります。
Misalignmentによってなぜパフォーマンスが低下するのか、以下の図で説明します。
Alignmentが正しいケースと誤っているケースを比較してみましょう。
上記スライドは、File Systemのブロックサイズ (※) が4KiBの場合を想定しています。
つまり、File Systemが発行するI/O命令は必ず4KiBの倍数になります。
(※) ディスクのセクターサイズとはまた別物。多くのファイルシステムでは、デフォルト値は4096Bか512B。例えばEXT4の場合、詳細はman mke2fs
を参照。
ここで4KiBのI/Oが発生したとします。
Alignmentが適切であれば、物理ディスク上で実際に発生するI/Oは物理セクタ1つ分 (4KiB) のI/Oになります。
一方でAlignmentが適切ではない場合、物理ディスク上で物理セクタ2つにまたがってI/Oが発生してしまうため、非効率的です。
File Systemのブロックサイズ、パーティションの開始位置、物理セクタサイズに合わせてシステムを構成することで、上述のMisalignmentによるI/Oパフォーマンスの低下を防ぐことができます。
では、実際に構築する際、どうすればAlignmentを正しくできるのでしょうか?
それについては、次のセクションに記載します。
Misaligmnetを防ぐ方法
今どきのfdisk (util-linux 2.18以降。RHEL6以降に同梱) であれば、以下のやり方でパーティションを作成すればMisalignmentは起こらないようになっています19, 20。
なぜなら、fdiskは以下のように動作するためです。
上記ルールと合わせれば、各パーティションの開始セクターは必ず2048セクター (1MiB) の倍数、つまり8セクターの倍数となります。
従って、Misalignmentは起こりえません。
- 最初のパーティション開始位置は第2048セクターで固定している (512B * 2048 = 1MiB) ※util-linux 2.18以降
- 2つ目以降のパーティション開始位置は、前のパーティション終了位置の次のセクターから開始する
なお、PartedやGPartedについても同様のAlignmentへの配慮がされています21。
Misalignmentが発生しているか否かの確認方法
sudo fdisk -l
において論理セクタサイズが512 Bytes 表記の場合、各パーティションの開始セクタを8で割り切れない場合は、misalignmentが発生している可能性があります。
ディスクのフォーマット形式が512eかどうかを調べる作業は労力がかかりますので、そういったことを考えずに済むように、1MiBの倍数でセクタ開始点を定めるように意識していきたいところです。
以下にfdisk -l
の出力の一部を貼ります。
Startの部分が2048, 1230848, 3328000と並んでいます。
これらはいずれも8で割り切れます。
つまり、パーティションの開始点は4KiB (512 Bytes * 8) の倍数なので、正しく4K Alignmentされています。
更に言うと2048でも割り切れるので、1M Alignmentされています (1MiB = 512 Bytes * 2048)。
1M Alignmentは、RAIDなどを考慮に入れても対応可能で、4K Alignmentよりも更に手堅いAlignment方法です22。
sudo fdisk -l # (中略) # Units: sectors of 1 * 512 = 512 bytes # Sector size (logical/physical): 512 bytes / 512 bytes # (中略) # Device Start End Sectors Size Type # /dev/vda1 2048 1230847 1228800 600M EFI System # /dev/vda2 1230848 3327999 2097152 1G Linux filesystem # /dev/vda3 3328000 52428766 49100767 23.4G Linux LVM
まとめ
KVM仮想マシンのディスク拡張の手順を紹介しました。
LVMならではのトラブルの対処方法や、GPTやAlignmentの予備知識を参考情報として盛り込んだことで、内容が大変盛りだくさんとなりました。
目次を活用して、必要な情報を拾って読んでいただければと思います。
-
Unix & Linux - How to calculate partition Start End Sector?↩
-
Red Hat - RHEL8 - Configuring and managing logical volumes - 19.5. Restoring metadata on an LVM physical volume↩
-
Red Hat - RHEL8 - Configuring and managing logical volumes - 7.3. Resizing an LVM physical volume↩
-
Red Hat - RHEL8 - Configuring and managing logical volumes - 3.1. Creating LVM physical volume↩
-
Red Hat - RHEL8 - Configuring and managing logical volumes - 5.1. Growing a logical volume and file system↩
-
Red Hat Customer Portal - Tool Battle Royale - FDISK vs. PARTED ※fdiskをシェルスクリプトで自動化している方もいました↩
-
WD Community - SN550 - Why it uses 512B sector instead of 4096? ※WD製やIntel製SSDの例↩
-
IBM - Linux on 4 KB sector disks: Practical advice - #Determining physical sector size↩
-
IBM - Linux on 4 KB sector disks: Practical advice #Determining physical sector size↩
-
libblkid, or why you don’t need to worry about 4K disk format↩
-
IBM - Linux on 4 KB sector disks: Practical advice #The fdisk family↩
-
IBM - Linux on 4 KB sector disks: Practical advice #The libparted library↩