微机课设启动过程文档格式.docx
《微机课设启动过程文档格式.docx》由会员分享,可在线阅读,更多相关《微机课设启动过程文档格式.docx(16页珍藏版)》请在冰豆网上搜索。
按照用户指定的启动顺序进行启动(即我们经常需要用到的设置系统从哪里启动,一般默认是硬盘,如果需要安装系统,还会设置为光驱或USB设备),注意,这里是指的启动顺序,如果设置为从光驱启动,而光驱中又没有光盘的话,系统还是会接着从硬盘启动的。
微机启动过程一览表
-A100
XXXX:
XXXXMOVAX,0201(用功能号2读1个扇区)
XXXXMOVBX,1000(把读出的数据放入缓冲区的地址为CS:
1000)
XXXXMOVCX,0001(读0柱面,1扇区)
XXXXMOVDX,0080(指定第一物理盘的0磁头)
XXXXINT13
XXXXINT3
XXXX(按回车键)
-G=100
由于win7系统中这一方法并不适用,因此通过winhex软件进行引导记录的导出,以及w32dsm进行反汇编,从而得到引导记录的汇编语言程序。
0000-0088
MasterBootRecord
主引导程序
主引导
程序
0089-01BD
出错信息数据区
数据区
01BE-01CD
分区项1(16字节)
分区表
01CE-01DD
分区项2(16字节)
01DE-01ED
分区项3(16字节)
01EE-01FD
分区项4(16字节)
01FE
55
结束标志
01FF
AA
三、课程设计(综合实验)总结或结论
反汇编清单
;
;
设置栈SS:
SP=0:
7C00
0000:
7C00xorax,ax
7C02movss,ax
7C04movsp,7C00h
7C07sti
DS=ES=0
7C08pushax
7C09popes
7C0Apushax
7C0Bpopds
将后面的代码复制到低端内存,为加载
活动分区的引导扇区腾出空间,因为引导
扇区也必须加载到0:
7C0Ccld
7C0Dmovsi,7C1Bh
7C10movdi,61Bh
7C13pushax
7C14pushdi
7C15movcx,1E5h
7C18repemovsb
跳到低端内存的代码继续执行
7C1Aretf
开始扫描分区表(PartitionTable),寻找活动分区
061Bmovbp,7BEh;
600h+1BEh,分区表起始偏移为1BEh
061Emovcl,4;
分区表中有4个分区表项
loc_620:
0620cmp[bp+0],ch;
是活动分区吗?
(此时ch中的值为0)
0623jlloc_62E;
活动分区的标志是80h,如果解释成有符号数,则小于0
0625jnzloc_63A;
引导标志的合法值只能是0和80h,其它的值则出错
0627addbp,10h;
指向下一个表项(每一个表项的长度为10h字节)
062Alooploc_620;
依次扫描所有分区表项
没有发现活动分区,无法启动OS,按照规范调用Int18h
早期的BIOS的Int18h中断服务程序就是启动ROM-Basic,
现在的BIOS一般是打印错误信息
062Cint18h
找到活动分区后,还要检查剩余分区的启动标志是否为0
不允许存在多个活动分区
loc_62E:
062Emovsi,bp
loc_630:
0630addsi,10h;
下一个分区表项
0633deccx
0634jzloc_64F;
所以剩余分区都扫描完
0636cmp[si],ch;
启动标志是否为0?
0638jzloc_630;
是则合法,检查下一分区
分区启动标志不合法,打印错误信息
"
Invalidpartitiontable"
loc_63A:
063Amoval,byte_7B5
loc_63D:
063Dmovah,7
063Fmovsi,ax
loc_641:
0641lodsb
0642
loc_642:
0642cmpal,0
0644jzloc_642;
打印完错误信息后,进入死循环
0646movbx,7
0649movah,0Eh
064Bint10h;
调用Int10h显示一个字符
064Djmpshortloc_641
开始加载活动分区的引导扇区
loc_64F:
将一个标志的初始值清0。
这个标志表示是否尝试过备份的引导扇区
[bp+10h]的字节肯定是没用的空间
064Fmov[bp+10h],cl
0652callsub_69B
0655jnbloc_681
loc_657:
0657incbyteptr[bp+10h];
标志已经尝试过加载备份的引导扇区
如果活动分区是FAT32分区,尝试加载备份的引导扇区
065Acmpbyteptr[bp+4],0Bh;
FAT32
065Ejzloc_66B
0660cmpbyteptr[bp+4],0Ch;
FAT32(需用扩展Int13h访问)
0664jzloc_66B
加载引导扇区失败,显示错误信息
Errorloadingoperatingsystem"
0666moval,byte_7B6
0669jnzloc_63D
loc_66B:
FAT32的备份引导扇区号=引导扇区号+6
066Baddbyteptr[bp+2],6
066Faddwordptr[bp+8],6
0673adcwordptr[bp+0Ah],0
0677callsub_69B
067Ajnbloc_681
连备份的引导扇区也坏了,就没辙了!
067Cmoval,byte_7B6
067Fjmpshortloc_63D
在把控制权交给引导扇区前,要先检查引导扇区的签名(signature)
防止把控制权交给已经损坏的引导扇区
0681
loc_681:
0681cmpwordptrds:
[7DFEh],0AA55h;
签名就是扇区最后的2个字节
0687jzloc_694
引导扇区损坏,则尝试用备份引导扇区
0689cmpbyteptr[bp+10h],0;
已经是备份的引导扇区?
068Djzloc_657
备份引导扇区也坏了,死翘翘
068Fmoval,byte_7B7
0692jmpshortloc_63D
交权给引导扇区,让它去完成OS的引导
0694
loc_694:
0694movdi,sp;
di=sp=7C00h
0696pushds
0697pushdi
0698movsi,bp;
把活动分区表项指针传给引导扇区
069Aretf;
跳到0:
读取引导扇区的子过程
sub_69Bprocnear
069Bmovdi,5;
磁盘I/O错允许重试次数为5次
069Emovdl,[bp+0];
分区的启动标志其实就是硬盘号
06A1movah,8
06A3int13h
06A5jbloc_6CA;
如果取参数失败,认为BIOS肯定不支持扩展
Int13h;
只好用传统Int13h
计算用传统Int13h能访问的最大逻辑扇区号
计算公式为:
(最大磁头号+1)*每道扇区数*(最大磁道号+1)
注意这个计算次序是有讲究的,因为(最大磁头号+1)*每道扇区数
的结果可以用16位寄存器就可以存放。
如果先用磁道号来计算,
乘的结果就必须用两个寄存器来存放,导致第二步乘计算复杂化
06A7moval,cl
06A9andal,3Fh
06ABcbw;
ax中为第道扇区数
06ACmovbl,dh
06AEmovbh,ah;
bh=0,ah肯定为0
06B0incbx
06B1mulbx;
(最大磁头号+1)*每道扇区数
06B3movdx,cx
06B5xchgdl,dh
06B7movcl,6
06B9shrdh,cl;
dx中为(最大磁道号+1)
06BBincdx
06BCmuldx;
判断引导扇区是否可以用传统Int13h来访问
如果引导扇区的逻辑扇区号&
gt;
=刚才算出的扇区号,必须用扩展Int13h来读取
否则就用传统Int13h来访问
注意一下双字数的比较方法!
06BEcmp[bp+0Ah],dx
06C1jaloc_6E6
06C3jbloc_6CA
06C5cmp[bp+8],ax
06C8jnbloc_6E6
06CA
用传统Int13h来读引导扇区
loc_6CA:
06CAmovax,201h
06CDmovbx,7C00h
06D0movcx,[bp+2]
06D3movdx,[bp+0]
06D6int13h
06D8jnblocret_72B
读取失败可以重试,试完规定的次数后还失败就没办法了
06DAdecdi
06DBjzlocret_72B
重试前重置一下磁盘系统
06DDxorah,ah
06DFmovdl,[bp+0]
06E2int13h
06E4jmpshortloc_6CA
检查BIOS是否支持扩展Int13h
06E6
loc_6E6:
06E6movdl,[bp+0]
06E9pusha
06EAmovbx,55AAh
06EDmovah,41h
06EFint13h
06F1jbloc_729
06F3cmpbx,0AA55h
06F7jnzloc_729
06F9testcl,1;
必须支持Fixeddiskaccess这个功能子集
06FCjzloc_729
06FEpopa
扩展Int13h读扇区
06FF
loc_6FF:
06FFpusha
在栈中构造磁盘地址包(DiskAddressPacket)
0700push0
0702push0
0704pushwordptr[bp+0Ah]
0707pushwordptr[bp+8];
要读扇区的LBA地址(4个word)
070Apush0
070Cpush7C00h;
引导扇区读到0:
7C00h
070Fpush1;
读一个扇区
0711push10h;
包长度16个字节
0713movah,42h
0715movsi,sp
0717int13h
0719popa;
这里用了一个小技巧,一下子从栈中弹出8个word
(地址包刚好是8个word)
071Apopa;
这才是真正的恢复保存的通用寄存器的值
071Bjnblocret_72B
071Ddecdi;
不成功有重试的机会
注意这里也有个小技巧:
dec指令不改变CF的状态
071Ejzlocret_72B;
直到所有重试次数用完
重试前重置磁盘系统
0720xorah,ah
0722movdl,[bp+0]
0725int13h
0727jmpshortloc_6FF
loc_729:
0729popa
072Astc
locret_72B:
072Bretn
sub_69Bendp
072Cdb'
Invalidpartitiontable'
0
0744db'
Errorloadingoperatingsystem'
0763db'
Missingoperatingsystem'
07B5byte_7B5db2Ch
07B6byte_7B6db44h
07B7byte_7B7db63h
07FEdw0AA55h;
MBR的signature
--------------------------------------------------------------------------------
四、参考文献
1、《清华大学TPC—2003A实验指导书》,2006版
2、《新编16/32位微型计算机原理及应用》,李继灿主编,清华大学出版社,2008版,第四版
3、《微机原理实验指导书》,杨国田、高明明编写,校内待出版,2002年3月,第一版
附录(设计流程图、程序、表格、数据等)