显示BIOS的日期 (以下PROMPT>表示目录提示符:一般为:C:\WINDOWS\COMMAND\)PROMPT> DEBUG<按回车> -D FFFF:0006 L 8<按回车> (显示 FFFFh, 偏移地址 6h, 长度 8 bytes) 在作者的电脑上这里显示为 "1/10/96." 译者的电脑显示" FFFF:0000 37 2F-30 36 2F 30 30 00 7/06/00."相信作者的电脑里也是用 这种格式显示的。这里显示出来的是使用者BIOS的日期,有兴趣的话可以重新开机看看,注意 开机时的显示。 -Q<按回车> (退出DEBUG) 思考:当只按DEBUG的时候,编辑的是什么?为什么可以找到BIOS的日期?(译者这里也不是 很清楚所以请大家知道的也留言给斑竹,改正。译者认为可能是内存的真实物理地址。) 返回目录 2)在你的电脑的COMMANG.COM文件里搜寻"IBM"这几个字符 下面的"C:\Win95\"是根据每不电脑不同的。像译者的电脑里就是"C:\WINDOWS" PROMPT> DEBUG C:\Win95\Command.com<按回车> -S 0 L FFFF "IBM"<按回车>(从0开始搜寻"IBM",搜寻FFFFh多个单元格) -Q<按回车> (退出DEBUG) C:\WINDOWS>DEBUG C:\WINDOWS\COMMAND.COM -S 0 L FFFF "IBM" -S 0 L FFFF "COMMAND" 12A7:008D 12A7:04F7 12A7:3870 12A7:38BE 12A7:38DD -S 0 L FFFF "PATH" 12A7:38AD 12A7:CCB7 12A7:CF55 -S 0 L FFFF "COMSPEC" 12A7:38D4 12A7:3A4D 12A7:CCC4 -Q C:\WINDOWS> (注意:搜寻是要区分大小写的) (你可以看到上面是没有找到"IBM"的, 可以试一试"PATH" , "COMSPEC" , "COMMAND") (注意: 这种方法用在查找加密资料和已被删除的资料等方面时是十分有用的) 返回目录 3) 一位十六进制数的运算: PROMPT> DEBUG<按回车> -H 9 1<按回车> (加减两个十六进制的数, 9h+1h=Ah & 9h-1h=8h) 结果是显示: 000A 0008 -Q<按回车> (退出DEBUG) C:\WINDOWS>debug -h 9 1 000A 0008 -q C:\WINDOWS> 返回目录 4) 检查x86寄存器内容 PROMPT> DEBUG<按回车> -R<按回车> (显示x86寄存器内容) -Q<按回车> (退出DEBUG) C:\WINDOWS>debug -R AX=0000 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=127C ES=127C SS=127C CS=127C IP=0100 NV UP EI PL NZ NA PO NC 127C:0100 043C ADD AL,3C -Q 下面是对寄存器的简单介绍: 数据存储器 在本类中,一般讲的AH就是AX的前八位,AL就是AX的后八位,后面的以此类推。 AX Accumulator;作为累加器,所以它是算术运算的主要寄存器。另外所有的I/O指令都使用 这一寄存器与外部设备传送信息。 BX Base register;可以作为通用寄存器使用,此外在计算存储器地址时,它经常用作基地 址寄存器。 CX Counting register;可以作为通用寄存器使用,此外在循环(LOOP)和串处理指令中作隐 含的计数器。 DX Data register;可以作为通用寄存器使用,一般在作双字长运算时,把DX和AX组合在一 起存放一个双字长数,DX用来存放高位字。此外,对某些I/O操作,DX可用来存放I/O的端口地 址。 指针及变址寄存器 BP Base pointers register ;机制指针寄存器 SI Source index register ;堆栈指针寄存器 DI Destiny index register ;目的变址寄存器 SP Battery pointer register ;堆栈指针寄存器 段寄存器 CS Code segment register ;代码段寄存器,存放正在运行的程序指令 DS Data segment register ;数据段寄存器,存放当前运行程序所用的数据 SS Battery segment register ;堆栈段寄存器,定义了堆栈所在区域 ES Extra segment register ;附加段寄存器,存放附加的数据,是一个辅助性的数据区,
控制寄存器 IP Next instruction pointer register;指令指针寄存器,它用来存放代码段中的偏移地 址,在程序运行的过程中,它始终指向下一条指令的首地址,它与CS寄存器联用确定下一条指 令的物理地址 F Flag register;标志寄存器 "NV UP EI PL NZ NA PO NC"就是了,也有人称之为PSW Pro gram Status Wold程序状态寄存器 (这里有一点必须讲明白的现在在,其实从奔腾开始这些寄存器(除了所有段寄存器,标志寄存 器 )都是32位的。并且加多了两个16位段寄存器FS,GS。dos下面看到这些寄存器是16位的。 要看32位寄存器可以使用soft-ice。对于FS,GS的作用我也不是很清楚,希望有高手指点,谢 谢。) 返回目录 5)我们来编写我们的第一个用机械语言编写的程序-打印一个字符 (这里用机械语言的主要原因是考虑到有一些用户不懂汇编命令,现在就要让他有一个认识 计算机程序实质是一些数字) PROMPT> DEBUG<按回车> -E 100<按回车> (在偏移地址为100的地方输入机械指令程序) B4<按空格>02<按空格> (在AX寄存器的前八位存入02) B2<按空格>41<按空格> (在DX寄存器的后八位存入41h,41h就是大写A的ASCII码,身边有AS CII表的朋友可以对着表改改数字试一试) CD<按空格>21<按空格> (当AH=02时这是DOS显示输出的中断号) CD<按空格>20<按回车> (退出DOS) -G<按回车> (程序运行,并在屏幕上显示出"A") 程序运行完以后你将看到"Program terminated normally"(程序正常结束了). -U 100<按回车> (我们把它反汇编,就是把机械命令变为汇编语言指令) 107F:0100 B402 MOV AH,02 :0102 B2 MOV DL,41 :0104 CD21 INT 21 :0106 CD20 INT 20 (下面会有一堆无用的东西) (对了,你的段地址可能与我的段地址CS=107F不同哦) -R<按回车> (让我们来看看寄存器的值; IP==100h, AX==0000h, DX==0000h) 好极了,我们看到电脑又做好了准备下一次运行程序了。 -T<按回车> (执行第一步操作... IP=>102h, AX=>0200h,指令指针寄存器指向下一条命令, AX的值被改变。 -T<按回车> (执行第二步操作... IP=>104h, , DX=>0041h,指令指针寄存器指向下一条命令 ,DX的值被改变。 -P<按回车> (继续执行 INT 21,IP=>106h, AX=>02h,) -P<按回车> (继续执行INT 20) -Q<按回车> (退出DEBUG) (注意:你必须小心使用"T".因为如果你在程序完结以后继续执行这条命令,因为我们无法预 知下面的指令是什么,所以我们也无法预知它可能带来的后果) C:\WINDOWS>DEBUG -E 100 127C:0100 B4.B4 02.02 B2.B2 41.41 CD.CD 21.21 CD.CD 20.20 -G A Program terminated normally -U 100 127C:0100 B402 MOV AH,02 127C:0102 B241 MOV DL,41 127C:0104 CD21 INT 21 127C:0106 CD20 INT 20 127C:0108 C706F1E30900 MOV WORD PTR [E3F1],0009 127C:010E EB59 JMP 0169 127C:0110 57 PUSH DI 127C:0111 BFF1E3 MOV DI,E3F1 127C:0114 8BDF MOV BX,DI 127C:0116 06 PUSH ES 127C:0117 0E PUSH CS 127C:0118 07 POP ES 127C:0119 32D2 XOR DL,DL 127C:011B EB34 JMP 0151 127C:011D 006B12 ADD [BP+DI+12],CH -R AX=0000 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=127C ES=127C SS=127C CS=127C IP=0100 NV UP EI PL NZ NA PO NC 127C:0100 B402 MOV AH,02 -T AX=0200 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=127C ES=127C SS=127C CS=127C IP=0102 NV UP EI PL NZ NA PO NC 127C:0102 B241 MOV DL,41 -T AX=0200 BX=0000 CX=0000 DX=0041 SP=FFEE BP=0000 SI=0000 DI=0000 DS=127C ES=127C SS=127C CS=127C IP=0104 NV UP EI PL NZ NA PO NC 127C:0104 CD21 INT 21 -P A AX=0241 BX=0000 CX=0000 DX=0041 SP=FFEE BP=0000 SI=0000 DI=0000 DS=127C ES=127C SS=127C CS=127C IP=0106 NV UP EI PL NZ NA PO NC 127C:0106 CD20 INT 20 -P Program terminated normally -Q C:\WINDOWS> 返回目录 6) 我们现在用汇编语言指令来做和例5一样的事情 PROMPT> DEBUG<按回车> -A 100<按回车> (在偏移地址为100的地方输入汇编语言程序) MOV AH,02<按回车> (选用DOS的02号功能调用,显示输出) MOV DL,<按回车> (在DX寄存器的后八位存入41h,41h就是大写A的ASCII码,身边有ASCII表 的朋友可以对着表改改数字试一试) INT 21<按回车> (当AH=02时这是DOS显示输出的中断号,显示"A") INT 20<按回车> (退出DOS) <按回车> (结束汇编语言编程状态,回到DEBUG命令状态) -G =100<按回车> (运行程序,其实可以不要"=100"因为一般默认启始位置是100) -Q<按回车> (退出DEBUG) C:\WINDOWS>DEBUG -A 100 127C:0100 MOV AH,02 127C:0102 MOV DL,41 127C:0104 INT 21 127C:0106 INT 20 127C:0108 -G A Program terminated normally -Q
返回目录 7) 现在,我们不但要编写一个汇编程序,而且我们还要把它存盘 (下面这个程序就要比原来的程序复杂一点了-显示输出:"ABC") PROMPT> DEBUG<按回车>(运行DEBUG程序;系统默认启始IP寄存器值为100h) -A 100<按回车> (用汇编语言编写一个程序,启始地址是100h) MOV AH,02<按回车> (选择DOS的02号功能调用, 显示输出) MOV DL,<按回车> (在DX寄存器的后八位存入41h,41h就是大写A的ASCII码) INT 21<按回车> (当AH=02时这是DOS显示输出的中断号,显示"A") MOV DL,42<按回车> (在DX寄存器的后八位存入41h,41h就是大写B的ASCII码) INT 21<按回车> (当AH=02时这是DOS显示输出的中断号,显示"B") MOV DL,43<按回车> (在DX寄存器的后八位存入41h,41h就是大写C的ASCII码) INT 21<按回车> (当AH=02时这是DOS显示输出的中断号,显示"C") INT 20<按回车> (程序结束,退出DEBUG) <按回车> (结束汇编命令输入,回到DEBUG命令输入) -R BX<按回车> (查看寄存器BX的值) :0000<按回车> (设置BX为0000h,这是程序的结尾地址是BX:CX) (注意,只要BX = 0000, 文件的大小就小于 < 64 Kb.) -R CX<按回车> (设置CX为Fh,这是程序的长度:16位) :0010<按回车> (现在我们可以把这个16字节的程序写入硬盘了) -N printabc.com<按回车> (将要存盘的程序命名) -W<按回车> (把这十六字节写到文件里面) -Q<按回车> (退出DEBUG) PROMPT> DIR printabc.com<按回车> 这里将会报告这个文件的大小是16字节 (10h 字节). PROMPT> printabc.com<按回车> 会马上在屏幕上打印出"ABC" C:\WINDOWS>DEBUG -A 100 127C:0100 MOV AH,02 127C:0102 MOV DL,41 127C:0104 INT 21 127C:0106 MOV DL,42 127C:0108 INT 21 127C:010A MOV DL,43 127C:010C INT 21 127C:010E INT 20 127C:0110 -R AX=0000 BX=0000 CX=0000 DX=0000 SP=FFEE BP=0000 SI=0000 DI=0000 DS=127C ES=127C SS=127C CS=127C IP=0100 NV UP EI PL NZ NA PO NC 127C:0100 B402 MOV AH,02 -R BX BX 0000 : -R CX CX 0000 :0010 -N PRINTABC.COM -W Writing 00010 bytes -Q C:\WINDOWS>DIR PRINTABC.COM Volume in drive C has no label Volume Serial Number is 28FB-70BA Directory of C:\WINDOWS PRINTABC COM 16 03-21-01 11:02 PRINTABC.COM 1 file(s) 16 bytes 0 dir(s) 557,711,360 bytes free C:\WINDOWS>PRINTABC ABC C:\WINDOWS> 这里可以有人告诉我,为什么要存入是BX:CX代表程序长度吗?(写信给译者,谢谢) 返回目录 8) 现在,我们试一试查看一个已经编好的程序: PROMPT> DEBUG<按回车>(运行DEBUG程序在CS:IP = CS:0100h) -N printabc.com<按回车> (告诉电脑你想装载的程序名) -L<按回车> (装载那个名字的程序进入内存) -U 100 L 10<按回车> (从偏移地址100开始反汇编16位字节) -R<按回车> (现在看看寄存器里面的内容) 注意:DEBUG本身是没有自动纪录文件大小的。 -G (运行被命名的程序,打印"ABC") 你将看到"ABC",然后是"Program terminated normally") C:\WINDOWS>DEBUG -N PRINTABC.COM -L -U 100 L 10 12A4:0100 B402 MOV AH,02 12A4:0102 B241 MOV DL,41 12A4:0104 CD21 INT 21 12A4:0106 B242 MOV DL,42 12A4:0108 CD21 INT 21 12A4:010A B243 MOV DL,43 12A4:010C CD21 INT 21 12A4:010E CD20 INT 20 -R AX=0000 BX=0000 CX=0010 DX=0000 SP=FFFE BP=0000 SI=0000 DI=0000 DS=12A4 ES=12A4 SS=12A4 CS=12A4 IP=0100 NV UP EI PL NZ NA PO NC 12A4:0100 B402 MOV AH,02 -G ABC Program terminated normally 返回目录 9)你可以用DEBUG的计算功能计算程序的长度。 一开始的时候你的程序初始地址是在0100h: 107F:0100 MOV AH,02 <--这就是 100h 你的程序的最后一行在010Eh: 107F:010E INT 20 <--最后一行 然后,最后一条命令的下一行的地址是0110h: 107F:0110 <--这就是110h 所以,从0110h里减去100h我们得到得长度是10h 字节. PROMPT> DEBUG<按回车> -H 110 100<按回车> (这条命令将运算110h+100h和110h-100h) 0210 0010<按回车> (汇报 110h-100h=0010h; 16-byte 程序长度16位) -Q<按回车> (退出DEBUG)
|