系統冷啟動完整流程 (12 步)
- 電源穩定 → Power Good 信號 → CPU 釋放 RESET。
- 執行 BIOS 入口
0xFFFF0 (JMP 真實啟動代碼)。
- POST 加電自檢,錯誤即停,通過執行
INT 19h (Bootstrap Loader)。
- 尋找並執行顯卡 BIOS → 顯示首屏信息。
- 執行所有設備 BIOS (軟驅、硬碟、網卡等)。
- 顯示 BIOS 啟動信息 (版本、日期、OEM Logo 等)。
- 額外檢測 (記憶體計數等)。
- 探測所有硬體,顯示硬碟/光驅參數。
- 給出已知硬體列表 (ESCD/ACPI 表)。
- 按啟動順序尋找驅動器,讀取啟動扇區 (0 柱面 0 磁頭 1 扇區)。
- 將 512 字節啟動扇區載入內存
0000:7C00,跳轉執行。
- 找不到啟動設備 → 報錯
No boot device / NO ROM BASIC 停機。
熱啟動 (Ctrl+Alt+Del) 從第 8 步開始。
MBR 結構佈局 (512 字節)
| 偏移 | 長度 | 內容 |
| 0x0000 | 446 字節 | MBR 程式代碼 (啟動引導代碼) |
| 0x01BE | 64 字節 | 分區表 (4 項 × 16 字節) |
| 0x01FE | 2 字節 | 結束標誌 55 AA |
分區表項目結構 (16 字節/項)
| 偏移 | 字段 | 說明 |
| 0 | Boot Indicator | 80h=啟動分區 (活動分區),00h=非啟動 |
| 1-3 | Starting CHS | 起始磁柱/磁頭/扇區 (舊模式) |
| 4 | System ID | 分區類型 (05=擴展, 07=NTFS, 0B/0C=FAT32 LBA 等) |
| 5-7 | Ending CHS | 結束磁柱/磁頭/扇區 |
| 8-11 | Relative Sectors (LBA) | 相對起始扇區號 (LBA 起始) |
| 12-15 | Total Sectors | 分區總扇區數 |
實測 MBR 十六進制轉储與反編譯 (Maxtor 金鑽 20GB 實例)
0000: 33 C0 8E D0 BC 00 7C FB 50 07 50 1F FC BE 1B 7C 3.....|.P.P....|
0010: BF 1B 06 50 57 B9 E5 01 F3 A4 CB BE BE 07 B1 04 ...PW...........
0020: 38 2C 7C 09 75 15 83 C6 10 E2 F5 CD 18 8B 14 8B 8,|.u...........
...
01B0: 00 00 00 00 00 2C 44 63 B5 D7 B5 D7 00 00 80 01 .....,Dc........
01C0: 01 00 0B FE 7F FD 3F 00 00 00 3F 04 7D 00 00 00 ......?...?.}...
01D0: 41 FE 0C FE FF FF 7E 04 7D 00 7D 9B E5 01 00 00 A.....~.}.}.....
01F0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 55 AA ..............U.
關鍵代碼邏輯解讀 (反編譯自 0000:7C00)
; 初始化段寄存器與堆疊
XOR AX,AX ; AX=0
MOV SS,AX ; SS=0
MOV SP,7C00h ; SP=7C00h
STI ; 開中斷
PUSH AX; POP ES ; ES=0
PUSH AX; POP DS ; DS=0
CLD ; 字串操作方向: 遞增
MOV SI,7C1Bh ; 源: MBR 原始位置
MOV DI,061Bh ; 目的: 0000:0600h
MOV CX,01E5h ; 長度: 446+64+2=512? 實為 0x1E5=485 字節
REP MOVSB ; 將 MBR 從 7C00h 複製到 0600h
RETF ; 遠跳轉到 0000:061Bh (分區表搜尋入口)
; 分區表搜尋主循環 (PARTITION_SEARCH_LOOP)
MOV SI,07BEh ; SI 指向分區表起始 (07BEh = 01BEh 相對 0600h)
MOV CL,04h ; 循環 4 次 (最多 4 主分區)
CMP [SI],CH ; 比較 Boot Indicator 與 CH(=0)
JL ACTIVE_FOUND ; 若 <0 (無符號視為 80h>0) 則找到活動分區
JNZ INVALID_TABLE; 若 !=0 且非 80h → 無效分區表
ADD SI,10h ; 下一項 (16 字節)
LOOP SEARCH_LOOP ; 循環
INT 18h ; 4 項均無活動分區 → INT 18h (無盤啟動鉤子)
ACTIVE_FOUND:
MOV DX,[SI] ; DX=Boot Indicator (80h)
MOV BP,SI ; BP=活動分區表項地址
; 唯一活動分區檢查循環 (ONLY_ONE_ACTIVE...)
ADD SI,10h; DEC CX; JZ GOOD_TABLE
CMP [SI],CH; JZ ONLY_ONE_LOOP ; 還有 80h → 無效表
INVALID_TABLE:
MOV SI,0710h ; 錯誤信息地址
HANG_LOOP: DEC SI
DISP_LOOP: LODSB; CMP AL,0; JZ HANG_LOOP
MOV BX,0700h; MOV AH,0Eh; INT 10h ; 顯示錯誤字符
JMP DISP_LOOP ; 死循環掛起
GOOD_TABLE:
MOV [BP+25h],AX ; 臨時變量清零
XCHG SI,AX ; SI=0
MOV AL,[BP+04h] ; AL=System ID (分區類型)
MOV AH,06h
CMP AL,0Eh ; 類型 0Eh: WIN95 FAT16 LBA
JZ TYPE_WIN95_FAT16_LBA
MOV AH,0Bh
CMP AL,0Ch ; 類型 0Ch: WIN95 FAT32 LBA
JZ TYPE_WIN95_FAT32_LBA
CMP AL,AH ; 類型 0Bh: WIN95 FAT32
JNZ TYPE_DEFAULT
INC AX ; AX=0B0Ch
TYPE_WIN95_FAT32_LBA:
MOV BYTE [BP+25h],06h
JNZ TYPE_DEFAULT ; (此處原代碼邏輯存疑)
TYPE_WIN95_FAT16_LBA:
MOV BX,0AA55h
PUSH AX
MOV AH,41h
INT 13h ; 檢測 INT 13h 擴展功能 (EDD)
POP AX
JB INT13_UNSUPP ; CF=1 不支援
CMP BX,0AA55h ; BX!=AA55 不支援
JNZ INT13_UNSUPP
TEST CL,01h ; CL bit0=1 支援
JZ INT13_UNSUPP
MOV AH,AL ; AH=0Eh (支援 EDD 類型標記)
MOV [BP+24h],DL ; 保存驅動器號
MOV WORD [06A1h],1EEBh ; 自修改代碼跳轉新位置
INT13_UNSUPP:
MOV [BP+04h],AH ; 不支援 EDD 時類型設 06h (FAT16>32M) 或 0Eh
TYPE_DEFAULT:
MOV DI,000Ah
READ_SECTOR_LOOP:
MOV AX,0201h ; INT 13h AH=02h 讀扇區 AL=1
... (後續讀取 VBR 並跳轉執行) ...
核心邏輯總結
- MBR 代碼將自身從
0000:7C00 移至 0000:0600 釋放低記憶體。
- 遍歷 4 項分區表,**尋找唯一 Boot Indicator=80h 的活動分區**。
- 若無或多於一個 → 顯示錯誤信息 (通常 "Invalid partition table") 並死循環。
- 識別分區類型 (FAT12/16/32, NTFS, LBA 模式等),檢測 BIOS INT 13h 擴展功能 (EDD) 支援情況。
- 根據支援情況決定使用 CHS 或 LBA 讀取該分區首扇區 (VBR) 到
0000:7C00 並跳轉執行,完成向作業系統引導程式 (NTLDR/BOOTMGR/GRUB/LILO) 的交接。
實戰價值
- 理解 MBR 結構是修復引導失敗、手工重建分區表、分析 Bootkit 病毒的基礎。
55 AA 結束標誌缺失/錯誤 → BIOS 拒絕識別為啟動扇區。
- 分區表項 System ID 錯誤 → 系統無法識別文件系統類型。
- INT 13h EDD 支援判斷邏輯決定了大硬碟 (>8.4GB) 能否正確引導。