实验3 多个段的汇编源程序编写与调试

一、实验目的

1. 理解和掌握将数据、代码、栈放入不同逻辑段的程序的编写和调试
2. 理解具有多个段的汇编源程序对应的目标程序执行时,内存分配方式
3. 掌握大小写字符的转换方法、数字字符和数值之间的转换方法
4. 理解并掌握各种寻址方式的灵活应用
5. 掌握汇编指令loop, and, or,div, mul的用法

二、实验准备

复习教材chapter 6-8章。
chapter 6 包含多个段的程序
chapter 7 更灵活的定位内存地址的方法
chapter 8 数据处理的两个基本问题
 

三、实验内容

实验任务1

使用任意文本编辑器,录入汇编源程序task1.asm。
 1 assume cs:code, ds:data
 2 data segment
 3         db 'Nuist'
 4         db 5 dup(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,因为nuist有五个字母
16         mov si, 0         ;//设置数据段地址偏移量
17         mov di, 0f00h     ;//设置es附加段的地址偏移量
18 s:      mov al, [si]      ;//将数据段偏移地址为si的数据存入al
19         and al, 0dfh      ;//dfh=11011111B,将al中的ASCII码的第五个位置为0,变为大写字母
20         mov es:[di], al   ;将al存入偏移地址为di的附加段中
21         mov al, [5+si]    ;将偏移地址为5+si的地址存入al
22         mov es:[di+1], al ;将al存入附加端偏移地址为di+1的内存
23         inc si            ;si自加1
24         add di, 2         ;di+2
25         loop s            ;循环s
26 
27         mov ah, 4ch
28         int 21h
29 code ends
30 end start

 使用masm、link对task1.asm进行汇编、链接,得到可执行文件task1.exe,运行并观察结果。

-g运行至27行处

 

 修改成db 2,3,4,5后执行结果如下图

 这里的数值的作用是修改显存显示内容的颜色。

实验任务2

task2.asm代码:

 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 bx,0     
11 s:  mov ah,0
12      mov al,ds:[bx]
13      mov dl,10
14      div dl
15      
16      mov ds:[5],al//放商
17      mov ds:[6],ah  //放余数   
18      mov ah,2
19      mov dl,ds:[5]
20      add dl,30h//加30h,变为ASCII码值
21      int 21h
22      mov ah,2
23      mov dl,ds:[6]
24      add dl,30h
25      int 21h     
26      mov dl,20h  //输出空格,空格的ASCII为20h
27      int 21h     
28      inc bx
29      loop s
30      
31      mov ax,4c00h
32      int 21h
33 code ends
34 end start

使用masm、link工具对task2.asm进行汇编和链接

成功输出5个数

实验任务3

task3.asm源代码:

 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 code ends
26 end start

使用masm、link工具对task3.asm进行汇编和链接

 

 ①CPU执行程序,程序返回前,data段中的数据:0123H, 0456H, 0789H, 0ABCH, 0DEFH, 0FEDH, 0CBAH, 0987H

②CPU执行程序,程序返回前,cs=076CH,ss=076BH,ds=076AH

 

③设程序加载后,code段的段地址为X,则data段的段地址为X-2,stack段的段地址为X-1

实验任务4

将下面的程序编译、连接,用Debug加载、跟踪,然后回答问题。

 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

①CPU执行程序,程序返回前,data段中的数据为0123H,0456H

 ②CPU执行程序,程序返回前,可以得出cs=076CH,ss=076BH,ds=076AH

 ③设程序加载后,code段的段地址为X,则data段的段地址为X-2,stack段的段地址为X-1

 ④如果段中的数据占N个字节,则程序加载后,该段实际占有的空间为(floor(N/16)+1)*16(向下取整)。

 最少占用16个字节,然后以16的倍数增加,16 32 48

实验任务5

task5.asm源代码:

 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

①CPU执行程序,程序返回前,data段中的数据为0123H ,0456H

 ②CPU执行程序,程序返回前,cs=076AH,ss=076EH,ds=076DH

③设程序加载后,code段的段地址为X,则data段的段地址为X+3,stack段的段地址为X+4

实验任务6

如果将(1)、(2)、(3)题中最后一条伪指令“end start”改为“end”(也就是说,不指明程序的入口),则哪个程序仍然可以正确执行?请说明原因。

答:第三题可以正确执行(task5.exe),因为如果他end start去掉,那么程序就会从默认的入口开始执行,默认的入口为code段,所以会从code段开始执行,

data段和stack段正好在code后面所以可以正确运行。

实验任务7

task7.asm源代码:

 1 assume cs:code
 2 a segment
 3   db 1,2,3,4,5,6,7,8
 4 a ends
 5 b segment
 6   db 1,2,3,4,5,6,7,8
 7 b ends
 8 c segment 
 9   db 8 dup(0)
10 c ends
11 code segment
12 start:
13      mov bx,0
14      mov cx,8
15 
16 s:   mov si,a
17      mov ds,si
18      mov al,ds:[bx]
19 
20      mov si,b
21      mov ds,si
22      add al,ds:[bx]
23 
24      mov si,c1 
25      mov ds,si
26      mov ds:[bx],al
27      inc bx
28      loop s
29 
30      mov ah,4ch
31      int 21h       
32 code ends
33 end start

查看数据段c1的数值如下,成功相加

实验任务8

程序如下,编写code段中的代码,用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 b segment
 6   dw 8 dup(0)
 7 b ends
 8 code segment
 9 start: 
10         mov ax,b
11         mov ss,ax
12         mov sp,10h
13         mov ax,a
14         mov ds,ax
15         mov si,0
16         mov cx,8
17 s:      push ds:[si]
18         add si,2
19         loop s
20         mov ah,4ch
21         int 21h
22 code ends
23 end start

反汇编,执行:

 查看内存:

 

已完成逆序存储。

 

posted @ 2020-11-27 00:51  yoyoMasterLi  阅读(124)  评论(1)    收藏  举报