1. 实验任务1
使用任意文本编辑器,录入汇编源程序task1.asm。
1 assume cs:code, ds:data 2 data segment 3 db ‘Nuist‘ 4 db 5 dup(2);重复初始化5个2 5 data ends 6 7 code segment 8 start: 9 mov ax, data 10 mov ds, ax 11 12 mov ax, 0b800H 13 mov es, ax 14 15 mov cx, 5;设置循环次数为5 16 mov si, 0;设置ds的源变址指针从0开始 17 mov di, 0f00h;目的地址相对es的偏移量,0f00是显存的位置 18 s: mov al, [si] ;将data段的第si个字节送入ax寄存器的低地址 19 and al, 0dfh;将它转化为大写字母 20 mov es:[di], al;将转化好的数据送入目的地址,也就是显示缓冲区显示 21 mov al, [5+si];获取data段si+5位置的2(控制字符颜色)送入al 22 mov es:[di+1], al;在刚才送入的内容后一个字节送入该字符的控制信息 23 inc si;si自增 24 add di, 2;di移到下一个字的位置 25 loop s;s标段循环 26 27 mov ah, 4ch 28 int 21h 29 code ends 30 end start
答:循环实现了读取data中的数据,并将其转化为大写字母输出到显示器上。
1 data segment 2 db ‘Nuist‘ 3 db 2,3,4,5,6 4 data ends
答:根据实验结果更改的数据是显示缓冲区显示字符的控制数据,控制输出字符的颜色。
2. 实验任务2
已知数据段data中定义字节数据如下:
data segment db 23, 50, 66, 71, 35 data ends
程序代码:
1 assume cs:code, ds:data 2 data segment 3 db 23, 50, 66, 71, 35 4 data ends 5 code segment 6 start: 7 mov ax, data 8 mov ds, ax 9 mov cx,5 10 mov si,0 11 s: 12 mov al, ds:[si] 13 mov ah,0 14 mov bl, 10 15 div bl 16 mov bx,ax 17 mov ah, 2 18 mov dl,bl 19 add dl, 30h 20 int 21h 21 mov dl, bh 22 add dl, 30h 23 int 21h 24 inc si 25 mov dl, " " ;输出空格 26 int 21h 27 loop s 28 29 mov ah, 4ch 30 int 21h 31 code ends 32 end start
运行结果:
针对div指令,除数为8位时,al存商,ah存余数。当除数8位,被除数16位时,默认放在ax中。在计算时不要忘记初始化ah.
3. 实验任务3
1 assume cs:code, ds:data, ss:stack 2 data segment 3 dw 0123h, 0456h, 0789h, 0abch, 0defh, 0fedh, 0cbah, 0987h 4 data ends 5 6 stack segment 7 dw 0, 0, 0, 0, 0, 0, 0, 0 8 stack ends 9 10 code segment 11 start: mov ax,stack 12 mov ss, ax 13 mov sp,16 14 15 mov ax, data 16 mov ds, ax 17 18 push ds:[0] 19 push ds:[2] 20 pop ds:[2] 21 pop ds:[0] 22 23 mov ax,4c00h 24 int 21h 25 26 code ends 27 end start
2、cpu执行程序,程序返回前,cs=076C,ss=076B,ds=076A。
3、程序加载后,code段地址为x,data段地址为X-2,stack段地址为X-1。
data段和stack段的长度都是16个字节。
1 assume cs:code, ds:data, ss:stack 2 data segment 3 dw 0123h, 0456h 4 data ends 5 6 stack segment 7 dw 0, 0 8 stack ends 9 10 code segment 11 start: mov ax,stack 12 mov ss, ax 13 mov sp,16 14 15 mov ax, data 16 mov ds, ax 17 18 push ds:[0] 19 push ds:[2] 20 pop ds:[2] 21 pop ds:[0] 22 23 mov ax,4c00h 24 int 21h 25 26 code ends 27 end start
1、cpu执行程序,程序返回前,data段中的数据为多少?
答:data段没变,0123h,0456h
2、cpu执行程序,程序返回前,cs=076C,ss=076B,ds=076A。
3、设程序加载后,code段的段地址为x,则data段的段地址为x-2,stack段的段地址为x-1.
4、如果段中的数据占N个字节,则该段实际占有的空间应该为:[(N+15)/16 ]*16。
因为该题段中数据只有4个字节,但实际上仍然每一段分配了16个字节的空间。所以猜测段中数据不足16个字节时系统自动扩展到16个字节。以16个字节为单位分配空间。
5. 实验任务5
1 assume cs:code, ds:data, ss:stack 2 3 code segment 4 start: mov ax,stack 5 mov ss, ax 6 mov sp,16 7 8 mov ax, data 9 mov ds, ax 10 11 push ds:[0] 12 push ds:[2] 13 pop ds:[2] 14 pop ds:[0] 15 16 mov ax,4c00h 17 int 21h 18 19 code ends 20 data segment 21 dw 0123h, 0456h 22 data ends 23 24 stack segment 25 dw 0,0 26 stack ends 27 end start
1、cpu执行程序,程序返回前,data段中的数据为多少?
data不变 0123h,0456h
2、cpu执行程序,程序返回前,cs=076A,ss=076E,ds=076D。
3、设程序加载后,code段的段地址为x,则data段的段地址为x+3,stack段的段地址为x+4。
如果将(1),(2),(3)题中最后一条伪指令改为end(也就是说不指明程序的入口),则那个程序仍然可以正确执行?
答:(3)可以正确运行。(3)和前两个程序的区别在于数据段在代码段的后面。如果程序结尾是end start,cpu能够知道程序从start的地方开始执行。但如果是end那么程序只能从头执行。所以在(1)(2)中,开头是数据段,将数据段当作指令肯定无法执行。但在(3)中代码段在先,执行完后正确退出,也就不会进入数据段中出错。
编写代码将a段和b段中的数据依次相加,将结果存在c段中。
1 assume cs:code 2 a segment 3 db 1,2,3,4,5,6,7,8 4 a ends 5 6 b segment 7 db 1,2,3,4,5,6,7,8 8 b ends 9 10 c segment ; 在集成软件环境中,请将此处的段名称由c→改为c1或其它名称 11 db 8 dup(0) 12 c ends 13 14 code segment 15 start: 16 mov si,0 17 mov cx,8 18 mov ax,c 19 mov es,ax 20 s: mov ax,a 21 mov ds,ax 22 mov dl,[si] 23 mov ax,b 24 mov ds,ax 25 add dl,[si] 26 mov es:[si],dl 27 mov dx,0;不能忘了每次循环复原 28 inc si 29 loop s 30 31 mov ah, 4ch 32 int 21h 33 code ends 34 end start
运行结果:
用push指令将a段中前8个字型数据逆序存进b段
代码:
1 assume cs:code 2 a segment 3 dw 1,2,3,4,5,6,7,8,9,0ah,0bh,0ch,0dh,0eh,0fh,0ffh 4 a ends 5 6 b segment 7 dw 8 dup(0) 8 b ends 9 10 code segment 11 start: 12 mov ax,a 13 mov bx,b 14 mov cx,8 15 mov si,0 16 mov ds,ax 17 mov ss,bx 18 mov sp,16 19 s: 20 push [si] 21 add si,2 22 loop s 23 24 mov ah, 4ch 25 int 21h 26 code ends 27 end start
运行结果:
1、在实验中对于字还是字节,运算的单位是哪一个要分清。一开始做实验的时候,对于代码段和数据段占的空间有很大的疑惑,反汇编时一直长度不对。
2、div运算时一定不要忘了将ah置零,因为一开始的数据不为0,这样之后除法就出现了错误。
3、在循环中要用到的变量一定要仔细查看,是否每次循环中要累加,如果每次都要清零。
原文:https://www.cnblogs.com/zzzzero/p/14042203.html