HSIAO-YANG CHEN 发布的文章

花了一天的功夫终于搞定HA-943GML-ML R261SCVX BIOS SLIC表动态寻址。

为了方便大家学习交流,也为了自己日后AWARD BIOS的修改积累思路和方法。

SLIC产生的原理:

1、SLIC依靠RSDT/XSDT表的导向作用,相当于RSDT/XSDT表的子表,也就是只要把SLIC表的32位地址,记录在RSDT/XSDT表内就可以产生SLIC表。
这是所有BIOS ACPI表子表产生的原理。静态方法也是用这个原理来产生SLIC表的。

AWARD BIOS的修改的基本思路:

1、修改ACPITBL.BIN,增加SLIC表;

2、修改ORIGINAL.BIN或GGROUP.BIN,增加SLIC表的寻址;
第1步的修改很简单就能完成,关键点在于第2步的修改。

具体步骤如下:

1、用16位编辑器打开ACPITBL.BIN,将RSDT表长度数值加4,且在表尾增加4字节的00。接下来就是SLIC表的添加,通常是在ACPITBL.BIN文件尾补足1至3个字节的 00,这是为了保证合并SLIC.BIN文件后,SLIC表头的地址能能被4整除。我的做法是SLIC紧跟RSDT表,由于SLIC为374字节,不能被4整除,将影响FACP的表头,所以在SLIC表尾增加2字节的00。
改前的截图
3edd751ex791a006345a6&690.png
改后的截图,黑色为差异处,蓝色为SLIC表,
3edd751ex791a028e7a76&690.jpg
新增的4字节为存放SLIC表的32位索引地址,偏移量为30。
2、修改ORIGINAL.BIN文件,查找RSDT,找到如下信息
3edd751ex791a07572d4a&690.png
太幸运了,前面还有刚好4字节的位置,可以放下一个表头。接下来就考虑SLIC存放的位置:
1、存放在RSDT前,将连锁影响到后面的表头索引地址偏移4字节;
2、存放在FACS后,感觉还是有点问题;(后面会提到)
3、存放在FACS前,那就是占用了FACS表头索引地址,只影响到后面的表头,比存放在RSDT前少了不少的修改,这个应该是最合适的。整个表前移4字节,由A290移到A28C,修改如图
3edd751ex791a0b5a69e9&690.png
接下来就反编译ORIGINAL.BIN,个人习惯使用hiew32进行反编译修改。
打开ORIGINAL.BIN文件,由于表由A290移到A28C,按F7,查找HEX:90A2, 来到这里
3edd751ex791a0eb08c99&690.png
按F3把A290修改A28C。由于已经增加了SLIC索引,把“MOV cx,5”姑且改为“MOV cx,6”。RSDTFACDSDTAPICMCFGFACS不是有6个表名,怎么cx寄存器才设置为5,难道FACS不在其内?带着这个疑问,继续往下。
按照前人的修改教程可知,8E44 为RSDTFACDSDTAPICMCFGFACS中RSDT表存放其索引地址的地址。
那么其他表依次存放的地址如下:

8E44  RSDT
8E48  FACP
8E4C  DSDT
8E50  APIC
8E54  MCFG
8E58  FACS
8E5C

如今我们已经新增加SLIC索引项,那么新的存放地址如下:

8E44  RSDT
8E48  FACP
8E4C  DSDT
8E50  APIC
8E54  MCFG
8E58  SLIC
8E5C  FACS
8E60

也就是SLIC占用了原先FACS的索引地址的地址,按F7查找HEX:588E
3edd751ex72829ba75add&690.png
刚好在其下,将8E58改为8E5C,A2A4正是FACS的位置,可见FACS的索引和RSDTFACDSDTAPICMCFG的索引是分开的,这也就是我选择把SLIC放于FACS前的原因,由于FACS没移位就省得改了。再按F7查找HEX:588E
3edd751ex791a186077f1&690.png
这里就是把FACS表的索引地址添加到RSDT表中,同样把8E58改为8E5C。由于FACS占用了8E5C,为了防止8E5C地址的重复使用,得再查找HEX:5C8E
3edd751ex791a1ed6faff&690.png
按F3把8E5C改为8E60,再查找HEX:608E,这次只找到毫不相关的代码。至此RSDTFACDSDTAPICMCFG重新定位寻址算是完成了,但是新增的SLIC索引地址还没加入到RSDT表中。
回到索引地址添加的地方
3edd751ex791a22f5594f&690.png
由于在ACPITBL.BIN中的RSDT表已经为SLIC表的索引地址设置好了偏移量为30的存放地址,现在只要把SLIC表的索引地址存入到RSDT表偏移30的位置处就可以完成RSDT表对SLIC表索引了。
3edd751ex791a26982923&690.png
去掉两句
or eax,eax

je 00000A4BF
这本是检验数值是否是0(空指针),以防系统崩溃的预防措施。整理得到如下代码
3edd751ex791a280310f6&690.png
到此全部修改完成。把ACPITBL.BIN和ORIGINAL.BIN替换掉原BIOS里的模块就OK了。

进入下载页面

3edd751ex7745c390e544&690.jpg
最近研究了XP启动引导文件多重启动菜单,顺手做了个XP SP3 17 OEM 大合集,集成了AMD、NVIDIA、INTEL 主板的SATA驱动和exFAT文件系统补丁,为了使光盘容量尽量小去除了XP升级方式,只能通过光盘进行全新安装。本光盘镜像使用微软的CDIMAGE进行制作,镜像文件的排放顺序应该比UltraISO更合理,安装速度更快。所有的安装文件均拷贝至MSDN最新的XPSP3光盘镜像(4个品牌激活OEMBIOS除外),安装完成的系统绝对干净。只要你的机器BIOS能通过验证,安装完成后都是激活状态,绝非修改WINLOGON.EXE、去除OEMBIOS.BI_ 达到减少光盘体积的残缺版本,最大程度上和原版保持一致,可以放心的通过Windows Updata进行升级补丁,不会因为系统补丁和正版增值更新WINLOGON.EXE造成,系统密钥验证失败的悲剧。经常给同学、朋友和同事装机的达人不妨下个备用,这个光盘对于国内品牌机器应该还是非常实用的。
进入下载页

3edd751ex76cfd0d82db1&690.jpg
3edd751ex7247fb64d523&690.jpg
这是制作完的光盘在机器上实际启动的画面,屏幕顶上还有其他非预期的提示信息在,直接造成了最后的显示信息靠在屏幕底部的囧样。于是有了美化这个想法,增加一个清屏效果。BIOS的屏显调用的是INT10中断,于是Google下相关的信息,在http://www.uv.tietgen.dk/staff/mlha/pc/Prog/ASM/INT/INT10.htm找到想要的内容
3edd751ex76cfd3306ff7&690.jpg
6:scroll up (clear screen) 就是我想要的效果,继续
3edd751ex7247fba6459b&690.jpg
清屏效果寄存器的设置,转化成堆栈代码

push       ax
push       bx
push       cx
push       dx
mov        ah,7
mov        al,0
mov        cx,0
mov        dx,0184F

mov        bh,7
int         10

pop        dx
pop        cx
pop        bx
pop        ax

有了理论基础,就开始动手修改。就在
3edd751ex76cfd5bdeeca&690.jpg,这句显示之前加清屏效果。这句就位于BOOTFIX.BIN文件中。在3edd751ex76cfd96c07d0&690.jpg找到调用3edd751ex76cfd5bdeeca&690.jpg相关的代码,修改CALL 129语句跳转到新增的代码段,结果一开始显示倒是和预期的效果一样,可是一倒计时,3edd751ex76cfd5bdeeca&690.jpg就没了。后来分析了下,随着时间的推移3edd751ex76cfd5bdeeca&690.jpg后面的“.”号依次增加,估计这条语句的调用应该是多次的,这样复杂度似乎是增加了些,对于像我这样急性子的人来说,当然要走捷径绝不绕远路。换个思维方式,干嘛不在BOOTFIX.BIN载入就来个清屏动作。于是分析文件的头部信息
3edd751ex76cfdad16976&690.jpg
,前面都是进栈操作,INT 13开始调用BIOS中断处理,于是把前一句“MOV dx,80”改成“call 3C9 ”,调用处理新增加的清屏代码,当然“MOV dx,80”还是得记得补上才行。由于清屏会使光标回到屏幕的最左上方(0,0),这样文字顶在屏幕边上也不好看,于是有查找了相关INT 10的光标位置设置
3edd751ex76cfdc14cff9&690.jpg
这样一来就完美了。

最终新增的清屏代码如下
3edd751ex76cfe1cecf3d&690.jpg
OK,做成ISO,用虚拟机测试下均正常。接下来用可重复擦写CDRW刻成光盘,放到实机上测试下
3edd751ex76cfe369943f&690.jpg
3edd751ex76cfe4bd0ed0&690.jpg
很完美和我预期的效果完全一致,屏幕上下方均保留一行,和微软原版安装光盘启动效果保持一致

近日对这个短小精悍且兼容性极佳的XP启动引导文件多重启动菜单十分感兴趣,特意还做了张17合1的XP OEM安装光盘,光盘总容量701MB。由于本人安装光盘的文字菜单部分较长,为了最大化利用有限的资源,不得不对其进行分析一番。

先看下本人已经挪位修改的目录描述
3edd751ex7247f87ead1a&690.jpg
当前起始位置为7B8,结束位置为7FD,总共70字节,去掉菜单项描述(7B8)1字节、目录字节宽度描述(7B9)1字节,剩68字节,最多可以有17个菜单项。
3edd751ex76cfb6bd06f3&690.jpg
修改 0000011C: 3A06B807 cmp al,[07B8] //指向新的菜单数描述

修改 00000126: A2B707 mov [07B7],al //指向新的临时变量地址

加亮部分简单分析:判断键盘输入的AL寄存器,是否在“A~Z”之间,通过“and al,1F”,得出一个值,当小于等于菜单数描述,就将值存入7B7H。
3edd751ex76cfb8428c9d&690.jpg

修改 0000049C: A0B707 mov al,[07B7] //取出临时变量的值,即菜单项
修改 0000049F: F626B907 mul b,[07B9] // al(菜单项)和7B9(目录字节宽度)相乘,得到偏移量,存放于ax寄存器
修改 000004A3: 05BA07 add ax,007BA //偏移量和7BA相加,得出菜单项相对应的目录名称的地址,并把这个地址存入536H,所以想把53BH菜单往前挪位,比较困难。

按照这个规律,便可弹性的调整菜单字节长度和目录长度的矛盾,轻松实现挪位操作。

前面讲的是如何去编辑启动文件,有兴趣的网友可以下个早期WIN2000的(不带SP)的启动文件,对比一下,慢慢研究。

下面讲处理启动组文件夹,先看一个图
3edd751ex78115a5152fe&690.gif
V1.6.BIN的500h行处有SETUPLDR.BINBOOTFIX.BINI386这样一个字段。告诉我们启动时要寻找I386里的这两个文件SETUPLDR.BIN和BOOTFIX.BIN。大家在做EASYBOOT时都会有run XXXX.BIN,这个XXXX.BIN(比如叫DEL1.BIN)要预先处理,修改I386为DEL1。这个I386是路径。这个在这个改过的V1.6.BIN的I386已经失去作用了,路径改过在750h行的ACE1及其后面的一些连续的四个字符,而且路径是可选择的,但我们选A(ACER)就是选ACE1路径,选B(ASUS)就是选ASU1路径,选择CDEFG。。。以此类推。

BOOTFIX.BIN干嘛用?微软的CD启动时总会有“Press any key to boot from CD”,如果不按任意键,5秒后计算机将从硬盘启动。如果按了,就从CD启动。现在如果想合集光盘也要出现“Press any key to boot from CD”,就必须从微软原版XP的I386复制一份 BOOTFIX.BIN到ACE1目录下。如果想延迟时间长一点 160h行的“49 00 12 00”,将“49”改为“AA”延时可达10秒,改为“FF”延时可达15秒。
为什么,BOOTFIX.BIN只放在ACE1,因为默认是从第一个启动组文件夹开始搜索这个BOOTFIX.BIN。

如何加载编辑好的启动文件?可以用CDIMAGE,也可以用ultraiso加载。

CDIMAGE命令行(假定你编好的V1.6.BIN在CDIMAGE文件夹里,而XPCD是你制作XP合集的文件夹):

f:\cdimage\cdimage -lWinXP -g -h -n -o -m -bf:\cdimage\V1.6.BIN f:\XPCD f:\xpsp3v1.6.iso

ultraiso则更简单些,“启动光盘--加载引导文件”,这个引导文件就是你编写好的V1.6.BIN。

二、 引导BCDW、引导软盘镜像、引导Easyboot菜单

其实BCDW启动兼容性也还可以,但支持的中文数量有限。运用最广泛的Easyboot,经常用BCDW来引导软盘镜像,最典型的是调用DOS工具包里的某个工具,所以我们很容易看到Easyboot启动文件夹里有一些后缀为ini的文件。

1、引导BCDW菜单,先看两张图。(以V1.3为例,因为只有V1.3才有BCDW菜单)
3edd751ex781178c6ede4&690.gif
上面是V1.3主菜单,下面是BCDW菜单,引导的各种软盘镜像,当然,BCDW也可以单独用来引导XP合集。
3edd751ex78117b154a5a&690.gif
引导BCDW菜单,首先你会编辑BCDW菜单。如果要详细学习,比较费时间,用我提供简单的菜单,你马上就可以应用了。当然这只是初步。

假定你的XP合集所在文件夹叫XPCD,那么在XPCD里面建一个bcdw文件夹,将bcdw.bin(附件下)复制进来。再建一个bcdw.ini文件,记事本打开后,复制以下内容。红色部分是一些个人信息,你自己修改。蓝色部分你要重点编辑部分。蓝色部分的最后二行是我加上去,实际上,因为我们主菜单里就可以直接安装XP了,所以这里重复了,但是如果你只想BCDW(而不想用微软的XP启动文件)来做OEM合集菜单时,后面两行就是你参考的例子。如果是XP启动文件(主菜单)和BCDW(扩展菜单或二级菜单)一起用的,最后两行倒不必要。



[MenuItems]
c:\              ;Boot Hard drive                      ;
:reboot         ;Reboot PC                            ;
\BCDW\XPBOOT.IMG ;Load Win2K/XP                      ;
\BCDW\OEM.INI    ;DMI Editor(Auto)                     ;
\BCDW\CMOS.INI   ;Cmos Password Removal           ;
\BCDW\NTPASS.INI ;Win2K/XP Password Removal          ;
\BCDW\GHOST.IMG   ;Ghost 11.5 ;
\BCDW\GHOST.INI   ;Ghost 8.3 ;
\BCDW\DOS.INI    ;Dos Tools ;
\ACE1\SETUPLDR.BIN          ;Windows XP SP3 ACER OEM ;
\ASU1\SETUPLDR.BIN          ;Windows XP SP3 ASUS OEM ;

\BCDW\CD.BIN     ;Install Windows XP SP3 ;   (这个是返回主菜单。注,括号和括号内的是备注,要删除掉)


[MenuOptions]
BGColors= 0f, 0f, 0f, 0f
BGSymbol= 32
BottomText=  http://hi.baidu.com/zxkh

MenuPosition= 02, 03, 76, 19
MenuColors= 0f, 0f, 0f, 0f, 8f, 0f
MenuBorderStyle= 1
MenuShadowStyle= 0
MenuTitle= [MenuOptions]
MenuDefault= 0
MenuTimerLabel= Time
MenuTimer= 30
ScrollPosition= 00, 01, 85, 01
ScrollColors= 0f, 0f, 0f, 0f, 0f, 0f
ScrollMode= 0
ScrollText= WinXP SP3 OEM^VOL V1.3

IMG和IMA文件,bcdw可以直接引导(格式如上面示例),这些文件(包括INI文件)也放在bcdw目录下。如果要引导DOS工具包里的一个工具,则需要bcdw目录增加一个INI文件,比如,启动DOS工具包的CMOS密码清除工具,经编写一个CMOS.INI的文件,其内容如下:


[MenuItems]
/boot/dos.ima ; ; ; CMOS

如何在BCDW里设置返回主菜单?将编写好的XP启动文件,叫V1.6.BIN也好,叫V1.3.BIN也好,复制一份,改名为CD.BIN,用UltraEdit-32打开,找到510h这一行,将BOOTFIX.BIN改名,BOOTFIX.XXX,随便改,因为这时候我们不需要“Press any key to boot from CD”这样的字样。

关键的一步,将bcdw目录下的BCDW.BIN,改名为SETUPLDR.BIN。这就是前面我们讲“SETUPLDR.BINBOOTFIX.BINI386”字段的原因。

那么主菜单里又怎么引导?和引导某个XP安装一样,750h行及以后的某个位置,编写BCDW四个字符,以选择引导BCDW菜单。

2、引导软盘镜像

引导软盘镜像可以有两种办法,一是用EASYBOOT,一是用BCDW,先讲BCDW。前面讲的引导BCDW是有显示菜单的,而且菜单里显示可引导多个IMA\IMG文件。现在我们只想在主菜单里选择,直接引导。怎么做?这里我们以V1.6为例(本文开头的图)。

首先还是CD菜单里750h行及以后的某个位置,编写四个字符,比如DOS3,用于引导DOS工具包。

其次,在光盘根目录下,建立一个DOS3的文件夹,复制进DOS.IMA(DOS工具包软盘镜像)和BCDW.BIN,改名为SETUPLDR.BIN,用UltraEdit-32打开,搜索“bcdw\bcdw.ini”(引号内),改成“dos3\dos3.ini”(小写),修改后保存。在此目录建一个dos3.ini文件,里面的内容为(绿色):

[MenuItems]
\DOS3\DOS.IMA    ; ;

举一反三,假定是一个GHOSTA.IMG,同样的办法。

如果要在主菜单里直接引导DOS工具包里的某个工具,比如那个“清除系统密码”的工具。如上,同样的,要建立一个文件夹,假定叫XPP3(我是用3表示软盘镜像,重启,硬盘启动等,1和2主要是好区别自动安装,手动安装,以及有没有加载SATA等,反正用你自己命名法则),四个字符,大写。将BCDW.BIN复制进来,改名为SETUPLDR.BIN,用UltraEdit-32打开编辑,搜索“bcdw\bcdw.ini”(引号内),改成“xpp3\xpp3.ini”(小写),修改后保存。在此目录建一个dos3.ini文件,里面的内容为(绿色):

[MenuItems]
\dos3\dos.ima ; ; ; PW

PW,在DOS状态下是执行的命令是“PW”。

主菜单里要想直接调用,在750h处及以后要加入命令接口,四个大写字符(数字、字母能混用)。如,DOS3,如,XPP3等。

三、从硬盘启动、重启、关机、引导同样类型的菜单

方法与上面差不多,利用BCDW引导,分别建立文件夹并复制进BCDW.BIN,改名为SETUPLDR.BIN并修改编辑,编写相应的ini文件。

“从硬盘启动”的ini文件的内容:

[MenuItems]
C:\         ;;

“重新启动”ini文件的内容

[MenuItems]
:reboot          ;;

“关机”ini文件的内容

[MenuItems]
:PowerOff          ;;

 从硬盘启动也可以这样(不需要INI文件):从I386复制一份BOOTFIX.BIN文件,并进行编辑(用UltraEdit-32),改160h行的49为00,将BOOTFIX.BIN改名SETUPLDR.BIN,新建一个文件夹,命名为BOO3,将这个SETUPLDR.BIN复制进来。然后主菜单增加引导接口。

照这个思路,如果有一个类似V1.6.BIN(如V1.6A.BIN)的启动菜单(作为次级菜单)和V1.6相互引导,怎么办?也是新建一个文件夹,改名就行了,然后主菜单增加引导接口。

引导EASYBOOT菜单,如图所示(这个是我的OEM^VOL V1.6版的帮助菜单的文件夹内部结构图):
3edd751ex78117e4b5f58&690.gif
ini文件内容:

[MenuItems]
/hel3/help.ezb ; ;

四、其他

编辑的启动菜单是否可行,要进行多次测试,通常用ULTRAISO加载,生成ISO后,用虚拟机测,这里仅是测启动菜单,以及引导。测试时不一定所有XP安装源文件全部拖进ULTRAISO,这样容量太大,形成ISO时间太长。这些技巧,多实践几次,就知道怎么做效率高。

无约而来 2008.12.25

附件1:

多重启动.rar http://www.namipan.com/d/bb08e6080f97fe3c80d2a4a9f99579c2034b0268b10b0000

附件2:

bcdw.bin http://www.namipan.com/d/006b8134ae5881f9d8ff3b1607f6e2f7a40ba3c542500000