操作系统开发之基础知识(MBR分区表)

要在MBR的64字节分区表(偏移0x1BE-0x1FD)​中设置主分区信息,需遵循分区条目结构规范​(每个主分区占16字节),并通过汇编指令逐字段构造分区参数。以下是完整实现步骤与代码​:

一、前置知识:MBR分区表结构

MBR的分区表位于自身偏移0x1BE​(即加载到内存0x7C00后,分区表地址为0x7C00+0x1BE=0x7DDE),包含4个主分区条目​(每个16字节),或3主分区+1扩展分区。每个主分区条目字段如下(小端序):

偏移(相对于分区表)字段含义说明
0引导标志(Boot Indicator)0x80=活动分区(可引导),0x00=非活动
1起始磁头(Starting Head)磁头号(0-255)
2起始扇区(Starting Sector)扇区号(低6位,1-63)
3起始柱面(Starting Cylinder)柱面号(高2位来自偏移2,低8位来自偏移3,共10位)
4系统类型(System Type)文件系统标识(如0x0B=FAT32,0x83=EXT4,0x07=NTFS)
5结束磁头(Ending Head)结束磁头号
6结束扇区(Ending Sector)结束扇区号(低6位)
7结束柱面(Ending Cylinder)结束柱面号(高2位来自偏移6,低8位来自偏移7)
8-11起始LBA(Starting LBA)分区第一个扇区的线性地址​(4字节,小端序)
12-15扇区总数(Sector Count)分区包含的扇区数(4字节,小端序)

二、汇编代码实现:设置主分区

以下代码将两个主分区信息写入MBR分区表:

  • 分区1:​活动分区,FAT32文件系统,起始LBA0x2000(硬盘第131072扇区),大小0x1000扇区(512KB);
  • 分区2:​非活动分区,EXT4文件系统,起始LBA0x3000,大小0x2000扇区(1MB)。

1. 定义关键常量

org 0x7C00                  ; MBR加载到内存0x7C00(必须)
bits 16                     ; 实模式汇编

; 定义MBR内部分区表地址(0x7C00 + 0x1BE = 0x7DDE)
mbroffset equ 0x7C00
partition_table equ mbroffset + 0x1BE

2. 设置分区表

逐字段构造两个主分区的16字节条目:

; ------------------- 分区1:活动分区(FAT32) -------------------
; 引导标志:活动(0x80)
mov byte [partition_table + 0], 0x80
; 起始磁头:0
mov byte [partition_table + 1], 0x00
; 起始扇区:0x10(低6位),起始柱面高2位:0 → 起始柱面0x000
mov byte [partition_table + 2], 0x10
; 起始柱面低8位:0
mov byte [partition_table + 3], 0x00
; 系统类型:FAT32(0x0B)
mov byte [partition_table + 4], 0x0B
; 结束磁头:0
mov byte [partition_table + 5], 0x00
; 结束扇区:0x10,结束柱面高2位:0 → 结束柱面0x000
mov byte [partition_table + 6], 0x10
; 结束柱面低8位:0
mov byte [partition_table + 7], 0x00
; 起始LBA:0x00002000(小端序:低字节在前)
mov byte [partition_table + 8], 0x00   ; LBA低字节(2^0)
mov byte [partition_table + 9], 0x20   ; LBA中字节(2^8)
mov byte [partition_table + 10], 0x00  ; LBA高字节(2^16)
mov byte [partition_table + 11], 0x00  ; LBA最高字节(2^24)
; 扇区总数:0x00001000(4096扇区,小端序)
mov byte [partition_table + 12], 0x00
mov byte [partition_table + 13], 0x10
mov byte [partition_table + 14], 0x00
mov byte [partition_table + 15], 0x00

; ------------------- 分区2:非活动分区(EXT4) -------------------
; 引导标志:非活动(0x00)(偏移partition_table+16)
mov byte [partition_table + 16], 0x00
; 起始磁头:0
mov byte [partition_table + 17], 0x00
; 起始扇区:0x20,起始柱面高2位:0 → 起始柱面0x000
mov byte [partition_table + 18], 0x20
; 起始柱面低8位:0
mov byte [partition_table + 19], 0x00
; 系统类型:EXT4(0x83)
mov byte [partition_table + 20], 0x83
; 结束磁头:0
mov byte [partition_table + 21], 0x00
; 结束扇区:0x20,结束柱面高2位:0 → 结束柱面0x000
mov byte [partition_table + 22], 0x20
; 结束柱面低8位:0
mov byte [partition_table + 23], 0x00
; 起始LBA:0x00003000(小端序)
mov byte [partition_table + 24], 0x00
mov byte [partition_table + 25], 0x30
mov byte [partition_table + 26], 0x00
mov byte [partition_table + 27], 0x00
; 扇区总数:0x00002000(8192扇区,小端序)
mov byte [partition_table + 28], 0x00
mov byte [partition_table + 29], 0x20
mov byte [partition_table + 30], 0x00
mov byte [partition_table + 31], 0x00

3. 验证与补充

  • 分区表完整性​:若需设置4个主分区,重复上述逻辑填充partition_table+32(第三个分区)和partition_table+48(第四个分区)。
  • MBR签名​:最后需确保MBR末尾添加0xAA55签名(通常在代码末尾用times指令填充):
    times 512 - ($ - $$) db 0  ; 填充剩余字节为0
    dw 0xAA55                  ; MBR必须的签名

三、编译与测试

1. 编译MBR为二进制

用NASM编译生成mbr.bin

nasm -f bin mbr.asm -o mbr.bin

2. 写入硬盘映像

mbr.bin写入硬盘映像的LBA 0​(MBR位置):

dd if=mbr.bin of=hard_disk.img bs=512 count=1 seek=0

3. 验证分区表

用Bochs加载硬盘映像,通过info disk命令查看分区表:

bochs -f bochs.cfg  # 启动Bochs
info disk           # 查看硬盘分区信息

若输出显示两个主分区(活动分区FAT32、非活动分区EXT4),说明分区表设置成功。

关键说明

  • LBA与CHS的转换​:现代系统更依赖LBA(线性寻址),CHS字段可留空或与LBA一致(如本示例)。
  • 系统类型​:需根据内核文件系统选择正确的类型码(如EXT4是0x83,NTFS是0x07)。
  • 扇区对齐​:分区起始LBA需对齐扇区大小(512字节),避免性能问题。

通过以上代码,可在MBR分区表中正确设置主分区信息,为后续内核加载或分区管理奠定基础。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值