实验3 转移指令跳转原理及其简单应用编程
实验结论
1. 实验任务1
使用任何一款文本编辑器,录入8086汇编程序源码task1.asm。
assume cs:code, ds:data data segment x db 1, 9, 3 len1 equ $ - x y dw 1, 9, 3 len2 equ $ - y data ends code segment start: mov ax, data mov ds, ax mov si, offset x mov cx, len1 mov ah, 2 s1:mov dl, [si] or dl, 30h int 21h mov dl, ' ' int 21h inc si loop s1 mov ah, 2 mov dl, 0ah int 21h mov si, offset y mov cx, len2/2 mov ah, 2 s2:mov dx, [si] or dl, 30h int 21h mov dl, ' ' int 21h add si, 2 loop s2 mov ah, 4ch int 21h code ends end start
① line27, 汇编指令 loop s1 跳转时,是根据位移量跳转的。通过debug反汇编,查看其机 器码,分析其跳转的位移量是多少?(位移量数值以十进制数值回答)从CPU的角度,说明 是如何计算得到跳转后标号s1其后指令的偏移地址的。
s1标号处的地址是 000D ,即十进制的13;loop后面一条指令的地址是001B,即十进制27,相减得到-14,loop指令在对应的机器码中包含转移的位移而不是目的地址。其跳转位移量为s1到loop s1的地址差值。
② line44,汇编指令 loop s2 跳转时,是根据位移量跳转的。通过debug反汇编,查看其机 器码,分析其跳转的位移量是多少?(位移量数值以十进制数值回答)从CPU的角度,说明 是如何计算得到跳转后标号s2其后指令的偏移地址的。
跳转的位移量=0029 h- 0039 h=41-57=-16,loop指令在对应的机器码中包含转移的位移而不是目的地址。其跳转位移量为s2到loop s2的地址差值。
2. 实验任务2
程序task2.asm源码
1 assume cs:code, ds:data 2 3 data segment 4 dw 200h, 0h, 230h, 0h 5 data ends 6 7 stack segment 8 db 16 dup(0) 9 stack ends 10 11 code segment 12 start: 13 mov ax, data 14 mov ds, ax 15 16 mov word ptr ds:[0], offset s1 17 mov word ptr ds:[2], offset s2 18 mov ds:[4], cs 19 20 mov ax, stack 21 mov ss, ax 22 mov sp, 16 23 24 call word ptr ds:[0] 25 s1: pop ax 26 27 call dword ptr ds:[2] 28 s2: pop bx 29 pop cx 30 31 mov ah, 4ch 32 int 21h 33 code ends 34 end start
① 根据call指令的跳转原理,先从理论上分析,程序执行到退出(line31)之前,寄存器(ax) = 21 寄存器(bx) = 26 寄存器(cx) = 076C
② 对源程序进行汇编、链接,得到可执行程序task2.exe。使用debug调试,观察、验证调试 结果与理论分析结果是否一致。
(ax)=pop ax的偏移地址;(bx)=pop bx的偏移地址,(cx)=段地址
3. 实验任务3
针对8086CPU,已知逻辑段定义如下:
data segment
x db 99, 72, 85, 63, 89, 97, 55
len equ $- x
data ends
编写8086汇编源程序task3.asm,在屏幕上以十进制形式输出data段中这一组连续的数据,数据和数据 之间以空格间隔。
要求: 编写子程序printNumber
功能:以十进制形式输出一个两位数
入口参数:寄存器ax(待输出的数据 --> ax)
出口参数:无
编写子程序printSpace
功能:打印一个空格
入口参数:无
出口参数:无
在主体代码中,综合应用寻址方式和循环,调用printNumber和printSpace, 实现题目要求。
程序源码task3.asm
1 assume cs:code, ds:data 2 data segment 3 x db 99, 72, 85, 63, 89, 97, 55 4 len equ $- x 5 data ends 6 code segment 7 start: 8 mov ax,data 9 mov ds,ax 10 mov si,0 11 mov cx,len 12 13 14 s: 15 call printNumber 16 call printSpace 17 18 inc si 19 loop s 20 21 mov ax,4c00h 22 int 21h 23 24 printNumber: 25 mov ah,0 26 mov al,ds:[0+si] 27 mov bl,10 ;将两位数的十位和个位分别存储在两个内存单元中 28 div bl 29 mov ds:[len+si],al 30 mov ds:[len+1+si],ah 31 32 mov ah,2 ; 输出十位数字 33 mov dl,ds:[len+si] 34 add dl,30H 35 int 21h 36 37 mov ah,2 ; 输出个位数字 38 mov dl,ds:[len+1+si] 39 add dl,30h 40 int 21h 41 42 ret 43 44 45 printSpace: 46 mov ah,2 ; 输出空格 47 mov dl,20H 48 int 21h 49 50 ret 51 52 53 code ends 54 end start
运行测试截图:
4. 实验任务4
针对8086CPU,已知逻辑段定义如下:
data segment
str db 'try'
len equ $ - str
data ends
编写8086汇编源程序task4.asm,在屏幕上以指定颜色、指定行,在屏幕上输出字符串。
要求:
编写子程序printStr
功能:在指定行、以指定颜色,在屏幕上显示字符串
入口参数
字符串首字符地址 --> ds:si(其中,字符串所在段的段地址—> ds, 字符串起始地址的偏 移地址—> si)
字符串长度 --> cx
字符串颜色 --> bl
指定行 --> bh (取值:0 ~24)
出口参数:无
在主体代码中,两次调用printStr,使得在屏幕最上方以黑底绿字显示字符串,在屏幕最下方以黑 底红色显示字符串
程序源码task4.asm
1 assume cs:code 2 data segment 3 str db 'try',0 ;data段定义好要输出的字符串,以'0'作为结束标志 4 len equ $ - str 5 data ends 6 7 stack segment 8 db 128 dup(0) 9 code segment 10 start: mov ax,data 11 mov ds,ax 12 mov ax,stack 13 mov ss,ax 14 mov sp,128 15 call init_data ;初始化数据 16 call printStr ;显示的方法 17 call init_data2 18 call printStr 19 mov ax,4c00h 20 int 21h 21 22 init_data2: mov ax,0B800h 23 mov es,ax 24 mov dh,24 ;指定行号 25 mov dl,0 ;指定列号 26 mov cl,00000100B;指定颜色 27 mov si,0 28 mov di,0 29 ret 30 31 init_data: mov ax,0B800h 32 mov es,ax 33 mov dh,0 ;指定行号 34 mov dl,0 ;指定列号 35 mov cl,00000010B;指定颜色 36 mov si,0 37 mov di,0 38 ret 39 40 printStr: ;call clear_screen ;清屏 41 call getRow ;获取指定行号的字节偏移数 42 call getCol ;获取指定列号 43 call show_String ;真正的显示字符串方法 44 ret 45 46 clear_screen: push cx 47 push dx 48 push es 49 push bx 50 mov cx,2000 ;一页有2000字符,每个字符2个字节 51 mov dx,0700h ;将屏幕上的双字用0700h代替 52 mov bx,0 53 clearScreen: mov es:[bx],dx 54 add bx,2 55 loop clearScreen 56 57 pop bx 58 pop es 59 pop dx 60 pop cx 61 ret 62 63 show_String: push cx ;保存下面将要用到的寄存器 64 push ds 65 push es 66 push dx 67 push si 68 push di 69 70 mov dh,cl ;高位存颜色 71 mov cx,0 72 showString: mov cl,ds:[si] 73 jcxz showStringRet 74 mov dl,ds:[si] ;低位存字符 75 mov es:[di],dx 76 add di,2 77 inc si 78 jmp showString 79 80 showStringRet: pop di ;还原寄存器 81 pop si 82 pop dx 83 pop es 84 pop ds 85 pop cx 86 ret 87 88 getRow: mov al,dh 89 mov bl,160 ;一行80字符,160字节 90 mul bl 91 mov di,ax 92 ret 93 94 getCol: mov al,dl 95 mov bl,2 96 mul bl 97 add di,ax 98 ret 99 100 code ends 101 end start
运行测试截图
5. 实验任务5
针对8086CPU,针对8086CPU,已知逻辑段定义如下:
data segment
stu_no db '20498329042'
len = $ - stu_no
data ends
在80×25彩色字符模式下,在屏幕最后一行正中间显示学号。要求输出窗口蓝底,学号和两侧折线,以 白色前景色显示。
程序源码task5.asm
1 assume ds:data, cs:code 2 data segment 3 stu_no db '201983290195' 4 ;db 2H,24H,71H ;字符串属性值 5 len = $ - stu_no 6 data ends 7 8 code segment 9 start: mov ax,data 10 mov ds,ax ;字符串及属性值所在段的段地址送入ds 11 12 mov ax,0b800H 13 mov es,ax ;80×25彩色字符模式显示缓冲区段地址送入es 14 15 ; 添加代码,通过循环逐个将每个字符及其属性送入相应的显示缓冲区对应行 16 ; 即:将data段的字符及属性通过循环逐个mov到显示缓冲区(es)段相应的单元内 17 18 ; 可以先尝试分别写三段代码,每次完成一行的显示 19 ; 程序运行起来后,再尝试通过灵活的寻址方式和循环,对三段代码修改和简化 20 ; 学习第10章子程序后,还可以进一步完善优化,设计子程序,将行号、列号、颜色属性设置成入口参数 21 mov bx,0 22 mov si,0 23 mov cx,80 24 25 s1: ; mov ax,[bx] 26 ; mov es:[bx+720h][si],ax 27 mov al,23 ;存放颜色属性值蓝色 28 mov es:[bx+1h][si],al 29 inc bx 30 inc si 31 loop s1 32 33 34 mov bx,0 35 mov cx,80 36 mov si,160 37 38 s2: ; mov ax,[bx] 39 ;mov es:[bx+720h][si],ax 40 mov al,23 ;存放颜色属性值蓝色 41 mov es:[bx+1h][si],al 42 inc bx 43 inc si 44 loop s2 45 46 47 mov bx,0 48 mov cx,80 49 mov si,320 50 51 s3: ; mov ax,[bx] 52 ;mov es:[bx+720h][si],ax 53 mov al,23 ;存放颜色属性值蓝色 54 mov es:[bx+1h][si],al 55 inc bx 56 inc si 57 loop s3 58 59 mov bx,0 60 mov cx,1760 61 mov si,480 62 63 s4: ; mov ax,[bx] 64 ;mov es:[bx+720h][si],ax 65 mov al,23 ;存放颜色属性值蓝色 66 mov es:[bx+1h][si],al 67 inc bx 68 inc si 69 loop s4 70 71 72 mov bx,0 73 mov cx,32 74 mov si,3840 75 76 s251: mov ax,'-' 77 mov es:[bx+0h][si],ax 78 mov al,23 ;存放颜色属性值蓝色 79 mov es:[bx+1h][si],al 80 inc bx 81 inc si 82 loop s251 83 84 85 mov bx,0 86 mov cx,80 87 mov si,3872 88 89 s252: mov ax,'-' 90 mov es:[bx+0h][si],ax 91 mov al,23 ;存放颜色属性值蓝色 92 mov es:[bx+1h][si],al 93 inc bx 94 inc si 95 loop s252 96 97 98 99 mov bx,0 100 mov cx,len 101 mov si,2080 102 103 s25: mov ax,[bx] 104 mov es:[bx+720h][si],ax 105 mov al,23 ;白底蓝色 106 mov es:[bx+721h][si],al 107 inc bx 108 inc si 109 loop s25 110 111 mov ax,4c00h 112 int 21h 113 code ends 114 end start
运行测试截图
posted on 2021-11-28 14:10 FlamingHotCheeto 阅读(42) 评论(2) 编辑 收藏 举报