TITLE 'PURDUE AUTOPATCH CONTROL PROGRAM' NAM WR9ACZ * WR9ACZ AUTO-PATCH CONTROLER * COPYRIGHT (C) 1976, HOWARD CUNNINGHAM * * 01/17/76 INITIAL VERSION * 10/23/76 CONFIGURED FOR WINCE BOARD * ASSEMBLY CONSTANTS CKPD EQU 4 CLOCK PERIOD IN MSEC CSPD EQU CKPD*256/1000 HIGH BYTE PERIOD IN SECONDS SPEED EQU 18 MORSE SENDING RATE IN WPM DITLEN EQU 1200/SPEED/CKPD DOT PERIOD IN CLOCK TICKS QUELEN EQU 10 MAX DIGITS IN DIAL PULSE QUEUE IDTONE EQU ^00111000 IDENT TONE, COLUMN 4 BPTONE EQU ^01000011 BEEP TONE, ROW 3 * I/O DATA REGESTER BIT DEFINITIONS BCAR EQU ^10000000 CARRIER (MUST BE HIGH ORDER BIT) BRNG EQU ^01000000 RINGER BUSE EQU ^00100000 PHONE IN USE BPRV EQU ^00010000 PRIVILEGED COMMANDS BHIF EQU ^00001000 INPUT HIGH IN FREQ BLOF EQU ^00000100 INPUT LOW IN FREQ BLSN EQU ^00001000 XMIT PATCH AUDIO BCON EQU ^00000100 CONNECT PATCH BOFF EQU ^00000010 OUT OF SERVICE BTRN EQU ^00000001 TRANSMIT * FIXED RAM LOCATIONS ORG 0 FWARAM EQU . CLOCK RMB 2 CLOCK TICKS MOD 2**16 WATCH RMB 1 WATCH DOG TIMER CURTSK RMB 2 CURRENT TASK TABLE INDEX XMIT RMB 1 TRANSMIT WHEN NON-ZERO ACCESS RMB 2 AUTO PATCH ACCESS CODE A911 RMB 1 NON-ZERO IF ACCESS VIA 911 DIGITS RMB 2 NUMBER OF DIGITS IN DIAL QUEUE SNDING RMB 1 NON-ZERO IF CODE IN PROGRESS ASMBLY RMB 2 TOUCH TONE DIGIT ASSEMBLY ACTIVE RMB 1 NON-ZERO IF PATCH ACTIVE POKE RMB 1 SHORT TRANSMISSION COUNTER QUEUE RMB QUELEN DIAL DIGIT QUEUE FREMEM EQU * * I/O REGISTERS PIAS EQU $200 ORG $210 IOAD RMB 1 I/O A-SIDE DATA IOAC RMB 1 A-SIDE CONTROL IOBD RMB 1 I/O B-SIDE DATA IOBC RMB 1 B-SIDE CONTROL ORG $240 TTID RMB 1 TOUCH TONE INPUT DATA TTIC RMB 1 INPUT CONTROL TTOD RMB 1 TOUCH TONE OUTPUT DATA TTOC RMB 1 OUTPUT CONTROL * INTERRUPT VECTORS ORG $FFF8 FDB INTRPT HARDWARE FDB EXEC SOFTWARE FDB RESET NON-MASKABLE FDB RESET POWER UP * TASK ENTRY POINT TABLE ORG $FC00 TASKS FDB COR CARRIER OPERATION FDB CONTRL CONTROL FUNCTION PROCESSER FDB DIAL DIAL PULSE GENERATOR FDB RINGER INCOMMING CALL DETECTOR FDB IDENT IDENTIFIER NONPRE EQU *-TASKS/2 * FDB $3C6C CRAMERKIT TERMINAL MONITOR TSKCNT EQU *-TASKS/2 * EXECUTIVE CONTROL TABLES STKLEN EQU 16 LENGTH OF STACK FOR EACH TASK STACKS EQU FREMEM TASK STACK POINTERS STKORG EQU 2*TSKCNT+STACKS STACK AREA LWARAM EQU TSKCNT*STKLEN+STKORG-1 PAGE * EXECUTIVE * * THE EXECUTIVE IS RESPONSIBLE FOR INITIALIZATION OF THE * MACHINE AFTER RESET AND FOR DISTRIBUTION OF CONTROL * BETWEEN TASKS AFTER A SOFTWARE INTERRUPT. * RESET ENTRY RESET LDX &LWARAM RES1 CLR 0,X CLEAR RAM AND I/O DEX CPX &FWARAM-1 BNE RES1 * INITIALIZE I/O LDX &PIAS COM TTOD-PIAS,X SET OUTPUT DATA DIRECTION COM IOBD-PIAS,X LDA A &^00111101 STA A IOAC-PIAS,X ENABLE INT FROM I/O A-SIDE DEC A STA A IOBC-PIAS,X BUT NOT OTHERS STA A TTIC-PIAS,X STA A TTOC-PIAS,X * PRESET TASK DATA AREAS LDS &TASKS-1 LDX &2*TSKCNT LDA A &STKORG-8 RES2 DEX ADVANCE TO NEXT TASK DEX ADD A &STKLEN COMPUTE STACK LOCATION STA A STACKS+1,X STX CURTSK LDX STACKS,X PUL B STORE ENTRY PC IN STACK STA B 6,X PUL B STA B 7,X LDX CURTSK BNE RES2 LOOP FOR EACH TASK BRA EXE1 ENTER EXECUTIVE * SOFTWARE INTERRUPT ENTRY EXEC LDX CURTSK STS STACKS-2,X SAVE CURRENT TASK'S STACK DEX DEX ADVANCE TO NEXT TASK BNE EXE2 EXE1 LDX &2*TSKCNT START OVER WITH FIRST TASK CLR WATCH RESET WATCH DOG EVERY MAJOR CYCLE LDA A &^00110101 STA A IOAC SCOPE SYNC LDA A &^00111101 STA A IOAC EXE2 STX CURTSK LDS STACKS-2,X LOAD NEXT TASKS STACK RTI * INTERRUPT HANDLER * * THE REAL TIME CLOCK IS INCREMENTED BY 1 MODULO 2**16 * FOR EACH CLOCK INTERRUPT. IF THE COUNT OF CLOCK TICKS * SINCE THE BEGINNING OF THE LAST EXECUTIVE MAJOR CYCLE * EXCEEDS 255 (APROX 1 SECOND) A TASK IS ASSUMED TO BE * HUNGUP AND A RESET IS INITIATED. INTRPT TST IOAD CLEAR INTERRUPT LDX CLOCK INX BUMP CLOCK STX CLOCK INC WATCH BEQ RESET IF WE SEEM TO BE HUNGUP LDA A CURTSK+1 CMP A &TSKCNT-NONPRE*2 BLE EXEC IF CURRENT TASK PREEMPTABLE RTI PAGE * REENTRANT SUBROUTINE BEEP * * ACKNOWLEDGE VIA MORSE CODE. ON ENTRY (A) IS ENCODED CHARACTER. * ON EXIT (A) IS ZERO, (B) IS PRESERVED. BEEP PSH B LDA B &BPTONE SELECT FREQUENCY BSR CODE PUL B RESTORE (B) RTS * REENTRANT SUBROUTINE CODE-SENDER * * MORSE CODE IS SENT VIA THE TOUCH-TONE GENERATOR. THE * SNDING INTERLOCK INSURES CONTIGUOUS CODE IF CALLS ARE * MADE WITH NO INTERVIENING SWI. * ON ENTRY (A) IS AN ENCODED MORSE CHARACTER, (B) IS * TOUCH TONE BUTTON PATTERN FOR DESIRED TONE. ON EXIT * (B) IS PRESERVED, (A) IS ZERO. * INTERRLOCK CODE INC XMIT COD0 TST SNDING BEQ COD1 IF SENDER AVAILABLE SWI BRA COD0 WAIT FOR OTHER TASK TO FINISH COD1 INC SNDING * SEND CHARACTER COD2 LSR A BEQ COD4 IF END OF LETTER STA B TTOD START TONE PSH A LDA A &DITLEN BCC COD3 IF DIT NEXT LDA A &3*DITLEN COD3 BSR DELAY CLR TTOD STOP TONE LDA A &DITLEN BSR DELAY PUL A BRA COD2 * FINISH UP COD4 LDA A &2*DITLEN LETTER SPACE BSR DELAY DEC SNDING DEC XMIT RTS * REENTRANT SUBROUTINES DELAY, PAUSE * * KILL TIME FOR (A) CLOCK TICKS. EXECUTIVE LOOP CYCLE TIME * NEED NOT BE FASTER THAN THE CLOCK. ON EXIT (A) IS ZERO, * (B) IS PRESERVED. ENTRY PAUSE WILL DELAY 1 SECOND. PAUSE CLR A DELAY PSH B LDA B CLOCK+1 START TIME DEL1 SWI DEL2 CMP B CLOCK+1 BEQ DEL1 IF SAME TIME INC B DEC A BNE DEL2 LOOP UNTIL TIME IS UP PUL B RTS * REENTRANT SUBROUTINES ON, OFF * * SELECTIVLY MANIPULATE OUTPUT LINES SELECTED BY (A). * ON EXIT (A) IS DESTROYED. ON ORA A IOBD OR IN BIT BRA OFF1 OFF COM A AND A IOBD MASK OFF BIT OFF1 STA A IOBD RTS PAGE * TASK COR * * CARRIER OPERATION AND THREE MINUTE TIMER. * WAIT FOR CARRIER COR SWI TST IOAD BPL COR WAIT FOR CARRIER LDA A &BOFF BIT A IOBD BNE COR IGNORE CARRIER IF OUT OF SERVICE LDA A &BTRN BSR ON TRANSMIT ON * PAUSE FOR CARRIER DELAY (SHORT TRANSMISSIONS ONLY) COR1 BSR PAUSE TST IOAD SENSE SHORT TRANSMISSION BPL COR5 LDA A &6 RESET POKE COUNTER STA A POKE COR5 DEC POKE BPL COR4 IF NOT MAD YET LDA A &^11011 MORSE Q BSR BEEP LDA A &^10100 MORSE F BSR BEEP LDA A &^110 MORSE A JSR BEEP * WAIT FOR CARRIER DROP OR TIMEOUT, SAMPLE FREQUENCY COR4 LDA A CLOCK START THREE MINUTE TIMER ADD A &3*60/CSPD CLR B COR2 SWI TST IOAD BPL COR8 IF CARRIER HAS DROPED TST CLOCK+1 BNE COR7 ORA B IOAD SAMPLE FREQ AT REGULAR INTERVALS COR7 CMP A CLOCK BNE COR2 IF NOT YET TIMED OUT LDA A &^11011 MORSE Q JSR BEEP LDA A &BOFF OUT OF SERVICE BSR ON CLR ACTIVE HANGUP PHONE * AUTO FREQUENCY NETTING RESPONSE COR8 BIT B &BHIF+BLOF BEQ COR3 IF ON FREQ LDA A &500/CKPD BSR DELAY LDA A &^10000 MORSE H BIT B &BHIF BNE COR9 IF HIGH LDA A &^10010 MORSE L COR9 JSR BEEP * HOLD TRANSMITTER UP FOR OTHER TASKS COR3 SWI LDA A &BOFF BIT A IOBD BNE COR6 IGNORE CARRIER IF OUT OF SERVICE TST IOAD BMI COR1 IF CARRIER IS BACK COR6 LDA A XMIT BNE COR3 IF OTHER TASK REQUIRES TRANS LDA A &BTRN JSR OFF TURN OFF TRANSMITTER BRA COR PAGE * TASK IDENTIFIER IDENT SWI LDA A &BTRN BIT A IOBD BEQ IDENT IF NOT TRANSMITTING LDX &CALL LDA A 0,X GET FIRST CHAR LDA B &IDTONE IDE1 JSR CODE INX GET NEXT CHAR LDA A 0,X BNE IDE1 IF NOT END OF TABLE LDA B CLOCK ADD B &4*60/CSPD 4 MINUTES IDE2 SWI CMP B CLOCK BNE IDE2 IF NOT YET TIME TO ID BRA IDENT * REPEATER IDENTIFICATION CALL FCB ^1 FCB ^1001 D FCB ^10 E FCB ^1 FCB ^1 FCB ^1110 W FCB ^1010 R FCB ^101111 9 FCB ^110 A FCB ^10101 C FCB ^10011 Z FCB ^1 FCB 0 PAGE * TASK RINGER * * THIS TASK SIGNALS WITH A MORSE CODE 5 WHENEVER AN INCOMMING * CALL IS DETECTED. NOTE, THE STRUCTURE OF COR WILL PREVENT * SPONTAINOUS OPERATION OF THE REPEATER. RINGER SWI LDA A &BRNG BIT A IOAD BEQ RINGER IF NOT RINGING LDA A &^100000 MORSE 5 JSR BEEP JSR PAUSE BRA RINGER PAGE * TASK DIAL-PULSER * * THE PATCH IS CONNECTED ACCORDING TO THE PATCH ACTIVITY FLAG. * DIGITS ARE REMOVED FROM THE DIGIT QUEUE 1 SECOND AFTER * THE FIRST DIGIT APPEARS. IF THE PATCH IS ACTIVE, * THE CONNECTION IS BROKEN TO PULSE THE LINE, OTHERWISE * THE DIGIT IS IGNORED. PATCH AUDIO IS MUTED DURRING DIALING * AND WHEN CARRIER IS PRESENT. * WAIT FOR PATCH ACTIVITY DIA0 LDA A &BCON+BLSN JSR OFF DIAL SWI LDA A ACTIVE BEQ DIAL IF INACTIVE LDA A &BCON CONNECT PATCH JSR ON * WAIT FOR DIGIT, CONTROL AUDIO MUTING DIA4 SWI LDA A &BLSN TST IOAD BMI DIA5 IF CARRIER, THEN MUTE JSR ON CLR A DIA5 JSR OFF LDA A ACTIVE BEQ DIA0 IF WE'VE HUNGUP LDX DIGITS BEQ DIA4 WAIT FOR DIGITS JSR PAUSE * GET NEXT DIGIT FROM QUEUE DIA1 LDX DIGITS CHECK QUEUE BEQ DIA4 IF DONE DIALING DEX STX DIGITS LDA B QUEUE GET DIGIT LDX &$FFFF -1 DIA2 LDA A QUEUE+2,X MOVE QUEUE DOWN STA A QUEUE+1,X INX CPX DIGITS BNE DIA2 * PULSE CONNECTION FOR DIGIT DIA3 LDA A ACTIVE BEQ DIA1 IF HUNGUP WHILE DIALING LDA A &BCON+BLSN DISCONNECT PHONE AND AUDIO JSR OFF LDA A &33/CKPD 10HZ, 33 PCT DUTY CYCLE JSR DELAY LDA A &BCON LEAVE AUDIO MUTED JSR ON LDA A &67/CKPD JSR DELAY DEC B COUNT PULSES BNE DIA3 IF PULSES REMAINING LDA A &600/CKPD 600 MSEC INTER-DIGIT JSR DELAY BEQ DIA1 PAGE * TASK CONTROL * * TOUCH TONE CONTROL FUNCTION PROCESSING AND AUTO-PATCH * SUPERVISION. CONTRL JSR GETDGT BEQ CONTRL IGNORE TIMEOUT LDA A &BOFF * OUT OF SERVICE CON1 CPX &$1242 BNE CON2 JSR ON BRA CON7 * IN SERVICE CON2 CPX &$4422 BNE CON3 JSR OFF BRA CON7 * COMPLETE SHUTDOWN (NOT ACKNOWLEDGED) CON3 CPX &$1824 BNE CON4 STA A IOBD SEI STOP CLOCK AND HALT BRA * * PROGRAM AUTO-PATCH ACCESS CON4 CPX &$4421 BNE CON5 LDA A &BPRV CHECK PRIVILEGE BIT A IOAD BEQ CONTRL IF NOT PRIVILEGED LDX &0 STX ASMBLY BSR GETDGT BSR GETDGT BSR GETDGT STX ACCESS UPDATE ACCESS CODE BRA CON7 * AUTO-PATCH ACCESS CON5 CLR B B=0 FOR NORMAL ACCESS CPX ACCESS BEQ PATCH INC B B=1 FOR 911 ACCESS CPX &$911 BEQ PATCH BRA CONTRL * ACKNOWLEDGE CONTROL FUNCTIONS CON7 LDA A &^1010 MORSE R INC XMIT HOLD XMIT UP CON9 BSR DROP JSR BEEP SEND ACKNOWLEDGEMENT DEC XMIT DROP XMIT BRA CONTRL * CONNECT PATCH PATCH LDA A &BOFF BIT A IOBD BNE CONTRL IF OUT OF SERVICE INC XMIT STA B A911 BSR DROP LDA A &^10001 MORSE B LDA B &BUSE BIT B IOAD BNE CON9 IF PHONE IN USE LDA A &^10101 MORSE C JSR BEEP INC ACTIVE CONNECT PATCH * PROCESS DIGITS FOR PATCH PAT2 BSR GETDGT BEQ PAT3 IF TIMED OUT LDA B A911 BNE PAT3 IF ACCESSED VIA 911 CPX &$12 BEQ PAT3 IF DISCONNECT CODE CMP A &10 BGT PAT2 IF NON-DIALABLE DIGIT * QUEUE DIGIT FOR DIAL PULSER LDX DIGITS CPX &QUELEN BEQ PAT3 IF QUEUE IS FULL STA A QUEUE,X INX POST INCREMENT QUEUE POINTER STX DIGITS BRA PAT2 * DISCONNECT PATCH PAT3 CLR ACTIVE LDA A &^1111 MORSE O BRA CON9 * SUBROUTINE DROP * * WAITS FOR INPUT CARRIER TO DROP. (A) AND (B) ARE * PRESERVED. DROP SWI TST IOAD BMI DROP IF CARRIER STILL THERE PSH A LDA A &500/CKPD 1/2 SECOND JSR DELAY PUL A RTS * SUBROUTINE GET-DIGIT * * GET DIGIT WAITS FOR AND RETURNS IN (A) THE NEXT ENTERED TOUCH- * TONE DIGIT. THE DIGIT IS ALSO SHIFTED INTO THE CODE NUMBER * ASSEMBLY IN THE INDEX REGISTER. A CARRIER DROP CLEARS THIS * ASSEMBLY. IF CARRIER IS NOT PRESENT FOR AN EXTENDED * PERIOD OF TIME GET DIGIT WILL TIME OUT RETURNING ZERO. * ON EXIT (B) IS DESTROYED. GETDGT SWI BSR READTT BNE GETDGT WAIT FOR PREVIOUS TONE TO STOP GET1 LDA B CLOCK START TIMER ADD B &3*60/CSPD 3 MINUTES GET2 SWI LDA A &BCAR+BPRV BIT A IOAD BEQ GET4 IF NEITHER CARRIER PRESENT BSR READTT BEQ GET1 IF NOT DIGIT YET LDA B ASMBLY BIT B &$F0 BNE GET5 IF ASSEMBLY FULL LDA B &4 GET3 ASL ASMBLY+1 LEFT SHIFT ASSEMBLY ROL ASMBLY DEC B BNE GET3 LOOP FOR 4 BITS ORA A ASMBLY+1 STA A ASMBLY+1 INSERT NEW DIGIT AND A &^00001111 BRA GET5 GET4 CLR A CLEAR ON CARRIER DROP STA A ASMBLY STA A ASMBLY+1 CMP B CLOCK CHECK FOR TIMEOUT BNE GET2 GET5 LDX ASMBLY RETURN ARGS TST A RTS * SUBROUTINE READ-TOUCH-TONE READTT LDX &TTLIST SEARCH TABLE FOR LEGAL COMBINATION LDA A &TTMAX LDA B TTID READ DEVICE REA1 CMP B 0,X BEQ REA2 IF FOUND LEGAL CODE INX DEC A BNE REA1 LOOP TO END OF LIST REA2 TST A RTS TTLIST FCB ^10000100 C (&) FCB ^10000001 B (*) FCB ^10000010 A (0) FCB ^01000100 9 FCB ^01000010 8 FCB ^01000001 7 FCB ^00100100 6 FCB ^00100010 5 FCB ^00100001 4 FCB ^00010100 3 FCB ^00010010 2 FCB ^00010001 1 TTMAX EQU *-TTLIST END FIN