实验5 编写、调试具有多个段的程序

时间:2023-01-15 01:25:08

从老师邮箱将实验五的相关代码下载下来

实验5 编写、调试具有多个段的程序

 

实验5 编写、调试具有多个段的程序

 

 

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

 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

 实验5 编写、调试具有多个段的程序

实验5 编写、调试具有多个段的程序

 

①CPU执行程序,程序返回前,data段中的数据如下图:

实验5 编写、调试具有多个段的程序

②CPU执行程序,程序返回前,CS= 076CH ,SS= 076BH ,DS= 076AH 

 实验5 编写、调试具有多个段的程序

③设程序加载后,CODE段的段地址为X,则DATA段的段地址为 X-2 ,STACK段的段地址为X-1 

 因为 code 指的是 cs ,data指的是 ds  ,stack指的是  ss

由②可知CS= 076CH ,SS= 076BH ,DS= 076AH 

所以     CODE段的段地址为X,则DATA段的段地址为 X-2 ,STACK段的段地址为X-1 

(2)将下面的程序编译连接,用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

实验5 编写、调试具有多个段的程序

实验5 编写、调试具有多个段的程序

①CPU执行程序,程序返回前,data段中的数据 如下图:

实验5 编写、调试具有多个段的程序

②CPU执行程序,程序返回前,CS= 076CH ,SS= 076BH ,DS= 076AH 。

实验5 编写、调试具有多个段的程序

③设程序加载后,CODE段的段地址为X,则DATA段的段地址为 X-2 ,STACK段的段地址为 X-1。

同实验(1)

④对于如下定义的段:

name segment

……

name ends

如果段中的数据占N个字节,则程序加载后,该段实际占有的空间为  ((N+15)/16)*16

这个问题不会,所以就百度了,参考网站:https://bbs.csdn.net/topics/390585699?page=1

相关解释为:

N分为被16整除和不被16整除。  
当N被16整除时: 占有的空间为(N/16)*16  
当N不被16整除时: 占有的空间为(N/16+1)*16,N/16得出的是可以整除的部分,还有一个余数,余数肯定小于16,加上一个16。 
两种情况总结成一个通用的公式:((N+15)/16)*16

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

 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

实验5 编写、调试具有多个段的程序

实验5 编写、调试具有多个段的程序

①CPU执行程序,程序返回前,data段中的数据 如下图:
实验5 编写、调试具有多个段的程序

②CPU执行程序,程序返回前,CS= 076AH ,SS= 076EH ,DS= 076DH 。

 实验5 编写、调试具有多个段的程序

③设程序加载后,CODE段的段地址为X,则DATA段的段地址为 X-2 ,STACK段的段地址为 X-1。

同实验(1)

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

 

ex5_1

实验5 编写、调试具有多个段的程序

ex5_2:

实验5 编写、调试具有多个段的程序

ex5_3:
实验5 编写、调试具有多个段的程序

所以只有实验(3)是正确的,原因如下:
当中用于将end start”改为“end 那么实验(2)(3)在实际中将 数据段 和 栈段  对应的的内容当中成了需要执行的代码,从而导致实验错误。

5)程序如下,编写code段中代码,将a段和b段中的数据依次相加,将结果存到C段中。

assume cs:code 
a segment 
        db 1,2,3,4,5,6,7,8 
a ends 
b segment 
        db 1,2,3,4,5,6,7,8 
b ends 
c segment 
        db 0,0,0,0,0,0,0,0 
c ends 
code segment 
start:           ;?code ends 
end start



相关思路:

让逻辑段a作为数据段(和ds关联起来),c作为附加段(和es关联起来);
将逻辑段a的 数据→复制到逻辑段c(可借助mov和loop实现)
让逻辑段b作为数据段(和ds关联起来),c作为附加段(和es关联起来);
将逻辑段b的 数据加到逻辑段c(可借助add和loop实现

实验5 编写、调试具有多个段的程序

 实验5 编写、调试具有多个段的程序

 实验5 编写、调试具有多个段的程序

实验5 编写、调试具有多个段的程序

 实验5 编写、调试具有多个段的程序

实验5 编写、调试具有多个段的程序

 

 

 (6)程序如下,编写code段中代码,用PUSH指令将A段中的前8个字型数据,逆序存储到B段中。

assume cs:code
a segment
    dw 1,2,3,4,5,6,7,8,9,0ah,0bh,0ch,0dh,0eh,0fh,0ffh
a ends
b segment
    dw 8 dup(0)
b ends
code segment
start: 
        ;?
code ends
end start



 实验5 编写、调试具有多个段的程序

实验5 编写、调试具有多个段的程序

实验5 编写、调试具有多个段的程序

实验5 编写、调试具有多个段的程序