home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
ftp.barnyard.co.uk
/
2015.02.ftp.barnyard.co.uk.tar
/
ftp.barnyard.co.uk
/
cpm
/
walnut-creek-CDROM
/
CPM
/
SMALLC21
/
SMC21LIB.LBR
/
CALL.MAC
< prev
next >
Wrap
Text File
|
2000-06-30
|
10KB
|
523 lines
;
;----- call.asm: Small-C ver. 2 arithmetic and logical library
; (ASM Version 7-28-83, Bill Randle)
; (Global symbols added 02-07-84, Dennis Quinn)
; (.8080 added 10 Jan 85, Earl Boebert)
; (Updated to version in the Handbook 4 Feb 85, Earl Boebert)
;
.8080
_call:: EXT _END
;
CCDCAL::
PCHL
;
CCDDGC::
DAD D
JMP CCGCHAR
;
CCDSGC::
INX H
INX H
DAD SP
;
;FETCH A SINGLE BYTE FROM THE ADDRESS IN HL AND
;SIGN EXTEND INTO HL
;
CCGCHAR::
MOV A,M
;
;PUT THE ACCUM INTO HL AND SIGN EXTEND THROUGH H.
;
CCARGC::
CCSXT::
MOV L,A
RLC
SBB A
MOV H,A
RET
;
CCDDGI::
DAD D
JMP CCGINT
;
CCDSGI::
INX H
INX H
DAD SP
;
;FETCH A FULL 16-BIT INTEGER FROM THE ADDRESS IN HL
;INTO HL
;
CCGINT::
MOV A,M
INX H
MOV H,M
MOV L,A
RET
;
CCDECC::
INX H
INX H
DAD SP
MOV D,H
MOV E,L
CALL CCGCHAR
DCX H
MOV A,L
STAX D
RET
;
CCINCC::
INX H
INX H
DAD SP
MOV D,H
MOV E,L
CALL CCGCHAR
INX H
MOV A,L
STAX D
RET
;
;
CCDDPC::
DAD D
CCPDPC::
POP B ;;RET ADDR
POP D
PUSH B
;
;STORE A SINGLE BYTE FROM HL AT THE ADDRESS IN DE
;
CCPCHAR::
PCHAR:: MOV A,L
STAX D
RET
;
CCDECI::
INX H
INX H
DAD SP
MOV D,H
MOV E,L
CALL CCGINT
DCX H
JMP CCPINT
;
CCINCI::
INX H
INX H
DAD SP
MOV D,H
MOV E,L
CALL CCGINT
INX H
JMP CCPINT
;
;
CCDDPI::
DAD D
CCPDPI::
POP B ;;RET ADDR
POP D
PUSH B
;
;STORE A 16-BIT INTEGER IN HL AT THE ADDRESS IN DE
;
CCPINT::
PINT:: MOV A,L
STAX D
INX D
MOV A,H
STAX D
RET
;
;INCLUSIVE "OR" HL AND DE INTO HL
;
CCOR::
MOV A,L
ORA E
MOV L,A
MOV A,H
ORA D
MOV H,A
RET
;
;EXCLUSIVE "OR" HL AND DE INTO HL
;
CCXOR::
MOV A,L
XRA E
MOV L,A
MOV A,H
XRA D
MOV H,A
RET
;
;"AND" HL AND DE INTO HL
;
CCAND::
MOV A,L
ANA E
MOV L,A
MOV A,H
ANA D
MOV H,A
RET
;
;IN ALL THE FOLLOWING COMPARE ROUTINES, HL IS SET TO 1 IF THE
;CONDITION IS TRUE, OTHERWISE IT IS SET TO 0 (ZERO).
;
;TEST IF HL = DE
;
CCEQ::
CALL CCCMP
RZ
DCX H
RET
;
;TEST IF DE <> HL
;
CCNE::
CALL CCCMP
RNZ
DCX H
RET
;
;TEST IF DE > HL (SIGNED)
;
CCGT::
XCHG
CALL CCCMP
RC
DCX H
RET
;
;TEST IF DE <= HL (SIGNED)
;
CCLE::
CALL CCCMP
RZ
RC
DCX H
RET
;
;TEST IF DE >= HL (SIGNED)
;
CCGE::
CALL CCCMP
RNC
DCX H
RET
;
;TEST IF DE < HL (SIGNED)
;
CCLT::
CALL CCCMP
RC
DCX H
RET
;
;COMMON ROUTINE TO PERFORM A SIGNED COMPARE
; OF DE AND HL
;THIS ROUTINE PERFORMS DE - HL AND SETS THE CONDITIONS:
; CARRY REFLECTS SIGN OF DIFFERENCE (SET MEANS DE < HL)
; ZERO/NON-ZERO SET ACCORDING TO EQUALITY.
;
CCCMP::
MOV A,H ;;INVERT SIGN OF HL
XRI 80H
MOV H,A
MOV A,D ;;INVERT SIGN OF DE
XRI 80H
CMP H ;;COMPARE MSBS
JNZ CCCMP1 ;;DONE IF NEQ
MOV A,E ;;COMPARE LSBS
CMP L
CCCMP1: LXI H,1 ;;PRESET TRUE COND
RET
;
;TEST IF DE >= HL (UNSIGNED)
;
CCUGE::
CALL CCUCMP
RNC
DCX H
RET
;
;TEST IF DE < HL (UNSIGNED)
;
CCULT::
CALL CCUCMP
RC
DCX H
RET
;
;TEST IF DE > HL (UNSIGNED)
;
CCUGT::
XCHG
CALL CCUCMP
RC
DCX H
RET
;
;TEST IF DE <= HL (UNSIGNED)
;
CCULE::
CALL CCUCMP
RZ
RC
DCX H
RET
;
;COMMON ROUTINE TO PERFORM UNSIGNED COMPARE
;CARRY SET IF DE < HL
;ZERO/NONZERO SET ACCORDINGLY
;
CCUCMP::
MOV A,D
CMP H
JNZ CCUCP1
MOV A,E
CMP L
CCUCP1: LXI H,1
RET
;
;SHIFT DE ARITHMETICALLY RIGHT BY HL AND RETURN IN HL
;
CCASR::
XCHG
DCR E
RM
MOV A,H
RAL
MOV A,H
RAR
MOV H,A
MOV A,L
RAR
MOV L,A
JMP CCASR+1
;
;SHIFT DE ARITHMETICALLY LEFT BY HL AND RETURN IN HL
;
CCASL::
XCHG
DCR E
RM
DAD H
JMP CCASL+1
;
;SUBTRACT HL FROM DE AND RETURN IN HL
;
CCSUB::
MOV A,E
SUB L
MOV L,A
MOV A,D
SBB H
MOV H,A
RET
;
;FORM THE TWO'S COMPLEMENT OF HL
;
CCNEG::
CALL CCCOM
INX H
RET
;
;FORM THE ONE'S COMPLEMENT OF HL
;
CCCOM::
MOV A,H
CMA
MOV H,A
MOV A,L
CMA
MOV L,A
RET
;
;MULTIPLY DE BY HL AND RETURN IN HL
;(SIGNED MULTIPLY)
;
CCMULT::
MULT:: MOV B,H
MOV C,L
LXI H,0
CCMLT1: MOV A,C
RRC
JNC CCMLT2
DAD D
CCMLT2: XRA A
MOV A,B
RAR
MOV B,A
MOV A,C
RAR
MOV C,A
ORA B
RZ
XRA A
MOV A,E
RAL
MOV E,A
MOV A,D
RAL
MOV D,A
ORA E
RZ
JMP CCMLT1
;
;DIVIDE DE BY HL AND RETURN QUOTIENT IN HL, REMAINDER IN DE
;(SIGNED DIVIDE)
;
CCDIV::
DIV:: MOV B,H
MOV C,L
MOV A,D
XRA B
PUSH PSW
MOV A,D
ORA A
CM CCDENEG
MOV A,B
ORA A
CM CCBCNEG
MVI A,16
PUSH PSW
XCHG
LXI D,0
CCDIV1: DAD H
CALL CCRDEL
JZ CCDIV2
CALL CCCMPBCDE
JM CCDIV2
MOV A,L
ORI 1
MOV L,A
MOV A,E
SUB C
MOV E,A
MOV A,D
SBB B
MOV D,A
CCDIV2: POP PSW
DCR A
JZ CCDIV3
PUSH PSW
JMP CCDIV1
CCDIV3: POP PSW
RP
CALL CCDENEG
XCHG
CALL CCDENEG
XCHG
RET
;
;NEGATE THE INTEGER IN DE
;(INTERNAL ROUTINE)
;
CCDENEG:
MOV A,D
CMA
MOV D,A
MOV A,E
CMA
MOV E,A
INX D
RET
;
;NEGATE THE INTEGER IN BC
;(INTERNAL ROUTINE)
;
CCBCNEG:
MOV A,B
CMA
MOV B,A
MOV A,C
CMA
MOV C,A
INX B
RET
;
;ROTATE DE LEFT ONE BIT
;(INTERNAL ROUTINE)
;
CCRDEL:
MOV A,E
RAL
MOV E,A
MOV A,D
RAL
MOV D,A
ORA E
RET
;
;COMPARE BC TO DE
;(INTERNAL ROUTINE)
;
CCCMPBCDE:
MOV A,E
SUB C
MOV A,D
SBB B
RET
;
; LOGICAL NEGATION
;
CCLNEG::
MOV A,H
ORA L
JNZ $+6
MVI L,1
RET
LXI H,0
RET
;
; EXECUTE "SWITCH" STATEMENT
;
; HL = SWITCH VALUE
; (SP) -> SWITCH TABLE
; DW ADDR1, VALUE1
; DW ADDR2, VALUE2
; ...
; DW 0
; [JMP default]
; continuation
;
CCSWITCH::
XCHG ;;DE = SWITCH VALUE
POP H ;;HL -> SWITCH TABLE
SWLOOP: MOV C,M
INX H
MOV B,M ;;BC -> CASE ADDR, ELSE 0
INX H
MOV A,B
ORA C
JZ SWEND ;;DEFAULT OR CONTINUATION CODE
MOV A,M
INX H
CMP E
MOV A,M
INX H
JNZ SWLOOP
CMP D
JNZ SWLOOP
MOV H,B ;;CASE MATCHED
MOV L,C
SWEND: PCHL
;
;(code added from DDJ)
;
_end: LHLD 6 ;get bdos address
SPHL ;use for base of stack
LXI H, _end ;get start of free memory
SHLD _memptr## ;use for memory allocation
JMP _main## ;parse command line, execut program
END _end
; HL = SWITCH VALUE
; (SP