1程序分析
分析下列程序,指出运行结果。
DAT1 DB 0, 1, 2, 3, 4,5, 6, 7, 8,9
DAT2 DB 5 DUP(?)
MOV CX, 5 ;—
MOV BX, 5 ;—
MOV SI, O
MOV DI, O
NEXT: MOV AL, DAT1[BX+SI];—,本行寻址方式为—
MOV DAT2[DI],AL ;—
INC SI
INC DI
LOOP NEXT
(1) 为加;行指令后加注释,注释不需很繁琐,解释清楚本行操作意图即可。
(2) 该程序完成的功能是什么? 程序执行后,DAT2数据区的内容是什么?
2、程序设计
建立两个操作:一个操作将16进制数变换成 ASCII码,一个操作将 ASCII 码字符在屏幕上显示输出。
(1)第一步应分析要求,选择合适的结构设计流程图。
例如:本设计采用( )结构。(注意选择的结构和下面自己编写的程序对应。)
(2) 请从数据段开始,编写完成功能的汇编程序。
该程序的功能是将 DAT1 数据区的前 5 个字节复制到 DAT2 的前 5 个字节中。DAT2 的后面 5 个字节内容未初始化,因此输出时可能是随机值。
section .data
; 存储 ASCII 码字符的数组
arr db '0123456789abcdef'
section .text
global main
; 将 1 个 16 进制数转换成 2 个 ASCII 码字符
hex_to_ascii:
push ax ; 保存现场
; 右移 4 位获取高位,通过 arr 数组访问相应的字符
mov al, bh
shr al, 4
mov bl, [arr + al]
mov [di], bl
inc di
; 取低位,通过 arr 数组访问相应的字符
mov al, bh
and al, 0x0f
mov bl, [arr + al]
mov [di], bl
inc di
pop ax ; 恢复现场
ret
; 在屏幕上显示一个字符串
print_string:
pusha ; 保存现场
; 设置显示字符的属性并清屏
mov ah, 0x0
mov bh, 0x0
mov al, 0x0
mov cx, 0x00fa ; 屏幕高度
mov dx, 0x184f ; 屏幕宽度
int 0x10 ; BIOS 中断
; 计算字符串长度并输出每个字符
xor ah, ah ; ah = 0
mov si, 0 ; si = 0
.loop:
mov al, [bx + si] ; 取一个字符
cmp al, 0 ; 判断字符串是否结束
je .done
mov ah, 0x0e ; 从 al 中取得字符并显示
int 0x10 ; BIOS 中断
inc si ; 指向下一个字符
jmp .loop ; 处理下一个字符
.done:
popa ; 恢复现场
ret
main:
; 将 16 进制数 0x4a 转换成 ASCII 码字符串
mov bh, 0x4a
mov di, buffer
call hex_to_ascii
; 在屏幕上显示转换后的字符串
mov bx, buffer
call print_string
; 程序结束
mov eax, 0
ret
section .bss
buffer resb 5 ; 用于存储转换后的 ASCII 码字符串
本设计采用顺序结构。
上面的程序将 16 进制数 0x4a 转换成 ASCII 码字符串,并在屏幕上显示输出。程序的主要思路是:
定义一个包含 16 进制数字与 ASCII 码字符的数组 arr;
将一个 16 进制数转换成 2 个 ASCII 码字符的函数 hex_to_ascii;
输出一个字符串的函数 print_string;
在 main 函数中将 0x4a 转换成 ASCII 码字符串并输出。
注意,此处为了简化程序并且使输出结果易于观察,定义的 ASCII 码字符数组只包含了 0-9 和 a-f,因此在实际运用中需要根据具体要求来定义这个数组。