1
0
mirror of https://github.com/PDP-10/stacken.git synced 2026-04-20 08:46:31 +00:00
Files
Lars Brinkhoff 6e18f5ebef Extract files from tape images.
Some tapes could not be extracted.
2021-01-29 10:47:33 +01:00

753 lines
22 KiB
Plaintext
Raw Permalink Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
TITLE TCXKON - TC10C DEVICE DEPENDENT CODE FOR TAPSER V2045
SUBTTL T.HESS/TAH/TW/DPM 9-AUGUST-88
SEARCH F,S,DEVPRM
$RELOC
$HIGH
;THIS SOFTWARE IS FURNISHED UNDER A LICENSE AND MAY BE USED
; OR COPIED ONLY IN ACCORDANCE WITH THE TERMS OF SUCH LICENSE.
;
;COPYRIGHT (c) DIGITAL EQUIPMENT CORPORATION 1975,1976,1977,1978,1984,1986,1988.
;ALL RIGHTS RESERVED.
.CPYRT<1975,1988>
XP VTCXKN,2045 ;DEFINE VERSION NUMBER FOR STORAGE MAP
SALL
TCXKON::ENTRY TCXKON
;BYTE POINTERS
CTYUNI: POINT CI.UNS,T1,CI.UNP ;UNIT # IN STATUS REG
CTYFCN: POINT CI.CMS,T1,CI.CMP ;FCN CODE IN STATUS REG
;OFFSETS INTO TKBCCL
TKBUNI==TKBCCL+2 ;CURRENT UNIT SELECTED (-1 IF NONE)
TCXDMX==10 ;MAXIMUM DRIVES PER KONTROLLER
TCXHDN==TCXDMX-1 ;HIGHEST DRIVE NUMBER ON KONTROLLER
TCXELN==1 ;SIZE OF FEP TABLE
;DRIVER CHARARCTERISTICS
; TCX = TCXCNF
; MTA = MAGTAPE
; 0 = MAXIMUM DEVICES IN SYSTEM (NO LIMIT)
; K.TC1 = KONTROLLER TYPE
; TCXDMX = MAXIMUM DRIVES PER KONTROLLER
; TCXHDN = HIGHEST DRIVE NUMBER ON KONTROLLER
; MDSEC0 = SECTION FOR KDB/UDB
; MDSEC0 = SECTION FOR DDB
DRVCHR (TCX,MTA,0,K.TC1,TCXDMX,TCXHDN,MDSEC0,MDSEC0,<DR.XAD!DR.MCD!DR.GCC!DR.DDN>)
.ORG TKBUDB ;START OF TC10C SPECIFIC DATA
TCXUTB:! BLOCK TCXDMX ;TABLE OF POINTERS TO UDBS
TCXIUM:! BLOCK TCXDMW ;IGNORE DRIVE MASK
TCXNUM:! BLOCK TCXDMW ;NEW DRIVE MASK
TCXKLN:! ;LENGTH OF KDB
.ORG
.ORG TUBLEN
TCXICS:! BLOCK 1 ;LAST ERROR INITIAL STATUS
TCXFCS:! BLOCK 1 ;LAST ERROR FINAL STATUS
TCXULN:! ;LENGTH OF UDB
.ORG
TCXKDB: KDBBEG (TCX,TCXKLN)
SETWRD (KDBNAM,<SIXBIT/MT/>) ;KONTROLLER NAME
SETWRD (KDBIUN,<TKBUDB>) ;INITIAL POINTER TO UDBS
SETWRD (KDBCUN,<TKBUDB>) ;CURRENT POINTER TO UDBS
SETWRD (KDBIUM,<TCXIUM>) ;OFFSET TO IGNORE UNIT MASK
SETWRD (KDBNUM,<TCXNUM>) ;OFFSET TO NEW UNIT MASK
IFN FTMP,<SETWRD (TKBFCT,<TKBICT##>)> ;FAIRNESS COUNTER FOR QUEUED I/O
KDBEND
TCXUDB: UDBBEG (TCX,TCXULN)
SETWRD (UDBNAM,<SIXBIT/MT/>) ;DRIVE NAME
SETWRD (TUBIEP,<-TCXELN,,TCXICS>) ;INITIAL ERROR POINTER
SETWRD (TUBFEP,<-TCXELN,,TCXFCS>) ;FINAL ERROR POINTER
UDBEND
EQUATE (LOCAL,0,<TCXULP,TCXULB,TCXCKT>)
EQUATE (LOCAL,CPOPJ##,<TCXCMD,TCXLOD,TCXEDL>)
EQUATE (LOCAL,CPOPJ1##,<TCXONL>)
EQUATE (LOCAL,CPOPJ2##,<TCXBSY>)
TCXICD==TAPICD## ;PROTOTYPE INTERRUPT CODE ADDRESS
TCXICL==TAPICL## ;PROTOTYPE INTERRUPT CODE ADDRESS
TCXINT==TAPINT## ;INTERRUPT SERVICE
TCXDSP: DRVDSP (TCX,TAPCHN##,TDVDDB##,TDVLEN##,TPMDIA##)
TPK (TCX,NO,16K) ;SERVICE DEPENDENT DISPATCH
;DEFAULT MONGEN'ED DEVICE TABLE
DEFMDT: MDKL10 (7,220,0,0,<MD.KON>) ;DEVICE CODE 220
MDTERM ;TERMINATE TABLE
;DEFINITIONS FOR CONI/CONO STATUS REGISTER
;CONI BITS LH
CI.EOF==1B0 ;TAPE MARK SEEN
CI.EOT==1B1 ;END OF TAPE
CI.BOT==1B2 ;LOAD POINT
CI.FPT==1B3 ;FILE PROTECT (WRITE LOCK)
CI.HNG==1B4 ;XPORT HUNG
CI.REJ==1B5 ;COMMAND REJECT
CI.REW==1B6 ;TAPE REWINDING
CI.RCC==1B7 ;READ STATUS
CI.WCC==1B8 ;WRITE STATUS
CI.DPE==1B9 ;DATA PARITY ERROR
CI.CER==1B10 ;PE CORRECTED ERROR
CI.RCE==1B11 ;READ/COMPARE ERROR
CI.RLD==1B12 ;RECORD LENGTH DIFFERS
CI.OVR==1B13 ;DATA LATE (OVERRUN)
CI.CES==2 ;CHANNEL ERROR BYTE SIZE
CI.CEP==^D15 ;CHANNEL ERROR BYTE POSITION
CE.DPE==1 ;DATA PARITY ERROR
CE.CWE==2 ;CONTROL WORD PARITY ERROR
CE.NXM==3 ;NON-EXISTENT MEMORY
CI.RDY==1B17 ;UNIT READY
;CONI BITS RH
CI.UNS==3 ;UNIT # BYTE SIZE
CI.UNP==^D20 ;UNIT # BYTE POSITION
CI.CMS==5 ;COMMAND BYTE SIZE
CI.CMP==^D25 ;COMMAND BYTE POSITION
CM.FNO==00 ;NO-OP / CLEAR FORMATTER
CM.FUR==10 ;UNIT READY
CM.FRW==01 ;REWIND
CM.FUN==11 ;REWIND / UNLOAD
CM.FRD==02 ;READ FORWARD
CM.FR1==12 ;READ FORWARD TO EOF
CM.FRB==22 ;READ REVERSE
CM.FRC==03 ;READ / COMPARE FORWARD
CM.FR2==13 ;READ / COMPARE FORWARD TO EOF
CM.FBC==23 ;READ / COMPARE REVERSE
CM.FB1==33 ;READ / COMPARE REVERSE TO EOF
CM.FWR==04 ;WRITE
CM.FWL==14 ;WRITE AFTER LONG ERG
CM.FTM==05 ;WRITE TAPE MARK
CM.FLG==15 ;WRITE 3" BLANK TAPE
CM.FFB==06 ;SPACE FORWARD RECORD
CM.FFF==16 ;SPACE FORWARD FILE
CM.FBB==07 ;SPACE BACKWARD RECORD
CM.FBF==17 ;SPACE BACKWARD FILE
CI.CDS==1B26 ;CORE DUMP STATUS
CI.CWW==1B27 ;CONTROL WORD WRITTEN
CI.WEP==1B28 ;WRITE EVEN PARITY
CI.NRZ==1B29 ;PE/NRZI STATUS
CI.CKS==1B31 ;CHECK STATUS
CI.JBD==1B32 ;JOB DONE
CI.PIA==7 ;MASK FOR PIA
NOPMSK==701000 ;PRESERVE UNIT AND MODE
;CONO BITS
CO.UNS==CI.UNS ;UNIT # BYTE SIZE
CO.UNP==CI.UNP ;UNIT # BYTE POSITION
CO.CMS==CI.CMS ;COMMAND BYTE SIZE
CO.CMP==CI.CMP ;COMMAND BYTE POSITION
CO.CDM==1B26 ;CORE DUMP MODE
CO.WCW==1B27 ;WRITE CONTROL WORD
CO.WEP==1B28 ;WRITE EVEN PARITY
CO.GO==1B30 ;EXECUTE COMMAND
CO.LCR==1B31 ;LOAD COMMAND REGISTER
CO.JBD==1B32 ;JOB DONE
CO.PIA==7 ;MASK FOR PIA
;DATAO / DATAI BITS
DO.STP==1B21 ;ABORT CURRENT OPERATION
DI.IDB==1B17 ;PE ID BURST DETECTED
DI.CHS==3 ;CHAR CNT BYTE SIZE
DI.CHP==^D20 ;CHAR CNT BYTE POSITION
;COUNTER FOR WAIT AT TCXSIO
MTWTTM==4000
SUBTTL TAPE INTERUPT SERVICE
;CALLED FROM TAPSER WITH W := KDB
TCXISR: XCT KDBCNI(W) ;GET STATUS REGISTER
MOVE T2,T1 ;GET COPY
ANDI T2,76017 ;GET BITS OF INTEREST
CAIN T2,CI.JBD+TAPCHN## ;CHECK FOR IDLE INTERUPT
JRST [PUSHJ P,CKSTRT ;CHECK IF STARTED
POPJ P, ;NOT STARTED - RETURN
JRST .+1]
LDB T2,CTYUNI ;GET UNIT SELECTED
PUSHJ P,SETUDB## ;SET UP U
JRST SETM1 ;NON-EX UNIT
XCT KDBCNI(W) ;GET STATUS AGAIN
MOVEM T1,TCXFCS(U) ;SAVE IN UDB
LDB T2,CTYFCN ;GET FCN
CAIE T2,CM.FUR ;UNIT READY?
CAIN T2,CM.FNO ; OR NO-OP
JRST TCXSEL ;YES - START I/O IF OK
PUSHJ P,CHKIRB## ;GET IORB
JRST TAPDIS## ;NONE - DISMISS INT.
MOVE T3,TCXFCS(U) ;GET STATUS IN T3
MOVSI T2,TUSBOT## ;CLEAR BOT INDICATION
ANDCAM T2,TUBSTS(U) ; WE WILL SET IT AGAIN IF NECESSARY
LDB T2,PRBFCN## ;GET DESIRED FCN
CAILE T2,TCIMAX ;CHECK VALIDITY
JRST TAPIFI## ;ILLEGAL TRANSFER VECTOR
JRST @TCIDSP(T2) ;DO IT
TCIDSP: IFIW TAPIFI## ;(00) ILLEGAL
IFIW TCIRD ;(01) READ
IFIW TCIWT ;(02) WRITE
IFIW TAPIFI## ;(03) READ BACKWARDS (ILLEGAL)
IFIW TCISR ;(04) SKIP RECORD
IFIW TCIBR ;(05) BACKSPACE RECORD
IFIW TCISF ;(06) SKIP FILE
IFIW TCIBF ;(07) BACKSPACE FILE
IFIW TCIEG ;(10) ERASE GAP
IFIW TAPIFI## ;(11) DSE (ILLEGAL)
IFIW TCIRW ;(12) REWIND
IFIW TCIUN ;(13) REWIND / UNLOAD
IFIW TCITM ;(14) WRITE TAPE MARK
IFIW TAPIFI## ;(15) ILLEGAL
IFIW TCIRD ;(16) CORRECTION READ
IFIW TCIRD ;(17) READ LOW THRESHOLD
TCIMAX==.-TCIDSP-1
;HERE TO CHECK FOR IDLE STATUS INTERUPT - SEE IF ALREADY STARTED
;C(T1) IS STATUS REGISTER - PRESERVED IF CHL STARTED
CKSTRT: MOVSI T2,TKSSTD##
TDNE T2,TKBSTS(W) ;STARTED?
JRST CPOPJ1## ;YES - SKIP RETURN
LDB T2,CTYUNI ;GET UNIT #
PUSHJ P,SETUDB## ;SET UP U := UDB
JRST SETM1
XCT KDBCNI(W) ;GET STATUS REG
MOVSI T2,TKSOFL##
TLNN T1,(CI.RDY!CI.REW) ;CHECK GOODNESS
IORM T2,TUBSTS(U) ;UNIT WENT OFF-LINE!
PUSHJ P,CLRCTL ;CLR CTL
SETM1: MOVNI T1,1 ;CAUSE SCHEDULING
POPJ P, ;RETURN
;ROUTINE TO MAKE CONTROLLER IDLE
CLRCTL:
TCXIDL: PUSH P,T1 ;SAVE IORB
HLLZS @KDBCSO(W) ;NO MORE INTS
XCT KDBCNI(W) ;GET CTL STATUS REG
ANDI T1,NOPMSK ;PRESERVE UNIT # ETC.
IORI T1,CO.LCR!CO.GO ;...
XCT KDBCNO(W) ;DO NO-OP TO DRIVE W/ PIA=0
SETOM TKBUNI(W) ;NO UNIT SELECTED
PJRST TPOPJ## ;RETURN
;HERE TO RESET ACTIVE I/O
TCXRES: MOVEI T2,DO.STP ;STOP CURRENT COMMAND
XCT KDBDTO(W) ;AND CLEAR CHL ICP
MOVSI T2,TKSSEL## ;SELECT BIT
HRRZ T1,TUBQUE(U) ;GET HEAD OF Q
JUMPE T1,CLRCTL ;NONE - EXIT
TDNE T2,TKBSTS(W) ;SELECTED?
PUSHJ P,ZAPEXL ;YES - FIX IOLIST
PJRST CLRCTL ;CLEAR WORLD & EXIT
;ROUTINE TO CAUSE AN INTERUPT TO FORCE A SCHEDULE CYCLE
TCXSCH: MOVE T1,UDBPDN(U) ;PHYSICAL DRIVE NUMBER
LSH T1,^D35-CO.UNP
IORI T1,<CM.FNO>B<CO.CMP>!CO.GO!CO.LCR+TAPCHN## ;DO NO-OP TO UNIT
MOVEI T2,CI.JBD ;ENABLE FOR JOB DONE
CONO PI,PI.OFF ;AVOID RACE
HRRM T2,@KDBCSO(W) ;...
XCT KDBCNO(W) ;...
PJRST ONPOPJ## ;EXIT
TCXCFG: XMOVEI T1,TCXMDT## ;MONGEN'ED DEVICE TABLE
XMOVEI T2,DEFMDT ;DEFAULT TABLE
MOVNI T3,1 ;NO MASSBUS UNIT OR DRIVE INFORMATION
MOVEI T4,MD.KON ;MATCH ON KONTROLLER DEFINITION
PUSHJ P,AUTMDT## ;SCAN THE TABLES
JRST CPOPJ1## ;NO MATCHES
PUSHJ P,SAVE1## ;SAVE P1
MOVSI T1,0 ;I/O BUS-STYLE CHANNEL
PUSHJ P,AUTCHN## ;BUILD A CHANNEL DATA BLOCK
POPJ P, ;NO CORE
HLRZ T1,P1 ;GET MASSBUS UNIT NUMBER
PUSHJ P,AUTKDB## ;BUILD A KDB
POPJ P, ;GIVE UP IF NO CORE
PUSHJ P,TAPCSA## ;SET UP CSO CONI ADDRESS
PUSHJ P,CLRCTL ;CLEAR WORLD
TCXCF1: MOVSI P1,-1 ;NO MASSBUS UNIT,,DRIVE 0
TCXCF2: PUSHJ P,TCXDRV ;AUTOCONFIGURE A SINGLE DRIVE
JFCL ;IGNORE ERRORS
HRRZ T1,P1 ;GET DRIVE NUMBER
CAIGE T1,TCXDMX-1 ;DONE ALL DRIVES?
AOJA P1,TCXCF2 ;LOOP BACK FOR MORE
PUSHJ P,CLRCTL ;CLEAR WORLD
JRST CPOPJ1## ;TRY ANOTHER DEVICE ON CHANNEL
TCXDRV: XMOVEI T1,TCXMDT## ;MONGEN'ED DEVICE TABLE
XMOVEI T2,DEFMDT ;AND THE DEFAULT TABLE
MOVE T3,P1 ;DRIVE INFORMATION
PUSHJ P,AUTMDT## ;FOUND A DRIVE MATCH?
POPJ P, ;NO
MOVE T2,T1 ;COPY DRIVE INFO
TRO T2,TUCIRD##+TUCD80##+TUCD16##+K.TC1
HRLZ T1,P1 ;PHYSICAL DRIVE NUMBER
HRR T1,P1 ;UDB TABLE INDEX
XMOVEI T3,HNGTBL ;POINT TO HUNG TIMER TABLE
PUSHJ P,TAPDRV## ;BUILD AND LINK UP UDB AND DDB
JFCL ;FAILED
JRST CPOPJ1## ;RETURN
SUBTTL START I/O
;ROUTINE TO START I/O
;USER JOB MUST BE NAILED DOWN - CAUSE SELECTION INTERUPT
;OR JUST START I/O IF UNIT ALREADY SELECTED
TCXSIO: LDB T3,PRBFCN## ;GET FCN
MOVEI T2,<CM.FUR>B<CO.CMP> ;ASSUME UNIT READY WANTED
MOVSI T1,TKSOFL## ;BETTER SEND NO-OP IF UNIT
TDNN T1,TUBSTS(U) ; WAS DISCOVERED OFF-LINE
CAIN T3,RB.FYB ;JUST WANT STATUS?
JRST [MOVEI T2,<CM.FNO>B<CO.CMP> ;YES - USE NO-OP
SETOM TKBUNI(W) ;CLEAR SELECTED UNIT
JRST .+1]
MOVE T1,UDBPDN(U) ;PHYSICAL DRIVE NUMBER
CAMN T1,TKBUNI(W) ;SELECT OR START?
JRST TMSTRT ;START IT
LSH T1,^D35-CO.UNP ;PUT IN PROPER PLACE
IORI T1,CO.GO!CO.LCR+TAPCHN##(T2) ;INT ON UNIT READY OR NOOP
MOVE T2,KDBCNI(W) ;GET CONI FOR TU'S KONTROLLER
TLO T2,(CONSO 0) ;CHANGE TO CONSO
HRRI T2,CI.JBD ;JOB DONE BIT
MOVEI T3,MTWTTM ;UPPER LIMIT WAIT COUNTER
XCT T2 ;DONE YET
SOJG T3,.-1 ;WAIT SOME MORE
MOVEI T2,CI.JBD ;THIS SHOULD COME UP
CONO PI,PI.OFF ;AVOID RACE
HRRM T2,@KDBCSO(W) ;SET IN CONSO
XCT KDBCNO(W) ;SELECT UNIT
PJRST ONPOPJ## ;WAIT FOR INT
;HERE TO START AN ALREADY SELECTED UNIT
TMSTRT: XCT KDBCNI(W) ;GET CTL STATUS
MOVEM T1,TCXFCS(U) ;SAVE IN UDB
;;; FALL INTO TCXSEL
;HERE WHEN DESIRED DRIVE HAS BEEN SELECTED
;CHECK FOR ERRORS AND UNIT IDLE
TCXSEL: PUSHJ P,CHKIRB## ;GET IORB
JRST TAPDIS## ;NONE
MOVSI T2,TKSOFL## ;CHECK IF OFF-LINE
TDNE T2,TUBSTS(U) ;...
JRST TCXOFL ;YES - TELL UPPER LEVEL
MOVE T3,TCXFCS(U) ;GET STATUS REG
MOVSI T4,TUSWTL## ;WRITE LOCKED BIT
MOVE T2,[ANDCAM T4,TUBSTS(U)]
TLNE T3,(CI.FPT) ;WRITE LOCKED?
MOVE T2,[IORM T4,TUBSTS(U)] ;YES - CORRECT INSTR
XCT T2 ;SET/CLEAR BIT
LDB T2,PRBFCN## ;SEE WHAT FCN
CAIN T2,RB.FYB ;STATUS CHECK?
JRST TCXSTS ;YES - GO HANDLE
TLNE T3,(CI.HNG!CI.REJ!<CE.NXM>B<CI.CEP>)
JRST TCXOFL ;UNIT OFFLINE
PUSH P,T2 ;SAVE T2
MOVE T2,KDBICP(W) ;SET UP ICPC
XCT KDBDTO(W) ;...
POP P,T2 ;RESTORE T2
PUSHJ P,SETCMD ;SET UNIT,PAR,DENS,COMPAT,FCN
PJRST TCIDON ;WRITE LOCKED
MOVEI T1,CO.GO!CO.LCR+TAPCHN##(T2) ;ADD PIA & MOVE TO T1
MOVEI T2,CI.JBD
CONO PI,PI.OFF ;SAVE US FROM OTHERS
HRRM T2,@KDBCSO(W) ;SET UP INT MASK
XCT KDBCNO(W) ;START DEVICE
CONO PI,PI.ON ;OK NOW
NXTINT: MOVEI T1,0 ;MORE INTS COMING
POPJ P, ;EXIT THIS INT
;HERE TO GET UNIT STATUS UPDATE ON REQUEST
TCXSTS: TLNE T3,(CI.HNG) ;IF HUNG?
JRST TCXOFL ;MUST BE OFF-LINE
TLNN T3,(CI.RDY) ;UNIT READY?
JRST TCIDON ;NO - DISMISS
TLNN T3,(CI.BOT) ;AT LOAD POINT?
TLNN T3,(CI.REW) ;OR NOT REW'D
PUSHJ P,REWDON## ;YES - SET BOT / CLR REW
PJRST TCIDON ;EXIT INTERUPT
;HERE IF NO STATUS WORTH REMEMBERING
TCXOFL: MOVSI T2,RB.SOL ;SET OFF-LINE STATUS
IORM T2,TRBSTS(T1)
MOVSI T2,TKSOFL## ;CLEAR BIT IN UDB
ANDCAM T2,TUBSTS(U)
PUSHJ P,CLRCTL ;RESET CTL
PJRST TCIDON ;AND RETURN
SUBTTL COMMAND SETUP
;ROUTINE TO SET UP CMD
;T1 := IORB FOR THIS REQUEST
;T3 CONTAINS CONI MTS, - DESTROYED
;T2 := COMMAND FOR CTL ON EXIT
SETCMD: LDB T4,PRBFCN## ;GET DESIRED FCN
SKIPN T2,IOFTAB(T4) ;CHECK LEGAL
JRST SETILG ;NOPE - ERROR
TLNE T2,(WRTOP) ;WRITING?
JRST SETCMW ;YES - CHECK WRITE-LOCKED
TLNE T2,(REWOP) ;REWINDING?
JRST CHKBOT ;YES - CHECK BOT
SETCM1: MOVE T2,UDBPDN(U) ;PHYSICAL DRIVE NUMBER
LSH T2,^D35-CO.UNP ;WHERE IT WILL DO THE MOST GOOD
IOR T2,IOFTAB(T4) ;GET FCN CODE
TLZ T2,(REWOP!WRTOP) ;CLEAR UNWANTED BITS
HRRZ T4,TRBXCW(T1) ;GET DATA ADDRS OR SPACING COUNT
TLZE T2,(DATOP) ;DATA?
JRST [PUSHJ P,SETCBX ;DO CTL SPECIFIC SETUP
JRST SETCM2] ;PROCEED
TLZN T2,(SPCOP) ;SPACING OP?
JRST [MOVEI T4,0 ;NO - ILLEGAL DATA REQUEST
JRST SETCM2] ;SET IN CHL AREA
MOVNI T4,-1(T4) ;GET COUNT -1 NEGATED
SKIPN T4
SETO T4,
LSH T4,4 ;ONLY 14 BITS OF INFO
HRLZM T4,TKBCCL(W) ;SAVE IN CHL PGM AREA
XMOVEI T4,TKBCCL(W) ;SET ADDRS
SETZM TKBCCL+1(W) ;CHL HALT FOR DF10
SETCM2: MOVEM T4,@KDBICP(W) ;PUT IN CORRECT PLACE
LDB T4,PRBMOD## ;GET DESIRED MODE
CAIN T4,RB.MCD ;CORE-DUMP?
IORI T2,CO.CDM ;YES - SET BIT
MOVEI T4,RB.D16 ;1600 BPI
DPB T4,PRBDEN## ;CORRECT DENSITY
PJRST CPOPJ1## ;GIVE GOOD RETURN
;SET IMPROPER MODE AND RETURN
SETILG: MOVSI T2,RB.SIL!RB.SER ;ILLEGAL OP
IORM T2,TRBSTS(T1) ;SET IN IORB
POPJ P, ;ERROR RETURN
;HERE IF WRITING - CHECK WRLK
SETCMW: TLNN T3,(CI.FPT) ;WRITE LOCKED?
JRST SETCM1 ;NO - PROCEED
MOVSI T2,RB.SLK!RB.SER ;AND IN IORB
IORM T2,TRBSTS(T1) ;...
POPJ P, ;ERROR RETURN
;ROUTINE TO SETUP CMD LIST TERMINATION WORD FOR DF10
;T4 := ADDRS OF CHL PGM
SETCBX: HLRZ T3,TRBEXL(T1) ;END OF XFER LIST
PUSH P,T2 ;SAVE AN AC
MOVEI T2,TKBCCL(W) ;HANDY ZERO
MOVEM T2,0(T3) ;CHL JUMP TO ZERO
POP P,T2 ;RESTORE USED AC
SETZM TKBCCL(W) ;GRNTEE ZERO
POPJ P, ;RETURN
;HERE TO CHECK ALREADY AT BOT - SUPPRESS REWIND
CHKBOT: TLNE T3,(CI.BOT) ;LOAD POINT?
PJRST REWDON## ;YES - NO NEED TO REWIND
JRST SETCM1 ;NO - START REWIND
;TABLE FOR I/O FUNCTIONS - ALREADY IN POSITION
DEFINE IOT(CMD,FLGS) <
FLGS+<CMD>B<CO.CMP>
>
DATOP==1B0 ;DATA XFER OPERATION
SPCOP==1B1 ;SPACING OPERATION
WRTOP==1B2 ;WRTITE OPERATION
REWOP==1B3 ;REWIND OPERATION
IOFTAB: 0 ;0 - ILLEGAL
IOT(CM.FRD,DATOP) ;1 - READ
IOT(CM.FWR,DATOP!WRTOP) ;2 - WRITE
0 ;3 - READ BACKWARDS (ILLEGAL)
IOT(CM.FFB,SPCOP) ;4 - FORWARD SPACE BLOCK
IOT(CM.FBB,SPCOP) ;5 - BACKWARD SPACE BLOCK
IOT(CM.FFF,SPCOP) ;6 - FORWARD SPACE FILE
IOT(CM.FBF,SPCOP) ;7 - BACKSPACE FILE
IOT(CM.FLG,WRTOP) ;10 - WRITE LONG GAP
0 ;11 - DATA SECURITY ERASE (ILLEGAL)
IOT(CM.FRW,REWOP) ;12 - REWIND
IOT(CM.FUN,0) ;13 - REWIND / UNLOAD
IOT(CM.FTM,WRTOP) ;14 - WRITE TAPE MARK
0 ;15 - WAIT FOR KONTROLLER IDLE (ILLEGAL)
IOT(CM.FRD,DATOP) ;16 - CORRECTION READ
IOT(CM.FRD,DATOP) ;17 - READ LOW THRESHOLD
;HUNG TIMER TABLE
EXP ^D320 ;MAXIMUM TIMEOUT VALUE
HNGTBL: BYTE(9) ^D000,^D031,^D031,^D000 ;IL,RD,WT,RB
BYTE(9) ^D031,^D031,^D320,^D320 ;SR,BR,SF,BF
BYTE(9) ^D031,^D000,^D150,^D150 ;LG,SE,RW,RU
BYTE(9) ^D031,^D031,^D031,^D031 ;TM,YB,CR,RL
SUBTTL READ
;HERE ON DONE INTERUPT FOR READ
TCIRD: PUSHJ P,TCCKMV ;SEE IF TAPE MOVED
JSP T4,TCERD0 ;NO - PROBS
PUSHJ P,CHRCT ;GET CHARACTER COUNT
JRST [MOVSI T4,RB.STL
IORM T4,TRBSTS(T1)
JRST .+1]
MOVEM T2,TRBRCT(T1) ;SAVE COUNT IN IORB
MOVE T3,TCXFCS(U) ;RESTORE STATUS
TLNE T3,(<CE.NXM>B<CI.CEP>) ;CHL ERRORS?
JRST TCECHN ;YES - HANDLE
PUSHJ P,TCSTM ;ENCOUNTER EOF?
JRST TCIRD1 ;NO - GO ON
AOS TUBFIL(U) ;PLUS 1 MORE FILE
TCIRD1: TRNE T3,CI.CKS ;CHECK BADNESS
JSP T4,TCERD1 ;ERROR - HANDLE
MOVE T2,TRBRCT(T1) ;GET CHAR COUNT FOR THIS RECORD
ADDM T2,TUBCRD(U) ;AND UPDATE STATISTICS
;HERE TO FINISH INTERUPT AND EXIT TO TAPSER
TCIDON: PUSHJ P,ZAPEXL ;CLEAN UP
MOVE T3,UDBPDN(U) ;PHYSICAL DRIVE NUMBER
MOVEM T3,TKBUNI(W) ;AND SAVE IT FOR LATER CHECK
HLRZ T3,TRBSTS(T1) ;LOOK AT FLAGS
JUMPE T3,CPOPJ## ;RETURN IF NONE
MOVSI T2,RB.EXC ;ELSE SET EXCEPTION
IORM T2,TRBLNK(T1) ;IN IORB
POPJ P, ;AND RETURN
;ROUTINE TO FIXUP DF10 XFER LIST
ZAPEXL: HLRZ T2,TRBEXL(T1) ;PNTR TO END OF XFER LIST
JUMPE T2,CPOPJ## ;RETURN IF NONE
SETZM 0(T2) ;CLEAR IT
POPJ P, ;RETURN
SUBTTL WRITE
;HERE ON DONE INTERUPT FOR WRITE
TCIWT: PUSHJ P,TCCKMV ;DID IT MOVE
JSP T4,TCEWT0 ;NO - TRY TO FIX
TLNE T3,(<CE.NXM>B<CI.CEP>) ;CHL ERROR?
JRST TCECHN ;YES - LOOK AT THAT
MOVSI T2,RB.SET ;NOW CHECK EOT
TLNE T3,(CI.EOT) ;???
IORM T2,TRBSTS(T1) ;SET INFO IN IORB
TRNE T3,CI.CKS ;EVERYTHING OK?
JSP T4,TCEWT1 ;NO - TRY TO FIX
PUSHJ P,CHRCT ;GET CHARACTER COUNT
JFCL ;DON'T CARE
ADDM T2,TUBCWR(U) ;ADD TO STATS
PJRST TCIDON ;AND EXIT
;HERE ON DONE INTERUPT FOR WRITE TAPE MARK
TCITM: MOVSI T2,RB.SET ;JUST IN CASE
TLNE T3,(CI.EOT) ;WE SAW A TI
IORM T2,TRBSTS(T1) ;SET FLG IF SEEN
TRNE T3,CI.CKS ;ANYTHING WRONG?
JSP T4,TCEWT1 ;YES - SORRY
SETZM TUBREC(U) ;ZEROTH RECORD
AOS TUBFIL(U) ;AND 1 MORE FILE
PJRST TCIDON ;EXIT
;ROUTINE SET SAY WE'VE SEEN A TAPE MARK
;ALSO RESETS RECORD COUNTER
TCSTM: TLNN T3,(CI.EOF) ;SEEN EOF?
POPJ P, ;NO - RETURN
MOVSI T2,RB.STM ;IORB FLAG ALSO
IORM T2,TRBSTS(T1) ;...
SETZM TUBREC(U) ;CLEAR RECORD COUNT
PJRST CPOPJ1## ;SKIP RETURN FOR FURTHER PROCESSING
SUBTTL REWIND/UNLOAD/BACKSPACE RECORD
;HERE ON INTERUPT AFTER STARTING REWIND
TCIRW: TLNE T3,(CI.HNG!CI.REJ) ;CHECK BADNESS
JSP T4,TCERW ;HANDLE PROBLEM
TCIUN: MOVSI T2,TUSREW## ;SAY WE ARE REWINDING
IORM T2,TUBSTS(U) ;...
TLNE T3,(CI.BOT) ;ALREADY DONE?
PUSHJ P,REWDON## ;YES - CLEAN UP THEN
SETZM TUBREC(U) ;IN CASE WE DON'T FINISH
SETZM TUBFIL(U) ;CLEAR THESE NOW
PJRST TCIDON ;AND EXIT
;HERE ON DONE INTERUPT FROM BACKSPACE RECORD/FILE
TCIBF:!
TCIBR: TLNE T3,(CI.HNG!<CE.NXM>B<CI.CEP>) ;DEVICE PROBS?
JSP T4,TCERD1 ;WHOOPS PROBLEM
PUSHJ P,TCSTM ;LOOK FOR TM
JRST TCIBR1 ;NONE SEEN
SOS TUBFIL(U) ;ONE LESS FILE
TCIBR1: SOS TUBREC(U) ;ALSO ONE LESS RECORD
TLNN T3,(CI.BOT) ;SEE IF WE CRASHED INTO BOT
PJRST TCIDON ;NO - DONE
MOVSI T2,RB.SBT!RB.SNM ;YES - LITE BITS
SKIPN TUBREC(U) ;TRY TO GUESS IF TAPE MOVED
SKIPE TUBFIL(U) ; BY SEEING IF AT LOGICAL BOT
TLZ T2,RB.SNM ;FIRST TIME HERE
IORM T2,TRBSTS(T1) ;SET RESULT IN IORB
MOVSI T2,TUSBOT## ;AND UDB
IORM T2,TUBSTS(U) ;...
SETZM TUBREC(U) ;GET THINGS RIGHT
SETZM TUBFIL(U)
PJRST TCIDON ;EXIT
SUBTTL SKIP RECORD/FILE/ERASE GAP
;HERE ON DONE INTERUPT FROM SKIP FORWARD RECORD/FILE
TCISF:!
TCISR: PUSHJ P,TCCKMV ;SEE IF WE MOVED?
JSP T4,TCERD0 ;NOPE
TRNE T3,CI.CKS ;CHECK ERRORS
JSP T4,TCERD1 ;HANDLE IT
PUSHJ P,TCSTM ;CHECK FOR TAPE MARK
JRST TCIDON ;NO TAPE MARK
AOS TUBFIL(U) ;INCR FILE COUNTER
JRST TCIDON ;AND EXIT
;HERE ON DONE INTERUPT FROM ERASE GAP
TCIEG: MOVSI T2,RB.SET ;IN CASE TAPE INDICATE
TLNE T3,(CI.EOT) ;SEEN ONE?
IORM T2,TRBSTS(T1) ;YES - SET BIT
TLNE T3,(CI.HNG!CI.REJ!<CE.NXM>B<CI.CEP>) ;ERROR ALLOWED
JRST TCEWT1 ;YES - TREAT IT
PJRST TCIDON ;EXIT INT
SUBTTL ERROR PROCEDURES
;HERE FOR CHANNEL ERROR
TCECHN: PUSHJ P,SAVE1## ;SAVE P1
MOVEI T2,CHENXM## ;ASSUME NXM
TLC T3,(<CE.NXM>B<CI.CEP>) ;COMPLEMENT BITS
TLCE T3,(<CE.NXM>B<CI.CEP>) ;NXM IF BOTH ON!
MOVEI T2,CHEMPE## ;ELSE PARITY ERROR
PUSH P,T1 ;SAVE IORB
MOVE T1,KDBICP(W) ;PNTR TO CCW
MOVE P1,KDBCHN(W) ;PNTR TO CHL DATA BLOCK
PUSHJ P,0(T2) ;CALL ROUTINE
POP P,T1 ;RESTORE IORB PNTR
MOVSI T2,RB.SER!RB.SED
IORM T2,TRBSTS(T1) ;SET BITS
PJRST TCIDON ;RETURN
;ROUTINE TO DETERMINE IF TAPE MOVED (DIVINATION)
TCCKMV: TLNE T3,(CI.HNG!CI.REJ)
POPJ P, ;TRY THIS FOR NOW
AOS TUBREC(U) ;MOVIN' ALONG
JRST CPOPJ1## ;SKIP RETURN
;ERRORS DETECTED DURING WRITE OPERATIONS
TCEWT0: MOVSI T2,RB.SNM!RB.SED ;TAPE DIDN'T MOVE
IORM T2,TRBSTS(T1)
TCEWT1: PUSHJ P,TCEANL ;ANALYSE ERROR
MOVSI T2,RB.SLK ;CHECK FOR WRITE LOCK
TLNE T3,(CI.FPT)
IORM T2,TRBSTS(T1) ;YES - SET BIT
PJRST TCIDON ;EXIT INTERUPT
;ERRORS DETECTED DURING READ / SPACING OPS
TCERD0: MOVSI T2,RB.SNM!RB.SED ;TAPE DIDN'T MOVE
IORM T2,TRBSTS(T1)
TCERD1: PUSHJ P,TCEANL ;ERROR ANALYSIS
PJRST TCIDON ;EXIT INT
;PROBLEM STARTING REWIND
TCERW: MOVSI T2,RB.SED!RB.SNM!RB.SOL
IORM T2,TRBSTS(T1) ;SET OFF-LINE ETC.
PUSHJ P,CLRCTL ;RESET CTL
PJRST TCIDON ;EXIT INT
;ROUTINE TO ANALYSE ERROR BITS IN RH(T3)
TCEANL: MOVEI T2,0 ;SET INITIAL ZERO
TLNE T3,(CI.HNG)
JRST TCEOFL ;DRIVE OFF-LINE
TLNE T3,(CI.REJ)
JRST TCECMR ;COMMAND REJECT
TLNE T3,(CI.OVR)
JRST TCEOVR ;OVERRUN
TLNE T3,(CI.DPE!CI.RCE)
JRST TCEDC ;DATA CHECK
TCEXIT: IORM T2,TRBSTS(T1) ;SET SELECTED BITS
POPJ P, ;RETURN
TCEOFL: PUSHJ P,TCXOFL ;SET UNIT OFF-LINE
TCECMR: MOVSI T2,RB.SNM!RB.SED ;SET BITS (TAPE DIDN'T MOVE)
PJRST TCEXIT
TCEDC: TLO T2,RB.SDE ;DATA ERROR
TCEOVR: TLO T2,RB.SED ;ERROR DETECTED - RETRY
PJRST TCEXIT
SUBTTL COMPUTE CHARACTER COUNTS
;ROUTINE COMPUTES CHARACTER COUNT
;RETURNS COUNT IN T2 , T1 SAVED
;CALLED WITH C(T3) := CONI MTS,
CHRCT: PUSH P,T1 ;SAVE IORB PNTR
PUSHJ P,WRDCTB ;GET WORDCOUNT
SKIPA ;LENGTH ERROR RETURN
AOS -1(P) ;SET FOR SKIP RETURN
MOVEI T2,-1(T1) ;WORD COUNT -1 INTO T2
PUSH P,T2 ;SAVE T2
XCT KDBDTI(W) ;GET BYTE RESIDUE
MOVE T1,T2 ;COPY RESULTS
POP P,T2 ;RESTORE T2
LDB T4,[POINT DI.CHS,T1,DI.CHP]
JUMPE T4,[AOJA T2,CHRCT1] ;IF ZERO RE-ADJUST WORD COUNT
TRCE T4,5 ;ELSE EXCHANGE HIGH & LOW ORDER BITS
TRCE T4,5 ;...
TRC T4,5 ;BYTE RESIDUE NOW IN T4
CHRCT1: DPB T4,PMTNCR## ;SAVE RESIDUE FOR MTCHR.
HRLM T2,TUBCHR(U) ;STORE LAST WORD COUNT FOR MTCHR.
XCT KDBCNI(W) ; SEE WHAT MODE
MOVEI T3,5 ;ASSUME CORE-DUMP
TRNN T1,CI.CDS ;IS IT?
MOVEI T3,4 ;NO - COMPAT THEN
IMUL T2,T3 ;CONVERT TO BYTES
ADD T2,T4 ;PLUS REMAINDER
MOVEI T1,0 ;CAN'T GET CRC
DPB T1,PMTCRC## ;STORE IT FOR MTCHR.
PJRST TPOPJ## ;RESTORE T1 AND EXIT
;ROUTINE TO COMPUTE WORD COUNT FOR DF10
;RETURNS WORD COUNT IN T1 , T3 PRESERVE
;CALLED WITH T1 := IORB
WRDCTB: MOVE T1,KDBICP(W) ;PNTR TO INITIAL CONTROL WORD
PUSHJ P,SAVE1## ;SAVE P1
MOVE P1,KDBCHN(W) ;ADDRS OF CDB
PUSH P,T3 ;SAVE T3
PUSHJ P,WRDCNT## ;CALL ROUTINE IN COMMON
POP P,T3 ;RESTORE T3
TLNN T3,(CI.RLD) ;LENGTH = REQUEST?
JRST CPOPJ1## ;OK - GIVE GOOD RETURN
MOVE T2,KDBICP(W) ;ICPC PNTR
HLRZ T2,1(T2) ;LH TERMINATION WORD
LSH T2,-4 ;DF10C HAS 14 BIT ADDRS
SKIPN (T2) ;ARE WE AT END OF LIST
POPJ P, ;YES - SHORT RECORDS OK
SOJA T1,CPOPJ1## ;NO - LENGTH IS ONE LESS
TCXEND: END