一、实验任务
1. 实验任务1
ex1.asm的源代码:
1 ;ex1.asm 2 assume cs:code 3 code segment 4 mov ax, 0b810h 5 mov ds, ax 6 7 mov byte ptr ds:[0], 1 8 mov byte ptr ds:[1], 1 9 mov byte ptr ds:[2], 2 10 mov byte ptr ds:[3], 2 11 mov byte ptr ds:[4], 3 12 mov byte ptr ds:[5], 3 13 mov byte ptr ds:[6], 4 14 mov byte ptr ds:[7], 4 15 16 mov ah, 4ch 17 int 21h 18 code ends 19 end
使用masm、link工具汇编、链接:
debug调试:
观察到cx=31,使用u命令精准反汇编至30;
使用g命令执行至倒数第二行,此时命令行出现图像
2. 实验任务2
ex2.asm的源代码:
1 ;ex2.asm 2 assume cs:code 3 code segment 4 mov ax, 0b810h 5 mov ds, ax 6 7 mov bx, 0 8 mov ax, 101H 9 mov cx, 4 10 s: mov [bx], ax 11 add bx, 2 12 add ax, 101H 13 loop s 14 15 mov ah, 4ch 16 int 21h 17 code ends 18 end
使用masm、link工具汇编、链接:
运行结果:
debug调试:
观察到cx=1c,使用u命令精准反汇编至1b;
使用g命令执行至倒数第二行,此时命令行出现图像:
实验分析:
该程序的作用与ex1.exe相同,都是对显存的指定位置写入特定的内容,使得屏幕上显示四个颜色形状各异的图标。
在具体实现上,ex1.exe通过代码的重复来更改显存地址,而ex2.exe则利用了loop语句简化了这一过程。
3. 实验任务3
ex3.asm的源代码:
1 assume cs:code 2 code segment 3 mov ax,0b800h 4 mov ds,ax 5 mov ax,0237h 6 mov bx,07b8h 7 8 mov cx,16 9 s: mov ds:[bx],ax 10 add bx,2h 11 loop s 12 13 mov ax,4c00h 14 int 21h 15 code ends 16 end
运行结果截图:
把填充的字数据,从0237H 改成0239H后,观察结果:
把填充的字数据,从0237H 改成0437H后,观察结果:
实验分析:
这个字数据中高位字节里存放的是图标的颜色,低位字节里存放的图标的内容。
4. 实验任务4
ex4.asm的源代码如下:
1 assume cs:code 2 code segment 3 mov ax,0 4 mov ds,ax 5 mov ax,0200h 6 mov bx,ax 7 8 mov ax,0 9 mov cx,03fh 10 s: mov ds:[bx],ax 11 add ax,1 12 add bx,1 13 loop s 14 15 mov ax,4c00h 16 int 21h 17 code ends 18 end
debug调试:
成功将0~63写入内存0:200~0:23f。
5. 实验任务5
ex5.asm的源代码如下:
1 assume cs:code 2 code segment 3 mov ax ,cs 4 mov ds,ax 5 mov ax,002h 6 mov es,ax 7 mov bx,0 8 mov cx,cx 9 10 s: mov al,ds:[bx] 11 mov es:[bx],al 12 inc bx 13 loop s 14 15 mov ax,4c00h 16 int 21h 17 code ends 18 end
debug调试结果如下:
可以看见已经成功把程序本身复制至0:200内存单元处。
二、实验总结
在实验过程中,对于实验1和实验2的调试过程中,发现了一个问题:对于显存的读写,有时候是成功的,而有时候是失败的。经过多次实验,可以总结出一个结论,当运行读写显存指令时,如果控制台的页面已经被语句铺满,因为新代码的显示,产生了页面的滚动,则无法正确读写显存;若控制台内容为空,新代码的显示不导致页面滚动,则可以读写显存显示图标。
经过分析,我认为是控制台语句滚动这一事实发生在读写显存语句之后,同时控制台为了滚动页面,会将下面行的内容写入滚上去的一行,这次写入会覆盖之前的语句读写现存,导致读写显存语句虽然生效,但是无法显示出结果。