;;; -*-Midas-*- .TITLE IOELEVEN .SBTTL DEFINITIONS ;;; note that the .IFM macro must be used only at toplevel ;;; (non-conditionalized) in PALX because it doesn't do the expansion of .IFM ;;; when conditionalized out, therefore it doesn't match it with the ;;; following .ENDC and the .ENDC will be seen at toplevel and end the ;;; conditionalization one is in. This will screw the code running on ;;; another one of the machines even if it doesn't signal an error in your ;;; assembly. --PGS .LIF NZ 0 .FATAL USE PALX DUMMY!! ;NOTE THAT THIS PROGRAM IS DESIGNED FOR 11/40'S. TO RUN ON AN ;11/10, MACRO OUT THE SOB INSTRUCTIONS. DOES NOT USE EIS NOR FIS. A=%0 ;TEMP/ARG/CHAR B=%1 ;TEMP/ARG C=%2 ;TEMP/ARG D=%3 ;TEMP/ARG H=%4 ;USUALLY INDEX IN HARDWARE UNIT TABLES I=%5 ;USUALLY LINE NUMBER TIMES 2 SP=%6 ;STACK POINTER PC=%7 ;PROGRAM POINTER PS=177776 ;PROGRAM STATUS SWR=177570 ;SWITCHES .MACRO RTI .ENDM ;FUCKING PALX! RTI=RTT ;11/40 HARDWARE MISFEATURE .IF P1 .PRINT /MACHINE NAME = / .TTYMAC MNAM %TTYFLG==%TTYFLG+1 .PRINT /MNAM / %TTYFLG==%TTYFLG-1 .MACRO .IFM MCHN ;REFERS TO PDP11 NAME .IF IDN MCHN,MNAM .ENDM .IFM .MACRO MCONDX MCHN ;REFERS TO ITS SYSTEM NAME, USUALLY THE SAME .IF IDN MCHN,MNAM .ENDM MCONDX .MACRO FUBAR .ENDC .ENDC .ENDM FUBAR .MACRO MNAME BODY ;INSERT ITS SYSTEM NAME INTO BODY IN PLACE OF "MCHN" .IRP MCHN, BODY .ENDM .ENDM MNAME .ENDM ;TTYMAC .ENDC ;P1 VERSION==%FNAM2 .IFM MC-DL ;MC'S DL-10 PDP11 .MACRO MCONDX MCHN .IF IDN MCHN,MC .ENDM MCONDX .MACRO FUBAR .ENDC .ENDM FUBAR .MACRO MNAME BODY .IRP MCHN, BODY .ENDM .ENDM MNAME DL10P==1 ;HAS DL10 DTE20P==0 ;DOES NOT HAVE DTE20 NODDT==0 ;HAS DDT NFTTY==102 ;2 * # OF FIRST TTY THIS 11 NDHS==1 ;NUMBER OF DH11'S NDHUN==15 ;NUMBER OF UNUSED DH11 LINES DHIBAS==320 ;DH11 INTERRUPT VECTOR BASE DHCBAS==160020 ;CSR of first DH11 NDLS==1 ;NUMBER OF DL11'S CTYP==0 ;FIRST DL11 NOT T00 (CTY) NMPTYS==0 ;NUMBER OF TTYS ON MULTIPLEXED LINE (REST IN PEACE) ;MPXIDX==2*27 ;TTY INDEX OF LINE THAT MULTIPLEXED TTYS RUN OVER NDMS==0 ;HAS DM11BB MODEM SCANNER (BUT IT'S NOT CONNECTED TO ANYTHING) GOULDP==0 ;DOESN'T HAVE GOULD LPT (ANYMORE) T300P==1 ;TRIDENT T-300 AND 2561 CONTROLLER CHAOSP==2 ;HAS TWO CHAOS NET INTERFACES CHSBTB=0 ;CHAOSNET INTERFACE IS NEW, DOESN'T GET HUNG ANY MORE CHAD0==440 ;CHAOSNET ADDRESS OF THIS PDP11 ITSELF DLCADR==1440 ;CHAOSNET ADDRESS OF PDP10 CONNECTED VIA DL10 (MC) CHAD1==3040 ;SECOND INTERFACE TEN11P==0 ;NO TEN-11 INTERFACE ETHERP==0 ;NO ETHERNET FTPULS==0 ;INITIALLY, MC DOES NOT GENERATE TEST PACKETS FTGARB==1 ;SAVE LAST GARBAGE PACKET RECEIVED MAXBSZ==250. ;MAXIMUM TYPEOUT BUFFER SIZE .MACRO ASPIRP BODY ;DEFINE LINE NUMBERS WITH AUTOSPEED .ENDM ASPIRP .ENDC ;MC-DL .IFM MC ;MC CONSOLE 11 DL10P==0 ;DOES NOT HAVE DL10 DTE20P==1 ;HAS DTE20 NODDT==0 ;HAS DDT AND KLDCP NFTTY==0 ;2 * # OF FIRST TTY THIS 11 NDHS==2 ;NUMBER OF DH11'S NDHUN==0 ;NUMBER OF UNUSED DH11 LINES DHIBAS==310 ;DH11 INTERRUPT VECTOR BASE DHCBAS==160020 ;CSR of first DH11 NDLS==1 ;NUMBER OF DL11'S CTYP==1 ;FIRST DL11 IS T00 (CTY) NMPTYS==0 ;NUMBER OF TTYS THAT GO THROUGH MULTIPLEXED LINE (NONE) NDMS==2 ;has 2 DM11BB modem scanners (really DH11AD) GOULDP==0 ;DOESN'T HAVE GOULD LPT T300P==0 ;TRIDENT T-300 AND 2561 CONTROLLER CHAOSP==0 ;NO CHAOS NET INTERFACE TEN11P==0 ;NO TEN-11 CHAOS INTERFACE ETHERP==0 ;NO ETHERNET MAXBSZ==250. ;MAXIMUM TYPEOUT BUFFER SIZE .MACRO ASPIRP BODY ;DEFINE LINE #S WITH AUTOSPEED .IRP N,<1,3,4,5,6,7,10,11,12,13,14,15,16,17> BODY .ENDM .ENDM ASPIRP TKS==177560 TKB==177562 TPS==177564 TPB==177566 .ENDC ;MC .IFM AI ;AI'S CHAOS-ETHER-GATEWAY PDP11 ;THIS IS A PDP11/10, WE HAVE TO REDEFINE A FEW THINGS .MACRO RTT .ENDM RTI==2 RTT==2 .MACRO SOB REG,TAG DEC REG BNE TAG .ENDM SOB DL10P==0 ;HAS NO DL10 DTE20P==0 ;DOES NOT HAVE DTE20 NODDT==1 ;DOESN'T HAVE DDT (USE CARPET) NFTTY==0 ;2 * # OF FIRST TTY THIS 11 NDHS==0 ;NUMBER OF DH11'S NDHUN==0 ;NUMBER OF UNUSED DH11 LINES DHIBAS==320 ;DH11 INTERRUPT VECTOR BASE DHCBAS==160020 ;CSR of first DH11 NDLS==0 ;NUMBER OF DL11'S (ACTUALLY HAS ONE, BUT WE'RE NOT USING IT NOW) CTYP==0 ;FIRST DL11 NOT T00 (CTY) NMPTYS==0 ;NUMBER OF TTYS ON MULTIPLEXED LINE NDMS==0 ;HAS NO DM11BB MODEM SCANNERS GOULDP==0 ;DOESN'T HAVE GOULD LPT T300P==0 ;TRIDENT T-300 AND 2561 CONTROLLER CHAOSP==2 ;HAS TWO CHAOS NET INTERFACES CHSBTB==0 ;CHAOSNET INTERFACE IS NEW-STYLE, DOES NOT GET HUNG ;CHAD0==426 ;CHAOSNET ADDRESS OF THIS PDP11 ITSELF (AI-MC-CROSS-STREET SUBNET) ;CHAD1==3072 ;SECOND INTERFACE (9TH FLOOR LISP MACHINE SUBNET) CHAD0==3072 ;Change these two around because subnet 1 is dying of old age. CHAD1==426 ;Note that with current code AI-11 can only do DOVER on CHAD0!! TEN11P==0 ;USES TEN-11 INTERFACE FOR CHAOS NET TO AI-10 (NOT ANY MORE!) T11ADR==2026 ;CHAOSNET ADDRESS OF PDP10 CONNECTED VIA TEN-11 INTERFACE (AI) NT11BF==3 ;THREE BUFFERS IN EACH DIRECTION FOR TEN-11 INTERFACE ETHERP==1 ;ETHERNET ETHHSN==6 ;MY HOST NUMBER BYTE, JNC SAYS I SHOULD USE 6 NDVRBF==6 ;6 DOVER BUFFERS DVRADR==1002 ;PUP ADDRESS OF DOVER FTPULS==0 ;INITIALLY, AI DOES NOT GENERATE TEST PACKETS FTGARB==1 ;DON'T SAVE LAST GARBAGE PACKET RECEIVED (LOW ON CORE) (not that low) MAXBSZ==250. ;MAXIMUM TYPEOUT BUFFER SIZE .MACRO ASPIRP BODY ;DEFINE LINE NUMBERS WITH AUTOSPEED .ENDM ASPIRP .ENDC ;AI .IIF NDF NDHS, .ERROR MACHINE NAME NOT RECOGNIZED .IIF NZ DL10P, .IIF Z NFTTY, .ERROR TTY # 0 DOESN'T WORK WITH DL10 PROTOCOL ;ASSIGN TTY INDICES, HARDWARE INDICES, ETC. TX==NFTTY ;TTY INDEX HX==0 ;HARDWARE INDEX NCT==0 ;NUMBER OF TTYS ;SYSTEM CONSOLE (OUT OF ORDER) .IFNZ CTYP TX==TX+2 NCT==NCT+1 .ENDC ;DH11 LINES NFDHTY==TX TX==TX+<32.*NDHS> NCT==NCT+<16.*NDHS> HX==HX+<2*NDHS> NLDHHX==HX-2 ;UNITS 0-NLDHHX INCLUSIVE ARE DH11S TX==TX-<2*NDHUN> ;COMPENSATE FOR UNUSED LINES NLDHTY==TX-2 ;LAST DH11 LINE INCLUSIVE NCT==NCT-NDHUN ;DL11 LINES NFDLTY==TX NFDLHX==HX TX==TX+<2*NDLS>-<2*CTYP> HX==HX+<2*NDLS> NLDLHX==HX-2 NCT==NCT+NDLS-CTYP ;MULTIPLEXOR LINES NFMPTY==TX MPKHWR==HX TX==TX+<2*NMPTYS> HX==HX+2 NCT==NCT+NMPTYS NLTTY==NFTTY+<2*NCT> ;2 * # OF FIRST TTY NOT THIS 11 LASTTY==NLTTY-2 ;LAST VALID TTY INDEX .IFNZ NDMS ;DM11-BB MODEM SCANNER ;1.1-1.4 MODEM CHANNEL # DMBSY==20 ;1.5 SCAN BUSY (R.O.) DMSCN==40 ;1.6 SCANNER ON DMIEN==100 ;1.7 INTERRUPT ENABLE DMDON==200 ;1.8 DONE - SCANNER HAS FOUND SOMETHING DMSTP==400 ;1.9 STEP SCANNER TO NEXT LINE (W.O.) 1.2 USEC. ;2.1 MAINTENANCE MODE DMCLR==2000 ;2.2 CLEAR RTS, DTR, SEC TX, LINE EN FOR ALL LINES (W.O.) DMCSN==4000 ;2.3 CLEAR SCAN - CLEAR CSR AND MODEM STATUS MEMORY (W.O.) 19 USEC DM2RX==10000 ;2.4 SECONDARY RECIEVE CHANGED ON SELECTED MODEM (R.O.) DMCTS==20000 ;2.5 CLEAR TO SEND CHANGED ON SELECTED MODEM (R.O.) DMCAR==40000 ;2.6 CARRIER DETECT CHANGED ON SELECTED MODEM (R.O.) DMRNG==100000 ;2.7 RING CHANGED ON SELECTED MODEM (R.O.) LINENB==1 ;1.1 ENABLE SCANNING OF LINE LINDTR==2 ;1.2 DATA TERMINAL READY LINRQS==4 ;1.3 REQUEST TO SEND (FORCE BUSY ON 103E) LIN2TX==10 ;1.4 SECONDARY TRANSMIT LIN2RX==20 ;1.5 SECONDARY RECEIVE (R.O.) LINCTS==40 ;1.6 CLEAR TO SEND (R.O.) LINCAR==100 ;1.7 CARRIER DETECT (R.O.) LINRNG==200 ;1.8 RING (R.O.) .ENDC ;NDMS ; KW11-L LINE FREQ CLOCK LKS=177546 ;1.8 CLOCK FLAG ;1.7 INTER ENB HNGDLY==3*60. ;CLEAR TO SEND OFF FOR 3 SECONDS => HANGUP .IFNZ GOULDP ;DEFINITIONS FOR GOULD LPT GLPCSR=166000 ;COMMAND STATUS REGISTER (NONSTANDARD) ;COMMAND CODES %GCFF==0 ;TOP-OF-FORM COMMAND %GCGRF==1 ;GRAPHIC MODE COMMAND %GCCUT==2 ;CUT COMMAND (NO CUTTER ON THIS MACHINE, THOUGH) %GCON==3 ;TURN PRINTER ON %GCOFF==4 ;TURN PRINTER OFF %GCLSL==5 ;LAST LINE (GRAPHIC MODE). => 2 MORE SCAN LINES. %GCION==6 ;INTERRUPT ON %GCIOF==7 ;INTERRUPT OFF %GCADV==201 ;ADVANCE ONE LINE ;STATUS BITS %GSNRD==400 ;NOT READY %GSDON==2000 ;TRANSFER COMPLETE %GSBSY==4000 ;BUSY %GSVAC==10000 ;VACUUM FAULT %GSPAP==20000 ;PAPER LOW %GSTIM==40000 ;TIMEOUT %GSERR==50400 ;ALL ERROR BITS GLPWC=166002 ;NEGATIVE WORD COUNT REG GLPCA=166004 ;CURRENT ADDRESS REG GLPBSZ==132. ;BUFFER SIZE (# CHARS PER LINE) NGLPBF==7 ;NUMBER OF BUFFERS GB.STA==0 ;BUFFER STATE - DON'T CHANGE ORDER OF %GB CODES %GBIDL==0 ;0 IDLE %GBMP==2 ;2 ACTIVE AT M.P. LEVEL %GBWRT==4 ;4 IN WRITE QUEUE %GBPI==6 ;6 ACTIVE AT P.I. LEVEL %GBDMA==8 ;8 ACTIVE AT D.M.A. LEVEL GB.NXT==2 ;CIRC POINTER TO NEXT BUFFER GB.FF==4 ;IF NON-ZERO, FF BEFORE THIS BUFFER GB.NL==6 ;NUMBER OF BLANK LINES BEFORE THIS BUFFER GB.PNT==10 ;-> NEXT BYTE TO INSERT GB.DAT==12 ;DATA BEGINS HERE GB.LEN==GB.DAT+GLPBSZ ;TOTAL NUMBER OF BYTES PER BUFFER .ENDC ;GOULDP .IFNZ CHAOSP ;DEFINITIONS OF CHAOS NET HARDWARE ;USUAL ADDRESS IS 764140 . USUAL INTERRUPT VECTOR IS 270 . CAICSR=164140 ;COMMAND STATUS REG CH%CSR==0 %CABSY==1 ;0 XMT BUSY (RO) %CALUP==2 ;1 LOOP BACK (R/W) %CASPY==4 ;2 RECIEVE MSGS FOR ANY DESTINATION (R/W) %CARCL==10 ;3 CLEAR THE RECEIVER, IT CAN NOW GOBBLE ANOTHER MSG (WO) %CAREN==20 ;4 RCV INT ENB (R/W) %CATEN==40 ;5 XMT INT ENB (R/W) %CATAB==100 ;6 TRANSMIT ABORTED BY ETHER CONFLICT (RO) %CATDN==200 ;7 TRANSMIT DONE. SET WHEN TRANSMITTER IS DONE %CATCL==400 ;8 CLEAR THE TRANSMITTER, MAKING IT READY (WO) ;9-12 LOST COUNT (RO) [# MSGS RCVED WITH RCV BFR FULL] ; WHEN MSG IS WAITING IN BUFFER, THIS COUNTS ; THE MESSAGES THAT MATCHED OUR DESTINATION OR ; WERE BROADCAST, BUT COULDN'T BE RECIEVED. ; WHEN RECEIVER IS RE-ENABLED (WRITE 1 INTO %CARDN) ; THE COUNT IS THEN CLEARED. ; WHEN A MESSAGE IS LOST, RECEIVER ZAPS ETHER ; SO TRANSMITTER WILL ABORT (IF MESSAGE WAS DESTINED ; TO US.) %CARST==20000 ;13 I/O RESET (WO) %CAERR==40000 ;14 CRC ERROR (RO) %CARDN==100000 ;15 RCV DONE. CAIMYN=164142 ;MY # (READ ONLY) CH%MYN==2 ;RETURNS THE [SOURCE] HOST# OF THIS INTERFACE. CAIWBF=164142 ;WRITE BUFFER (WRITE ONLY) CH%WBF==2 ;FIRST WAIT FOR TDONE. (OR SET IT VIA CSR) ;FIRST WORD IN RESETS TRANSMITTER AND CLEARS TDONE. ;STORE INTO THIS REGISTER TO WRITE WORDS OF MESSAGE, ;LAST WORD IN IS DESTINATION ADDRESS, THEN READ CAIXMT. ;SOURCE ADDRESS AND CHECK WORD PUT IN BY HARDWARE. CAIRBF=164144 ;READ BUFFER (READ ONLY) CH%RBF==4 ;THE FIRST WORD READ WILL BE FILLED TO THE LEFT ;TO MAKE THE MESSAGE RECIEVED A MULTIPLE OF 16 BITS. ;IF THE NUMBER OF DATA BITS IN THE MESSAGE WAS A ;MULTIPLE OF 16, THIS WORD WILL BE THE FIRST WORD PUT ;INTO THE BUFFER BY THE TRANSMITTING HOST. ;THE LAST 3 WORDS READ ARE DESTINATION, SOURCE, CHECK. CAIRBC=164146 ;RECEIVE BIT COUNTER (READ ONLY) CH%RBC==6 ;WHEN A MESSAGE HAS BEEN RECEIVED THIS IS ONE LESS THAN ;THE NUMBER OF BITS IN THE MESSAGE (16 X THE ;NUMBER OF WORDS INCLUDING THE THREE OVERHEAD WORDS.) ;AFTER THE LAST WORD (THE CRC WORD) HAS BEEN READ, IT IS 7777 ;BITS 10 AND 11 ARE THE HIGH ORDER BITS, AND IF THEY ARE ONE, ;THEN THERE WAS A BUFFER OVERFLOW CAIXMT=164152 ;READING THIS INITIATES TRANSMISSION (!!) CH%XMT==12 ;THE VALUE READ IS ONE'S OWN HOST#. ;REFERENCING ADDRESSES IN THE GROUP OF 8 WORDS NOT LISTED HERE, OR ;USING COMBINATIONS OF READ/WRITE NOT LISTED HERE, WILL TYPICALLY CAUSE ;STRANGE AND BIZARRE EFFECTS. ;PACKET DEFINITIONS ;THESE ARE FOR 4K PACKET BUFFERS AND FOR THE ORIGINAL CHAOSNET PROTOCOL PKMAX==256. ;MAXIMUM LENGTH OF PACKET (INCLUDING ALL HARDWARE WORDS) DATMAX==488. ;MAXIMUM NUMBER OF DATA BYTES PKHDW==8 ;NUMBER OF HEADER WORDS PKTMXW==+PKHDW ;MAX WORDS THROUGH PACKET SWITCH (SEE MOVDH ETC.) PKOP==1 ;BYTE INDEX OF THE OPCODE OF THE PACKET %CORFC==1 %COOPN==2 %COCLS==3 %COANS==5 %COSNS==6 %COSTS==7 %CORUT==10 %COLOS==11 %COEOF==14 %COUNC==15 PKNBYT==2 ;WORD INDEX OF NUMBER OF BYTES IN PACKET PKNBMS==170000 ;MASK FOR THE NUMBER OF BYTES PKFC==2 ;WORD INDEX FOR THE FORWARD COUNT PKFCMS==7777 ;IT IS THE TOP 4 BITS PKDHST==4 ;DESTINATION HOST PKDIND==6 ; " " " INDEX PKSHST==10 ;SOURCE HOST PKSIND==12 ;SOURCE INDEX PKPKN==14 ;THE PACKET NUMBER PKACN==16 ;THE ACK PACKET NUMBER PKDAT==20 ;THE START OF THE DATA .ENDC ;CHAOSP ;STANDARD MACROS .MACRO PUSH X .IRP Y, MOV Y,-(SP) .ENDM .ENDM .MACRO POP X .IRP Y, MOV (SP)+,Y .ENDM .ENDM .MACRO CALL X JSR PC,X .ENDM .MACRO RET RTS PC .ENDM .MACRO SETOM LOC ZZ===%COMPAT ;DON'T CARE WHETHER .+2 OR .+4 GETS STORED %COMPAT===0 MOV PC,LOC %COMPAT===ZZ .ENDM .MACRO MASK LEVEL PUSH PS MOV #_5,PS .ENDM .MACRO UNMASK POP PS .ENDM .MACRO W .=.+2 .ENDM .MACRO T TAG ;usage is T TAG: STMNT .=.-NFTTY TAG .=.+NFTTY .ENDM .MACRO CONC A,B,C,D,E,F,G A'B'C'D'E'F'G .ENDM .MACRO INFORM A,B,C,D,E,F,G .IF P1 .PRINT /A'B'C'D'E'F'G / .ENDC .ENDM .MACRO MSG X .NCHR ZZ,^\X\ .WORD ZZ .ASCII \X\ .EVEN .ENDM .MACRO .IREPT N,BOD .REPT N BOD .ENDR .ENDM .IFNZ DL10P .SBTTL DL10 CONTROL AREA ZZ==. .=100000 DLXCSR: W ;DL10 11-SIDE CONTROL & STATUS REG ;1.1-1.2 PIA DLXIEN==4 ;1.3 ENABLE DLX11I TO INTERRUPT DLXEEN==10 ;1.4 ENABLE ERRORS TO INTERRUPT ;1.5 UNUSED DLXPRT==40 ;1.6 PORT ENABLE (R.O.) DLXZWC==100 ;1.7 CLEAR DLXWCO (W.O.) DLXWCO==200 ;1.8 WORD COUNT OVERFLOW DLXZPA==400 ;1.9 CLEAR DLXPAR (W.O.) DLXPAR==1000 ;2.1 PAR ERR IN 10 MEM DLXZNX==2000 ;2.2 CLEAR DLXNXM (W.O.) DLXNXM==4000 ;2.3 NXM IN 10 MEM DLXZ10==10000 ;2.4 CLEAR DLX10I (W.O.) DLX10I==20000 ;2.5 INTERRUPT PDP10 DLXZ11==40000 ;2.6 CLEAR DLX11I (W.O.) DLX11I==100000 ;2.7 INTERRUPT PDP11 VERS: W ;.BYTE FIRST LINE, # OF LINES ;SET BY -10. USED TO CHECK CONSISTENCY. DLXUP: W ;CHECK FOR UP-NESS IN BOTH DIRECTIONS ;INCREMENTED BY 11 EVERY 1/60 SECOND, SETOM'ED BY 10 EVERY 1/2 SEC. TTYST: W ;LINE# TO START OUTPUT ON (I.E. SET OUTPUT DONE) ;SET BY 10, CLEARED BY 11 TYILIN: W ;TYPEIN STATUS WORD - LINE NUMBER ;SET BY 11, CLEARED BY 10 - INTERRUPTS 10 TYICHR: W ;TYPEIN CHARACTER - GOES WITH PRECEDING WORD TYOSTS: W ;STATUS WORD (OUTPUT DONE LINE #) ;SET BY 11, CLEARED BY 10 - INTERRUPTS 10 TYOBSZ: W ;BUFFER SIZE FOR LINE WITH OUTPUT DINE (SET BY 11) TYOPNT: W ;BUFFER POINTER FOR TTY OUTPUT ;SET BY 10 TYOCNT: W ;BUFFER LENGTH FOR TTY OUTPUT ;SET BY 10 TYOLIN: W ;LINE NUMBER FOR TTY OUTPUT ;SET BY 10, CLEARED BY 11 HNGLIN: W ;0000NN - LINE # NN HUNG UP ;01RTNN - LINE # NN HAS SPEED RCV=R, XMT=T (SEE TTYTYP FOR CODES) ;SET BY 11, CLEARED BY 10 - INTERRUPTS 10 LPRLIN: W ;LINE NUMBER FOR SETTING LINE PARAMETERS ;SET BY 10, CLEARED BY 11 LPRLPR: W ;DH11 LPR REGISTER FOR SETTING LINE PARAMETERS ;SET BY 10 LPRBSZ: W ;BUFFER SIZE FOR SETTING LINE PARAMETERS ;SET BY 10 EXDSTS: W ;STATUS WORD (EXAMINE/DEPOSIT 11 CORE) ;1 = EXAMINE, 2 = DEPOSIT ;SET BY 10, CLEARED BY 11 EXDADR: W ;ADDRESS FOR ABOVE ;SET BY 10 EXDDAT: W ;DATA WORD FOR ABOVE ;SET BY 10 (DEPOSIT) OR 11 (EXAMINE) GLPPTR: W ;BUFFER POINTER FOR GOULD OUTPUT GLPCTR: W ;NUMBER OF BYTES YET TO BE GOBBLED GLPTER: W ;ERROR STATUS, SET BY 11 GLPGRF: W ;GRAPHIC MODE IF NON-ZERO, SET BY 10 ;CHAOS NET SHARED VARIABLES DLCINI: W ;WHEN THIS IS NON-ZERO, 11 RESETS ITS POINTERS AND CLEARS IT DLCSP1: W ;SEND PACKET 1 (ILDB POINTER) DLCSP2: W ;SEND PACKET 2 DLCSS1: W ;SEND STATE 1 (0 IDLE, 1 TO 11, 2 OUTPUT DONE) DLCSS2: W ;SEND STATE 2 DLCRP1: W ;RECEIVE PACKET 1 (ILDB POINTER) DLCRP2: W ;RECEIVE PACKET 2 DLCRS1: W ;RECEIVE STATE 1 (0 IDLE, 1 READY FOR INPUT FROM 11, 2 INPUT DONE) DLCRS2: W ;RECEIVE STATE 2 ;^ ADD MORE HERE, E.G. IMP .IFNZ T300P ;DISK AREA. 14. WORDS 48. WORDS INTO THE DL-10 AREA. .=100000+<60*2> DSCCHK: W ;MUST BE 2561 OCTAL TO MAKE SURE WE HAVE CORRECT PDP-10 PROGRAM DSCREQ: W ;0 MEANS NO REQUEST. NON-ZERO MEANS 10 HAS PENDING REQUEST TO 11. DSCDON: W ;0 MEANS NOT DONE, NON-ZERO MEANS 11 IS TELLING 10 IT'S DONE. ;NEXT 2 WORDS WRITTEN BY 11 TO TELL STATUS OF OPERATION DSCFLT: W ;0 NO FAULT %DFRST==100000 ; BIT 15=POWER CYCLED OR UNIBUS HUNG, SO CONTROLLER WAS RESET ; BIT 12=Q ERROR, BIT 11=CMD NXM, BIT 10=CMD PAR ; IF ONE OF THESE BITS IS ON, BITS 1-0 AND DSCSTS ARE THE ERROR ADDRESS ; BITS 7-0 SYSTEM FAULT CODE IF LEFT BYTE IS ZERO ; SEE THE 2561 OEM MANUAL FOR MEANING OF FAULT CODES DSCSTS: W ;STATUS FROM 2561: %DSRTR==100000 ;COMMAND WAS RETRIED %DSECH==40000 ;UNCORRECTABLE DATA ERROR (ECC HARD) %DSECC==20000 ;CORRECTED DATA ERROR %DSIDE==10000 ;ID ERROR %DSHCE==4000 ;ADDRESS ERROR (HEADER COMPARE ERROR) %DSPRT==2000 ;WRITE-PROTECT STATUS OF SECTOR (ABORTS WRITE COMMAND) %DSALT==1000 ;ALTERNATE-SECTOR STATUS (ABORTS READ, WRITE, AND CHECK) %DSOVR==400 ;FIFO OVER-RUN, NOT CORRECTED BY 1 RETRY %DSSKE==200 ;SEEK ERROR FROM DRIVE %DSOFL==100 ;DRIVE OFF-LINE OR FAULT %DSFLT==20 ;DRIVE FAULT %DSNXM==10 ;NXM ON PDP11 MEMORY %DSPAR==4 ;PARITY ERROR IN PDP11 MEMORY %DSSFL==2 ;SYSTEM FAULT, SEE LOW BYTE OF DSCFLT %DSWLK==1 ;DRIVE WRITE-LOCKED, WRITE ABORTED ;FOLLOWING WORDS ARE WRITTEN BY 10 TO TELL WHAT TO DO DSCCMD: W ;COMMAND OPCODE: ;%DMNOP==0 ;DO NOTHING ;%DMCST==1 ;READ OUT CONTROLLER STATE (NOT USEFUL SINCE NOT RETURNED TO 10) %DMSNS==2 ;SENSE DRIVE STATE. DSCSTS GETS CODE FOR DRIVE TYPE IN ; BITS 14-8 (10 FOR T-300), AND %DSWLK, %DSFLT, %DSOFL, %DSSKE %DMTST==3 ;TEST SPECIFIED DRIVE (RUNS DIAGNOSTICS) %DMREC==4 ;RECALIBRATE %DMSEK==5 ;SEEK %DMWRT==6 ;WRITE DATA ;%DMFMT==7 ;WRITE FORMAT ;%DMPWT==10 ;WRITE AND SET WRITE-PROTECT BIT ;%DMAWT==11 ;WRITE AND SET ALTERNATE-SECTOR BIT ;%DMCHK==12 ;READ AND CHECK ECC BUT DON'T STORE DATA ;%DMLWT==14 ;LONG WRITE, WILL WRITE ECC AS WELL AS DATA %DMRED==20 ;READ DATA. ADD 1-10 FOR VARIOUS RECOVERY FEATURES AS ; DOCUMENTED IN THE 2561 OEM MANUAL. ;%DMRID==40 ;READ IF FIELD, NOT USEFUL SINCE NOT RETURNED TO 10 DSCDRV: W ;UNIT NUMBER DSCCYL: W ;CYLINDER ADDRESS (THESE ARE COPIED BACK BY THE 11 IN CASE OF ERROR) DSCHED: W ;HEAD ADDRESS DSCSEC: W ;SECTOR ADDRESS ;WORD COUNT IS ALWAYS 12.*256. ;IF WE PUT IN SEEK-OVERLAP AN ATTENTION FEATURE WILL BE NEEDED ;THAT WOULD ALSO BE USED FOR DISK POWER-UP SIGNALLING ;THESE WORDS ARE SET UP BY THE 10 AS BYTE-POINTERS TO THE DATA ;TO BE TRANSFERRED. EACH BYTE POINTER CAN TRANSFER AT MOST 256 PDP10 WORDS ;DUE TO BRAIN-DAMAGE IN THE DL10, SO THERE ARE 4 OF THEM DSCPNT: .BLKW 4 .ENDC ;T300P DLXHGH:: .=ZZ .ENDC ;DL10P .IFNZ DTE20P .SBTTL DTE20 CONTROL AREA ;LOCATIONS 400-437 ARE JUST BETWEEN US AND ITS ;LOCATIONS 440-457 ARE KNOWN ABOUT BY KLDCP ALSO ;EPTDDT==441 ;START ADDRESS OF PDP10 NON TIME SHARING DDT DTEFLG==444 ;NON TIME SHARING TYPEIN/TYPEOUT DONE FLAG (SET BY 11, CLEARED BY 10) DTEF11==450 ;USED BY NON TIMESHARING TYPEIN COMMAND TO RETURN THE CHAR (SET BY 11) DTECMD==451 ;NON TIME SHARING COMMAND (SET BY 10) ;COMMANDS THAT CAN GO IN DTECMD: ;0-377 CHAR TO BE TYPED OUT %DTTYI==3400 ;TYPE IN, CHAR RETURNED IN DTEF11 %DTCLN==1001 ;60 CYCLE CLOCK ON %DTCLF==1000 ;60 CYCLE CLOCK OFF ;THERE ARE MILLIONS OF OTHERS, BUT WHO NEEDS 'EM? DTECLK==445 ;60 CYCLE CLOCK FLAG (SET BY 11, CLEARED BY 10) ;DTESWR==457 ;SIMULATED SWITCH REGISTER (SET BY 11) ;THE FOLLOWING LOCATIONS ARE ONLY USED IN TIME SHARING AND NOT KNOWN ABOUT BY KLDCP DTEVER==400 ;I/O VERSION NUMBER. .BYTE FIRST LINE, NUMBER OF LINES. ;SET BY 10, CHECKED BY 11 DTECHK==401 ;INCREMENTED BY 11 60 TIMES PER SECOND, SETOMED BY 10 EVERY 1/2 SECOND ;USED TO CHECK THAT 10 IS GETTING INTERRUPTS OK DTEINP==402 ;CONTROLS "BYTE TRANSFERS" FROM 11 TO 10 (INPUT DIRECTION). ;SET BY 10 TO REQUEST A TRANSFER, SETOM'ED BY 11 WHEN XFER COMPLETE. ;10 SHOULD SET UP DTEBPI IN EPT AND DO DATAO DTE, BEFORE SETTING DTEINP. ;SEE COMMENTS BELOW DTEOUT FOR WHAT GOES IN DTEINP. DTEOUT==403 ;CONTROLS "BYTE TRANSFERS" FROM 10 TO 11 (OUTPUT DIRECTION). ;SET BY 10 TO REQUEST A TRANSFER, SETOM'ED BY 11 WHEN TRANSFER STARTS. ;EACH SIDE KNOWS WHEN TRANSFER IS IN PROGRESS, DOESN'T TRY TO START ; ANOTHER UNTIL IT HAS RECEIVED HARDWARE TRANSFER-DONE INTERRUPT. ;10 SHOULD SET UP DTEBPO IN EPT BEFORE SETTING DTEOUT. ;RH IS #BYTES EXPECTED, LH IS COMMAND+LINE#. COMMANDS ARE: %DTTYO==1000 ;TELETYPE OUTPUT ;%DTETI==2000 ;ETHERNET INPUT ;%DTETO==3000 ;ETHERNET OUTPUT ;^ ADD MORE COMMANDS HERE. NOTE: THE 4.1 BIT IS 1 FOR OUTPUT, 0 FOR INPUT. DTELSP==404 ;LINE# TO SET SPEED OF (SET BY 10, SETOMED BY 11) DTELPR==405 ;DH11 LINE-PARAMETER-REGISTER,,BUFFER SIZE DTEOST==406 ;LINE# TO START OUTPUT ON (SET OUTPUT DONE). (SET BY 10, SETOMED BY 11) ;407 NOT USED DTETYI==410 ;TELETYPE INPUT ;LH=LINE#, RH=CHAR RECEIVED. (SET BY 11, SETOM'ED BY 10) DTEODN==411 ;TELETYPE OUTPUT DONE ;LH=LINE#, RH=BUFFER SIZE. (SET BY 11, SETOM'ED BY 10) DTEHNG==412 ;HANGUP/DIALIN WORD (SET BY 11, SETOM'ED BY 10) ;0000NN - LINE # NN HUNG UP ;01RTNN - LINE # NN HAS SPEED RCV=R, XMT=T (SEE TTYTYP FOR CODES) ;^ ADD MORE HERE, NOT TO EXCEED LOCATION 437 ;.IFNZ DTE20P ;IOELEVEN RESIDES IN THE BOTTOM 14K OF THE CONSOLE PDP11, ALONG WITH 11DDT. ;I.E. LOCATIONS 0-70000. BE SURE TO USE .;11DDT 14K VERSION OF DDT. ;THE UPPER 14K CONTAIN KLDCP. THE FOLLOWING CALLS TO KLDCP ARE USED. ;THEY RETURN WITH C-BIT SET IF THEY LOSE (MICROCODE HUNG). ;NOTE: KLDCP ENJOYS CLOBBERING REGISTER 0 (A). I DON'T ;KNOW IF ALL THESE CALLS DO, BUT WE'LL ASSUME THAT THEY DO. TENSW=EMT!145 ;UPDATE LOCATION DTESWR FROM THE SWITCHES EXAM=EMT!103 ;EXAMINE PDP10 MEMORY ;BEFORE CALL, REGISTER A HAS ADDRESS OF 3 BYTES CONTAINING PDP10 ADDRESS (LOW BITS FIRST) ;AFTER CALL, REGISTER A HAS ADDRESS OF 3 WORDS CONTAINING CONTENTS (LOW BITS FIRST) EXAMT=EMT!104 ;EXAMINE PDP10 MEMORY ;.WORD PDP10-ADDRESS ;.WORD ADDRESS OF 3-WORD DATA BLOCK DPOS=EMT!105 ;DEPOSIT PDP10 MEMORY ;BEFORE CALL, REGISTER A HAS ADDRESS OF 3 WORDS CONTAINING CONTENTS ;AND REGISTER B HAS ADDRESS OF 3 BYTES CONTAINING ADDRESS DPOST=EMT!106 ;DEPOSIT PDP10 MEMORY ;.WORD PDP10-ADDRESS ;.WORD ADDRESS OF 3-WORD DATA BLOCK D10MON=EMT!111 ;DEPOSIT PDP10 MEMORY, -1 ;.WORD PDP10-ADDRESS $PMSG=EMT!25 ;PRINT MESSAGE ON TTY ;.WORD ADDRESS OF ASCIZ MESSAGE $CNTLC=100004 ;JUMP HERE TO "CONTROL C" BACK TO KLDCP ;WHEN KLDCP IS IDLE, AND IN "ITS MODE", IT DOES JSR PC,3000 ;WHICH CALLS IOELEVEN'S MAIN PROGRAM. RETURN WITH "C" SET ;TO READ AND EXECUTE ONE KLDCP COMMAND LINE. RETURN WITH "C" ;CLEAR TO PRINT KL10 HALTED OR CLOCK ERROR STOP MESSAGE. ;LOCATIONS 3004, 3006 MUST CONTAIN .RAD50/IOELEV/ ;IOELEV WILL RUN ON KLDCP'S STACK. ;.IFNZ DTE20P ;INFORMATION ABOUT THE DTE20. ;EXCEPT FOR BYTE TRANSFER, WE USE THE TIME-TESTED SUBROUTINES PROVIDED BY KLDCP. ;THE INTERRUPT VECTOR IS AT 774, BUT WE CAN'T USE IT BECAUSE WOULD HAVE ;TO COORDINATE THINGS WITH KLDCP, WHICH IS OBVIOUSLY IMPOSSIBLE. DLYCNT=174400 ;2.6-2.7 UNIBUS ADDRESS EXTENSION FOR BYTE TRANSFER DMA ;1.1-2.5 14-BIT 2'S COMPLEMENT OF NUMBER OF HALF-MICROSECONDS ; TO DELAY BETWEEN PI0 INTERRUPTS IN BYTE TRANSFER TO10AD=174420 ;ADDRESS (WORD OR BYTE) OF TO-10 BYTE TRANSFER DATA TO10BC=174414 ;1.1-2.3 NEGATIVE BYTE COUNT, 2.7 LAST XFER ;NORMALLY SET BY 10 WITH DATAO DTE, ;TO10 XFER STARTS WHEN BOTH TO10AD AND TO10BC HAVE BEEN LOADED TO11AD=174422 ;ADDRESS (WORD OR BYTE) OF TO-11 BYTE TRANSFER DATA TO11BC=174416 ;1.1-2.3 NEGATIVE BYTE COUNT FOR TO-11 BYTE TRANSFER ;2.5=1 => TO-11 TRANSFER IS 8-BIT BYTES, =0 => 16-BIT WORDS ;2.6=1 => "ASCIZ" MODE (WHICH WE DON'T USE, OF COURSE) ;2.7=1 => LAST XFER, UPON COMPLETION INTERRUPT BOTH 10 AND 11 ; =0 => ONLY INTERRUPT 11. 11 CAN CHANGE TO11AD, TO11BC, CONTINUE. ;TO11 XFER STARTS WHEN BOTH TO11AD AND TO11BC HAVE BEEN LOADED ;THE TRANSFER HAPPENS USING DMA (NPR) IN 11, PI LEVEL 0 IN 10. STATUS=174434 ;DTE20 STATUS REGISTER ;READS: %STDNI==100000 ;2.7 TO10 XFER DONE WITHOUT ERROR %STERI==20000 ;2.5 TO10 XFER ABORTED BY ERROR ;2.4 DATA OUT OF DTE RAM IS ALL ZERO (MAINT) %STINV==4000 ;2.3 PDP10 IS INTERRUPTING PDP11 ;2.2 DEPOST OR EXAMINE WORD ONE (MAINT) ;2.1 PDP11 MEMORY PARITY ERROR IN TO10 XFER ;1.9 PDP11 IS INTERRUPTING PDP10 %STDNO==200 ;1.8 TO11 XFER DONE WITHOUT ERROR ;1.7 E BUFFER SELECT (MAINT) ;1.6 TO11 XFER STOPPED DUE TO ZERO BYTE (IN ASCIZ MODE) ;1.5 TO11 XFER OR PDP10 EXAMINE ENCOUNTERED EBUS PARITY ERROR ;1.4 1 => RESTRICTED MODE ;1.3 0 => EXAMINE/DEPOSIT IN PROGRESS, 1 => DONE %STERO==2 ;1.2 TO11 XFER ABORTED BY ERROR ;1.1 1 => DTE ENABLED TO INTERRUPT PDP11 ;WRITES: %STCLI==51000 ;2.6+2.4+2.1 CLEAR TO10 XFER DONE AND ERROR FLAGS %STUNV==2000 ;2.2 CLEAR PDP10 INTERRUPTING PDP11 %STINX==400 ;1.9 SET PDP11 INTERRUPTING PDP10 %STCLO==121 ;1.7+1.5+1.1 CLEAR TO11 XFER DONE AND ERROR FLAGS ;1.6 ENABLE INTERRUPTS ;1.4 DISABLE INTERRUPTS DIAG1=174430 ;DIAGNOSTIC WORD 1, INCLUDES FLAGS %D1ERR==4000 ;2.3 KL10 CLOCK ERROR STOP %D1RUN==2000 ;2.2 KL10 RUN INDICATOR (1 IF 11 WANTS 10 TO RUN) %D1HLT==1000 ;2.1 KL10 HALT INDICATOR (1 IF 10 DOES A JRST 4) DIAG3=174436 ;DIAGNOSTIC WORD 3, INCLUDES FLAGS %D3BYT==1 ;1.1 WRITING 0 SETS TO10 XFER IN WORD MODE, 1 BYTE MODE ;THERE'S NOTHING ELSE OF THE SLIGHTEST USE IN THIS REGISTER, ;SO IT'S OK TO WRITE IT AT ANY TIME. .ENDC ;DTE20P .SBTTL LOW CORE .IFZ DTE20P ;IF USING DTE20, THESE ARE SET UP BY KLDCP .=4 TRAP4 340 TRAP10 340 ; TRAP14 ;SET UP BY 11DDT ; 340 .=20 TRAP10 ;IOT 340 PWRFAL 340 TRAP10 ;EMT 340 TRAP10 ;TRAP 340 .ENDC ;DTE20P ;CHAOS NET INTERRUPT VECTORS ARE UNFORTUNATELY NOT IN A REASONABLE ARRAY .IFGE CHAOSP-1 .=270 .WORD CHS0BK,5_5 ;274 IS INTERVAL TIMER .ENDC ;CHAOSP-1 .IFGE CHAOSP-2 .=230 .WORD CHS1BK,5_5 ;234 IS INTERVAL TIMER .ENDC ;CHAOSP-2 .IFGE CHAOSP-3 .=240 .WORD CHS2BK,5_5 ;244 IS INTERVAL TIMER .ENDC ;CHAOSP-3 .IFGE CHAOSP-4 .ERROR WHERE DOES THE FOURTH CHAOSNET INTERRUPT VECTOR GO? .ENDC ;CHAOSP-4 .IFNZ ETHERP .=400 ETHOBK 5_5 ETHIBK 5_5 ETHOBK ;COLLISION 5_5 .ENDC ;ETHERP .IFNZ T300P .=254 DSKBRK 240 ;BR5 .ENDC ;T300P .=300 .REPT NDMS ;DM11s go in floating vectors CONC DM,\.RPCNT+1,BRK 240 ;INTERRUPTS ON BR4 BUT WE MASK TO BR5 ANYWAY .ENDR ;NDMS .IFNZ NDLS .=60 DL1IBK ;FIRST DL11 LINE IS PDP11'S CONSOLE TTY, DIFFERENT ADDRESS 240 ;AGAIN INTERRUPTS ON BR4 BUT MASK TO BR5 SO CAN USE DH11 ROUTINES W/O FEAR DL1OBK 240 .ENDC ;NDLS .=310 .REPT NDLS-1 ;DL11S AFTER THE FIRST ARE IN FLOATING VECTORS CONC DL,\.RPCNT+2,IBK 240 CONC DL,\.RPCNT+2,OBK 240 .ENDR .=DHIBAS ;DON'T RELY ON RANDOM FLOATING VECTOR TO ;COME OUT RIGHT, E.G. IF THERE IS A DL11 ;THERE WHICH WE AREN'T USING. .REPT NDHS ;DH11S ARE IN FLOATING VECTOR AFTER DL11[E]S CONC DH,\.RPCNT+1,IBK ;DH11 #n RECEIVE 240 CONC DH,\.RPCNT+1,OBK ;DH11 #n TRANSMIT & ERROR 240 .ENDR ;NDHS .=100 CLKBRK ;KW11-L 60-CYCLE CLOCK 300 ;ON BR6 .IFNZ GOULDP .=174 GLPBRK 300 ;BR5 BUT NEED TO LOCK OUT CLOCK SO MASK 6 .ENDC ;GOULDP .IFG NMPTYS .=56 MPXENB::0 ;NONZERO TO ENABLE MULTISCHLUNKER .ENDC .IFZ DTE20P ;IF DTE20, KLDCP SUPPLIES THE STACK .=1000 STKBAS:: JMP INIT ;START AT 1000 IS CONVENTIONAL .IFF ;DTE20P .=3000 ;ENTRY VECTOR JMP @#INIT SADR=.-2 ;ARG OF THE JMP@# IS CHANGED AFTER INITIALIZATION .RAD50 /IOELEV/ .ENDC ;DTE20P .SBTTL TEN-11 CHAOSNET COMMUNICATION AREA .IFNZ TEN11P T11BFL==8+<2*PKTMXW> ;BYTE LENGTH OF A PACKET BUFFER ;FIRST 8 BYTES ARE BUFFER-FULL FLAG AND CKSM .IIF NE T11BFL-<*4>, .ERROR T11BFL NOT MULTIPLE OF 4 .IIF NE .-1004, .ERROR CHAOSNET TEN-11 COMMUNICATION AREA NOT AT RIGHT ADDRESS ;THIS AREA IS SHARED WITH THE PDP10 VIA TEN-11 INTERFACE. .WORD "CH,1 ;ERROR CHECK AND VERSION NUMBER T11I10: .WORD 0,0 ;SET NON-ZERO BY 11 TO REINITIALIZE 10 T11I11: .WORD 0,0 ;SET NON-ZERO BY 10 TO REINITIALIZE 11 .WORD T11BFL,NT11BF ;BUFFER SIZE, NUMBER OF BUFFERS .BLKW 8 ;SPARE WORDS T11OBF: .BLKB T11BFL*NT11BF ;TO-10 BUFFERS T11OBE==. ;END OF TO-10 BUFFERS T11IBF: .BLKB T11BFL*NT11BF ;FROM-10 BUFFERS T11IBE==. ;END OF FROM-10 BUFFERS ;THE FIRST 32-BIT WORD OF A BUFFER IS 0 IF IDLE, OR ;NON-ZERO IF BUFFER IS TO BE SENT TO OTHER MACHINE. ;THE SECOND 32-BIT WORD IS THE CHECKSUM, WHICH IS ;COMPUTED BY ADDING ALL THE 32-BIT WORDS, IGNORING OVERFLOW, ; AND LOGICALLY SHIFTING RIGHT ONE BIT AFTER EACH ADD; BITS SHIFTED ; OUT ON THE RIGHT ARE BROUGHT BACK IN ON THE LEFT. ;IF THE NUMBER OF 16-BIT WORDS IS ODD, THE LEFT-OVER ONE BETTER BE 0. .ENDC ;TEN11P .SBTTL CONFIGURATION ; TABLES INDEXED BY H (PER HARDWARE UNIT) .MACRO DHTE AD ;DH11 REGISTER ADDRESS GENERATOR .REPT NDHS +<20*.RPCNT> .ENDR .ENDM .MACRO DLTE AD ;DL11 REGISTER ADDRESS GENERATOR, FIRST IS WIERD .IFNZ NDLS 177560+<&7> .REPT NDLS-1 +<10*.RPCNT> .ENDR .ENDC ;NDLS .ENDM .MACRO DMTE AD ;DM11 register address generator .REPT NDMS +<10*.RPCNT> ;a DM11 eats 8 locations .ENDR .ENDM DMCSR: DMTE 170500 ;first DM11 is at 170500 DMLSR: DMTE 170502 ;selected line status at 170502 DHSCR: DHTE DHCBAS ;SYSTEM CONTROL REGISTER ;1.1-1.4 LINE NUMBER ;1.5-1.6 MEMORY ADDRESS EXTENSION DHRENB==100 ;1.7 RECEIVER INTERRUPT ENABLE ;1.8 RECEIVER INTERRUPT ;1.9 CLEAR NXM FLAG ;2.1 MAINTENANCE MODE DHSNXM==2000 ;2.2 NXM FLAG (GENERATES XMT INTERRUPT) ;2.3 MASTER CLEAR DHSENB==10000 ;2.4 STORAGE SILO FULL INTERRUPT ENABLE DHTENB==20000 ;2.5 TRANSMITTER & NXM INTERRUPT ENABLE ;2.6 STOARGE FULL INTERRUPT DHTDON==100000 ;2.7 TRANSMITTER DONE INTERRUPT DLKS==DHSCR DLTE 175610 ;KEYBOARD STATUS REGISTER ;1.1 PAPER TAPE READER ENABLE (WO) ;1.2 DATA TERMINAL READY (RW) ;1.3 REQUEST TO SEND (RW) ;1.4 SECONDARY TRANSMIT DATA [OR MAKE BUSY] (RW) ;1.5 UNUSED ;1.6 DATASET INTERRUPT ENABLE (RW) ;1.7 RECEIVE INTERRUPT ENABLE (RW) ;1.8 RECEIVE DATA READY (RO) ;1.9 UNUSED ;2.1 UNUSED ;2.2 SECONDARY RECEIVE DATA (RO) ;2.3 RECEIVE ACTIVE (RO) ;2.4 CARRIER DETECT (RO) ;2.5 CLEAR TO SEND (RO) ;2.6 RING INDICATOR (RO) ;2.7 DATASET STATUS CHANGE (RO) DHNRC: DHTE DHCBAS+2 ;NEXT RECEIVED CHARACTER ;1.1-1.8 THE CHARACTER ;1.9-2.3 LINE NUMBER %DXPAR==10000 ;2.4 CHAR HAS WRONG PARITY %DXBRK==20000 ;2.5 FRAMING ERROR (BREAK) %DXOVR==40000 ;2.6 OVERRUN, PREVIOUS CHARS LOST ;2.7 1 => THIS WORD VALID DLKB==DHNRC DLTE 175612 ;KEYBOARD INPUT REGISTER ;1.1-1.8 RECEIVED DATA ;2.4 PARITY ERROR (RO) ;2.5 FRAMING ERROR (RO) ;2.6 OVERRUN (RO) ;2.7 OR OF ERROR BITS (RO) DHLPR: DHTE DHCBAS+4 ;LINE PARAMETER REGISTER ;1.1-1.2 CHARACTER LENGTH 0=5, 1=6, 2=7, 3=8 (PARITY BIT EXTRA) ;1.3 1 => EXTRA STOP BIT ;1.5 ENABLE PARITY ;1.6 0 -> EVEN PARITY, 1 => ODD ;1.7-2.1 RECEIVER SPEED ; 0 OFF, 1 50, 2 75, 3 110, 4 134.5, 5 150, 6 200, 7 300 ; 10 600, 11 1200, 12 1800, 13 2400, 14 4800, 15 9600, 16 A, 17 B ;2.2-2.5 TRANSMITTER SPEED, SAME CODES AS RECEIVER ;2.6 HALF DUPLEX ;2.7 ECHOPLEX DHCA: DHTE DHCBAS+6 ;CURRENT ADDRESS DLCA==DHCA .IREPT NDLS,0 DHBC: DHTE DHCBAS+10 ;BYTE COUNT (MINUS) DLBC==DHBC .IREPT NDLS,0 ;POSITIVE FOR DLS DHBAR: DHTE DHCBAS+12 ;BUFFER ACTIVE REGISTER ;BIT = 1 IF XMT ACTIVE ON CORRESP LINE, NUMBERED RIGHT TO LEFT DLPS==DHBAR DLTE 175614 ;PRINTER STATUS ;1.1 SEND BREAK (RW) ;1.3 LOOP BACK (RW) ;1.6 INTERRUPT ENABLE (RW) ;1.7 TRANSMITTER READY (RO) DHBCR: DHTE DHCBAS+14 ;BREAK CONTROL REGISTER ;BIT = 1 => SEND BREAK ON CORRESP LINE, NUMBERED RIGHT TO LEFT DLPB==DHBCR DLTE 175616 ;PRINTER BUFFER ;1.1-1.8 DATA TO TRANSMIT DHSSR: DHTE DHCBAS+16 ;SILO STATUS REGISTER ;1.1-1.6 SILO ALARM LEVEL ;1.7-1.8 READ EXTENDED ADDRESS (R.O.) ;1.9-2.5 SILO FILL LEVEL (R.O.) ;2.7 MAINTENANCE PATTERN (W.O.) DHOAC: .IREPT NDHS,0 ;BIT ON IF SOFTWARE THINKS LINE'S TRANSMITTER IS ACTIVE DLOAC==DHOAC .IREPT NDLS,0 ;NON-ZERO IF LINE'S TRANSMITTER IS ACTIVE DHTYNO: .IREPT NDHS, NFDHTY+<32.*.RPCNT> ;TTY INDEX OF FIRST LINE ON THIS DH11 DLTYNO==DHTYNO .IIF NZ CTYP,0 ;TTY INDEX OF LINE ON THIS DL11 .IREPT NDLS-CTYP,NFDLTY+<2*.RPCNT> STROUT: .IREPT NDHS, STRDH ;OUTPUT-START ROUTINES .IREPT NDLS, STRDL .IIF NZ NMPTYS, STRMPK .BLKB NFTTY ;AVOID LABEL OVERLAPPAGE ;TABLES INDEXED BY I (PER LINE) T HDWR: ;HARDWARE UNIT INDEX, GOES IN H .IIF NZ CTYP, NFDLHX .REPT NDHS ZZ==.RPCNT*2 .REPT 16. ZZ ;16 LINES ON EACH DH-11 .ENDR .ENDR .=.-<2*NDHUN> .IREPT NDLS-CTYP,NFDLHX+<2*.RPCNT>+<2*CTYP> .IREPT NMPTYS, MPKHWR ;MULTIPLEXOR-KLUDGE TTYS T DHLSEL: ;DH11 LINE SELECT WORDS .IIF NZ CTYP, 0 ;NONE FOR CTY .REPT NDHS .REPT 16. DHTENB+DHRENB+.RPCNT .ENDR .ENDR T DHLBIT: ;BIT CORRESPONDING TO THIS LINE IN DHBAR, ETC. .IIF NZ CTYP, 0 ;NONE FOR CTY .REPT NDHS .REPT 16. 1_.RPCNT .ENDR .ENDR T BUFPNT: ;BUFFER POINTERS .IREPT NCT, BUFFRS+<.RPCNT*MAXBSZ> T BUFSIZ: ;BUFFER SIZES (I.E. AMOUNT TO USE AT CURRENT SPEED) .REPT NCT 0 ;SET DURING INITIALIZATION .ENDR T NRMIPC: ;NORMAL INPUT CHARACTER PROCESSING ROUTINES .IIF NZ CTYP, RCV ;CTY NORMAL INPUT .REPT 16.*NDHS DHNRMI ;DH11 TTY NORMAL INPUT .ENDR .=.-<2*NDHUN> .IREPT NDLS-CTYP,RCV ;DL11 NORMAL INPUT .IREPT NMPTYS, RCV ;NORMAL INPUT FOR TTYS ON MULTIPLEXOR-KLUDGE .IIF NE .-NRMIPC-NLTTY, .ERROR BARF AT NRMIPC .IFNZ NMPTYS .=NRMIPC+MPXIDX MPXINP ;INPUT FROM THE MULTIPLEXED LINE IS SPECIAL .=NRMIPC+NLTTY .ENDC T TTYIPC: ;CURRENT INPUT CHAR PROCESSING ROUTINES .BLKW NCT ;SET UP AT INIT TIME .IIF NE .-TTYIPC-NLTTY, .ERROR BARF AT TTYIPC T AUTOSP: ;IF NON-ZERO, LINE GOES INTO AUTOSPEED WHEN DIALED UP .REPT NCT ;IF MINUS ALSO WHEN BREAK SEEN ZZ===. ASPIRP ^\ .IIF EQ .RPCNT+-N,+1 ;THIS LINE AUTOSPEED ON DIALUP .IIF EQ .RPCNT++N,-1 ;ALSO ON BREAK \ .IIF EQ .-ZZ, 0 ;THIS LINE NOT AUTOSPEED .ENDR .IIF NE .-AUTOSP-NLTTY, .ERROR BARF AT AUTOSP .IFM MC M2LMAP: ;MAP FROM DM11-BB CHANNEL NUMBERS TO TTY INDICES 2*1 ;0 T01 0 ;1 NONE 0 ;2 NONE 2*4 ;3 T04 2*5 ;4 T05 2*6 ;5 T06 2*7 ;6 T07 2*10 ;7 T10 2*11 ;10 T11 2*12 ;11 T12 2*13 ;12 T13 2*14 ;13 T14 2*15 ;14 T15 2*16 ;15 T16 2*17 ;16 T17 0 ;17 NONE 2*21 ;20 T21 2*22 ;21 T22 2*23 ;22 T23 2*24 ;23 T24 2*25 ;24 T25 2*26 ;25 T26 2*27 ;26 T27 2*30 ;27 T30 2*31 ;30 T31 2*32 ;31 T32 2*33 ;32 T33 2*34 ;33 T34 2*35 ;34 T35 2*36 ;35 T36 2*37 ;36 T37 2*40 ;37 T40 .ENDC ;MC .IIF NE NDMS, .IIF NE .-M2LMAP-<40*NDMS>, .ERROR Too few M2LMAP entries for DM11s. .IFNZ NDMS T DIALED: ;0 IF LINE NOT DIALED UP (OR NO MODEM CONTROL ON THIS LINE) .REPT NCT ;+ IF DIALED UP (CLEAR TO SEND IS ON) 0 ;- IF CLEAR TO SEND DROPPED, INC EACH TICK, REACHES 0 => HUNG UP .ENDR .ENDC ;NDMS T TTYHNG: ;DIALUP/HANGUP STATUS WAITING TO BE SENT TO 10 (0 IF NONE) .REPT NCT 0 .ENDR T TYPING: ;POSITIVE IF LINE IS TYPING OUT FOR 10 .REPT NCT ; WHICH MEANS -10 SHOULD BE INFORMED WHEN TYPEOUT IS FINISHED 0 ;0 FOR NO -10 TYPEOUT, MINUS TO SEND AFTER TYPEOUT .ENDR ;MISC VARIABLES DLXOFF: -1 ;NON-ZERO IF DL10 PORT TURNED OFF BY 10 NO.ITS: -1 ;NON-ZERO IF HAVEN'T ESTABLISHED COMMUNICATION WITH ITS YET VERSN: .BYTE NFTTY/2,NCT ;I/O VERSION NUMBER DMINI: 0 ;NON-ZERO => MODEM SCANNER JUST TURNED ON, GETTING INITIAL STS WAKE: 0 ;CLOCK INTERRUPT WAKE UP MAIN PROGRAM FLAG HNGSIG: 0 ;NUMBER OF NON-ZERO TTYHNG WORDS 10RQ: 0 ;LIGHT HACKS LITHSE: 7 .IFNZ DTE20P CLKENB: 0 ;KL10 WANTS 11 TO RELAY CLOCK INTERRUPTS KLDCPF: 0 ;NON-ZERO => USER WANTS TO GIVE A COMMAND TO KLDCP DDTMOD: 0 ;NON-ZERO => DDT MODE TTY INPUT DDTCHR: -1 ;NON-NEGATIVE => CHAR TYPED FOR DDT CURSWR: 52525 ;LAST SWITCHES SENT TO -10 OUTCMD: 0 ;0 IF OUTPUT TRANSFER IDLE ;ELSE CURRENT COMMAND / 400 OUTSVI: -1 ;LINE# OF CURRENT OUTPUT TRANSFER OUTSVC: -1 ;#BYTES OF CURRENT OUTPUT TRANSFER INPCMD: 0 ;0 IF INPUT TRANSFER IDLE ;ELSE CURRENT COMMAND / 400 INPSVI: -1 ;LINE# OF CURRENT INPUT TRANSFER INPSVC: -1 ;#BYTES OF CURRENT INPUT TRANSFER .ENDC ;DTE20P .IFNZ NMPTYS MPXOAC: 0 ;0 IDLE, -1 SENDING HEADER, 1 SENDING DATA MPXOLN: 0 ;2 x MPXK# OUTPUTTING FOR MPXSEL: NFMPTY ;TTY INDEX SELECTED FOR MPX INPUT MPXPNT: .IREPT NMPTYS,0 ;POINTER TO CRUFT TO SEND TO EACH MPXED LINE MPXNBT: .IREPT NMPTYS,0 ;# BYTES TO SEND, 0 IF IDLE MPXHED: .BYTE 0,0 ;MPX OUTPUT HEADER: 200+MPXK#, BYTE COUNT .ENDC ;NMPTYS .SBTTL CHAOSNET VARIABLES & TABLES .IFNZ CHAOSP NSUBNT==80. ;MAXIMUM CAPACITY 80. SUBNETS .IFNZ DL10P ;DL10 UNSHARED DLCRBN: 0 ;CURRENT RECEIVE (11 to 10) BUFFER (0 OR 2) DLCNXT: .WORD 2,0 ;FOR SWITCHING BUFFERS DLCIBF: .BLKW PKMAX ;DL10 INPUT BUFFER .ENDC ;DL10P .IFNZ TEN11P ;TEN11 UNSHARED T11OBP: T11OBF ;NEXT BUFFER TO 10 T11IBP: T11IBF ;NEXT BUFFER FROM 10 T11IBA: 0 ;NON-ZERO MEANS INPUT BUFFER ACTIVE, T11IBP NEEDS ADVANCING ;THIS IS SEPARATE FROM CHISTS+CHXT11 FOR GOOD REASONS T11CKE: 0 ;COUNT OF TEN-11 CHECKSUM ERRORS T11TIM: 0 ;TIMEOUT ON TRANSMISSION OF PACKET TO 10 .ENDC ;TEN11P .IFNZ ETHERP ETHSBN==2 ;SUBNET WHICH IS THE ETHERNET .SEE ETHHSN ;MY HOST NUMBER BYTE (DEFINED IN MACHINE CONFIGURATION AREA) ETHMXH==15.-1 ;MAXIMUM NUMBER OF HOPS (-1 => BUG IN XEROX PROGRAMS) ETHIBF: .BLKW PKTMXW+1 ;INPUT FROM ETHERNET BUFFERED HERE (+1 HARDWARE BUG?) ETHHDW==PKHDW-2 ;ALLOW FOR OVERLAP OF CHAOSNET HEADER AND 2-WORD ETHERNET HEADER ;THIS IS THE OFFSET (IN WORDS) WHERE THE ETHERNET PACKET STARTS ;HERE IS A PACKET USED TO BUILD THE ETHERNET BROADCAST GATEWAY INFO. WHAT A CROCK. EGTBUF: .BLKW PKHDW ;SPACE FOR CHAOSNET HEADER EGTPLN: 0 ;PUP LENGTH 201 ;PUP TYPE 201 EGTPID: .WORD 0,0 ;PUP IDENTIFIER 0 ;DESTINATION (BROADCAST) .WORD 0,2 ;DEST SOCKET 2 EGTSRC: .BYTE ETHHSN,ETHSBN ;SOURCE (ME) .WORD 0,2 ;SOURCE SOCKET 2 EGTSBN: ;; FOR EACH SUBNET, .BYTE GATE-NET, TARGET-NET, HOP-COUNT, GATE-HOST .BLKW 2*NSUBNT 0 ;PUP CHECKSUM .IF DF NDVRBF DVRHST: 0 ;ZERO IF IDLE, OR FOREIGN HOST USING DVRIDX: 0 ;FOREIGN INDEX DVRLIX: 0 ;LOCAL INDEX (AOS EACH TIME) DVRTIM: 0 ;COUNTS UP TO IDLE THE FOREIGN HOST DVRRTR: 0 ;COUNTS UP FOR RETRANSMISSION DVRBFL==2*+1> ;NUMBER OF BYTES IN A DOVER BUFFER (HOLDS PUP IN CHAOSNET PACKET) DVRBUF: .BLKB DVRBFL*NDVRBF ;RING OF BUFFERS HERE DVRBF2: .BLKW PKHDW+2 ;BUFFER FOR SENDING STS/OPN/CLS BACK (ALSO END OF RING) DVRBFP: DVRBUF ;POINTER TO NEXT BUFFER TO GO OUT TO DOVER DVRMSK: 0 ;MASK OF WHICH BUFFERS CONTAIN PACKETS (MSB = DVRBFP PKT) .IIF GT NDVRBF-16., .ERROR NDVRBF MAXIMUM OF 16. ALLOWED DVRPKP: 0 ;IF NON-ZERO, POINTER TO SPECIAL PACKET TO SEND DVRID: 0 ;ID FOR NEXT PACKET EXPECTED BY DOVER, THIS PACKET IS OR ; WILL BE IN THE BUFFER DVRBFP POINTS AT DVROFS: 0 ;ID OFFSET, SUBTRACT FROM CHAOS ID TO GET PUP ID NDVRFK: 0 ;*** TEMPORARY KLUDGE *** .ENDC ;NDVRBF .ENDC ;ETHERP PULSAR: 0 ;COUNTS DOWN TO 0 THEN TRIGGERS TRANSMISSION OF A "TEST MESSAGE" PULSON: FTPULS ;IF THIS IS NON-ZERO, FEATURE IS ENABLED, VALUE IS TICKS BETWEEN PULSES USECBL: 0 ;IF NON-ZERO, 10 TALKING TO SELF STILL GOES THROUGH CABLE NCHX==DL10P+TEN11P+CHAOSP+<2*ETHERP> ;NUMBER OF ENTRIES IN SOURCE AND SINK TABLES .IIF DF NDVRBF, NCHX==NCHX+1 ;METERS ETC. .IFNZ FTGARB CHSGBF: .BLKW PKMAX ;HOLDS LAST PACKET THAT CAME IN WITH A CHECKSUM ERROR CHSGBH: 0 ;UNIBUS ADDRESS OF INTERFACE THAT ABOVE CAME IN ON CHSGBS: 0 ;STATUS REGISTER THAT GOES WITH ABOVE CHSGBC: 0 ;BIT COUNT THAT GOES WITH ABOVE .ENDC ;FTGARB ;FOLLOWING HAVE SEPARATE ENTRIES FOR EACH CABLE NPKSGB: .IREPT CHAOSP+ETHERP,0 ;COUNTS THE NUMBER OF PACKETS RECEIVED WITH CHECKSUM ERRORS HPKSGB: .IREPT CHAOSP+ETHERP,0 ;HIGH-ORDER WORD OF COUNTER NPKSRL: .IREPT CHAOSP+ETHERP,0 ;COUNTS THE NUMBER OF PACKETS RAM LOST, ; I.E. DIDN'T COME IN WITH A CHECKSUM ERROR BUT AFTER ; READING IT OUT HAD ONE. EITHER THE PACKET WAS THE ; WRONG LENGTH, OR THE RAM IS LOSING, OR HARDWARE ; CLOBBERAGE. FOR ETHERNET IS PUP CKSM ERR COUNT ;THIS WORD ALSO IS WHERE BIT COUNT ERRORS WOULD END UP HPKSRL: .IREPT CHAOSP+ETHERP,0 ;HIGH-ORDER WORD OF COUNTER CHSRLH: 0 ;UNIBUS ADDRESS OF INTERFACE THAT ABOVE LAST HAPPENED ON. CHSRLC: 0 ;RESIDUAL BIT COUNT FOR ABOVE NPKSLS: .IREPT CHAOSP,0 ;NUMBER OF PACKETS LOST ACCORDING TO LOSS COUNT IN HARDWARE HPKSLS: .IREPT CHAOSP,0 ;HIGH-ORDER WORD OF COUNTER NPKSAB: .IREPT CHAOSP+ETHERP,0 ;NUMBER OF TRANSMISSIONS ABORTED (BY COLLISION OR RECEIVE-BUSY) HPKSAB: .IREPT CHAOSP+ETHERP,0 ;HIGH-ORDER WORD OF COUNTER NPKSI: .IREPT NCHX,0 ;TOTAL NUMBER OF PACKETS IN ON EACH SOURCE HPKSI: .IREPT NCHX,0 ;HIGH-ORDER WORD OF COUNTER NPKSO: .IREPT NCHX,0 ;TOTAL NUMBER OF PACKETS OUT ON EACH SINK HPKSO: .IREPT NCHX,0 ;HIGH-ORDER WORD OF COUNTER NPKSIG: 0 ;NUMBER OF PACKETS IGNORED AT CHIFLS NPKSBD: .IREPT NCHX,0 ;NUMBER OF PACKETS BAD AT CHSIHB HPKSBD: .IREPT NCHX,0 ;HIGH-ORDER WORD OF COUNTER NPKSRF: 0 ;NUMBER OF PACKETS FOR WHICH ROUTING FAILED RFSBNT: -1 ;2* SUBNET# OF LAST ROUTING FAILURE ;"INTERFACE ADDRESSES" ; A NEGATIVE INTERFACE ADDRESS IS THE UNIBUS ADDRESS OF A CHAOS INTERFACE. ; A ZERO INTERFACE ADDRESS MEANS THE DL10 ; A POSITIVE INTERFACE ADDRESS MEANS THE TEN-11, VALUE BETTER BE OCTAL 1011. CHSIBF: .BLKW PKMAX*CHAOSP ;INPUT BUFFER FOR PACKETS IN FROM CHAOS HDWR ;THIS IS WHAT IS SENT BACK IN RESPONSE TO RFC TO "STATUS". ;FOR NOW, JUST THE NAME OF THE MACHINE. HSTNAM: .ENDC ;CHAOSP ;FUCK A DOG, PALX! .IFM MC-DL .ASCII \MC-IO/11\ .ENDC .IFM AI .ASCII \AI-CHAOS-11\ .ENDC .IFNZ CHAOSP ;FUCK A DOG, PALX! .IIF GE .-HSTNAM-32., .ERROR HSTNAM TOO LONG .IREPT 32.-<.-HSTNAM>, .BYTE 0 ;PAD ON THE RIGHT WITH 0'S ;CHAOSNET INPUT SOURCE AND OUTPUT SINK TABLES ;NOTE WELL, THE CODE RELIES ON THE ORDER OF THESE INDICES .IIF NZ DL10P, CHXDLC==0 ;DL10 INDEX .IIF NZ TEN11P, CHXT11==2*DL10P ;TEN11 INDEX CHXCHS==2* ;FIRST CHAOS INDEX .IIF NZ ETHERP, CHXETH==CHXCHS+<2*CHAOSP> ;ETHERNET INDEX .IIF NZ ETHERP, CHXEGT==CHXETH+2 ;ETHERNET GATEWAY-INFO-BROADCAST KLUDGE INDEX .IIF DF NDVRBF, CHXDVR==CHXEGT+2 ;DOVER PROTOCOL TRANSLATOR .MACRO CHXCHK TAG .IIF NE .-TAG-NCHX-NCHX, .ERROR TAG WRONG LENGTH TABLE .ENDM CHXCHK ;CHAOSNET INPUT SOURCE TABLES CHIBFP: ;BUFFER POINTER .IIF NZ DL10P, DLCIBF ;DL10 INPUT BUFFER .IIF NZ TEN11P, 0 ;CURRENT TEN11 INPUT BUFFER (SET FROM T11IBP+8) .IREPT CHAOSP, CHSIBF+ ;CHAOS INPUT BUFFER .IIF NZ ETHERP, ETHIBF ;ETHERNET .IALSO EGTBUF ;.. .IIF DF NDVRBF, 0 ;CURRENT DOVER BUFFER, COULD BE CHAOS OR PUP CHXCHK CHIBFP CHIHDL: .IREPT NCHX, 0 ;LENGTH OF HEADER IN WORDS, PACKET CURRENTLY IN BFR CHISTS: .IREPT NCHX, 0 ;STATUS (0 IDLE, +1 HAS INPUT, -1 BEING OUTPUT) CHILNG: .IREPT NCHX, 0 ;LENGTH OF CONTAINED PACKET IN WORDS CHIOUX: .IREPT NCHX, 1 ;DESTINATION OUTPUT SINK INDEX (-1 IF DIRECTED TO PDP11 ITSELF) CHICBA: .IREPT NCHX, 0 ;DESTINATION CABLE ADDRESS CHIRFL: ;ADDRESS OF REFILL ROUTINE .IIF NZ DL10P, DLCRFL .IIF NZ TEN11P, T11RFL .IREPT CHAOSP, CHSRFL .IIF NZ ETHERP, ETHRFL ;ETHERNET .IALSO CPOPJ ;.. .IIF DF NDVRBF, DVRRFL CHXCHK CHIRFL CHIHWR: ;POINTER TO HARDWARE .IIF NZ DL10P, 1 ;NOT USED .IIF NZ TEN11P, 3 ;NOT USED .IREPT CHAOSP, CAICSR+<400*.RPCNT> ;QUAD-CHAOS INTERFACES HAVE TO BE 200 APART .IIF NZ ETHERP, 164200 ;AND WE MAKE IT 400 BECAUSE ETHERNET GETS IN WAY .IALSO 5 ;NOT USED .IIF DF NDVRBF, 7 ;NOT USED ;CHAOSNET OUTPUT SINK TABLES CHOHWR==CHIHWR ;POINTER TO HARDWARE CHOSTS: .IREPT NCHX, 0 ;STATUS (0 IDLE, +1 TRANSMITTING, -1 RETRANSMITTING ; AFTER TRANS ABORT, +2 DELAYING AFTER TRANSMIT ABORT BEFORE RETRANSM) CHOINX: .IREPT NCHX, 1 ;CURRENTLY-ACTIVE CHIxxx INDEX CHOXMT: ;START TRANSMISSION ROUTINE .IIF NZ DL10P, DLCXMT .IIF NZ TEN11P, T11XMT .IREPT CHAOSP, CHSXMT .IIF NZ ETHERP, ETHXMT ;ETHERNET .IALSO 1 ;NOT USED (CHXEGT) .IIF DF NDVRBF, DVRPKT ;DOVER CHXCHK CHOXMT CHXSBN: ;SUBNET NUMBER +400 FOR STATUS SERVER .IIF NZ DL10P, DLCADR/400+400 .IIF NZ TEN11P, T11ADR/400+400 .REPT CHAOSP CONC CHAD,\.RPCNT,/400+400 .ENDR ;CHAOSP .IIF NZ ETHERP, ETHSBN+400 ;ETHERNET .IALSO 776 ;NOT REAL (ETHERNET GATEWAY) .IIF DF NDVRBF, 777 ;NOT REAL (DOVER) CHXCHK CHXSBN CHXRTF: .IREPT NCHX, 0 ;NON-ZERO MEANS BROADCAST ROUTING INFO TO THIS GUY .IFNZ CHSBTB CHSIDL: .IREPT NCHX, 0 ;NUMBER OF TICKS WAITING FOR TRANSMIT-DONE CHSRST: .IREPT NCHX, 0 ;NUMBER OF TIMES HAD TO RESET HUNG INTERFACE .ENDC ;CHSBTB ;;; SUBNET/ROUTING TABLES ;INDEX BY TWICE SUBNET NUMBER SBNTYP: .IREPT NSUBNT, 0 ;TYPE OF CONNECTION TO THIS SUBNET: ; 0 VIA GATEWAY, WITH AUTOMATIC ROUTING ; -1 VIA GATEWAY, PATCHED IN BY HUMAN, DON'T CHANGE ; 1 HARDWARE CONNECTION SBNADR: ;ADDRESS OF CONNECTION TO THIS SUBNET ;NETWORK ADDRESS IF SBNTYP NEGATIVE OR ZERO ;INDEX IN SOURCE/SINK TABLES IF SBNTYP GREATER THAN ZERO 0 ;0 USED FOR UNKNOWN SUBNETS. WHEN IN DOUBT, BROADCAST. 0 ;1 9TH FLOOR CABLE 0 ;2 (NOT CURRENTLY USED) 440 ;3 MC, ASSUME VIA MC-IO-11 426 ;4 AI, ASSUME VIA AI-CHAOS-11 .IREPT NSUBNT-5, 0 ; WHEN IN DOUBT, BROADCAST SBNCST: .IREPT NSUBNT, 1000 ;COST OF ROUTING VIA CURRENT GATEWAY, SEE CHAORD ;NOW FILL IN TABLES FOR HARDWARE CONNECTIONS THAT EXIST ON THIS MACHINE ;INCLUDING TRANSFINITE HAIR FOR ETHERNET GATEWAY INFO PACKET ZZ==. .IFNZ DL10P DLCSBN==DLCADR/400 ;SUBNET PDP10 ON OTHER END OF DL10 IS ON .=SBNTYP+ 1 .=SBNADR+ CHXDLC .=SBNCST+ 10. ;DIRECT 10/11 CONNECTION COSTS 10. .ENDC ;DL10P .IFNZ TEN11P T11SBN==T11ADR/400 ;SUBNET PDP10 ON OTHER END OF TEN11 IS ON .=SBNTYP+ 1 .=SBNADR+ CHXT11 .=SBNCST+ 10. ;DIRECT 10/11 CONNECTION COSTS 10. .ENDC ;TEN11P .ENDC ;CHAOSP .IFM MC-DL CBLCST=11. ;CABLE CONNECTION COSTS 11. .ENDC .IFM AI CBLCST=22. ;AI COSTS MORE 'CAUSE IT'S SICK .ENDC .IFNZ CHAOSP ;sweet fucking jesus, palx ;HAIR FOR MULTIPLE CABLE INTERFACES .REPT CHAOSP CONC IZZZ==CHAD,\.RPCNT IZZ==*2 .=SBNTYP+IZZ 1 .=SBNADR+IZZ CHXCHS+<.RPCNT*2> .=SBNCST+IZZ CBLCST ;THE CABLE COST .ENDR ;CHAOSP .IFNZ ETHERP .=SBNTYP+ 1 .=SBNADR+ CHXETH .=SBNCST+ 11. .ENDC ;ETHERP .=ZZ ;;; CLOCKS 4SEC: 0 ;4-SECOND CLOCK COUNTER 15SEC: 0 ;15-SECOND CLOCK COUNTER .ENDC ;CHAOSP ;PATCH AREA PAT: PATCH: .BLKW 100 .SBTTL RING BUFFERS .MACRO RING SIZE 99$ ;IN-POINTER 99$ ;OUT-POINTER 0 ;NUMBER OF WORDS IN RING ;MAX NUMBER ALLOWED <2*>+99$ ;MAX ADDRESS ALLOWED 99$ ;MIN ADDRESS ALLOWED 99$: .BLKW ;BUFFER .ENDM RINGIN==0 RINGOT==2 RINGCT==4 RINGSZ==6 RINGTP==10 RINGBT==12 RINGBF==14 ; DEFINE THE RING BUFFERS TYORNG: RING ;OUTPUT-DONE RING, CONTENTS = LINE NUMBER PDP10 STYLE ;HAS TO BE EXTRA BIG BECAUSE THE OUTPUT DONES PUT IN ON ;STARTUP FILL IT UP, THEN SOMETIMES ITS PUTS ONE IN ;BEFORE IT TAKES ANY OUT. TYIRSZ==NCT*20 ;8 CHARS PER TTY (2 WORDS PER CHAR) TYIRNG: RING TYIRSZ ;TTY INPUT RING, FIRST WORD IS CHARACTER, SECOND LINE NUMBER ;MOV #RING,B ;MOV WORD,A ;CALL PUT PUT: CMP RINGCT(B),RINGSZ(B) BLT 1$ BPT ;BLOATED 1$: PUSH C MOV RINGIN(B),C MOV A,(C)+ CMP C,RINGTP(B) BLO 2$ MOV RINGBT(B),C 2$: MOV C,RINGIN(B) POP C INC RINGCT(B) RET ;MOV #RING,B ;CALL GET ;WORD RETURNED IN A ; IT IS AN ERROR TO CALL THIS IF RING IS EMPTY GET: TST RINGCT(B) BGT 1$ BPT ;EMPTY 1$: PUSH C MOV RINGOT(B),C MOV (C)+,A CMP C,RINGTP(B) BLO 2$ MOV RINGBT(B),C 2$: MOV C,RINGOT(B) POP C DEC RINGCT(B) RET CLRING: CLR RINGCT(B) ;CLEAR A RING MOV RINGBT(B),RINGIN(B) MOV RINGBT(B),RINGOT(B) RET .IFNZ DTE20P .SBTTL DTE20 SUBROUTINES ;THE DTE20 MUST NOT BE HACKED AT INTERRUPT LEVEL, BECAUSE KLDCP USES IT TOO. ;THE FOLLOWING THREE LOCATIONS ARE ARGS TO/FROM THE FOLLOWING TWO SUBROUTINES. LH: 0 ;LOW 16 BITS OF LEFT HALF RH: 0 ;LOW 16 BITS OF RIGHT HALF SNB: 0 ;SIGN BIT (0 IF +, NON-0 IF -) ;JSR B,HWEXAM ; .WORD ADDR ;EXAMINE PDP10 LOC, SPLIT INTO HALFWORDS, SET LH, RH, SNB ;RETURNS WITH "Z" SET IF LOCATION HAS POSITIVE SIGN, "Z" CLEAR IF MINUS SIGN HWEXAM: PUSH ;SAVE REGS PUSH <#0,(B)+> ;PUT PDP10 ADDRESS ONTO PDL MOV SP,A ;SET UP POINTER TO ADDRESS EXAM ;EXAMINE LOCATION, SET A TO POINT TO 3-WORD RESULT BUFFER BCS UHUNG ;BRANCH IF UCODE HUNG MOV (A)+,RH ;LOW 16 BITS => RH MOV (A)+,C ;PICK UP MIDDLE 16 BITS MOV (A)+,A ;PICK UP HIGH 4 BITS ROR A ;LSHC ,-2 TO GET PDP10 LH INTO C ROR C ROR A ROR C MOV C,LH BIC #177775,A ;LEAVE SIGN BIT IN 1.2 OF A MOV A,SNB ADD #4,SP ;POP ADDRESS OFF PDL POP ;RESTORE REGS TST SNB RTS B ;RETURN SKIPPING IN-LINE PARAMETER ;JSR B,HWDEP ; .WORD ADDR ;ASSEMBLE LH, RH, SNB INTO PDP10 AND DEPOSIT IN ADDR HWDEP: PUSH MOV LH,C CLR A TST SNB BEQ 1$ MOV #2,A 1$: ASL C ROL A ASL C ROL A PUSH ;PUSH HIGH, MIDDLE, AND LOW BITS MOV SP,A ;POINTER TO DATA PUSH <#0,(B)> ;PUSH HIGH AND LOW ADDRESS MOV SP,B ;POINTER TO ADDRESS DPOS ;DO THE DEPOSIT BCS UHUNG ;BRANCH IF UCODE HUNG ADD #10.,SP ;POP ADDRESS AND DATA OFF PDL POP TST (B)+ ;SKIP TRAILING PARAMETER RTS B UHUNG: $PMSG .WORD 1$ SETOM NO.ITS ;GIVING UP JMP $CNTLC 1$: .ASCIZ/?MICROCODE HUNG/ .ENDC ;DTE20P .IFNZ DL10P .SBTTL MAIN LOOP FOR DL10 MAIN: .IIF NZ TEN11P, CALL T11WAK ;CHECK UP ON TEN-11 INTERFACE .IFNZ ETHERP TST CHXRTF+CHXETH ;NEED TO BROADCAST ROUTING INFO TO ETHERNET? BEQ 666$ CALL ETHRUT 666$: .ENDC ;ETHERP BIT #DLXPRT,DLXCSR ;PORT TO 10 ENABLED? BNE 1$ ;YES SETOM NO.ITS ;NO, FLAG THERE IS NO ITS SETOM DLXOFF ;AND THAT WE THINK DL10 PORT IS OFF BR MAIN ;AND WAIT FOR IT TO TURN ON 1$: TST DLXOFF ;DID DL10 JUST TURN ON? BEQ 4$ ;NO, IT WAS ON BEFORE CLR DLXOFF ;YES, SO REMEMBER THAT MOV VERS,A ;CHECK VERSION SUPPLIED BY -10 BEQ 2$ ;ZERO OK (MUST BE SALVAGER) CMP A,VERSN BEQ 2$ BPT ;-10 AND -11 PROGRAMS NOT SAME CONFIG 2$: 4$: BIT #DLXPAR+DLXNXM,DLXCSR ;ERROR ACCESSING MEMORY? BEQ 5$ ;NO BPT ;DON'T GO OFF DESTROYING PEOPLE'S FILES ;WAIT FOR -10 TO REQUEST SERVICE, OR CLOCK TO TICK 5$: CLR 10RQ BIT #DLX11I,DLXCSR ;10 REQUESTING SERVICE? BEQ 10$ SETOM 10RQ BIS #DLXZ11,DLXCSR ;YES, CLEAR FLAG BR CHKOST ;AND GO CHECK FOR THINGS TO DO 10$: TST WAKE ;NO, CHECK ANYWAY IF 60 CYCLE CLOCK HAS TICKED BEQ MAIN ;NEITHER, JUST WAIT CLR WAKE ;CLOCK HAS TICKED, CLEAR FLAG INC DLXUP ;AND INCREMENT COUNTER 10 IS SUPPOSED BEQ 11$ ; TO SETOM EVERY 1/2 SEC CMP DLXUP,#15.*60. ;IF IT DOESN'T TOUCH IT FOR 15 SECONDS, BLE 12$ ; CONSIDER IT DOWN. NOTE THAT PARITY SWEEPS SETOM NO.ITS ; THROUGH LARGE MEMORY CAN TAKE SEVERAL SECONDS MOV #15.*60.,DLXUP ;DON'T LET COUNTER OVERFLOW BR 12$ ;BUT CHECK FOR COMMANDS ANYWAY (SALVAGER DISK) 11$: CLR NO.ITS ;-10 HAS SETOMED COUNTER, IT'S UP 12$: ;FALL INTO CHKOST ; CHECK FOR OUTPUT-START FROM -10 CHKOST: MOV TTYST,A ;LINE# TO START OUTPUT BEQ CHKOUT ;NONE. CLR TTYST ;TELL -10 IT'S BEEN PICKED UP MOV #TYORNG,B MASK 5 ;DON'T INTERFERE WITH P.I. LEVEL CALL PUT ;PUT IN RING, LATER WILL SEND IT BACK TO 10 UNMASK ; CHECK FOR TTY OUTPUT SENT BY -10 CHKOUT: MOV TYOLIN,I ;OUTPUT TO BE DONE? BEQ CHKIN ;NO. MOV TYOCNT,C ;YES, GET NUMBER OF CHARS CALL TYOSER ;CALL OUTPUT HANDLER CLR TYOLIN ;TELL 10 WE'VE GOBBLED THE OUTPUT BIS #DLX10I,DLXCSR ;GIVE TRANSFER-COMPLETE INTERRUPT ; CHECK FOR TTY INPUT TO BE SENT TO -10 CHKIN: TST TYIRNG+RINGCT BEQ CHKDON ;NO STATUS TO BE STORED TST TYILIN BNE CHKDON ;PREVIOUS STATUS NOT PICKED UP MOV #TYIRNG,B CALL GET MOV A,TYICHR ;GIVE INPUT CHARACTER TO 10 CALL GET MOV A,TYILIN ;GIVE LINE NUMBER TO 10 BIS #DLX10I,DLXCSR ;SEND INTERRUPT TO 10 ; CHECK FOR OUTPUT-DONE TO BE SENT TO -10 CHKDON: TST TYORNG+RINGCT BEQ CHKHNG ;NO STATUS TO BE STORED TST TYOSTS BNE CHKHNG ;PREVIOUS STATUS NOT PICKED UP MOV #TYORNG,B CALL GET MOV A,I ASL I MOV BUFSIZ(I),TYOBSZ ;TELL -10 HOW MANY CHARS TO GIVE MOV A,TYOSTS ;GIVE OUTPUT DONE TO 10 BIS #DLX10I,DLXCSR ;WITH INTERRUPT ; CHECK FOR HANGUPS TO BE SENT TO -10 CHKHNG: TST HNGSIG ;ANY HANGUPS TO BE REPORTED? BEQ CHKLPR ;NO TST HNGLIN BNE CHKLPR ;PREVIOUS STATUS NOT PICKED UP MOV #LASTTY,I ;SCAN OVER ALL LINES 1$: MASK 5 MOV TTYHNG(I),A ;GET HANG-UP STATUS BNE 2$ ;BRANCH IF FOUND SOMETHING TO REPORT UNMASK TST -(I) CMP I,#NFTTY BHIS 1$ BPT ;HNGSIG OUT OF PHASE WITH TTYHNG 2$: CLR TTYHNG(I) ;GOT STATUS, CLEAR IT DEC HNGSIG ;DECREASE COUNT OF FROBS WAITING TO BE SIGNALLED UNMASK ;NOW IT'S OK TO INTERRUPT AND SET TTYHNG MOV A,HNGLIN ;GIVE LINE NUMBER AND OTHER DATA TO 10 BIS #DLX10I,DLXCSR ;WITH INTERRUPT ; CHECK FOR REQUEST FROM -10 TO SET LINE PARAMETERS CHKLPR: MOV LPRLIN,I ;LINE PARAMETERS TO BE SET? BEQ CHKCHS ;NO. ASL I ;YES, GET LINE INDEX MOV LPRLPR,A ;AND DH11 PARAMETER REGISTER VALUE MOV LPRBSZ,B ;AND BUFFER SIZE CALL SPARAM ;CALL PARAMETER SETTER CLR LPRLIN ;TELL 10 IT IS DONE ; CHECK FOR CHAOS NET ACTIVITY CHKCHS: .IFNZ CHAOSP CALL DLCWAK ;WAKEUP DL10-CHAOSNET STUFF .ENDC ;CHAOSP .IFNZ T300P CALL DSKSTR ;CHECK FOR DISK REQUEST .ENDC ;T300P ; CHECK FOR EXAMINE/DEPOSIT REQUEST FROM -10 CHKEXD: TST EXDSTS ;EXAMINE/DEPOSIT? BEQ CHKGLD ;NO. MOV EXDADR,A ;GET ADDRESS CMP EXDSTS,#2 BNE 21$ MOV EXDDAT,(A) ;DEPOSIT 21$: MOV (A),EXDDAT ;EXAMINE CLR EXDSTS ;IT IS DONE ;CHECK FOR GOULD LPT OUTPUT CHKGLD: .IF EQ GOULDP ; CLR GLPCTR ;IF NO GOULD, FLUSH OUTPUT FOR IT ; SETOM GLPTER ;AND SAY "NOT READY" TST 10RQ BEQ 20$ ;10 WANTED US TO DO SOMETHING, PLAY WITH THE LIGHTS MOV LITHSE,A ROL A ROL LITHSE 20$: MOV LITHSE,GLPTER .IFF TST GLPCTR ;ANY BYTES IN BUFFER? BEQ 1$ CALL GLPTYO ;YES, OUTPUT THEM 1$: MOV GLPERR,GLPTER ;COPY ERROR STATUS FROM P.I. LEVEL TO -10 .ENDC ;DONE HERE SO NO USE OF DL10 AT P.I. LEVEL ; BR MAINX MAINX: JMP MAIN ;THAT'S IT MAINE:: .ENDC ;DL10P .IFNZ DTE20P .SBTTL MAIN LOOP FOR DTE20 MAIN: BIT #%D1RUN,DIAG1 ;IS KL10 RUNNING? BEQ TENDED ;NO, LOSE! BIT #%D1ERR+%D1HLT,DIAG1 ;HAS KL10 CLOCK STOPPED FOR HARDWARE ERROR? OR JRST 4 BNE TENDED ;YES, LOSE! TST KLDCPF ;MAYBE USER WANTS TO GIVE A KLDCP COMMAND? BNE KLDCPR ;YES, RETURN TO KLDCP TSTB @DLKS+NFDLHX ;CTY INPUT? BPL 10$ ;TEST KBD BEFORE CLK SINCE MIGHT BE MORE THAN ; 1/60'TH SECOND PER TRIP AROUND THE LOOP. MASK 5 ;YES, SIMULATE INTERRUPT CALL DL1IBK ;CAN'T USE REAL INTS BECAUSE WOULD INTERFERE WITH KLDCP 10$: TSTB LKS ;60 CYCLE CLOCK TICK? BMI CLKSER ;YES BIT #%STINV,STATUS ;REQUEST FROM 10? BNE TENSER ;YES, SERVICE IT. BIT #%STDNI,STATUS ;TO10 XFER COMPLETE? BNE INPDON ;YES, SERVICE IT. BIT #%STDNO,STATUS ;TO11 XFER COMPLETE? BNE OUTDON ;YES, SERVICE IT. BIT #%STERI+%STERO,STATUS BNE LOSSAG ;BYTE TRANSFER LOST BR MAIN ;CLOSE LOOP ;60-CYCLE CLOCK SERVICE CLKSER: CLR LKS ;CLEAR CLOCK FLAG TST CLKENB ;DOES 10 WANT CLOCK INTERRUPTS? BEQ 1$ D10MON ;YES, GIVE ONE DTECLK ;SET CLOCK FLAG IN LOW CORE BCS UHUNG MOV #%STINX,STATUS ;AND SEND INTERRUPT 1$: CMP SWR,CURSWR ;MAYBE NEED TO UPDATE 10'S SWITCHES BEQ 2$ MOV SWR,CURSWR TENSW ;LET KLDCP DO IT BCS UHUNG 2$: JSR B,HWEXAM ;INCREMENT COUNTER -10 IS SUPPOSED DTECHK ; TO SETOM EVERY HALF-SECOND CLR LH CLR SNB INC RH BEQ 3$ CMP RH,#15.*60. ;IF IT DOESN'T SETOM IT FOR 15 SECONDS BLE 4$ ;THEN IT IS DOWN. NOTE THAT PARITY SWEEPS SETOM NO.ITS ;THROUGH LARGE MEMORY CAN TAKE SEVERAL SECONDS. MOV #15.*60.,RH ;DON'T LET COUNTER OVERFLOW BR 4$ 3$: CLR NO.ITS ;IT SETOMED COUNTER, IT'S UP. 4$: JSR B,HWDEP ;PUT COUNTER BACK DTECHK MASK 6 ;NOW SIMULATE BR6 CLOCK INTERRUPT CALL CLKBRK BR TENSER ;AND GO SERVICE 10 (IN CASE LOST INTERRUPT) ; HERE IF KL10 HALTS TENDED: SETOM NO.ITS CLC RET ;LET KLDCP PRINT THE MESSAGE ; BYTE TRANSFER ENCOUNTERED HARDWARE LOSSAGE LOSSAG: BPT BR LOSSAG ; USER WANTS TO GIVE A KLDCP COMMAND KLDCPR: CLR KLDCPF SEC RET TENSER: JMP TENSR0 ; HERE WHEN TO10 BYTE TRANSFER COMPLETE INPDON: MOV #%STCLI,STATUS ;CLEAR FLAGS IN DTE20 MOV INPCMD,A ;GET COMMAND FOR XFER THAT JUST FINISHED BNE 1$ BPT ;WOOPS, NO XFER IN PROGRESS 1$: CLR INPCMD ;NO XFER IN PROGRESS NOW MOV INPSVI,I MOV INPSVC,C CALL @FINAL-2(A) ;CALL APPROPRIATE FINISHER ROUTINE BR MAIN ; HERE WHEN TO11 BYTE TRANSFER COMPLETE OUTDON: MOV #%STCLO,STATUS ;CLEAR FLAG MOV OUTCMD,A ;GET COMMAND FOR XFER THAT JUST FINISHED BNE 1$ BPT ;WHOOPS, NO XFER IN PROGRESS 1$: CLR OUTCMD ;NO XFER IN PROGRESS NOW MOV OUTSVI,I MOV OUTSVC,C CALL @FINAL-2(A) ;CALL APPROPRIATE FINISHER ROUTINE BR MAINJ ; HERE TO START TO10 BYTE TRANSFER. HWEXAM OF DTEINP HAS BEEN DONE. INPSER: D10MON ;VALUE HAS BEEN PICKED UP, SETOM IT DTEINP BIT #1000,LH ;RIGHT GENDER OF COMMAND? BEQ OUTSR1 ;YES BR MAINJ ;(USED TO BE BPT) NO, IGNORE, MAYBE ITS BEING RELOADED ; HERE TO START TO11 BYTE TRANSFER. HWEXAM OF DTEOUT HAS BEEN DONE. OUTSER: D10MON ;VALUE HAS BEEN PICKED UP, SETOM IT DTEOUT BIT #1000,LH ;RIGHT GENDER OF COMMAND? BNE OUTSR1 ;YES BR MAINJ ;(USED TO BE BPT) NO, IGNORE, MAYBE ITS BEING RELOADED OUTSR1: MOV RH,C ;GET BYTE COUNT MOVB LH,I ;GET LINE# MOVB LH+1,A ;GET COMMAND TIMES 2 BEQ MAINJ ;CLEARING CORE? IGNORE ZERO COMMAND BLE OUTSR2 CMP A,#LBEGIN BGT OUTSR2 CALL @BEGIN-2(A) ;CALL APPROPRIATE BEGIN-XFER ROUTINE BIT #2,A BNE 1$ MOV A,INPCMD ;REMEMBER CRUFT FOR XFER IN PROGRESS MOV I,INPSVI MOV C,INPSVC BR MAINJ 1$: MOV A,OUTCMD ;REMEMBER CRUFT FOR XFER IN PROGRESS MOV I,OUTSVI MOV C,OUTSVC MAINJ: JMP MAIN OUTSR2: BR MAINJ ;BAD COMMAND FROM 10 (USED TO BE BPT) JUST IGNORE IT ;TABLE OF ROUTINES TO PROCESS DATA TRANSFER COMMANDS FROM -10 BEGIN: TYOSER ;%DTTYO ;ETHISR ;%DTETI ;ETHOSR ;%DTETO LBEGIN==.-BEGIN ;TABLE OF ROUTINES TO FINISH UP DATA TRANSFERS FINAL: TYOFIN ;%DTTYO ;ETHIFN ;%DTETI ;ETHOFN ;%DTETO ;CHECK FOR COMMANDS FROM 10, STORE STATUS IN ANY STATUS WORDS ;THAT 10 HAS SET BACK TO -1 TENSR0: MOV #%STUNV,STATUS ;CLEAR 10 INTERRUPTING 11 FLAG JSR B,HWEXAM ;CHECK FOR A NON-TIMESHARING COMMAND DTECMD MOV RH,A ;IS THERE ONE? BEQ TENSR1 ;NO, GO CHECK FOR TIMESHARING STUFF CLR LH CLR SNB CMP A,#377 BHI 2$ 1$: TSTB TPS ;CHAR TO BE TYPED, WAIT FOR READY BPL 1$ MOVB A,TPB ;TYPE IT OUT 9$: CLR RH ;CLEAR OUT THE COMMAND JSR B,HWDEP DTECMD D10MON ;TELL 10 IT'S DONE DTEFLG JMP MAIN 2$: CMP A,#%DTTYI BNE 5$ CLR RH ;SNB,LH,RH NOW HAS ZERO SETOM DDTMOD ;KEYBOARD INPUT WANTED TST DDTCHR ;TEST IF READY BMI 3$ ;IF NO INPUT, GIVE ZERO MASK 5 MOV DDTCHR,RH ;GIVE THE CHAR COM DDTCHR ;MAKE NEGATIVE UNMASK 3$: JSR B,HWDEP DTEF11 BR 9$ 5$: CMP A,#%DTCLN BNE 6$ SETOM CLKENB BR 9$ 6$: CMP A,#%DTCLF BNE 7$ CLR CLKENB BR 9$ 7$: BPT ;SOME COMMAND WE DON'T IMPLEMENT BR 9$ ;IF CONTINUED, IGNORE IT ;CHECK FOR ITS UP/DOWN TENSR1: TST NO.ITS ;IF SYSTEM ISN'T UP, BNE MAINJ ;DON'T TRY TO HACK TS STUFF INC DLXOFF ;OTHERWISE, FIRST TIME THROUGH HERE BNE CHKOST ;WE CHECK THE VERSION JSR B,HWEXAM DTEVER TST RH ;STORED? BNE 1$ DEC DLXOFF ;NO, DON'T LOOK AT IT BR MAINJ ;PROBABLY CORE BEING CLEARED 1$: CMP RH,VERSN BEQ CHKOST BPT ;-10 AND -11 PROGRAMS NOT SAME VERSION CHKOST: JSR B,HWEXAM ;CHECK FOR 10 WANTING OUTPUT START DTEOST BNE CHKTRN ;BRANCH IF LOCATION DTEOST IS -1 D10MON ;HAVING PICKED IT UP, SET BACK TO -1 DTEOST MOV RH,A MOV #TYORNG,B MASK 5 ;DON'T INTERFERE WITH P.I. LEVEL CALL PUT UNMASK CLR DDTMOD ;SYSTEM UP, TURN OFF DDT MODE MOV #-1,DDTCHR ;.. CHKTRN: TST INPCMD BNE 1$ ;INPUT IN PROGRESS, DON'T START AGAIN JSR B,HWEXAM ;CHECK FOR DATA TRANSFER COMMAND DTEINP BNE 1$ ;DTEINP -1, NO REQUEST JMP INPSER 1$: TST OUTCMD BNE CHKLSP ;OUTPUT IN PROGRESS, DON'T START AGAIN JSR B,HWEXAM ;CHECK FOR DATA TRANSFER COMMAND DTEOUT BNE CHKLSP ;DTEOUT -1, NO REQUEST JMP OUTSER CHKLSP: JSR B,HWEXAM ;CHECK FOR SET LINE SPEED COMMAND DTELSP BNE CHKTYI MOV RH,I ;GET LINE# ASL I CMP I,#NFTTY ;VALIDATE IT BLO 1$ ;IGNORE IF BAD CMP I,#LASTTY BHI 1$ JSR B,HWEXAM ;GET LPR,,BUFFERSIZE DTELPR MOV LH,A MOV RH,B CALL SPARAM ;DO IT 1$: D10MON ;DONE, SETOM DTELSP CHKTYI: TST TYIRNG+RINGCT BEQ CHKODN ;NO TTY INPUT WAITING JSR B,HWEXAM DTETYI BEQ CHKODN ;PREVIOUS CHAR NOT PICKED UP MOV #TYIRNG,B CALL GET MOV A,RH ;CHAR CALL GET MOV A,LH ;LINE# CLR SNB JSR B,HWDEP ;GIVE 10 LINE#,,CHAR DTETYI MOV #%STINX,STATUS ;INTERRUPT THE 10 CHKODN: TST TYORNG+RINGCT BEQ CHKHNG ;NO OUTPUT DONES WAITING JSR B,HWEXAM DTEODN BEQ CHKHNG ;PREVIOUS STATUS NOT PICKED UP MOV #TYORNG,B CALL GET ;GET LINE# WITH OUTPUT DONE MOV A,LH ASL A MOV BUFSIZ(A),RH CLR SNB JSR B,HWDEP ;GIVE 10 LINE#,,BUFFERSIZE DTEODN MOV #%STINX,STATUS ;INTERRUPT THE 10 CHKHNG: TST HNGSIG BEQ MAINX ;NO HANGUPS/DIALINS WAITING JSR B,HWEXAM DTEHNG BEQ MAINX ;PREVIOUS STATUS NOT PICKED UP MOV #LASTTY,I ;SCAN OVER ALL LINES 1$: MASK 5 MOV TTYHNG(I),A ;GET HANG-UP STATUS BNE 2$ ;BRANCH IF FOUND SOMETHING TO REPORT UNMASK TST -(I) CMP I,#NFTTY BHIS 1$ BPT ;HNGSIG OUT OF PHASE WITH TTYHNG 2$: CLR TTYHNG(I) ;GOT STATUS, CLEAR IT DEC HNGSIG ;DECREASE COUNT OF FROBS WAITING TO BE SIGNALLED UNMASK ;NOW IT'S OK TO INTERRUPT AND SET TTYHNG MOV A,RH ;GIVE LINE NUMBER AND OTHER DATA TO 10 CLR LH CLR SNB JSR B,HWDEP DTEHNG MOV #%STINX,STATUS ;INTERRUPT THE 10 MAINX: JMP MAIN .ENDC ;DTE20P .IFZ DL10P+DTE20P .SBTTL MAIN LOOP FOR AI MAIN: .IIF NZ TEN11P, CALL T11WAK ;CHECK UP ON TEN-11 INTERFACE .IIF Z TEN11P, CALL CHSRUN ;DAMNED THING GETS WEDGED .IFNZ ETHERP TST CHXRTF+CHXETH ;NEED TO BROADCAST ROUTING INFO TO ETHERNET? BEQ 666$ CALL ETHRUT 666$: .ENDC ;ETHERP TST WAKE ;CLOCK TICK? BEQ MAIN ;NO, JUST WAIT CLR WAKE ;CLOCK HAS TICKED, CLEAR FLAG BR MAIN ;NOT MUCH TO DO, NO TTYS .ENDC ;DL10P+DTE20P .SBTTL OUTPUT HANDLERS TYOSER: ASL I ;CONVERT -10 LINE# TO -11 TTY INDEX CMP I,#NFTTY BLO 11$ CMP I,#LASTTY BLOS 12$ 11$: BPT ;10 GAVE BAD LINE# 12$: MOV HDWR(I),H ;GET HARDWARE INDEX MOV BUFPNT(I),D ;AND ADDRESS OF TYPEOUT BUFFER CMP BUFSIZ(I),C ;MAKE SURE THERE IS ROOM IN BUFFER BHIS 2$ BPT ;THERE ISN'T 2$: MOV C,B ;MUSTN'T CLOBBER BYTE COUNT IN C .IFNZ DL10P MOV #TYOPNT,A ;GET CRUFT FROM DL10 3$: MOVB @A,(D)+ ;COPY BUFFER SOB B,3$ .ENDC ;DL10P .IFNZ DTE20P MOV D,TO11AD ;SET UP BYTE TRANSFER NEG B BIC #050000,B ;SET LAST, BYTE; CLEAR ASCIZ, 2.4 MOV B,TO11BC ;START XFER RET TYOFIN: MOV HDWR(I),H ;COMES BACK WHEN XFER COMPLETE .ENDC ;DTE20P ;BUFFER HAS BEEN LOADED, START DEVICE MASK 5 ;DON'T LET DEVICE INTERRUPT MOV BUFPNT(I),D CALL @STROUT(H) ;CALL DEVICE-DEPENDENT ROUTINE MOV #40000,TYPING(I) ;TELL 10 WHEN OUTPUT FINISHES (LARGE POSITIVE NUMBER) UNMASK RET ;GIVE MESSAGE. A -> .WORD LENGTH,MSG. I HAS LINE NUMBER. GIVMSG: PUSH MOV (A)+,C ;C HAS BYTE COUNT, A HAS ADDRESS MOV A,D ;PUT ADDRESS IN D MOV HDWR(I),H MASK 5 CALL @STROUT(H) ;START OUTPUT TO LINE UNMASK POP RET ASPACK: MNAME ^% MSG ^\ ‡Connected to MCHN'.\% DWNMSG: MSG ^\ ‡ITS is down.\ IBOMSG: MSG ^\IBO\ ;DEVICE-DEPENDENT OUTPUT START ROUTINES (CALL AT PI LEVEL 5) ;H HDWR IDX, I TTY IDX, D BUFFER POINTER, C NUMBER OF BYTES STRDH: BIC DHLBIT(I),@DHBAR(H) ;IF LINE ALREADY TRANSMITTING, STOP IT ;IT SHOULDN'T OUGHT TO BE... MOV DHLSEL(I),@DHSCR(H) ;HARDWARILY SELECT THIS LINE MOV D,@DHCA(H) ;SET XMT ADDRESS NEG C ;HARDWARE LIKES NEGATIVE BYTE COUNTS MOV C,@DHBC(H) ;SET XMT COUNT BIS DHLBIT(I),@DHBAR(H) ;START TRANSMISSION HARDWARILY BIS DHLBIT(I),DHOAC(H) ;SOFTWARILY ALSO RET STRDL: MOV D,DLCA(H) MOV C,DLBC(H) CLR @DLPS(H) MOV #300,@DLPS(H) ;CAUSE INTERRUPT SETOM DLOAC(H) CPOPJ: RET .IFNZ NMPTYS STRMPK: TST MPXENB BEQ CPOPJ MOV D,MPXPNT-NFMPTY(I) ;QUEUE OUTPUT MOV C,MPXNBT-NFMPTY(I) STRMPX: PUSH I TST MPXOAC ;START THE MPXR BNE 10$ ;ALREADY BUSY CLR I MOV #NMPTYS,D 2$: MOV MPXNBT(I),C ;FIND MPX KLUDGE LINE WANTS TO OUTPUT BNE 15$ TST (I)+ SOB D,2$ 10$: POP I RET 15$: MOV I,MPXOLN ;SAVE LINE# OUTPUT ON ASR I ;SET UP HEADER ADD #200,I MOVB I,MPXHED MOVB C,MPXHED+1 MOV #-1,MPXOAC ;SEND HEADER MOV #MPXIDX,I MOV HDWR(I),H MOV #MPXHED,D MOV #2,C CALL @STROUT(H) BR 10$ .ENDC ;NMPTYS .IFNZ GOULDP .SBTTL GOULD LPT OUTPUT (M.P. LEVEL) .IIF Z DL10P, .ERROR GOULD LPT ONLY CODED FOR DL10 .ERR BY THE WAY, THESE ROUTINES DON'T WORK WORTH GUBBISH GLPTYO: MOV GLPOIP,H ;GET NEXT BUFFER CMP GB.STA(H),#%GBMP BEQ 2$ ;BRANCH IF M.P. ACTIVE BLT 1$ ;BRANCH IF IDLE BUFFER AVAIL RET ;NO FREE BUFFERS 1$: CALL GLPBGB ;GOBBLE A BUFFER 2$: MOV GB.PNT(H),D MOV GLPCTR,C ;SET UP BYTE COUNTER MOV GLPGRF,GLPGF1 ;COPY ARG FROM 0 FOR SPEED TST GLIMBF ;CHAR SAVED FROM LAST TIME? BEQ GLPNCL CLR GLIMBF ;YES, PRINT IT MOVB GLIMBO,A CALL GLPPUT MOVB GLIMBO+1,A ;SECOND CHAR? BEQ GLPNCL CLR GLIMBO CALL GLPPUT ;CHARACTER PROCESSING LOOP ;C HAS # CHARS YET TO GO, D HAS WHERE TO PUT THEM, H -> BUFFER ;A WILL HAVE CHAR GLPNCL: MOV GLPPTR,A ;GET NEXT CHAR TST GLPGF1 BNE GLPNRM ;GRAPHIC MODE, NO CHARACTER PROCESSING CMP A,#177 ;ESCAPE? BEQ GLPESC CMP A,#40 ;CONTROL? BGE GLPNRM ;NO, NORMAL PRINTING CMP A,#14 ;CHECK FOR SPECIAL CONTROLS BNE 10$ 8$: CLR GLPROW ;START NEW PAGE TST GLPCOL ;IN MIDDLE OF LINE? BEQ 9$ ;NO, OK CALL GLPBWW ;OTHERWISE, HAIR CLR GLPFIL ;HACK HACK MAKE FF NEXT LINE BR GLPNB1 9$: SETOM GB.FF(H) BR GLPNXC 10$: CMP A,#12 BNE 12$ INC GLPROW CMP GLPROW,#GLPRMX BHIS 8$ ;SKIP OVER PERFORATION TST GLPCOL BNE GLPNBF ;IF NOT A BLANK LINE, FINISH BUFFER INC GB.NL(H) BR GLPNXC 12$: CMP A,#11 BNE 15$ 13$: MOV #40,A ;TAB - SPACE OVER CALL GLPPUT BIT #7,GLPCOL BNE 13$ BR GLPNXC 15$: CMP A,#15 BEQ GLPNXC ;IGNORE CR CMP A,#33 BNE 16$ MOV #'$,A ;PRINT ALTMODE AS DOLLAR BR GLPNRM 16$: BIS #100,A ;RANDOM CONTROL AS UPARROW, LETTER MOVB A,GLIMBO+1 MOV #'^,A CALL GLPPUT MOVB GLIMBO+1,A CLR GLIMBO GLPNRM: CALL GLPPUT ;HERE FOR NORMAL CHARACTER GLPNXC: DEC C ;HERE TO GOBBLE CHARACTER BGT GLPNCL ;BRANCH IF MORE CHARS TO GO BR GLPEND ;BUFFER EMPTIED GLPNBF: CALL GLPBWW ;HERE TO ADVANCE TO NEXT BUFFER GLPNB1: CMP GB.STA(H),#%GBIDL ;NEXT BUFFER AVAIL? BNE GLPEN1 ;NO, STOP CALL GLPBGB ;YES, GOBBLE IT BR GLPNXC GLPESC: DEC C ;HERE FOR TWO CHAR ESC SEQ BEQ GLPEND ;-10 FORGOT 2ND CHAR, FLUSH MOV GLPPTR,A ;GET & DECODE 2ND CHAR CMP A,#105 ;EOF BEQ GLPEOF BR GLPNXC ;OTHER CHARS ARE IGNORED GLPEOF: CLR GLPFIL CLR GLPROW CALL GLPBWW ;EOF, WRITE LAST BUFFER GLPEN1: DEC C ;GOBBLE A CHARACTER GLPEND: MOV C,GLPCTR ;HERE WHEN DONE, RELEASE 10'S BUFFER CMP GB.STA(H),#%GBMP ;BUFFER ACTIVE AT M.P. LEVEL? BNE 1$ ;IF NOT, DON'T CLOBBER GB.PNT MOV D,GB.PNT(H) ;IF SO, REMEMBER AMT OF STUFF IN CURRENT BUFFER 1$: RET ;RETURN TO MAIN LOOP ;OUTPUT PRINTING CHAR IN A GLPPUT: CMP D,GLPLIM ;LINE OVERFLOW? BLO 5$ ;NO CALL GLPBWW ;YES, DONE WITH THIS BUFFER INC GLPROW ;OUGHT TO CHECK FOR PERFORATION, BUT... CMP GB.STA(H),#%GBIDL ;MORE BUFFERS? BNE 6$ ;NO CALL GLPBGB 5$: MOVB A,(D)+ ;DROP CHAR IN BUFFER INC GLPCOL ;AND ADVANCE COLUMN RET 6$: MOVB A,GLIMBO ;NO BUFFERS, SAVE CHAR BEING PRINTED SETOM GLIMBF ;SET FLAG SO WILL BE PRINTED NEXT TIME TST (SP)+ ;STOP THE WORLD BR GLPEN1 ;GOBBLE IDLE BUFFER H -> FOR M.P. RETURNS GB.PNT(H) IN D. GLPBGB: MOV #%GBMP,GB.STA(H) ;ACTIVATE AT M.P. LEVEL CLR GB.FF(H) ;INIT THE BUFFER CLR GB.NL(H) CLR GLPCOL ;START LINE IN COLUMN 0 MOV H,D ;INIT INSERT POINTER ADD #GB.DAT,D MOV D,GB.PNT(H) MOV H,GLPLIM ;SET UP MAX. VALUE OF GB.PNT ADD #GB.LEN,GLPLIM RET ;GIVE BUFFER H -> TO P.I. LEVEL GLPBWW: BIT #1,D ;MUST BE EVEN NUMBER OF BYTES BEQ 1$ CLRB (D)+ 1$: PUSH A ;INTERFACE GETS BYTES IN WRONG ORDER MOV P,A ;COMPUTE NUMBER OF WORDS IN LINE SUB H,A SUB #GB.DAT,A ASR A BNE 4$ CLR (D)+ ;CAN'T HAVE ZERO-LENGTH LINE INC A 4$: MOV A,GB.PNT(H) ;SAVE WORD COUNT FOR P.I. LEVEL 2$: SWAB -(D) SOB A,2$ POP A TST GLPFIL ;IF STARTING NEW FILE, BNE 5$ SETOM GLPFIL SETOM GB.FF(H) ; BE SURE TO GET NEW PAGE 5$: MOV #%GBWRT,GB.STA(H) ;QUEUE TO P.I. LEVEL MOV GB.NXT(H),H ;ADVANCE TO NEXT BUFFER MOV H,GLPOIP MASK 6 ;STOP P.I. LEVEL (HAVE TO LOCK OUT GLPBRK & CLKBRK) TST GLPOAC ;PRINTER ON? BNE 3$ ;YUP MOV #%GCOFF,@#GLPCSR ;NO, CLEAR OLD STUFF IN INTERFACE TST GLPGF1 ;AND PUT IN LOW-SPEED GRAPHIC MODE IF NECC BEQ 6$ MOV #%GCGRF,@#GLPCSR MOV #%GCLSL,@#GLPCSR ;LOW SPEED (COME ON, THIS IS ONLY A KL10!) 6$: MOV #%GCON,@#GLPCSR ;TURN IT ON MOV #%GCION,@#GLPCSR ;TURN ON INTERRUPTS SETOM GLPOAC ; PUSH @#PS ;FAKE AN INTERRUPT ; CALL GLPBRK ;IS THIS NECESSARY? 3$: UNMASK RET ;GOULD LPT VARIABLES GLPCOL: 0 ;CURRENT COLUMN NUMBER GLPROW: 0 ;CURRENT ROW NUMBER GLPRMX==67. ;NUMBER OF LINES PER PAGE GLPLIM: 0 ;ADDRESS OF END OF CURRENT BUFFER GLPOAC: 0 ;NON-ZERO => GOULD LPT P.I. ACTIVE GLPGF1: 0 ;NON-ZERO => GOULD LPT IN GRAPHIC MODE GLIMBO: 0 ;SAVE CHAR HERE WHEN RUN OUT OF BUFFERS GLIMBF: 0 ;NON-ZERO => CHAR IN GLIMBO GLPFIL: 0 ;NON-ZERO => IN MIDDLE OF A FILE GLPTIM: 10. ;COUNT DOWN WHEN LOSING GLPERR: 0 ;NON-ZERO => ERROR STATUS FROM P.I. .ENDC ;GOULDP .SBTTL T-300 DISK .IFNZ T300P ;DISK UNIBUS REGISTERS DSKCRA=176700 ;COMPLETION REGISTER A %DAPON==100000 ;SPONTANEOUS COMPLETION DUE TO POWER-ON. DISK NUMBER ; IN LOW BITS OF COMMAND-COMPLETION REGISTER B %DACQE==10000 ;CONSISTENCY ERROR IN COMMAND QUEUE %DANXM==4000 ;NXM ERROR IN COMMAND QUEUE %DAPAR==2000 ;PARITY ERROR IN COMMAND QUEUE ;LOW 2 BITS OF COMMAND COMPLETION REGISTER A AND ;COMMAND COMPLETION REGISTER B CONTAIN THE ADDRESS ;OF THE PARITY OR NXM ERROR DSKCRB=176702 ;COMPLETION REGISTER B DSKCSR=176704 ;COMMAND/STATUS REGISTER %DCCPL==100000 ;COMMAND IS COMPLETE, RESET BY %DCACK. READ-ONLY %DCDER==40000 ;"DMA ERROR", RESET ONLY BY SYSTEM RESET. ;1=NORMAL, 0=ERROR ;BITS 30004 ALWAYS ON %DCMNT==4000 ;HOST-ADAPTOR MAINTENANCE MODE %DCRST==2000 ;RESET. WRITE-ONLY. %DCACK==1000 ;ACKNOWLEDGE COMMAND COMPLETION. WRITE-ONLY %DCCMD==400 ;TAKE COMMAND FROM CTRA/CTRB. WRITE-ONLY %DCRDY==200 ;READY TO TAKE A COMMAND. READ-ONLY %DCTIE==100 ;COMMAND TRANSMISSION (%DCRDY) INTERRUPT ENABLE %DCCIE==40 ;COMMAND COMPLETION (%DCCPL) INTERRUPT ENABLE %DCPCY==20 ;POWER JUST CYCLED ON OR OFF. READ-ONLY %DCPON==10 ;POWER ON. READ-ONLY %DCDMA==2 ;DMA IN PROGRESS. READ-ONLY %DCBOT==1 ;BOOT (READ DRIVE 0 SECTOR 0 INTO MEMORY 0). WRITE-ONLY DSKCTA=176706 ;COMMAND TRANSMISSION A (ADDRESS OF RQB HIGH BITS) DSKCTB=176710 ;COMMAND TRANSMISSION B (ADDRESS OF RQB LOW BITS) ;176714 DUPLICATES DSKCSR FOR UNKNOWN REASONS ;DISK REQUEST BLOCK. WE ONLY HAVE ONE SINCE NO SEEK OVERLAP. RQBACT: 0 ;NON-ZERO IF REQUEST ACTIVE AND EXPECTING COMPLETION RQBID: 0 ;RETURNED IN CCRB WHEN COMMAND COMPLETES RQBSTS: 0 ;STATUS STORED BY 2561, COPIED INTO DSCSTS RQBFLT: 0 ;FAULT CODE IN HIGH BYTE, BITS 1-0 HIGH BITS OF LINK ADDRESS RQBLNK: 0 ;LINK ADDRESS TO NEXT RQB (MUST BE ZERO) RQBCMD: 0 ;COMMAND CODE, COPIED FROM DSCCMD RQBDRV: 0 ;UNIT NUMBER, COPIED FROM DSCDRV RQBCYL: 0 ;CYLINDER NUMBER, COPIED FROM DSCCYL RQBHED: 0 ;HEAD NUMBER, COPIED FROM DSCHED RQBSEC: 0 ;SECTOR NUMBER, COPIED FROM DSCSEC RQBWC: 0 ;POSITIVE WORD COUNT (ALWAYS 12.*256.) RQBMA: 0 ;MEMORY ADDRESS (ALWAYS DSKBUF) RQBMAH: 0 ;MEMORY ADDRESS HIGH (ALWAYS 0) ; BITS 1-0 BITS 17-16 OF ADDRESS. BIT 6 MA INCR INH RQBID1: 0 ;RETURNS RECORD ID 1 RQBID2: 0 ;RETURNS RECORD ID 2 RQBMNT: .BLKW 27. ;DIAGNOSTIC DATA MAY BE RETURNED ;DISK BUFFER. HOLDS ENOUGH 12-BIT BYTES IN 16-BIT WORDS TO MAKE 1024. 36-BIT WORDS DSKBUF: .BLKW 3.*1024. ;ROUTINE TO START DISK IF IT IS READY AND THERE IS A REQUEST. DSKSTR: TST DSCREQ ;ANY REQUEST FROM 10? BEQ 99$ ;NO, EXIT CMP DSCCHK,#2561 BNE 99$ ;CHECK WORD WRONG, DON'T TOUCH DISK TST RQBACT ;PREVIOUS OPERATION FINISHED? BEQ 10$ BPT ;NO, MUST BE BUG IN 10? 10$: TSTB DSKCSR ;TEST IF READY FOR COMMAND TRANSMISSION BPL 99$ ;NO, WAIT CLR DSCDON ;YES, CLEAR 10/11 COMMUNICATION FLAGS CLR DSCREQ CLR RQBLNK ;SET UP RQB FROM 10'S PARAMETERS MOV DSCCMD,RQBCMD MOV DSCDRV,RQBDRV MOV DSCCYL,RQBCYL MOV DSCHED,RQBHED MOV DSCSEC,RQBSEC MOV #12.*256.,RQBWC MOV #DSKBUF,RQBMA CLR RQBMAH CMP RQBCMD,#%DMWRT ;IF A WRITE COMMAND, MUST COPY DATA BUFFER BNE 30$ MOV #DSKBUF,D .REPT 4 ;TAKES 4 BYTE POINTERS TO DO IT MOV #DSCPNT+<2*.RPCNT>,H .REPT 3 ;EACH BYTE POINTER HAS 768 12-BIT BYTES MOV #256.,C CALL MOVHD .ENDR .ENDR 30$: CLR DSKCTA ;GIVE ADDRESS OF RQB TO 2561 MOV #RQBID,DSKCTB SETOM RQBACT ;TELL INTERRUPT LEVEL INTERRUPT EXPECTED MOV #%DCCMD+%DCCIE,DSKCSR ;GIVE COMMAND, ENABLE COMPLETION INTERRUPT 99$: RET ;DONE ;CALL HERE WHEN DISK INTERRUPTS DSKBRK: PUSH ;SAVE ALL REGISTERS MOV DSKCSR,A BIT #%DCPCY,A ;POWER CYCLED? BNE 5$ ;YES, RESET CONTROLLER AND IGNORE INTERRUPT BIT #%DCMNT,A ;NO, MAINTAINENCE MODE BEQ 4$ ;OK BPT ;BLEAH, MUST BE BROKEN BR 5$ 4$: BIT #%DCDER,A ;WHAT ABOUT UNIBUS ERROR BNE 10$ BPT 5$: MOV #%DCRST,DSKCSR ;RESET THE CONTROLLER AND TURN OFF INTERRUPTS TST RQBACT ;DID THIS LOSE IN THE MIDDLE OF A DISK OPERATION? BEQ 99$ ;NO, DISMISS MOV #%DFRST,A ;YES, GIVE ERROR STATUS CLR B BR 20$ 10$: BIT #%DCCPL,A ;TEST FOR COMMAND COMPLETION BPL 99$ ;NO, IGNORE INTERRUPT MOV DSKCRA,A ;GET COMPLETION STATUS MOV DSKCRB,B MOV #%DCACK+%DCCIE,DSKCSR ;ACKNOWLEDGE COMPLETION, ENABLE MORE INTERRUPTS TST RQBACT ;EXPECTED? BEQ 99$ ;NO, IGNORE BIT #%DAPON,A ;POWER-UP INDICATION? BNE 99$ ;FOR NOW, IGNORE IT BIT #%DACQE+%DANXM+%DAPAR,A BEQ 30$ ;OK, NO COMMAND-QUEUE ERROR MOV #%DCRST,DSKCSR ;RESET CONTROLLER (I DON'T KNOW IF IT NEEDS IT) 20$: MOV A,DSCFLT ;COMMAND-QUEUE ERROR, GIVE STATUS TO PDP10 MOV B,DSCSTS BR 80$ 30$: CLR DSCFLT ;CLEAR HIGH BYTE MOVB RQBFLT+1,DSCFLT ;PICK UP FAULT CODE, PUT IN LOW BYTE BEQ 35$ ;IF FAULT CODE IS NON-ZERO, THE THING MAY BE FROZEN, MOV #%DCRST,DSKCSR ;SO RESET IT. OTHERWISE ERROR SEEMS TO HAPPEN OVER AND OVER 35$: MOV RQBSTS,DSCSTS ;GIVE STATUS TO PDP10 MOV RQBCYL,DSCCYL ;STORE BACK DISK ADDRESS, MAY BE USEFUL TO PDP10 MOV RQBHED,DSCHED MOV RQBSEC,DSCSEC BIT #%DMRED,RQBCMD ;IF COMMAND WAS READ, COPY BUFFER BACK BEQ 80$ MOV #DSKBUF,D .REPT 4 ;TAKES 4 BYTE POINTERS TO DO IT MOV #DSCPNT+<2*.RPCNT>,H .REPT 3 ;EACH BYTE POINTER HAS 768 12-BIT BYTES MOV #256.,C CALL MOVDH .ENDR .ENDR 80$: SETOM DSCDON ;SIGNAL PDP10 OPERATION IS COMPLETE BIS #DLX10I,DLXCSR ;AND INTERRUPT THE PDP10 CLR RQBACT ;NO LONGER EXPECTING COMPLETION ON THE RQB 99$: POP ;RESTORE REGISTERS AND EXIT INTERRUPT RTI .ENDC ;T300P .SBTTL SET LINE PARAMETERS ;LINE INDEX IN I ;DH11 PARAM REG IN A ;BUFFER SIZE IN B SPARAM: CMP I,#NFTTY BGE 1$ BPT 1$: CMP I,#LASTTY BLE 2$ BPT 2$: CMP B,#1. ;MINIMUM BUFFER SIZE ONE CHARACTER BGE 3$ MOV #1.,B 3$: CMP B,#MAXBSZ ;MAXIMUM BUFFER SIZE CHARACTERS BLE 4$ MOV #MAXBSZ,B 4$: MOV B,BUFSIZ(I) ;SET AMOUNT OF BUFFER TO BE USED FROM NOW ON MOV HDWR(I),H ;(BUT NO LONGER DO WE ATTEMPT DYNAMIC BUFFER ALLOCATION) CMP H,#NLDHHX BHI 5$ MASK 5 ;LINE IS A DH11, HAVE TO SET LINE PARAM REG MOV DHLSEL(I),@DHSCR(H) ;SELECT THE LINE MOV A,@DHLPR(H) ;GIVE LINE-PARAMETER REG TO DH11 UNMASK 5$: MOV A,LPRVAL(I) ;STORE LPR IN CASE SOMEONE IS CURIOUS RET .SBTTL DH11 INPUT INTERRUPT .REPT NDHS CONC DH,\.RPCNT+1, 2*.RPCNT .ENDR DHIBK: MOV (H),H ;PICK UP HARDWARE INDEX PUSH 1$: MOV @DHNRC(H),A ;RECIEVE A CHARACTER BPL DHIEX ;EXIT INTERRUPT IF NO MORE CHARS MOV A,I ;EXTRACT LINE NUMBER SWAB I BIC #177760,I ASL I ADD DHTYNO(H),I .IFNZ NDHUN CMP I,#NLDHTY ;IGNORE NON-EXISTENT LINES BHI 1$ .ENDC CALL @TTYIPC(I) ;CALL LINE HACKER BR 1$ ;AND CHECK FOR MORE DHIEX: POP RTI ;NORMAL DH11 INPUT DHNRMI: BIT #%DXPAR,A BEQ 1$ ;IGNORE IF PARITY ERROR 10$: RET 1$: BIT #%DXBRK,A ;IF BREAK, BEQ RCV TST AUTOSP(I) ;AND LINE WANTS AUTOSPEED-ON-BREAK FEATURE BPL 10$ ASPMD: MOV #DHASP,TTYIPC(I) ;PUT IT IN AUTOSPEED MODE MOV DHLSEL(I),@DHSCR(H) ;AND SET HARDWARE TO 1200 BAUD MOV #023103,@DHLPR(H) RET ;CHAR IN A RECEIVED FROM LINE IN I RCV: BIC #177400,A ;8-BIT CHAR RECEIVE RCV.FW: TST NO.ITS ;ENTER HERE FOR FULL WORD RECEIVE BEQ 10$ 21$: MOV #DWNMSG,A ;ITS DOWN, GIVE MESSAGE 12$: CALL GIVMSG RET 10$: MOV #TYIRNG,B CMP RINGCT(B),#TYIRSZ-2 BGT 11$ CALL PUT ;FIRST PUT THE CHARACTER MOV I,A ASR A CALL PUT ;THEN THE TENNISH LINE NUMBER RET 11$: MOV #IBOMSG,A ;INPUT BUFFER OVERFLOW BR 12$ .IFNZ NMPTYS ;HANDLE INPUT FROM THE MULTIPLEXOR LINE MPXINP: TST MPXENB BEQ RCV MOV MPXSEL,I ;CURRENT INPUT LINE TSTB A ;SPECIAL CHAR? BMI 1$ JMP @TTYIPC(I) ;NO, RECEIVE ON APPROP LINE 1$: MOV A,I ;SPECIAL CHAR, EXTRACT LINE# BIC #177700,I ;FOLLOWING FEATURE COMMENTED OUT SINCE IT CAUSES 11 TO LOOP ; WHEN NEXT INPUT ARRIVES -- NOT OBVIOUS HOW TO FIX. ; CMP I,#77 ;SELECT NON-MULTIPLEX INPUT? ; BEQ 3$ ;YES, DO SO ASL I ADD #NFMPTY,I CMP I,#LASTTY BHI 2$ ;OUT OF RANGE, IGNORE MOV I,MPXSEL ;INPUT SELECT, SAVE LINE# 2$: RET 3$: MOV #MPXIDX,MPXSEL ;SELECT PASS THROUGH RET .ENDC ;NMPTYS ;AUTOSPEED MODE COMES HERE WHEN CHAR RECIEVED DHASP: BIC #177400,A ;CLEAR FRAMING ERR, ETC. BEQ ASP10 ;11 0'S = 110 BAUD CMP A,#200 ;7 0'S, 1 = 150 BAUD BEQ ASP15 CMP A,#170 ;3 0'S, 4 1'S, 0 = 300 BAUD BEQ ASP30 CMP A,#370 ;300/600 IS NOW RUBOUT, NOT I BEQ ASP36 CMP A,#146 ;1 0, 2 1'S, 2 0'S, ... = 600 BEQ ASP60 CMP A,#340 ;5 0'S, 3 1'S ? MYSTERY TO ME BEQ ASP60 CMP A,#015 ;CR = 1200 BEQ ASP120 CMP A,#215 ;CR WITH EITHER PARITY BEQ ASP120 MOV A,#. ;SAVE GARBAGE FOR DEBUGGING RET ;SOMETHING ELSE, IGNORE ASP10: MOV #006307,A ;110 IN, 110 OUT, NO PARITY, 8 BITS, EXTRA STPBT MOV #5,B MOV #12200,-(SP) BR ASPX ASP15: MOV #012503,A ;150 IN, 150 OUT, NO PARITY, 8 BITS MOV #7,B MOV #13300,-(SP) BR ASPX ASP30: MOV #016703,A ;300 IN, 300 OUT, NO PARITY, 8 BITS MOV #15.,B MOV #14400,-(SP) BR ASPX ASP36: MOV #020703,A ;300 IN, 600 OUT, NO PARITY, 8 BITS MOV #30.,B MOV #14100,-(SP) BR ASPX ASP60: MOV #021003,A ;600 BAUD, NO PARITY, 8 BITS MOV #30.,B MOV #11100,-(SP) BR ASPX ASP120: MOV #023103,A ;1200 IN, 1200 OUT, NO PAR, 8 BITS MOV #60.,B MOV #15500,-(SP) BR ASPX ASPX: CALL SPARAM ;SET BUFFER SIZE AND HARDWARE SPEED MOV I,A ;SET UP SET-SPEED COMMAND TO -10 ASR A BIS (SP)+,A TST TTYHNG(I) ;IF THIS IS NEW STATUS FOR 10, BNE 11$ INC HNGSIG ;INDICATE STATUS WAITING 11$: MOV A,TTYHNG(I) ;SAVE THIS LINE'S LATEST STATUS MOV #ASPACK,A ;ACKNOWLEDGE TO USER THAT HE WON CALL GIVMSG DEC TYPING(I) ;IF NO WAKEUP FOR 10, HIT CALL WHEN TYPING DONE MOV NRMIPC(I),TTYIPC(I) ;AND TAKE LINE OUT OF AUTOSPEED MODE RET .SBTTL DH11 OUTPUT INTERRUPTS .REPT NDHS CONC DH,\.RPCNT+1, 2*.RPCNT .ENDR DHOBK: MOV (H),H ;GET HARDWARE UNIT NUMBER BIT #DHSNXM,@DHSCR(H) ;IS THIS INTERRUPT DUE TO NXM? BEQ 1$ BPT ;YES 1$: BIC #DHTDON,@DHSCR(H) ;HARDWARE KLUDGE TO MAKE INTERRUPTS WIN PUSH MOV DHOAC(H),C ;SEE WHICH BAR BITS HAVE TURNED OFF BIC @DHBAR(H),C BIC C,DHOAC(H) MOV DHTYNO(H),I ADD #15.*2,I 2$: BIT DHLBIT(I),C BEQ 4$ .IFNZ NMPTYS CMP I,#MPXIDX BNE 3$ CALL MPXDON .ENDC ;NMPTYS 3$: .IFNZ NDHUN CMP I,#NLDHTY ;IGNORE NON-EXISTENT LINES BHI 4$ .ENDC CALL XMTDON 4$: SUB #2,I CMP I,DHTYNO(H) BGE 2$ DHOEX: POP RTI XMTDON: TST TYPING(I) ;HERE WHEN OUTPUT FINISHES BGT 1$ ;BRANCH IF -10 WANTS TO KNOW ABOUT IT BEQ 3$ ;BRANCH IF NOTHING TO DO MOV #32,A ;SEND A CALL CALL RCV BR 3$ 1$: MOV I,A ASR A ;PUT TENNISH LINE NUMBER INTO RING MOV #TYORNG,B ;MAIN PROG LEVEL WILL LATER TELL -10 CALL PUT 3$: CLR TYPING(I) RET .IFNZ NMPTYS ;OUTPUT DONE ON MULTIPLEXED LINE MPXDON: PUSH TST MPXOAC BGE 1$ NEG MPXOAC ;SENT HEADER, NOW SEND DATA MOV MPXOLN,A MOV MPXPNT(A),D MOV MPXNBT(A),C CLR MPXNBT(A) CALL @STROUT(H) BR 9$ 1$: MOV MPXOLN,I ;OUTPUT IS DONE ON THAT LINE NOW ADD #NFMPTY,I CALL XMTDON CLR MPXOAC ;MPX IDLE CALL STRMPX ;LOOK FOR NEW STUFF TO DO 9$: POP RET .ENDC ;NMPTYS .SBTTL DL11 INTERRUPTS .REPT NDLS CONC DL,\.RPCNT+1, NFDLHX+<2*.RPCNT> CONC DL,\.RPCNT+1, NFDLHX+<2*.RPCNT> .ENDR DLIBK: MOV (H),H ;GET HARDWARE INDEX OF INTERRUPTING UNIT PUSH MOV @DLKB(H),A ;GET RECEIVED CHARACTER MOV DLTYNO(H),I ;GET LINE NUMBER RECEIVED ON .IFNZ DTE20P BNE 2$ ;ONLY T00 CAN RETURN TO KLDCP BIT #20000,A ;IF BREAK KEY IS HIT BEQ 1$ SETOM KLDCPF ;USER WANTS TO RETURN TO KLDCP BR DLBKEX ;FOR ONE COMMAND LINE 1$: TST DDTMOD ;IF IN DDT MODE, BEQ 2$ BIC #-200,A ; HANDLE INPUT DIFFERENTLY MOV A,DDTCHR BR DLBKEX 2$: .ENDC ;DTE20P CALL @TTYIPC(I) DLBKEX: POP RTI DLOBK: MOV (H),H ;GET HARDWARE INDEX OF INTERRUPTING UNIT TST DLOAC(H) BEQ DLBKX1 ;NOT SUPPOSED TO BE TYPING OUT, IGNORE INT DEC DLBC(H) ;GOT ANY MORE CHARACTERS? BLT DLBKX2 ;NO, GO GIVE OUTPUT DONE MOV DLCA(H),-(SP) ;YES, GIVE NEXT CHARACTER MOVB @(SP)+,@DLPB(H) INC DLCA(H) DLBKX1: POP H RTI DLBKX2: PUSH ;OUTPUT DONE MOV DLTYNO(H),I ;GET TTY INDEX OF INTERRUPTING LINE CLR DLOAC(H) ;OUTPUT NO LONGER ACTIVE ON THIS LINE CALL XMTDON BR DLBKEX .SBTTL CLOCK INTERRUPT ;NOTE - IT IS IMPORTANT THAT THIS BE AT A HIGHER INTERRUPT LEVEL THAN THE CHAOS NET CLKBRK: SETOM WAKE ;WAKE UP MAIN LOOP .IFNZ GOULDP PUSH @#PS ;CHECK GOULD LPT CALL GLPBRK ;(LOSES INTERRUPTS) DEC GLPTIM ;TIME TO CHECK GOULD LPT? BGT 13$ ;NOT YET MOV #10.*60.,GLPTIM BIT #%GSNRD,@#GLPCSR ;YES, LOSING? BNE 14$ ;PROBABLY CLR GLPERR ;PROBABLY NOT BR 13$ ;(CAN'T TELL FOR SURE IF %GCON NOT DONE) 14$: MOV @#GLPCSR,GLPERR ;LPT LOSING, TELL 10 CALL GLPRST ;AND MAKE SURE BUFFERS DON'T CHOKE UP .ENDC ;GOULDP 13$: PUSH .IFNZ NDMS ;MODEM SCANNER GETS SHUT OFF SOMEHOW CLR A ;loop over the DM11s, turning them on MOV #NDMS,B 259$: BIT #DMSCN,@DMCSR(A) BEQ 14$ BIT #DMIEN,@DMCSR(A) BNE 15$ 14$: MOV #DMSCN+DMIEN,@DMCSR(A) ;ENABLE SCANNER INTERRUPTS 15$: TST (A)+ ;next DM11 SOB B,259$ ;until all DM11s done .ENDC ;NDMS .IFNZ CHAOSP ;WAKE-UP OUTPUT LINKS IN RE-TRANSMIT DELAY MOV #CHXCHS,I 50$: MOV CHOHWR(I),A ;ADDRESS OF HARDWARE CSR TST CHOSTS(I) ;IF ZERO, IS IDLE, DON'T WANT INTERRUPT ENABLE BEQ 51$ ;NOTE THAT THIS RUNS MASKED HIGHER THAN CHAOS INT LVL BIS #%CATEN,(A) ;RE-ENABLE INTERRUPT IF OFF 51$: .IFNZ CHSBTB BIT #%CATDN,(A) ;TRANSMIT-DONE? BNE 59$ INC CHSIDL(I) ;NO, KEEP TIME-OUT CMP CHSIDL(I),#60. ;IF TRANSMIT-DONE STUCK OFF FOR 1 SECOND, BLO 59$ MOV #%CARST,(A) ; THEN RESET THE INTERFACE ; MOV #%CAREN+%CATEN,(A) ;INTERRUPT ENABLES WILL TURN THEMSELVES BACK ON IF NECESSARY! INC CHSRST(I) ;COUNT NUMBER OF TIMES HAD TO DO THIS 59$: .ENDC ;CHSBTB .IFG CHAOSP-1 TST (I)+ CMP I,#CHXCHS+CHAOSP+CHAOSP BLO 50$ .ENDC ;CHAOSP-1 DEC PULSAR ;TIME TO GENERATE TEST PACKET TO CHAOS NET? BGT 66$ ;NOT YET MOV PULSON,PULSAR ;RE-INITIALIZE COUNTER .REPT CHAOSP ;YES, AWAKEN ALL TRANSMIT INTERRUPT SIDES BIS #%CATEN,@CHOHWR+CHXCHS+<2*.RPCNT> .ENDR .IFNZ TEN11P TST CHOSTS+CHXT11 ;AWAITING BUFFER FROM 10? BNE 65$ ;YES, COUNT TIMEOUT CLR T11TIM ;NO, RESET TIMEOUT 65$: INC T11TIM .ENDC ;TEN11P 66$: DEC 4SEC ;TIME FOR 4-SECOND CLOCK? BGT 90$ MOV #4*60.,4SEC ;YES MOV #*2,I ;INCREMENT ROUTING COSTS 71$: TST SBNTYP(I) ;THIS GUY'S COSTS SUPPOSED TO INCREMENT? BNE 72$ ;NOPE CMP SBNCST(I),#1000 ;DON'T INCREMENT TOO HIGH AND OVERFLOW BHIS 72$ INC SBNCST(I) ;YEP 72$: SUB #2,I BPL 71$ DEC 15SEC ;TIME FOR 15-SECOND CLOCK? (REALLY 16) BGT 90$ MOV #4,15SEC ;YES .REPT CHAOSP ;TELL CABLES TO BROADCAST %CORUT PACKETS SETOM CHXRTF+CHXCHS+<2*.RPCNT> BIS #%CATEN,@CHOHWR+CHXCHS+<2*.RPCNT> .ENDR .IIF NZ ETHERP, SETOM CHXRTF+CHXETH ;TELL ETHERNET TO BROADCAST ROUTING 90$: ;CAN'T DO IT NOW BECAUSE WRONG INTERRUPT LEVEL .ENDC ;CHAOSP .IF DF NDVRBF INC DVRTIM ;TIME OUT DOVER CONNECTION CMP DVRTIM,#15.*60. ;IF IDLE FOR 15 SECONDS, FLUSH BLO 15$ CLR DVRHST CLR DVRMSK 15$: INC DVRRTR ;COUNT UP RETRANSMISSION COUNTER .ENDC ;NDVRBF .IFNZ NDMS ;GOT ANY TTYS WITH MODEM CONTROL? MOV #NFTTY,I ;CHECK FOR HANGUPS 16$: TST DIALED(I) ;HANGUP IN PROGRESS ON THIS LINE? BPL 17$ ;NO INC DIALED(I) ;YES, TIMED OUT? BMI 17$ CLR DIALED(I) ;YUP, LINE IS HUNG UP MOV I,A ;TELL -10 ABOUT IT ASR A TST TTYHNG(I) ;IF THIS IS NEW STATUS FOR 10, BNE 18$ INC HNGSIG ;INDICATE STATUS WAITING 18$: MOV A,TTYHNG(I) ;SAVE THIS LINE'S LATEST STATUS 17$: ADD #2,I CMP I,#LASTTY BLO 16$ .ENDC ;NDMS POP ROR SWR ;LOW BIT OF SWITCHES => DDT BCC CLKEX BPT CLKEX: RTI .IFNZ NDMS .SBTTL MODEM CONTROL ;;; hack multiple DM interrupt vectors .REPT NDMS CONC DM,\.RPCNT+1, 2*.RPCNT .ENDR ;NDMS DMBRK: PUSH MOV (H),A ;get the device offset in A MOV @DMCSR(A),I ;GET ASSOCIATED TTY INDEX BIC #177760,I ;gives us channel (0-17) on this DM11 ;; now add to get offset into table for any DM MOV A,B ;device offset in B, is 2*device number ASL B ASL B ASL B ;multiply by 8 for offset in B ADD B,I ;add to I for offset for this channel ASL I ;now get word offset in I by shifting ;; get index into map between DM channels and TTY indices MOV M2LMAP(I),I BEQ 90$ ;EXIT IF THIS LINE NOT UNDER MODEM CONTROL ; TST @DMCSR(A) .SEE DMRNG ; BPL 10$ ; TST DIALED(I) ;RINGING. IS LINE DIALED UP ALREADY? ; BNE 10$ ;YES, NOT SUPPOSED TO BE RINGING ; MOV #LINENB+LINDTR,@DMLSR(A) ;ANSWER THE PHONE 10$: BIT #LINCTS,@DMLSR(A) ;DO WE HAVE CLEAR-TO-SEND? BEQ 20$ ;NO TST DIALED(I) ;YES, WHAT WAS PREVIOUS STATE? BEQ 13$ ;WAS OFF, THIS IS A DIALUP BPL 90$ ;WAS ON, IGNORE NEG DIALED(I) ;WAS HANGING UP, ABORT IT BR 90$ 13$: INC DIALED(I) ;LINE IS NOW DIALED UP TST DMINI ;IF GETTING INITIAL STATE, BNE 90$ ;DON'T HACK AUTOSPEED TST AUTOSP(I) ;IF IT HAS AUTOSPEED, BEQ 90$ MOV HDWR(I),H ;HACK THAT CALL ASPMD BR 90$ 20$: TST DIALED(I) ;CTS DROPPED BMI 90$ ;ALREADY KNOWN ABOUT, IGNORE MOV #-HNGDLY,DIALED(I) ;OTHERWISE START HANGUP TIMEOUT 90$: BIC #DMDON,@DMCSR(A) ;RESTART SCANNER POP POP H RTI .ENDC ;NDMS .IFNZ GOULDP .SBTTL GOULD PRINTER P.I. LEVEL GLPBRK: BIT #%GSBSY,@#GLPCSR BEQ 1$ RTI ;LPT BUSY, WAIT 1$: BIT #%GSDON,@#GLPCSR BNE 2$ RTI ;LPT BUSY OTHER FLAVOR 2$: PUSH BIT #%GSERR,@#GLPCSR ;LPT LOSING? BEQ GLPBR1 CALL GLPRST ;YUP, RESET THE BUFFERS MOV @#GLPCSR,GLPERR ;AND TELL 10 GLPOFF: CLR GLPOAC ;HERE TO STOP P.I. MOV #%GCIOF,@#GLPCSR MOV #5000.,A ;LPT SOMETIMES BUSY FOR A WHILE 1$: BIT #%GSBSY,@#GLPCSR ;HAVE TO WAIT SO TONER PUMPS WILL BEQ 2$ ;REALLY TURN OFF SOB A,1$ 2$: MOV #%GCOFF,@#GLPCSR GLPEX: POP RTI GLPFIN: MOV #%GBIDL,GB.STA(H) ;DONE WITH THIS BUFFER MOV GB.NXT(H),H ;CHECK NEXT MOV H,GLPOOP GLPBR1: MOV GLPOOP,H ;CHECK ON BUFFERS CMP GB.STA(H),#%GBDMA ;FINISH DMA XFER? BEQ GLPFIN ;YES CMP GB.STA(H),#%GBWRT ;QUEUED OR ALREADY ACTIVE AT P.I.? BLT GLPOFF ;NO, STOP MOV #%GBPI,GB.STA(H) ;YES, ACTIVATE IT AT P.I. TST GB.FF(H) ;NEED FF? BEQ 1$ MOV #%GCFF,@#GLPCSR ;YES CLR GB.FF(H) BR GLPEX 1$: TST GB.NL(H) ;NEED BLANK LINES? BEQ 2$ DEC GB.NL(H) ;YES, GIVE ONE MOV #%GCADV,@#GLPCSR BR GLPEX 2$: MOV H,B ;SET UP TEXT ADDR ADD #GB.DAT,B MOV GB.PNT(H),A ;SET UP TEXT WORD COUNT NEG A MOV A,@#GLPWC MOV B,@#GLPCA ;START XFER MOV #%GBDMA,GB.STA(H) ;FLAG BUFFER ACTIVE AT DMA LEVEL BR GLPEX GLPRST: PUSH H MOV #GLPBFF,H ;FLUSH ALL BUFFERS MOV H,GLPOOP MOV H,GLPOIP 3$: CLR (H)+ MOV (H),H CMP H,#GLPBFF BNE 3$ MOV #60.*10.,GLPTIM ;SET TIMEOUT POP H RET .ENDC ;GOULDP .IFNZ CHAOSP .SBTTL CHAOSNET ROUTINES ;ALL ROUTINES ON THIS PAGE CALLED WITH INTERRUPTS MASKED, INDEX IN I. ;REFILL FROM CHAOS INTERFACE CHSRFL: BIS #%CAREN,@CHIHWR(I) ;TURN ON RECEIVER INTERRUPTS RET ;WILL NOTICE INPUT LATER .IFNZ DL10P ;LOOPS BACK TO HERE WHEN DISCARDING A PACKET DLCRF1: CMP (SP)+,(SP)+ ;POP POP A INC DLCSS1(A) ;2 ;INDICATE BUFFER HAS BEEN COPIED BIS #DLX10I,DLXCSR ;AND INTERRUPT THE PDP10 ;DROP INTO DLCRFL ;REFILL FROM DL10 DLCRFL: CALL DLCCHK ;SEE IF DL10 IS DISABLED BNE 99$ ;BRANCH IF YES MOV #2,A ;CHECK BOTH 10 TO 11 BUFFERS SO CAN'T GET OUT OF PHASE WITH 10 10$: CMP DLCSS1(A),#1 ;10 SAYS BUFFER READY? BEQ 11$ ;YES SUB #2,A ;NO, TRY NEXT BPL 10$ BR 99$ ;NONE READY 11$: PUSH A ;SAVE CURRENT 10 TO 11 BUFFER ADD #DLCSP1,A ;OUTPUT READY, GET IT MOV #DLCIBF,B ;COPY INTO BUFFER .REPT PKHDW ;FIRST GET HEADER MOV (A),(B)+ .ENDR PUSH CALL CHSIHD ;PROCESS HEADER, GET LENGTH, DEST BVS DLCRF1 ;BRANCH IF PACKET NO GOOD POP PUSH C SUB CHIHDL(I),C ;GET NUMBER OF DATA WORDS TO FOLLOW CALL MOVHD ;MOVE THOSE WORDS POP ;RESTORE LENGTH, 10 TO 11 BUFFER NUMBER INC DLCSS1(A) ;2 ;INDICATE BUFFER HAS BEEN COPIED BIS #DLX10I,DLXCSR ;AND INTERRUPT THE PDP10 TST B ;SWAB IF NOT TO 10-COMPATIBLE DEST CALL SWAB10 INC CHISTS(I) ;INDICATE BUFFER READY TO SEND 99$: RET ;TRANSMIT TO DL10 OUTPUT SINK ;REQUIRES I TO BE SET UP, SMASHES ALL REGS. DLCXMT: CALL DLCCHK ;DL10 DISABLED? BNE 70$ ;YES, DISCARD PACKET MOV DLCRBN,A ;GET CURRENT 11 TO 10 BUFFER NUMBER CMP DLCRS1(A),#1 ;BUFFER READY? BNE 80$ ;NO, WAIT MOV CHOINX+CHXDLC,D ;GET ADDRESS OF BUFFER TO BE SENT OVER MOV CHILNG(D),C ;AND LENGTH MOV CHIBFP(D),D MOV A,H ;GET POINTER TO DL10 MAGIC IDPB WORD ADD #DLCRP1,H CALL MOVDH ;COPY WORDS INTO PDP10 INC DLCRS1(A) ;SIGNAL DATA AVAILABLE TO PDP10 BIS #DLX10I,DLXCSR ;AND INTERRUPT IT MOV DLCNXT(A),DLCRBN ;SWITCH BUFFERS 70$: JMP CHSODN ;TRANSMISSION IS DONE ALREADY 80$: MOV #1,CHOSTS+CHXDLC ;TRANSMISSION AWAITING BUFFER FROM 10 RET ;CALL HERE WHEN DL10 INTERRUPTS, CLOBBERS ALL. DLCWAK: MASK 5 TST CHOSTS+CHXDLC ;DL10 HUNG ON TRANSMIT? BEQ 10$ MOV #CHXDLC,I ;YES, WAKE IT UP CALL DLCXMT 10$: TST CHISTS+CHXDLC ;DL10 INPUT ACTIVE? BNE 20$ MOV #CHXDLC,I ;NO, TRY TO GET SOME CALL DLCRFL TST CHISTS(I) ;GOT SOME? BLE 20$ CALL CHSOUT ;YES, START TRANSMISSION 20$: CALL CHSRUN ;DO ANYTHING ELSE REQUIRED UNMASK RET ;RETURN 'NE' IF DL10 IS DISABLED, BASHES NOTHING. DLCCHK: TST DLXOFF BNE 99$ TST NO.ITS BNE 99$ TST DLCINI ;RE-INITIALIZE? BEQ 99$ ;NO, EVERYTHING IS OK. CLR DLCRBN ;YES TST CHOSTS+CHXDLC ;WAS OUTPUT HUNG ON DL10? BEQ 90$ PUSH ;YES, SIGNAL OUTPUT DONE ON DL10 MOV #CHXDLC,I CALL CHSODN POP 90$: CLR DLCINI ;SIGNAL INIT DONE, RETURN 'EQ' 99$: RET .ENDC ;DL10P ;FAST BLOCK MOVE ;THESE CAN MOVE AT MOST 256. WORDS ;MOV (H),(D)+ ;SOB C,.-2 MOVHD: SUB #256.,C ;GET -#WDS LESS THAN MAXIMUM ADD C,C ;CONVERT TO BYTES SUB C,PC ;JUMP INTO MOVE TABLE .REPT 256. MOV (H),(D)+ .ENDR RET ;MOV (D)+,(H) ;SOB C,.-2 MOVDH: SUB #256.,C ;GET -#WDS LESS THAN MAXIMUM ADD C,C ;CONVERT TO BYTES SUB C,PC ;JUMP INTO MOVE TABLE .REPT 256. MOV (D)+,(H) .ENDR RET .IFNZ TEN11P ;REFILL FROM TEN-11 INTERFACE T11RFL: CALL T11CHK ;CHECK FOR DISABLE BNE 99$ ;BRANCH IF DISABLED MOV T11IBP,A TST T11IBA ;WAS INPUT BUFFER IN USE? BEQ 10$ CLR (A)+ ;YES, INDICATE BUFFER IS NOW EMPTY CLR (A) CLR T11IBA ADD #T11BFL-2,A ;ADVANCE POINTER CMP A,#T11IBE BLO 7$ MOV #T11IBF,A 7$: MOV A,T11IBP 10$: TST (A) ;INPUT BUFFER CONTAIN A PACKET? BEQ 99$ ;NO SETOM T11IBA ;YES, INPUT BUFFER NOW ACTIVE ADD #8,A ;GET INPUT FROM PDP10 MOV A,CHIBFP+CHXT11 ;AS CURRENT INPUT BUFFER CALL CHSIHD ;PROCESS THE HEADER BVS T11RFL ;BRANCH IF PACKET NO GOOD PUSH ;COMPUTE CHECKSUM BEFORE SWABBING INC C ;C GETS NUMBER OF 32-BIT WORDS ASR C CLR D ;CLEAR LOW WORD OF CHECKSUM CLR H ;CLEAR HIGH WORD OF CHECKSUM SUB #PKFCMS+1,PKFC(A) ;DECREMENT FWD COUNT (IS HIGH END OF WORD) ;FWD COUNT HAS TO BE PUT BACK FOR CHECKSUM COMPUTATION 21$: ADD (A)+,H ;ADD HIGH HALFWORD TO HIGH SUM ADD (A)+,D ;ADD LOW HALFWORD TO LOW SUM ADC H ;CARRY INTO HIGH SUM MOV D,B ;NOW ROTATE RIGHT DOUBLE ROR B ROR H ROR D SOB C,21$ MOV T11IBP,A ;NOW COMPARE CHECKSUM CMP H,4(A) BNE 30$ CMP D,6(A) BNE 30$ POP ADD #PKFCMS+1,PKFC(A) ;INCREMENT FWD COUNT (IS HIGH END OF WORD) TST B ;SWAB IF NOT TO 10-COMPATIBLE DEST CALL SWAB10 INC CHISTS(I) ;INDICATE BUFFER READY TO SEND 99$: RET 30$: POP ;CHECKSUM ERROR INC T11CKE ;COUNT CHECKSUM ERRORS BR T11RFL ;AND IGNORE PACKET ;TRANSMIT TO TEN11 OUTPUT SINK ;REQUIRES I TO BE SET UP, SMASHES ALL REGS. T11XMT: CALL T11CHK ;TEN11 DISABLED? BNE 70$ ;YES, DISCARD PACKET TST @T11OBP ;OUTPUT BUFFER EMPTY? BNE 80$ ;NO, WAIT MOV CHOINX+CHXT11,D ;GET ADDRESS OF BUFFER TO BE SENT OVER MOV CHIBFP(D),B MOV CHILNG(D),C ;AND LENGTH MOV PKNBYT(B),A BIT #1,A ;IF ODD NUMBER OF BYTES, CLEAR THE EXTRA ONE BEQ 5$ BIC #PKNBMS,A ADD B,A CLRB PKDAT-1(A) ;NOTE, AT THIS POINT BYTES ARE SWAPPED 5$: MOV T11OBP,A ;COPY INTO TEN11 OUTPUT BUFFER ADD #8,A PUSH 10$: MOV (B)+,(A)+ SOB C,10$ MOV (SP),C ;NOW COMPUTE CHECKSUM INC C ;C GETS NUMBER OF 32-BIT WORDS ASR C BCS 11$ CLR (A)+ ;IF ODD NUMBER OF 16-BIT WORDS, CLEAR THE EXTRA ONE 11$: CLR D ;CLEAR LOW WORD OF CHECKSUM CLR H ;CLEAR HIGH WORD OF CHECKSUM MOV T11OBP,A ADD #8,A 21$: ADD (A)+,H ;ADD HIGH HALFWORD TO HIGH SUM ADD (A)+,D ;ADD LOW HALFWORD TO LOW SUM ADC H ;CARRY INTO HIGH SUM MOV D,B ;NOW ROTATE RIGHT DOUBLE ROR B ROR H ROR D SOB C,21$ MOV T11OBP,A ;STORE CHECKSUM INTO OUTPUT BUFFER MOV H,4(A) MOV D,6(A) POP SETOM (A) ;SIGNAL PRESENCE OF PACKET TO PDP10 ADD #T11BFL,A ;ADVANCE POINTER CMP A,#T11OBE BLO 30$ MOV #T11OBF,A 30$: MOV A,T11OBP 70$: CLR T11TIM ;NO TIMEOUT, 10 IS TAKING PACKETS JMP CHSODN ;TRANSMISSION IS DONE ALREADY 80$: MOV #1,CHOSTS+CHXT11 ;TRANSMISSION AWAITING BUFFER FROM 10 RET ;WHACK YOUR TEN11 T11WAK: MASK 5 MOV #CHXT11,I CALL T11CHK ;IS 10 UP? BNE 30$ ;IT'S DOWN, PUNT IT TST CHOSTS(I) ;TEN11 HUNG ON TRANSMIT? BEQ 10$ CALL T11XMT ;YES, WAKE IT UP 10$: TST CHISTS+CHXT11 ;TEN11 INPUT ACTIVE? BNE 20$ MOV #CHXT11,I ;NO, TRY TO GET SOME CALL T11RFL TST CHISTS(I) ;GOT SOME? BLE 20$ CALL CHSOUT ;YES, START TRANSMISSION 20$: CALL CHSRUN ;DO ANYTHING ELSE REQUIRED UNMASK RET 30$: TST CHOSTS(I) ;TRANSMITTING TO DEAD TEN-11? BEQ 20$ CLR T11TIM ;YES, FLUSH IT CALL CHSODN BR 20$ ;CHECK TEN-11 INTERFACE, DO RESET IF NECESSARY, RETURN 'NE' IF DISABLED. ;SMASHES NOTHING. T11CHK: CMP T11TIM,#5*60. ;10 TAKING 5 SECONDS TO RESPOND? BLO 5$ SETOM T11I10 ;YES, DECLARE IT DOWN, REINITIALIZE PROTOCOL 5$: TST T11I10 ;IS 10 DONE INITIALIZING? BNE 99$ ;NO, DO NOTHING TST T11I11 ;ARE WE SUPPOSED TO INITIALIZE? BEQ 99$ ;NO, IT'S OK MOV #T11OBF,T11OBP ;YES, REINITIALIZE POINTERS MOV #T11IBF,T11IBP PUSH A MOV #T11OBF,A ;INITIALIZE INPUT AND OUTPUT BUFFER HEADERS 10$: CLR (A)+ ;CLEAR INTER-MACHINE SIGNAL WORD CLR (A)+ ADD #T11BFL-4,A ;SKIP THE REMAINING WORDS CMP A,#T11IBE BLO 10$ CLR T11IBA ;IDLE THE INPUT POP A TST CHOSTS+CHXT11 ;WAS OUTPUT HUNG ON TEN11? BEQ 90$ PUSH ;YES, SIGNAL OUTPUT DONE ON TEN11 MOV #CHXT11,I CALL CHSODN POP 90$: CLR T11I11 ;SIGNAL INIT DONE, RETURN 'EQ' CLR T11I11+2 99$: RET .ENDC ;TEN11P ;THIS ROUTINE PROCESSES THE HEADER OF PACKET IN INPUT BUFFER FOR SOURCE I ;RETURN DESTINATION OUTPUT SINK INDEX IN B (-1 IF THIS IS FOR US (PDP11 ITSELF)), ;PACKET BUFFER POINTER IN A, AND LENGTH IN WORDS IN C. ;RETURNS WITH OVERFLOW SET IF PACKET IS DISCARDED BECAUSE OF ;TOO MUCH FORWARDING, BAD ADDRESS, TOO BIG, CRUFTY, ETC. ;OTHERWISE RETURNS WITH MINUS INDICATOR SET IF PACKET DIRECTED TO 11. CHSIHD: ADD #1,NPKSI(I) ;COUNT PACKETS IN FROM THIS SOURCE ADC HPKSI(I) MOV CHIBFP(I),A ;POINTER TO PACKET TSTB (A) ;CHECK FOR MUPPET BNE CHSIHB ;DISCARD, WE DON'T SUPPORT THEM MOV #PKHDW,CHIHDL(I) ;SET HEADER LENGTH ADD #PKFCMS+1,PKFC(A) ;INCREMENT FWD COUNT (IS HIGH END OF WORD) BCS CHSIHB ;BRANCH IF FORWARDING LOOP MOV PKNBYT(A),C ;GET BYTE COUNT BIC #PKNBMS,C CMP C,#DATMAX BHI CHSIHB ;TOO LONG, LOSES INC C ;MAKE WORD COUNT ASR C ADD CHIHDL(I),C ;ADD IN LENGTH OF HEADER MOV C,CHILNG(I) ;SAVE FOR LATER USE ;; NOW ROUTE THIS PACKET MOV #-1,B ;MAGIC INDEX MEANING "MYSELF" MOV PKDHST(A),D ;GET DESTINATION ADDRESS ;HERE WE HAVE HAIR FOR MULTIPLE CHAOSNETS .REPT CHAOSP CONC ,\.RPCNT ;ADDRESSED TO PDP11 ITSELF? BEQ 50$ ;YES, LET CHSRUN HANDLE IT LATER .ENDR ;CHAOSP CMPB PKOP(A),#%CORUT ;ROUTING INFO PACKET? BEQ 40$ ;YES, ADDRESS TO PDP11 TST USECBL ;SUPPOSED TO USE CABLE EVEN TO TALK TO SELF? BEQ 20$ CMP I,#CHXCHS ;YES, IS THIS COMING FROM CABLE? BHIS 20$ ;YES, ROUTE REGULAR WAY MOV #CHXCHS,B ;NO, SEND TO SELF ON FIRST CABLE MOV #CHAD0,D BR 39$ 20$: MOVB PKDHST+1(A),B ;GET SUBNET ADDRESSED TO CMP B,#NSUBNT BLO 21$ CLR B ;OUT OF RANGE, USE 0 21$: ASL B ;MAKE INDEX INTO SUBNET TABLES TST SBNTYP(B) ;IS THIS A DIRECT HARDWARE CONNECTION? BGT 38$ ;YES, SEND TO IT MOV SBNADR(B),D ;NO, GO VIA GATEWAY BEQ CHSIRF ;HAVEN'T GOT A GATEWAY, AND BROADCAST CODE NOT WORKING YET MOVB SBNADR+1(B),B ;GET SUBNET GATEWAY IS ON ASL B ;MAKE INDEX INTO TABLES CMP B,#NSUBNT*2 BHIS CHSIRF ;OUT OF RANGE, CAN'T GET THERE FROM HERE TST SBNTYP(B) ;IS THIS A DIRECT CONNECTION? BLE CHSIRF ;NO, CAN'T GET THERE FROM HERE (SHOULDN'T HAPPEN!) 38$: MOV SBNADR(B),B ;GET SINK INDEX 39$: MOV D,CHICBA(I) ;STORE CABLE ADDRESS OF IMMEDIATE DEST (GATEWAY) .IIF NDF NDVRBF, 50$: ;IF NO DOVER, ALL TO-11 PACKETS COME HERE 40$: MOV B,CHIOUX(I) ;STORE SINK INDEX, SET INDICATORS RET ;NOTE THAT MOV CLEARS OVERFLOW .IF DF NDVRBF 50$: CMP PKDIND(A),DVRLIX ;DIRECTED TO DOVER? BNE 40$ ;NO, TO 11 CMP PKSHST(A),DVRHST BNE 40$ ;NOT DOVER-CONNECTED HOST CMP PKSIND(A),DVRIDX BNE 40$ ;RIGHT HOST, WRONG PROCESS MOV #CHXDVR,B ;ROUTE PACKET TO DOVER GATEWAY BR 40$ .ENDC ;NDVRBF ;HERE FOR ROUTING FAILURE. METER, RETURN WITH OVERFLOW SET. CHSIRF: INC NPKSRF MOV B,RFSBNT ;SAVE 2* SUBNET TRYING TO GET TO ;FALL INTO CHSIHB ;HERE WHEN CHSIHD SEES A GARBAGE PACKET. RETURN WITH OVERFLOW SET. CHSIHB: ADD #1,NPKSBD(I) ;GOD-DAMN BRAIN-DAMAGE ADC HPKSBD(I) SEV RET ;SWAB PACKET COMING FROM PDP-10 OR ETHERNET (BYTES LEFT TO RIGHT) ;IF GOING TO INCOMPATIBLE DESTINATION. CALL RIGHT AFTER CHSIHD. SWAB10: BMI CHSSWB ;SWAB IF TO-11 CMP CHOXMT(B),#CHSXMT ;CHECK DESTINATION TYPE BEQ CHSSWB ;PDP11 OR CHAOSNET, SWAB IT OUT 5$: RET ;PDP10 OR ETHERNET, LEAVE ALONE ;SWAB PACKET COMING FROM PDP-11 OR CHAOSNET (BYTES RIGHT TO LEFT) ;IF GOING TO INCOMPATIBLE DESTINATION. CALL RIGHT AFTER CHSIHD. SWAB11=. BMI 5$ ;RETURN IF TO-11 CMP CHOXMT(B),#CHSXMT ;CHECK DESTINATION TYPE BEQ 5$ ;PDP11 OR CHAOSNET, LEAVE ALONE ;PDP10 OR ETHERNET, SWAB IT OUT ;DROPS THROUGH INTO CHSSWB ;THIS ROUTINE SWABS THE PACKET FOR THE SOURCE IN I. ;CALLED WITH NUMBER OF WORDS IN PACKET IN C. ;CLOBBERS A, C, AND D. ;SUITABLE FOR CALLING RIGHT AFTER CHSIHD RETURNS. CHSSWB: MOV CHIBFP(I),A ;ADDRESS OF PACKET SUB CHIHDL(I),C ;GET LENGTH OF DATA AREA IN WORDS BLE 99$ ;EMPTY MOVB PKOP(A),D ;GET OPCODE BPL 5$ ;BRANCH IF NON-DATA BIT #100,D ;CHECK FOR BINARY DATA BEQ 10$ ;NO, GO SWAB 99$: RET 5$: TSTB CHSBIN(D) ;CONTROL, LOOK UP OPCODE BNE 99$ ;BINARY, NO SWAB 10$: ADD CHIHDL(I),A ;POINT TO DATA AREA OF BUFFER ADD CHIHDL(I),A ;BYTES, WATSON, BYTES! SUB #PKTMXW,C ;GET -#WDS LESS THAN MAXIMUM ADD C,C ;CONVERT TO BYTES SUB C,PC ;JUMP INTO SWAB TABLE .REPT PKTMXW SWAB (A)+ .ENDR RET ;BYTE TABLE INDEXED BY OPCODE, NON-ZERO IF BINARY ;BINARY OPERATIONS ARE 2 (%COOPN), 7 (%COSTS), 10 (%CORUT) CHSBIN: .BYTE 0,0,2,0,0,0,0,7,10,0,0,0,0,0 .BYTE 0,0 ;SPARES IN CASE MORE OPCODES ADDED .EVEN ;TRANSMIT PACKET FROM INPUT SOURCE I TO OUTPUT SINK, IN B. ;SMASHES ALL REGISTERS. CHISTS(I), CHIOUX(I), CHICBA(I) MUST BE ALREADY SET UP. CHSOUT: TST B ;THIS DESTINED TO PDP11? BMI CHSOUX ;YES, LET CHSRUN PICK IT UP LATER TST CHOSTS(B) ;IS SINK BUSY? BNE CHSOUX ;YES, CAN'T SEND NOW, WILL TRY AGAIN LATER NEG CHISTS(I) ;NO, SET SOURCE STATUS TO CONNECTED MOV I,CHOINX(B) ;CONNECT SINK TO SOURCE MOV B,I ;SET UP SINK INDEX ADD #1,NPKSO(I) ADC HPKSO(I) JMP @CHOXMT(I) ;GO START TRANSMISSION TO SINK ;CALL HERE WHEN OUTPUT IS DONE ON SINK I. CHSODN: CLR CHOSTS(I) ;IDLE THE SINK PUSH I MOV CHOINX(I),I ;GET CORRESPONDING SOURCE CLR CHISTS(I) ;IDLE IT CALL @CHIRFL(I) ;TELL SOURCE IT'S DONE, TRY TO GET MORE INPUT POP I CHSOUX: RET ;CALL HERE AFTER EACH PACKET TRANSFER TO INITIATE AS MANY ADDITIONAL TRANSFERS ;AS POSSIBLE. BASHES ALL REGISTERS. ON DL10 AND TEN11, WE COULD ACTUALLY DO SEVERAL ;TRANSFERS BEFORE RETURNING. CHSRUN: .IF DF NDVRBF CALL DVRRFL ;WAKE UP DOVER, MIGHT BE TIME TO RETRANSMIT .ENDC ;NDVRBF MOV #*2,I ;SCAN ALL INPUT SOURCES CHSRN1: TST WAKE ;GIVE UP IF CLOCK HAS TICKED, LET TTYS RUN BNE CHSOUX TST CHISTS(I) ;IS THIS SOURCE LOOKING FOR A SINK? BLE CHSRN3 CHSRN2: MOV CHIOUX(I),B ;GET SINK IT WANTS TO SEND TO BMI FOR11 ;BRANCH IF FOR PDP11 TST CHOSTS(B) ;SINK AVAILABLE? BNE CHSRN3 ;NO, LET INPUT SIT CALL CHSOUT ;YES, ATTEMPT TO TRANSMIT BR CHSRUN ;LOOK FOR MORE WORK CHSRN3: SUB #2,I ;NEXT INPUT SOURCE BGE CHSRN1 RET ;NOTHING LEFT TO DO FOR11: MOV CHIBFP(I),A ;PACKET FOR PDP11, CHECK IT OUT MOVB PKOP(A),B ;GET OPCODE CMP B,#%CORUT ;IF ROUTING INFO, GOBBLE IT BEQ CHARUT CMP B,#%CORFC ;ALL WE KNOW IS RFC TO CERTAIN CONTACT NAMES BNE FOR11J ;BARF AT JUNK PACKETS CALL SERVE ;RUN THE SERVER BEQ FOR11X ;IT DIDN'T LIKE IT FOR11R: PUSH ;INTERCHANGE SOURCE AND DESTINATION MOV PKSHST(A),PKDHST(A) MOV PKSIND(A),PKDIND(A) POP CALL CHSIHD ;ROUTE BVS FOR11X ;NO GOOD, FLUSH (SOURCE IN PACKET WAS WRONG) CALL SWAB11 ;SWAB IF GOING TO 11-INCOMPATIBLE DEST BR CHSRN2 ;FIRE IT OFF (CHISTS IS ALREADY 1) FOR11X: CLR CHISTS(I) ;DISCARD THIS PACKET CALL @CHIRFL(I) BR CHSRUN ;LOOK FOR MORE WORK ;PACKET FROM RANDOM PLACE DIRECTED TO 11, TELL HIM TO GO AWAY FOR11J: CMP B,#%COLOS ;DON'T BARF AT LOS PACKETS BEQ FOR11X MOV #<%COLOS*400>,(A) MOV #6$-5$-1,PKNBYT(A) MOV #5$,B MOV A,C ADD #PKDAT,C 1$: MOVB (B)+,(C)+ BNE 1$ BR FOR11R ;SEND OFF THE LOS 5$: .ASCIZ /Packet unrecognized by gateway-11/ 6$: .EVEN ;ROUTING PACKET CHARUT: MOV CHILNG(I),C ;GET NUMBER OF DATA WORDS SUB #PKHDW,C ASR C ;MAKE NUMBER OF 2 WORD PAIRS BEQ FOR11X ;MIGHT BE ZERO-LENGTH MOV A,D ADD #PKDAT,D ;POINT TO START OF PACKET'S DATA 61$: MOV (D)+,B ;GET SUBNET BEING TALKED ABOUT CMP B,#NSUBNT ;ONE WE KNOW ABOUT? BHIS 62$ ;NO, FORGET IT ASL B ;MAKE WORD INDEX TST SBNTYP(B) ;IS THIS AN AUTO ROUTING TYPE SUBNET? BNE 62$ ;NO, DON'T MUNG OUR FIXED ROUTING INFO CMP (D),SBNCST(B) ;COMPARE COSTS BHI 62$ ;NEW ONE WORSE (IF EQUAL, SWITCH TO EQUALIZE LOAD) MOV (D),SBNCST(B) ;SAVE BEST COST MOV PKSHST(A),SBNADR(B) ;AND HOST ADDRESS THIS CAME FROM AS BEST BET 62$: TST (D)+ ;SKIP COST SOB C,61$ BR FOR11X ;DONE WITH PACKET .SBTTL CHAOS NET SERVERS ;CALLED WITH PACKET IN A. ;MUST PRESERVE A,I. ;RETURN 'EQ' IF NO GOOD, 'NE' IF MODIFIED PACKET TO BE RETURNED TO SOURCE ;CURRENTLY WE SERVE THE FOLLOWING CONTACT NAMES: ; STATUS - RETURNS ANS WITH THE NAME OF THE MACHINE, LATER WILL HAVE OTHER DATA ; PULSAR - RETURNS ANS WITH DATA OF 1 BYTE, VALUE OF PULSON AS AN ASCII DIGIT, ; I.E. "0" MEANS OFF, "1" MEANS 60 PER SECOND, ETC. ; IF CONTACT NAME IN RFC IS FOLLOWED BY A SPACE AND AN ASCII DIGIT, ; SETS PULSON TO THAT STATUS. ; DOVER - DOVER PROTOCOL TRANSLATOR ;NOTE THAT WE DON'T USE THE MOST WINNING STRING COMPARE IN THE WORLD, ;THIS CODE ASSUMES IT DOESN'T MATTER WHAT HAPPENS IF AN RFC TO ;AN UNKNOWN CONTACT NAME IS DONE, AS LONG AS THE 11 DOESN'T CRASH. SERVE: MOV #SRVTBL,B ;ADDRESS OF SERVER TABLE 10$: MOV (B)+,D ;ADDRESS OF CONTACT NAME FOR THAT SERVER BEQ 99$ ;EXIT IF TABLE EXHAUSTED, 'EQ' IN COND CODE MOV A,C ADD #PKDAT,C ;ADDRESS OF CONTACT NAME IN THIS RFC 11$: TSTB (D) ;END OF STRING? BEQ 20$ ;YUP, RUN THIS SERVER CMPB (C)+,(D)+ ;DO STRING COMPARE BEQ 11$ ;MATCHES TST (B)+ ;DOESN'T MATCH, TRY NEXT BR 10$ 99$: RET 20$: JMP @(B)+ ;CALL SERVER, IT CAN RETURN EQ OR NE SRVTBL: .WORD 1$,STSSRV ;STATUS - RETURN HOST NAME AND METERS .WORD 2$,PLSSRV ;PULSAR - SET AND GET PULSAR RATE .IIF DF NDVRBF, .WORD 3$,DVROPN ;DOVER - DOVER PROTOCOL TRANSLATOR .WORD 0 ;END OF TABLE 1$: .ASCIZ /STATUS/ 2$: .ASCIZ /PULSAR/ 3$: .IIF DF NDVRBF, .ASCIZ /DOVER/ .EVEN ;SERVERS MUST PRESERVE A (PACKET), AND I, AND RETURN 'NE' IF TO BE SENT BACK TO SOURCE. ;NOTE THAT C POINTS AT THE NEXT BYTE AFTER THE CONTACT NAME STSSRV: MOV A,B ;RFC TO "STATUS", CHANGE INTO ANS CARRYING APPROPRIATE DATA. MOV #32.+<12.*NCHX>+<24.*CHAOSP>+<12.*ETHERP>,PKNBYT(A) ;SET BYTE LENGTH, CLEAR FORWARDING COUNT ADD #PKDAT,B MOV #HSTNAM,D ;SEND NAME OF HOST MOV #32.,C 45$: MOVB (D)+,(B)+ SOB C,45$ CLR D ;NOW STORE METERING INFO FOR EACH SUBNET 50$: MOV CHXSBN(D),(B)+ ;STORE SUBNET NUMBER+400 MOV #4,(B)+ ;ASSUME NOT A CABLE MOV NPKSI(D),(B)+ MOV HPKSI(D),(B)+ MOV NPKSO(D),(B)+ MOV HPKSO(D),(B)+ .IFNZ ETHERP CMP D,#CHXETH ;ETHERNET HAS SOME OF THESE COUNTERS BNE 55$ MOV #12.,-10.(B) ;THERE ARE 4 MORE DOUBLE-WORDS MOV NPKSAB-CHXCHS(D),(B)+ MOV HPKSAB-CHXCHS(D),(B)+ CLR (B)+ CLR (B)+ MOV NPKSGB-CHXCHS(D),(B)+ MOV HPKSGB-CHXCHS(D),(B)+ MOV NPKSRL-CHXCHS(D),(B)+ MOV HPKSRL-CHXCHS(D),(B)+ BR 59$ .ENDC ;ETHERP 55$: CMP CHIRFL(D),#CHSRFL ;CHAOSNET CABLE? BNE 59$ ;NO, THAT'S ALL MOV #16.,-10.(B) ;YES, THERE ARE 6 MORE DOUBLE-WORDS MOV NPKSAB-CHXCHS(D),(B)+ MOV HPKSAB-CHXCHS(D),(B)+ MOV NPKSLS-CHXCHS(D),(B)+ MOV HPKSLS-CHXCHS(D),(B)+ MOV NPKSGB-CHXCHS(D),(B)+ MOV HPKSGB-CHXCHS(D),(B)+ MOV NPKSRL-CHXCHS(D),(B)+ MOV HPKSRL-CHXCHS(D),(B)+ CLR (B)+ ;I DON'T KEEP TRACK OF BIT COUNT ERRS SEPARATELY CLR (B)+ MOV NPKSBD(D),(B)+ MOV HPKSBD(D),(B)+ 59$: TST (D)+ CMP D,#2*NCHX BLO 50$ RETANS: MOVB #%COANS,PKOP(A) ;RETURN THIS PACKET TO SOURCE AS AN 'ANS' RET ;NOTE CONDITION CODES HAVE 'NE' PLSSRV: MOVB PKNBYT(A),C ;GET BYTE COUNT, SHOULD BE SMALL CMP C,#8 ;6 FOR PULSAR, 1 FOR SPACE, 1 FOR CHARACTER BLO 20$ ;NOT GIVEN AN ARGUMENT, JUST READ STATUS MOVB PKDAT+7(A),C ;YES, GET THE ARGUMENT SUB #'0,C ;CONVERT TO BINARY (CHEAPO!) MOV C,PULSON ;CHANGE PULSON STATUS 20$: MOV #1,PKNBYT(A) ;SET BYTE LENGTH, CLEAR FORWARDING COUNT MOV PULSON,C ;RETURN PULSAR STATUS ADD #'0,C ;IN ASCII MOVB C,PKDAT(A) BR RETANS .SBTTL CHAOSNET INTERRUPT HANDLER ;INTERRUPT HANDLER ENTRIES .REPT CHAOSP CONC CHS,\.RPCNT,BK: JSR I,CHSBRK CHXCHS+<.RPCNT*2> .ENDR ;SUBROUTINE TO ENABLE CHAOSNET INTERFACE IN H,I TO RECEIVE NEXT PACKET CHINXT: MOVB 1(H),A ;GET CSR BITS 9-12 (LOST COUNT) ASR A BIC #-20,A ADD A,NPKSLS-CHXCHS(I) ADC HPKSLS-CHXCHS(I) BIS #%CARCL+%CAREN,(H) ;MAKE READY TO RECEIVE ANOTHER MESSAGE RET ;COMMON CHAOS INTERRUPT ROUTINE CHSBRK: MOV (I),I ;GET SOURCE/SINK INDEX PUSH ;SAVE ALL REGISTERS MOV CHIHWR(I),H ;GET HARDWARE ADDRESS MOV (H),A .SEE CH%CSR ;GET CSR BPL CHSBK1 ;TEST RECEIVE DONE, BRANCH IF NOT .SEE %CARDN ;PALX SCREWS UP IF THIS IS ON PREVIOUS LINE! TST CHISTS(I) ;MAKE SURE INPUT BUFFER IS IDLE BNE CHSBK1 ;BUSY, DON'T LOOK AT RECEIVE DONE NOW BIT #%CAERR,A ;CRC ERROR? BNE CHICRC ;JUMP IF YES MOV CH%RBC(H),C ;BIT COUNT -1 SUB #47.,C ;ADD 1, THEN SUBTRACT 3*16. FOR HARDWARE WORDS .IREPT 4, ASR C ;CONVERT TO NUMBER OF WORDS CMP C,#256. BHI CHIFLS ;THIS CAN ONLY HAPPEN IF HARDWARE BROKEN ADD #CH%RBF,H ;POINT H TO RECEIVE DATA REG MOV CHIBFP(I),D ;COPY PACKET INTO BUFFER CALL MOVHD TST (H) ;READ OUT THE 3 HARDWARE LEADER WORDS CMP (H),(H) SUB #CH%RBF,H ;RESTORE H BIT #%CAERR,(H) ;WAS IT READ CORRECTLY OUT OF RAM? BNE CHIGBG ;NO, GARBAGE CMP CH%RBC(H),#7777 ;WAS PACKET CORRECT LENGTH? BNE CHIGBG ;NO, GARBAGE CALL CHINXT ;DONE WITH HARDWARE, ENABLE FOR NEXT CALL CHSIHD ;PROCESS HEADER, GET LENGTH, DEST BVS CHIFL0 ;BRANCH IF NO GOOD CALL SWAB11 ;SWAB IF NOT GOING TO 11-COMPATIBLE DEST INC CHISTS(I) ;INDICATE BUFFER READY TO SEND PUSH I CALL CHSOUT ;SEND IT OUT POP I MOV CHIHWR(I),H ;RESTORE H TST CHISTS(I) ;INPUT BUFFER STILL BUSY? BEQ CHSBK1 BIC #%CAREN,(H) ;YES, CLEAR RECEIVE INTERRUPT ENABLE BR CHSBK1 ;GO CHECK ON OUTPUT SIDE ;HERE WHEN A PACKET WAS RECEIVED WITHOUT ERROR, BUT AFTER ;READING OUT OF THE RAM, CRC ERROR WAS SET. EITHER THE ;PACKET WAS THE WRONG LENGTH, OR THE RAM FAILED, OR THE ;HARDWARE RANDOMLY CLOBBERED IT. ;WE ALSO GET HERE IF THE BIT COUNT WAS NOT -1 AFTER ALL WORDS WERE READ. CHIGBG: ADD #1,NPKSRL-CHXCHS(I) ;LOG THE ERROR ADC HPKSRL-CHXCHS(I) MOV H,CHSRLH MOV CH%RBC(H),CHSRLC BR CHIFLS ;GO RESET RECEIVER AND CHECK OUTPUT STATUS ;HERE WHEN A PACKET IS RECEIVED WITH A CRC ERROR. DISCARD IT, ;BUT ALSO SAVE IT IN CHSGBF, CHSGBH, CHSGBS, CHSGBC FOR DEBUGGING (IF FTGARB). CHICRC: ADD #1,NPKSGB-CHXCHS(I) ADC HPKSGB-CHXCHS(I) .IFNZ FTGARB MOV H,CHSGBH MOV (H),CHSGBS MOV CH%RBC(H),CHSGBC ADD #CH%RBF,H MOV #CHSGBF,D MOV #PKMAX,C CALL MOVHD SUB #CH%RBF,H ;DROP INTO CHIFLS .ENDC ;FTGARB ;HERE TO IGNORE AN INPUT PACKET AND ENABLE HARDWARE FOR NEXT CHIFLS: CALL CHINXT CHIFL0: INC NPKSIG ;HERE TO CHECK ON TRANSMIT SIDE CHSBK1: TSTB (H) .SEE %CATDN ;TRANSMIT DONE? BPL CHSBKX ;NO, EXIT .IFNZ CHSBTB CLR CHSIDL(I) ;CLEAR TRANSMIT-DONE TIME-OUT .ENDC ;CHSBTB MOV CHOSTS(I),A ;WAS OUTPUT IN PROGRESS? BEQ CHSBK6 ;NO, LOOK FOR OUTPUT CMP A,#2 ;TRANSMIT ABORT DELAY COMPLETED? BEQ 10$ BIT #%CATAB,(H) ;NO, TRANSMIT ABORTED? BEQ CHSBK4 ;NO ADD #1,NPKSAB-CHXCHS(I) ;YES, METER IT, AND SET CHOSTS TO ADC HPKSAB-CHXCHS(I) INC CHOSTS(I) ;2 IF THIS IS FIRST TIME, OR 0 IF SECOND TIME BEQ CHSBK4 ;LOST TWICE IN A ROW, GIVE UP BR CHSBK5 ;TURN OFF INTERRUPT, DELAY FOR A WHILE 10$: MOV #-1,CHOSTS(I) ;TRANSMIT ABORT DELAY COMPLETED, SET CHOSTS TO -1 CALL CHSXM0 ;INITIATE RE-TRANSMISSION (CHOSTS ALREADY SET) BR CHSBKX ;DISMISS CHSBK4: CALL CHSODN ;OUTPUT DONE CHSBK6: PUSH I CALL CHSRUN ;INITIATE MORE TRANSFERS POP I TST CHOSTS(I) ;DID IT INITIATE TRANSMISSION? BNE CHSBKX ;YES, LEAVE INTERRUPT ENABLED. MOV CHOHWR(I),H ;RESTORE H TST CHXRTF(I) ;TIME TO BROADCAST ROUTING INFO? BNE CHORUT ;YES TST PULSON ;IS THIS FEATURE TURNED ON? BEQ CHSBK5 ;NO, FLUSH CMP PULSAR,PULSON ;NOTHING TO DO. TIME FOR A TEST MESSAGE? BNE CHSBK5 ;NOPE, GO IDLE MOV #52525,CH%WBF(H) ;WRITE A PACKET OF 3 HEADER WORDS, 0, 52525 CLR CH%WBF(H) MOV #-1,CH%WBF(H) ;TO HOST -1, WHICH IS NON-EXISTENT CHSBK7: TST CH%XMT(H) ;INITIATE TRANSMISSION, DON'T ENABLE INTERRUPT CHSBK5: BIC #%CATEN,(H) ;GO IDLE, CLEAR TRANSMIT INTERRUPT ENABLE ;HERE TO EXIT FROM CHAOS INTERRUPT. RESTORE REGS AND RETURN FROM INT CHSBKX: POP RTI .IIF NZ CH%WBF-CH%MYN, .ERR FOO CODE ASSUMES CH%WBF = CH%MYN ;BROADCAST A PACKET FULL OF ROUTING INFO, SINCE WE ARE MORE OR LESS A GATEWAY CHORUT: MASK 6 ;INHIBIT CLOCK INTERRUPTS SO COSTS DON'T CHANGE ADD #CH%WBF,H ;ADDRESS WRITE BUFFER MOV #%CORUT*400,(H) ;OPCODE MOV #2*,A ;COUNT SUBNETS WHICH WE KNOW ANYTHING ABOUT (REASONABLE COST) CLR B 5$: CMP SBNCST(A),#1000 BHIS 6$ ADD #4,B ;THIS ONE WILL GENERATE 2 WORDS 6$: SUB #2,A BPL 5$ MOV B,(H) ;BYTE COUNT CLR (H) ;DESTINATION CLR (H) ;.. MOV (H),(H) ;SOURCE = CH%MYN CLR (H) ;SOURCE INDEX CLR (H) ;PACKET NUMBER CLR (H) ;ACK NUMBER MOV #2*,A ;GO THROUGH SUBNET TABLES MOVB 1(H),C ;GET SUBNET THIS IS GOING OUT ON ASL C MOV SBNCST(C),C ;GET COST OF GETTING TO US FROM GUY WHO RECEIVES THIS 10$: CMP SBNCST(A),#1000 ;WAS THIS ONE INCLUDED IN BYTE COUNT? BHIS 11$ ;NO, DON'T PUT IT IN PACKET MOV A,B ;FIRST WORD IS SUBNET NUMBER ASR B MOV B,(H) MOV SBNCST(A),B ;SECOND WORD IS COST ADD C,B ;WHICH MUST INCLUDE COST OF GETTING TO US MOV B,(H) 11$: SUB #2,A ;NEXT SUBNET BPL 10$ CLR (H) ;BROADCAST THIS PACKET SUB #CH%WBF,H ;RESTORE H CLR CHXRTF(I) ;CLEAR REQUEST FOR ROUTING PACKET UNMASK BR CHSBK7 ;FIRE IT OFF, DON'T ENABLE TRANSMIT-DONE INTERRUPT ;INITIATE TRANSMISSION ON CHAOS INTERFACE ;CALL WITH SINK NUMBER IN I, AT PI LEVEL OR MASKED. BASHES ALL REGS. CHSXMT: INC CHOSTS(I) ;SET CHOSTS TO 1, TRANSMIT STARTING CHSXM0: MOV CHOHWR(I),H ;GET HARDWARE ADDRESS MOV CHOINX(I),B ;GET SOURCE SUPPLYING THE PACKET MOV CHIBFP(B),D ;GET PACKET ADDRESS ADD #CH%WBF,H ;ADDRESS THE WRITE BUFFER MOV CHILNG(B),C ;GET WORD COUNT CALL MOVDH ;COPY INTO HARDWARE MOV CHICBA(B),(H) ;STORE CABLE DESTINATION SUB #CH%WBF,H ;RESTORE H TST CH%XMT(H) ;TRIGGER TRANSMISSION BIS #%CATEN,(H) ;ENABLE DONE INTERRUPT RET ;PI LEVEL WILL PICK UP OUTPUT .ENDC ;CHAOSP .IFNZ ETHERP .SBTTL ETHERNET SUPPORT ;ENABLE NEXT ETHERNET PACKET TO COME IN. ;SINCE WE ONLY HAVE ONE BUFFER, THIS SETS UP THE TRANSFER RATHER ;THAN JUST ENABLING THE INTERRUPT AS THE CHAOSNET DOES. ;THAT WOULDN'T WORK ANYWAY, BECAUSE THE HARDWARE IS SO TOTALLY BRAIN-DAMAGED. ETHRFL: MOV CHIHWR(I),H ADD #10,H MOV #-,(H)+ ;- WORD COUNT, +1 FOR HARDWARE BUG MOV #ETHIBF+,(H)+ ;BUFFER ADDRESS MOV #101,(H) ;START, INTERRUPT-ENABLE RET ;INCOMING PUP TOO BIG. WE DON'T HAVE FRAGMENTATION, SO SEND A PUP ERROR REPORT ETHBIG: MOV #ETHIBF+PKDAT,A ;COPY PUP HEADER INTO DATA FIELD MOV A,C MOV #ETHIBF+PKDAT+20.,B .IREPT 10.,< MOV (A)+,(B)+ > MOV #517.,(B)+ ;PACKET TOO LARGE ERROR MOV #DATMAX,(B)+ ;MAX NUMBER OF BYTES ALLOWED MOV #50$,A 5$: MOVB (A)+,(B)+ ;ASCII MESSAGE BNE 5$ INC B ;MESSAGE LENGTH IS EVEN. INCLUDE CHECKSUM IN COUNT. SUB #ETHIBF+PKDAT,B ;GET PUP LENGTH MOV B,(C)+ ;BUILD PUP HEADER NOW MOV #4,(C)+ ;PUP TYPE = ERROR CMP (C)+,(C)+ ;PUP ID SAME .IREPT 3,< MOV 6(C),(C)+ > ;DESTINATION = ORIGINAL SOURCE MOV #,(C)+ ;SOURCE = ME .IREPT 2,< CLR (C)+ > ;SOURCE PORT ZERO CALL ETHOUT ;TRANSMIT JMP ETHINX ;DISMISS ;The ascii message. This isn't as destroyed as it looks. 50$: .ASCIZ/UP Pot oalgr eotf tii n ahCoanstep caek.t/ .EVEN ;INPUT INTERRUPT ETHIBK: PUSH MOV #CHXETH,I MOV CHIHWR(I),H MOV 14(H),A ;PICK UP STATUS CLR 14(H) ;CLEAR RECEIVE INTERRUPT ENABLE CMP ETHIBF+PKDAT-2,#1000 ;TYPE = PUP? BNE ETHIIX ;NO, IGNORE PACKET TST 10(H) ;CHECK RESIDUAL WORD COUNT BEQ ETHBIG ;PACKET TOO BIG, RESPOND WITH PUP ERROR TST A ;CHECK COMBINED INPUT ERRORS BIT BMI 70$ ;ERROR, IGNORE PACKET MOV ETHIBF+PKDAT+10,A ;GET DESTINATION HOST BEQ 5$ ;AND SEE IF BROADCAST OR SELF CMP A,# BNE 11$ ;NO, ROUTE AS REGULAR MESSAGE 5$: CMPB ETHIBF+PKDAT+2,#1 ;PUP TYPE = ECHO-ME? BEQ ETHECO ;YES, ECHO IT (MAYBE TAKE THIS OUT AFTER 11 DEBUGGED) CMPB ETHIBF+PKDAT+2,#200 ;GATEWAY INFORMATION REQUEST? BNE 10$ TST ETHIBF+PKDAT+12 ;NOT REALLY UNLESS DESTINATION SOCKET IS 2 BNE 10$ CMP ETHIBF+PKDAT+14,#2 BNE 10$ TST CHISTS+CHXEGT ;PSEUDO DEVICE AVAILABLE? BNE ETHIIX MOV #ETHIBF+PKDAT+4,A ;YES, SEND HIM SOME INFO MOV #EGTPID,B .IREPT 2,< MOV (A)+,(B)+ > ;COPY PUP ID ADD #6,A ;COPY SOURCE HOST AND SOCKET INTO DESTINATION .IREPT 3,< MOV (A)+,(B)+ > CALL ETHRT1 MOV #CHXETH,I ;I CLOBBERED BY ETHRT1 BR ETHIIX 10$: TST A ;DON'T HARASS REST OF NET WITH BROADCASTS BEQ ETHIIX 11$: MOV #ETHIBF+PKDAT,A ;CHECK THE CHECKSUM CALL PUPCKT BNE 60$ ;BAD, COUNT AS RAM ERROR .IF DF NDVRBF CMP ETHIBF+PKDAT+10,DVRHST ;SEE IF ADDRESSED TO DOVER USER BNE 12$ CMP ETHIBF+PKDAT+14,DVRIDX BNE 12$ CALL DVRPUP ;YES, PROCESS MOV #CHXETH,I BR ETHIIX .ENDC ;NDVRBF ;TRANSLATE PUP AND SEND TO CHAOSNET 12$: MOV #ETHIBF,A ;FILL IN CHAOSNET HEADER MOV #<%COUNC*400>,(A)+ ;PKOP MOV ETHIBF+PKDAT+0,B ;PKNBYT (TOTAL PUP LENGTH = CHAOS DATA LENGTH) INC B ;ROUND UP TO AN EVEN NUMBER ASR B ASL B MOV B,(A)+ MOV ETHIBF+PKDAT+10,(A)+ ;PKDHST MOV ETHIBF+PKDAT+14,(A)+ ;PKDIND (LOW HALF OF PUP PORT) MOV ETHIBF+PKDAT+16,(A)+ ;PKSHST MOV ETHIBF+PKDAT+22,(A)+ ;PKDIND (LOW HALF OF PUP PORT) MOV ETHIBF+PKDAT+6,(A)+ ;PKPKN (LOW HALF OF PUP ID) MOV #100001,(A)+ ;PKACN = PROTOCOL NUMBER CALL CHSIHD ;PROCESS THIS HEADER, GET LENGTH, DEST BVS ETHIIX ;IGNORE IF NO GOOD CALL SWAB10 ;SWAB IF NOT GOING TO 10-COMPATIBLE DEST INC CHISTS(I) ;INDICATE BUFFER READY TO SEND CALL CHSOUT ;SEND IT OUT BR ETHINX ;ETHRFL WILL BE CALLED WHEN NECESSARY 60$: ADD #1,NPKSRL-CHXCHS(I) ;COUNT ERRORS (SOFTWARE CHECKSUM) ADC HPKSRL-CHXCHS(I) BR ETHIIX 70$: ADD #1,NPKSGB-CHXCHS(I) ;COUNT ERRORS (HARDWARE CHECKSUM) ADC HPKSGB-CHXCHS(I) ETHIIX: CALL ETHRFL ;AND READ ANOTHER PACKET ETHINX: POP RTI ;ETHERNET PUP ECHO PROTOCOL ETHECO: MOV #ETHIBF+PKDAT+10,A ;INTERCHANGE SOURCE AND DESTINATION MOV A,B ;I DON'T BOTHER CHECKING CHECKSUM, BUT I DO GENERATE IT .IREPT 3, PUSH (A)+ .IREPT 3,< MOV (A)+,(B)+ > .IREPT 3, POP -(A) MOV #,(A) ;FIX SOURCE TO BE ME INCB ETHIBF+PKDAT+2 ;SET PUP TYPE = 2 (I AM AN ECHO) CALL ETHOUT ;SEND BACK OUT ON THE ETHERNET BR ETHINX ;GENERAL PURPOSE ROUTINE FOR TRANSMITTING INTERNALLY-GENERATED PUPS TO ;THE ETHERNET. FIXES THE DESTINATION ADDRESS (THIS IS HOW OTHER ;HOSTS FIGURE OUT WHAT SUBNET THEY ARE ON!), COMPUTES THE PUP CHECKSUM, ;AND INTERFACES TO THE PACKET SWITCH. CALLED WITH SOURCE INDEX IN I. ;CALL THIS WITH A PACKET THAT ALREADY HAS ITS BYTES IN ETHERNET ORDER. ;BASHES ALL REGISTERS. ETHOUT: MOV CHIBFP(I),A ADD #PKDAT,A ;ADDRESS OF PUP TST 10(A) ;ONLY IF NOT BROADCASTING, BEQ 10$ TSTB 11(A) ;DESTINATION ADDRESS HAVE NETWORK NUMBER? BNE 10$ MOVB #ETHSBN,11(A) ;NO, PUT IT IN 10$: CALL PUPCKS ;INSERT CHECKSUM MOV #CHXETH,B MOV B,CHIOUX(I) INC CHISTS(I) JMP CHSOUT ;INITIATE TRANSMISSION ON ETHER INTERFACE ;CALL WITH SINK NUMBER IN I, AT PI LEVEL OR MASKED. BASHES ALL REGS. ;PACKET IS ALREADY SWABBED INTO ETHERNET BYTE ORDER (REVERSE OF CHAOSNET). ETHXMT: INC CHOSTS(I) ;SET CHOSTS TO 1, TRANSMIT STARTING CLR A ;NO OUTPUT START DELAY ETHXM0: MOV CHOHWR(I),H ;GET HARDWARE ADDRESS MOV CHOINX(I),B ;GET SOURCE SUPPLYING THE PACKET MOV CHIBFP(B),D ;GET PACKET ADDRESS ADD #PKDAT,D ;GET PUP ADDRESS MOV #1000,-(D) ;SMASH LAST 2 WORDS OF CHAOS HEADER. TYPE=PUP MOV #ETHHSN,-(D) ;STORE SOURCE ADDRESS MOVB 14(D),1(D) ;STORE DESTINATION ADDRESS MOV 4(D),B ;GET PUP SIZE IN BYTES ADD #5,B ;CONVERT TO WORDS, ALLOW FOR ETHERNET HEADER ASR B NEG B ;HARDWARE WANTS IT NEGATIVE MOV B,(H)+ ;OUTPUT WORD COUNT MOV D,(H)+ ;OUTPUT BUFFER ADDRESS MOV A,2(H) ;OUTPUT START DELAY MOV #101,(H) ;START OUTPUT, ENABLE INTERRUPT RET ;PI LEVEL WILL FINISH ;OUTPUT DONE/ABORTED INTERRUPT ETHOBK: PUSH MOV #CHXETH,I MOV CHOHWR(I),H MOV 4(H),A ;PICK UP STATUS BEFORE WRITING IT CLR 4(H) ;CLEAR INTERRUPT ENABLE TST A ;CHECK FOR ERROR BPL 10$ ADD #1,NPKSAB-CHXCHS(I) ADC HPKSAB-CHXCHS(I) NEG CHOSTS(I) ;ERROR, ENTER RETRANSMIT MODE BPL 10$ ;ALREADY RETRANSMITTED ONCE, PUNT MOV #25.,A ;WAIT 1 MS (DON'T BOTHER BEING RANDOM) CALL ETHXM0 ;START TRANSMISSION AGAIN BR ETHINX ;AND EXIT 10$: CALL CHSODN ;TRANSMISSION FINISHED CALL CHSRUN ;FIND MORE WORK TO DO BR ETHINX ;DISMISS ;CHECKSUM PUP ADDRESSED BY A. BASHES A,B,C. PUPCKS: CALL PUPCK1 ;COMPUTE CHECKSUM MOV B,(A) ;STORE CHECKSUM RET ;RETURN 'EQ' IF CHECKSUM MATCHES PUPCKT: CALL PUPCK1 ;COMPUTE CHECKSUM CMP (A),#-1 ;PACKET CHECKSUMMED? BEQ 5$ ;NO, ALWAYS MATCH CMP B,(A) ;RETURN WITH CC SET FROM NEW AND OLD CKSMS 5$: RET ;A POINTS AT PACKET, RETURN WITH A -> CHECKSUM AND CHECKSUM IN B. BASH C. PUPCK1: MOV (A),C ;GET LENGTH DEC C ;IN WORDS NOT COUNTING CHECKSUM ASR C CLR B ;BUILD CHECKSUM IN B 10$: ADD (A)+,B ;ONE'S COMPLEMENT ADD ADC B BPL 11$ ;TRANSFER SIGN BIT INTO CARRY SEC 11$: ROL B ;AND LEFT CYCLE SOB C,10$ INC B ;GRONK MINUS ZERO BEQ 15$ DEC B 15$: RET ;BROADCAST ETHERNET GATEWAY INFO ETHRUT: MASK 5 ;ENTER SUITABLE LEVEL FOR HACKING NET TST CHISTS+CHXEGT ;IS THE PSEUDO SOURCE THAT EMITS THE BNE 99$ ; PACKET AVAILABLE? IF NOT, PUNT. CLR CHXRTF+CHXETH ;CLEAR REQUEST FLAG MOV #EGTPID,A CLR (A)+ ;PUP ID ZERO CLR (A)+ CLR (A)+ ;BROADCAST DESTINATION CLR (A)+ ;TO SOCKET 2 MOV #2,(A)+ CALL ETHRT1 ;BUILD AND SEND GATEWAY INFO 99$: UNMASK RET BADSBP: .WORD BADSUB ;POINTER INTO BAD SUBNETS BADSUB: ;SUBNETS THAT SHOULD NOT HAVE INFORMATION SENT ;ABOUT. THIS LIST MUST BE IN INCREASING ORDER ;AND MUST END IN 377. .BYTE 004 ;AI CHAOS 11 pseudo subnet (only AI PDP-10 (RIP) is on this) .BYTE 010 ;Tech Square LCSnet (unused) .BYTE 011 ;Tech Square LCS asynchronous line net (IP) .BYTE 012 ;Tech Square VII LCSnet (IP) .BYTE 014 ;Symbolics: Los Angeles-Chatsworth land line .BYTE 020 ;CHAOS MIT IN subnet (ask JNC) .BYTE 027 ;Experimental asynchronous line net .BYTE 030 ;Experimental radio broadcast net .BYTE 040 ;Symbolics: Tech Square-Vassar St. microwave link .BYTE 041 ;Symbolics: Cambridge-Palo Alto land line .BYTE 042 ;Symbolics: Palo Alto-Chatsworth land line .BYTE 047 ;Symbolics: Cambridge-Chatsworth land line .BYTE 054 ;S-1: 10Mb Ethernet .BYTE 055 ;S-1: Pronet ring .BYTE 056 ;S-1: serial line subnet .BYTE 057 ;S-1: serial line subnet .BYTE 061 ;Symbolics: Cambridge-Cambridge land line .BYTE 062 ;Symbolics: Cambridge-Washington land line .BYTE 064 ;Symbolics: Cambridge-Houston land line .BYTE 070 ;Symbolics: Chatsworth-Westwood land line .BYTE 072 ;Atari: Cambridge-MIT land line .BYTE 073 ;Atari: Cambridge-Sunnyvale land line .REPT 8 .BYTE 377 ;SPARES .ENDR .BYTE 377 .EVEN ETHRT1: MOV #BADSUB,BADSBP ;INITIAL BAD SUBNET POINTER MOV #EGTSBN,A ;FILL IN GATEWAY INFORMATION IN THE PUP CLR I ;I SUBNET*2, A EGTSBN POINTER 10$: ;; FOR EACH SUBNET, .BYTE GATE-NET, TARGET-NET, HOP-COUNT, GATE-HOST CLR B ;FOR NON-GATEWAY, USE 0 AS GATEWAY ADDRESS TST SBNTYP(I) ;HARDWARE CONNECTION? BGT 11$ MOV SBNADR(I),B ;NO, GET GATEWAY ADDRESS 11$: cmpb i,#60 bhi 20$ ;dover, as of 1-Dec-83 can't handle more than 60 ;; FILTER OUT KNOWN BAD SUBNETS CMPB I,@BADSBP ;MAYBE UPDATE POINTER BHI 115$ ; NO UPDATE NEEDED INC BADSBP 115$: CMPB I,@BADSBP ;THIS TIME, CHECK FOR EQUALITY BEQ 20$ ;PUNT ;; END FILTER MOV SBNCST(I),C ;GET COST CMP C,#1000 ;IF NOT REACHABLE, DON'T PUT IN PACKET BHIS 20$ .IREPT 3, ASR C ;DIVIDE BY 8 TO GET APPROXIMATE HOP COUNT CMP C,#ETHMXH ;DON'T PUT MORE THAN MAXHOPS BLOS 12$ MOV #ETHMXH,C 12$: MOV I,D ;GET TARGET-NET ASR D SWAB B MOVB B,(A)+ ;STORE IN WIERD XEROX BYTE ORDER MOVB D,(A)+ MOV B,(A)+ MOVB C,-2(A) 20$: TST (I)+ ;NEXT SUBNET CMP I,#NSUBNT*2 BLO 10$ SUB #EGTSBN,A ;NUMBER OF DATA BYTES IN PUP ADD #22.,A ;FOR HEADER AND CHECKSUM MOV A,EGTPLN ;SET PUP LENGTH MOV #CHXEGT,I ;SET UP TO TRANSMIT TO ETHERNET JMP ETHOUT .ENDC ;ETHERP .IF DF NDVRBF .SBTTL DOVER PROTOCOL TRANSLATOR ;RFC PACKET IN A. MUST PRESERVE I, AND RETURN 'EQ'. DVROPN: MOV PKPKN(A),C MOV PKSIND(A),B MOV PKSHST(A),A PUSH I CALL 5$ POP I SEZ RET ;SET UP DOVER TO TALK TO HOST IN A, INDEX IN B, PKT# IN C, SENDING BACK AN OPN ;OR SENDING A LOS IF BUSY. MUST WATCH FOR DUPLICATE RFC'S ;MUST BE CALLED WITH CHAOS AND ETHER INTERRUPTS MASKED 5$: TST DVRHST ;BUSY? BEQ 10$ ;NO CMP A,DVRHST BNE DVRBSY ;YES, TALKING TO ANOTHER HOST CMP B,DVRIDX BNE DVRBSY ;YES, TALKING TO ANOTHER GUY SAME HOST BR 11$ ;DUPLICATE RFC 10$: CLR DVRTIM ;FLUSH TIMEOUT MOV A,DVRHST MOV B,DVRIDX INC DVRLIX ;ESTABLISH UNIQUE LOCAL INDEX BNE 11$ INC DVRLIX ;DON'T USE 0 11$: CLR DVRMSK ;CLEAR THE BUFFER RING CLR DVRID ;FIRST PACKET TO SEND TO DOVER IS PACKET 0 INC C ;C := FIRST PACKET ID THAT WILL COME IN FROM CHAOS MOV C,DVROFS MOV #%COOPN*400,B ;SEND AN OPN BR DVRST1 ;REST IS LIKE STS DVRBSY: TST DVRPKP ;SPECIAL BUFFER BUSY? BNE CPOPJ0 ;YES, PUNT MOV #DVRBF2,C ;SEND A CLS MOV #%COCLS*400,(C)+ MOV #4,(C)+ MOV A,(C)+ MOV B,(C)+ MOV #CHAD0,(C)+ CLR (C)+ CLR (C)+ CLR (C)+ MOV #"BU,(C)+ MOV #"SY,(C)+ MOV #DVRBF2,DVRPKP BR DVRRFL ;HERE TO SEND STS TO GUY CONNECTED TO DOVER ;MUST BE MASKED AGAINST CHAOS INTERRUPTS DVRSTS: MOV #%COSTS*400,B DVRST1: MOV #DVRBF2,A ;USE THIS BUFFER MOV #4,D ;NUMBER OF BYTES DVRST2: MOV A,C MOV B,(A)+ ;OPCODE MOV D,(A)+ ;NUMBER OF BYTES MOV DVRHST,(A)+ ;DESTINATION HOST MOV DVRIDX,(A)+ ;DESTINATION INDEX MOV #CHAD0,(A)+ ;SOURCE HOST MOV DVRLIX,(A)+ ;SOURCE INDEX CLR (A)+ ;NO PACKET NUMBER CMP B,#%COLOS*400 ;IF SENDING LOS, PUNT THE REST BEQ 20$ MOV DVRID,B DEC B ;LAST PACKET ACKNOWLEDGED BY DOVER ADD DVROFS,B ;CONVERT TO CHAOSNET ID MOV B,(A)+ ;ACKNOWLEDGE PACKET NUMBER MOV B,(A)+ ;RECEIPT MOV #NDVRBF,(A)+ ;WINDOW SIZE 20$: MOV C,DVRPKP ;CAUSE PACKET TO GET SENT ;DROP INTO DVRRFL ;HERE TO GET ANOTHER PACKET FROM THE DOVER. THIS CAN BE EITHER A CHAOSNET ;PACKET TO BE SENT BACK TO THE APPROPRIATE GUY, OR A PUP TO GO TO THE DOVER DVRRFL: MOV #CHXDVR,I ;THIS MIGHT NOT BE SET UP WHEN CALLED TST CHISTS(I) ;PACKET SOURCE ONLY EMANATES ONE AT A TIME BNE CPOPJ0 CMP CHIBFP(I),DVRPKP ;FINISHED SENDING SPECIAL PACKET? BNE 10$ CLR DVRPKP ;YES, MAKE READY FOR ANOTHER 10$: CLR CHIBFP(I) ;THIS PACKET NO LONGER BEING SENT MOV DVRPKP,A ;GOT SPECIAL PACKET TO SEND? BNE 30$ ;YES, SEND IT TST DVRMSK ;GOT NEXT BUFFER TO SEND TO DOVER? BPL CPOPJ0 ;NO CMP DVRRTR,#60. ;1-SECOND RETRANSMISSION INTERVAL ELAPSED? BLO CPOPJ0 ;NO, DON'T SEND YET CLR DVRRTR ;SENDING, RESET RETRANSMISSION TIMER MOV DVRBFP,A BIC #PKFCMS,PKFC(A) ;CLEAR FORWARDING COUNT SINCE SENDING AGAIN 30$: MOV A,CHIBFP(I) ;SEND THIS PACKET CALL CHSIHD ;ROUTE HIM BVS DVRRFL ;BAD, IGNORE CMP B,#CHXCHS ;SWAB IF SENDING TO 10, BUT NOT ETHERNET BHIS 35$ CALL CHSSWB 35$: INC CHISTS(I) ;INDICATE BUFFER READY TO SEND RET ;CALLED WITH A PUP IN ETHIBF WHICH IS FROM THE DOVER AND ADDRESSED ;TO THE GUY WHO'S TRYING TO PRINT ON IT. MUST BE MASKED AGAINST ETHER & CHAOS INTERRUPTS. DVRPUP: MOVB ETHIBF+PKDAT+2,B CMP B,#31 ;EFTP ACKNOWLEDGE? BNE DVRPP1 CMP ETHIBF+PKDAT+6,DVRID ;ACKNOWLEDGING EXPECTED PACKET? BNE CPOPJ0 ;NO, IGNORE IT INC DVRID ;YES, ADVANCE ID, POINTER, AND PACKET-PRESENCE MASK MOV DVRBFP,A ADD #DVRBFL,A CMP A,#DVRBF2 BLO 11$ MOV #DVRBUF,A 11$: MOV A,DVRBFP ASL DVRMSK SETOM DVRRTR ;FAKE RETRANSMIT TIMER TO SEND NEXT PUP RIGHT AWAY TST CHISTS+CHXDVR ;PACKET SOURCE BUSY? BEQ DVRSTS ;NO, SEND AN ACKNOWLEDGEMENT TO THE CHAOSNET CPOPJ0: RET DVRPP1: MOV #22.,A ;RELATIVE ADDRESS OF ASCII STRING CMP B,#33 ;EFTP ABORT? BEQ DVRERR MOV #44.,A ;RELATIVE ADDRESS OF ASCII STRING CMP B,#4 ;PUP ERROR? BNE CPOPJ0 ;IGNORE ANYTHING ELSE DVRERR: CLR DVRMSK ;DON'T SEND ANYTHING MORE TO THE DOVER MOV ETHIBF+PKDAT,C ;PUP LENGTH SUB A,C SUB #2,C ;GET LENGTH OF ASCII STRING ADD #ETHIBF+PKDAT,A ;GET ADDRESS OF ASCII STRING MOV #DVRBUF+PKDAT,B ;BUILD A LOS PACKET TO SEND BACK MOV C,D ;SAVE BYTE LENGTH INC C ASR C ;WORD COUNT BEQ 11$ 10$: MOV (A)+,(B) SWAB (B)+ ;ALTO HAS BYTES IN THE WRONG ORDER SOB C,10$ 11$: MOV #%COLOS*400,B ;SEND A LOS MOV #DVRBUF,A CALL DVRST2 CLR DVRHST ;KILL CONNECTION RET ;HERE IS A PACKET DIRECTED TO THE DOVER. DO GOOD THINGS WITH IT. ;NOTE, IT HAS ALREADY BEEN SWABBED INTO ETHERNET BYTE ORDER. DVRPKT: MOV CHOINX(I),B ;GET SOURCE SUPPLYING THE PACKET MOV CHIBFP(B),A ;GET ADDRESS OF PACKET CLR DVRTIM ;FOREIGN HOST IS NOT IDLE MOVB PKOP(A),B ;DATA PACKET? BMI 50$ ;YES CMP B,#%COSNS BNE 11$ TST CHISTS+CHXDVR BNE 90$ CALL DVRSTS ;SNS => STS BR 90$ 11$: CMP B,#%COCLS BEQ 12$ ;CLS OR LOS PUNTS THE CONNECTION CMP B,#%COLOS BNE 13$ 12$: CLR DVRHST BR 90$ 13$: CMP B,#%COEOF ;NOTE THAT EOF IS TREATED VERY MUCH LIKE DATA! BNE 90$ ;IGNORE ANYTHING RANDOM 50$: MOV PKPKN(A),B ;GET ID OF DATA PACKET SUB DVROFS,B MOV DVRBFP,D ;FIND WHERE IN THE BUFFER IT GOES MOV #100000,C ;AND GET MASK BIT FOR IT SUB DVRID,B ;B := ID RELATIVE TO NEXT EXPECTED BEQ 53$ CMP B,#NDVRBF BHIS 90$ ;IGNORE DUPLICATE OR NOT IN WINDOW 51$: ADD #DVRBFL,D CMP D,#DVRBF2 BLO 52$ MOV #DVRBUF,D 52$: CLC ROR C SOB B,51$ 53$: BIT C,DVRMSK ;ALREADY HAVE PACKET? BNE 90$ ;YES, IGNORE BIS C,DVRMSK ;NO, STORE IT AWAY MOV D,C ADD #PKDAT,D ;BUILD PUP MOV PKNBYT(A),B BIC #PKNBMS,B MOV B,(D) ADD #22.,(D)+ ;PUP LENGTH MOV #30,(D)+ ;PUP TYPE TST (A) ;WAS THIS DATA OR EOF? BMI 54$ ;DATA SUB (PC),-2(D) ;EOF, SET PUP TYPE TO 32 54$: CLR (D)+ ;PUP ID HIGH MOV PKPKN(A),(D) ;PUP ID LOW SUB DVROFS,(D)+ ; CORRECTED MOV #DVRADR,(D)+ ;DESTINATION HOST CLR (D)+ ;DESTINATION SOCKET HIGH MOV #20,(D)+ ;DESTINATION SOCKET LOW MOV DVRHST,(D)+ ;SOURCE HOST CLR (D)+ ;SOURCE SOCKET HIGH MOV DVRIDX,(D)+ ;SOURCE SOCKET LOW ADD #PKDAT,A INC B ASR B ;NUMBER OF DATA WORDS ;*** TEMPORARY KLUDGE *** PUSH ;PUSH B LAST!! ;*** END TEMPORARY KLUDGE *** BEQ 56$ 55$: MOV (A)+,(D)+ ;MOVE THE DATA SOB B,55$ 56$: MOV C,A ADD #PKDAT,A MOV #<%COUNC*400>,(C) ;PKOP MOV 10(A),PKDHST(C) MOV (A),PKNBYT(C) ;SHOULD BE ENOUGH TO GET IT ROUTED TO ETHERNET CALL PUPCKS ;STORE APPROPRIATE CHECKSUM ;*** TEMPORARY KLUDGE *** POP ;LOOK FOR SOME KIND OF MACHINE FAILURE TST B BEQ 79$ 70$: CMP (D)+,(A)+ BNE 75$ SOB B,70$ BR 79$ 75$: DVRFKT=. NOP ;PUT A BPT HERE IF YOU LIKE INC NDVRFK CLR DVRMSK ;DO IT ALL OVER AGAIN 79$: ;*** END TEMPORARY KLUDGE *** CALL DVRRFL ;SEND THIS PACKET MAYBE 90$: MOV #CHXDVR,I JMP CHSODN ;THIS PACKET HANDLED .ENDC ;NDVRBF .IFNZ DL10P .SBTTL TRAP HANDLING TRAP14: HALT ;BPT WITH NO RUG IN CORE TRAP10: BPT ;ILLEGAL INSTRUCTION TRAP4: NOP ;PATCH BPT HERE IF YOU WANT CMP (SP),#MAIN ;IF TRAP4 IN MAIN LOOP... BLO CRASH CMP (SP),#MAINE BHIS CRASH BIT #DLXPRT,DLXCSR ;AND DL10 PORT TURNED OFF BNE CRASH TST DLXOFF ;AND WE THOUGHT IT WAS ON BNE CRASH RESTRT: MOV #STKBAS,SP ;THEN RESTART MAIN LOOP CLR -(SP) ;WHICH WILL WAIT FOR DL10 PORT TO TURN ON MOV #MAIN,-(SP) RTI CRASH: BPT ;OTHERWISE, CRASH PWRFAL: RESET ;POWER FAIL OR UP - IF FAIL, HALT DURING RESET MOV #20,B ;WAIT 2 SECONDS TO 1$: CLR A ; MAKE SURE POWER IS REALLY ON SOB A,. SOB B,1$ JMP INIT ;POWER SEEMS UP, RESTART PROGRAM .ENDC ;DL10P .IFNZ NODDT ;IF NO DDT OR OTHER "OPERATING SYSTEM", SET UP TRAP HANDLERS TRAP4: .=4 .WORD TRAP4,340,TRAP10,340,TRAP14,340,TRAP10,340,PWRFAL,340,TRAP10,340,TRAP10,340 .=TRAP4 ;ILLEGAL ADDRESS, UNIBUS NXM, STACK OVERFLOW TRAP4: BPT 0 ;ILLEGAL INSTRUCTION, IOT, EMT TRAP10: BPT 0 ;POWER FAILURE OR RESTORE PWRFAL: HALT 0 ;BPT (OR TRACE) TRAP14: .REPT 7 ;SAVE REGISTERS WHERE CARPET CAN FIND THEM MOV %0+.RPCNT,BPTACS+<.RPCNT*2> .ENDR CLR BPTGO SETOM BPTFLG 5$: TST BPTGO BEQ 5$ CLR BPTFLG .REPT 7 MOV BPTACS+<.RPCNT*2>,%0+.RPCNT .ENDR RTI BPTFLG: 0 ;NON-ZERO IF GOT A BPT BPTGO: 0 ;NON-ZERO TO PROCEED BPTACS: .BLKW 7 ;REGS EXCEPT PC .ENDC ;NODDT .SBTTL INITIALIZATION GO:: INIT: CLR PS .IFNZ DL10P RESET MOV #STKBAS,SP TST 14 BNE 1$ ;BPT ALREADY SET UP BY RUG MOV #TRAP14,14 MOV #340,16 1$: .ENDC ;DL10P .IFNZ NODDT ;NO OPERATING SYSTEM RESET MOV #STKBAS,SP .ENDC ;NODDT SETOM DLXOFF ;REINITIALIZE VARIOUS VARIABLES SETOM NO.ITS .REPT CHAOSP ;IDLE CHAOS NET INTERFACES CLR CHISTS+CHXCHS+<2*.RPCNT> CLR CHOSTS+CHXCHS+<2*.RPCNT> .ENDR .IIF NZ T300P, CLR RQBACT .IFNZ NCT MOV #NFTTY,I 76$: MOV NRMIPC(I),TTYIPC(I) ADD #2,I CMP I,#LASTTY BLE 76$ MOV #TYORNG,B ;CLEAR THE TYPOUT-DONE RING CALL CLRING MOV #,A ;GIVE OUTPUT DONE ON ALL LINES 78$: CALL PUT INC A CMP A,#+NCT BLO 78$ .ENDC ;NCT .IFNZ NDMS ;;; Turn on DM11-BBs CLR B ;iterated over DM11 units MOV #NDMS,H 5$: MOV #DMCLR+DMCSN,@DMCSR(B) ;CLEAR SCANNER MEMORY 2$: BIT #DMBSY,@DMCSR(B) BNE 2$ CLR I ;iterated over modem channels ;; turn on connected modem channels for one DM11 CLR A ;counter for channels per unit 3$: TST M2LMAP(I) BEQ 4$ MOV A,@DMCSR(B) MOV #LINENB,@DMLSR(B) 4$: TST (I)+ INC A CMP A,#16. BLT 3$ TST (B)+ SOB H,5$ ;next DM11 ;; treat first-time interrupts differently SETOM DMINI CLR B MOV #NDMS,A 6$: MOV #DMSCN+DMIEN,@DMCSR(B) ;enable scanner interrupts TST (B)+ SOB A,6$ ;on all DMs MOV #20000.,A SOB A,. ;DELAY 50 MILLISECONDS CLR DMINI ;WHILE P.I. LEVEL GETS INITIAL STATUS .ENDC ;NDMS .IFG NDHS ;TURN ON DH11'S MOV #NLDHHX,H DHINIL: MOV DHSCR(H),A ;DEVICE ADDRESS MOV #100000,16(A) ;TURN ON SILO MAINTENANCE MODE, SUSPECTED OF ;LOSING MOV #4000,(A) ;RESET DH11 MOV 16(A),B ;CHECK SILO STATUS BIC #300,B ;THESE BITS ARE IN RAM & DON'T CLEAR BEQ DHSWIN ;SHOULD HAVE CLEARED MAINTENANCE MODE AND OTHER CRUD DHSLUZ: BPT ;LOSE DHSWIN: MOV #DHRENB+DHTENB,(A) ;NOW ENABLE INTERRUPTS ON DH11 SUB #2,H BGE DHINIL .ENDC ;NDHS ;TURN ON DL11S .IFG NDLS MOV #NLDLHX,H MOV #NDLS-1,A 21$: .IIF NZ DTE20P, BEQ 22$ ;NO KBD INT ON KL10 CTY DUE TO KLDCP LOSSAGE MOV #103,@DLKS(H) ;ACTIVATE KEYBOARD INTERRUPT, D.T.R., READER 22$: MOV #100,@DLPS(H) ;ACTIVATE PRINTER INTERRUPT SUB #2,H DEC A BPL 21$ .ENDC ;NDLS ;SET LINE PARAMETERS AND ALLOCATE BUFFERS .IFNZ NCT MOV #NFTTY,I 10$: MOV LPRVAL(I),A MOV BUFSIZ(I),B CALL SPARAM ADD #2,I CMP I,#LASTTY BLE 10$ .ENDC ;NCT ;TURN ON CLOCK .IIF Z DTE20P, MOV #100,@#LKS ;NO CLOCK INTERRUPTS IF KLDCP IS HACKING CLOCK TOO .IFNZ DTE20P ;INITIALIZE DTE20 MOV #37774,DLYCNT ;DMA TO BANK 0, 2 USEC DELAY MOV #%D3BYT,DIAG3 ;DO TO10 TRANSFERS IN BYTE MODE MOV #MAIN,SADR ;ONLY DO INIT ONCE .ENDC ;DTE20P .IIF NZ TEN11P, SETOM T11I10 ;CAUSE 10 TO REINITIALIZE TEN-11 CHAOS .REPT CHAOSP MOV CHIHWR+CHXCHS+<2*.RPCNT>,H ;ADDRESS THE INTERFACE CONC ,\.RPCNT ;CHECK THE HOST NUMBER SWITCHES AGAINST THE PROGRAM BEQ .+4 BPT BIS #%CAREN,(H) ;ENABLE CHAOS NET INPUT INT .ENDR ;CHAOSP .IFNZ ETHERP MOV CHIHWR+CHXETH,H ;ADDRESS THE INTERFACE MOV 16(H),A ;GET HOST NUMBER SWITCHES COMB A ;FIX XEROX MISTAKE CMPB A,#ETHHSN ;CHECK HOST NUMBER SWITCHES BEQ .+4 BPT MOV #CHXETH,I ;ENABLE TO RECEIVE FIRST ETHERNET PACKET CALL ETHRFL .ENDC ;ETHERP ;GO JMP MAIN .IFNZ GOULDP .SBTTL GOULD PRINTER BUFFERS GLPOIP: GLPBFF ;NEXT BUFFER IN AT M.P. LEVEL GLPOOP: GLPBFF ;NEXT BUFFER OUT AT P.I. LEVEL .REPT NGLPBF ;ASSEMBLE THE BUFFERS 0 .SEE GB.STA GLPBFF ;DUE TO PALX BUG, LEAVE .SEE ON NEXT LINE .SEE GB.NXT GLPBFF==.-4 0 .SEE GB.FF 0 .SEE GB.NL 0 .SEE GB.PNT .BLKB GLPBSZ .ENDR .ENDC ;GOULDP .SBTTL "TTYTYP" PARAMETER FILE T LPRVAL: .BLKW NCT ;DH11 PARAMETER REG BUFFRS: ;BEGIN ALLOCATING BUFFERS HERE .IIF NZ NCT, INFORM ,\BUFFRS ZZ===+3777>/4000 ;NUMBER OF K USED .IRP ZZZZ,<0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16> .LIF EQ ZZ-.IRPCNT ;THIS IS A CRETINOUS CROCK TO GET IT COME OUT IN DECIMAL INFORM ,\BUFFRS+,< (>,ZZZZ, .ENDR .IFNZ NCT ;TTYTYP FILE ONLY IF WE HAVE TTYS .IF P2 ;SPEED UP THE ASSEMBLY OFF==69105 ;KLUDGES SO I DON'T HAVE TO PUT KEYWORD PARAMETERS INTO PALX 40K==40000 80K==80000 .MACRO SPEED BAUD ZZ==-1 .IIF EQ BAUD-OFF, ZZ==0 .IIF EQ BAUD-50, ZZ==1 .IIF EQ BAUD-75, ZZ==2 .IIF EQ BAUD-110, ZZ==3 .IIF EQ BAUD-134, ZZ==4 .IIF EQ BAUD-150, ZZ==5 .IIF EQ BAUD-200, ZZ==6 .IIF EQ BAUD-300, ZZ==7 .IIF EQ BAUD-600, ZZ==10 .IIF EQ BAUD-1200, ZZ==11 .IIF EQ BAUD-1800, ZZ==12 .IIF EQ BAUD-2400, ZZ==13 .IIF EQ BAUD-4800, ZZ==14 .IIF EQ BAUD-9600, ZZ==15 .IIF EQ BAUD-80K, ZZ==16 .IIF EQ BAUD-40K, ZZ==17 .IIF LT ZZ, .ERROR UNRECOGNIZED SPEED "BAUD" .ENDM SPEED .MACRO IPARM N,ODFLT,IDFLT,MUMLST .IF GE <2*N>-NFTTY .IF LE <2*N>-LASTTY %%.ISPEED==-1 %%.SPEED==-1 .IRP MUM, .IF NB ZZ==0 .IRPC MUMB, .IIF GE .IRPCNT-2, .MEXIT .IIF IDN MUMB,S, .IIF EQ .IRPCNT, ZZ==1 .IIF IDN MUMB,P, .IIF EQ .IRPCNT-1, ZZ==ZZ+1 .IIF IDN MUMB,I, .IIF EQ .IRPCNT, ZZ==1 .IIF IDN MUMB,S, .IIF EQ .IRPCNT-1, ZZ==ZZ+1 .ENDM .IIF EQ ZZ-2, %%.'MUM .ENDC .ENDM .IF LT %%.ISPEED .IIF LT %%.SPEED, %%.ISPEED==IDFLT .IELSE %%.ISPEED==%%.SPEED .ENDC .IIF LT %%.SPEED, %%.SPEED==ODFLT SPEED %%.ISPEED IZZ==ZZ SPEED %%.SPEED ; BUFFER SIZE IS 1/2 SECOND'S TYPING ; BUT WILL BE SUBJECT TO LIMIT OF MAXBSZ .IIF LT ZZ-7, BZZ==5. .IIF EQ ZZ-7, BZZ==15. .IIF EQ ZZ-10, BZZ==30. .IIF EQ ZZ-11, BZZ==60. .IIF EQ ZZ-12, BZZ==90. .IIF EQ ZZ-13, BZZ==120. .IIF EQ ZZ-14, BZZ==240. .IIF EQ ZZ-15, BZZ==480. .IIF GT ZZ-15, BZZ==1000. .=LPRVAL+<2*N> ;ASSEMBLE LINE PARAMETER WORD .IIF NE ZZ-3, ++3 ;ISPEED, OSPEED, NO PARITY, 8 BITS, FULL DUPLEX .IELSE ++3+4 ;110 BAUD EXTRA STOP BIT .=BUFSIZ+<2*N> BZZ ;ASSEMBLE BUFFER SIZE .ENDC .ENDC .ENDM IPARM ;MACROS USED IN THE TTYTYP FILE: .MACRO TTDPRT TN,A,B,C,D,E,F,G,H,I,J IPARM TN,300,300, .ENDM TTDPRT .MACRO TTDMRX TN,A,B,C,D,E,F,G,H,I,J IPARM TN,600,600, .ENDM TTDMRX .MACRO TTDTRM TN,A,B,C,D,E,F,G,H,I,J IPARM TN,1200,1200, .ENDM TTDTRM .MACRO TTDLPT TN,A,B,C,D,E,F,G,H,I,J IPARM TN,9600,9600, .ENDM TTDLPT .MACRO TTDLA36 TN,A,B,C,D,E,F,G,H,I,J IPARM TN,300,300, .ENDM TTDLA36 .MACRO TTDIML TN,A,B,C,D,E,F,G,H,I,J IPARM TN,50K,25K, .ENDM TTDIML .MACRO TTDVT TN,A,B,C,D,E,F,G,H,I,J IPARM TN,9600,9600, .ENDM TTDVT .MACRO TTDTEK TN,A,B,C,D,E,F,G,H,I,J IPARM TN,1200,1200, .ENDM TTDTEK .MACRO TTDLSR TN,A,B,C,D,E,F,G,H,I,J IPARM TN,2400,2400, .ENDM TTDLSR .MACRO TTDDPT TN,A,B,C,D,E,F,G,H,I,J IPARM TN,2400,2400, .ENDM TTDDPT .MACRO TTDGT40 TN,A,B,C,D,E,F,G,H,I,J IPARM TN,4800,4800, .ENDM TTDGT40 .MACRO TTDRAY TN,A,B,C,D,E,F,G,H,I,J IPARM TN,9600,9600, .ENDM TTDRAY .MACRO TTDH19 TN,A,B,C,D,E,F,G,H,I,J IPARM TN,9600,9600, .ENDM TTDRAY .MACRO TTD11 TN,A,B,C,D,E,F,G,H,I,J IPARM TN,4800,4800, .ENDM TTD11 .MACRO TTDRAN TN,A,B,C,D,E,F,G,H,I,J IPARM TN,FOO,FOO, .ENDM TTDRAN .MACRO TTDTV TN,A,B,C,D,E,F,G,H,I,J IPARM TN,FOO,FOO, .ENDM TTDTV .MACRO TTDGRN TN,A,B,C,D,E,F,G,H,I,J IPARM TN,9600,9600, .ENDM TTDGRN .MACRO TTDSTY TN,A,B,C,D,E,F,G,H,I,J IPARM TN,FOO,FOO, .ENDM TTDSTY .MACRO REPEAT N,FOO FAKOUT: .REPT N FAKOUT===0 .ENDM NSTTYS==0 ;WE'RE NOT INTERESTED IN PSEUDO-TTYS N11TYS==0 ;NOR IN PDP11 TVS .INSRT SYSTEM;TTYTYP > .EXPUNGE ZZ,IZZ,IZZZ,BZZ,OFF,40K,80K,%%.ISPEED,%%.SPEED .EXPUNGE TT,TY,TO,TP,TCT,HOR,VER,ROL,SPEED,ISPEED .ENDC ;P2 .ENDC ;NCT .END INIT