Windows操作系统学习之启动引导过程调试.docx
《Windows操作系统学习之启动引导过程调试.docx》由会员分享,可在线阅读,更多相关《Windows操作系统学习之启动引导过程调试.docx(26页珍藏版)》请在冰豆网上搜索。
Windows操作系统学习之启动引导过程调试
Windows操作系统学习之——启动引导过程调试
关于Windows的启动引导过程,相信很多大牛都了如指掌,这里只是将自己的学习过程分享,文章中肯定有很多理解的不是很到位的地方,还望各位牛指点。
一、MBR调试
关于MBR的调试,网上也有好多帖子了,这个帖子也只是把我的学习过程分享出来,如果可以,我会从MBR开始,一步一步的去调试,去学习Windows操作系统,同时也把这个过程分享出来。
闲话不多说了,开始进入主题。
目前用到的工具:
虚拟机:
VMware
系统:
ReactOS.0.3.15(安装win732位或者XP系统也可以用这个方法调试,这里选择ReactOS是为了后面的调试做准备)
调试工具:
IDA 首先设置虚拟机。
在VMware创建的系统文件夹下找到.vmx文件,用记事本打开,添加如下配置信息
代码:
debugStub.listen.guest32="TRUE"
debugStub.hideBreakpoints="TRUE"
bios.bootDelay="3000"
然后设置IDA。
打开IDA,Debugger-->Attach-->RemoteGDBdebugger,在弹出的对话框进行如下设置
启动虚拟机后,再点击IDA弹出的对话框的"OK"按钮,选择第一个进程,点"OK",如下图
进入调试窗口后,转到0x7c00处,按"F2"下断点,然后按"F9"运行程序,当程序断下来之后,按"Alt+s",选择16位编码,这时反汇编可能会变成一堆数据,我们只要将其选中(446个字节),然后按“C”,选择“Force”,将数据强行转换成代码即可。
接下来就开始我们的调试了,先看下面的代码
代码:
MEMORY:
7C00loc_7C00:
;CODEXREF:
MEMORY:
loc_7CAEJ
MEMORY:
7C00 cli
MEMORY:
7C01 cld
MEMORY:
7C02 xor ax,ax
MEMORY:
7C04 mov ss,ax
MEMORY:
7C06 mov ds,ax
MEMORY:
7C08 mov bp,7C00h
MEMORY:
7C0B lea sp,[bp-20h]
MEMORY:
7C0E sti
MEMORY:
7C0F mov ax,1FE0h
MEMORY:
7C12 mov es,ax
MEMORY:
7C14 assumees:
nothing
MEMORY:
7C14 mov si,bp
MEMORY:
7C16 mov di,bp
MEMORY:
7C18 mov cx,100h
MEMORY:
7C1B repmovsw ;把MBR移动到1FE0h:
7C00h处
MEMORY:
7C1D jmp farptr1FE0h:
7C22h
这段代码很简单,就是把MBR拷贝到1FE0h:
7C00h处,然后跳转到1FE0h:
7C22h继续执行。
接下来是在分区表中查找活动分区,看代码
代码:
MEMORY:
27A22loc_27A22:
;CODEXREF:
MEMORY:
7C1DJ
MEMORY:
27A22 mov ds,ax
MEMORY:
27A24 assumeds:
MEMORY
MEMORY:
27A24 mov ss,ax
MEMORY:
27A26 assumess:
MEMORY
MEMORY:
27A26 xor ax,ax
MEMORY:
27A28 mov es,ax
MEMORY:
27A2A lea di,[bp+1BEh] ;获取分区表地址
MEMORY:
27A2E test byteptr[di],80h;是否是活动分区
MEMORY:
27A31 jnz shortloc_7AA0附件6243
MEMORY:
27A33 add di,10h ;每个分区表项大小为16个字节
MEMORY:
27A36 cmp di,7DFEh ;分区表搜索是否结束
MEMORY:
27A3A jb shortloc_7A2E
这里需要对MBR有所了解才行。
MBR是磁盘的第一个扇区,占512个字节(每个扇区都是512个字节)。
前446个字节是引导代码,接下来的64个字节是分区表,共四个表项,最后两个字节是结束标志0xAA55。
分区表每个表项16个字节,第一个字节是分区标记,表示这个分区是不是活动分区(0x80为活动分区,否则为0)。
如下图所示
上面这段代码就是检测每个分区表项的第一个字节是不是0x80,如果是就跳转。
我们接下来看跳转过去的代码
代码:
MEMORY:
27AA0 call loc_7AB3
MEMORY:
27AA3 jb shortloc_7A5B
MEMORY:
27AA5 cmp es:
word_7DFE,0AA55h
MEMORY:
27AAC jnz shortloc_7A7F
MEMORY:
27AAE jmp farptrloc_7C00
跳转过来就是一个call,我们跟进去看看。
代码:
MEMORY:
27AB3 mov bx,55AAh
MEMORY:
27AB6 mov ah,41h;'A'
MEMORY:
27AB8 int 13h ;DISK-CheckforINT13hExtensions
MEMORY:
27AB8 ;BX=55AAh,DL=drivenumber
MEMORY:
27AB8 ;Return:
CFsetifnotsupported
MEMORY:
27AB8 ;AH=extensionsversion
MEMORY:
27AB8 ;BX=AA55h
MEMORY:
27AB8 ;CX=Interfacesupportbitmap
MEMORY:
27ABA jb shortloc_7AEE
MEMORY:
27ABC cmp bx,0AA55h
MEMORY:
27AC0 jnz shortloc_7AEE
MEMORY:
27AC2 test cl,1
MEMORY:
27AC5 jz shortloc_7AEE
MEMORY:
27AC7 jmp shortloc_7AD9
这里其实是检测int13h的拓展功能可不可以用,如果可用,则跳转到1FE0h:
7AD9h处,否则跳转到1FE0h:
7AEEh处。
我们先来看1FE0h:
7AEEh处的代码
代码:
MEMORY:
27AEE mov ax,204h
MEMORY:
27AF1 mov bx,7C00h
MEMORY:
27AF4 mov cx,[di+2] ;di为分区表首地址
MEMORY:
27AF7 mov dh,[di+1]
MEMORY:
27AFA int 13h ;DISK-READSECTORSINTOMEMORY
MEMORY:
27AFA ;AL=numberofsectorstoread,CH=track,CL=sector
MEMORY:
27AFA ;DH=head,DL=drive,ES:
BX->buffertofill
MEMORY:
27AFA ;Return:
CFsetonerror,AH=status,AL=numberofsectorsread
MEMORY:
27AFC retn
这里其实是使用了int13h来读取扇区数据(不是拓展功能),先来看看介绍:
int13h,ah=02h读扇区说明:
调用此功能将从磁盘上把一个或更多的扇区内容读进存贮器。
因为这是一个
低级功能,在一个操作中读取的全部扇区必须在同一条磁道上(磁头号和磁道号
相同)。
BIOS不能自动地从一条磁道末尾切换到另一条磁道开始,因此用户必须
把跨多条磁道的读操作分为若干条单磁道读操作。
入口参数:
AH=02H指明调用读扇区功能。
AL置要读的扇区数目,不允许使用读磁道末端以外的数值,也不允许
使该寄存器为0。
DL需要进行读操作的驱动器号。
DH所读磁盘的磁头号。
CH磁道号的低8位数。
CL低5位放入所读起始扇区号,位7-6表示磁道号的高2位。
ES:
BX读出数据的缓冲区地址。
返回参数:
如果CF=1,AX中存放出错状态。
读出后的数据在ES:
BX区域依次排列。
详情请参见磁盘错误状态返回码一文。
由此可知,上面的代码是读取4个扇区的数据到1FE0h:
7C00h处,读取的偏移由分区表的起始CHS确定。
接下来我们来看1FE0h:
7AD9h处的代码
代码:
MEMORY:
27AC9 db 10h
MEMORY:
27ACA db 0
MEMORY:
27ACB db 4
MEMORY:
27ACC db 0
MEMORY:
27ACD db 0
MEMORY:
27ACE db 7Ch;|
MEMORY:
27ACF db 0
MEMORY:
27AD0 db 0
MEMORY:
27AD1word_27AD1 dw0 ;DATAXREF:
MEMORY:
7CDCw
MEMORY:
27AD3word_27AD3 dw0 ;DATAXREF:
MEMORY:
loc_7CE2w
MEMORY:
27AD5 db 0
MEMORY:
27AD6 db 0
MEMORY:
27AD7 db 0
MEMORY:
27AD8 db 0
MEMORY:
27AD9;---------------------------------------------------------------------------
MEMORY:
27AD9 mov ax,[di+8]
MEMORY:
27ADC mov word_7CD1,ax
MEMORY:
27ADF mov ax,[di+0Ah]
MEMORY:
27AE2 mov word_7CD3,ax
MEMORY:
27AE5 mov ax,4200h
MEMORY:
27AE8 mov si,7CC9h
MEMORY:
27AEB int 13h ;DISK-IBM/MSExtension-EXTENDEDREAD(DL-drive,DS:
SI-diskaddresspacket)
MEMORY:
27AED retn
这里其实也是读取扇区数据,不过使用的是int13h的拓展功能来读取。
我们先来了解下int13h的拓展功能怎么读取数据
入口:
AH=42h
DL=驱动器号
DS:
SI=磁盘地址数据包(DiskAddressPacket)
返回:
CF=0,AH=0成功
CF=1,AH=错误码
这里涉及到一个结构体,我们先看这个结构体:
structDAP{
BYTE PacketSize; //数据包尺寸,固定为0x10
BYTE Reserved; //保留
WORD BlockCount; //要传输的扇区数
WORD BufferOffset; //传输缓冲区偏移地址
WORD BufferSegment; //传输缓冲区段地址
DWORD LBNLow; //要读取数据的起始扇区号低位
DWORD LBNHigh; //要读取数据的起始扇区号高位
};
这个结构体就是上面MEMORY:
27AC9开始的数据,在读取的时候,把这个结构体的地址传给si,然后调用int13h来读取。
上面这两段代码其实读取的是活动分区的引导扇区数据(每个分区的第一个扇区都分区引导扇区,这里要和MBR区分开来)。
读完之后,程序反回继续前面的call下面的代码
代码:
MEMORY:
27AA3 jb shortloc_7A5B
MEMORY:
27AA5 cmp es:
word_7DFE,0AA55h
MEMORY:
27AAC jnz shortloc_7A7F
MEMORY:
27AAE jmp farptrloc_7C00
这里其实是检测分区引导扇区是否正确读取,如果正确读取则跳转去执行分区引导扇区的代码(这里是jmpfarptrloc_7C00)。
到这里,MBR的调试就结束了,接下来我们看DBR的调试。
二、PBR调试
在开始之前,我们先来认识下PBR
点击图片以查看大图
图片名称:
DBR.jpg
查看次数:
0
文件大小:
161.3KB
文件ID:
97457
下面我们再来看下BPB和EBPB的相关介绍
BPB结构:
0x0b~0x0c:
每扇区字节数
0x0d:
每簇扇区数
0x0e~0x0f:
保留扇区数
0x10:
fat表数
0x11~0x12:
根目录项数(只有FAT12/FAT16使用此字段,FAT32此字段为0)
0x13~0x14:
小扇区数(只有FAT12/FAT16使用此字段,FAT32此字段为0)
0x15:
媒体描述符(0xf8表示硬盘,0xf0表示高密度3.5寸软盘)
0x16~0x17:
每fat扇区数(只有FAT12/FAT16使用此字段,FAT32此字段为0)
0x18~0x19:
每磁道扇区数
0x1a~0x1b:
磁头数
0x1c~0x1f:
隐藏扇区数
0x20~0x23:
总扇区数
0x24~0x27:
每fat扇区数(只被fat32使用)
0x28~0x29:
fat表镜像标志,值为0表示系统保存2份互为备份的fat表,值为1表示系统仅保存1份fat表
0x2a~0x2b:
文件系统版本(只供fat32使用)
0x2c~0x2f:
根目录簇号(只供fat32使用)
0x30~0x31:
文件系统信息扇区号(只供fat32使用)
0x32~0x33:
备份引导扇区(只供fat32使用)
0x34~0x3f:
保留
EBPB结构:
0x40:
物理驱动器号
0x41:
保留
0x42:
拓展引导标签
0x43~0x46:
分区序号
0x47~0x51:
卷标
0x52~0x59:
系统ID
接下来,我们开始调试PBR了。
在上一个帖子里,我们调玩MBR之后,程序跳转到PBR去执行,而从上面PBR的介绍可知,在开始处是一个跳转指令
代码:
MEMORY:
7C00 jmp shortnearptrunk_7C5A
我们直接看7C5A处的代码
代码:
MEMORY:
7C5A xor ax,ax
MEMORY:
7C5C mov ds,ax
MEMORY:
7C5E assumeds:
MEMORY
MEMORY:
7C5E mov es,ax
MEMORY:
7C60 assumees:
MEMORY
MEMORY:
7C60 mov ss,ax
MEMORY:
7C62 mov bp,7C00h
MEMORY:
7C65 mov sp,7C00h
MEMORY:
7C68 cmp byteptr[bp+40h],0FFh;检测磁盘物理驱动号是否正确
MEMORY:
7C6D jnz shortloc_7C73 ;判断分区文件系统是fat12/fat16还是fat32
MEMORY:
7C6F mov [bp+40h],dl
MEMORY:
7C73
MEMORY:
7C73loc_7C73:
;CODEXREF:
MEMORY:
7C6Dj
MEMORY:
7C73 cmp wordptr[bp+16h],0;判断分区文件系统是fat12/fat16还是fat32
MEMORY:
7C78 jnz shortloc_7C89 ;如果是fat12/fat16则跳转
MEMORY:
7C7A cmp dwordptr[bp+11h],0;判断分区文件系统是fat12/fat16还是fat32
MEMORY:
7C80 jnz shortloc_7C89 ;如果是fat12/fat16则跳转
MEMORY:
7C82 cmp wordptr[bp+2Ah],0
MEMORY:
7C87 jbe shortloc_7C8C ;如果是fat32则跳转
MEMORY:
7C89
MEMORY:
7C89loc_7C89:
;CODEXREF:
MEMORY:
7C78j
MEMORY:
7C89 ;MEMORY:
7C80j
ME