;;; ************************************************************** TITLE ***** MACLISP ****** ALLFILES FOR ITS/TOPS10 NEWIO *********** ;;; ************************************************************** ;;; ** (C) COPYRIGHT 1977 MASSACHUSETTS INSTITUTE OF TECHNOLOGY ** ;;; ****** THIS IS A READ-ONLY FILE! (ALL WRITES RESERVED) ******* ;;; ************************************************************** IFNDEF TOPS10, TOPS10==:0 IFNDEF ITS, ITS==:1-TOPS10 .MLLIT==1 .FASL IF1,[ .INSRT SYS:.FASL DEFS 10% .INSRT DSK:SYSTEM;FSDEFS > 10$ .INSRT LISP;DECDFS > 10$ .DECDF ] ;END OF IF1 TMPC==0 ;TEMPORARY I/O CHANNEL IN NEWIO VERPRT ALLFILES SUBTTL DOCUMENTATION OF FUNCTIONS ;;; (ALLFILES X) TAKES THE LIST OF NAMELISTS X AND RETURNS A LIST ;;; OF NAMELISTS IN THE FILE SYSTEM WHICH MATCH ELEMENTS OF X. ;;; THERE IS NO GUARANTEE AS TO THE ORDERING OF THE FILES IN ;;; THE RETURNED LIST. IF A SORTED LIST IS DESIRED, THE SORTCAR ;;; FUNCTION SHOULD BE USED WITH AN APPROPRIATE PREDICATE. ;;; ;;; (DIRECTORY X) IS LIKE (ALLFILES X), BUT INSTEAD OF ;;; NAMELISTS IT RETURNS A LIST OF FILE DESCRIPTORS, WHERE ;;; EACH DESCRIPTOR HAS A NAMELIST IN THE CAR AND A ;;; PROPERTY LIST IN THE CDR. TYPICAL PROPERTIES ARE: ;;; WORDS SIZE OF FILE IN PDP-10 WORDS ;;; CHARACTERS SIZE OF FILE IN ASCII CHARACTERS ;;; BITS SIZE IN BITS ;;; BYTESIZE SIZE OF BYTES FILE WAS WRITTEN IN ;;; BYTES SIZE OF FILE IN BYTES ;;; CREDATE DATE OF CREATION ;;; CRETIME TIME OF CREATION ;;; REFDATE DATE OF MOST RECENT REFERENCE ;;; LINK NAME LINKED TO (ITS) ;;; PACK PACK NUMBER (ITS) ;;; STRUCTURE NAME AND UNIT NUMBER (E.G. DSKB0) (TOPS10) ;;; UNDUMPED T IF FILE NOT YET BACKED UP ON MAGTAPE (ITS) ;;; NOREAP T IF NO REAP BIT IS SET (ITS) ;;; AUTHOR AUTHOR'S PPN (TOPS10) ;;; PROTECTION PROTECTION CODE (TOPS10) ;;; MODE MODE WRITTEN IN (TOPS10) ;;; VERSION VERSION NUMBER FROM RIB (TOPS10) ;;; SPOOL SPOOLING NAME (TOPS10) ;;; ;;; (DIRECTORY X PROPS) IS SIMILAR, BUT INCLUDES ONLY ;;; THE PROPERTIES MENTIONED IN "PROPS" FOR EFFICIENCY. ;;; AS A SPECIAL CASE, OMITTING "LINK" CAUSES LINKS NOT ;;; TO BE INCLUDED AT ALL. ;;; ;;; (MAPALLFILES FN X) IS LIKE (MAPC FN (ALLFILES X)) ;;; BUT DOESN'T HAVE TO CONS UP THE WHOLE LIST AT ONCE. ;;; ;;; (MAPDIRECTORY FN X) AND (MAPDIRECTORY FN X PROPS) ;;; ARE SIMILAR. ;;; * AS A DEVICE NAME IMPLIES DSK. ;;; * AS A DIRECTORY NAME USES ALL DIRECTORIES FOR DSK, ;;; AND THE DEFAULT DIRECTORY FOR ALL OTHER DEVICES. ;;; AS A SAFETY FEATURE, THE NAMESTRING "*" IS NOT PERMITTED. ;;; FLAGS (KEPT IN WORD ON FLP) AF.==:1,,525252 AF.NLO==:400000 ;CONS UP NAMELIST ONLY AF.WDS==:200000 ;WANT WORDS PROPERTY AF.CRD==:100000 ;CREATION DATE AF.CRT==:40000 ;CREATION TIME AF.RFD==:20000 ;REFERENCE DATE 10% AF.NRP==:10000 ;NOREAP 10$ AF.AUT==:10000 ;AUTHOR PPN 10% AF.DMP==:4000 ;UNDUMPED 10$ AF.PRO==:4000 ;PROTECTION 10% AF.LNK==:2000 ;LINK 10$ AF.MDE==:2000 ;MODE AF.PAK==:1000 ;PACK NUMBER AF.CHS==:400 ;CHARACTERS AF.BIT==:200 ;BITS AF.BYT==:100 ;BYTES AF.BYS==:40 ;BYTESIZE 10$ AF.VER==:20 ;VERSION 10$ AF.SPL==:10 ;SPOOLING NAME AF.ALL==376000 ;"ALL" THE PROPS 10$ AF.ALL==AF.ALL\AF.VER\AF.SPL AF.MFD==:1 ;1 => MUST USE ALL DIRS IN MFD 10$[ ;OFFSETS FROM FLP WHILE HACKING A DIRECTORY (TOPS10 ONLY) DEFINE ORG -15(FLP)TERMIN ;ORIGION OF FXP WHEN ENTERING ALLFILES DEFINE HAK -14(FLP)TERMIN ;CONTAINS ONE OF: HAKUFD, HAKMFD DEFINE RPT -13(FLP)TERMIN ;POINTER TO P STACK FOR ROUTINE TO CALL & FOR CHANNEL POINTERS DEFINE MDP -12(FXP)TERMIN ;MULTIPLE DEVICE POINTER DEFINE DVB -11(FXP)TERMIN ;DEVICE BLOCK DEFINE FLG -10(FLP)TERMIN ;FLAGS DEFINE AOP -7(FLP)TERMIN ;AOBJN POINTER OVER REQUESTS DEFINE MFP -6(FLP)TERMIN ;POINTER TO MFD BLOCK DEFINE UFP -5(FLP)TERMIN ;POINTER TO UFD BLOCK DEFINE ELP -4(FLP)TERMIN ;POINTER TO EXTENDED LOOKUP BLOCK DEFINE JSP -3(FLP)TERMIN ;POINTER TO DSK: SEARCHLIST DEFINE SSP -2(FLP)TERMIN ;POINTER TO SYS: SEARCHLIST DEFINE ASP -1(FLP)TERMIN ;POINTER TO ALL: SEARCHLIST DEFINE PTN -0(FLP)TERMIN ;POINTER TO NAMELISTS REMAINING MAXFLP==:15 ;NUMBER OF WORDS TO RESERVE ON FLP ELL==:35 ] SUBTTL FUNCTION ENTRY POINTS .ENTRY ALLFILES SUBR 0002 ;SUBR 1 MOVSI R,AF.NLO ;WANT NAMELISTS ONLY ALLFL0: PUSH P,[NIL] ;WILL CONS ENTRIES INTO A LIST PUSHJ P,DIRGEN ;GENERATE DIRECTORY ENTRIES ALLFL1 JRST POPAJ ALLFL1: HRRZ B,CRAP(P) ;"CRAP" IS - CALL 2,.FUNCTION CONS ;DATUM IS IN A MOVEM A,CRAP(P) POPJ P, .ENTRY DIRECTORY LSUBR 2003 ;LSUBR (1 . 2) JSP TT,LWNACK LA12,,.ATOM DIRECTORY MOVSI R,AF.ALL ;WANT ALL THE GARBAGE BY DEFAULT CAMN T,[-2] JSP F,HAKPROPS ;OF COURSE, USER MAY SPECIFY PROPS POP P,A JRST ALLFL0 .ENTRY MAPALLFILES SUBR 0003 ;SUBR 2 MOVSI R,AF.NLO ;NAMELISTS ONLY MAPAL0: HRLI A,(JCALL 1,) ;THE OLD "UUO CELL" HACK TO ALLOW CLOBBERAGE PUSH P,A MOVEI A,(B) PUSHJ P,DIRGEN ;DO THE GENERATE BIT MAPAL1 SUB P,[1,,1] SETZ A, POPJ P, MAPAL1: XCT CRAP(P) ;XCT THE UUO TO CALL THE USER FN .ENTRY MAPDIRECTORY LSUBR 3004 ;LSUBR (2 . 3) JSP TT,LWNACK LA23,,.ATOM MAPDIRECTORY MOVSI R,AF.ALL ;ALL THE PROPERTIES BY DEFAULT CAMN T,[-3] JSP F,HAKPROPS ;BUT USER MAY SPECIFY THE PROPS POP P,B POP P,A JRST MAPAL0 ;;; PROPS PROCESSOR -- SETS FLAGS FROM GIVEN PROPERTY NAMES HAKPROPS: SETZ R, POP P,A HAKPR1: JUMPE A,(F) HLRZ B,(A) CAIN B,.ATOM WORDS TLO R,AF.WDS CAIN B,.ATOM CREDATE TLO R,AF.CRD CAIN B,.ATOM CRETIME TLO R,AF.CRT CAIN B,.ATOM REFDATE TLO R,AF.RFD 10%[ CAIN B,.ATOM NOREAP TLO R,AF.NRP CAIN B,.ATOM UNDUMPED TLO R,AF.DMP CAIN B,.ATOM LINK TLO R,AF.LNK] CAIN B,.ATOM PACK TLO R,AF.PAK CAIN B,.ATOM CHARACTERS TLO R,AF.CHS CAIN B,.ATOM BITS TLO R,AF.BIT CAIN B,.ATOM BYTES TLO R,AF.BYT CAIN B,.ATOM BYTESIZE TLO R,AF.BYS 10$[ CAIN B,.ATOM AUTHOR TLO R,AF.AUT CAIN B,.ATOM PROTECTION TLO R,AF.PRO CAIN B,.ATOM MODE TLO R,AF.MDE CAIN B,.ATOM VERSION TLO R,AF.VER CAIN B,.ATOM SPOOL TLO R,AF.SPL] HRRZ A,(A) JRST HAKPR1 ;ITS ONLY CODE FOR DIRECTORY SEARCHING 10%[ SUBTTL GENERATE DIRECTORY ENTRIES (ITS) ;;; COME HERE WITH FLAGS IN R AND LIST OF NAMELIST PATTERNS IN A DIRGEN: MOVEI F,1(FXP) ;FXP WILL ACCUMULATE FOUR-WORD NAME BLOCKS PUSH FLP,. ;SEE BELOW PUSH FLP,R ;SAVE FLAGS PUSH FLP,F ;THIS WILL BECOME AOBJN PTR TO NAME BLOCKS PUSH P,A ;SAVE LISTS HRRZ A,.SPECIAL DEFAULTF PUSHJ P,FIL6BT SUB FXP,[2,,2] POP FXP,-2(FLP) SUB FXP,[1,,1] HRRZ A,(P) DIRG1: HLRZ A,(A) DIRG1Q: CALL 1,.FUNCTION TYPEP CAIE A,.ATOM SYMBOL JRST DIRG1R HLRZ A,@(P) WTA [NAMESTRING NOT PERMITTED TO ALLFILES - USE A NAMELIST!] JRST DIRG1Q DIRG1R: HLRZ A,@(P) PUSHJ P,FIL6BT ;CONVERT NAMELIST TO NAME BLOCK MOVSI T,(SIXBIT \*\) MOVSI TT,(SIXBIT \DSK\) CAMN T,-3(FXP) ;* AS A DEVICE => DSK MOVEM TT,-3(FXP) CAMN TT,-3(FXP) JRST DIRG1A MOVE D,-2(FLP) ;NON-DSK DEVICE, * DIR => DEFAULT SNAME CAMN T,-2(FXP) MOVEM D,-2(FXP) JRST DIRG1B DIRG1A: MOVSI D,AF.MFD CAMN T,-2(FXP) ;DSK DEVICE, * DIR => USE ALL DIRS IN MFD IORM D,-1(FLP) DIRG1B: MOVSI D,-4 ;BUMP SIZE OF AOBJN PTR ADDM D,(FLP) HRRZ A,@(P) MOVEM A,(P) JUMPN A,DIRG1 PUSH P,(P) ;A NIL; CREATE TWO NILS ON STACK PUSH FLP,(FLP) ;COPY AOBJN PTR ;STATE OF THE WORLD: ; FLP: AOBJN POINTER TO PART OF BLOCK AS YET UNSEARCHED FOR ; AOBJN POINTER TO WHOLE BLOCK OF NAMES ON FXP ; FLAGS WORD ; DEFAULT SNAME ; FXP: ; P: NIL ;FOR DIR ARRAY ; NIL ;FOR MFD ARRAY ; RETURN ADDRESS (POINTS TO ADDRESS OF RECEIVER) CRAP==:-6 ;RET ADR, TWO NILS, PUSHJ TO MFDHAK, ; PUSHJ TO DIRHAK, PUSHJ TO RECEIVER MOVE R,-2(FLP) TLNE R,AF.MFD ;DO THE MFD THING IF NECESSARY PUSHJ P,MFDHAK PUSH P,. ;NULL SLOT (FAKES THE PUSHJ TO MFDHAK) MOVE D,(FLP) ;NOW SCAN OVER ALL NAME BLOCKS DIRG2: SKIPE (D) JRST DIRG2F ;JUMP IF NOT FLUSHED YET DIRG2A: MOVE D,[4,,4] ADDB D,(FLP) JUMPL D,DIRG2 HLRE TT,-1(FLP) ;RESTORE FXP MOVNS TT HRLI TT,(TT) SUB FXP,TT SUB FLP,[4,,4] ;RESTORE FLP SKIPN T,-2(P) ;RELEASE THE ARRAYS JRST DIRG2Z PUSH P,[DIRG2Z] PUSH P,T MOVNI T,1 JCALL 16,.FUNCTION *REARRAY DIRG2Z: SKIPN T,-1(P) JRST DIRG2Y PUSH P,[DIRG2Y] PUSH P,T MOVNI T,1 JCALL 16,.FUNCTION *REARRAY DIRG2Y: SUB P,[3,,3] ;RESTORE P POP P,T JRST 1(T) ;SKIP RETURN DIRG2F: MOVEM D,(FLP) ;FOUND A NAME BLOCK MOVE TT,1(D) MOVE T,(D) PUSHJ P,DIRHAK ;HACK A DIRECTORY FOR THAT ENTRY'S SAKE MOVE D,(FLP) ; (MAY SATISFY OTHER ENTRIES ALSO, JRST DIRG2A ; AND THEY WILL BE FLUSHED) ;;; DISPATCH TO SOME DIRECTORY GROVELER DIRHAK: JRST DSKDIR .SEE DSKD1 ;EXCLUDE LOSING DEVICES BY LOOKING INSIDE ; CAMN T,[SIXBIT \DSK\] ;DSK => DSK DIRECTORY ; JRST DSKDIR ; CAME T,[SIXBIT \AI\] ;MANY OTHER DEVICES ARE DSK-LIKE ; CAMN T,[SIXBIT \ML\] ;Indeed! Like ARC's ... --SMM ; JRST DSKDIR ; CAME T,[SIXBIT \MC\] ; CAMN T,[SIXBIT \DM\] ; JRST DSKDIR ; CAMN T,[SIXBIT \TTY\] ; JRST TTYDIR ; POPJ P, ;DO NOTHING FOR UNKNOWN DEVICE SUBTTL GROVEL OVER DSK MFD ;;; DO DSK DIRECTORY THING FOR EVERY DIRECTORY IN MFD MFDHAK: SKIPN A,-2(P) PUSHJ P,GETMFD ;GET MFD ARRAY IF NECESSARY MOVEM A,-2(P) MOVEI TT,MDNAMP ;OFFSET OF START OF NAME AREA MOVE D,@TTSAR(A) HRLI D,-2000(D) MOVEI TT,MDCHK ;USURP MDCHK TO HOLD AOBJN PTR MFDH1: MOVEM D,@TTSAR(A) MOVEI TT,MNUNAM(D) ;GET A DIRECTORY NAME FROM MFD MOVSI T,(SIXBIT \DSK\) ;THE DEVICE NAME IS "DSK" SKIPE TT,@TTSAR(A) PUSHJ P,DSKDIR ;HACK THAT DIRECTORY (IF NOT ZERO) MOVE A,-2(P) MOVEI TT,MDCHK MOVE D,@TTSAR(A) ADD D,[LMNBLK,,LMNBLK] ;LOOP OVER ALL MFD ENTRIES JUMPL D,MFDH1 POPJ P, ;;; ROUTINE TO MAKE A FIXNUM ARRAY WITH THE DSK MFD IN IT GETMFD: PUSH P,[GTMFD1] ;THE MFD IS 2000 WORDS LONG PUSH P,[NIL] PUSH P,[.ATOM FIXNUM ] PUSH P,[.ATOM #2000 ] MOVNI T,3 JCALL 16,.FUNCTION *ARRAY GTMFD1: HLLOS NOQUIT ;LOCK OUT INTERRUPTS AND QUITS .OPEN TMPC,[SIXBIT \ &DSKM.F.D.(FILE)\] .VALUE HRRZ TT,TTSAR(A) HRLI TT,-2000 .IOT TMPC,TT ;GOBBLE DOWN MFD .CLOSE TMPC, HRRZS NOQUIT JRST CHECKI ;UNLOCK INTERRUPTS SUBTTL GROVEL OVER DSK DIRECTORY DSKDIR: PUSH FXP,T ;DEVICE NAME (DSK, AI, ML, MC, DM) PUSH FXP,TT ;DIRECTORY NAME SKIPE A,-2(P) ;MAY NEED TO CREATE ARRAY TO HOLD DIR JRST DSKD1 ;NOPE - ONE ALREADY CREATED PUSH P,[DSKD1] ;OTHERWISE CREATE ONE PUSH P,[NIL] ;A DSK DIRECTORY IS 2000 WORDS LONG PUSH P,[.ATOM FIXNUM ] PUSH P,[.ATOM #2000 ] MOVNI T,3 JCALL 16,.FUNCTION *ARRAY DSKD1: MOVEM A,-2(P) HLLOS NOQUIT ;LOCK OUT INTERRUPTS AND QUITS .CALL DSKD9 JRST DSKD8 ;DIR MAY NOT EXIST -- BUT THERE ARE OTHER POSSIBILITIES HRRZ TT,TTSAR(A) HRLI TT,-2001 .IOT TMPC,TT ;GOBBLE DOWN DIR .CLOSE TMPC, HLLZS NOQUIT PUSHJ P,CHECKI ;UNLOCK INTERRUPTS AOBJN TT,DSKD8A ;Directory too short--First of a series of checks TLNE TT,-1 ;Too long? ;Even on KA, this wins because lisp doesn't JRST DSKD8A ; use last page (remember aobjn difference?) MOVEI TT,UDESCP ;More checks for "In DSK dir format?" MOVE D,@TTSAR(A) CAIL D,6*<2000-11> ;Maximum possible value for udescp JRST DSKD8A ; MOVEI TT,UDNAME ;Check that user name agrees (will screw translations-- ; MOVE D,@TTSAR(A) ; is that a bug or a feature?--i think a bug) ; CAME D,0(FXP) ;The other checks should be sufficient to exclude ; JRST DSKD8A ; the most obvious cases: TTY, COR... and include MOVEI TT,UDNAMP ; DSK:, AI:..., DIR:, ARC: (including funny names) MOVE D,@TTSAR(A) CAILE D,2000 ;Maximum value for udnamp JRST DSKD8A HRLI D,-2000(D) MOVEI TT,UDNAME DSKD2: JUMPL D,DSKD2A POP FXP,TT ;ALL DONE -- FLUSH SATISFIED NAME BLOCKS POP FXP,T JRST FMARK DSKD2A: MOVEM D,@TTSAR(A) ;USURP UDNAME FOR AOBJN PTR MOVEI TT,UNRNDM(D) MOVE T,@TTSAR(A) TLNE T,DELBTS ;IGNORE DELETED FILES JRST DSKD7 TLNN T,UNLINK JRST DSKD3 MOVE F,-2(FLP) ;IGNORE LINKS IF NOT TLNE F,AF.NLO ; SPECIFICALLY ASKED FOR JRST DSKD3 TLNN F,AF.LNK JRST DSKD7 DSKD3: MOVEI TT,UNFN2(D) ;ELSE GET FILE NAMES MOVE R,@TTSAR(A) MOVEI TT,UNFN1(D) MOVE D,@TTSAR(A) MOVE T,-1(FXP) ;GET DEVICE AND DIR NAMES MOVE TT,(FXP) PUSHJ P,FMATCH ;TRY TO MATCH A NAME BLOCK JRST DSKD7 ;LOSE LOSE MOVE F,-2(FLP) ;IF WIN, NAMELIST IS IN A TLNE F,AF.NLO JRST DSKD6 ;WANT JUST THE NAMELIST MOVEI TT,UDNAME ;WANT INFINITE CRAP. MOVE AR2A,-2(P) ; SET UP DIR ARRAY IN AR2A, MOVE D,@TTSAR(AR2A) ; DIR INDEX IN D, SETZ AR1, ; ACCUMULATING PLIST IN AR1. PUSH P,A ;HACK ALL THE POSSIBLE PROPERTIES TLNE F,AF.DMP PUSHJ P,PRDMP ;INVERSE OF DUMPED BIT TLNE F,AF.NRP PUSHJ P,PRNRP ;NOREAP BIT TLNE F,AF.PAK PUSHJ P,PRPAK TLNE F,AF.RFD PUSHJ P,PRRFD ;REFERENCE DATE TLNE F,AF.CRT PUSHJ P,PRCRT ;CREATION TIME TLNE F,AF.CRD PUSHJ P,PRCRD ;CREATION DATE TLNE F,AF.LNK PUSHJ P,PRLNK ;LINK TLNE F,AF.WDS\AF.CHS\AF.BIT\AF.BYT\AF.BYS PUSHJ P,PRSIZ ;VARIOUS SIZES POP P,A MOVEI B,(AR1) CALL 2,.FUNCTION CONS ;CONS TOGETHER NAMELIST AND PLIST DSKD6: MOVE T,@CRAP+2(P) ;CALL THE RECEIVER WITH THE GOODIE PUSHJ P,(T) DSKD7: MOVE A,-2(P) ;CYCLE OVER ALL DSK DIRECTORY ENTRIES MOVEI TT,UDNAME MOVE D,@TTSAR(A) ADD D,[LUNBLK,,LUNBLK] JRST DSKD2 DSKD8A: ;PERHAPS EVENTUALLY USE FOR "USER LOSSAGE" ENTRY DSKD8: HLLZS NOQUIT ;Directory doesn't exist or perhaps can't be gotten ; should check if error of type 6,7,10 (i.e. recoverable ; system error) and if not give "user error" SUB FXP,[2,,2] ;RESTORE THE WORLD AND EXIT, JRST CHECKI ; UNLOCKING INTERRUPTS DSKD9: SETZ SIXBIT \OPEN\ ;OPEN FILE 5000,,6 ;IMAGE BLOCK INPUT MODE 1000,,TMPC ;CHANNEL # ,,-1(FXP) ;DEVICE NAME ,,[SIXBIT \.FILE.\] ;FILE NAME 1 ,,[SIXBIT \(DIR)\] ;FILE NAME 2 400000,,0(FXP) ;DIRECTORY NAME SUBTTL PROPERTY CONSING ROUTINES PRDMP: MOVEI TT,UNRNDM(D) MOVE T,@TTSAR(AR2A) TLNE T,UNDUMP POPJ P, MOVEI C,.ATOM UNDUMPED PRBIT: MOVEI A,.ATOM T JRST PRCONS PRNRP: MOVEI TT,UNRNDM(D) MOVE T,@TTSAR(AR2A) TLNN T,UNREAP POPJ P, MOVEI C,.ATOM NOREAP JRST PRBIT PRPAK: MOVEI TT,UNRNDM(D) LDB TT,[UNPKN @TTSAR(AR2A)] MOVEI C,.ATOM PACK PFCONS: JSP T,FXCONS PRCONS: MOVEI B,(AR1) CALL 2,.FUNCTION CONS MOVEI B,(C) CALL 2,.FUNCTION XCONS MOVEI AR1,(B) POPJ P, PRRFD: MOVEI TT,UNREF(D) MOVEI C,.ATOM REFDATE JRST PRCRD1 PRCRD: MOVEI TT,UNDATE(D) MOVEI C,.ATOM CREDATE PRCRD1: MOVE R,@TTSAR(AR2A) LDB TT,[UNDAY R] JSP T,FXCONS CALL 1,.FUNCTION NCONS MOVEI B,(A) LDB TT,[UNMON R] JSP T,FXCONS CALL 2,.FUNCTION CONS MOVEI B,(A) LDB TT,[UNYRB R] JSP T,FXCONS CALL 2,.FUNCTION CONS JRST PRCONS PRCRT: MOVEI TT,UNDATE(D) MOVEI C,.ATOM CRETIME LDB T,[UNTIM @TTSAR(AR2A)] LSH T,-1 ;DSK TIME IN IN HALF-SECONDS IDIVI T,60. PUSH FXP,TT IDIVI T,60. PUSH FXP,T EXCH TT,-1(FXP) JSP T,FXCONS CALL 1,.FUNCTION NCONS MOVEI B,(A) MOVE TT,-1(FXP) JSP T,FXCONS CALL 2,.FUNCTION CONS MOVEI B,(A) POP FXP,TT JSP T,FXCONS CALL 2,.FUNCTION CONS SUB FXP,[1,,1] JRST PRCONS PRLNK: MOVEI TT,UNRNDM(D) MOVE T,@TTSAR(AR2A) TLNN T,UNLINK ;NO LINK PROP IF NOT A LINK POPJ P, ANDI T,.BM UNDSCP ;GOBBLE UP DESCRIPTOR POINTER IDIVI T,UFDBPW ;CONVERT TO BYTE POINTER MOVEI R,44 IMULI TT,UFDBYT SUBI R,(TT) ROT R,-6 ADD R,[UFDBYT_6,,] HRRI R,UDDESC(T) ;R NOW HAS BYTE POINTER INTO DIR FOR LINK DESCRIPTOR MOVEI A,3 ;WILL GOBBLE DIR AND TWO FILE NAMES PUSH FXP,-1(FXP) ;DEVICE IS SAME AS WAS GIVEN TO DSKDIR PUSH FXP,[0] PRLNK1: MOVEI T,(FXP) ;BYTE POINTER FOR ACCUMLATING NAME HRLI T,440600 PUSH FXP,T PRLNK2: IBP R ;INCREMENT DESCRIPTOR BYTE PTR MOVEI TT,(R) HLLZ T,R ADD T,[@TTSAR(AR2A)] LDB TT,T ;GOBBLE BYTE FROM ARRAY CAIE TT,'; ;SEMICOLON TERMINATES NAMES CAIN TT,0 ;SO DOES A ZERO BYTE JRST PRLNK4 CAIE TT,': ;COLON QUOTES CHARACTERSSP; JRST PRLNK3 IBP R ;FETCH QUOTED BYTE MOVEI TT,(R) HLLZ T,R ADD T,[@TTSAR(AR2A)] LDB TT,T PRLNK3: IDPB TT,(FXP) ;PUT BYTE INTO NAME LDB T,[360600,,(FXP)] JUMPN T,PRLNK2 ;FILLING NAME WORD ALSO FINISHES PRLNK4: SETZM (FXP) ;MAY NEED TO GOBBLE SOJG A,PRLNK1 ; ANOTHER NAME SUB FXP,[1,,1] PUSH FLP,D PUSH P,AR2A PUSH P,AR1 PUSHJ P,6BTNML ;NAME A NAMELIST FOR LINK (SAVES F) POP P,AR1 POP P,AR2A POP FLP,D MOVEI C,.ATOM LINK JRST PRCONS ;CONS ON LINK PROPERTY PRSIZ: MOVEI TT,UNRNDM(D) MOVE T,@TTSAR(AR2A) TLNE T,UNLINK ;NO SIZE PROPS IF A LINK POPJ P, ANDI T,.BM UNDSCP ;GOBBLE UP DESCRIPTOR POINTER IDIVI T,UFDBPW ;CONVERT TO BYTE POINTER MOVEI R,44 IMULI TT,UFDBYT SUBI R,(TT) ROT R,-6 ADD R,[UFDBYT_6,,] HRRI R,UDDESC(T) ;R NOW HAS BYTE POINTER FOR FILE BLOCK DESCRIPTOR BYTES ;THE FOLLOWING CODE WAS SWIPED FROM NFLLN1 IN ITS SETO T, PRSIZ1: IBP R ;FETCH NEXT BYTE MOVEI TT,(R) HLLZ C,R ADD C,[@TTSAR(AR2A)] ;TTSAR=1, ERGO SAFE TO PUT IN C LDB TT,C JUMPE TT,PRSIZ5 ;ZERO BYTE TERMINATES CAILE TT,UDTKMX JRST PRSIZ2 ADDI T,(TT) ;NEXT N BLOCKS JRST PRSIZ1 PRSIZ2: CAIGE TT,UDWPH AOJA T,PRSIZ1 ;SKIP N, TAKE 1 CAIN TT,UDWPH JRST PRSIZ1 ;PLACE-HOLDER OR NULL REPEAT NXLBYT, IBP R ;LOAD ADDRESS (GOBBLES MORE BYTES), AOJA T,PRSIZ1 ; TAKE 1 BLOCK PRSIZ5: IMULI T,2000 MOVEI TT,UNRNDM(D) LDB TT,[UNWRDC @TTSAR(AR2A)] SKIPN TT ;NUMBER OF WORDS IN MOVEI TT,2000 ; LAST BLOCK ADD TT,T PUSH FXP,TT ;THIS IS THE SIZE IN WORDS MOVEI C,.ATOM WORDS TLNE F,AF.WDS PUSHJ P,PFCONS ;THE FOLLOWING CODE WAS SWIPED FROM QBDCD IN ITS MOVEI TT,UNREF(D) LDB T,[UNBYTE @TTSAR(AR2A)] TRZN T,400 JRST PRSZ6A IDIVI T,100 JRST PRSZ6F PRSZ6A: TRZN T,200 JRST PRSZ6B IDIVI T,20 JRST PRSZ6F PRSZ6B: SUBI T,44 JUMPL T,PRSZ6C IDIVI T,4 JRST PRSZ6F PRSZ6C: MOVNS T SETZ TT, ;BYTE SIZE IS IN T, NUMBER OF UNUSED BYTES IN TT PRSZ6F: PUSH FXP,T PUSH FXP,TT MOVEI TT,44 IDIV TT,-1(FXP) PUSH FXP,TT ;FXP HAS: BYTES PER WORD, NUMBER OF UNUSED BYTES, BYTE SIZE, FILE LENGTH IN WORDS IMUL TT,-3(FXP) SUB TT,-1(FXP) ;BYTES IN FILE MOVE R,TT IMUL TT,-2(FXP) ;BITS IN FILE MOVEI C,.ATOM BITS TLNE F,AF.BIT PUSHJ P,PFCONS MOVE TT,R MOVEI C,.ATOM BYTES TLNE F,AF.BYT PUSHJ P,PFCONS MOVE TT,-2(FXP) ;BYTE SIZE MOVEI C,.ATOM BYTESIZE TLNE F,AF.BYS PUSHJ P,PFCONS MOVE T,(FXP) SUB T,-1(FXP) ;NUMBER OF USED BYTES IN LAST WORD IMUL T,-2(FXP) ;NUMBER OF USED BITS IN LAST WORD IDIVI T,7 ;NUMBER OF USED CHARACTERS IN LAST WORD SOS TT,-3(FXP) IMULI TT,5 ;NUMBER OF USED CHARACTERS IN ALL BUT LAST WORD ADD TT,T MOVEI C,.ATOM CHARACTERS TLNE F,AF.CHS PUSHJ P,PFCONS SUB FXP,[4,,4] POPJ P, SUBTTL UTILITY ROUTINES (FILE NAME MATCHER, EXPUNGER, ETC.) ;;; TAKE FILE NAMES IN T, TT, D, R AND SKIP IFF A MATCH ;;; IS FOUND IN GIVEN LIST OF FILE NAMES. FMATCH: MOVE F,-1(FLP) MOVSI AR2A,(SIXBIT \*\) FMAT0: SKIPN (F) ;CAN'T MATCH FLUSHED ENTRY JRST FMAT7 CAME T,(F) ;MATCH DEVICE NAME CAMN AR2A,(F) CAIA JRST FMAT7 CAME TT,1(F) ;MATCH SNAME CAMN AR2A,1(F) CAIA JRST FMAT7 CAME D,2(F) ;MATCH FILE NAME 1 CAMN AR2A,2(F) CAIA JRST FMAT7 CAME R,3(F) ;MATCH FILE NAME 2 CAMN AR2A,3(F) CAIA JRST FMAT7 PUSH FXP,T ;IF MATCH, CREATE NAMELIST PUSH FXP,TT PUSH FXP,D PUSH FXP,R AOS (P) ;SKIP RETURN JRST 6BTNML FMAT7: ADD F,[3,,3] ;CYCLE OVER ALL NAME BLOCKS AOBJN F,FMAT0 POPJ P, ;NO SKIP IF LOSE ;;; TAKE (DEV,DIR) IN (T,TT) AND FLUSH ALL PATTERNS ;;; WHICH MATCH EXACTLY (THEY CAN'T BE USED AGAIN, SINCE ;;; WE HAVE ALREADY TRAVERSED THAT DEVICE DIRECTORY). ;;; A PATTERN IS FLUSHED BY ZEROING THE DEVICE NAME. ;;; IF TT HAS 0, DIR IS IGNORED. FMARK: MOVE F,-1(FLP) FMARK0: SKIPE TT CAMN TT,1(F) CAME T,(F) CAIA SETZM (F) ADD F,[4,,4] JUMPL F,FMARK0 POPJ P, IF2,[ ;EXPUNGE ALL THE CRETINOUS SYMBOLS DEFINE DEFSYM X/ IRPS Z,,[X] EXPUNGE Z TERMIN TERMIN .INSRT DSK:SYSTEM;FSDEFS > ] ;END OF IF2 ] ;END OF 10% ;TOPS10 ONLY DIRECTORY SEARCHING AND PROPERTY CONSING ROUTINES 10$[ SUBTTL GENERATE DIRECTORY ENTRIES (TOPS10) ;;; COME HERE WITH FLAGS IN R AND LIST OF NAMELIST PATTERNS IN A DIRGEN: REPEAT MAXFLP, PUSH FLP,[0] ;ALLOCATE THE APPROPRIATE NUMBER OF WORDS MOVEM P,RTP ;SAVE THE CURRENT REPEAT 3, PUSH P,[0] ;ALSO NEED 3 WORDS ON P MOVEM R,FLG ;SAVE FLAGS ON FLP MOVEI F,1(FXP) ;THIS WILL BECOME PONTER TO NAMELISTS MOVEM F,AOP MOVEM FXP,ORG ;SAVE FXP SO IT CAN BE RESTORED LATER PUSH P,A ;SAVE LIST POINTER HLRZ A,(A) ;GET THE CAR DIRNL: CALL 1,.FUNCTION TYPEP ;GET TYPE DIRCHT: CAIE A,.ATOM SYMBOL ;MUST NOT BE A SYMBOL JRST DIRNSY ;OK IF NOT HLRZ A,@(P) WTA [NAMESTRING not permitted to ALLFILES -- Use a NAMELIST!] JRST DIRCHT DIRNSY: HLRZ A,@(P) ;NAMELIST PUSHJ P,FIL6BT ;CONVERT TO SIXBIT ON FXP STACK HRLZI T,(SIXBIT/*/) ;WILDCARD CHARACTER HRLZI TT,(SIXBIT/DSK/) ;DEFAULT DEVICE NAME CAMN T,-3(FXP) ;WILDCARD DEVICE? MOVEM TT,-3(FXP) ;YES, REPLACE WITH DSK MOVE D,-3(FXP) ;GET FINALIZED DEVICE DEVTYP D, ;GET TYPE BITS JRST DIRNDU ;NO DEVTYP UUO, WE MUST USE OTHER MEANS TRNE D,77 ;DEVICE 0 MEANS DISK JRST DIRNDK ;NOT A DISK, MUST TAKE DRASTIC MEASURES! PUSH FXP,[0] ;BUILD OPEN BLOCK PUSH FXP,-4(FXP) ;DEVICE PUSH FXP,[0] ;NO BUFFERS ;Lock LISP interrupts here as we will use TMPC OPEN TMPC,-2(FXP) ;GET THE DEVICE JRST DIROER ;NOT THERE, WHY DID DEVNAM WORK? MOVEI T,-2(FXP) ;POINTER TO STACK FOR PATH. UUO HRLI T,3 ;NEED THREE VALUES MOVEI TT,TMPC ;CHANNEL FOR PATH. MOVEM TT,-2(FXP) ;STORE IN ARG BLOCK PATH. T, ;NOW GET DATA ABOUT DEVICE JRST DIRNPU ;MUST BE NO PATH. UUO, KLUDGE DATA SOME OTHER WAY RELEAS TMPC, ;WE DON'T NEED THE DEVICE ANYMORE ;Done with TMPC, we can unlock interrupts MOVEI TT,PT.IPP ;THIS DEVICE HAVE AN IMPLIED PPN (ERSATZ DEVICE)? TDNN TT,-1(FXP) JRST DIRNIP ;NOT IMPLIED PPN, GO ON MOVE TT,(FXP) ;GET THE DEVICE'S PPN MOVEM TT,-5(FXP) ;REPLACE USER'S VALUE HRLZI TT,(SIXBIT/DSK/) ;SUBSTITUTE LEFT HALF OF DEVICE WITH 'DSK' HLLM TT,-2(FXP) DIRNIP: LDB TT,[XXX] ;GET SEARCHLIST BYTE MOVE D,-2(FXP) ;GET DEVICE FROM PATH. RETURN TRNE D,-1 ;NOT EXPLICIT STRUCTURE? CAIN TT,2 ;OR JOB SEARCHLIST? HRLZI D,(SIXBIT/DSK/) ;YES, USE DSK CAIN TT,3 ;SYS: SEARCHLIST? HRLZI D,(SIXBIT/SYS/) CAIN TT,1 ;ALL STRUCTURES? HRLZI D,(SIXBIT/ALL/) SUB FXP,[3,,3] ;WE NO LONGER NEED PATH./OPEN BLOCK MOVEM D,-3(FXP) ;STORE NEW DEVICE NAME SETZI TT, ;START WITH NO FLAGS CAMN D,[SIXBIT/SYS/] ;SYSTEM DEVICE? MOVEI TT,DF.SYS ;YES, FLAG AS SUCH CAMN D,[SIXBIT/ALL/] ;THIS IS ALSO SPECIAL MOVEI TT,DF.ALL CAMN D,[SIXBIT/DSK/] ;LAST CHECK MOVEI TT,DF.DSK HRRM TT,(FXP) ;STORE FLAGS NEXT TO THE EXTENSION HRLZI TT,AF.ALS ;ALL STRUCTURE FLAG CAMN D,[SIXBIT/ALL/] ;DOES THIS ONE WANT EVRYTHING? IORM TT,FLG ;YES, REMEMBER MOVSI D,-4 ;BUMP AOBJN POINTER TO NAME DESCRIPTORS ADDM D,AOP HRRZ A,@(P) ;GET CDR MOVEM A,(P) ;REPLACE OVER OLD POINTER JUMPN A,DIRNL ;IF NON-NIL THEN READ NEXT NAMELIST PUSHJ P,GTHDSK ;GATHER DSK: SEARCHLIST PUSHJ P,GTHSYS ;GATHER SYS: SEARCHLIST HRLZI T,AF.ALS ;ANY NEED FOR ALL:? TDNE T,FLG PUSHJ P,GTHALL ;YUP, WE WILL NEED SO WE WILL GET MOVE D,AOP ;GET THE NAMELIST POINTER MOVEM D,PTN ;STORE IN A TEMP LOCATION DIRWLD: SKIPN (D) ;THIS ENTRY BEEN HACKED? JRST DIRDON ;YUP, SO IT MAY BE IGNORED HLRE T,1(D) ;GET LEFT HALF PPN AOJE T,DIRHWD ;HACK WILD PPN IF -1 HRRE T,1(D) ;RIGHT HALF AOJN T,DIRDON ;NO WILD PPN IF NEITHER HALF -1 DIRHWD: MOVE TT,(D) ;GET THE DEVICE TO HACK MOVEI TT,HAKMFD ;ROUTINE TO CALL MOVEM TT,HAK ;REMEMBER FOR LATER PUSHJ P,OPNDEV ;THEN HACK ALL UFD'S DIRDON: MOVE T,[4,,4] ;BUMP FOR POINTER ADDM T,PTN SKIPGE D,PTN ;GET POINTER, SKIP IF NO ENTRIES REMAIN JRST DIRWLD ;HACK THE NEXT ENTRY MOVE D,AOP ;RETRIEVE THE POINTER MOVEM D,PTN ;SAVE A NEW COPY DIRPPN: SKIPN TT,(D) ;THIS BEEN DONE BY A WILD ENTRY? JRST DIRDN1 ;YES, SO IT MAY BE IGNORED MOVEI T,HAKUFD ;ROUTINE TO CALL MOVEM T,HAK ;MAKE ACCESSIBLE TO OTHER ROUTINES PUSHJ P,OPNDEV ;GET THIS DEVICE DIRDN1: MOVE T,[4,,4] ;POINTER SHOULD BE BUMPED ADDM T,PTN SKIPGE D,PTN ;IF POINTER IS STILL OK THEN DON'T SKIP JRST DIRPPN ;AND TRY FOR NEXT PPN SUB FLP,[MAXFLP,,MAXFLP] ;RESTORE FLP TO ORIGIONAL STATE MOVE FXP,ORG ;SAME WITH FXP SUB P,[3,,3] ;GET RID OF CHANNEL BLOCKS ALLOCATED POPJ P, ;RETURN AS WE ARE DONE SUBTTL Searchlist building routines ;GTHDSK: Build the JOB's searchlist GTHDSK: MOVEI D,(FXP) ;WILL BUILD POINTER IN D PUSH FXP,[-1] ;GET THE FIRST THING FIRST! HRLZI T,1 ;ONLY DEVICE NAME DSKNXT: HRRI T,(FXP) ;POINTER FOR JOBSTR UUO JOBSTR T, ;GET THE INFO JRST DSKJFL ;JOBSTR FAILED SKIPN TT,(FXP) ;ARE WE AT THE FENCE? JRST DSKEND ADD D,[-1,,0] ;BUMP POINTER PUSH FXP,TT ;COPY DEVICE NAME FOR NEXT ROUND JRST DSKNXT DSKEND: MOVEM D,JSP ;PLANT POINTER IN ITS SPOT POP FXP,T ;RESTORE STACK TO CORRECT VALUE POPJ P, ;GTHSYS: Build the system's searchlist GTHSYS: MOVEI D,(FXP) ;START BUILDING POINTER PUSH FXP,[0] ;WE NEED SYSTEM SEARCHLIST PUSH FXP,. ;IGNORED PUSH FXP,[-1] ;START FROM FIRST STRUCTURE HRLZI T,3 ;ALWAYS 3 ARGS HRRI T,-2(FXP) ;CORRECT POINTER GOBSTR T, ;GET THE NEXT STRUCTURE JRST SYSGFL ;GOBSTR FAILURE SKIPN TT,(FXP) ;ONLY USEFUL IF NON-NULL JRST SYSEND MOVEM TT,-2(FXP) ;STORE IN SAFE LOCATION PUSH FXP,TT ;THEN THE DEVICE SETZM -2(FXP) ;WE STILL WANT SYSTEM SEARCHLIST ADD D,[-1,,0] ;BUMP POINTER JRST SYSNXT ;NOW GET THE NEXT STRUCTURE SYSEND: MOVEM D,SSP ;REMEMBER POINTER SUB FXP,[3,,3] ;RETURN STACK TO NORMAL POPJ P, ;GTHALL: Build the ALL searchlist GTHALL: MOVEI D,(FXP) ;START BUILDING POINTER SETZI T, ;START FROM FIRST STRUCTURE ALLNXT: SYSSTR T, ;GET THE NEXT STRUCTURE JRST ALLSFL ;UUO FAILURE! JUMPE T,ALLEND ;DONE IF NO MORE STRUCTURES PUSH FXP,T ;ELSE REMEMBER THIS ADD D,[-1,,0] ;BUMP THE POINTER JRST ALLNXT ;THEN PROCEED TO NEXT STRUCTURE ALLEND: MOVEM D,ASP ;STORE THE POINTER POPJ P, SUBTTL Device hacking routines ;OPNDEV: ROUTINE TO PROCESS DEVICES ;CALLED WITH: DEVICE IN TT ; ROUTINE TO CALL IN -1(P) ; POINTER TO FILE DESCRIPTOR BLOCK IN D OPNDEV: MOVSS TT ;REVERSE DEVICE NAME FOR FAST CHECKING CAIN TT,(SIXBIT/DSK/) ;JOB SEARCHLIST? HRLZI TT,JSP ;YES, POINT TO IT CAIN TT,(SIXBIT/ALL/) ;EVERY STRUCTURE? HRLZI TT,ASP ;YES, POINTER TO IT CAIN TT,(SIXBIT/SYS/) ;SYSTEM SEARCHLIST? HRLZI TT,SSP ;YES, POINTER TO IT IN FLP MOVSS TT ;REVERSE HALVES AGAIN TLNN TT,-1 ;IS IT A POINTER? JRST OPNPNT ;YES, HANDLE AS LIST OF DEVICES ;ALTERNATE ENTRY-POINT IF NON-MUTIPLE-DEVICE 'DEVICES' (SYS, ALL, DSK) ;ACTUAL DEVICE IN TT IS NOW A GOOD ONE TO USE OPNNXT: SETZI F, ;CLEAR FLAGS SKIPN T,JSP ;ANY JOB SEARCHLIST? JRST $DOSSP ;NOPE, TRY SYSTEM SEARCHLIST $NXJSP: CAMN TT,(T) ;IS THIS A MATCH? TROA F,DF.DSK ;YES, SO WE ARE IN DSK: SEARCHLIST AOBJN T,$NXJSP ;DO ALL ENTRIES $DOSSP: SKIPN T,SSP ;ANY SYS:? JRST $DOASP ;NOPE, TRY ALL: SEARCHLIST $NXSSP: CAMN TT,(T) ;THIS A MATCH? TROA F,DF.SYS AOBJN T,$NXSSP $DOASP: SKIPN T,ASP ;TRY FOR ALL: SEARCHLIST JRST NMSL ;NONE, SO GO BACK TO CODE $NXASP: CAMN TT,(T) ;THIS A MATCH ON THE DEVICE? TROA F,DF.ALL AOBJN T,$NXASP NMSL: TRC F,DF.ALL ;MAKE SENSE OF FLAG CORRECT HRRM F,FLG ;THESE ARE THE FLAGS FOR THIS ROUND MOVE T,AOP ;POINTER TO ALL NAMELISTS MOVEI T,HAKMFD ;WE MUST TEST TO SEE WHICH CHANNEL CAMN T,-1(P) ;ARE WE HACKING AN MFD? SKIPA T,[MFP] ;YES, USE MFD CHANNEL MOVE T,[UFP] ;ELSE USE UFD CHANNEL SKIPE R,@T ;HAVE WE BUILT THE BLOCK YET? JRST OPNHBK ;YES, WE HAVE THE BLOCK MOVEI R,(FXP) ;THIS WILL BE THE POINTER MOVEM R,@T ;SAVE FOR LATER USE PUSH FXP,TT ;SAVE DEVICE NAME AS FIRST ENTRY MOVEI R,207 ;WE NEED 1+3+203 WORDS PUSH FXP, SOJG R,.-1 ;ALLOCATE WORDS IN TIGHT LOOP PUSH FXP,T ;SAVE POINTER PUSHJ P,ALFILE ;GET A CHANNEL ALLOCATED MOVE B,RPT ;GET POINTER TO WORDS ON P SKIPN 1(B) ;THIS SLOT BEEN USED? EXCH A,1(B) ;NOPE, WE CAN USE IT NOW SKIPE A ;DID WE STORE ALREADY? MOVEM A,2(B) ;NOPE, DO SO NOW LSH T,27 ;MOVE CHANNEL # TO AC FIELD EXCH T,(FXP) ;REMEMBER CHANNEL NUMBER AND RESTORE POINTER MOVE R,@T ;R MUST HOLD POINTER INTO FXP POP FXP,1(R) ;THEN PUT CHANNEL NUMBER WHERE IT BELONGS OPNHBK: PUSH FXP,[14] ;BUILD THE OPEN BLOCK ON FXP PUSH FXP,TT ;DEVICE NAME HRLZI T,2(R) ;POINTER TO BUFFER HEADER PUSH FXP,T ;LAST WORD FOR OPEN MOVE T,[OPEN -2(FXP)] ;GET THE OPEN INSTRUCTION IOR T,1(R) ;PLACE IN IT THE CHANNEL NUMBER XCT T ;THEN PERFORM THE OP JRST OPNOPF ;FAILURE, WHAT SHOULD WE DO? MOVEI T,5(R) ;THIS IS WHERE THE BUFFER HAS TO GO SUB FXP,[3,,3] ;GET RID OF THE OPEN BLOCK PUSH FXP,.JBFF ;SAVE THE CURRENT FIRST FREE LOCATION MOVEM T,.JBFF ;KLUDGE IT SO BUFFER GOES IN RIGHT PLACE MOVE T,[INBUF 1] ;WE WILL TAKE ONE BUFFER IOR T,1(R) ;THE CORRECT CHANNEL XCT T ;GET THE BUFFER POP FXP,.JBFF ;RESTORE .JBFF FOR OTHER PEOPLE TO USE MOVEM R,DVB ;REMEMBER THE POINTER PUSHJ P,@HAK ;CALL THE APPROPRIATE ROUTINE MOVE R,DVB ;RESTORE THE POINTER MOVE T,[RELEAS] ;WE CAN NOW RID OURSELVES OF THE DEVICE IOR T,1(R) ;BUT ON THE CORRECT CHANNEL XCT T ;DO IT MOVE TT,(R) ;THIS IS THE DEVICE WE JUST HACKED SETZI F, ;CLEAR FLAGS SKIPN T,JSP ;ANY JOB SEARCHLIST? JRST DOSSP ;NOPE, TRY SYSTEM SEARCHLIST NXTJSP: CAMN TT,(T) ;IS THIS A MATCH? SETZM (T) ;YES, CLEAR THE DEVICE AS WE HAVE HACKED IT SKIPE (T) ;IS THERE A DEVICE HERE? TRO F,DF.DSK ;YES, SO DSK: IS NOT COMPLETELY DONE AOBJN T,NXTJSP ;THEN DO ALL ENTRIES DOSSP: TRCN F,DF.DSK ;COMPLEMENT THE SENSE SETZM JSP ;NO DSK: LEFT SO OPTIMIZE BY CLEARING POINTER SKIPN T,SSP ;ANY SYS:? JRST DOASP ;NOPE, TRY ALL: SEARCHLIST NXTSSP: CAMN TT,(T) ;THIS A MATCH? SETZM (T) SKIPE (T) ;A DEVICE HERE? TRO F,DF.SYS AOBJN T,NXTSSP DOASP: TRCN F,DF.SYS ;COMPLEMENT STATE FOR CORRECTNESS LATER ON SETZM SSP ;NO MORE POINTER NEEDED SKIPN T,ASP ;TRY FOR ALL: SEARCHLIST JRST DONDEV ;NONE, SO WE CAN GO THROUGH ALL ENTRIES NOW NXTASP: CAMN TT,(T) ;THIS A MATCH ON THE DEVICE? SETZM (T) SKIPE (T) ;A DEVICE LEFT HERE? TRO F,DF.ALL AOBJN T,NXTASP DONDEV: TRCN F,DF.ALL ;MAKE SENSE OF FLAG CORRECT SETZM ASP MOVE T,AOP ;POINTER TO ALL NAMELISTS NXTBLK:CAME TT,(T) ;IS THIS IDENTICAL DEVICE? TDNE F,3(T) ;OR IS IT SPECIAL DEVICE THAT IS FINISHED? SETZM (T) ;YES, REMOVE IT FROM FURTHUR USE AOBJN T,NXTBLK ;GO ON TILL ALL DONE POPJ P, ;THEN RETURN TO MAINLINE ;Handle multiple device pseudo-devices OPNPNT: SKIPL T,(TT) ;GET THE POINTER IF IT IS THERE JRST MULDON ;NONE THERE, WE ARE DONE WITH THIS DEVICE MULNXT: SKIPN TT,(T) ;GET DEVICE IF IT IS STILL THERE JRST MULBLK ;NOPE, BLANK DEVICE MOVEM T,MDP ;SAVE THE POINTER PUSH P,-1(P) ;PUT THE ROUTINE POINTER IN THE CORRECT SPOT PUSHJ P,OPNNXT ;THEN HANDLE THIS DEVICE SUB P,[1,,1] ;THROW AWAY THE SAVED POINTER MOVE T,MDP ;RESTORE THE POINTER INTO LIST OF DEVICES MULBLK: AOBJN T,MULNXT ;NEXT DEVICE IF ANY LEFT TO DO MULDON: POPJ P, ;RESTORE WHEN DONE SUBTTL Hack MFD routines ;HAKMFD: Routine to go through the MFD on the currently open device. ; HAKUFD is called for every valid entry in the MFD. HAKMFD: PUSH FXP,[1,,1] ;THE MFD IS [1,1] PUSH FXP,[SIXBIT/UFD/] ;IT IS REALLY A SPECIAL UFD PUSH FXP,[0] PUSH FXP,[1,,1] ;AND IT IS FOUND IN THE MFD PPN MOVE T,[LOOKUP -3(FXP)] ;THE LOOKUP UUO IOR T,1(R) ;PLACE IN THE CHANNEL NUMBER XCT T ;THEN GET THE MFD JRST MFDEOF ;WOW! IF NO MFD, THEN JUST SKIP DEVICE SUB FXP,[4,,4] ;LOOKUP BLOCK NO LONGER NEEDED SKIPE T,UFP ;SKIP IF NO UFD BLOCK YET JRST MFDUFD ;WE HAVE THE UFD BLOCK, SO WE ARE OK MOVEI T,(FXP) ;THIS WILL BE THE POINTER PUSH FXP,TT ;SAVE THE DEVICE NAME TO BE STANDARD PUSH FXP,T ;SAVE T OVER ALFILE PUSHJ P,ALFILE ;GET ANOTHER CHANNEL MOVE TT,RPT ;GET POINTER SKIPN 1(TT) ;DID WE USE THIS SLOT? EXCH A,1(TT) ;NOPE, SO USE IT NOW SKIPE A ;WAS THE OTHER SLOT OK? MOVEM A,2(TT) ;NOPE, SO USE THIS ONE LSH T,27 ;MOVE CHANNEL TO AC FIELD EXCH T,(FXP) ;THEN RESTORE T AND SAVE CHANNEL MOVEI TT,206 ;WE NOW NEED ROOM FOR BUFFERS PUSH FXP,TT ;MAKE ROOM ON STACK FXP SOJG TT,.-1 ;LOOP UNTIL WE HAVE ENOUGH MOVEM T,UFP ;ALSO REMEMBER POINTER FOR LATER USE MFDUFD: PUSH FXP,[14] ;MODE 14 FOR UFD PUSH FXP,(T) ;THE DEVICE TO OPEN MOVEI TT,3(T) ;THIS IS WHERE THE BUFFER HEADER IS PUSH FXP,TT ;PLACE THAT ON THE STACK MOVE T,[OPEN -2(FXP)] ;THE UUO TO GET THE DEVICE FOR UFD HACKING IOR TT,1(T) ;PLACE IN THE CORRECT CHANNEL NUMBER XCT TT ;THEN GET THE DEVICE ON THIS CHANNEL JRST MFDOPF ;OPEN FAILED, OH WELL SUB FXP,[3,,3] ;RID OURSELVES OF EXTRA STACK MOVEI TT,5(T) ;THIS IS WHERE WE WANT OUR BUFFER TO GO EXCH TT,.JBFF ;MAKE SURE THE MONITOR PUTS IT THERE PUSH FXP,TT ;SAVE THE OLD ONE AS WE WILL PUT IT BACK LATER MOVE TT,[INBUF 1] ;WE MUST FORCE ONE BUFFER IOR TT,1(T) ;MAKE A CORRECT UUO XCT TT ;GET THE BUFFERS POP FXP,.JBFF ;THEN RESTORE OLD .JBFF MFDNXT: SOSG 4(R) ;ANY DATA LEFT IN BUFFER? JSP T,MFDGET ;TRY TO GET MORE DATA ILDB TT,3(R) ;GET THE PPN NAME SOSG 4(R) ;ALSO NEEDED IS AN EXTENSION JSP T,MFDGET ;MUST BE IN THE NEXT BUFFER ILDB T,3(R) HLRZS T ;GET ONLY THE DATA CAIE T,(SIXBIT/UFD/) ;IS THIS A VALID ENTRY? JRST MFDNXT ;NOPE, SO GO TO NEXT ENTRY JUMPE TT,MFDNXT ;IS THERE ANYTHING TO CHECK? PUSH P,R ;SAVE R OVER UFD HACKING ROUTINE PUSHJ P,HAKUF1 ;CALL WITH UFD NAME IN TT POP P,R ;RESTORE POINTER JRST MFDNXT ;THEN PROCESS NEXT ENTRY MFDGET: MOVE F,[IN] ;WE NEED TO READ MORE DATA IOR F,1(R) ;ADD IN THE CHANNEL XCT F ;ASK THE MONITOR JRST (T) ;NO ERRORS, SO RETURN MOVE F,[RELEAS] ;WE MUST ASSUME EOF, SO BYE-BYE TO CHANNEL MOVE T,UFP ;NO MORE UFD HACKING CHANNEL, GET POINTER IOR F,1(T) ;USE THE CORRECT CHANNEL XCT F POPJ P, SUBTTL Hack ufd routines ;HAKUFD: ROUTINE TO GO THROUGH ALL FILES IN A UFD. UFD NAME IN 1(D) ;HAKUF1: ALTERNATE ENTRY, UFD IN TT HAKUFD: MOVE TT,1(D) ;STANDARDIZE PPN: INTO TT HAKUF1: PUSH FXP,T ;BUILD A LOOKUP BLOCK PUSH FXP,[SIXBIT/UFD/] PUSH FXP,[0] PUSH FXP,[1,,1] MOVE R,UFP ;POINTER TO UFD DATA BLOCK MOVE T,[LOOKUP -3(FXP)] ;WE WANT THIS UFD IOR T,1(R) ;ON THE CORRECT CHANNEL XCT T JRST UFDDON ;MAKE BELIEVE WE ARE DONE IF LOOKUP FAILS UFDNXT: SOSG 4(R) ;ANY BYTES LEFT? JSP A,UFDGET ;NOPE, GET MORE OF THEM ILDB T,3(R) ;GET THE FILENAME INTO T SOSG 4(R) ;NOW TRY FOR THE EXTENSION JSP A,UFDGET ;GET MORE DATA ILDB TT,3(R) ;EXTENSION INTO TT JUMPE T,UFDNXT ;IGNORE NULL ENTRIES HLLZS TT ;THROW AWAY MONITOR INTERNAL GARBAGE PUSHJ P,MATCH ;TRY TO MATCH THIS FILE ENTRY JRST UFDNXT ;THEN GO ON TO NEXT ONE IN UFD UFDGET: HRLZI TT,(IN) ;WE CAN ALWAYS USE TT HERE, GET THE INS IOR TT,1(R) ;PLACE IN THE CORRECT CHANNEL XCT TT ;DO THE I/O JRST (A) ;ALL IS WELL UFDDON: SUB FXP,[4,,4] ;GET RID OF THE LOOKUP BLOCK HRLZI TT,(CLOSE) ;WE MUST CLOSE THE CHANNEL IOR TT,1(R) ;THE CORRECT CHANNEL! XCT TT POPJ P, ;NOW RETURN TO MAINLINE SUBTTL File matching routines ;MATCH: Here to check a file to see if it matches any request block ; (R): Device ; -7(FXP): PPN ; T: Filename ; TT: Extension MATCH: PUSH P,R ;SAVE AS WE CANNOT DESTROY IT PUSH FXP,TT ;SAVE EXTENSION AS WE WILL NEED TT MOVE R,AOP ;THIS IS THE POINTER TO THE REQUEST BLOCKS MTCNXT: SKIPN (R) ;ANY ENTRY HERE? JRST MTCDON ;NOPE, SO DONE HRRZ F,FLG ;GET THE FLAGS INTO F TDNE F,3(R) ;ANY DEVICE SPECS IN COMMON? JRST MTCDEV ;YES, THEN THE DEVICES MATCH MOVE TT,@(P) ;GET THE DEVICE NAME WE WERE GIVEN CAME TT,(R) ;DOES THAT MATCH THE CURRENT ENTRY? JRST MTCDON ;NOPE, THEN THIS ENTRY CANNOT MATCH MTCDEV: SETZI F, ;CLEAR PPN MASK HLRE TT,1(R) ;GET THE PROJECT NUMBER OF THE ENTRY AOSN TT ;WILDCARD? HRROS F ;YES, FLAG AS SUCH HRRE TT,1(R) ;NOW CHECK THE PROGRAMMER NUMBER AOSN TT HLLOS F IOR F,-10(FXP) ;MAKE PPN TO CHECK AGAINST CAME F,1(R) ;THIS MUST MATCH TO BE A WIN JRST MTCDON HRLZI TT,(SIXBIT/*/) ;THIS IS THE WILDCARD CHECKER CAME TT,2(R) ;IS IT A WILDCARD? CAMN T,2(R) ;OR AN EXACT MATCH FOR THE FILENAME? SKIPA JRST MTCDON HLLZ F,3(R) ;GET ONLY THE EXTENSION FROM THE ENTRY CAME TT,T ;WILDCARD? CAMN F,(FXP) ;OR EXACT MATCH FOR THE EXTENSION SKIPA JRST MTCDON PUSH FXP,@(R) ;SAVE THE DEVICE PUSH FXP,-11(FXP) ;THE PPN PUSH FXP,T ;THE FILENAME PUSH FXP,-3(FXP) ;THEN FINALLY THE EXTENSION PUSHJ P,6BTNML ;THEN CONVERT TO A NAMELIST MOVE F,FLG ;GET THE FLAGS TLNE F,AF.ALL ;ANY PROPERTIES TO BE CONS'ED? PUSHJ P,DOFILE ;PROCESS THE LOOKUP BLOCK IF MORE INFO DESIRED POP FXP,TT ;RESTORE EXTENSION TO TT POP P,R ;RESTORE POINTER POPJ P, MTCDON: ADD R,[4,,4] ;BUMP POINTER TO NEXT ENTRY JUMPL R,MTCNXT ;GO ON IF ANY ENTRIES LEFT POP FXP,TT ;RESTORE THE EXTENSION POP P,R ;ELSE RESTORE THE OLD POINTER POPJ P, SUBTTL Property CONS'ing routines ;DOFILE: The main routine. Dispatches to appropriate other routines ; that actually do the work. Also LOOKUP's the file on the ; proper channel. DOFILE: MOVE R,ELP ;GET THE EXTENDED LOOKUP BLOCK POINTER SKIPE (R) ;HAS THIS CHANNEL BEEN ALLOCATED? JRST DOFIL1 ;YES, SO DON'T ALLOCATE IT AGAIN! PUSHJ P,ALFILE ;ALLOCATE A CHANNEL MOVEM F,1(R) ;STORE FOR LATER USE SETOM (R) ;FLAG THAT WE NOW OWN A CHANNEL MOVE F,RPT ;GET POINTER TO P STACK MOVEM A,3(F) ;MAKE IT SO GARBAGE COLLECTOR SAVES CHANNEL DOFIL1: PUSH FXP,[0] ;FOR THE OPEN BLOCK, MODE 0 PUSH FXP,@UFP ;SAVE THE DEVICE ALSO PUSH FXP,[0] ;NO BUFFERS NEEDED MOVE F,[OPEN -2(FXP)] ;OPEN UUO IOR F,1(R) ;NOW USE THE CORRECT CHANNEL XCT F JRST DOFOPF ;AWWW..... SUB FXP,[3,,3] ;NOW GET RID OF THE OPEN BLOCK MOVEI TT,ELL ;FIRST ARG FOR EXTENDED LOOKUP MOVEM TT,2(R) MOVEM T,3(R) ;PLANT THE FILENAME MOVE TT,(FXP) ;THE EXTENSION HLLZM TT,4(R) ;INTO THE CORRECT SPOT ] FASEND