Boot

Grub:只安裝 MBR 部分,不安裝引導目錄?

  • September 17, 2019

似乎我總是必須--boot-directory在使用grub-install.

如果我/boot的分區上已經有現有的 grub 文件怎麼辦?我不應該只需要安裝 grub 的 MBR 部分並將其指向我現有的分區之一/boot/grub嗎?我找不到這樣的選擇。

我已將 GPT 降級為 MBR 並刪除了我的 BIOS 引導分區,這意味著如果我沒有誤解任何內容,我需要將 Grub 重新安裝到我的 MBR。如果不這樣做,我會留下一個 grub 救援提示,在執行ls. 我意識到在將 grub 重新安裝到 MBR 後,我的菜單條目可能仍然無法工作,因為它們引用了類似的分區hd0,gpt5,但是有一個可用的提示就足夠了,它可以讓我更容易地確認我對 grub 的理解。

每當我想安裝 grub 時,我是否必須寫入 a --boot-directory,即使目錄已經存在?

當 GRUB 從 MBR 引導時,它在引導過程開始時需要採取的遺留 BIOS 兼容性步驟的數量意味著實際在 MBR 中的程式碼只能載入一個LBA 編號已修補到 MBR 的磁碟塊安裝時的程式碼。該塊通常是GRUB 核心映像的第一個塊。它包含載入更多塊的程式碼,以及定義其餘 GRUB 核心映像所在位置的塊編號列表。

在 MBR 分區的磁碟上,在 MBR 和第一個分區的開頭之間通常有未使用的空間。對於 MS-DOS,最初的約定是在下一個磁碟磁軌的開頭開始第一個分區,這通常意味著在第一個分區之前至少有 63 個磁碟塊,包括 MBR。在現代系統上,第一個 MBR 分區現在更常見地放置在距磁碟開頭正好 1MiB 的位置,即塊 #2048,以優化可能在內部使用塊的磁碟、SSD 和 SAN 儲存系統的數據對齊大小大於 512 字節。

因此,在 MBR 分區的磁碟上,磁碟的開頭通常是這樣排列的:

  • 塊#0:MBR
  • 塊 #1:GRUB 核心映像的第一個塊,包含塊列表
  • 塊 #2…#n:GRUB 核心映像的其餘部分
  • 塊 #2048:第一個分區的開始。

請注意,GRUB 核心映像的載入僅通過預先確定的塊編號進行:在完全載入和提取 GRUB 核心映像之前,GRUB 將不知道分區表或任何類型的文件系統。

在 GPT 分區磁碟上,塊 #0 之後的塊被 GPT 分區表佔用,因此 GRUB 核心映像嵌入到“BIOS 引導分區”中。這只是意味著嵌入到 MBR 中的塊編號不會是 1,而是 BIOS 引導分區的第一個塊的編號,其餘屬於核心映像的塊將同樣移位。因此,在帶有 BIOS 樣式 GRUB 的 GPT 分區磁碟上,物理佈局將是這樣的,假設 BIOS 引導分區是磁碟上的第一個分區:

  • 塊 #0:GPT 保護 MBR,嵌入了 GRUB MBR 程式碼
  • blocks #1…#(x-1):實際的 GPT 分區表
  • block #x:BIOS 引導分區的第一個塊,包含 GRUB 核心映像的第一個塊和塊列表
  • 塊 #(x+1)…#(x+n):GRUB 核心映像的其餘部分

您仍然可以進入 GRUB 救援模式這一事實表明,儘管您說您刪除了 BIOS 引導分區,但您還沒有覆蓋它的塊;儘管 BIOS 引導分區佔用的空間現在可能是分區之間的未分配空間,或者是另一個調整大小的分區中的未使用空間,但它仍然有它的舊內容,GRUB 仍然可以載入這些塊並找到它的核心映像。但是現在沒有什麼可以特別保護這些塊免於被覆蓋:一旦由於某種原因發生這種情況,GRUB 核心映像將被破壞,並且 GRUB 將無法到達救援模式。

GRUB 核心映像的內容

GRUB 核心映像包含以下內容:

  • GRUB 核心:這是進入 GRUB 救援模式在技術上唯一需要的部分。
  • 嵌入的初始 GRUB 根路徑,以指示其中包含 GRUB 配置文件和 GRUB 模組目錄的磁碟、分區和目錄。在 Linux 中,這些通常在 Linux 系統正常執行時分別/boot/grub/grub.cfg出現。/boot/grub/i386-pc
  • 一組嵌入式 GRUB 模組,至少包含用於讀取和理解分區表的程式碼以及在初始 GRUB 根路徑引用的分區上使用的文件系統類型。由於核心映像可能需要放入少於 63 個磁碟塊中,因此這組模組通常在 MBR 系統上保持盡可能少。
  • 可選地,帶有一個或多個 GRUB 命令的嵌入式 GRUB 配置文件
  • 可選,嵌入式磁碟映像,類似於memdiskSYSLINUX 引導載入程序系列的工具使用的那些
  • 可選的,用於簽署其他 GRUB 模組和作業系統核心的 GPG 公鑰以確保安全(並滿足對 GRUB 的 UEFI 版本的安全啟動接受要求)

所有這些都是 LZMA 壓縮以最小化其大小,因此無法輕鬆讀取或手動修改。

由於您現在進入救援模式並且無法列出您的分區,這表明 GRUB 核心映像包含 GPT ( part_gpt.mod) 的分區模組,但不包含 MBR ( part_msdos.mod) 的分區模組。如果沒有 MBR 分區模組,即使 GRUB 核心映像包含適用於它的文件系統驅動程序模組,它也無法訪問包含/boot/grub/i386-pc目錄的分區……因此 GRUB 無法載入normal.mod這將使您繼續超越救援模式。

現在需要做什麼

  • 可能需要將 GRUB 核心映像重寫到一個安全位置,可能是在 MBR 和第一個分區開頭之間的空間中,該空間以前被 GPT 分區表的結構佔用。由於 BIOS 引導分區已被刪除,目前位置並不安全:它可能會被重新分配到另一個分區並在將來被覆蓋而不會發出警告。
  • 在重寫 GRUB 核心映像時,需要將其中嵌入的 GPT 分區模組替換為 MBR 分區模組。由於所有組件都應該以未壓縮的形式(位於/usr/lib/grub/i386-pc或類似目錄)在手邊,因此最簡單的方法是獲取所有適當的未壓縮組件,從中建構一個新的核心映像並對其進行壓縮。解壓舊程式碼並對其進行修改是不值得的麻煩:為什麼在重用最初從頭安裝 GRUB 時使用的程式碼時編寫另一段程式碼就可以了?
  • 由於 GRUB 核心映像的位置很可能會發生變化,因此也需要重寫 MBR 程式碼。
  • grub-install命令需要以某種方式確保normal.mod位於其中的其他 GRUB 模組/boot/grub/i386-pc與新的 GRUB 核心映像具有相同的版本。當然,它可以將現有文件與它用於重建核心映像的文件集進行比較,但是再次……為什麼在簡單地/boot/grub/i386-pc用已經存在的 GRUB 安裝常式覆蓋現有內容時為另一種特殊情況編寫和調試程式碼工作得好嗎?

所有 GRUB 組件的總未壓縮大小i386-pc肯定小於 4 MiB。沒什麼。如果它已經存在,試圖避免重寫根本不值得麻煩,除非你正在使用一些特殊的東西,比如舊的第一代 PATA SSD,可用的寫入周期數非常有限。

原生 UEFI 如何做到這一點?

由於 UEFI 韌體包括 FAT32 文件系統支持作為標準,GRUB 引導載入程序的本機 UEFI 版本可以打包為grubx64.efi包含所有必要模組的單個文件,包括 normal.mod如果您願意的話。它作為正常文件載入:根本不需要在固定磁碟位置擺弄塊編號或嵌入程式碼。

引用自:https://unix.stackexchange.com/questions/542123