EFIシステムパーティションが破損してUbuntuがbootできない

この記事では、電源ユニット交換後にUbuntuが起動しなくなった問題を、EFIシステムパーティションの再構築によって解決した過程を詳しく説明します。UEFIブートの仕組みや、Linuxシステムのトラブルシューティングに興味がある方に役立つ内容です。

## 経緯

* デスクトップ型のPCからガラガラという音がするようになり、バラしてみたところ電源ユニットが原因とわかりました。
* 新しい電源と交換をしたところなぜかUbuntuが起動できなくなりました。

## 環境

- 対象OS: Ubuntu
- ブート方式: UEFI
- 使用ツール: Ubuntu Live USB
## 結論

* EFIシステムパーティションが破損していてブートができなかった。
* EFIシステムパーティションを再構築することでブートすることが可能となった。



## 調査

### UEFI設定画面での確認

BIOS設定画面を確認したところ、HDDがSATAデバイスとして認識されていることがわかりました。

![preview.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/308715/4a177a7e-a996-0a63-2535-c261c4299344.png)

### 作業用の環境を作成

一時的にHDDの中身などを確認できるように、UbuntuのブータブルUSBを作成してUbuntuを起動させることにしました。
起動したUbuntuとHDDを接続して中身について確認をします。

### ブータブルUSBを作成

ブータブルUSBの作成はMacPCを利用して作成しました。

dd ユーティリティを使用して、`ubuntu-24.04-desktop-amd64.iso` イメージファイルを `/dev/disk4s1` デバイスに書き込みます。

### USBの確認

```bash
$mount
...省略...
/dev/disk4s1 on /Volumes/NO NAME (msdos, local, nodev, nosuid, noowners, noatime, fskit)
```

### イメージファイルの書き込み

```bash
sudo dd if=ubuntu-24.04-desktop-amd64.iso of=/dev/disk4s1 bs=256m
```

:::note
コマンドの詳細
* `dd`: データをコピーおよび変換するためのユーティリティ。
    * `if=ubuntu-24.04-desktop-amd64.iso`: 入力ファイル（ISOイメージ）。
    * `of=/dev/disk4s1`: 出力ファイル（書き込み先デバイス）。
    * `bs=256m`: コマンドが一度に読み書きするデータの単位を指定するオプション。ブロックサイズを256メガバイトに設定。
:::


```bash:出力
22+1 records in
22+1 records out
6114656256 bytes transferred in 358.868734 secs (17038699 bytes/sec)
```

:::note
出力の詳細
* `22+1 records in`: 22個の完全なブロックと1個の部分的なブロックが読み込まれた。
* `22+1 records out`: 22個の完全なブロックと1個の部分的なブロックが書き込まれた。
* `6114656256 bytes transferred in 358.868734 secs (17038699 bytes/sec)`: 6114656256バイトが358.868734秒で転送され、転送速度は17038699バイト/秒。
:::


### PCの起動

ブータブルUSBをPCに接続して`Try or Install ubuntu`でUbuntuを起動させます。インストールの案内を無視してTerminalを開き作業を行います。


### パーティション構成の確認

システムのパーティションを確認します。

```bash:デバイス確認
sudo fdisk -l
```

EFIシステムパーティション（通常FAT32で500MB程度）とUbuntuのルートパーティションを特定します。

```bash:出力(抜粋)
ディスク /dev/sdb: 1.84 TiB, 2000398934016 バイト, 3907029168 セクタ
Disk model: ST2000DM006-2DM1
単位: セクタ (1 * 512 = 512 バイト)
セクタサイズ (論理 / 物理): 512 バイト / 4096 バイト
I/O サイズ (最小 / 推奨): 4096 バイト / 4096 バイト
ディスクラベルのタイプ: gpt
ディスク識別子: 8306994D-A195-44F8-A0EA-F3B233663430

デバイス開始位置最後からセクタ サイズ タイプ
/dev/sdb1 34262177262144128M Microsoft 予約領域
/dev/sdb2 264192 1952185573 1951921382 930.8G Microsoft 基本データ
/dev/sdb3 1952186368 19532369911050624513M EFI システム
/dev/sdb4 1953236992 3907028991 1953792000 931.7G Linux ファイルシステム
```

Windowsとのデュアルブートにしているので、sdb1とsdb2はWindowsのための領域でしょう。
`/dev/sdb3`の `EFIシステム`がブートのためのパーティションです。

:::note
EFIシステムパーティション（ESP）は、UEFIファームウェアを使用するコンピュータシステムに不可欠な特別なパーティションです。このパーティションは通常、FAT32形式でフォーマットされ、100MB〜500MB程度のサイズを持ちます。
ESPの主な役割は、オペレーティングシステムの起動に必要なブートローダーやその他のEFIアプリケーションを格納することです。
UbuntuとWindowsの両方がこのESPを利用します。Ubuntuでは、GRUB2ブートローダーがESPに保存され、通常/boot/efiにマウントされます。Windows（8以降）では、Windows Boot Managerが同じESPに格納されます。
:::


ちなみに、この時点でLinux ファイルシステム(`/dev/sdb4`)の中身を除いたところデータが壊れずに保存されていることを確認しました。

### EFIパーティションのマウントと内容確認

特定したEFIパーティション(`/dev/sdb3`)をマウントし、内容を確認します。`/mnt/efi`はマウント先のディレクトリなので任意に変更して下さい。

```bash:パーティションのマウントと中身の確認
sudo mount /dev/sdb3 /mnt/efi
ls -R /mnt/efi
```

```bash:出力
'System Volume Information'
```
通常このフォルダはWindowsのメインパーティション（Cドライブなど）のルートに存在します。バックアップ情報などが保存されるものです。
誤って Windows パーティションとして認識してフォーマットされてしまった可能性があります。
理由は分かりませんが**boot用のEFIパーティションが破損したことが原因**でUbuntuが起動しなくなったことがわかりました。

## 修復手順

以下の手順で修復を試みます。

### 1. 正しいパーティションのマウント

```bash
sudo mount /dev/sdb4 /mnt  # Ubuntuのルートパーティション
sudo mount /dev/sdb3 /mnt/boot/efi  # EFIシステムパーティション
```

### 2. chroot環境の準備

```bash
for i in /dev /dev/pts /proc /sys /run; do sudo mount -B $i /mnt$i; done
sudo chroot /mnt
```

### 3. GRUBの再インストール

```bash
grub-install --target=x86_64-efi --efi-directory=/boot/efi --bootloader-id=ubuntu
update-grub
```

### 4. chroot環境からの退出とアンマウント

```bash
exit
sudo umount -R /mnt
```
## 結果

無事にUbuntuを起動することができるようになりました。ただしcronなど一部の設定が吹き飛んでいました。


## 注意事項

- データのバックアップ：重要なデータは必ずバックアップを取ってから作業を行ってください。
- 正確なデバイス名：コマンドを実行する際は、必ず自身のシステムの正確なデバイス名を使用してください。

## 参考リンク
- [Ubuntu公式ドキュメント: UEFI](https://help.ubuntu.com/community/UEFI)
- [GNU GRUB Manual](https://www.gnu.org/software/grub/manual/grub/)