Chinaunix首页 | 论坛 | 博客
  • 博客访问: 35720
  • 博文数量: 17
  • 博客积分: 608
  • 博客等级: 中士
  • 技术积分: 265
  • 用 户 组: 普通用户
  • 注册时间: 2012-07-07 00:56
文章分类
文章存档

2012年(17)

我的朋友

分类: 虚拟化

2012-07-29 00:56:32

    硬盘的0柱面、0磁头、1扇区称为主引导扇区(也叫主引导记录MBR),该记录占用512个字节,它用于硬盘启动时将系统控制权转给用户指定的、在分区表中登记了某个操作系统分区。bios在执行自己固有的程序以后就会jmp到mbr中的第一条指令。MBR的内容是在硬盘分区时由分区软件写入该扇区的,MBR不属于任何一个操作系统。MBR的引导程序占了其中的前446个字节(偏移0H-偏移1BDH),随后的64个字节(偏移1BEH-偏移1FDH)为DPT(Disk PartitionTable,硬盘分区表),最后的两个字节“55 AA”(偏移1FEH-偏移1FFH)是分区有效结束标志。
    DPT有最多4个分区; 为了适应超过8G的硬盘,APO忽略了Start CHS和End CHS,而使用StartLBA和TotalSector 来确定分区在整个磁盘中的位置和大小。

分区表项结构(16字节):
; typedef struct _PARTITION_ENTRY
; {
;  BU8 BootIndicator;  // 引导指示符(BootIndicator), >=80H, 活动分区。
;  BU8 StartHead;      // 开始磁头 (Starting Head)
;  BU8 StartSector;    // 起始柱面号高2位和6位起始扇区号
;  BU8 StartCylinder;  // 起始柱面号低8位
;  BU8 PartitionType;  // 分区类型; APO为38H。
;  BU8 EndHead;        // 该分区终止磁头号
;  BU8 EndSector;      // 终止柱面号高2位和6位终止扇区号
;  BU8 EndCylinder;    // 终止柱面号低8位
;  BU32 StartLBA;      // 起始扇区号
;  BU32 TotalSector;   // 分区尺寸(总扇区数)
; }
;==================================================================================
;    主引导记录(MBR)结构
;==================================================================================
; typedef struct _MASTER_BOOT_RECORD
; {
;  BU8   BootCode[446];
;  PARTITION_ENTRY  Partition[4];
;  BU16    Signature;
; }
;====================================================================
; 扇区最后的标记字节
;====================================================================
Signature    dw 0AA55H

    分区表的每一分区的第0个字节是自举标志,其值为非0与大于等于80H时,表示该分区是当前活动分区,可引导,其值为00H时,表示该分区不可引导。
    新的INT 13服务扩展标准不再使用操作系统的寄存器传递硬盘的寻址参数,而使用存储在操作系统内存里的地址包。地址包里保存的是64位LBA地址,新的硬盘传输规范ATA 133规范使用48位的寄存器空间,支持最大128FB的硬盘空间。分区表这类数据结构的表达方式是低位在前,高位在后。因此,转换时,需将字段中的16进制数以字节为单位翻转调位置,用4个字节可以表示最大2^32个扇区,即2TB=2048GB。注:APO不支持FAT16。

主引导代码实现下列功能:

1.扫描分区表查找活动分区;

2.寻找活动分区的起始扇区;

3.将活动分区的引导扇区读到内存;

4.执行引导扇区的运行代码。

如果主引导代码未完成这些功能,系统显示下列错误信息:

Invalid partition table
Error loading operating system
Missing operating system

开机过程:
1. 开机
2. BIOS 加电自检 ( Power On Self Test -- POST ) 内存地址为 0FFFF : 0000
3. 将硬盘第一个扇区 (Boot Sector) 读入内存地址0000 : 7C00 处.
4. 检查(WORD) 0000 : 7DFE 是否等于0xAA55,若不等于则转去尝试其它启动介质如果没有其它启动介质则显示"No ROM BASIC" 然后死机.
5. 跳转到0000 : 7C00 处执行MBR 中的程序.
6. MBR 首先将自己复制到 0000 : 0600 处, 然后继续执行.
7. 在主分区表中搜索标志为活动的分区. 如果发现没有活动分区或有不止一个活动分区, 则转停止.
8. 将活动分区的第一个扇区读入内存地址 0000 : 7C00 处.
9. 检查(WORD) 0000 : 7DFE是否等于0xAA55,若不等于则显示"Missing Operating System"然后停止,或尝试软盘启动。
10. 跳转到0000 : 7C00处继续执行特定系统的启动程序.
11. 启动系统 。。。
以上步骤中 2,3,4,5 步是由 BIOS 的引导程序完成. 6,7,8,9,10步由MBR中的引导程序完成。

磁盘地址数据包 Disk Address Packet(DAP)
DAP 是基于绝对扇区地址的, 因此利用DAP, Int13H 可以轻松地逾越1024 柱面的限制, 因为它根本就不需要CHS 的概念。DAP 的结构如下:

struct DiskAddressPacket
{
 BU8  PacketSize;   // 数据包尺寸(16 字节)
 BU8  Reserved;     // ==0
 BU16 BlockCount;   // 要传输的数据块个数(以扇区为单位)
 BU32 BufferAddr;   // 传输缓冲地址(segment:offset)
 BU64 BlockNum;     // 磁盘起始绝对块地址
};

   PacketSize 保存了DAP 结构的尺寸, 以便将来对其进行扩充. 在目前使用的扩展Int13H 版本中PacketSize 恒等于16. 如果它小于16, 扩展Int13H 将返回错误码( AH=01,CF=1 ).
   BlockCount 对于输入来说是需要传输的数据块总数, 对于输出来说是实际传输的数据块个数。 BlockCount=0表示不传输任何数据块。BufferAddr 是传输数据缓冲区的32 位地址(段地址:偏移量),数据缓冲区须位于常规内存以内(1M)。BlockNum 表示的是从磁盘开始算起的绝对块地址(以扇区为单位),与分区无关。第一个块地址为0,一般来说, BlockNum 与CHS 地址的关系是:
    BlockNum = cylinder * NumberOfHeads + head * SectorsPer + sector - 1;
     其中cylinder, head, sector 是CHS 地址, NumberOfHeads 是磁盘的磁数,SectorsPerTrack 是磁盘每磁道的扇区数.也就是说BlockNum 是沿着扇区->磁道->柱面的顺序记数的. 这一顺序是由磁盘控制器虚拟的, 磁盘表面数据块的实际排列顺序可能与此不同(如为了提高磁盘速度而设置的间隔因子将会打乱扇区的排列顺序)。

在扩展Int13H 调用中一般使用如下寄存器约定:
ds:di ==> 磁盘地址数据包( disk address packet )
dl ==> 驱动器号
ah ==> 功能代码/ 返回码

    在基本Int13H 调用中, 0 - 0x7F 之间的驱动器号代表可移动驱动器0x80 - 0xFF 之间的驱动器号代表固定驱动器. 但在扩展Int13H 调用中0x80 - 0xFF 之间还包括一些新出现的可移动驱动器, 比如活动硬盘等. 这些驱动器支持先进的锁定,解锁等功能。
Ah 返回的错误码除了标准Int13H 调用规定的基本错误码以外,又增加了以下错误码:
B0h 驱动器中的介质未被锁定
B1h 驱动器中的介质已经锁定
B2h 介质是可移动的
B3h 介质正在被使用
B4h 锁定记数溢出
B5h 合法的弹出请求失败

硬盘API详解:

1) 检验扩展功能是否存在
入口: AH = 41h  ,BX = 55AAh ,DL = 驱动器号
返回: CF=0,AH=扩展功能的主版本号,AL=内部使用,BX = AA55h,CX = API 子集支持位图。
CF = 1,AH = 错误码01h, 无效命令。
    这个调用检验对特定的驱动器是否存在扩展功能. 如果进位标志置1 则此驱动器不支持扩展功能. 如果进位标志为0, 同时BX = AA55h, 则存在扩展功能。此时CX的0 位表示是否支持第一个子集, 1 位表示是否支持第二个子集。对于1.x 版的扩展Int13H来说, 主版本号AH = 1;AL 是副版本号,但这仅限于BIOS内部使用, 任何软件不得检查AL 的值。

2) 扩展读
入口: AH = 42h,DL = 驱动器号,DS:DI = 磁盘地址数据包(Disk Address Packet)
返回: CF = 0, AH = 0 成功;CF = 1, AH = 错误码。
    这个调用将磁盘上的数据读入内存,如果出现错误,DAP的BlockCount项中则记录了出错前实际读取的数据块个数。

3) 扩展写
入口:AH=43h,AL 0位=0关闭写校验、1打开写校验;1-7位保留,置0;DL=驱动器号。DS:DI=磁盘地址数据包(DAP)
返回: CF = 0, AH = 0 成功;CF = 1, AH = 错误码
    这个调用将内存中的数据写入磁盘. 如果打开了写校验选项, 但BIOS 不支持, 则会返回错误码AH=01h, CF=1。功能48h可以检测BIOS是否支持写校验。如果出现错误, DAP的BlockCount项中则记录了出错前实际写入的数据块个数.

4) 校验扇区
入口: AH = 44h;DL = 驱动器号;DS:DI = 磁盘地址数据包(Disk Address Packet)
返回: CF = 0, AH = 0 成功;CF = 1, AH = 错误码
    这个调用校验磁盘数据, 但并不将数据读入内存.如果出现错误, DAP 的BlockCount 项中则记录了出错前实际校验的数据块个数。

5) 锁定/解锁驱动器
入口: AH = 45h;AL = 0 锁定驱动器、= 1 驱动器解锁、= 02 返回锁定/解锁状态、
      = 03h-FFh - 保留;DL = 驱动器号。
返回: CF = 0, AH = 0 成功;CF = 1, AH = 错误码
    这个调用用来缩定指定驱动器中的介质。所有标号大于等于0x80 的可移动驱动器必须支持这个功能. 如果在支持可移动驱动器控制功能子集的固定驱动器上使用这个功能调用, 将会成功返回。驱动器必须支持最大255 次锁定, 在所有锁定被解锁之前, 不能在物理上将驱动器解锁。解锁一个未锁定的驱动器,将返回错误码AH= B0h. 如果锁定一个已锁定了255 次的驱动器,将返回错误码AH = B4h。锁定一个没有介质的驱动器是合法的。

6) 弹出可移动驱动器中的介质
入口: AH = 46h;AL = 0 保留;DL = 驱动器号
返回: CF = 0, AH = 0 成功;CF = 1, AH = 错误码
    这个调用用来弹出指定的可移动驱动器中的介质。所有标号大于等于0x80的可移动驱动器必须支持这个功能。如果在支持可移动驱动器控制功能子集的固定驱动器上使用这个功能调用,将会返回错误码AH=B2h(介质不可移动)。如果试图弹出一个被锁定的介质将返回错误码AH = B1h (介质被锁定)。如果试图弹出一个没有介质的驱动器,则返回错误码Ah = 31h (驱动器中没有介质).如果试图弹出一个未锁定的可移动驱动器中的介质, Int13h 会调用Int15h(AH=52h) 来检查弹出请求能否执行. 如果弹出请求被拒绝则返回错误码(同Int15h). 如果弹出请求被接

受,但出现了其他错误, 则返回错误码AH = B5h。

7) 扩展定位
入口: AH = 47h;DL = 驱动器号;DS:DI = 磁盘地址数据包(Disk Address Packet)
返回: CF = 0, AH = 0 成功;CF = 1, AH = 错误码
    这个调用将磁头定位到指定扇区。

8) 取得驱动器参数
入口: AH = 48h;DL = 驱动器号;DS:DI = 返回数据缓冲区地址
返回: CF = 0, AH = 0 成功;DS:DI 驱动器参数数据包地址, CF = 1, AH = 错误码
    这个调用返回指定驱动器的参数。

9) 取得扩展驱动器介质更换检测线状态
入口: AH = 49h;DL = 驱动器号
返回: CF = 0, AH = 0 介质未更换;CF = 1, AH = 06h 介质可能已更换
    这个调用返回指定驱动器的介质更换状态。这个调用与Int13h AH = 16h 子功能调用相同, 只是允许任何驱动器标号. 如果对一台支持可移动介质功能子集的固定驱动器使用此功能,则永远返回CF = 0, AH = 0.简单地将可移动介质锁定再解锁就可以激活检测线, 而无须真正更换介质。

10) Int 15h 可移动介质弹出支持
入口: AH = 52h;DL = 驱动器号
返回: CF=0,AH=0 弹出请求可能可以执行;CF=1, AH=错误码B1h 或B3h 弹出请求不能执行
    这个调用是由Int13h AH=46h 弹出介质功能调用内部使用的.



阅读(493) | 评论(0) | 转发(0) |
0

上一篇:第二十二章 建立386架构的模拟平台

下一篇:没有了

给主人留下些什么吧!~~