clear MACRO Field, size
xor cx,cx
mov cl,size
mov al,20h
lea di,Field
rep stosb
ENDM
Extrn divFloat:Far
Public Len1,Num1,Len2,Num2,Bin1,Bin2,AnsMsg,Dividend,Divisor
Public Sign,Quotient,Remainder
TITLE prog04a: links with Extrn divFloat
.MODEL SMALL
.STACK 100h
.DATA
PgmMsg db 0dh,0ah,0dh,0ah
db "This Program simulates Floating-point Division.", "$"
EnterMsg1 db 0dh,0ah,0dh,0ah
db "Enter Dividend in the range of -255 thru 255, now!",0dh,0ah
db "To Exit, press key only.", 0dh,0ah, "$"
EnterMsg2 db 0dh,0ah,0dh,0ah
db "Enter Divisor in the range of 1 thru 255, now!",0dh,0ah
db "To Exit, press key only.", 0dh,0ah, "$"
InBuff1 db 05
Len1 db 00
Num1 db 20h,20h,20h,20h,0dh
InBuff2 db 04
Len2 db 00
Num2 db 20h,20h,20h,0dh
InvalMsg1 db 0dh,0ah
db "An Invalid Number was entered for Dividend!", 0dh,0ah, "$"
db "Enter a Number in the range of -255 thru 255.", 0dh,0ah,"$"
InvalMsg2 db 0dh,0ah
db "An Invalid Number was entered for Divisor!", 0dh,0ah, "$"
db "Enter a Number in the range of 1 thru 255.", 0dh,0ah,"$"
ZeroMsg db 0dh,0ah
db "The Zero was entered for Divisor!", 0dh,0ah, "$"
db "Enter a Nonzero number in 1 thru 255.", 0dh,0ah, "$"
Factor db 1,1,10,100
Bin1 dw 0000
Bin2 dw 0000
AnsMsg db 0dh,0ah,0dh,0ah, "When the Dividend is "
Dividend db 20h,20h,20h,20h, " and the Divisor is "
Divisor db 20h,20h,20h
db 0dh,0ah, "the Result is "
Sign db 20h
Quotient db 20h,20h,20h,2eh
Remainder db 20h,20h,0dh,0ah,"$"
ByeMsg db 0dh,0ah, "Bye for Now!", 0dh,0ah, "$"
.CODE
MAIN PROC
mov ax,@data ; get @ of data segment
mov ds,ax ; set ds and es to data segment
mov es,ax
lea dx,PgmMsg ; point to first message $ delimits message
mov ah,09h ; indicate output
int 21h ; print message
Start: call ClrStorage ; clear work area
call GetDividnd ; get input from user
call ChkDividnd ; check and adjust input to binary
call GetDivisor ; get input from user
call ChkDivisor ; check and adjust input to binary
call divFloat ; perform math
jmp Start ; do again
MAIN ENDP
ClrStorage PROC
clear Dividend,04 ; Clear Dividend field
clear Divisor,03 ; Clear Divisor field
clear Sign,04 ; Clear Sign & Quotient fields
clear Remainder,02 ; Clear Remainder field
ret
ClrStorage ENDP
GetDividnd PROC
lea dx,EnterMsg1 ; get @ of message to prompt user
mov ah,09h
int 21h ; print message
lea dx,InBuff1 ; point dx to @ of input buffer
; byte 0 of buffer is max allowable input
; byte 1 will be count of data input
; byte 2 is start of data
mov ah,0ah ; indicate that input will occur
int 21h ; perform input
xor ch,ch ; clear high byte of cx
mov cl,Len1 ; get count of data read in
cmp cl,00 ; if no data input
je Exit1 ; then terminate program
ret
Exit1: lea dx,ByeMsg ; point to exit message
mov ah,09h ; output function
int 21h ; perform output
mov ah,4ch ; terminate function
int 21h ; terminate
GetDividnd ENDP
ChkDividnd PROC
Again1: lea di,Factor ; destination index to a list of factors
xor dx,dx ; zero out dx, ax, and ch
xor ax,ax ; dx and ax used for math
xor ch,ch
mov cl,Len1 ; initialize cx to length of input data
lea si,Num1 ; point si to input data
mov al,[si] ; fetch digit to al register
cmp al,'-' ; if character is -
je LessZero ; then handle - value
Rest1: cmp al,30h ; check that the value is between
jl Inval1 ; 30h and 39h - ascii 0-9
cmp al,39h
ja Inval1
and al,0Fh ; cheater's convert - throw out the 3
push di ; preserve the beginning @ of factor list
add di,cx ; increment into factor list by # of
; digits in input number
mov bl,[di] ; move factor to low byte of bx
mul bl ; ax = al * bx
add dx,ax ; add ax to dx (our accumulated value)
inc si ; point to the next input digit
pop di ; restore di to beginning of factor list
mov al,[si] ; get next digit of input
loop Rest1 ; do again until cx = 0
mov Bin1,dx ; store our final binary value in Bin1
ret ; return to call
LessZero: mov ah,'-' ; put - in Sign variable - 8086 can not
mov Sign,ah ; write a literal directly to memory
dec cx ; move past the sign bit
inc si
mov al,[si] ; get the next digit in the input buffer
jmp Rest1 ; and process normally
Inval1: lea dx,InvalMsg1 ; point to invalid message
mov ah,09h ; indicate output
int 21h ; output message
call GetDividnd ; ask the user again for a number
jmp Again1 ; and recheck input
ChkDividnd ENDP
GetDivisor PROC
lea dx,EnterMsg2 ; print input message
mov ah,09h
int 21h
lea dx,InBuff2 ; get input
mov ah,0ah
int 21h
xor ch,ch ; get count of digits
mov cl,Len2
cmp cl,00 ; if no input then exit
je Exit2
ret
Exit2: lea dx,ByeMsg
mov ah,09h
int 21h
mov ah,4ch
int 21h
GetDivisor ENDP
; Note - divisor only allows + values, final sign
; will be set based on sign flag set by ChkDividend
ChkDivisor PROC
Again2: lea di,Factor
xor dx,dx
xor ax,ax
xor ch,ch
mov cl,Len2
lea si,Num2
Rest2: mov al,[si]
cmp al,30h
jl Inval2
cmp al,39h
ja Inval2
and al,0Fh
push di
add di,cx
mov bl,[di]
mul bl
add dx,ax
inc si
pop di
loop Rest2
cmp dx,0
je ZeroErr
mov Bin2,dx
ret
Inval2: lea dx,InvalMsg2
mov ah,09h
int 21h
call GetDivisor
jmp Again2
ZeroErr: lea dx,ZeroMsg
mov ah,09h
int 21h
call GetDivisor
jmp Again2
ChkDivisor ENDP
END Main