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
/
SIMTEL
/
CPMUG
/
CPMUG025.ARK
/
DCHAYES.ASM
< prev
next >
Wrap
Assembly Source File
|
1984-04-29
|
9KB
|
378 lines
;MODEM CONTROL PROGRAM BY DALE HEATHERINGTON
; 4/4/77
; ENTERED BY R.J.S. 01/01/78
;
; MODIFIED BY DAVE JAFFE
; FOR: BDOS CALLS
; RETURN TO CP/M ON CONTROL C
;
;
;MODEM CONTROL BYTES
ORIG300 EQU 5 ;300 BPS ORIGINATE
ANSW300 EQU 1 ;300 BPS ANSWER
ORIG110 EQU 4 ;100 BPS ORIGINATE
ANSW110 EQU 0 ;110 BPS ANSWER
OFFHOOK EQU 80H ;OFF HOOK MASK
ONHOOK EQU 7FH ;ON HOOK MASK
TXE EQU 2 ;XMTR ON MASK
TXOFF EQU 0FDH ;XMTR OFF MASK
WORD EQU 1FH ;8 BITS, NO PARITY, 2 STOP BITS
;
;PORT ASSIGNMENTS
;
DATA EQU 80H ;MODEM DATA I/O PORT
STAT EQU DATA+1 ;STATUS PORT
MODE EQU DATA+2 ;MODE CONTROL PORT
;
; SYSTEM EQUATES
BDOS EQU 5
;
ORG 100H
;SENSE SWITCH A-15 IS USED FOR SPEED SELECT.UP IS 300 BAUD
;DOWN IS 110 BAUD.
;
;SENSE SWITCH A-8 UP WILL SUPRESS ECHO ON DATA TRANSMISSION
;
START JMP SIGNON
OUTPUT JMP USEROT ;JUMP TO USER OUT ROUTINE
INPUT JMP USERIN ;JUMP TO USER IN ROUTINE
INSTAT JMP USERST ;JUMP TO USER CONSOLE STATUS
;CHECK ROUTINE. RETURNS 'FF'
;IF A BYTE IS WAITING OR
; '00' IF NOT.
;
;THIS ROUTINE LOOPS UNTIL THE LINE RINGS OR A
;CONTROL B IS TYPED ON THE CONSOLE.
;
SIGNON: LXI SP,STKTOP
LXI H,SIGN ;POINT TO SIGNON MESSAGE
CALL PRINTM
MVI A,0
OUT STAT ;CLEAR MODEM REGISTER
RINGCK:
CALL INSTAT ;GET CONSOLE STATUS
CNZ INPUT ;GET BYTE IF READY
CPI 2 ;CHECK FOR "STX" OR CONTROL B
JZ MAKCALL ;GOTO ORIG ROUTINE
CPI 3 ;CONTROL C?
JZ 0 ;BACK TO CP/M
IN STAT ;GET MODEM STATUS
ANI 80H ;ISOLATE RING DET. BIT
JNZ RINGCK ;LOOP UNTIL IT GOES LOW
ANCALL:
CALL AN110 ;SET TO ANSWER MODE
CALL OFFHK ;GO OFFHOOK
LDA MDBYTE ;GET MODE
ORI TXE
STA MDBYTE
OUT MODE ;TURN ON XMITTER
JMP CARR-3 ;JMP TO DATA HANDLING ROUTINE
MAKCALL:
LXI SP,STKTOP
CALL OR110 ;SET TO ORIGINATE MODE
LXI H,MNUM ;POINT TO STRING "NUMBER"
CALL PRINTM ;PRINT THE STRING
CALL DIAL ;GET AND DIAL A PHONE NUMBER
LXI D,400 ;SETUP FOR A 20 SECOND DELAY
CARR: CALL SPEED ;SET SPEED
IN STAT ;LOOK FOR A CARRIER
ANI 40H ;ISOLATE CARRIER BIT
JNZ CONNECT ;JUMP IF TRUE
CALL DELAY ;WAIT 50 MS
DCX D ;COUNT IT
MOV A,D ;TEST FOR D&E =0
ORA E
JNZ CARR ;LOOP IF NOT TIMED OUT
LXI H,NOASW ;POINT TO STRING "NO ANSWER"
CALL PRINTM ;PRINT THE STRING
JMP EOT ;DISCONNECT
CONNECT:
LDA MDBYTE ;GET MODE
ORI TXE ;TURN ON XMTTR
OUT MODE
STA MDBYTE
ANI 4 ;ISOLATE ORIG/ANSW BIT
CZ SAB ;SEND ANSWER/BACK
TTY: IN STAT ;GET MODEM STATUS
ANI 40H ;ISOLATE CARRIER DETECT BIT
JNZ OK ;
LXI H,LOSTC ;POINT TO STRING "LOST CARRIER"
CALL PRINTM ;PRINT THE STRING
JMP EOT
OK: CALL SPEED ;SET SPEED
IN STAT ;GET MODEM STATUS
ANI 1 ;CHECK FOR A DATA BYTE
CNZ GETC ;GET THE BYTE
CALL INSTAT ;CHECK THE CONSOL STATUS
ANA A ;SET THE FLAGS
JZ TTY ;LOOP IF STATUS NOT TRUE
CALL INPUT ;GET THE CONSOL CHAR
MOV C,A ;SAVE IT
TTY1: CALL TRANS ;SEND AND ECHO THE CHAR
JMP TTY ;LOOP AGAIN
;
;SPEED SELECT ROUTINE
;USES SENSE SWITCH A-15; UP IS 300 BAUD,DOWN IS 110
;
SPEED: PUSH B
LDA MDBYTE ;GET PRESENT MODE
MOV B,A
IN 255 ;GET SENSE SWITCH
ANI 80H
MOV A,B
JZ S110
ORI 1 ;SET TO 300 BPS
DB 01H ;*****TRICK*** LXI B (NOP NEXT 2 BYTES)
S110: ANI 0FEH ;SET TO 110 BPS
STA MDBYTE
OUT MODE ;SET MODEM
POP B
RET
;
;PRINTS CHAR ON CONSOLE.CHECKS FOR EOT CHAR
;AND TERMINATES CALL IF TRUE.
;
PRINT: MOV A,C ;GET A BYTE
CPI 4 ;CHECK FOR EOT
JNZ OUTPUT ;OUTPUT THE BYTE
EOT1: LXI H,MEOT ;POINT TO STRING "EOT"
CALL PRINTM ;PRINT IT
MVI B,10 ;SET FOR .5 SEC DELAY
DLY3: CALL DELAY
DCR B
JNZ DLY3 ;LOOP FOR .5 SEC
EOT: LDA MDBYTE ;GET CURRENT MODE
ANI TXOFF ;TURN OFF XMTTR
ANI ONHOOK ;DISCONNECT LINE
OUT MODE
STA MDBYTE
LXI H,TERM ;POINT TO STRING "TERMINATED"
CALL PRINTM ;PRINT IT
JMP SIGNON ;BACK TO THE START
;
;GETS A BYT FROM THE MODEM
;
GETC: IN DATA ;GET A MODEM BYTE
ANI 7FH ;KILL PARITY
CPI 4 ;CHECK FOR EOT
JZ EOT1 ;
CPI 5 ;CHECK FOR ENQ
CZ SAB ;SEND ANSWERBACK IF TRUE
MOV C,A
CALL OUTPUT ;PRINT THE CHAR
RET
;
;THIS ROUTINE PRINTS AN ASCII STRING IN MEMORY ON THE CONSOL
;
PRINTM: MVI A,255
MOV C,M ;GET A BYTE
CMP C ;TEST FOR FF (END OF STRING)
RZ ;FINISHED
CALL OUTPUT ;PRINT IT
INX H ;POINT TO NEXT BYTE
JMP PRINTM ;LOOP AGAIN
;
;SETS THE MODEM TO ORIGINATE OR ANSWER MODE
;
OR110: MVI A,ORIG110 ;GET MODE BYTE
JMP AN110+2
AN110: MVI A,ANSW110 ;GET ANSWER MODE BYTE
STA MDBYTE ;SAVE IT
OUT MODE ;SETUP MODEM
MVI A,WORD ;GET WORD FORMAT
OUT STAT ;SETUP MODEM
RET
;
;THIS ROUTINE GETS DIGITS FROM THE CONLOL
;AND STORES THEM IN MEMORY. IT HTEN TAKES THE LINE
;OFF HOOK AND DIALS THE DIGITS STORED IN MEMORY.
;IF A '*' APPEARS IN THE DIGIT STRING THE PROGRAM
;PAUSES FOR 2 SECONDS. THIS IS TO WAIT FOR SECOND DIAL
;TONE IN SOME EXCHANGES.
;
DIAL: CALL GETNUM ;GET PHONE NUMBER FROM KBD
CALL OFFHK ;GO OFFHOOK
LXI H,MDIAL ;POINT TO STRING "DIALING--"
CALL PRINTM ;PRINT IT
MVI B,40 ;SETUP FOR 2 SECOND DELAY
WAIT: CALL DELAY ;WAIT FOR DIAL TONE
DCR B
JNZ WAIT
DIAL2 LXI H,NMBR ;POINT TO PHONE NUMBER
MOV A,M ;GET A DIGIT
CPI 0DH ;CHECK FOR THE END
RZ
MOV C,A ;
CALL OUTPUT ;PRINT THE DIGIT TO BE DIALED
CPI '*' ;DELAY?
JNZ NODLY
MVI B,40 ;SETUP FOR 2 SECOND DELAY
WAIT2: CALL DELAY
DCR B
JNZ WAIT2
NODLY: INX H ;POINT TO NEXT DIGIT
SUI 30H ;REMOVE ASCII BIAS
JNZ NOTZERO ;CHECK FOR A DIGIT "0"
MVI A,10 ;MAKE A 0 A 10
NOTZERO:
JC DIAL2+3 ;IF <0 GET NEXT DIGIT
CPI 11 ;CHECK FOR MORE THAN 10
JNC DIAL2+3 ;IF MORE GET NEXT DIGIT
CALL PULSE ;MAKE DIAL PULSES
JMP DIAL2+3
;
;THIS SUBROUTINE PULSES THE LINE,
;THE VALUE IN ACC EQUALS THE NUMBER OF
;PULSES OUTPUT.
;
PULSE: PUSH PSW
CALL ONHK ;GO ONHOOK
CALL DELAY ;WAIT 50 MS
CALL OFFHK ;GO OFF HOOK
CALL DELAY ;WAIT 50 MS
POP PSW ;GET DIGIT
DCR A ;SUBTRACT 1 FROM DIGIT
JNZ PULSE ;ANOTHER PULSE IF NOT ZERO
MVI A,10 ;SET UP FOR 500 MS DELAY
SPACE: CALL DELAY ;WAIT 500 MS
DCR A ;
JNZ SPACE
RET ;DIGIT COMPLETE
;
; THIS ROUTINE WAITS 50 MS BEFORE RETURNING
;
DELAY: PUSH H
PUSH D
PUSH PSW
CALL INSTAT
ORA A ;SET FLAGS
CNZ INPUT ;GET A CONSOL BYTE
CPI 4 ;CONTROL D?
JZ EOT1 ;ABORT
POP PSW
LXI D,50
LXI H,0
DLYLP: XTHL ;WAIST TIME FOR DELAY
XTHL
DAD D ;ADD D&E TO H&L
JNC DLYLP ;LOOP UNTIL CARRY
POP D
POP H
RET
;
;GETS BYTES FROM THE CONSOLE AND STORES THEM IN RAM.
;
GETNUM: LXI H,NMBR ;POINT TO BUFFER
CALL INSTAT ;GET KBD STATUS
ANA A ;SET FLAGS
JZ GETNUM+3;LOOP UNTIL KBD IS READY
CALL INPUT ;GET A DIGIT
CPI 4 ;CONTROL D
JZ SIGNON ;ABORT
CPI 2 ;IS IT A CONTROL B?
JZ GETNUM+3;IGNORE GARBAGE CHAR
CPI 3 ;IS IT A CONTROL C?
JZ 0 ;RETURN TO CP/M
MOV M,A ;STORE IT
MOV C,A ;
PUSH PSW ;SAVE ACC FROM VDM ROUTINE
CALL OUTPUT ;ECHO THE DIGIT
POP PSW ;SAFE AND SOUND
CPI 0DH ;CHECK FOR ASCII "CR"
RZ ;DONE IF TRUE
INX H ;POINT TO NEXT BUFFER LOC.
CPI 08H ;BACKSPACE?
JNZ GETNUM+3;IF NOT GET NEXT DIGIT
DCX H
DCX H ;BACKUP POINTER
JMP GETNUM+3 ;GET NEXT DIGIT
;
;THESE ROUTINES SET THE MODEM FOR "ONHOOK" OR "OFFHOOK"
;
OFFHK: LDA MDBYTE ;GET THE CURRENT MODE BYTE
ORI OFFHOOK ;SET THE OFF HOOK BIT
JMP SETT
ONHK: LDA MDBYTE ;GET CURRENT MODE BYTE
ANI ONHOOK ;RESET THE OFF HOOK BIT
SETT: STA MDBYTE ;SAVE NEW MODE BYTE
OUT MODE ;SET THE MODEM
RET
;
;THIS SUBROUTINE SENDS THE ANSWER BACK MESSAGE
;
SAB: PUSH H
PUSH B
LXI H,ANSBK ;POINT TO ANSWER BACK MESSAGE
GAB: MOV A,M ;GET A BYTE
CPI 255 ;END?
JZ EXIT
MOV C,A
CALL TRANS ;SEND THE BYTE
INX H
JMP GAB ;LOOP AGAIN
EXIT: POP B
POP H
RET
;
;THIS SUBROUTINE SENDS A BYTE TO THE MODEM
;AND TO THE CONSOL DISPLAY DEVICE.
;
TRANS: IN STAT ;SEE IF READY FOR BYTE
ANI 2
JZ TRANS ;LOOP UNTIL READY
MOV A,C ;GET THE BYTE
OUT DATA ;SEND IT
IN 0FFH ;INPUT FROM SENSE
ANI 01 ;CHECK ECHO BIT
RZ ;DO NOT ECHO
MOV A,C ;GET BACK CHAR
CALL PRINT ;ECHO CHAR
RET
MNUM: DB 0DH,0AH
DB 'NUMBER ?'
DB 0DH,0AH,255
NOASW: DB 0DH,0AH
DB 'NO ANSWER---'
DB 255
TERM: DB 0DH,0AH
DB 'CALL TERMINATED'
DB 0DH,0AH,255
MDIAL: DB 0DH,0AH
DB 'DIALING-'
DB 255
LOSTC: DB 0DH,0AH
DB 'LOST CARRIER'
DB 255
MEOT: DB 0DH,0AH
DB 'EOT'
DB 255
SIGN: DB 0DH,0AH
DB '80/103 CONTROL PROGRAM'
DB 0DH,0AH
DB 0DH,0AH
DB 'WAITING FOR RING OR CONTROL SHIFT B'
DB 0DH,0AH
DB 255
ANSBK: DB 0,0,0DH,0,0,0AH
DB 'THE CACHE COMPUTER NETWORK'
DB 0DH,0,0,0,0AH,255
;
;USER ROUTINES
;
USEROT: CALL 5A0CH
RET
USERIN: IN 1
ANI 7FH
RET
USERST: IN 0
ANI 80H
MVI A,0
RNZ
DCR A
RET
MDBYTE DS 1 ;MODE BYTE STORAGE LOC.
NMBR: DS 20 ;20 SPACES FOR PHONE #
STKTOP EQU $+16H ;STACK HERE
END START