从扇区看USB-FDD和USB-HDD在引导时的区别

原文链接 http://www.ituring.com.cn/article/190035

这个问题其实大家在平时是不会注意到的,我也是因为最近在PC机上写系统引导程序的时候,才注意到的。

起因是这样的,我在bochs虚拟机里写了个引导程序,想移植到物理机上,大家都懂的,虚拟机是支持软驱的,操作简单方便,而且还可以创建虚拟软盘,在系统启动的时候,可以通过BIOS中断调用,写入镜像也很方便。但是,问题来了!现在已经很难搞到软驱了和软盘了,所以,最好的解决办法就是用U盘代替软盘,而且,大家现在也都这么干。于是乎,我就去网上找了找关于U盘启动相关的资料。本来以为没什么,就没把它当回事,可是,百度查出来的结果很不乐观,第一页一堆U盘引导助手什么的,显然不是咱们要的东西,不过倒是可以强读MBR,把引导扇区的数据读出来,然后反汇编,就能看出来了,但是,貌似比较耗时、费力,而且结果也不一定让人满意。那么,下一步该怎么办呢?

还是从原点出发吧!因为在BIOS的配置选项里面有启动项的设置,这个大家都是知道的。等我进入到BIOS启动项配置界面的时候,困惑就出来了,到底该用那么模式?什么是USB-FDD?什么是USB-HDD?

经过一番简单的调查以后,原来USB-FDD是模拟软盘模式,一般的软盘都可以用这个模式来启动;USB-HDD是硬盘模式,像移动硬盘什么的都可以用这种方式启动;

知道了这些,下面就该为U盘选取转化模式了。我用的磁盘管理软件是DiskGenius,这个小巧易用,如果大家手头有别的软件也可以。然后找了一个16MB大小的U盘,这个淘宝都可以买到,也就几块钱。下面先把U盘里扇区的数据全部清空。大家一定要注意,不要光格式化U盘,因为这样的话U盘里的文件系统是清空的,但是扇区里还是会残留脏数据的,这个原因如果你看过文件系统是如何操作的,那么你就会理解其中的缘由了,所以,这就是为什么误删除的文件还可以找回来的原因。

清理完U盘里的数据后,该选择启动模式了,先选USB-FDD模式吧,感觉软盘模式会简单一些。
enter image description here

要注意把更改驱动器号、扫描坏扇区、建立DOS系统几个选项勾选掉,这样才能保证扇区里是一个干净的文件系统。

至于为什么要格式化成FAT12呢?是因为它的结构比较简单,大致可以一目了然。点击转换,完成对U盘的设置及文件系统的格式化。

接下来我们看看U盘MBR(引导扇区)里的数据:

enter image description here

如果你了解引导扇区的结构,那么只要仔细观察可以看出,这个引导扇区记录和软盘的没有什么区别。如果不了解的话,那么也没关系,其实里面并不复杂,它由两部分构成:主引导记录、55AA结束标志符。读者可以很清楚的看到在0x36地址处的字符串“FAT12”和附近的一些乱码是这个文件系统的结构,如果有兴趣的读者可以到网上查一查FAT12文件系统的各项字段。值得注意的是:FAT12文件系统的开始位置一般不是从MBR 的0x36或者0x00处开始的,而是从0x03开始的,这点在读者自己学习的时候要注意,不然得到的结果就会和你已经格式化了的文件系统不一致。

对于了解磁盘结构的同学们,大家都知道软盘和硬盘都是有扇区、磁头、磁道的,但是在U盘里没有这个概念,不过呢,我在DiskGenius软件里还是获得了相关的信息,详见下图所示:

enter image description here[+]查看原图

大家可以清楚的看到,这个U盘容量16MB,2个柱面,255个磁头,每磁道63个扇区,总扇区数:32768。但是大家千万要注意,这里的数据应该是DiskGenius这个软件自己模拟的,我在写引导程序的时候,用int13 AH=2 以CHS(cylinders-heads-sectors,磁柱-磁头-扇区)寻址模式读取U盘扇区的数据是无效的,或者读出来的数据和扇区对应不上;对于出现这种问题,将在本文的后面介绍,请大家稍安勿躁。

再来看看USB-HDD模式,这个是硬盘的启动模式。同样,为了看清扇区内容,我们还是要先清空扇区里的数据。然后选择制作USB-HDD启动盘,并且创建可引导分区。使用默认的配置就可以了,作者这里的默认配置如下:

enter image description here

我们还是使用的FAT12文件系统。在完成格式化以后,让我们还是来看看MBR(引导扇区)里面的数据吧,详见下图所示:

enter image description here

如果了解引导扇区结构的朋友肯定能明白,其实硬盘的引导扇区和软盘的引导扇区还是有一定区别的;如前面提到的,软盘的引导扇区包括:引导代码和55AA结束符两部分,加在一起是512B字节;而硬盘的引导扇区包括:引导代码、硬盘分区表、55AA结束符三部分组成;把引导扇区分成三段:0~0x1BD是引导代码,0x1BE~0x1FD是硬盘分区表,一共四项每项16个字节,最后两个字节是55AA结束符。

在这里是80h,01h,01h,00h,01h,feh,3fh,01h,3fh,00h,00h,00h,43h,7dh,00h,00h看来只有一个硬盘分区,其他的硬盘分区表内容全部都是0x00,正好我们刚才只创建了一个硬盘分区,那么这16个字节都是代表什么意思呢?请参见下表:

字节位移 字段长度 字段名和定义
0 1Byte 80h 引导指示符,制定该分区是否是活动分区
1 1Byte 01h 开始磁头
2 2Byte 0001h 开始扇区和柱面
4 1Byte 01h 系统ID,定义了分区的类型
5 1Byte FEh 结束磁头
6 2Byte 013Fh 结束扇区和柱面
8 4Byte 0000,003Fh 相对扇区数,从该磁盘的开始到该分区的开始的位移量,以扇区来计算
12 4Byte 0000,7D43h 总扇区数,该分区中的扇区总数

可以与下图U盘的参数做一下简单的对照,

enter image description here[+]查看原图

0000,003Fh的十进制表示就是63,0000,7D43h的十进制表示就是32067,与起始扇区号63、总扇区数32067是一致的,至于系统ID嘛,这个算是固定的,01代表的是FAT12,05代表的是扩展分区表,linux的文件系统是83等等,这里就不多介绍了。

再让我们跳转到3fh扇区去看看,哪里的内容是什么吧!

enter image description here

我想聪明的你已经发现了,在0x7E36处也是FAT12文件系统标示符,看来我们格式化的文件系统在这里,而不是在MBR里,这就是硬盘分区表的功能,如果我们把一块硬盘只给一个系统或者分区使用,对于今天的我们,未免容量有些大,使用硬盘分区表可以把硬盘分解成4个主逻辑分区。在主逻辑分区内可以在定义扩展分区表,主分区再细分为若干个逻辑扩展分区(就是系统ID:05),这回看来跟硬盘上的结构没有什么区别了。

介绍了这么多,下面该解决前文留下的那个问题了,对于那些假的扇区、磁头、磁道参数我们该怎么办呢?

其实BIOS早就为我们解决了这个问题,对于正常的读扇区操作,使用BIOS的INT 13h AH = 02h中断即可,其中AL=要读扇区数,CH=柱面(磁道)号,CL=起始扇区号,DH=磁头号,DL=驱动器号(软驱从0开始,0:软驱A,1:软驱B;硬盘从80h开始,80h:硬盘C,81h:硬盘D)。这里在多讲一句,BIOS通过设置实现软驱引导,当我们的引导程序被执行的时候,那么我们的代码所在的软驱就是软驱A,所以代码的DL寄存器赋值0就可以,不必纠结那个软驱是A,那个软驱是B。硬盘也是一样,设置成80h即可,等到系统内核运行起来以后,磁盘的驱动程序会重新为磁盘分配磁盘设备序列号。这种模式就是传统的CHS(cylinders-heads-sectors,磁柱-磁头-扇区)寻址模式,根据相应的设置定位到具体的读取扇区上。对于传统的分扇区、磁头、磁道的磁盘设备这种操作方式没有问题,但是像U盘或者固态硬盘等没有扇区、磁头、磁道的设备我们该如何读取扇区呢?

对于这些不分扇区、磁头、磁道的设备,BIOS使用了一种新型的读写方式——LBA(Logical Block Address) ,中文名称:逻辑区块地址。这种方式可以直接使用顺序的扇区号,而不用再进行磁头,磁道,扇区的转换了。因此BIOS的INT 13h AH = 42h中断实现了读扇区的扩展,其中DL=驱动器号,这个和INT 13h AH = 02h中断的DL寄存器一样,而DS:SI指向的是一个叫做disk address packet(硬盘地址包)的结构,它的格式如下表:

Offset Size Description
00h Byte Size of packet(10h or 18h)
01h Byte Reserved(0)
02h Word Number of blocks to transfor(max 007fh for phoenix EDD)
04h DWord Transfer buffer
08h QWord Starting absolute block number
10h QWord 64-bit flat address of transfer buffer(used if DWord at 04h is FFFF:FFFFh)

这个结构有16字节和24字节两种,根据用户需要读取的地址长度而决定,作者目前使用的是在实模式下寻址4GB空间并且使用16字节的LBA寻址结构,通过BIOS的INT 13h AH = 42h中断读取扇区内容,可以使程序正常执行,并且获得正确的结果。

希望这篇文章能给你在编写引导程序方面提供一些帮助。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值