实验3 多个段的汇编源程序编写与调试
1. 实验任务1
使用任意一款文本编辑器,编写8086汇编源程序ex1.asm。源代码如下:
;ex1.asm assume cs:code code segment mov ax, 0b810h mov ds, ax mov byte ptr ds:[0], 1 mov byte ptr ds:[1], 1 mov byte ptr ds:[2], 2 mov byte ptr ds:[3], 2 mov byte ptr ds:[4], 3 mov byte ptr ds:[5], 3 mov byte ptr ds:[6], 4 mov byte ptr ds:[7], 4 mov ah, 4ch int 21h code ends end
阅读源程序,从理论上分析源代码的功能,尤其是line15-25,循环实现的功能是什么,逐行理解每条指 令的功能。
使用masm、link对task1.asm进行汇编、链接,得到可执行文件task1.exe,运行并观 察结果。
使用debug工具对程序进行调试,执行到程序返回前,即line27之前,观察结果。
修改line4里5个字节单元的值,重新汇编、链接、运行,观察结果。
db 5 dup(2) --> 改成: db 2,3,4,5,6
基于观察,分析、猜测这里的数值作用是什么。


(1)首先向数据段的前10个字节输入数据,其中db 5 dup(2)表示5个重复的2(字节数据)。向附加段寄存器es输送显存地址(在内存地址结构中,B8000H~BFFFFH共32KB的空间,为80x25彩色字符模式的显示缓冲区。向这个地址空间写入数据,写入的内容将立即出现在显示器)。执行5次循环,循环的内容是:将数据段中的字符数据送往显存地址中,并执行add al,odfh(将小写转化为大写),mov al, [5+si],mov es:[di+1], al(为设置显示颜色的操作,将2送往显存中存储对应字符地址的下一个地址,实现控制颜色)。
(2)db 2,3,4,5,6即设置颜色的值为不同颜色。
2. 实验任务2
已知数据段data中定义字节数据如下:
data segments db 23, 50, 66, 71, 35 data ends
编写程序,在屏幕上以十进制整数形式打印输出这5个两位数。
assume cs:code, ds:data data segment db 23,50,66,71,35 data ends code segment start: mov ax,data mov ds,ax mov di,0 mov cx,5 s: mov ah,0 mov al,ds:[di] mov bl,10 div bl mov ds:[di+10],al mov ds:[di+11],ah mov ah,2 mov dl,ds:[10+di] add dl,30h int 21h mov ah,2 mov dl,ds:[11+di] add dl,30h int 21h mov ah,2 mov dl," " int 21h inc di loop s mov ax,4c00h int 21h code ends end start

3. 实验任务3
教材「实验5 编写、调试具有多个段的程序」(1) 程序源码见task3.asm
assume cs:code, ds:data, ss:stack data segment dw 0123h, 0456h, 0789h, 0abch, 0defh, 0fedh, 0cbah, 0987h data ends stack segment dw 0, 0, 0, 0, 0, 0, 0, 0 stack ends code segment start: mov ax,stack mov ss, ax mov sp,16 mov ax, data mov ds, ax push ds:[0] push ds:[2] pop ds:[2] pop ds:[0] mov ax,4c00h int 21h code ends end start


1、CPU执行程序,程序返回前,data段中数据为多少?
0123,0456,0789,0abc,0def,0fed,0cba,0987
2、CPU执行程序,程序返回前,cs=076c,ss=0769,ds=075a
3、设程序加载后,code段的段地址为X,则data段的段地址为x-2,stack段的段地址为x-1
4. 实验任务4
教材「实验5 编写、调试具有多个段的程序」(2) 程序源码见task4.asm。
assume cs:code, ds:data, ss:stack data segment dw 0123h, 0456h data ends stack segment dw 0, 0 stack ends code segment start: mov ax,stack mov ss, ax mov sp,16 mov ax, data mov ds, ax push ds:[0] push ds:[2] pop ds:[2] pop ds:[0] mov ax,4c00h int 21h code ends end start


21由42-十进制(16+16)=22得出
data段中的数据为:0123h, 0456h
CPU执行程序,程序返回前,cs=076C、ss=076B、ds=076A
设程序加载后,code段的段地址为X,则data段的段地址为X-2,stack段的段地址为X-1
如果段中的数据占N个字节,则程序加载后,该段实际占有的空间为:(N/16)*16 注意: (N/16)向上取整。
5. 实验任务5
此部分书写内容: 附上源代码文件task5.asm 回答教材中①②③三个问题。 附上回答②时反汇编调试截图,即:在debug中,执行到程序返回前的调试截图。
assume cs:code, ds:data, ss:stack code segment start: mov ax,stack mov ss, ax mov sp,16 mov ax, data mov ds, ax push ds:[0] push ds:[2] pop ds:[2] pop ds:[0] mov ax,4c00h int 21h code ends data segment dw 0123h, 0456h data ends stack segment dw 0,0 stack ends end start

1、CPU执行程序,程序返回前,data段中的数据为:0123h, 0456h
2、CPU执行程序,程序返回前,cs=076A,ss=076E,ds=076D
3、设程序加载后,code段的段地址为X,则data段的段地址为X+3,stack段的段地址为X+4
6. 实验任务6
此部分书写内容: 回答教材中提出的问题,并按要求说明原因。
实验任务五可以正常执行。如果不指名程序入口,实验任务三和四代码的前几行数据段将被当做代码来执行,
而实验任务五的代码把数据段和栈段的内容放在代码段的后面,所以不会影响程序的正常执行。
7. 实验任务7
此部分书写内容: 附上完整源代码文件task7.asm
附上在debug环境中,执行到程序返回前,查看逻辑段c的数据的截图,以此验证所编写的程序正 确实现了题目要求。
1 assume cs:code<br>a segment<br> db 1,2,3,4,5,6,7,8<br>a ends<br><br>b segment<br> db 1,2,3,4,5,6,7,8<br>b ends<br><br>c segment <br> db 8 dup(0)<br>c ends<br><br>code segment<br>start:<br> mov ax,a<br> mov ds,ax<br> mov si,0<br> mov cx,8<br> s:mov al,ds:[si]<br> add al,ds:[si+16]<br> mov ds:[si+32],al<br> inc si<br> loop s<br> mov ax,4c00h<br> int 21h<br>code ends<br>end start

指令长度为4BH ,数据段共占用30H个字节,故 u 0 1a ,g命令执行到编号为16的指令之前,调用d命令查看c处的内存单元内容 c的起始地址为 ds:20 共对8个字节的数字进行加法,故查看到27截至。
8. 实验任务8
此部分书写内容: 附上完整源代码文件task8.asm 附上在debug环境中,执行到程序返回前,查看逻辑段c的数据的截图,以此验证所编写的程序正 确实现了题目要求。
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: mov ax,a mov ds,ax mov bx,0 mov ax,b mov ss,ax mov sp,16 mov cx,8 s:push [bx] add bx,2 loop s mov ax,4c00h int 21h code ends end start

指令总长度为4FH,其中30H为数据段和栈段的内容,故u 0 1E
调用d命令查询cpu执行后栈段中的内容如图
1. 实验任务1
使用任意文本编辑器,录入汇编源程序task1.asm。
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
|
assume cs:code, ds:datadata segmentdb 'Nuist'db 5 dup(2)data endscode segmentstart:mov ax, datamov ds, axmov ax, 0b800Hmov es, axmov cx, 5mov si, 0mov di, 0f00hs: mov al, [si]and al, 0dfhmov es:[di], almov al, [5+si]mov es:[di+1], alinc siadd di, 2loop smov ah, 4chint 21hcode endsend start |
阅读源程序,从理论上分析源代码的功能,尤其是line15-25,循环实现的功能是什么,逐行理解每条指 令的功能。
使用masm、link对task1.asm进行汇编、链接,得到可执行文件task1.exe,运行并观 察结果。
使用debug工具对程序进行调试,执行到程序返回前,即line27之前,观察结果。
修改line4里5个字节单元的值,重新汇编、链接、运行,观察结果。
|
1
2
3
|
db 5 dup(2)--> 改成:db 2,3,4,5,6 |
基于观察,分析、猜测这里的数值作用是什么。


(1)首先向数据段的前10个字节输入数据,其中db 5 dup(2)表示5个重复的2(字节数据)。向附加段寄存器es输送显存地址(在内存地址结构中,B8000H~BFFFFH共32KB的空间,为80x25彩色字符模式的显示缓冲区。向这个地址空间写入数据,写入的内容将立即出现在显示器)。执行5次循环,循环的内容是:将数据段中的字符数据送往显存地址中,并执行add al,odfh(将小写转化为大写),mov al, [5+si],mov es:[di+1], al(为设置显示颜色的操作,将2送往显存中存储对应字符地址的下一个地址,实现控制颜色)。
(2)db 2,3,4,5,6即设置颜色的值为不同颜色。
2. 实验任务2
已知数据段data中定义字节数据如下:
|
1
2
3
|
data segmentsdb 23, 50, 66, 71, 35data ends |
编写程序,在屏幕上以十进制整数形式打印输出这5个两位数。
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
|
assume cs:code, ds:datadata segment db 23,50,66,71,35data endscode segmentstart: mov ax,data mov ds,ax mov di,0 mov cx,5s: mov ah,0 //*将字节数据存入ax寄存器中,因为ax存储2个字节,所以 mov al,ds:[di] ah中存0*// mov bl,10 div bl //ax中数据除以10,余数存在ah,商存在al mov ds:[di+10],al //将商的内容存入数据段中,(取可用的内存单元即可) mov ds:[di+11],ah //将商的内容存入数据段中,(取可用的内存单元即可) mov ah,2 //* mov dl,ds:[10+di] 显示商 add dl,30h int 21h *// mov ah,2 //* mov dl,ds:[11+di] 显示余数 add dl,30h int 21h *// mov ah,2 mov dl," " int 21h inc di //di自增1,用于读取下一位置处的字节数据 loop s mov ax,4c00h int 21hcode endsend start |

3. 实验任务3
教材「实验5 编写、调试具有多个段的程序」(1) 程序源码见task3.asm
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
|
assume cs:code, ds:data, ss:stackdata segment dw 0123h, 0456h, 0789h, 0abch, 0defh, 0fedh, 0cbah, 0987hdata endsstack segment dw 0, 0, 0, 0, 0, 0, 0, 0stack endscode segmentstart: mov ax,stack mov ss, ax mov sp,16 mov ax, data mov ds, ax push ds:[0] push ds:[2] pop ds:[2] pop ds:[0] mov ax,4c00h int 21hcode endsend start |


1、CPU执行程序,程序返回前,data段中数据为多少?
0123,0456,0789,0abc,0def,0fed,0cba,0987
2、CPU执行程序,程序返回前,cs=076c,ss=0769,ds=075a
3、设程序加载后,code段的段地址为X,则data段的段地址为x-2,stack段的段地址为x-1
4. 实验任务4
教材「实验5 编写、调试具有多个段的程序」(2) 程序源码见task4.asm。
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
|
assume cs:code, ds:data, ss:stackdata segment dw 0123h, 0456hdata endsstack segment dw 0, 0stack endscode segmentstart: mov ax,stack mov ss, ax mov sp,16 mov ax, data mov ds, ax push ds:[0] push ds:[2] pop ds:[2] pop ds:[0] mov ax,4c00h int 21hcode endsend start |
21由42-十进制(16+16)=22得出
data段中的数据为:0123h, 0456h
CPU执行程序,程序返回前,cs=076C、ss=076B、ds=076A
设程序加载后,code段的段地址为X,则data段的段地址为X-2,stack段的段地址为X-1
如果段中的数据占N个字节,则程序加载后,该段实际占有的空间为:(N/16)*16 注意: (N/16)向上取整。
5. 实验任务5
此部分书写内容: 附上源代码文件task5.asm 回答教材中①②③三个问题。 附上回答②时反汇编调试截图,即:在debug中,执行到程序返回前的调试截图。
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
|
assume cs:code, ds:data, ss:stackcode segmentstart: mov ax,stack mov ss, ax mov sp,16 mov ax, data mov ds, ax push ds:[0] push ds:[2] pop ds:[2] pop ds:[0] mov ax,4c00h int 21hcode endsdata segment dw 0123h, 0456hdata endsstack segment dw 0,0stack endsend start |

1、CPU执行程序,程序返回前,data段中的数据为:0123h, 0456h
2、CPU执行程序,程序返回前,cs=076A,ss=076E,ds=076D
3、设程序加载后,code段的段地址为X,则data段的段地址为X+3,stack段的段地址为X+4
6. 实验任务6
此部分书写内容: 回答教材中提出的问题,并按要求说明原因。
实验任务五可以正常执行。如果不指名程序入口,实验任务三和四代码的前几行数据段将被当做代码来执行,
而实验任务五的代码把数据段和栈段的内容放在代码段的后面,所以不会影响程序的正常执行。
7. 实验任务7
此部分书写内容: 附上完整源代码文件task7.asm
附上在debug环境中,执行到程序返回前,查看逻辑段c的数据的截图,以此验证所编写的程序正 确实现了题目要求。
|
1
|
assume cs:code<br>a segment<br> db 1,2,3,4,5,6,7,8<br>a ends<br><br>b segment<br> db 1,2,3,4,5,6,7,8<br>b ends<br><br>c segment <br> db 8 dup(0)<br>c ends<br><br>code segment<br>start:<br> mov ax,a<br> mov ds,ax<br> mov si,0<br> mov cx,8<br> s:mov al,ds:[si]<br> add al,ds:[si+16]<br> mov ds:[si+32],al<br> inc si<br> loop s<br> mov ax,4c00h<br> int 21h<br>code ends<br>end start |

指令长度为4BH ,数据段共占用30H个字节,故 u 0 1a ,g命令执行到编号为16的指令之前,调用d命令查看c处的内存单元内容 c的起始地址为 ds:20 共对8个字节的数字进行加法,故查看到27截至。
8. 实验任务8
此部分书写内容: 附上完整源代码文件task8.asm 附上在debug环境中,执行到程序返回前,查看逻辑段c的数据的截图,以此验证所编写的程序正 确实现了题目要求。
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
|
assume cs:codea segment dw 1,2,3,4,5,6,7,8,9,0ah,0bh,0ch,0dh,0eh,0fh,0ffha endsb segment dw 8 dup(0)b endscode segmentstart: mov ax,a mov ds,ax mov bx,0 mov ax,b mov ss,ax mov sp,16 mov cx,8 s:push [bx] add bx,2 loop s mov ax,4c00h int 21hcode endsend start |
指令总长度为4FH,其中30H为数据段和栈段的内容,故u 0 1E
调用d命令查询cpu执行后栈段中的内容如图

浙公网安备 33010602011771号