SSD Nodes Learn Hosting plans →
ガイド Matt Connor著者 Matt Connor

Ubuntu VPSがgrub rescue>で止まったときの直し方:原因の見分け方と恒久対策

grub rescue> は画面のエラー文で原因を絞れます。ls・set・insmod normal で今すぐ起動させる手順と、grub-install と dpkg-reconfigure grub-pc で再発を防ぐ方法を、VNCコンソールから順に解説します。

grub rescue> で止まった Ubuntu VPS は、まずエラー文を読む

Ubuntu VPS が grub rescue> で止まるのは、多くの場合、GRUB が normal モジュールを読み込めなかったからです。GNU GRUB のマニュアルも、rescue シェルだけが出る状態を「通常は normal モジュールの読み込みに失敗したことを意味する」と説明しています。このプロンプトからは、ls、set root、set prefix、insmod normal、normal の順に入力すると、手動で起動を続けられることがあります。起動できたら、grub-install と dpkg-reconfigure grub-pc でディスク上のブートコードを直し、次の再起動で同じことが起きないようにします。

この記事は、プロバイダーの管理パネルにある VNC コンソールやシリアルコンソールで、すでに grub rescue> を見ている人のための手順です。SSH はもう使えません。コンソールの開き方は カーネル更新後に VPS が起動しないときの記事 の「How do I reach the console when SSH is dead?」の節にまとめてあるので、ここでは繰り返しません。

GRUB はディスクの先頭に小さなブートコードを置き、残りのモジュールと設定ファイル grub.cfg を /boot/grub から読み込みます。この二つの片方が見つからない、または組み合わせが合わないと、GRUB は先に進めずに rescue シェルに落ちます。画面には次のような行が出ます。

Entering rescue mode...
grub rescue>

Entering rescue mode... の直前に error: で始まる行があれば、それが原因の手がかりです。最初にその行をそのままメモしてください。写真でもかまいません。

エラー文ごとに原因を分ける

以下の三種類の文字列は、どれも GRUB のソースコードに実在するエラーメッセージです。自分の画面の文言と照らし合わせてください。

error: unknown filesystem. または error: no such partition.。no such partition は GRUB のディスク処理(disk.c)が出すエラーで、GRUB が探しに行ったパーティション番号がディスク上に存在しないことを示します。unknown filesystem はファイルシステム処理(fs.c)が出すエラーで、パーティションはあっても、GRUB がその中身を読めないことを示します。どちらも、ディスクのレイアウトが GRUB の覚えている形と変わったときに出ます。たとえば、パーティションを作り直した、ディスクを別のサーバーに複製した、といった場合です。マニュアルは、GRUB が対応していない暗号化やファイルシステムは読めないとも書いています。

error: symbol 'grub_calloc' not found.。これはモジュールローダー(dl.c)のエラーで、読み込んだモジュールが必要とする関数が、ディスク先頭のブートコード側に存在しないことを意味します。grub_calloc はブートコード本体にある関数です。つまり、/boot/grub のモジュールは新しいのに、ディスク先頭のブートコードは古いまま、という食い違いが起きています。関数名は grub_calloc 以外のこともありますが、symbol と not found が並ぶ行なら同じ種類の問題です。この原因については後半で詳しく説明します。

error: file のあとにパスが続き、not found で終わる行。GRUB のファイル検索処理(fshelp.c)は、探したファイルが見つからないと、そのパスを含めて not found を報告します。パスに normal.mod が含まれていれば、GRUB はモジュールを探すディレクトリ、つまり prefix を間違った場所に向けています。このときはパーティション自体は読めているので、次の節の手順で prefix を正しい場所に向け直せば起動できる見込みが高いです。

エラー行がまったく出ずに grub rescue> だけが表示されることもあります。その場合も手順は同じです。まず set と ls で状況を見てください。

rescue シェルでできることと、できないこと

GRUB のマニュアルによると、rescue モードで通常使えるコマンドは insmod、ls、set、unset の四つだけです。ファイルを編集するコマンドも、ディスクに書き込むコマンドもありません。そのため、このプロンプトで何を入力しても、ディスクの中身は変わりません。set で変えた値はメモリ上にあるだけで、再起動すると元に戻ります。安心して試せる、ということでもあります。

マニュアルの rescue シェルの節は、normal を読み込む以外の抜け出し方を説明していません。normal がどうしても読み込めないときは、プロバイダーの管理パネルから強制リセット(電源の再投入)をしてください。これはマニュアルの手順ではなく、VPS を使う側でできる操作です。

日本語キーボードで VNC コンソールを使うときは、記号に注意してください。VNC クライアントと VPS 側でキー配列の扱いが違うと、(、)、=、/ などが、押したキーと違う文字で表示されることがあります。Enter を押す前に、画面に出ている文字が意図どおりか必ず確かめてください。

ls で /boot/grub のあるパーティションを探す

まず現在の設定を確認します。set を引数なしで実行すると、GRUB が使っている変数が表示されます。prefix と root の値を見てください。

grub rescue> set

次に ls を引数なしで実行します。マニュアルの説明どおり、GRUB が認識しているデバイスが一覧で表示されます。以下は出力の例です。あなたの画面では、ディスクの数もパーティション番号も違うはずです。

grub rescue> ls
(hd0) (hd0,gpt15) (hd0,gpt14) (hd0,gpt13) (hd0,gpt1)

hd0 は GRUB から見た 1 台目のディスクです。gpt1 は GPT(GUID パーティションテーブル)の 1 番目のパーティションを表します。古い MBR(マスターブートレコード)形式のディスクでは (hd0,msdos1) のように表示されます。マニュアル自身の例は (hd0,1) という書き方です。どの形でも、自分の ls の出力に出てきた名前をそのまま使ってください。

候補のパーティションを一つずつ調べます。ls にかっこ付きのデバイス名を渡すとファイルシステムの種類が表示され、/ で始まるパスを付けるとそのディレクトリの中身が表示されます。

grub rescue> ls (hd0,gpt1)/
grub rescue> ls (hd0,gpt1)/boot/grub/
grub rescue> ls (hd0,gpt13)/
grub rescue> ls (hd0,gpt13)/grub/

探しているのは、中に grub.cfg があるディレクトリです。エラーになるパーティションは飛ばして、次を試してください。

どこを探すべきかは、/boot が独立したパーティションかどうかで変わります。Ubuntu 公式の amd64 クラウドイメージのビルドスクリプト(livecd-rootfs)では、GPT ディスクに次のパーティションを作ります。1 番がルートファイルシステム(ラベル cloudimg-rootfs)、13 番が 1G の ext4 で /boot(ラベル BOOT)、14 番が 4M の BIOS ブートパーティション、15 番が 106M の EFI システムパーティション(vfat、ラベル UEFI、/boot/efi にマウント)です。この形なら /boot は 13 番なので、GRUB のファイルは (hd0,gpt13)/grub にあります。/boot がルートと同じパーティションにある構成なら、(hd0,gpt1)/boot/grub のような場所になります。

ただし、これは現在のビルドスクリプトの内容です。手元の 24.04 や 26.04 のイメージで確かめたものではありません。また、プロバイダーが独自に作ったイメージは、まったく違うレイアウトのことがあります。答えは常に、あなたの画面の ls の出力です。

set root、set prefix、insmod normal、normal で起動する

grub.cfg のあるディレクトリが見つかったら、root にそのパーティションを、prefix にそのディレクトリを設定します。次の例は、/boot が独立した 13 番パーティションにある場合です。デバイス名は自分の ls の結果に置き換えてください。

grub rescue> set root=(hd0,gpt13)
grub rescue> set prefix=(hd0,gpt13)/grub
grub rescue> insmod normal
grub rescue> normal

/boot がルートと同じパーティションにある場合は、こうなります。

grub rescue> set root=(hd0,gpt1)
grub rescue> set prefix=(hd0,gpt1)/boot/grub
grub rescue> insmod normal
grub rescue> normal

prefix は、GRUB がモジュールと grub.cfg を探すディレクトリです。insmod normal でエラーが出なければ、prefix は正しい場所を指しています。続けて normal を実行すると grub.cfg が読み込まれ、GRUB メニューが出るか、そのまま Ubuntu の起動が始まります。

insmod normal で error: file と not found を含む行が出る場合は、prefix がまだ違う場所を指しています。ls で別のパーティションを調べ直してください。symbol と not found の行が出る場合は、ディレクトリは正しくても、モジュールとブートコードの組み合わせが合っていません。その場合、このプロンプトから先へは進めません。次の節の方法を使います。

ここで起動できても、問題は直っていません。set の値はどこにも保存されないので、次の再起動でまた grub rescue> に戻ります。起動したら、すぐに後半の恒久対策に進んでください。

プロンプトから先に進めないときは、レスキュー環境から直す

symbol ... not found が出続ける場合や、どのパーティションにも grub.cfg が見つからない場合は、VPS の外側から作業します。プロバイダーによっては、レスキューモードや ISO イメージからの起動を管理パネルで提供しています。その環境で VPS のディスクをマウントし、chroot で中に入って grub-install を実行します。2020 年の Launchpad の報告でも、Azure や DigitalOcean の利用者がこの方法で復旧したと書いています。ただし、これは利用者の報告であり、各社の公式手順ではありません。

以下はコマンドの例です。レスキュー環境では、ディスク名が普段と違うことがあります。まず lsblk で確認し、/dev/vda や /dev/vda1 を自分のものに置き換えてください。

lsblk -o NAME,SIZE,FSTYPE,LABEL
sudo mount /dev/vda1 /mnt
sudo mount /dev/vda13 /mnt/boot
for d in dev proc sys; do sudo mount --bind /$d /mnt/$d; done
sudo chroot /mnt

/boot が独立していない構成なら、3 行目の /boot のマウントは不要です。chroot の中に入ったら、後の節と同じ grub-install と update-grub を実行します。終わったら exit で抜け、管理パネルからレスキューモードを解除して再起動します。

起動したら:GRUB をどのディスクに書くべきか確認する

恒久対策の前に、ディスクの構成と、GRUB のインストール先として記録されている値を確認します。

lsblk -o NAME,SIZE,FSTYPE,LABEL,MOUNTPOINTS
sudo debconf-show grub-pc
ls -l /dev/disk/by-id/

lsblk では、ディスク全体(例:vda、sda、nvme0n1)と、その下のパーティション(例:vda1、vda13)が区別して表示されます。

debconf-show grub-pc の出力の中で、grub-pc/install_devices の行を見てください。これが、パッケージ更新のたびに grub-install を実行する対象のデバイスです。値が /dev/disk/by-id/ のパスなら、そのパスが ls -l /dev/disk/by-id/ の一覧に本当にあるかを確かめます。存在しないパスや、パーティション(vda1 など)が入っていれば、それが原因です。ディスク先頭のブートコードが正しく更新されず、/boot/grub のモジュールだけが新しくなっていきます。

恒久対策:grub-install をディスク全体に、そして update-grub

BIOS で起動している VPS では、GRUB をパーティションではなくディスク全体に書きます。GRUB のマニュアルは「ディスク全体のデバイスへのインストールの方が通常は堅牢」と書いています。例外は、GPT の BIOS ブートパーティションのような GRUB 専用のパーティションです。Ubuntu のクラウドイメージのビルドでも、BIOS 用の GRUB はディスク全体に書かれています。

sudo grub-install /dev/vda
sudo update-grub

/dev/vda は例です。lsblk で見たディスク全体の名前を使ってください。末尾に数字の付いたパーティション名(/dev/vda1)ではありません。NVMe ディスクでは /dev/nvme0n1 がディスク全体で、/dev/nvme0n1p1 がパーティションです。24.04 の grub-install の man ページによると、ターゲットを指定しないときの既定値は i386-pc、つまり BIOS 用です。

update-grub は grub-mkconfig -o /boot/grub/grub.cfg を実行するだけのスタブです。grub.cfg を作り直しますが、ディスク先頭のブートコードには触れません。そのため、update-grub だけを実行しても symbol ... not found は直りません。必ず grub-install とセットで実行してください。

dpkg-reconfigure grub-pc でインストール先を正しく記録する

grub-install を手で実行しても、debconf に記録された grub-pc/install_devices が間違ったままなら、次の GRUB パッケージ更新でまた同じ食い違いが起きます。記録を直すには、次のコマンドを使います。

sudo dpkg-reconfigure grub-pc

いくつかの画面のあと、grub-install を自動で実行するデバイスを選ぶメニューが出ます。パッケージの説明文は、GRUB のコアイメージがモジュールや grub.cfg とずれないように、自動実行を勧めています。パーティションも選択肢に出ますが、パーティションに入れると GRUB は信頼性の低いブロックリスト方式を使うことになるので、推奨しないとも書いています。ここではディスク全体(例:/dev/vda)だけを選んでください。どのディスクが起動ディスクかわからない場合、説明文は全部のディスクに入れることを勧めています。

終わったら、もう一度確認します。

sudo debconf-show grub-pc | grep install_devices

選んだディスクが表示されていれば完了です。2020 年の Launchpad の報告には、AWS で dpkg-reconfigure を実行してもドライブを選ぶ画面が出なかったという書き込みもあります。画面が出なかった場合も、この確認で値が正しいかどうかはわかります。最後に通常どおり再起動し、コンソールで Ubuntu が起動することを確かめてください。

なぜ起きるのか:Launchpad #1889509 の事例

この問題は 2020 年 7 月 30 日に Launchpad のバグ #1889509 として報告されました。題名は symbol 'grub_calloc' not found を含むもので、画面には error: symbol 'grub_calloc' not found.、Entering rescue mode...、grub rescue> が順に表示されていました。

Julian Andres Klode さんは、同じ日のコメントで仕組みを説明しています。GRUB のインストール先として間違ったデバイスが設定されていると、grub-install はそのデバイスへの書き込みに失敗します。しかし、パッケージの更新処理全体は失敗しません。その結果、ディスクの GRUB ローダーが、/boot 側の GRUB と一致しなくなります。手作業で RAID1 に変えた場合や、ディスクを複製して GRUB を再設定しなかった場合も同じだと書いています。対策としては dpkg-reconfigure grub-pc が「おそらく直す」とし、インストール先をもう一度尋ねてくれるからだと説明しています。

スレッドには、AWS EC2、Azure、Linode、DigitalOcean の利用者からの報告が並んでいます。AWS では、新しいインスタンスの正しいデバイスは /dev/nvme0n1 だという指摘があり、報告者の debconf の値は NVMe の by-id パスでした。記録された by-id パスがいまのディスクに存在しなければ、grub-install は書き込み先を見つけられません。最初の報告は Ubuntu 16.04 で、コメントでリリースを書いている報告では 18.04 がいちばん多く、20.04 の報告もありました。DigitalOcean では Debian 10 の例もありました。これは 2020 年の記録です。24.04 や 26.04 で同じように起きるかを確かめた資料は、ここでは開いていません。

現在のパッケージも確認しました。24.04(noble)と 26.04(resolute)の grub-pc のインストール後スクリプトは、記録された各デバイスに grub-install --target=i386-pc --force --no-floppy を実行し、失敗すると grub-install failure for に続けてデバイス名を表示します。どちらのパッケージにも「GRUB failed to install to the following devices:」で始まる確認画面の文面があり、26.04 のスクリプトでは失敗時にこの画面を出します。apt upgrade の途中でこの画面やメッセージを見たら、そのまま続けずに、インストール先を見直してください。2026 年 11 月 8 日時点で、Launchpad 上の GRUB パッケージは 24.04 が 2.12-1ubuntu7.3、26.04 が 2.14-2ubuntu2.1 です。手元のバージョンは apt-cache policy grub-pc で確認できます。

UEFI で起動している VPS の場合

Klode さんは、この問題は UEFI のシステムでは起きないと書いています。UEFI の GRUB は、ディスク先頭の小さなイメージから残りを /boot から読む形ではなく、EFI システムパーティションに置かれた一つのファイルにまとまっているからです。UEFI の VPS で grub rescue> が出た場合は、上の三つのエラー文のどれに当たるかを見て、ls と set の手順から始めてください。

UEFI 用のパッケージ(grub-efi-amd64)も、更新時に --target=x86_64-efi で grub-install を実行します。26.04 のスクリプトでは、失敗しても更新を止めず、WARNING: Bootloader is not properly installed, system may not be bootable という警告を出すだけです。apt の出力にこの行があったら、再起動する前に対処してください。Ubuntu のクラウドイメージのビルドでは、UEFI 側を次のオプションでインストールしています。

sudo grub-install --target=x86_64-efi --efi-directory=/boot/efi --boot-directory=/boot --uefi-secure-boot

実行する前に、lsblk で EFI システムパーティションが /boot/efi にマウントされていることを確かめてください。--efi-directory は EFI システムパーティションのルートを指定するオプションなので、マウントされていないと正しい場所に書かれません。これはビルド用の手順をそのまま示したもので、手元の VPS で試したものではありません。

再発を防ぐ:リリースアップグレードの前にスナップショットを取る

GRUB の食い違いは、パッケージ更新の直後ではなく、次の再起動で初めて表に出ます。カーネル更新やリリースアップグレードのあとの再起動が、いちばん危ないタイミングです。作業の前に、管理パネルからスナップショットを取っておいてください。スナップショットとバックアップの違いは VPS のスナップショットとバックアップの違い で説明しています。

アップグレードの前には、sudo debconf-show grub-pc | grep install_devices で GRUB のインストール先が実在するディスク全体を指しているかも見ておきましょう。24.04 から 26.04 へ上げる手順は Ubuntu 24.04 から 26.04 へのアップグレード に、途中で止まったアップグレードの立て直し方は 失敗した Ubuntu リリースアップグレードの復旧 にまとめています。GRUB メニューまでは出るのに特定のカーネルで起動しない場合は、VPS で起動するカーネルを固定する方法 が役に立ちます。

FAQ

grub rescue> と grub> の違いは何ですか?

grub rescue> は、GRUB が normal モジュールを読み込めなかったときに出る最小限のシェルです。GNU GRUB のマニュアルによると、使えるコマンドは通常 insmod、ls、set、unset だけです。set root、set prefix で GRUB のファイルの場所を指定し、insmod normal と normal を実行すると、通常のメニューに進めることがあります。

grub rescue> から再起動するにはどうすればいいですか?

GRUB のマニュアルの rescue シェルの節は、normal を読み込む以外の抜け出し方を説明していません。normal が読み込めないときは、VPS の管理パネルから強制リセットや電源の再投入をしてください。rescue シェルにはディスクに書き込むコマンドがないので、リセットしてもディスクの中身は変わりません。

error: symbol 'grub_calloc' not found はどう直しますか?

ディスク先頭の GRUB ブートコードが古く、/boot/grub のモジュールが新しいために起きる食い違いです。2020 年の Launchpad #1889509 では、GRUB のインストール先として間違ったデバイスが記録されていたことが原因でした。レスキュー環境から chroot して、ディスク全体(例:/dev/vda)に sudo grub-install を実行し、sudo update-grub のあと sudo dpkg-reconfigure grub-pc で正しいディスクを選び直してください。

update-grub だけでは直らないのはなぜですか?

update-grub は grub-mkconfig -o /boot/grub/grub.cfg を実行して設定ファイルを作り直すだけで、ディスク先頭のブートコードには書き込みません。ブートコードとモジュールの食い違いを直すのは grub-install です。次のパッケージ更新でも正しいディスクに書かれるように、dpkg-reconfigure grub-pc で記録も直してください。

この記事は役に立ちましたか?