mirror of
https://github.com/SEPPDROID/Digital-Research-Source-Code.git
synced 2025-10-22 07:54:25 +00:00
305 lines
13 KiB
Plaintext
305 lines
13 KiB
Plaintext
NAME FPCNV
|
|
CSEG
|
|
|
|
PUBLIC FFLOAT,FFIX,FINP,FOUT
|
|
EXTRN FSTOR,FZERO,FABS,FTEST,FLOAD,FMUL
|
|
EXTRN FDIV,FADD,ADD10,LSH,RSH,FCOMP
|
|
EXTRN OVER,ACCE,ACCS,ACC1,ACC2,ACC3,SF
|
|
EXTRN FTEN,RND0
|
|
EXTRN ADRL,ADRH,TMP1,TMP2,TMP3,VALE,VAL1,VAL2,VAL3,TMP4
|
|
; 8080 BINARY FLOATING POINT SYSTEM
|
|
; FORMAT CONVERSION PACKAGE
|
|
; PROGRAMMER CAL OHME
|
|
; DATE 26 DECEMBER 1973
|
|
|
|
|
|
; SUBROUTINE TO CONVERT FROM FIXED
|
|
; POINT TO FLOATING POINT FORMAT.
|
|
FFLOAT: MOV L,E; INPUT EXPONENT
|
|
MOV E,D; 4TH INPUT FRACTION
|
|
MOV D,C; 3RD INPUT FRACTION
|
|
MOV C,B; 2ND INPUT FRACTION
|
|
MOV B,A; 1ST INPUT FRACTION
|
|
MOV A,L; INPUT EXPONENT
|
|
XRI 80H; APPLY EXPONENT BIAS
|
|
LXI H,ACCE; TO ADDR ACCUM EXPONENT
|
|
MOV M,A; ACCUMULATOR EXPONENT
|
|
INR L; TO ADDRESS ACCUM SIGN
|
|
MVI M,80H; SET ACCUM SIGN POSITIVE
|
|
INR L; TO ADDR ACCUM 1ST FRCTN
|
|
MOV A,B; 1ST INPUT FRACTION
|
|
ANA A ; SET SIGN BIT
|
|
RAL ; INPUT SIGN TO CARRY
|
|
JMP ADD10; COMPLETE CONVERSION
|
|
; SUBROUTINE TO CONVERT FROM FLOATING
|
|
; POINT TO FIXED POINT FORMAT.
|
|
FFIX: LXI H,ACCE; TO ADDRESS SCRATCH BANK
|
|
MOV A,M; ACCUMULATOR EXPONENT
|
|
ANA A ; SET CONTROL BITS
|
|
JZ FIX1; IF ACCUMULATOR IS ZERO
|
|
MOV A,E; INPUT EXPONENT
|
|
ADI 7FH; APPLY BIAS - 1
|
|
SUB M; SHIFT COUNT - 1
|
|
RC ; RETURN IF ACCUM TOO LARGE
|
|
CPI 1FH; COMPARE TO LARGE SHIFT
|
|
JNC FIX1; IF ACCUMULATOR TOO SMALL
|
|
ADI 1; SHIFT COUNT
|
|
MVI L,LOW(ACC1); TO ADDR ACCUM 1ST FRCTN
|
|
MOV B,M; ACCUMULATOR 1ST FRACTION
|
|
INR L; TO ADDR ACCUM 2ND FRCTN
|
|
MOV C,M; ACCUMULATOR 2ND FRCTN
|
|
INR L; TO ADDR ACCUM 3RD FRCTN
|
|
MOV D,M; ACCUMULATOR 3RD FRCTN
|
|
CALL RSH; POSITION THE FRACTION
|
|
MVI L,LOW(ACCS); TO ADDR ACCUM SIGN
|
|
MOV A,M; ACCUMULATOR SIGN
|
|
ANA A ; SET CONTROL BITS
|
|
CP FCOMP; COMPLEMENT FRCTN IF NEG
|
|
MVI A,1; NON-ZERO
|
|
ORA B; SET CONTROL BITS FOR EXIT
|
|
MOV A,B; 1ST RESULT
|
|
MOV B,C; 2ND RESULT
|
|
MOV C,D; 3RD RESULT
|
|
MOV D,E; 4TH RESULT
|
|
RET ; RETURN TO CALLER
|
|
FIX1: XRA A; ZERO
|
|
MOV B,A; ZERO
|
|
MOV C,A; ZERO
|
|
MOV D,A; ZERO
|
|
RET ; RETURN TO CALLER
|
|
DB 0; CHECKSUM WORD
|
|
; INP SUBROUTINE ENTRY POINT.
|
|
; INITIALIZE TEMPORARY STORAGE.
|
|
FINP: MOV E,M; FIRST CHARACTER OF STRING
|
|
CALL SVAD; SET CHAR ADDR, PNT FLG, EXP
|
|
INR L; TO ADDRESS VALUE SIGN
|
|
MVI M,80H; SET VALUE SIGN POSITIVE
|
|
LXI H,ACCE; TO ADDR ACCUM EXPONENT
|
|
MOV M,D; SET ACCUM TO ZERO
|
|
MOV A,E; FIRST CHARACTER
|
|
CPI 0F0H; COMPARE TO SPACE
|
|
JZ INP1; IF SPACE CHARACTER
|
|
CPI 0FBH; COMPARE CHAR TO PLUS
|
|
JZ INP1; IF PLUS SIGN
|
|
CPI 0FDH; COMPARE TO MINUS
|
|
JNZ INP2; IF NOT MINUS SIGN
|
|
LXI H,TMP3; TO ADDR VALUE SIGN
|
|
MOV M,D; SET VALUE SIGN NEGATIVE
|
|
; ANALYZE NEXT CHARACTER IN STRING.
|
|
INP1: CALL CHAD; CALL CHAR ADDR SBRTN
|
|
MOV A,M; NEXT CHARACTER
|
|
INP2: MVI B,0; DIGIT 2ND WD OR DEC EXP
|
|
CPI 0FEH; COMPARE TO DECIMAL POINT
|
|
JZ INP3; IF DECIMAL POINT
|
|
CPI 15H; COMPARE TO EXPONENT SIGN
|
|
JZ INP4; IF EXPONENT SIGN
|
|
CPI 0AH; SET CARRY IF CHAR IS DIGIT
|
|
JNC INP8; IF CHAR IS NOT A DIGIT
|
|
LXI H,TMP4; TO ADDR CURRENT DIGIT
|
|
MOV M,A; SAVE CURRENT DIGIT
|
|
LXI H,FTEN; TO ADDR FLOATING TEN
|
|
CALL FMUL; MULTIPLY BY TEN
|
|
MVI L,LOW(VALE); TO ADDR VALUE
|
|
CALL FSTOR; STORE OLD VALUE TIMES TEN
|
|
INR L; TO ADDR CURRENT DIGIT
|
|
MOV A,M; CURRENT DIGIT
|
|
MVI B,0; CLEAR 2ND WORD OF DIGIT
|
|
MOV C,B; CLEAR 3RD WORD OF DIGIT
|
|
MOV D,B; CLEAR 4TH WORD OF DIGIT
|
|
MVI E,8; INDICATE DIGIT IS IN REG A
|
|
CALL FFLOAT; CONVERT DIGIT TO FLOATING PNT
|
|
MVI L,LOW(VALE); TO ADDR VALUE
|
|
CALL FADD ; ADD OLD VALUE TIMES TEN
|
|
MVI L,LOW(TMP2); TO ADDR DEC PNT FLAG
|
|
MOV A,M; DECIMAL POINT FLAG
|
|
ANA A ; SET CONTROL BITS
|
|
JZ INP1; IF NO DEC PNT ENCOUNTERED
|
|
DCR L; TO ADDR INPUT EXPONENT
|
|
MOV B,M; INPUT EXPONENT
|
|
DCR B; DECREMENT INPUT EXPONENT
|
|
MOV M,B; UPDATE INPUT EXPONENT
|
|
JMP INP1; TO GET NEXT CHARACTER
|
|
INP3: LXI H,TMP2; TO ADDR DEC PNT FLAG
|
|
XRA M; ZERO IF FLAG SET
|
|
MOV M,A; SET DEC PNT FLAG
|
|
JNZ INP1; IF FLAG NOT ALREADY SET
|
|
JMP INP8; IF 2ND DEC PNT
|
|
; PROCESS DECIMAL EXPONENT.
|
|
INP4: CALL CHAD; CALL CHAR ADDR SBRTN
|
|
MOV A,M; NEXT CHARACTER OF STRING
|
|
MOV B,A; CURRENT CHARACTER
|
|
SUI 0FDH; COMPARE TO MINUS CHAR
|
|
MOV E,A; CHAR - MINUS SIGN
|
|
JZ INP5; IF MINUS SIGN
|
|
ADI 2; COMPARE TO PLUS CHAR
|
|
MOV A,B; CURRENT CHARACTER
|
|
JNZ INP6; IF NOT PLUS SIGN
|
|
INP5: INR L; TO ADDRESS NEXT CHAR
|
|
MOV A,M; NEXT CHARACTER OF STRING
|
|
INP6: MVI B,0; POSSIBLE DEC EXPONENT
|
|
CPI 0AH; SET CARRY IF CHAR IS DIGIT
|
|
JNC INP8; IF CHAR IS NOT A DIGIT
|
|
MOV B,A; DEC EXP EQUAL DIGIT
|
|
INR L; TO ADDRESS NEXT CHAR
|
|
MOV A,M; NEXT CHARACTER OF STRING
|
|
CPI 0AH; SET CARRY IF CHAR IS DIGIT
|
|
JNC INP7; IF CHAR IS NOT A DIGIT
|
|
; FORM COMPLETE DECIMAL EXPONENT.
|
|
MOV C,A; LS DIGIT OF DEC EXP
|
|
MOV A,B; MS DIGIT OF DEC EXP
|
|
ADD A; 2 * MS DIGIT
|
|
ADD A; 4 * MS DIGIT
|
|
ADD B; 5 * MS DIGIT
|
|
ADD A; 10 * MS DIGIT
|
|
ADD C; 10 * MS + LS DIGIT
|
|
MOV B,A; DECIMAL EXPONENT
|
|
INP7: MOV A,E; SIGN OF DEC EXPONENT
|
|
ANA A ; SET CONTROL BITS
|
|
JNZ INP8; IF SIGN PLUS
|
|
SUB B; COMPLEMENT DEC EXP
|
|
MOV B,A; DECIMAL EXPONENT
|
|
INP8: LXI H,TMP3; TO ADDRESS SCRATCH BANK
|
|
MOV C,M; INPUT SIGN
|
|
LXI H,ACCS; TO ADDRESS ACCUM SIGN
|
|
MOV M,C; ACCUMULATOR SIGN
|
|
MOV A,B; DECIMAL EXPONENT
|
|
; CONVERT DECIMAL EXPONENT TO BINARY.
|
|
INP9: LXI H,TMP1; TO ADDRESS DEC EXPONENT
|
|
ADD M; ADJUST DECIMAL EXPONENT
|
|
JZ FTEST; IN DEC EXP IS ZERO
|
|
MOV M,A; CURRENT DECIMAL EXPONENT
|
|
LXI H,FTEN; TO ADDR FLOATING TEN
|
|
JP INP10; IF MULTIPLY REQUIRED
|
|
CALL FDIV; DIVIDE BY TEN
|
|
MVI A,1; TO INCREMENT DEC EXP
|
|
JMP INP9; TO TEST FOR COMPLETION
|
|
INP10: CALL FMUL; MULTIPLY BY TEN
|
|
RC ; RETURN IF OVERFLOW
|
|
MVI A,0FFH; TO DECREMENT DEC EXP
|
|
JMP INP9; TO TEST FOR COMPLETION
|
|
; OUT SUBROUTINE ENTRY POINT.
|
|
; SAVE CHARACTER ADDRESS AND ACCUMULATOR.
|
|
FOUT: DCR L; DECREMENT CHARACTER ADDRESS
|
|
CALL SVAD; SET CHAR ADDR, DIG CNT, DEC EXP
|
|
CALL FTEST; LOAD ACCUM TO REGISTERS
|
|
LXI H,VALE; TO ADDR ACCUM SAVE AREA
|
|
CALL FSTOR; CALL REG STR SUBROUTINE
|
|
; OUTPUT SIGN CHARACTER.
|
|
CALL CHAD; CALL CHAR ADDR SBRTN
|
|
MVI M,0F0H; STORE SPACE CHARACTER
|
|
ANA A ; SET CONTROL BITS
|
|
JZ OUT3; IF ACCUMULATOR IS ZERO
|
|
MOV E,A; ACCUMULATOR EXPONENT
|
|
MOV A,B; ACCUM SIGN AND 1ST FRCTN
|
|
ANA A ; SET CONTROL BITS
|
|
MOV A,E; ACCUMULATOR EXPONENT
|
|
JP OUT1; IF ACCUM IS POSITIVE
|
|
MVI M,0FDH; CHANGE SIGN TO MINUS
|
|
; SCALE ACCUMULATOR TO .1 - 1. RANGE.
|
|
OUT1: CPI 7EH; COMPARE TO SMALL EXPONENT
|
|
OUT2: LXI H,FTEN; TO ADDR FLOATING TEN
|
|
JC OUT4; IF EXPONENT TOO SMALL
|
|
CPI 81H; COMPARE TO LARGE EXP
|
|
JC OUT5; IF EXP SMALL ENOUGH
|
|
CALL FDIV; DIVIDE BY TEN
|
|
OUT3: LXI H,TMP2; TO ADDRESS SCRATCH BANK
|
|
MOV E,M; DECIMAL EXPONENT
|
|
INR E; INCREMENT DECIMAL EXPONENT
|
|
MOV M,E; DECIMAL EXPONENT
|
|
JMP OUT2; TO TEST FOR SCALING COMPLETE
|
|
OUT4: CALL FMUL; MULTIPLY BY TEN
|
|
LXI H,TMP2; TO ADDR DECIMAL EXPONENT
|
|
MOV E,M; DECIMAL EXPONENT
|
|
DCR E; DECREMENT DECIMAL EXPONENT
|
|
MOV M,E; DECIMAL EXPONENT
|
|
JMP OUT1; TO TEST FOR SCALING COMPLETE
|
|
; ROUND THE VALUE BY ADDING .00000005.
|
|
OUT5: CALL FABS; SET ACCUM POSITIVE
|
|
LXI H,RND0; TO ADDRESS ROUNDER
|
|
CALL FADD; ADD THE ROUNDER
|
|
CPI 81H; CHECK FOR OVERFLOW
|
|
JNC OUT2; IF EXP TOO LARGE
|
|
; SET DIGIT COUNTS.
|
|
LXI H,TMP2; TO ADDR DECIMAL EXPONENT
|
|
MOV A,M; DECIMAL EXPONENT
|
|
MOV E,A; DIGITS BEFORE DEC POINT
|
|
CPI 8; COMPARE TO LARGE EXP
|
|
JC OUT6; IF EXPONENT IN RANGE
|
|
MVI E,1; DIGITS BEFORE DEC POINT
|
|
OUT6: SUB E; ADJUST DEC EXPONENT
|
|
MOV M,A; DECIMAL EXPONENT
|
|
MVI A,7; TOTAL NUMBER OF DIGITS
|
|
SUB E; DIGITS AFTER DECIMAL PNT
|
|
INR L; TO ADDR 2ND DIGIT CNT
|
|
MOV M,A; DIGITS AFTER DECIMAL POINT
|
|
DCR E; DECREMENT DIGIT COUNT
|
|
MOV A,E; DIGITS BEFORE DEC PNT
|
|
; OUTPUT SIGNIFICANT DIGITS.
|
|
OUT7: LXI H,TMP1; TO ADDR DIGIT COUNT
|
|
ADD M; ADJUST DIGIT COUNT
|
|
MOV M,A; NEW DIGIT COUNT
|
|
JM OUT8; IF COUNT RUN OUT
|
|
LXI H,FTEN; TO ADDR FLOATING TEN
|
|
CALL FMUL; MULTIPLY BY TEN
|
|
MVI E,8; TO PLACE DIGIT IN REG A
|
|
CALL FFIX; CONVERT TO FIXED FORMAT
|
|
CALL CHAD; CALL CHAR ADDR SBRTN
|
|
MOV M,A; OUTPUT DECIMAL DIGIT
|
|
XRA A; CLEAR CURRENT DIGIT
|
|
MVI E,8; BINARY SCALING FACTOR
|
|
CALL FFLOAT; RESTORE VALUE MINUS DIGIT
|
|
MVI A,0FFH; TO ADJUST DIGIT CNT
|
|
JMP OUT7; LOOP FOR NEXT DIGIT
|
|
OUT8: LXI H,TMP3; TO ADDR 2ND DIGIT CNT
|
|
MOV A,M; DIGITS AFTER DECIMAL PNT
|
|
MVI M,0FFH; SET 2ND COUNT NEG
|
|
ANA A ; SET CONTROL BITS
|
|
JM OUT9; IF 2ND COUNT RAN OUT
|
|
CALL CHAD; CALL CHAR ADDR SBRTN
|
|
MVI M,0FEH; STORE DECIMAL POINT
|
|
JMP OUT7; LOOP FOR NEXT DIGIT
|
|
OUT9: DCR L; TO ADDR DECIMAL EXP
|
|
ANA M ; DECIMAL EXPONENT
|
|
JZ OUT13; IF DECIMAL EXPONENT IS ZERO
|
|
; OUTPUT DECIMAL EXPONENT.
|
|
MVI B,0FBH; PLUS CHARACTER
|
|
JP OUT10; IF EXPONENT IS POSITIVE
|
|
MVI B,0FDH; CHANGE SIGN TO MINUS
|
|
MOV C,A; NEGATIVE EXPONENT
|
|
XRA A; ZERO
|
|
SUB C; COMPLEMENT EXPONENT
|
|
OUT10: MVI C,0FFH; EMBRYO TENS DIGIT
|
|
OUT11: MOV D,A; UNITS DIGIT
|
|
INR C; INCREMENT TENS DIGIT
|
|
SUI 0AH; REDUCE REMAINDER
|
|
JNC OUT11; IF MORE TENS
|
|
MVI A,15H; EXPONENT SIGN
|
|
OUT12: CALL CHAD; CALL CHAR ADDR SBRTN
|
|
CALL FSTOR; STORE LAST 4 CHARACTERS
|
|
LXI H,VALE; TO ADDRESS ACCUM SAVE AREA
|
|
JMP FLOAD; RESTORE ACCUM AND EXIT
|
|
; OUTPUT 4 SPACES IF EXPONENT IS ZERO.
|
|
OUT13: MVI A,0F0H; SPACE CHARACTER
|
|
MOV B,A; SPACE CHARACTER
|
|
MOV C,A; SPACE CHARACTER
|
|
MOV D,A; SPACE CHARACTER
|
|
JMP OUT12; TO STORE CHARACTERS
|
|
; SUBROUTINE TO SAVE CHARACTER STRING ADDR.
|
|
SVAD: MOV A,L; CHARACTER STRING WORD
|
|
MOV B,H; CHARACTER STRING BANK
|
|
MVI C,0; INPUT EXP OR DIGIT CNT
|
|
MOV D,C; DEC PNT FLAG OR DEC EXP
|
|
LXI H,ADRL; TO ADDR CHAR STRING WORD
|
|
CALL FSTOR; STORE A, B, C, AND D
|
|
RET ; RETURN TO CALLER
|
|
; SUBROUTINE TO OBTAIN NEXT CHARACTER ADDR.
|
|
CHAD: LXI H,ADRL; TO ADDRESS SCRATCH BANK
|
|
MOV E,M; CHARACTER STRING WORD
|
|
INR E; TO ADDR NEXT CHARACTER
|
|
MOV M,E; UPDATE CHAR STRING WORD
|
|
INR L; TO ADDR CHAR STRING BANK
|
|
MOV H,M; CHARACTER STRING BANK
|
|
MOV L,E; CHARACTER STRING WORD
|
|
RET ; RETURN TO CALLER
|
|
END
|