Trailing-Edge
-
PDP-10 Archives
-
BB-Y393U-SM
-
monitor-sources/lpksdv.mac
There are 20 other files named lpksdv.mac in the archive. Click here to see a list.
;<4-1-FIELD-IMAGE.MONITOR>LPKSDV.MAC.2, 25-Feb-82 20:29:39, EDIT BY DONAHUE
;UPDATE COPYRIGHT DATE
; UPD ID= 402, FARK:<4-WORKING-SOURCES.MONITOR>LPKSDV.MAC.2, 15-Feb-81 17:36:54 by ZIMA
;Edit 1832 - move 1824 to a device dependent routine.
; UPD ID= 271, SNARK:<4.MONITOR>LPKSDV.MAC.92, 18-Feb-80 15:24:34 by SANICHARA
;Fix for error status 0
;<4.MONITOR>LPKSDV.MAC.91, 3-Jan-80 08:09:29, EDIT BY R.ACE
;UPDATE COPYRIGHT DATE
;<4.MONITOR>LPKSDV.MAC.90, 7-Nov-79 09:27:47, EDIT BY OSMAN
;tco 4.2465 - Don't print garbage on KS printer when system coming up
;<4.MONITOR>LPKSDV.MAC.89, 17-Oct-79 09:30:57, EDIT BY OSMAN
;tco 4.2529 - Don't start printer if it's already printing (LPWGO)
;<4.MONITOR>LPKSDV.MAC.88, 1-Oct-79 17:08:00, EDIT BY OSMAN
;tco 4.2504 - Don't restart printer in LPINT if LPWGO is set (it's printing!)
;<OSMAN.MON>LPKSDV.MAC.1, 10-Sep-79 15:41:50, EDIT BY OSMAN
;TCO 4.2412 - Move definition of BUGHLTs, BUGCHKs, and BUGINFs to BUGS.MAC
;TCO 4.2240 - DO ERROR RESET WHEN DONE LOADING RAM OR VFU
;<4.MONITOR>LPKSDV.MAC.85, 20-Apr-79 15:00:48, EDIT BY OSMAN
;DON'T GENERATE ERROR IF PAGE COUNTER REACHES 0
;<4.MONITOR>LPKSDV.MAC.84, 19-Apr-79 10:16:27, EDIT BY OSMAN
;tco 4.2235 - handle GO ERR like any other error (don't restart printer)
;<4.MONITOR>LPKSDV.MAC.83, 2-Apr-79 09:17:11, EDIT BY OSMAN
;more 4.2186 - Don't error reset in CLRERR if merely page counter reached 0
;<4.MONITOR>LPKSDV.MAC.82, 4-Mar-79 18:21:45, EDIT BY KONEN
;UPDATE COPYRIGHT FOR RELEASE 4
;<4.MONITOR>LPKSDV.MAC.81, 9-Feb-79 09:41:00, EDIT BY OSMAN
;tco 4.2186 - set .DVFFE when setting .DVFHE
;<4.UTILITIES>LPKSDV.MAC.1, 5-Jan-79 14:19:30, EDIT BY OSMAN
;more 4.2142, copy page counter to itself if user doesn't care
;<4.MONITOR>LPKSDV.MAC.78, 2-Jan-79 15:09:13, EDIT BY OSMAN
;tco 4.2142 - check for page-counter-zeroed at CLRERR
;<4.MONITOR>LPKSDV.MAC.77, 27-Sep-78 11:20:11, Edit by MCLEAN
;FIX FOR LP07 VFU NOT READY
;<4.MONITOR>LPKSDV.MAC.76, 27-Sep-78 11:19:43, Edit by MCLEAN
;THIS SOFTWARE IS FURNISHED UNDER A LICENSE AND MAY ONLY BE USED
; OR COPIED IN ACCORDANCE WITH THE TERMS OF SUCH LICENSE.
;
;COPYRIGHT (C) 1976,1977,1978,1979,1980,1981,1982 BY DIGITAL EQUIPMENT CORPORATION, MAYNARD, MASS.
; DEVICE DEPENDENT CODE FOR THE LINE PRINTER
; (LP20 SERVICE) SPECIFIC CODE.
;DEFSTRS NEEDED WITHIN
DEFSTR (LPXBTS,L11A,19,2) ;PDP-11 TWO EXTENDED ADDRESSING BITS
; LINE PRINTER DEVICE DISPATCH TABLE
FELPVT: IFIW!FESFLO ;SEND FLUSH
IFIW!FESLOP ;PAGE COUNTER
IFIW!FESACK ;ACK
IFIW!FESDTA ;SEND DATA
IFIW!FESEOF ;EOF
IFIW!FESNDS ;STRING DATA
IFIW!OURTLS ;SEND STATUS
IFIW!LP20RS ;RESTART
IFIW!LP20IN ;INITALIZE
IFIW!LP20IE ;CHECK INTERRUPT ENABLE
;**;[1832] Add one line at FELPVT: +10L JGZ 15-FEB-81
IFIW!LP20OP ;[1832] DEVICE OPEN
IFN <.-FELPMX>-FELPVT,<PRINTX %%INVALID DEVICE DEPENDENT TABLE SIZE>
;TABLE OF -11 HARDWARE ADDRESSES OF THE LINEPRINTER CONTROLLER REGISTERS
;LCRTAB+N SHOWS THE ADDRESS FOR THE DATA BASE FOR LINEPRINTER N.
LCRTAB: LP11CA
;PARALLEL TABLE OF -11 INTERRUPT VECTOR ADDRESSES. THAT IS, THE
;CONTENTS OF LPVTAB+N IS THE -11 ADDRESS WHICH WOULD CONTAIN THE
;ADDRESS OF THE INTERRUPT ROUTINE FOR LINEPRINTER N, IF WE WERE
;AN -11.
LPVTAB: LP11IV
;TABLE OF ADDRESSES OF INTERRUPT ROUTINES, ONE FOR EVERY LINEPRINTER.
LPINTB: LP0INT
;INITIALIZATION ROUTINE.
LP20IN: MOVEI U,LPTN
LP20I1: SOJL U,R ;RETURN IF ALL LP'S INITIALIZED
SKIPE PROFLG ;IF PROFLG DON'T INITALIZE
CALL L2INI ;INITIALIZE A LINE PRINTER
JRST LP20I1 ;LOOP FOR ALL LP'S
RET ;DONE
;ROUTINE TO INITIALIZE A LINE PRINTER. IT EXPECTS U TO CONTAIN 0
;THROUGH N-1 WHERE THERE ARE N LINE PRINTERS ON THE SYSTEM.
L2INI: MOVE A,LCRTAB(U) ;GET ADDRESS ON UNIBUS FOR THIS LP
SETZRO LPXBIT,(U) ;ASSUME NONE
CALL UBGOOD ;CHECK FOR EXISTANCE
RET ;RETURN NO DEVICE
SETONE LPXBIT,(U) ;SET DEVICE EXISTS
MOVE A,U ;SEE WHICH LINE PRINTER WE'RE DOING
LSH A,2 ;MULTIPLY BY FOUR BECAUSE XPCW NEEDS FOUR WORDS
ADDI A,LPXPTB ;POINT XPCW AT CORRECT PLACE
SETZM 2(A) ;CLEAR FLAGS OUT OF WHERE XPCW WILL POINT TO
MOVE B,LPINTB(U) ;GET INTERRUPT ROUTINE ADDRESS FOR THIS LP
MOVEM B,3(A) ;STORE IT FOR XPCW TO TRANSFER TO ON INTERRUPT
HRLI A,(XPCW) ;MAKE THE XPCW INSTRUCTION
MOVE B,SMTEPT+LPTUBN ;GET ADDRESS OF XPCW TABLE
MOVE C,LPVTAB(U) ;GET -11 ADDRESS THAT HOLDS LP INTERRUPT ROUTINE ADDRESS
LSH C,-2 ;DIVIDE BY 4 TO GET OFFSET INTO XPCW TABLE
ADD B,C ;GET ADDRESS WHERE XPCW SHOULD GO
MOVEM A,(B) ;STORE THE XPCW
MOVEI A,LPTUBN ;UNIBUS ADAPTOR NUMBER
MOVEI B,1 ;WE NEED ONE -11 PAGE
CALL ALUBWA ;GET IT
BUG(NLWA)
MOVEM A,LPWINA(U) ;SAVE ADDRESS OF UBA
MOVEM B,L11A(U) ;REMEMBER -11 ADDRESS WE GOT
LP20RS: CALL GETLPA ;GET ADDRESS OF THIS LINEPRINTER'S BUFFER
MOVE C,A
MOVE B,L11A(U) ;GET BUFFER ADDRESS
LSH C,-9 ;MAKE PAGE NUMBER
TXO C,UNBD18+UNBVBT ;DISABLE 18-BIT TRANSFERS, SAY VALID TRANSFER
WRIO C,@LPWINA(U) ;ASSOCIATE -10 PAGE WITH FAKE -11 PAGE
CALL LPTRUE ;MAKE SURE PRINTER EXISTS
RET ;DON'T REFERENCE NONEXISTENT HARDWARE!
move B,LCRTAB(U) ;GET BASE ADDRESS FOR REGISTERS
MOVX A,LP1RSE+LP1INT ;SET ERROR RESET AND INITIALIZE
WRIOB A,LPCSRA+1(B)
MOVX A,LP1IEN ;INTERRUPT ENABLE BIT
WRIOB A,LPCSRA(B) ;MAKE SURE INTERRUPTS ARE ENABLED
RET
;**;[1832] Add several lines at LP20RS: +16L JGZ 15-FEB-81
;DEVICE DEPENDENT OPEN FUNCTIONS. CALL WITH U SETUP.
;SETS LINE ALLOCATION BASED ON BYTE SIZE OF OPEN.
LP20OP: LOAD B,LPBSZ,(U) ;[1832] GET BYTE SIZE FROM OPENF
MOVX A,NLPBF*5 ;[1832] ASSUME 7-BIT BYTES BY DEFAULT
CAIN B,^D8 ;[1832] IS IT 8-BIT BYTES?
MOVX A,NLPBF*4 ;[1832] YES, USE LOWER BYTE ALLOCATION
STOR A,LPTMX,(U) ;[1832] SET BYTE ALLOCATION FOR DEVICE
RET ;[1832] AND DONE
;ROUTINE TO CALL WITH U SET UP, WHICH SKIPS IFF LINEPRINTER EXISTS,
;AS DETERMINED DURING SYSTEM STARTUP
LPTRUE: LOAD A,LPXBIT,(U) ;GET EXISTENCE BIT FOR THIS LP
JUMPE A,R ;NON-SKIP IF NONX LINEPRINTER
RETSKP ;SKIP IF EXISTENT PRINTER
;LINEPRINTER INTERRUPT ROUTINES.
LP0INT: MOVEM P,LPACS+P ;SAVE CALLER'S P
MOVEI P,LPACS ;SAVE ACS
BLT P,LPACS+16
MOVE P,[XWD -LPSLEN,LPSTAK-1] ;GET STACK POINTER FOR LP INTERRUPT ROUTINE
MOVEI U,0 ;IDENTIFY WHICH PRINTER INTERRUPTED
; JRST LPINT ;JOIN COMMON INTERRUPT ROUTINE
;COMMON INTERRUPT ROUTINE FOR LINEPRINTERS. IT ASSUMES U CONTAINS UNIT
;OF LINEPRINTER THAT INTERRUPTED, THAT P IS SET UP, AND THAT THE ACS
;FROM BEFORE THE INTERRUPT ARE SAVED
LPINT: LOAD A,LPTCC,(U) ;GET CHARACTER COUNT
JUMPE A,LPINTA
SETZRO LPTCC,(U) ;ZERO INTERRUPT CHARACTER COUNT
MOVE B,U ;GET UNIT NUMBER FOR LPTINT
CALL LPTINT ;NOTIFY INTERRUPT ROUTINE
LPINTA: MOVE A,U ;GET UNIT NUMBER
LSH A,2 ;GET OFFSET INTO XPCW DATA TABLE
ADD A,[XJEN LPXPTB] ;MAKE APPROPRIATE XJEN INSTRUCTION FOR DISMISSING INTERRUPT
MOVEM A,LPXJEN ;REMEMBER THE INSTRUCTION FOR LATER
MOVE Q2,LCRTAB(U) ;GET -11 ADDRESS OF THIS LP'S REGISTERS
MOVX A,LPWCI+LPWDON ;CHARACTER INTERRUPT + DONE FLAG
TIOE A,LPCSRA(Q2) ;SKIP IF NOT DONE OR CHARACTER INTERRUPT
JRST PDJCOL ;PRINTER DIDN'T JUST COME ONLINE IF
;DONE IS SET OR THERE'S AN UNDEFINED CHARACTER INTERRUPT
MOVX A,7777 ;BYTE COUNTER IS 12 BITS WIDE
MOVX B,LP1OFL+LP1DVN+LP1PER+LP1MPE+LP1RPE+LP1SYE ;CAN'T USE LP1ERR
;BECAUSE IT STICKS AFTER ERROR IS REMEDIED
TIOEB B,LPCSRB(Q2) ; WAS THERE SORT OF ERROR?
JRST NOCINT ;YES, GO LOG IT
MOVX C,LPWGO ;GET GO BIT (DESIGNATES THAT PRINTER IS RUNNING)
TIOE C,LPCSRA(Q2) ;IS PRINTER STILL RUNNING?
JRST LPXIT ;Yes, so quietly dismiss interrupt without doing
;anything. Getting here means an interrupt happened while the
;printer is still printing. I never thought this could happen
;but it mysteriously started happening around 9/28/79.
TIOE A,LPBCTR(Q2) ;SKIP IF BYTE COUNT IS 0
JRST [ MOVEI T2,3 ;NO ERROR AND BYTE COUNT NON-0,
TIONB T2,T2(Q2) ; GO RESTART PRINTER
JRST LPGO ;DO NOT RESTART IF DME OR GO ERR
CALL CLRER1
JRST LPXIT]
PDJCOL: LOAD A,ARROWF,(U) ;SEE IF DOING CTRL CHAR
JUMPN A,FINCTL ;YES, PREPARE TO GO BACK TO ORIG BUFF
MOVX A,LPWCI ;BIT WE WANT TO TEST
TIOE A,LPCSRA(Q2) ;DID WE JUST GET A CHARACTER INTERRUPT?
JRST LPCINT ;YES, GO HANDLE IT
NOCINT: CALL OURTLS ;GET STATUS OF THIS LINEPRINTER
MOVX A,LP1DON ;SEE IF LINEPRINTER DONE PRINTING
MOVE B,U ;LPTINT EXPECTS UNIT NUMBER IN B
TIOEB A,LPCSRA(Q2) ;TEST DONE FLAG
JRST [ SETZRO LPTFE,(U) ;ZERO COUNT OF CHARACTERS
LOAD A,LPTLOR,(U) ;GET BIT SAYING WHETHER RAM OR VFU WAS BEING LOADED
CAIE A,0 ;WAS IT?
CALL CLRER1 ;YES, SO DO ERROR RESET
SETZRO LPTLOR,(U) ;RAM OR VFU NO LONGER BEING LOADED
JE LPTBL,(U),LPXIT
SETZRO LPTBL,(U)
MOVEI 1,0 ;FAKE INTERRUPT RESTART
CALL LPTINT
JRST LPXIT]
; JRST LPXIT ;DISMISS INTERRUPT
;LINEPRINTER INTERRUPT EXIT ROUTINE. RESTORES AC'S AS BEFORE INTERRUPT
;AND DISMISSES INTERRUPT...
LPXIT: MOVSI 17,LPACS ;MAKE BLT POINTER
BLT 17,17 ;RESTORE AC'S
XCT LPXJEN ;RETURN TO CALLER
;GET HERE ON CHARACTER INTERRUPT
LPCINT: RDIOB A,LPRAMD(Q2) ;GET RAM DATA FOR THIS INTERRUPT
CAIE A,"^" ;IS THIS INTERRUPT FOR A CONTROL CHARACTER
;DESIRING TO BE MADE "UPARROW-CHARACTER"
JRST NOCINT ;NO, HANDLE THIS CONDITION AS ANY OTHER ERROR
RDIO A,LPBCTR(Q2) ;GET BYTE COUNTER SO FAR FOR THIS PRINTER
STOR A,SAVBCT,(U) ;REMEMBER IT FOR LATER TO CONTINUE PRINTER
RDIO A,LPBSAD(Q2) ;GET BUS ADDRESS
STOR A,SAVBUS,(U) ;REMEMBER IT TOO
MOVE A,L11A(U) ;GET -11 ADDRESS OF LPT DATA BUFFER
WRIO A,LPBSAD(Q2) ;TELL LP20 WHERE DATA IS
MOVEI A,1
STOR A,ARROWF,(U) ;MARK THAT WE'RE DOING ARROWS
;GET THE UP-ARROW FOR THE CONTROL CHAR
CALL GETLPA ;GET BUFFER ADDRESS
MOVEI B,"^" ;WHAT YOU MEAN "WE", KIMO SABE?
DPB B,[POINT 8,(A),17] ;PUT THE ^ IN THE BUFFER
LDB C,[POINT 8,(A),9] ;GET CHARACTER THAT HASN'T BEEN PRINTED YET
STOR C,SAVCHR,(U) ;SAVE IT BECAUSE WE NEED THE BUFFER SPACE
RDIOB B,LPCBUF(Q2) ;GET CONTROL CHARACTER
TRO B,100 ;MAKE IT A PRINTING CHARACTER
ANDI B,177 ;AND OFF GARBAGE BITS
DPB B,[POINT 10,(A),9] ;MAKE ^ CHARACTER IN BUFFER & CLR B0/B1
MOVNI A,2 ;GET NEG OF # OF CHARS
WRIO A,LPBCTR(Q2) ;SET UP BYTE COUNT TO 2
LPGO1: CALL SETGOA
JRST LPXIT ;DON'T SEND STATUS FOR EACH CONTROL CHARACTER
LPGO: CALL SETGOA ;START THE LP
CALL OURTLS ;ALWAYS REPORT STATUS AFTER RESTARTING PRINTER
JRST LPXIT ;WAIT FOR TWO CHARS TO PRINT
;GET HERE TO FINISH INTERRUPTED BUFFER
FINCTL: MOVEI A,0
STOR A,ARROWF,(U) ;SAY NOT DOING CTRL CHAR
LOAD A,SAVBCT,(U)
JUMPE A,NOCINT ;QUIT IF THIS WAS THE LAST CHARACTER
WRIO A,LPBCTR(Q2) ;RESTORE ORIG BYTE COUNTER
LOAD A,SAVBUS,(U)
WRIO A,LPBSAD(Q2) ;RESTORE ORIG BUS ADDRESS
CALL GETLPA ;GET BUFFER ADDRESS
LOAD B,SAVCHR,(U) ;GET SAVED BUFFER CHARACTER
DPB B,[POINT 8,(A),9] ;RESTORE BUFFER CHARACTER
JRST LPGO1 ;START PRINTER AGAIN
; ROUTINE TO SEND A FLUSH
;THIS CAUSES LINEPRINTER TO IMMEDIATELY STOP PRINTING
FESFLO: CALL LPTRUE ;MAKE SURE PRINTER EXISTS
RET ;DOESN'T!
MOVE B,LCRTAB(U) ;GET REGISTER FOR THIS LP
MOVEI A,LPWINT+LP1IEN ;SET INTERRUPT ENABLE
WRIO A,(B) ;AND STOP DEVICE WITH LOCAL INIT
MOVEI A,LP1IEN+LP1GO ;SET IENERRUPT ENABLE
WRIO A,(B)
SETZRO LPTFE,(U) ;ZERO COUNT OF BYTES IN FE
RET ;RETURN
;SET page counter
;SKIPS IFF SUCCESFUL
FESLOP: CALL LPTRUE ;DOES LINEPRINTER EXIST?
RET ;NO, GIVE FAILURE RETURN
LOAD A,PGCTR,(U) ;GET VALUE TO BE SET
MOVE B,LCRTAB(U) ;GET BASE REGISTER
WRIO A,LPPCTR(B) ;SET THE PAGE COUNTER
RETSKP ;DONE
; ROUTINE TO SEND AN ACK
;THIS IS CALLED TO GET THE PRINTER ROLLING AGAIN AFTER IT HAS
;STOPPED DUE TO SOME ERROR.
FESACK: CALL LPTRUE ;MAKE SURE PRINTER EXISTS
RET ;DOESN'T
MOVE B,LCRTAB(U) ;GET REGISTER FOR THIS LP
RDIO A,LPPCTR(B)
WRIO A,LPPCTR(B) ;SET PAGE COUNTER IN CASE THERE WAS A PAGE COUNTER INTERRUPT
RDIO A,LPBCTR(B) ;SEE HOW MANY CHARACTERS LEFT IN BUFFER
TXNE A,7777 ;ANY CHARACTERS LEFT TO PRINT?
CALL SETGO ;YES, SET THE GO FLAG
RET ;RETURN
;ROUTINE TO LOAD VFU OR RAM DATA. ACCEPTS:
; B/ FUNCTION-CODE,,0 ;.DFLVF => LOAD VFU
; ;.DFLTR => LOAD TRANSLATION RAM
; D/ NUMBER OF 8-BIT BYTES
FESDTA: STKVAR <LVFU,N8BB>
SETOM LVFU ;FIRST ASSUME LOADING VFU
CAMN B,[.DFLTR,,0] ;LOADING RAM??
SETZM LVFU ;YES, SO NOT LOADING VFU!
MOVEM D,N8BB ;REMEMBER NUMBER OF 8-BIT BYTES
CALL LPTRUE
RET ;JUST RETURN IF PRINTER DOESN'T EXIST
MOVE D,LCRTAB(U) ;GET BASE REGISTER FOR THIS LP
RDIO A,LPCSRA(D) ;GET GO BIT
TXNE A,LPWGO ;IS PRINTER ALREADY PRINTING?
RET ;YES, SO RETURN RATHER THAN MINGLE.
;NOTE: I SUSPECT THAT ON THE KL, THE SNDEOF
;ROUTINE CAUSES THE FRONT END TO WAIT UNTIL ALL
;ACTIVITY HAS STOPPED. THE KS'S SNDEOF ROUTINE
;SHOULD SOMEHOW WAIT TOO (BY USING LPTDIS?).
;HOWEVER, UNTIL IT IS TAUGHT TO, THIS LPWGO
;CHECK PREVENTS TRAFFIC JAMS. --E.O. 10/17/79
CALL GETLPA ;GET BUFFER ADDRESS FOR THIS LINEPRINTER
MOVE B,LPTRLP(U) ;FIGURE OUT WHERE DATA TO BE LOADED IS
OPSTR <SKIPN>,ALTP,(U)
ADDI B,NLPBF
HRLI B,(<POINT 16,0>) ;EACH BYTE IS 8+8 BITS
MOVE C,N8BB ;LOAD UP NUMBER OF BYTES TO DIGEST
CALL CHANGE ;REARRANGE DATA THE WAY IT WOULD BE IN AN -11
MOVE B,U ;LODDON ROUTINE EXPECTS UNIT NUMBER IN B
CALL LODDON ;TELL WORLD WE'VE RECEIVED THE DATA
MOVE A,L11A(U) ;GET LPT BUFFER ADDRESS
WRIO A,LPBSAD(D) ;TELL PRINTER WHERE DATA IS
MOVN A,N8BB ;GET NEGATIVE OF NUMBER OF BYTES
WRIO A,LPBCTR(D) ;TELL PRINTER HOW MUCH DATA WE'RE SENDING
SETONE LPTLOR,(U) ;REMEMBER THAT WE'RE DOING RAM/VFU LOAD
MOVX B,LP1PEN+LP1DVU+LP1IEN+LP1GO ;PARITY ENABLE, LOAD VFU, INTERRUPT ENABLE
SKIPN LVFU ;SKIP IF REALLY LOADING VFU
MOVX B,LP1PEN+LP1TM+LP1DVU+LP1IEN+LP1GO ;PARITY, TEST MODE, LOAD DVU, INTERRUPT ENABLE
CALL SETGOB ;START THE PRINTER
RET ;DONE
FESEOF: CALL OURTLS ;WHEN EOF REQUESTED, ASK FOR STATUS
RET ;RETURN
;ROUTINE TO SEND DATA TO THE LINE PRINTER TO BE PRINTED.
;PASS IT COUNT IN F OF NUMBER OF BYTES
;THIS ROUTINE SKIPS IFF SUCCESSFUL
FESNDS: STOR F,LPTCC,(U) ;SAVE COUNT OF CHARACTERS
CALL LPTRUE
RET ;FAILURE RETURN IF PRINTER DOESN'T EXIST
MOVE D,LCRTAB(U) ;GET -11 BASE ADDRESS FOR HARDWARE LP REGISTERS
RDIO A,LPCSRA(D) ;GET GO BIT
TXNE A,LPWGO ;IS PRINTER ALREADY PRINTING?
RET ;YES, SO FAIL RATHER THAN MINGLE.
;NOTE: I SUSPECT THAT ON THE KL, THE SNDEOF
;ROUTINE CAUSES THE FRONT END TO WAIT UNTIL ALL
;ACTIVITY HAS STOPPED. THE KS'S SNDEOF ROUTINE
;SHOULD SOMEHOW WAIT TOO (BY USING LPTDIS?).
;HOWEVER, UNTIL IT IS TAUGHT TO, THIS LPWGO
;CHECK PREVENTS TRAFFIC JAMS. --E.O. 10/17/79
CALL GETLPA ;GET BUFFER ADDRESS FOR THIS PRINTER
MOVE B,LPTCCW(U) ;GET POINTER TO DATA BEING SENT
LOAD C,LPTCC,(U) ;GET NUMBER OF CHARACTERS BEING SENT
CALL SHUFFL ;PUT BYTES IN -11 FORMAT
MOVE D,LCRTAB(U) ;GET -11 BASE ADDRESS FOR HARDWARE LP REGISTERS
MOVE A,L11A(U) ;GET -11 ADDRESS OF LPT DATA BUFFER
WRIO A,LPBSAD(D) ;TELL LP20 WHERE DATA IS
LOAD A,LPTCC,(U) ;GET NUMBER OF BYTES BEING SENT
MOVNS A ;NEGATE IT
WRIO A,LPBCTR(D) ;TELL LP20 HOW MANY
CALL SETGO ;START THE PRINTER
LOAD A,LPTCC,(U) ;SET NUMBER OF CHARACTERS SENT
RETSKP ;ALL DONE
;ROUTINE TO START THE PRINTER.
SETGO: MOVX B,LP1IEN+LP1GO ;INTERRUPT ENABLE + GO
SETGOB: LOAD A,LPXBTS,(U) ;GET PDP-11 EXTENDED ADDRESS BITS
STOR A,LP1A17+LP1A16,B ;SET HIGH ORDER ADDRESS BITS IN WORD BEING WRITTEN TO PRINTER
MOVE A,LCRTAB(U) ;GET REGISTER ADDRESS FOR THIS PRINTER
WRIOB B,LPCSRA(A) ;START THE PRINTER
RET
SETGOA: CALL CLRERR ;CLEAR ALL ERRORS
MOVX B,LP1IEN+LP1GO ;SET GO
MOVE A,LCRTAB(U) ;GET DEVICE ADDRESS
BSIOB B,LPCSRA(A) ;START DEVICE
RET ;RETURN
;ROUTINE TO CALL BEFORE SENDING DATA TO PRINTER. IT DOES THE
;APPROPRIATE ERROR CLEARING.
CLRERR: MOVX A,LPWERR ;GET BIT BEING TESTED
MOVE D,LCRTAB(U) ;GET REGISTER FOR THIS PRINTER
TIOE A,LPCSRA(D) ;SKIP IF NOT ERROR
CALL CLRER1 ;DO ERROR RESET
LOAD C,PGENB,(U) ;SEE IF USER WANTS PRINTER TO KEEP TRACK OF PAGE COUNT
JUMPN C,R ;DONE IF SO
MOVX A,LPWPZR
MOVX B,LPWRSE+LP1IEN ;GET BIT BEING SET
TION A,LPCSRA(D) ;PAGE COUNTER EXCEEDED?
RET ;NO, NOTHING MORE TO DO
RDIO B,LPPCTR(D) ;READ CURRENT PAGE COUNTER
WRIO B,LPPCTR(D) ;COPY PAGE COUNTER TO ITSELF TO CLEAR COUNTER EXCEEDED ERROR
RET ;DONE
;ROUTINE TO ACTUALLY DO THE ERROR RESET.
CLRER1: MOVX B,LPWRSE+LP1IEN ;GET BIT BEING SET
MOVE D,LCRTAB(U) ;GET BASE ADDRESS FOR THIS LP
WRIO B,LPCSRA(D) ;THERE'S AN ERROR, SO CLEAR IT
RDIO A,LPBCTR(D) ;COPY BYTE COUNTER TO ITSELF
WRIO A,LPBCTR(D) ;SINCE ERROR RESET SETS DONE (WHICH WOULD CAUSE PREMATURE INTERRUPT)
RET
;ROUTINE TO RETURN LINEPRINTER BUFFER ADDRESS IN A FOR LINEPRINTER
;UNIT NUMBER IN U.
GETLPA: MOVE A,U ;SEE WHICH LINEPRINTER WE'RE GETTING BUFFER FOR
IMULI A,NLPBF ;MAKE CORRECT OFFSET INTO BUFFER SPACE
ADDI A,LPBUF ;ADD BASE ADDRESS TO MAKE CORRECT WORD ADDRESS
RET ;DONE
;WHEN SENDING RAM OR VFU DATA TO PRINTER, IT IS INITIALLY PACKED
;IN PDP-10 WORDS IN THE FORMAT BYTE(16)WORD,WORD,WORD...
;THE LP20 WANTS IT IN THE FORMAT BYTE(2)0(16)WORD(2)0(16)WORD...
;THE FOLLOWING ROUTINE CREATES THE SECOND FORMAT GIVEN THE FIRST.
;ACCEPTS:
; A/ ADDRESS TO RECIEVE SHUFFLED BYTES
; B/ ILDB POINTER TO CONTIGUOUS BYTES
; C/ NUMBER OF BYTES TO DO
CHANGE: SAVEAC <Q2> ;SAVE AN AC
HRLI A,(<POINT 18,0>) ;MAKE BYTE POINTER TO HALFWORDS
ASH C,-1 ;DIVIDE BYTES BY 2 TO GET NUMBER OF -11 WORDS
JUMPE C,R ;RETURN IF NONE
CHAN1: ILDB Q2,B ;GET SOME DATA
IDPB Q2,A ;STORE IT
SOJG C,CHAN1 ;LOOP
RET ;RETURN
;ROUTINE TO CHANGE CONTIGUOUS BYTES IN -10 FORMAT TO SHUFFLED BYTES
;IN -11 FORMAT.
;ACCEPTS:
; A/ ADDRESS TO RECIEVE SHUFFLED BYTES
; B/ ILDB POINTER TO CONTIGUOUS BYTES
; C/ NUMBER OF BYTES TO DO
;RETURNS: +1
SHUFFL: PUSH P,Q2 ;SAVE A REGISTER
SHUF1: SOJL C,SHUF2 ;DONE QUIT
ILDB Q2,B ;GET FIRST CHARACTER
SOJL C,SHUF3 ;DONE AFTER 1 CHARACTER
ILDB D,B ;GET NEXT CHARACTER
LSH D,^D8 ;SHIFT INTO POSITION
IOR D,Q2 ;BUT CHARACTERS TOGETHER
HRLZM D,(A) ;STORE CHARACTERS
SOJL C,SHUF2 ;QUIT
ILDB Q2,B ;GET ANOTHER CHARACTER
SOJL C,SHUF4 ;QUIT
ILDB D,B ;GET LAST CHARACTER
LSH D,^D8 ;PUT INTO POSITION
IOR D,Q2 ;PUT TOGETHER
HRRM D,(A) ;STORE CHARACTER
AOJA A,SHUF1 ;NEXT WORD
SHUF2: POP P,Q2 ;RESTORE REGISTER
RET ;RETURN
SHUF3: HRLZM Q2,(A) ;STORE CHARACTER
JRST SHUF2 ;QUIT
SHUF4: HRRM Q2,(A) ;STORE CHARACTER
JRST SHUF2
;AS ASCII /ABCDE/ TO THE NEW FORM BYTE(1)0,0(7)B,A(1)0,0(7)D,C(1)0,0(7)E
;THIS IS DONE BECAUSE FOR DMA DEVICES (DIRECT MEMORY ACCESS) THAT
;THINK THEY'RE LOOKING AT AN -11 AND NOT A -10, SO WE MUST SHUFFLE THE
;DATA SO THEY DON'T FIND OUT THE TRUTH.
;ROUTINE TO ASK FOR THE LPT STATUS
;ROUTINE TO GET LPT STATUS. ON THE KL, THE -11 SUPPLIED THE STATUS
;TO THE -10 AS PACKED BYTES, WHICH THE LPTTLS ROUTINE UNPACKS. WE'LL
;CALL LPTTLS TOO, BUT WE'LL FIRST PACK THE BYTES SO THAT LPTTLS WON'T
;KNOW THAT WE'RE NOT AN -11 SENDING THE DATA.
NSIZE==26 ;NUMBER OF 8-BIT BYTES IN DEVICE DEPENTENT STATUS
;
; THE STATUS BLOCK IS IN THE FOLLOWING FORMAT:
;
; PDP11 WORD NUMBERS
;
; WORD 0 STATUS WORD 0 (DV.XXX)
; WORD 1 STATUS WORD 1 (DD.XXX)
; WORD 2 (HIGH 8 BITS) # BYTES OF DEVICE DEPENDENT INFO
; (LOW BYTE) # BYTES OF DEVICE REGISTERS (ALWAYS 20)
; WORD 3 (LOW BYTE) ACCUMULATED CHECKSUM (HIGH BYTE)RETRY COUNT (NOT ALL IMPL)
; LP20 DEVICE REGISTERS
; WORD 4 LPCSRA
; WORD 5 LPCSRB
; WORD 6 LPBSAD
; WORD 7 LPBCTR
; WORD 10 LPPCTR
; WORD 11 LPRAMD
; WORD 12 LPCBUF/LPCCTR
; WORD 13 LPTDAT/LPCKSM
OURTLS: SAVEPQ ;SAVE REGISTERS
HRRZ A,U ;GET UNIT NUMBER
IMULI A,LPERSZ ;POINT TO CORRECT BLOCK
ADD A,[POINT 8,LPERBF] ;POINT TO BUFFER
MOVE P6,A ;SAVE BUFFER POINTER
MOVE P5,A
MOVEI B,0 ;SET "DEVICE HUNG" AND "ERROR FROM -11" BITS TO 0
IDPB B,P5 ;STORE THOSE BITS
MOVEI Q2,0 ;START WITH 0'S FOR SECOND BYTE
CALL LPTRUE ;MAKE SURE PRINTER EXISTS
TXO Q2,.DVFNX+.DVFOL ;NO, SET BIT THAT SAYS SO,
;ALSO OFF LINE, OP INTERVENTION REQUIRED
MOVE B,Q2
MOVE D,LCRTAB(U) ;GET REGISTER BASE ADDRESS
SETZB Q3,P3 ;FIRST ASSUME THE REGISTERS ARE 0
TXNE B,.DVFNX ;PRINTER EXIST?
JRST OURTL1 ;NO, SO DON'T REFERENCE HARDWARE!
RDIO Q3,LPCSRA(D) ;GET STANDARD STATUS BITS
RDIO P3,LPCSRB(D) ;SPECIAL BITS
OURTL1: TXNN Q3,LPWOL ;IS PRINTER ON-LINE?
TXO B,.DVFOL ;NO, OFF, SO SAY SO
TXNE P3,LP1PER+LP1MPE+LP1RPE+LP1SYE ;PARITY ERROR, MEMORY PARITY ERROR, RAM PARITY ERROR, MASTER SYNC ERROR
TXOA B,.DVFHE!.DVFFE ;HARD ERROR ON ANY OF THESE CONDITIONS
;NOTE: THE KL FRONT END DOESN'T SET IT'S CORRESPONDING .DVFFE
;UNTIL A RETRY COUNT OF 10 RUNS OUT. HENCE SOMEONE MAY WANT
;TO IMPLEMENT THE RETRY FEATURE ON THE KS IF PROBLEMS ARISE.
TXNE Q2,.DVFNX ;CHECK FOR END OF FILE IF NO ERRORAND EXISTS
JRST NOTEOF ;EOF NOT POSSIBLE IF THERE'S AN ERROR
MOVEI A,7777 ;CHECK FOR COUNTER 0
TION A,LPBCTR(D) ;IS COUNTER 0? (ALL CHARACTERS BEEN PRINTED?)
TXO B,.DVFEF ;YES, SET EOF BIT
NOTEOF: IDPB B,P5 ;STORE VALUE OF REST OF STANDARD STATUS BITS
MOVEI B,0 ;FIRST WORD OF LPT STATUS IS ALL 0
IDPB B,P5
TXNE Q3,LPWPZR ;DID PAGE COUNTER REACH 0?
TXO B,MO%LPC ;YES
TXNE Q3,LPWCI ;UNDEFINED CHARACTER INTERRUPT?
TXO B,MO%LCI ;YES
TXNE P3,LPWDVN ;IS VFU ALRIGHT?
JRST [ TXNE Q3,LPERR ;NOT AN ERROR IF ERROR NOT SET
TXO B,MO%LVF ;NO
JRST .+1]
TXNE P3,LPWOVF ;DO WE HAVE AN OPTICAL VFU?
TXO B,MO%LVU ;YES
TXNE P3,LPWRPE ;WAS THERE A RAM PARITY ERROR?
TXO B,MO%RPE ;YES
IDPB B,P5 ;STORE LPT STATUS BYTE
MOVEI B,2 ;NUMBER OF DEVICE-DEPENDENT INFO
IDPB B,P5
MOVEI B,20 ;NUMBER OF DEVICE REGISTER BYTES
IDPB B,P5
TXNE Q2,.DVFNX ;CHECK FOR EXISTANT DEVICE
JRST LPNEXA ;DON'T READ REGISTERS
MOVEI A,0 ;NO RETRY
IDPB A,P5
RDIOB A,LPCKSM(D) ;GET CHECKSUM
IDPB A,P5 ;STORE CHECKSUM
IBP P5 ;MUST GET TO NEXT WORD HERE
HRLI P5,(<POINT 16,0>) ;SET UP FOR DEVICE REGISTERS
MOVEI A,10 ;NUMBER OF REGISTERS TO DUMP
LPDVDL: RDIO B,(D) ;READ A REGISTER
IDPB B,P5 ;STORE IN BUFFER
ADDI D,2 ;LOOK AT NEXT REGISTER
SOJG A,LPDVDL ;DO UNTIL ALL DONE
TXNN Q2,.DVFHE ;CHECK FOR HARDERR
JRST LPNEXD ;NO SYSERR REQUIRED
MOVEI A,NSIZE+FE%LEN ;GET LENGTH OF BUFFER NEEDED
MOVEI B,NSIZE+FE%SIZ
CALL ALCSEB ;ALLOCATE BA BUFFER
JRST LPNEXD ;NO BUFFER FORGET IT
SETZM FE%DTE+SEBDAT(A) ;SET NO DTE
MOVEI B,.FELPT ;GET THE DEVICE CODE
HRLI B,0(U) ;SET THE UNIT NUMBER
MOVEM B,FE%DEV+SEBDAT(A)
MOVNI D,NSIZE ;GET THE SIZE
HRLM D,FE%PTR+SEBDAT(A) ;SAVE COUNT OF WORDS
MOVEI C,NSIZE ;GET SIZE
MOVE D,P6 ;GET POINTER TO BUFFER
MOVE B,[POINT 8,FE%INF+SEBDAT(A)] ;POINTER TO DEVICE DATA
MOVEM C,FE%BYT+SEBDAT(A)
SYELP: ILDB P5,D ;GET BUFFER CHARACTERS
IDPB P5,B ;STORE CHARACTERS
SOJG C,SYELP
MOVE B,[-2,,[
SEBPTR 0,SBTEVC,SEC%FE
SEBPTR 0,SBTFNA,LPTSER]]
MOVE Q2,A ;SAVE POINTER TO ERROR BUFFER
CALL SEBCPY
JFCL ;FORGET IT IF ERROR
MOVE A,Q2 ;RESTORE BUFFER POINTER
CALL QUESEB ;QUEUE ERROR
LPNEXD: CALL CLRERR ;CLEAR ERRORS
LPNEXA: MOVE B,U ;LPTTLS EXPECTS UNIT IN B
MOVE D,P6 ;POINTER TO BEGINNING OF BUFFER IN D
MOVEI C,NSIZE ;NUMBER OF BYTES IN C
CALLRET LPTTLS ;GO MULL OVER STATUS AND RETURN
;
; ROUTINE TO CHECK FOR INTERRUPT ENABLE ON THE LP20
;
LP20IE: CALL LPTRUE ;CHECK TO SEE IF LINEPRINTER EXISTS
RET ;NOPE -- JUST RETURN
MOVEI A,LP1IEN ;GET INTERRUPT ENABLE FLAG
TIOE A,@LCRTAB(U) ;CHECK TO SEE IF IT IS SET
RET ;YES -- ALL OK
BUG(LP2IEN,<<U,D>>)
BSIO A,@LCRTAB(U) ;SET INTERRUPT ENABLE AND HOPE
RET ;RETURN
;ROUTINE CALLED BY SYSER RO DETERMINE OWING PROCESS AND
;COMPLETE THE SYSERR BLOCK
;
;
LPTSER: SETZ B ;SET UNIT (ONLY 1 FOR NOW)
JE LPOPN,(B),[ ;OPENED?
MOVNI C,-1 ;SAY UNASSIGNED
JRST LPFKS] ;STORE IT
LOAD B,LPFRK,(B) ;GET ID OF OWNER
HLRZ C,FKJOB(B) ;FIND FORK
HRLI C,0(B) ;UNIT
MOVE B,JOBDIR(C) ;DIRECTORY
HRLI B,USRLH ;SET UP USER NUMBER
MOVEM B,FE%DIR+SEBDAT(A) ;STORE DIR NUMBER
MOVE B,JOBPNM(C) ;GET NAME
MOVEM B,FE%NAM+SEBDAT(A)
LPFKS: MOVEM C,FE%FJB+SEBDAT(A)
MOVEI B,FE%INF ;START OF ERROR WORDS
HRRM B,FE%PTR+SEBDAT(A)
SETZM FE%ID+SEBDAT(A)
RET ;RESTURN
TNXEND
END