Trailing-Edge
-
PDP-10 Archives
-
bb-jr93j-bb
-
7,6/ap023/qsrcat.x23
There is 1 other file named qsrcat.x23 in the archive. Click here to see a list.
TITLE QSRCAT - Interface to [SYSTEM]CATALOG and catalog cache management
;
;
;COPYRIGHT (c) DIGITAL EQUIPMENT CORPORATION 1984,1985,1986,1987.
;ALL RIGHTS RESERVED.
;
; THIS SOFTWARE IS FURNISHED UNDER A LICENSE AND MAY BE USED
; AND COPIED ONLY IN ACCORDANCE WITH THE TERMS OF SUCH LICENSE
; AND WITH THE INCLUSION OF THE ABOVE COPYRIGHT NOTICE. THIS
; SOFTWARE OR ANY OTHER COPIES THEREOF MAY NOT BE PROVIDED OR
; OTHERWISE MADE AVAILABLE TO ANY OTHER PERSON. NO TITLE TO
; AND OWNERSHIP OF THE SOFTWARE IS HEREBY TRANSFERRED.
;
; THE INFORMATION IN THIS SOFTWARE IS SUBJECT TO CHANGE
; WITHOUT NOTICE AND SHOULD NOT BE CONSTRUED AS A COMMITMENT
; BY DIGITAL EQUIPMENT CORPORATION.
;
; DIGITAL ASSUMES NO RESPONSIBILITY FOR THE USE OR RELIABILITY
; OF ITS SOFTWARE ON EQUIPMENT WHICH IS NOT SUPPLIED BY
; DIGITAL.
SEARCH GLXMAC ;GALAXY SYMBOLS
SEARCH QSRMAC ;QUASAR SYMBOLS
SEARCH ORNMAC ;ORION SYMBOLS
SEARCH CATPRM ;CATALOG SYMBOLS
PROLOG (QSRCAT) ;INITIALIZE ASSEMBLY
%%.QSR==:%%.QSR
QSRVRS==:QSRVRS
SALL ;FOR CLEAN LISTINGS
.DIREC FLBLST ;FOR CLEANER LISTINGS
SUBTTL Table of Contents
; TABLE OF CONTENTS FOR QSRCAT
;
;
; SECTION PAGE
; 1. Table of Contents......................................... 2
; 2. Local storage............................................. 3
; 3. V$INIT - Initialize....................................... 4
; 4. V$AQST - Send queue structure info to catalog daemon...... 5
; 5. V$CERR - Report errors detected in [SYSTEM]CATALOG........ 6
; 6. V$COMP - Compare catalog entries.......................... 7
; 7. V$CREA - Create an entry for an existing volume-set....... 9
; 8. V$DELE - Delete a non-sharable volume-set from the cache.. 10
; 9. V$DELS - Delete a sharable volume-set from the cache...... 10
; 10. V$DUMP - Dump entire cache................................ 11
; 11. V$DISA - Disable catalog updates by MDA................... 12
; 12. V$ENAB - Enable catalog updates by MDA.................... 12
; 13. V$EXTV - Extend a volume-set.............................. 13
; 14. V$GCAT - Get catalog information.......................... 16
; 15. V$FIND - Find a volume-set in the cache................... 17
; 16. V$RCAT - Response from [SYSTEM]CATALOG.................... 18
; 17. V$SEND - Send a message to [SYSTEM]CATALOG................ 21
; 18. V$STRG - Convert SIXBIT volume-set names to ASCIZ......... 22
; 19. V$TYPE - Type a catalog entry............................. 23
; 20. Message translation
; 20.1 VSL table......................................... 24
; 20.2 Device code table................................. 25
; 20.3 VSL processing.................................... 27
; 20.4 VOL processing.................................... 28
; 20.5 Load resource numbers into MDA volume blocks...... 30
; 21. End....................................................... 33
SUBTTL Local storage
DATSIZ==<2*ARG.SZ>+.CTVSL+.CTVLM;SIZE OF VSL & VOL BLOCK STORAGE
CATMSG: BLOCK .OHDRS+DATSIZ ;STORAGE FOR CATALOG MESSAGES
CATQUE: BLOCK 1 ;CATALOG CACHE LINKED LIST ID
CATTMP: BLOCK VSNSIZ ;TEMPORARY VOLUME-SET NAME STORAGE
CATOLD: BLOCK 1 ;OLD CATALOG CACHE ENTRY ADDRESS
CATNEW: BLOCK 1 ;NEW CATALOG CACHE ENTRY ADDRESS
CATTXT: BLOCK <CATSIZ==100> ;TEXT BLOCK
CATCNT: BLOCK 1 ;CHARACTER COUNT
CATPTR: BLOCK 1 ;BYTE POINTER
DTAFLG: BLOCK 1 ;DECTAPE CATALOG UPDATE FLAG
MTAFLG: BLOCK 1 ;MAGTAPE CATALOG UPDATE FLAG
STRFLG: BLOCK 1 ;STRUCTURE CATALOG UPDATE FLAG
VOLCUR: BLOCK 1 ;CURRENT VOL BLOCK OFFSET
DMPFLG: BLOCK 1 ;DUMP FLAG
RSNNUM: BLOCK 1 ;RESOURCE NUMBER
RSNNAM: BLOCK 1 ;RESOURCE NAME
SUBTTL V$INIT - Initialize
; Here to initialize the interface to the catalog daemon
; Call: PUSHJ P,V$INIT
V$INIT::SKIPN G$MDA## ;QUASAR NEED A CATALOGER?
$RETT ;NOPE, JUST RETURN
MOVEI S1,SP.CAT ;SPECIAL PID INDEX
PUSHJ P,C%RPRM ;SEE IF THE CATALOG DEAMON
SKIPT ;IS ALIVE AND KICKING
PUSHJ P,I$SCAT## ;NO, GO START IT UP
SKIPT
STOPCD (CSF,HALT,,<CATLOG Startup Failed>)
INIT.1: MOVEI S1,1 ;INITIAL FLAG
MOVEM S1,DTAFLG ;ALLOW DECTAPE UPDATES
MOVEM S1,MTAFLG ;ALLOW MAGTAPE UPDATES
MOVEM S1,STRFLG ;ALLOW STRUCTURE UPDATES
PUSHJ P,L%CLST ;CREATE A LINKED LIST
MOVEM S1,CATQUE ; FOR THE CATALOG CACHE
PUSHJ P,AQST.1 ;SEND QUEUE STRUCTURE TO CATALOG DAEMON
$RETT ;RETURN
SUBTTL V$AQST - Send queue structure info to catalog daemon
V$AQST::MOVE S1,G$MCOD## ;EXTERNAL ENTRY POINT
AQST.1: MOVEI S1,0 ;INTERNAL ENTRY POINT
$SAVE <P1> ;SAVE P1
PUSH P,S1 ;SAVE ACK CODE
MOVEI P1,CATMSG ;POINT TO MESSAGE BLOCK
MOVEI S1,.CFAQS ;MESSAGE TYPE
STORE S1,.MSTYP(P1),MS.TYP ;SAVE
MOVEI S1,.OHDRS+1 ;MESSAGE LENGTH
STORE S1,.MSTYP(P1),MS.CNT ;SAVE
SETZM .MSFLG(P1) ;NO MESSAGE FLAGS
POP P,.MSCOD(P1) ;SET POSSIBLE ACK CODE
SETZM .OFLAG(P1) ;NO FLAGS
SETZM .OARGC(P1) ;NO BLOCK COUNT
MOVE S1,G$QSTR## ;GET QUEUE STRUCTURE
MOVEM S1,.OHDRS(P1) ;SAVE
MOVEM P1,G$SAB##+SAB.MS ;SAVE MESSAGE ADDRESS
LOAD S1,.MSTYP(P1),MS.CNT ;GET MESSAGE SIZE
MOVEM S1,G$SAB##+SAB.LN ;SAVE
PUSHJ P,V$SEND ;SEND TO CATALOG DAEMON
$RETT ;RETURN
SUBTTL V$CERR - Report errors detected in [SYSTEM]CATALOG
V$CERR::$WTO (<^I/CATTX1/>,<^I/CATTX2/>,,<$WTFLG(WT.SJI)>)
$RETF ;RETURN
CATTX1: ITEXT (<Invalid message from [SYSTEM]CATALOG>)
CATTX2: ITEXT (<Message header:
Len,,type ^O6R0/.MSTYP(M),MS.CNT/,,^O6R0/.MSTYP(M),MS.TYP/
Flg,,pfx ^O6R0/.MSFLG(M),LHMASK/,,^W3L /.MSFLG(M),MF.SUF/
Ack code ^O12R0/.MSCOD(M)/>)
SUBTTL V$COMP - Compare catalog entries
; Call: MOVE S1, old entry address
; MOVE S2, new entry address
; PUSHJ P,V$COMP
;
; TRUE return: match, duplicate (new) entry deleted, or old entry
; updated to reflect changed parameters if possible.
;
; FALSE return: mismatch, attempt to update the old entry failed.
; to purge the old entry will be made
;
; Note: On either return, the operator will be notified of a
; catalog update or failure to do so. S1 will always
; contain the entry address to use.
;
V$COMP::$SAVE <P1,P2,P3,P4> ;SAVE SOME ACS
DMOVE P1,S1 ;COPY ARGUMENTS
DMOVE P3,P1 ;THIS WAY WE'LL NEVER FORGET!
MOVE S1,.CQNVL(P1) ;GET NUMBER OF VOLUMES IN OLD VSN
CAME S1,.CQNVL(P2) ;SAME AS NEW VSN?
JRST COMP.2 ;NO
HRROI S1,.CQVSN(P1) ;GET OLD VSN
HRROI S2,.CQVSN(P2) ;GET NEW VSN
PUSHJ P,S%SCMP ;COMPARE
JUMPN S1,COMP.2 ;JUMP IF DIFFERENT
MOVE TF,.CQNVL(P1) ;GET NUMBER OF VOLUMES
MOVEI P1,.CQVSL(P1) ;POINT TO START OF VOLUME BLOCKS
MOVEI P2,.CQVSL(P2) ;HERE TOO
COMP.1: MOVE S1,.CQVID(P1) ;GET AN OLD UNIT ID
MOVE S2,.CQRSN(P1) ;GET AN OLD RESOURCE NUMBER
CAMN S1,.CQVID(P2) ;SAME AS NEW UNIT ID?
CAME S2,.CQRSN(P2) ;SAVE AS NEW RESOURCE NUMBER?
JRST COMP.2 ;NO
ADDI P1,.CQVLL ;POINT TO NEXT ENTRY
ADDI P2,.CQVLL ;HERE TOO
SOJG TF,COMP.1 ;LOOP
MOVE S1,P4 ;GET DUPLICATE (NEW) ENTRY ADDRESS
PUSHJ P,DELETE ;DELETE IT
MOVE S1,P3 ;GET ENTRY ADDRESS TO USE
$RETT ;AND RETURN
COMP.2: MOVEI S1,.CQVSN(P3) ;POINT TO THE VOLUME-SET NAME
$WTO (<QUASAR catalog conflict>,<^I/COMP.T/>,,<$WTFLG(WT.SJI)>)
MOVE S1,P4 ;GET DUPLICATE (NEW) ENTRY ADDRESS
PUSHJ P,DELETE ;DELETE IT
MOVE S1,P3 ;GET ENTRY TO USE
$RETF ;AND RETURN
COMP.T: ITEXT (<Volume-set ^T/(S1)/ is currently in use>)
SUBTTL V$CREA - Create an entry for an existing volume-set
V$CREA::PUSHJ P,.SAVE1 ;SAVE P1
MOVE P1,S1 ;COPY VOLUME BLOCK ADDRESS
MOVE S1,.VLNAM(P1) ;GET SIXBIT NAME
PUSHJ P,V$STRG ;CONVERT TO A STRING
PUSHJ P,V$FIND ;LOOK FOR IT IN THE CATALOG
SKIPT ;FOUND IT?
SETZ S1, ;NO
MOVEM S1,CATOLD ;REMEMBER IT FOR LATER
MOVE S1,CATQUE ;GET THE CATALOG QUEUE ID
PUSHJ P,L%LAST ;POSITION TO THE END OF THE Q
MOVE S1,P1 ;GET THE VOL BLK ADDRESS BACK
SETZM S2 ;ZERO THE VOLUME COUNTER
CREA.1: LOAD S1,.VLPTR(S1),VL.NXT ;GET THE NEXT VOL BLK ADDRESS
AOS S2 ;BUMP THE VOLUME COUNT
JUMPN S1,CREA.1 ;CONTINUE FOR ALL VOLUMES
PUSH P,S2 ;SAVE THE VOLUME COUNT
IMULI S2,.CQVLL ;CALCULATE NUMBER OF WORDS TO GET
ADDI S2,.CQVSL ;INCLUDE THE CATALOG HEADER
MOVE S1,CATQUE ;GET THE CATALOG QUEUE ID BACK
PUSHJ P,L%CENT ;CREATE A NEW CATALOG ENTRY
JUMPF CREA.4 ;FAILD FOR SOME REASON
MOVEM S2,CATNEW ;SAVE NEW ADDRESS FOR LATER
MOVSI S1,CATTMP ;POINT TO ASCIZ NAME
HRRI S1,.CQVSN(S2) ;WHERE TO COPY
BLT S1,.CQVSN+VSNSIZ-1(S2) ;MOVE VOLUME-SET NAME
MOVEI TF,%UNKN ;ASSUME DEVICE TYPE UNKNOWN
SKIPE S1,.VLVSL(P1) ;GET A VSL ADDRESS
LOAD TF,.VSFLG(S1),VS.TYP ;GET THE VOLUME TYPE
CAIE TF,%UNKN ;STILL UNKNOWN?
JRST CREA.2 ;NO
SKIPE S1,.VLUCB(P1) ;SEE IF THERE'S A UCB
LOAD TF,.UCBST(S1),UC.DVT ;GET MDA DEVICE CODE
CREA.2: STORE TF,.CQFLG(S2),CQ.TYP ;SAVE
LOAD S1,.CQFLG(S2),CQ.USE ;GET USE COUNT
ADDI S1,1 ;PLUS ONE
STORE S1,.CQFLG(S2),CQ.USE ;UPDATE
MOVE S1,.VLOID(P1) ;GET THE OWNER PPN
MOVEM S1,.CQVUS(S2) ;SAVE IT
MOVEI S1,.CQQSR ;SET THE BUILD CODE TO SAY
STORE S1,.CQFLG(S2),CQ.BLD ; THIS ENTRY WAS CREATED BY QUASAR
POP P,.CQNVL(S2) ;INSERT VOLUME COUNT
MOVEI S2,.CQVSL(S2) ;POINT TO VOLUME BLOCKS
CREA.3: MOVE S1,.VLVID(P1) ;GET THE VOLID
MOVEM S1,.CQVID(S2) ;SET IT
MOVE S1,.VLUCB(P1) ;GET THE UNIT THIS VOLUME IS ON
LOAD S1,.UCBST(S1),UC.RSN ;GET THE UNIT RESOURCE NUMBER
MOVEM S1,.CQRSN(S2) ;SET IT
ADDI S2,.CQVLL ;POINT TO THE NEXT VOLID BLOCK
LOAD P1,.VLPTR(P1),VL.NXT ;GET THE NEXT VOL BLK ADDRESS
JUMPN P1,CREA.3 ;CONTINUE IF THERE IS ONE
SKIPN S1,CATOLD ;WAS THERE AN OLD ENTRY?
$RETT ;NO
MOVE S2,CATNEW ;GET THE NEW ENTRY
PUSHJ P,V$COMP ;COMPARE THE TWO
POPJ P, ;RETURN TRUE OR FALSE
CREA.4: $WTO (<Internal catalog cache error>,<^I/CREA.T/>,,<$WTFLG(WT.SJI)>)
$RETF ;RETURN
CREA.T: ITEXT (<Cannot create entry for ^T/CATTMP/>)
SUBTTL V$DELE - Delete a non-sharable volume-set from the cache
SUBTTL V$DELS - Delete a sharable volume-set from the cache
; Call: MOVE S1, address of ASCIZ volume-set name
; PUSHJ P,V$DELE/V$DELS
;
; TRUE return: VSN found and deleted
; FALSE return: VSN not in the the cache
V$DELE::TDZA S2,S2 ;DELETE ANY ENTRY
V$DELS::MOVEI S2,1 ;DELETE SHARABLE RESOURCE ENTRY
PUSHJ P,.SAVE2 ;SAVE P1 AND P2
DMOVE P1,S1 ;COPY ARGUMENTS
PUSHJ P,V$FIND ;SEARCH THE CACHE
$RETIF ;RETURN IF NO MATCH
SKIPN S2,P2 ;SKIP IF DELETING A STRUCTURE
LOAD S2,.CQFLG(S1),CQ.USE ;GET USE COUNT
SUBI S2,1 ;MINUS ONE
STORE S2,.CQFLG(S1),CQ.USE ;UPDATE
JUMPG S2,.RETT ;RETURN IF STILL IN USE
DELETE: MOVE S2,S1 ;COPY ENTRY ADDRESS
SETZM .CQVSN(S2) ;BE DEFENSIVE
MOVE S1,CATQUE ;GET LINKED LIST HANDLE
PUSHJ P,L%APOS ;POSITION
SKIPF ;SHOULDN'T HAPPEN
PUSHJ P,L%DENT ;DELETE THE ENTRY
$RETT ;AND RETURN
SUBTTL V$DUMP - Dump entire cache
; Call: PUSHJ P,V$DUMP
V$DUMP::PUSHJ P,.SAVE4
PUSHJ P,.SAVET
PUSH P,S1 ;SAVE S1
PUSH P,S2 ;SAVE S2
SETOM DMPFLG ;INDICATE DUMP
SKIPN CATQUE ;SANITY CHECK
JRST DUMP.2 ;DONE
HRROI S1,DUMP.H ;POINT TO HEADER
PUSHJ P,K%SOUT ;PRINT IT
MOVE S1,CATQUE ;GET LINKED LIST HANDLE
PUSHJ P,L%FIRST ;FIND FIRST ENTRY
DUMP.1: JUMPF DUMP.2 ;RETURN IF NO MORE
MOVEI S1,<CATSIZ*5>-1 ;GET CHARACTER COUNT
MOVEM S1,CATCNT ;SAVE IT
MOVE S1,[POINT 7,CATTXT] ;GET BYTE POINTER
MOVEM S1,CATPTR ;SAVE IT
MOVE S1,S2 ;COPY ENTRY ADDRESS
PUSHJ P,V$TYPE ;TYPE IT
HRROI S1,CATTXT ;POINT TO TEXT
PUSHJ P,K%SOUT ;TYPE IT
MOVE S1,CATQUE ;GET LINKED LIST HANDLE
PUSHJ P,L%NEXT ;FIND NEXT ENTRY
JRST DUMP.1 ;LOOP
DUMP.2: SETZM DMPFLG ;DUMP COMPLETED
POP P,S2 ;RESTORE S2
POP P,S1 ;RESTORE S1
POPJ P, ;RETURN
DUMP.H: ASCIZ /
Addr Use Volume Set Name Volume Resource
------ ----- --------------------------------------- ------ --------
/
SUBTTL V$DISA - Disable catalog updates by MDA
SUBTTL V$ENAB - Enable catalog updates by MDA
V$DISA::TDZA S1,S1 ;DISABLE
V$ENAB::MOVEI S1,1 ;ENABLE
SKIPN S2,.OFLAGS(M) ;GET CATALOG DEVICE TYPE
PJRST V$CERR ;NO DEVCE?
CAIN S2,.CTDTA ;DECTAPE?
MOVEM S1,DTAFLG ;YES
CAIN S2,.CTMTA ;MAGTAPE?
MOVEM S1,MTAFLG ;YES
CAIN S2,.CTSTR ;STRUCTURE?
MOVEM S1,STRFLG ;YES
$RETT ;RETURN
SUBTTL V$EXTV - Extend a volume-set
; Notify [SYSTEM]CATALOG of a possible volume-set extension
; Call: MOVE S1, VSL address
; PUSHJ P,V$EXTV
V$EXTV::PUSHJ P,.SAVE3 ;SAVE SOME ACS
MOVE P1,S1 ;COPY VSL
MOVEI S1,.VSVSN(P1) ;POINT TO VOLUME-SET NAME
PUSHJ P,V$FIND ;SEARCH THE CACHE
$RETIF ;DON'T BOTHER IF NOT CACHED
MOVE P2,S1 ;COPY CACHE ENTRY ADDRESS
LOAD S1,.VSCVL(P1),VS.CNT ;GET TOTAL VOLS IN THIS VOLUME-SET
CAMG S1,.CQNVL(P2) ;REALLY A VOL SWITCH?
$RETT ;NO
LOAD S1,.CQFLG(P2),CQ.TYP ;GET MDA DEVICE CODE
PUSHJ P,QCDEV ;TRANSLATE TO CATALOG CODE
MOVEM S1,EXTDEV ;SAVE IN MESSAGE
MOVSI S1,.CQVSN(P2) ;POINT TO VOLUME-SET NAME
HRRI S1,EXTVSN ;AND STORAGE IN MESSAGE
BLT S1,EXTVSN+VSNSIZ-1 ;COPY
LOAD P3,.VSCVL(P1),VS.OFF ;GET OFFSET TO CURRENT VOL
ADDI P3,.VSVOL(P1) ;POINT TO ADDRESS OF VOL
MOVE P3,(P3) ;GET VOL ADDRESS
$TEXT (<-1,,EXTUNI>,<^W/.VLNAM(P3)/^0>) ;COPY TO MESSAGE
PUSHJ P,EXTSND ;SEND MESSAGE TO [SYSTEM]CATALOG
PUSHJ P,EXTCAT ;ADD NEW VOL TO CATALOG CACHE
$RETT ;RETURN
; Here to actually send the message to [SYSTEM]CATALOG
EXTSND: PUSHJ P,M%GPAG ;GET A PAGE
MOVEI S2,.CFMOD ;FUNCTION CODE
STORE S2,.MSTYP(S1),MS.TYP
MOVEI S2,.OHDRS+EXTLEN ;LENGTH OF MESSAGE
STORE S2,.MSTYP(S1),MS.CNT
MOVEI S2,^D8 ;ARGUMENT BLOCK COUNT
MOVEM S2,.OARGC(S1)
MOVSI S2,EXTMSG ;POINT TO STATIC BLOCK
HRRI S2,.OHDRS(S1) ;AND TO THE DESTINATION
BLT S2,.OHDRS+EXTLEN-1(S1) ;COPY
MOVEM S1,G$SAB##+SAB.MS ;SAVE MESSAGE ADDRESS
LOAD S2,.MSTYP(S1),MS.CNT ;GET MESSAGE SIZE
MOVEM S2,G$SAB##+SAB.LN ;SAVE
PJRST V$SEND ;SEND TO [SYSTEM]CATALOG
EXTMSG: XWD 2,.CMKEY ;DEVICE TYPE
EXTDEV: EXP .CTMTA
XWD VSNSIZ+1,.CMFLD ;VOLUME-SET NAME
EXTVSN: BLOCK VSNSIZ
XWD 1,.CMCFM ;CRLF
XWD 2,.CMKEY ;ADD
EXP .CTADD
XWD 3,.CMFLD ;REELID
EXTUNI: BLOCK 2
XWD 1,.CMCFM ;CRLF
XWD 2,.CMKEY ;DONE
EXP .CTDON
XWD 1,.CMCFM ;CRLF
EXTLEN==.-EXTMSG ;LENGTH OF MESSAGE
; Here to expand the catalog cache entry
EXTCAT: MOVE S1,CATQUE ;POINT TO QUEUE HEADER
PUSHJ P,L%SIZE ;GET SIZE OF THIS ENTRY
$RETIF ;CAN'T EXTEND CACHE
PUSH P,S2 ;SAVE IT
ADDI S2,.CQVLL ;PLUS WHAT'S NEEDED FOR ANOTHER BLOCK
PUSHJ P,L%CENT ;CREATE A NEW ENTRY
POP P,S1 ;RESTORE OLD LENGTH
$RETIF ;CAN'T EXTEND CACHE
PUSH P,S2 ;SAVE NEW ADDRESS
ADDI S1,(S2) ;COMPUTE END OF BLT
HRLI S2,(P2) ;MAKE A BLT POINTER
BLT S2,-1(S1) ;COPY
MOVE S2,.VLNAM(P3) ;GET VOL NAME
MOVEM S2,.CQVID(S1) ;SAVE IN CACHE
MOVE S2,.VLUCB(P3) ;GET THE UCB ADDRESS
LOAD S2,.UCBST(S2),UC.RSN ;AND IT'S PHYSICAL RESOURCE NUMBER
MOVEM S2,.CQRSN(S1) ;SAVE IN CACHE
POP P,S1 ;GET NEW ADDRESS BACK
AOS .CQNVL(S1) ;COUNT THE NEW VOLUME
MOVE S1,P2 ;COPY OLD CACHE ENTRY ADDRESS
PJRST DELETE ;DELETE IT AND RETURN
SUBTTL V$GCAT - Get catalog information
; Routine to get catalog informat. First, QUASAR's catalog
; cache is checked. If the entry isn't found, a request will
; be sent to [SYSTEM]CATALOG for the necessary information.
; Call: MOVE S1, [-1,,VSN address] ;IF AN INTERNAL REQUEST
; MOVE S1, [0,,VSN address] ;IF A USER REQUEST
; PUSHJ P,V$GCAT
;
; TRUE return: VSN found in cache, VSL and VOLs updates, S1=VSL address
; FALSE return: VSN not in cache
V$GCAT::PUSHJ P,.SAVE4 ;SAVE SOME ACS
SKIPL P1,S1 ;SAVE CALLING PARMS, SKIP IF INTERNAL
MOVEI S1,.VSVSN(P1) ;POINT TO THE ASCIZ VOLUME SET NAME
PUSHJ P,V$FIND ;FIND IT IN OUR CATALOG CACHE
JUMPF GCAT.2 ;NOT THERE,,GO REQUEST IT
LOAD S2,.CQFLG(S1),CQ.USE ;GET USE COUNT
ADDI S2,1 ;PLUS ONE
STORE S2,.CQFLG(S1),CQ.USE ;UPDATE
LOAD S2,.CQFLG(S1),CQ.TYP ;GET MDA DEVICE CODE
SKIPL P1 ;SKIP IF AN INTERNAL REQUEST
STORE S2,.VSFLG(P1),VS.TYP ;MARK THIS VOLUME SET
MOVE P4,P1 ;COPY VSL INTO P4
MOVE P1,S1 ;COPY ENTRY INTO P1
PUSHJ P,CQVSL ;DO VSL SPECIFIC PROCESSING
MOVN P3,.CQNVL(P1) ;GET NUMBER OF VOLUMES IN VOLUME-SET
HRLZS P3 ;PUT IN LH
HRRI P3,.CQVSL(P1) ;POINT TO START OF VOLUME ENTRY BLOCKS
GCAT.1: PUSHJ P,CQVOLX ;DO VOLUME BLOCK PROCESSING
$RETIF ;SHOULD NEVER FAIL
ADDI P3,.CQVLL-1 ;ADVANCE CATALOG CACHE POINTER
AOBJN P3,GCAT.1 ;LOOP FOR ALL VOLUME BLOCKS
MOVE S1,P4 ;COPY POSSIBLY NEW VSL ADDRESS
$RETT ;AND RETURN
GCAT.2: MOVEI P2,CATMSG ;GET A TEMP MSG BUFFER
MOVEM P2,G$SAB##+SAB.MS ;SAVE IT IN THE SAB
MOVE S1,[.OHDRS+1,,.CFRCT] ;GET REQUEST FOR CATALOG INFO HEADER
MOVEM S1,.MSTYP(P2) ;SAVE IT
SETOM S2 ;INDICATE 'NOT A USER' REQUEST
SKIPL P1 ;UNLESS WE POINT TO A VSL
MOVE S2,.VSRID(P1) ;THEN GET THE REQUEST ID
MOVEM S2,.MSCOD(P2) ;SAVE THE ACK CODE (RID OR -1)
SETZM .MSFLG(P2) ;NO FLAG WORD
SETZM .OFLAG(P2) ;NO MESSAGE FLAG WORD
MOVEI S1,1 ;GET A BLOCK COUNT OF 1
MOVEM S1,.OARGC(P2) ;SAVE IT
MOVEI P2,.OHDRS(P2) ;POINT TO THE FIRST (ONLY) MSG BLOCK
MOVE S1,[.CTVSL+ARG.DA,,.CTVSB] ;GET VOLUME SET NAME BLOCK HEADER
MOVEM S1,ARG.HD(P2) ;SAVE IT
MOVEI P3,ARG.DA(P2) ;POINT TO FIRST DATA WORD
LOAD S1,.VSFLG(P1),VS.TYP ;GET MDA DEVICE CODE
PUSHJ P,QCDEV ;TRANSLATE TO CATALOG DEVICE CODE
STORE S1,.CTVFL(P3),CT.TYP ;SAVE IN MESSAGE
SETZM S1 ;CLEAR S1 (USE AS BYTE COUNTER)
SKIPL P1 ;IF INTERNAL,,SKIP
MOVEI P1,.VSVSN(P1) ;POINT TO THE VOL SET NAME
HRLI P1,(POINT 7,0) ;MAKE THE VOL SET NAME ADDR A BYTE PTR
MOVE S2,[POINT 7,.CTVSN(P3)] ;GET THE DESTINATION BYTE POINTER
GCAT.3: ILDB TF,P1 ;GET A VOLUME SET NAME BYTE
IDPB TF,S2 ;INSERT IT INTO THE MESSAGE
AOS S1 ;BUMP BYTE COUNT BY 1
JUMPN TF,GCAT.3 ;CONTINUE TILL ASCIZ
MOVEI S1,.CTVSL+ARG.DA ;SIZE OF BLOCK
LOAD S2,CATMSG+.MSTYP,MS.CNT ;GET CURRENT LENGTH
ADDI S1,(S2) ;ACCUMULATE
STORE S1,CATMSG+.MSTYP,MS.CNT ;UPDATE
MOVEM S1,G$SAB##+SAB.LN ;SAVE IT IN THE SAB
PUSHJ P,V$SEND ;SEND IT OFF TO THE TAPE LABELER
$RETF ;AND RETURN
SUBTTL V$FIND - Find a volume-set in the cache
; Call: MOVE S1, address of ASCIZ volume-set name
; PUSHJ P,V$FIND
;
; TRUE return: S1 contains the entry address
; FALSE return: Volume-set not cached
V$FIND::PUSHJ P,.SAVE3 ;SAVE SOME ACS
MOVE P1,S1 ;SAVE THE VOL SET NAME
HRLI P1,(POINT 7,) ;MAKE A BYTE POINTER
MOVE S1,CATQUE ;GET THE CATALOG QUEUE ID
PUSHJ P,L%FIRST ;GET THE FIRST ENTRY
JRST FIND.2 ;JUMP THE FIRST TIME THROUGH
FIND.1: MOVE S1,CATQUE ;GET THE CATALOG QUEUE ID
PUSHJ P,L%NEXT ;GET THE NEXT ENTRY
FIND.2: JUMPF .RETF ;NOT THERE,,RETURN NO GOOD
MOVE P2,P1 ;COPY POINTER TO TARGET
MOVEI P3,.CQVSN(S2) ;POINT TO THIS NAME
HRLI P3,(POINT 7,) ;MAKE A BYTE POINTER
FIND.3: ILDB TF,P2 ;GET A CHARACTER
ILDB S1,P3 ;HERE TOO
CAIE TF,(S1) ;MATCH?
JRST FIND.1 ;NO
ADDI TF,(S1) ;ADD THEM
JUMPN TF,FIND.3 ;LOOP 'TIL END OF STRING
MOVE S1,S2 ;VOLUME-SET NAMES MATCH
$RETT ;AND RETURN
SUBTTL V$RCAT - Response from [SYSTEM]CATALOG
V$RCAT::MOVX S1,MF.FAT ;GET FATAL BIT
TDNE S1,.MSFLG(M) ;KNOWN VOLUME-SET?
JRST RCAT.E ;NO
PUSHJ P,.SAVE4 ;SAVE SOME ACS
MOVX S1,.CTVSB ;VOLUME-SET BLOCK TYPE
PUSHJ P,A$FNDB## ;FIND IT
JUMPF RCAT.6 ;NOT THERE,,THATS AN ERROR
MOVEI P2,(S1) ;PUT BLOCK ADDRESS IN P2
HRROI S1,.CTVSN(P2) ;POINT TO VSN TEXT
PUSHJ P,S%SIXB ;CONVERT TO SIXBIT
MOVEM S2,MDAOBJ##+OBJ.UN ;SAVE
SETZ P4, ;ASSUME NOT A USER REQUEST
SKIPN S1,.MSCOD(M) ;GET THE ACK CODE (MDR ID)
JRST RCAT.6 ;NONE THERE,,THATS AN ERROR
CAMN S1,[-1] ;IS IT -1 ???
JRST RCAT.0 ;YES,,NOT A USER REQUEST
PUSHJ P,D$FVSL## ;FIND THE VSL FOR THIS USER
JUMPF RCAT.0 ;NOT THERE,,SKIP THIS
MOVE P4,S1 ;SAVE THE VSL ADDRESS
RCAT.0: SETZM CATOLD ;CLEAR OLD CATALOG ENTRY ADDRESS
MOVEI S1,.CTVSN(P2) ;POINT TO VOLUME-SET NAME TEXT
PUSHJ P,V$FIND ;TRY TO FIND THE VOL SET IN THE CATALOG
SKIPF ;FOUND IT?
MOVEM S1,CATOLD ;YES - REMEMBER THE ADDRESS
;Here to create an entry in the Vol Set Catalog
MOVE S1,CATQUE ;GET THE CATALOG QUEUE ID
PUSHJ P,L%LAST ;POSITION TO LAST ENTRY
MOVE S1,CATQUE ;GET THE CATALOG QUEUE ID
MOVE S2,.OARGC(M) ;GET NUMBER OF ARGUMENT BLOCK
CAIE S2,1 ;JUST ONE (NO VOLUME BLOCKS)?
SUBI S2,1 ;ACCOUNT FOR VOLUME-SET BLOCK
IMULI S2,.CQVLL ;ADD LENGTH OF EACH ENTRY
ADDI S2,.CQVSL ;ADD THE HEADER LENGTH
PUSHJ P,L%CENT ;CREATE AN ENTRY
MOVEM S2,CATNEW ;REMEMBER IT FOR LATER
PUSH P,M
MOVE P1,S2
MOVE M,P2
PUSHJ P,C2Q ;COPY FROM CATALOG DATA INTO CACHE
POP P,M
PUSHJ P,CQVSL ;DO VSL SPECIFIC PROCESSING
MOVN P3,.CQNVL(P1) ;GET NUMBER OF VOLUMES IN VOLUME-SET
HRLZS P3 ;PUT IN LH
HRRI P3,.CQVSL(P1) ;POINT TO START OF VOLUME ENTRY BLOCKS
MOVEI S1,.CTVLB ;VOLUME BLOCK TYPE
PUSHJ P,A$FNDB## ;FIND IT
JUMPF RCAT.6 ;NOT THERE,,THATS AN ERROR
MOVEI P2,(S1) ;PUT BLOCK ADDRESS IN P2
RCAT.1: PUSHJ P,CQVOL ;DO VOLUME BLOCK PROCESSING
JUMPF RCAT.5 ;NO GOOD,,THATS AN ERROR
LOAD S1,-ARG.DA(P2),AR.LEN ;GET LENGTH OF BLOCK
ADDI P2,(S1) ;ADVANCE MESSAGE POINTER
ADDI P3,.CQVLL-1 ;ADVANCE CATALOG CACHE POINTER
AOBJN P3,RCAT.1 ;LOOP FOR ALL VOLUME BLOCKS
RCAT.2: SKIPN S1,CATOLD ;HAVE AN OLD ENTRY?
JRST RCAT.3 ;NO
MOVE S2,CATNEW ;GET NEW ENTRY ADDRESS
MOVEI TF,.CQCAT ;SET THE BUILD CODE TO SAY
STORE TF,.CQFLG(S2),CQ.BLD ; THIS ENTRY CAME FROM [SYSTEM]CATALOG
PUSHJ P,V$COMP ;COMPARE THE TWO
MOVE P1,S1 ;GET THE ENTRY ADDRESS TO USE
MOVE S2,S1 ;...
MOVE S1,CATQUE ;GET QUEUE HEADER
PUSHJ P,L%APOS ;POSITION THERE
RCAT.3: LOAD S2,.CQFLG(P1),CQ.USE ;GET USE COUNT
ADDI S2,1 ;PLUS ONE
STORE S2,.CQFLG(P1),CQ.USE ;UPDATE
JUMPE P4,.RETT ;RETURN IF AN INTERNAL REQUEST
MOVE S1,P4 ;GET THE VSL ADDRESS
PUSHJ P,D$ALOC## ;TRY TO COMPLETE ALLOCATION
JUMPF [JUMPL S1,.RETT ;ALLOCATION POSTPONED,,JUST RETURN
MOVE S1,P4 ;NO GOOD,,GET THE VSL ADDRESS BACK
PJRST D$DLVS##] ; AND DELETE THE VOL SETS JUST ADDED
LOAD S2,.MRJOB(AP),MR.JOB ;GET THE PROCESS JOB NUMBER
TXNE S2,BA%JOB ;IS THIS A PSEUDO PROCESS ??
MOVE P4,.MRVSL(AP) ;YES,,MOUNT TO THE FIRST VSL
LOAD S1,.VSFLG(P4),VS.TYP ;GET TYPE
CAXE S1,%TAPE ;ONLY DO TAPES
JRST RCAT.4 ;NOT A MAGTAPE
MOVE S1,.VSVOL(P4) ;GET 1ST VOL BLOCK ADDRESS
MOVE S1,.VLNAM(S1) ;GET VOLUME NAME
PUSHJ P,D$FTPX## ;SEE IF VOL MOUNTED ON A DRIVE
JUMPF RCAT.4 ;IF NOT FOUND, GO TRY TO MOUNT
JUMPE S2,RCAT.4 ;IF NOT MOUNTED ON DRIVE, SKIP IT
CAME S1,.VSVOL(P4) ;"OUR" VOL BLOCK?
SKIPE .UCBVS(S2) ;UCB OWNED ALREADY?
JRST RCAT.4 ;OWNED OR "OURS", SKIP IT
MOVX TF,UC.INI!UC.OFL ;IF OFFLINE OR INITING, SKIP IT
TDNE TF,.UCBST(S2)
JRST RCAT.4
$SAVE <T1,T2,T3> ;NEED THESE ACS
MOVE T2,S2 ;GET UCB ADDRESS
MOVEI T1,STSBLK ;GET FAKE .STSTS BLOCK ADDR
MOVEI T3,TLSBLK ;GET FAKE .TLSTA BLOCK ADDR
MOVE TF,.UCBNM(T2) ;GET UNIT NAME
MOVEM TF,.STUNT(T1) ;STORE IT
MOVE TF,.VLNAM(S1) ;GET VOLUME NAME
MOVEM TF,.TLVOL(T3) ;SET IN FAKE .TLSTA BLOCK
LOAD TF,.UCBST(T2),UC.WLK ;GET WRITE LOCK STATUS
STORE TF,.STFLG(T1),ST.LOK ;SET IT
LOAD TF,.VLFLG(S1),VL.LBT ;GET LABEL TYPE OF VOL ON DRIVE
STORE TF,.STFLG(T1),TS.LAB ;SET IT
LOAD TF,.VLFLG(S1),VL.DEN ;GET DENSITY BITS FROM VOL ON DRIVE
STORE TF,.STFLG(T1),TS.DEN ;STORE IT
PJRST TAPDEV## ;FAKE A RECOGNIZE OF A TAPE
RCAT.4: MOVE S1,P4 ;GET VSL ADDRESS BACK
PUSHJ P,D$MNTV## ;TRY TO MOUNT THE USERS REQUEST
$RETT ;RETURN IN ANY CASE
RCAT.5: MOVE S1,CATQUE ;GET THE QUEUE ID
PUSHJ P,L%DENT ;DELETE THE CURRENT ENTRY
JUMPE P4,.RETT ;AN INTERNAL REQUEST,,RETURN
$TEXT (<-1,,G$MSG##>,<Can't mount volume set ^T/.VSVSN(P4)/ - No drives available^M^J^0>)
SETOM ERRACK## ;INDICATE AN ERROR ACK
MOVE S1,P4 ;[1173] GET VSL ADDRESS
SETOM S2 ;[1173] USE MDR ACK DATA IF VALID
PUSHJ P,D$USRN## ;TELL THE USER
MOVE S1,P4 ;GET THE VSL ADDRESS
PUSHJ P,D$REMO## ;DELETE THIS VSL AND RETRY THE MOUNT
$RETT ;RETURN
RCAT.6: PUSHJ P,V$CERR ;REPORT ERROR
$RETT ;AND RETURN
; Here on catalog NAKs
RCAT.E: PUSHJ P,.SAVE1 ;SAVE P1 FOR A MINUTE
SKIPG S1,.MSCOD(M) ;GET THE ACK CODE
$RETT ;INTERNAL REQUEST,,RETURN NOW
PUSHJ P,D$FVSL## ;FIND THE VSL
JUMPF .RETT ;NOT THERE,,JUST RETURN
MOVE P1,S1 ;SAVE THE VSL ADDRESS
MOVE AP,.VSMDR(P1) ;SETUP THE MDR ADDRESS
$TEXT (<-1,,G$MSG##>,<^I/RCAT.T/^M^J^0>)
SETOM ERRACK## ;THIS IS AN ERROR ACK
MOVE S1,P1 ;GET VSL ADDRESS
SETZM S2 ;USE VSL ACK DATA
PUSHJ P,D$USRN## ;ACK THE USER
MOVE S1,P1 ;GET THE VSL ADDRESS BACK
PUSHJ P,D$REMO## ;GO AND DELETE THIS VSL & RETRY MOUNT
HRROI S1,.VSVSN(P1) ;POINT TO THE ASCIZ VOL SET NAME
PUSHJ P,S%SIXB ;CONVERT IT TO SIXBIT
MOVE S1,S2 ;MOVE IT TO S1
PUSHJ P,D$SRSN## ;GET THE RESOURCE NUMBER
PUSHJ P,D$GVRS## ;TRY TO RETURN IT
$RETT ;RETURN
RCAT.T: ITEXT (<Volume-set "^T/.VSVSN(P1)/" is not cataloged>)
STSBLK: EXP 0
EXP 0
TLSBLK: EXP 0
SUBTTL V$SEND - Send a message to [SYSTEM]CATALOG
V$SEND::MOVX S1,SI.FLG+SP.CAT ;SPECIAL INDEX FOR THE CATALOG MANAGER
MOVEM S1,G$SAB##+SAB.SI ;SAVE IT IN THE SAB
SETZM G$SAB##+SAB.PD ;ZAP THE SAB PID WORD
PUSHJ P,C$SEND## ;SEND THE MESSAGE OFF
$RETT ;AND RETURN
SUBTTL V$STRG - Convert SIXBIT volume-set names to ASCIZ
; Call: MOVE S1, SIXBIT name
; PUSHJ P,V$STRG
;
; TRUE return: S1 contains the address of ASCIZ name
; FALSE return: Never
V$STRG::MOVE S2,[CATTMP,,CATTMP+1] ;SET UP BLT
SETZM CATTMP ;CLEAR FIRST WORD
BLT S2,CATTMP+VSNSIZ-1 ;CLEAR ENTIRE BLOCK
PUSH P,[POINT 7,CATTMP] ;BYTE POINTER TO RESULT
MOVE S2,S1 ;COPY NAME
STRG.1: LSHC S1,6 ;SHIFT IN A CHARACTER
ANDI S1,77 ;STRIP OFF JUNK
ADDI S1,40 ;CONVERT TO ASCII
IDPB S1,(P) ;STORE CHARACTER
JUMPN S2,STRG.1 ;LOOP
POP P,(P) ;PHASE STACK
MOVEI S1,CATTMP ;POINT TO ASCIZ TEXT
POPJ P, ;AND RETURN
SUBTTL V$TYPE - Type a catalog entry
; Call: MOVE S1, entry address
; PUSHJ P,V$TYPE
V$TYPE::PUSHJ P,.SAVE3 ;SAVE SOME ACS
MOVE P1,S1 ;SAVE ENTRY ADDRESS
SKIPE DMPFLG ;DUMPING?
$TEXT (TYPE.T,<^O6R0/P1/ ^A>);YES--PUT OUT ENTRY ADDRESS
LOAD S1,.CQFLG(P1),CQ.USE ;GET USE COUNT
$TEXT (TYPE.T,<^D5R /S1/ ^T39L /.CQVSN(P1)/ ^A>)
MOVEI P2,.CQVSL(P1) ;POINT TO START OF VOLUME BLOCKS
MOVEI P3,1 ;START WITH THE FIRST VOLUME
TYPE.1: CAIN P3,1 ;FIRST TIME?
JRST TYPE.2 ;YES
MOVEI S1," " ;GET A SPACE
MOVEI S2,^D48 ;NORMAL DISPLAY COLUMNS TO PAD
SKIPE DMPFLG ;DUMPING?
MOVEI S2,^D56 ;YES (ENTRY ADDRESS INCLUDED)
PUSHJ P,TYPE.T ;PUT OUT A SPACE
SOJG S2,.-1 ;LOOP
TYPE.2: MOVE S1,.CQRSN(P2) ;GET RESOURCE NUMBER
IMULI S1,AMALEN ;GET 'A' MATRIX OFFSET
ADD S1,AMATRX## ;COMPUTE RESOURCE ENTRY IN MATRIX
LOAD S1,.AMNAM(S1),AM.NAM ;GET ADDRESS OF ASCIZ RESOURCE NAME
$TEXT (TYPE.T,<^W6L /.CQVID(P2)/ ^T/(S1)/>)
ADDI P2,.CQVLL ;POINT TO NEXT VOL BLOCK
CAMGE P3,.CQNVL(P1) ;DONE?
AOJA P3,TYPE.1 ;LOOP FOR ANOTHER VOLUME
MOVEI S1,.CHNUL ;GET A NUL
TYPE.T: SOSLE CATCNT ;COUNT CHARACTERS
IDPB S1,CATPTR ;STUFF ONE IN THE BUFFER
$RETT ;RETURN
SUBTTL Message translation -- VSL table
; Macro to generate translation table
DEFINE CQ (R,C,Q),<
ZZ==0
REPEAT R,<
<<C>+ZZ>
<<Q>+ZZ>
ZZ==ZZ+1
> ;;END REPEAT
> ;END CQ MACRO
; Translation table for converting catalog data to QUASAR cache data.
; This table consists of word pairs, each containing a byte pointer
; to some storage. The format is:
;
; Word 1: byte pointer to catalog data
; Word 2: byte pointer to QUASAR's cache
CQTAB:
CQ VSNSIZ,<POINT 36,.CTVSN(M),35>,<POINT 36,.CQVSN(P1),35>
CQ 1,<POINTR .CTVFL(M),CT.NVL>,<POINT 36,.CQNVL(P1),35>
CQ 1,<POINT 36,.CTVUS(M),35>,<POINT 36,.CQVUS(P1),35>
CQ NAMSIZ,<POINT 36,.CTVNM(M),35>,<POINT 36,.CQVNM(P1),35>
CQ LOCSIZ,<POINT 36,.CTVLO(M),35>,<POINT 36,.CQVLO(P1),35>
CQ 1,<POINT 36,.CTVSC(M),35>,<POINT 36,.CQVSC(P1),35>
CQLEN==.-CQTAB
SUBTTL Message translation -- Device code table
; Device code translation
; Format: catalog code,,MDA code
CQDEVT: XWD .CTDTA,%DTAP ;DECTAPE
XWD .CTMTA,%TAPE ;MAGTAPE
XWD .CTSTR,%DISK ;STRUCTURE
XWD .CTUNK,%UNKN ;UNKNOWN (MUST BE LAST)
CQDEVL==.-CQDEVT ;LENGTH OF TABLE
MDADVN: [ASCIZ /Unknown /]
[ASCIZ /Magtape /]
[ASCIZ /Structure/]
[ASCIZ /DECtape /]
; Copy catalog data to QUASAR's cache
C2Q: PUSH P,T1 ;SAVE T1
MOVE T1,[<-CQLEN/2>,,CQTAB] ;AOBJN POINTER
C2Q.1: LDB TF,0(T1) ;GET A BYTE
DPB TF,1(T1) ;PUT A BYTE
ADDI T1,1 ;ACCOUNT FOR TWO WORD ENTRIES
AOBJN T1,C2Q.1 ;LOOP
LOAD S1,.CTVFL(M),CT.TYP ;GET CATALOG DEVICE CODE
PUSHJ P,CQDEV ;TRANSLATE TO MDA DEVICE CODE
STORE S1,.CQFLG(P1),CQ.TYP ;SAVE
POP P,T1 ;RESTORE T1
POPJ P, ;AND RETURN
; Copy QUASAR's cache to catalog data
Q2C: PUSH P,T1 ;SAVE T1
MOVE T1,[<-CQLEN/2>,,CQTAB] ;AOBJN POINTER
Q2C.1: LDB TF,1(T1) ;GET A BYTE
DPB TF,0(T1) ;PUT A BYTE
ADDI T1,1 ;ACCOUNT FOR TWO WORD ENTRIES
AOBJN T1,Q2C.1 ;LOOP
LOAD S1,.CQFLG(P1),CQ.TYP ;GET MDA DEVICE CODE
PUSHJ P,QCDEV ;TRANSLATE TO CATALOG DEVICE CODE
STORE S1,.CTVFL(M),CT.TYP ;SAVE
POP P,T1 ;RESTORE T1
POPJ P, ;AND RETURN
SUBTTL Message translation -- VSL processing
CQVSL: JUMPE P4,.POPJ ;RETURN IF NO VSL
SETZM VOLCUR ;INIT CURRENT VOL NUMBER
LOAD S1,.CQFLG(P1),CQ.TYP ;GET MDA DEVICE CODE
STORE S1,.VSFLG(P4),VS.TYP ;SET DEVICE TYPE IN VSL
POPJ P, ;RETURN
SUBTTL Message translation -- VOL processing
CQVOL: PUSHJ P,CQRSN ;LOAD DEVICE RESOURCE NUMBERS
$RETIF ;GIVE UP IF ERRORS
CQVOLX: JUMPE P4,.RETT ;NO VOL BLOCKS IF NO VSL
LOAD S1,.CQFLG(P1),CQ.TYP ;GET MDA DEVICE CODE
CAIN S1,%DISK ;STRUCTURE?
$RETT ;YES--ALL DONE
MOVE S1,.CQRSN(P3) ;GET RESOURCE NUMBER
STORE S1,.VSATR(P4),VS.RSN ;SAVE AS VSL RESOURCE
AOS S1,VOLCUR ;GET CURRENT VOL BLOCK OFFSET
LOAD S2,.VSCVL(P4),VS.CNT ;GET VOL COUNT FOR THIS VSL
CAIG S1,(S2) ;RUN OUT OF VOL BLOCKS?
JRST CQVOL1 ;NO
MOVE S2,.CQNVL(P1) ;GET NUMBER OF VOLUMES IN VOLUME-SET
SUBI S2,-1(S1) ;COMPUTE ADDITIONAL NUMBER NEEDED
MOVE S1,P4 ;COPY VSL ADDRESS
PUSHJ P,D$XVSL## ;EXTEND THE VSL
$RETIF ;FAILED
MOVE P4,S1 ;UPDATE NEW VSL ADDRESS IN P4
MOVE S1,VOLCUR ;GET CURRENT VOLUME NUMBER
CQVOL1: ADDI S1,.VSCVL(P4) ;OFFSET TO THIS VOL POINTER
MOVE S1,(S1) ;POINT TO THE VOL BLOCK
MOVE S2,.CQVID(P3) ;COPY REAL VOLUME NAME
MOVEM S2,.VLNAM(S1) ; INTO VOL BLOCK
MOVE S2,.CQVUS(P1) ;GET USER ID (PPN)
MOVEM S2,.VLOID(S1) ;SET IN VOL
LOAD S2,.CQFLG(P1),CQ.TYP ;GET MDA DEVICE CODE
JRST @.+1(S2) ;DISPATCH
EXP .RETF ;INVALID CODE
EXP CQVMTA ;(%TAPE) MAGTAPES
EXP CQVSTR ;(%DISK) STRUCTURES
EXP CQVDTA ;(%DTAP) DECTAPES
; Magtapes
CQVMTA: MOVX S2,VS.SCR!VS.NEW!VS.DDN!VS.DTK ;LOTS OF BITS
ANDCAM S2,.VSFLG(P4) ;CLEAR IN VSL
MOVX S2,VL.SCR ;GET SCRATCH BIT
ANDCAM S2,.VLFLG(S1) ;CLEAR IN VOL
LOAD S2,.CQVSC(P1),CT.LAB ;GET LABEL CODE
STORE S2,.VSFLG(P4),VS.LBT ;SET IN VSL
STORE S2,.VLFLG(S1),VL.LBT ;SET IN VOL
LOAD S2,.CQVSC(P1),CT.DEN ;GET DENSITY CODE
STORE S2,.VSATR(P4),VS.DEN ;SET IN VSL
STORE S2,.VLFLG(S1),VL.DEN ;SET IN VOL
MOVX S2,VL.SRD ;BIT TO SET
IORM S2,.VLFLG(S1) ;SET DENSITY FOR USER
LOAD S2,.CQVSC(P1),CT.TRK ;GET TRACK CODE
STORE S2,.VSATR(P4),VS.TRK ;SET IN VSL
MOVE S1,.VSFLG(P4) ;GET FLAG BITS
TXOE S1,VS.WLK ;WRITE-LOCK ON ALREADY?
$RETT ;YES, JUST RETURN
TXNE S1,VS.MWE ;WAS WRITE ENABLED SPECIFIED?
TXZ S1,VS.WLK ;YES, CLEAR WRITE-LOCK
MOVEM S1,.VSFLG(P4) ;RESTORE FLAGS
$RETT ;AND RETURN
; Structures
CQVSTR: MOVE S1,.VSFLG(P4) ;GET FLAG BITS
TXOE S1,VS.WLK ;WRITE-LOCK ON ALREADY?
$RETT ;YES, JUST RETURN
TXNN S1,VS.MWL ;WAS WRITE-LOCKED SPECIFIED?
TXZ S1,VS.WLK ;NO, CLEAR WRITE-LOCK
MOVEM S1,.VSFLG(P4) ;RESTORE FLAGS
$RETT ;RETURN
; DECtapes
CQVDTA: MOVX S2,VS.SCR!VS.NEW ;GET SCRATCH AND NEW BITS
ANDCAM S2,.VSFLG(P4) ;CLEAR
MOVE S1,.VSFLG(P4) ;GET FLAG BITS
TXOE S1,VS.WLK ;WRITE-LOCK ON ALREADY?
$RETT ;YES, JUST RETURN
TXNE S1,VS.MWE ;WAS WRITE ENABLED SPECIFIED?
TXZ S1,VS.WLK ;YES, CLEAR WRITE-LOCK
MOVEM S1,.VSFLG(P4) ;RESTORE FLAGS
$RETT ;AND RETURN
SUBTTL Message translation -- Load resource numbers into MDA volume blocks
CQRSN: LOAD S1,.CQFLG(P1),CQ.TYP ;GET MDA DEVICE CODE
JRST @.+1(S1) ;DISPATCH
EXP CQRERR ;INVALID CODE
EXP CQRMTA ;(%TAPE) MAGATAPES
EXP CQRSTR ;(%DISK) STRUCTURES
EXP CQRDTA ;(%DTAP) DECTAPES
; Here when invalid codes detected in catalog message
CQRERR: PUSHJ P,V$CERR ;COMPLAIN TO OPR
$RETF ;AND RETURN
; Magtapes
CQRMTA: MOVEI S1,.MTRID(P2) ;POINT TO REELID
HRLI S1,(POINT 8,) ;MAKE A BYTE POINTER
MOVEI S2,.CQVID(P3) ;POINT TO STORAGE
HRLI S2,(POINT 6,) ;MAKE A BYTE POINTER
CQRMT1: ILDB TF,S1 ;GET A CHARACTER
JUMPE TF,CQRMT2 ;DONE?
CAIL TF,"a" ;LOWER CASE?
CAILE TF,"z"
TRNA ;NO
SUBI TF,40 ;YES, MAKE UPPER CASE
SUBI TF,40 ;CONVERT TO SIXBIT
ANDI TF,77 ;STRIP OFF JUNK
IDPB TF,S2 ;STORE
JRST CQRMT1 ;LOOP FOR ALL CHARACTERS
CQRMT2: SETZB S1,S2 ;INIT DENSITY AND TRACK CODES
LOAD TF,.CQVSC(P1),CT.DEN ;GET DENSITY
CAIN TF,.CT200 ;200 BPI?
MOVX S1,UC.200 ;YES
CAIN TF,.CT556 ;556 BPI?
MOVX S1,UC.556 ;YES
CAIN TF,.CT800 ;800 BPI?
MOVX S1,UC.800 ;YES
CAIN TF,.CT160 ;1600 BPI?
MOVX S1,UC.160 ;YES
CAIN TF,.CT625 ;6250 BPI?
MOVX S1,UC.625 ;YES
JUMPE S1,.RETF ;RETURN IF UNKNOWN DENSITY CODE
LOAD TF,.CQVSC(P1),CT.TRK ;GET TRACKS
CAIN TF,.CT7TK ;7-TRACKS?
MOVX S2,%TRK7 ;YES
CAIN TF,.CT9TK ;9-TRACKS?
MOVEI S2,%TRK9 ;YES
JUMPE S2,.RETF ;RETURN IF UNKNOWN TRACK CODE
PUSHJ P,D$TRSN## ;GET ITS RESOURCE NUMBER
$RETIF ;GIVE UP IF NO RESOURCE NUMBER
MOVEM S1,.CQRSN(P3) ;SAVE IT
$RETT ;RETURN
; Structures
CQRSTR: MOVE S1,.STUID(P2) ;GET UNIT-ID
MOVEM S1,.CQVID(P3) ;SAVE IT
SETZ S1, ;INIT UNIT STATUS WORD
LOAD S2,.STUCH(P2),ST.UKT ;GET KONTROLLER TYPE
STORE S2,S1,UC.KTP ;SAVE IT
LOAD S2,.STUCH(P2),ST.UTY ;GET UNIT TYPE
STORE S2,S1,UC.UTP ;SAVE IT
PUSHJ P,D$DRSN## ;GET ITS RESOURCE NUMBER
$RETIF ;GIVE UP IF NO RESOURCE NUMBER
MOVEM S1,.CQRSN(P3) ;SAVE IT
$RETT ;RETURN
; DECtapes
CQRDTA: MOVEI S1,1 ;DECTAPES CAN ONLY HAVE
MOVEM S1,.CQNVL(P1) ; ONE REEL PER VOLUME-SET
HRROI S1,.CQVSN(P1) ;POINT TO THE VSN
SKIPN S2,.DTRID(P2) ;TRY FOR THE DECTAPE REELID IF THERE
PUSHJ P,S%SIXB ;ELSE CONVERT VSN TO SIXBIT
MOVEM S2,.CQVID(P3) ;SAVE REELID
PUSHJ P,D$ORSN## ;GET ITS RESOURCE NUMBER
$RETIF ;GIVE UP IF NO RESOURCE NUMBER
MOVEM S1,.CQRSN(P3) ;SAVE IT
$RETT ;RETURN
; Translate catalog device code to MDA device code
CQDEV: PUSH P,T1 ;SAVE T1
MOVE T1,[-CQDEVL,,CQDEVT] ;AOBJN POINTER
HLRZ S2,(T1) ;GET CATALOG DEVICE CODE
CAIE S1,(S2) ;MATCH?
AOBJN T1,.-2 ;LOOP
HRRZ S1,(T1) ;GET MDA DEVICE CODE
POP P,T1 ;RESTORE T1
POPJ P, ;RETURN
; Translate MDA device code to catalog device code
QCDEV: PUSH P,T1 ;SAVE T1
MOVE T1,[-CQDEVL,,CQDEVT] ;AOBJN POINTER
HRRZ S2,(T1) ;GET MDA DEVICE CODE
CAIE S1,(S2) ;MATCH?
AOBJN T1,.-2 ;LOOP
HLRZ S1,(T1) ;GET CATALOG DEVICE CODE
POP P,T1 ;RESTORE T1
POPJ P, ;RETURN
SUBTTL End
END