完成 32 位无符号数的加法、减法,16 位乘以 16 位,32 位除以 16 位除法的四则运算练习。
A DW 1234H, 5678H ;被加数
,可以看到这一句定义了连续的两个字数据,数据地址按先后顺序由低到高排列,又因为每一个字在存储时按找小段存储规则,所以它在内存中的存储情况时34 12 78 56
,解释称十六进制数就是0x56781234
DATA SEGMENT
A DW 1234H, 5678H ;被加数 32位数分两个16位存 56781234H
B DW 0FEDCH, 123AH 加数 32位数分两个16位存 FEDC123AH
C DW 2 DUP (?) ;预留和 留两个双字(16位)空间存加法结果
AD DW 0FEDCH, 0BA98H;被减数 BA98FEDCH
BD DW 1234H, 789AH ;减数 789A1234H
CD DW 2 DUP (?) ;预留差
A1 DW 0D678H ;被乘数
B1 DW 0012H ;乘数
C1 DW 2 DUP (?) ;预留积
A2 DW 5678H, 0234H ;被除数 02345678
B2 DW 0F234H ;除数 F234
C2 DW 2 DUP (?) ;预留商,余数
DATA ENDS
STACK1 SEGMENT STACK
;DB 100 DUP(?)
buffer db 100 dup(0)
STACK1 ENDS
CODE SEGMENT
ASSUME CS:CODE,DS:DATA,SS:STACK1
START PROC FAR
;标准序
PUSH DS
MOV AX, 0
PUSH AX
MOV AX, DATA
MOV DS, AX
;32位+32位 结果68B31110H
MOV AX, A
ADD AX, B
MOV C, AX ;低16位加完存在C,进位在CF
MOV AX, A+2
ADC AX, B+2 ;ADC带进位加,处理高16位,存在C+2
MOV C+2, AX
;32位-32位 结果41FEECA8H
MOV AX, AD
SUB AX, BD
MOV CD, AX
MOV AX, AD+2
SBB AX, BD+2
MOV CD+2, AX
;16位乘16位 结果000F1470H
MOV AX, A1
MOV BX, B1
MUL BX
MOV C1, AX
MOV C1+2, DX
;32位除16位 结果254H..7568H
MOV DX, A2+2
MOV AX, A2
MOV BX, B2
DIV BX
MOV C2, AX ;商在AX
MOV C2+2, DX ;余数在DX
RET
START ENDP
CODE ENDS
END START
;宏函数,输出回车
CRLF MACRO
MOV DL, 0DH
MOV AH, 02H ;INT21的2号功能(单个字符输出)
INT 21H
MOV DL, 0AH
MOV AH, 02H
INT 21H ;连续输出0DH和0AH,显示回车
ENDM
DATA SEGMENT
NUM DB 12H,88H,82H,89H,33H,90H,0H,10H,0BDH,01H ;10个8位数据
Positive DB DUP (0) ;正数个数 4
Negative DB DUP (0) ;负数个数 5
Zero DB DUP (0) ;0个数 1
SUM DW 2 DUP (0) ;总和
MESP DB 'Positive number:$'
MESN DB 'Negative number:$'
MESZ DB 'Zero number:$'
MESS DB 'Sum = $'
result DB 0,0,'$'
DATA ENDS
STACK1 SEGMENT STACK
;DB 100 DUP(?)
buffer db 100 dup(0)
STACK1 ENDS
CODE SEGMENT
ASSUME CS:CODE,DS:DATA,SS:STACK1 ;设置段寄存器
START PROC FAR
PUSH DS
MOV AX, 0
PUSH AX
MOV AX, DATA
MOV DS, AX
MOV CX,10 ;循环10次
LEA SI,NUM
MOV BX,0
LAB1:
MOV DL,[SI]
CMP DL,0 ;判断num是否为0
JG LAB2 ;num>0,跳转到LAB2
JL LAB3 ;num<0,跳转到LAB3
INC ZERO ;num=0,ZERO加1
JMP LAB4
LAB2:
INC Positive ;负数+1
JMP LAB4
LAB3:
INC Negative ;正数+1
LAB4:
MOV AL,[SI]
CBW ;符号拓展,8位拓展为16位
ADD SUM,AX ;+sum
ADC [SUM+2],0
INC SI
LOOP LAB1 ;循环
RET
START ENDP
CODE ENDS
END START
MOV DX,OFFSET MESP ;显示“Positive number:”提示
MOV AH,9
INT 21H
MOV BL,Positive ;取字节变量positive
MOV AL,BL
SHR AL,4
CALL ToASCII ;把高四位转换为对应的ASCII码
MOV [result],AL
MOV AL,BL
CALL ToASCII ;把低四位转换为对应的ASCII码
MOV [result+1],AL
MOV DX,OFFSET result
MOV AH,9
INT 21H
ToASCII PROC
AND AL,0FH
ADD AL,'0'
CMP AL,'9'
JBE LAB5
ADD AL,7
LAB5:
RET
ToASCII ENDP
输入小写字母用 INT 21 的 0AH 号功能,将读入的数据存放在缓冲区 SMALL 中,其中 SMALL
的笫一个字节指岀缓冲区能容纳的字节数,不能为 0(程序暂定为 50),第二个字节保留,以用作存放
实际键入的输入字符的个数;从笫三个字节开始存放从键盘上输入字符的 ASCII 码,所以转换时要
从 SMALL 的笫三个字节,即 SMALL+2 开始。
SMALL 中存放的是小写字母的 ASSII 码,将此值减去 20H,即为大写字母的 ASSII 码,将其依次
存放在名为 CAPITAL 的数据段中,然后用 INT 21 中的 09H 功能输出。
CRLF MACRO
MOV DL, 0DH
MOV AH, 02H ;INT21的2号功能(单个字符输出)
INT 21H
MOV DL, 0AH
MOV AH, 02H
INT 21H ;连续输出0DH和0AH,显示回车
ENDM
DATA SEGMENT
MES1 DB 'PLEASE INPUT THE SMALL LETTER,ENDED WITH ".":$'
MES2 DB 'THE CAPTAL LETTER IS:$'
SMALL DB 50 ; 预留键盘输入缓冲区长度为50个
DB 0 ; 预留实际键盘输入字符数的个数
DB 50 DUP(0) ; 存放输入符号串的位置
CAPITAL DB 50 DUP(0) ; 预留大写字母缓冲区长度为50个
DATA ENDS
STACK1 SEGMENT STACK
DB 100 DUP (0)
STACK1 ENDS
CODE SEGMENT
ASSUME CS:CODE,DS:DATA,SS:STACK1
START PROC FAR
PUSH DS
MOV AX, 0
PUSH AX
MOV AX, DATA
MOV DS, AX ;数据段DS指向DATA
MOV AH, 9 ;INT21的9号功能(输出)
LEA DX, MES1 ;输出信息位置
INT 21H ;输岀提示信息MES1
CRLF ;宏调用,输出回车
MOV AH, 0AH ;INT21的10号功能(输入)
LEA DX, SMALL ;输入信息缓存位置
;INC DX
INT 21H ;接收小写字符串
CRLF ;宏调用,输出回车
;转换部分利用INT21的10号功能得到的字符串长度实现,没有考虑超长问题
;LEA SI,SMALL
;LEA DI,CAPITAL
;XOR CH,CH ;CL中存储循环次数,注意最后输入的.不算
;MOV CL,[SI+1]
;ADD SI,2 ;指向真正输入数据
;DEC CL
;LOOPSIGN: ;循环cx次,把小写字符转大写存入CAPITAL
;MOV AL,[SI]
;SUB AL,20H
;MOV [DI],AL
;INC DI
;INC SI
;LOOP LOOPSIGN
;转换时利用句号判断终止时机,进行了长度限制,比上面那个好
LEA BX, SMALL+2
LEA DI, CAPITAL
MOV CX, 20 ;最多20个字符
LAB:
MOV AL, [BX]
CMP AL, 2EH ;是否遇到句号.
JE KE
SUB AL, 20H ;转为大写,ASCLL-20H
MOV [DI], AL
INC BX
INC DI
LOOP LAB
KE:
MOV AL, '$' ;大写字符串后加“$”
MOV [DI], AL
MOV DX, OFFSET MES2 ;输岀提示信息MES2
MOV AH, 9
INT 21H
CRLF ;宏调用,输出回车
MOV DX, OFFSET CAPITAL
MOV AH, 9 ;输岀大写字符串
INT 21H
RET
START ENDP
CODE ENDS
END START