Trailing-Edge
-
PDP-10 Archives
-
BB-D868C-BM
-
4-sources/checkd.mac
There are 35 other files named checkd.mac in the archive. Click here to see a list.
;<4.UTILITIES>CHECKD.MAC.30, 3-Jan-80 15:24:49, EDIT BY R.ACE
;UPDATE COPYRIGHT DATE
;<4.UTILITIES>CHECKD.MAC.29, 11-Oct-79 15:24:06, EDIT BY GRADY
;<4.UTILITIES>CHECKD.MAC.28, 11-Oct-79 14:57:55, EDIT BY GRADY
;TCO 4.2496 - DELETE ALL GENERATIONS OF THE LOST PAGES FILE IN RLSPG2
;<4.UTILITIES>CHECKD.MAC.27, 8-Aug-79 11:33:07, EDIT BY GRANT
;TCO 4.2379 - CHANGE LF TO CRLF TO CLEAN UP SOME OUTPUT FORMATS
;<4.UTILITIES>CHECKD.MAC.26, 17-Apr-79 16:28:55, EDIT BY DBELL
;TCO 4.2232 - AT NXTPR ROUND DOWN BAT BLOCK ENTRIES TO PAGE BOUNDARIES
; SO THAT 3/4 OF THE PAGES WITH A BAD SECTOR WILL NOT BE MISSED.
;<4.UTILITIES>CHECKD.MAC.25, 10-Mar-79 13:39:25, EDIT BY KONEN
;UPDATE COPYRIGHT FOR RELEASE 4
;<4.UTILITIES>CHECKD.MAC.24, 8-Mar-79 13:25:35, EDIT BY R.ACE
;TAKE OUT TAPE-INIT FUNCTIONS
;<4.UTILITIES>CHECKD.MAC.23, 19-Feb-79 11:54:59, Edit by KONEN
;INCREMENT MOUNT COUNT AFTER MOUNTING A STRUCTURE
;<4.UTILITIES>CHECKD.MAC.22, 12-Feb-79 13:12:50, EDIT BY R.ACE
;CHANGE CKMNT TO ACCOMMODATE NEW GALAXY TEXT MESSAGE FORMAT
;<4.UTILITIES>CHECKD.MAC.21, 10-Jan-79 10:32:00, EDIT BY R.ACE
;RELEASE PID IN QUIT CODE
;<4.UTILITIES>CHECKD.MAC.20, 12-Dec-78 10:48:23, EDIT BY DBELL
;TCO 4.2119 - FIX BUG IN RELEASING MORE THAN 12K LOST PAGES
;<4.UTILITIES>CHECKD.MAC.19, 8-Dec-78 14:39:41, EDIT BY DBELL
;TCO 4.2115 - MOVE LOCATION HFLAGS TO PREVENT BAT LOGIC ERRORS
;<4.UTILITIES>CHECKD.MAC.18, 8-Dec-78 11:10:21, EDIT BY DBELL
;TCO 4.2114 - FIX BAT LOGIC AT NXTPR TO USE FULL 27 BIT ADDRESSES
;<4.UTILITIES>CHECKD.MAC.17, 27-Nov-78 10:31:31, Edit by LCAMPBELL
; Add QUIT as a synonym for EXIT
;<4.UTILITIES>CHECKD.MAC.16, 12-Nov-78 13:53:58, EDIT BY R.ACE
;CHANGE VOLID PARSING TO USE ^V INSTEAD OF QUOTED STRINGS
;<4.UTILITIES>CHECKD.MAC.15, 6-Nov-78 07:47:29, EDIT BY R.ACE
;TCO 4.2079 - ADD TAPE-INITIALIZATION FUNCTIONS
;PERFORM GENERAL CLEAN-UP
;<4.UTILITIES>CHECKD.MAC.14, 31-Aug-78 17:16:39, Edit by MCLEAN
;MAKE CYLUN2 HAVE 558 CYLINDERS PER UNIT FOR DIAGNOSTICS
;<4.UTILITIES>CHECKD.MAC.13, 24-Jul-78 07:38:08, EDIT BY MILLER
;CHANGE DEFINITION OF DSKMSK TO INCLUDE DSKNB
;<4.UTILITIES>CHECKD.MAC.12, 19-Jun-78 13:27:15, Edit by MCLEAN
;<1MCLEAN>CHECKD.MAC.6, 6-May-78 23:39:32, Edit by MCLEAN
;ADD RP07
;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 BY DIGITAL EQUIPMENT CORPORATION, MAYNARD, MASS.
TITLE CHECKD CHECK/RECONSTRUCT CONSISTENCY OF FILE STRUCTURE
.REQUIRE SYS:MACREL
SEARCH MONSYM,MACSYM
EXTERN .JBSA ;LH/ FIRST FREE LOC IN CHECKD
SALL
.DIRECTIVE FLBLST ;SUPPRESS LENGTHY OCTAL MACHINE CODE
;ENTRY VECTOR
PRGCST==0 ;CUSTOMER ID
PRGVER==4 ;VERSION NUMBER
PRGMIN==0 ;MINOR VERSION
PRGEDT==30 ;EDIT NUMBER
ENTVEC: JRST START ;MAIN START
JRST START ;REENTER
BYTE (3)PRGCST (9)PRGVER (6)PRGMIN (18)PRGEDT
JRST REBST ;REBUILD THE BIT TABLE
;CHECKD OPERATES ACCORDING TO HOW IT WAS CALLED:
;
;1. CALLED BY MONITOR JOB 0 (AT SYSTEM STARTUP - MEXEC MODULE)
; ENTRY VECTOR LOCATION 0 - CHECK PS: FILE CONSISTENCY
; ENTRY VECTOR LOCATION 3 - INITIALIZE PS: BITTABLE
;
;2. RUN BY ENABLED WHEEL OR OPERATOR
; ENTRY VECTOR LOCATIONS 0 AND 1 - ACCEPT COMMANDS FROM TTY
; AC'S
F=0
T1=1
T2=2
T3=3
T4=4
Q1=5
Q2=6
Q3=7
P1=10
P2=11
P3=12
CX=16
P=17
;MISCELLANEOUS DEFINITIONS
NWSEC==200 ;WORDS/SECTOR ON THE DISK
PGSIZ==1000 ;PAGE SIZE
PGSFT==11 ;SHIFT FOR CONVERTING ADDRESS TO PAGE
;SIZE OF BIT TABLE FILE IF WRITTEN BY PRE-RELEASE-2 MONITOR
OLDTOP=3100 ;SIZE OF TOP HALF OF BIT TABLE
OLDBOT=11300 ;SIZE OF BOTTOM HALF OF BIT TABLE
DEFP4S==^D3050 ;DEFAULT PAGES FOR SWAPPING
DEFPFS==^D950 ;DEFAULT PAGES FOR FRONT END
;INFORMATION ABOUT THE STRUCTURE BEING WORKED ON
BTBTOP: BLOCK 1 ;SIZE OF TOP HALF OF BIT TABLE
BTBBOT: BLOCK 1 ;SIZE OF BOTTOM HALF OF BIT TABLE
BTBPGS: BLOCK 1 ;NUMBER OF PAGES IN BIT TABLE
NSSUN: BLOCK 1 ;NUMBER OF SECTORS IN SWAPPING SPACE
FSSUN: BLOCK 1 ;FIRST SECTOR IN SWAPPING SPACE
NPACKS: BLOCK 1 ;NUMBER OF PACKS IN STRUCTURE
HITRK: BLOCK 1 ;LAST CYLINDER IN STRUCTURE
LOTRK: BLOCK 1 ;FIRST CYLINDER IN STRUCTURE
;INFORMATION ABOUT THE SIZE OF THE STRUCTURE BASED ON THE TYPE OF DISK
;THIS BLOCK IS FILLED IN BY A BLT FROM OTHER TABLES, SO DO NOT CHANGE
;THE ORDER OF THESE WORDS.
SECPAG: BLOCK 1 ;SECTORS PER PAGE
SECCYL: BLOCK 1 ;SECTORS PER CYLINDER
PAGCYL: BLOCK 1 ;PAGES PER CYLINDER
CYLUNT: BLOCK 1 ;CYLINDERS PER UNIT
SECUNT: BLOCK 1 ;SECTORS PER UNIT
BTWCYL: BLOCK 1 ;BIT WORDS IN BIT TABLE PER CYLINDER
MINFRE: BLOCK 1 ;MINIMUM FREE PAGES FOR FREE CHOICE
LPPCYL: BLOCK 1 ;LOST SECTORS PER CYL
;HOME BLOCKS. EACH NUMBER IS A SECTOR NUMBER RELATIVE TO THE START
;OF A UNIT. EVERY UNIT IN A STRUCTURE HAS THESE BLOCKS ASSIGNED.
;COPIED FROM <2-MONITOR>STG.MAC 6/23/76
HOME:: 0 ;BOOT STRAP FOR THE 11
1 ;HOME BLOCK
2 ;BAT BLOCK
3 ;RESERVED
4 ;RESERVED
5 ;RESERVED
6 ;RESERVED
7 ;RESERVED
10 ;RESERVED
11 ;RESERVED
12 ;SECONDARY HOME BLOCK
13 ;SECONDARY BAT BLOCK
NHOME==:.-HOME
;ERROR BITS RETURNED FROM DSKASA
ER%IDA==1B0 ;ILLEGAL DISK ADDRESS
ER%MDA==1B1 ;MULTIPLY ASSIGNED DISK ADDRESS
ER%BAT==1B2 ;BAD ADDRESS MARKED IN BAT BLOCKS
;FLAG BITS FOR MRKBTB TO KNOW WHAT KIND OF ADDRESS IT HAS
MR%PT==1B0 ;PAGE TABLE
MR%PTT==1B1 ;PAGE TABLE TABLE
MR%SWP==1B2 ;SWAPPING SPACE
MR%SPC==1B3 ;HOME BLOCKS, BAT BLOCKS, ETC.
;MISCELLANEOUS BITS
FILNB==1B3 ;NEW FILE BIT
DSKMSK==-1B15 ;MASK TO SELECT ONLY DISK ADDRESS FIELD
ADRMSK==-1B13 ;MASK FOR COMPLETE STORAGE ADDRESS
;BAT BLOCK DEFINITIONS
;THE BAT BLOCK IS ONE SECTOR IN LENGTH. IT CONSISTS OF 4 WORDS OF
;HEADER, FOLLOWED BY DATA, TWO WORDS PER ENTRY, INDICATING WHERE THE
;BAD SPOTS ON THE DISK ARE. WORD ^D126 CONTAINS A SPECIAL CODE, AND
;WORD ^D127 CONTAINS THE SECTOR NUMBER OF THE BAT BLOCK
MAXBFR==172 ;MAX FREE SPACE IN A BAT BLOCK
MAXPAR==MAXBFR/2 ;MAX PAIRS IN A BAT BLOCK
MNPAKS==4 ;MAXIMUM NO. OF PACKS IN A STRUCTURE
MAXPR==MAXBFR*MNPAKS ;SIZE OF BAT PAIR ARRAY
BPRBLK: BLOCK MAXPR ;BAT PAIRS
BATBUF: BLOCK 200 ;BUFFER FOR BAT BLOCK
BATBL1==2 ;SECTOR NO. OF FIRST BAT BLOCK
;HEADER
BATNAM==0 ;OFFSET OF SIXBIT /BAT/
BATFRE==1 ;WORD WITH FREE BLOCKS LEFT
DEFSTR BATFR,BATFRE,17,18 ;FIELD WITH FREE COUNT
DEFSTR BTFR2,BATFRE+HBLEN,17,18 ;IN THE SECONDARY BLOCK
DEFSTR BTHCT,2,17,9 ;NUMBER OF PAIRS ADDED BY MAPPER
DEFSTR BTMCT,3,35,36 ;COUNT OF PAIRS ADDED BY MONITOR
DEFSTR BTMC2,HBLEN+3,35,36 ;IN SECONDARY BLOCK
;DATA PAIRS
DEFSTR BATNB,0,8,9 ;COUNT OF BAD BLOCKS IN PAIR
PUBCNT==22 ;RIGHT-MOST BIT OF UNARY UNIT FIELD
DEFSTR BTKNM,0,20,3 ;MASSBUS CONTROLLER #
DEFSTR BADT,0,21,1 ;TYPE FIELD IN BAT PAIR
DEFSTR APRNM,0,35,13 ;APR SERIAL NUMBER FIELD
DEFSTR ADD18,1,35,18 ;OLD STYLE DISK ADDRESS OF STARTING SECTOR
DEFSTR ADD27,1,35,27 ;NEW STYLE ADDRESS OF STARTING SECTOR
;SPECIAL WORDS AT END OF BAT BLOCK
BATCOD==^D126 ;OFFSET FOR UNLIKELY CODE 606060
CODE=606060 ;THE CODE
BATBLK==^D127 ;OFFSET FOR SECTOR NUMBER
;LOCATIONS WHERE THINGS ARE MAPPED
FSTPAG==24000 ;FIRST PAGE USED FOR STORAGE
HBUF=FSTPAG ;HELP BUFFER
NHBUFP==2 ;LENGTH OF HELP BUFFER
PT=HBUF+<NHBUFP*1000> ;WHERE TO MAP THE PAGE TABLE
PTT=PT+1000 ;WHERE TO MAP THE PAGE TABLE TABLE
LOSBUF=PTT+1000 ;WHERE TO SAVE LOST PAGES
MAXLOS==40000 ;NUMBER OF LOST PAGES THAT CAN BE ACCOUNTED
SYSBTB=LOSBUF+MAXLOS ;PLACE TO MAP THE BIT TABLE
BTBMAX==50000 ;MAX SIZE OF THE BIT TABLE
LOCBTB=SYSBTB+BTBMAX ;LOCAL COPY OF THE BIT TABLE
IDXORA=LOCBTB+BTBMAX ;START OF LOCAL COPY OF IDXFIL
NIDXPG==60
DIRORG=IDXORA+<NIDXPG*1000> ;START OF MAP AREA FOR DIRECTORY
NDIRPG==500 ;MAX SIZE OF DIR IN PAGES
LSTPPG==DIRORG+<NDIRPG*1000> ;END OF PAGE AREA
IF2,<IFL <770000-LSTPPG>,<PRINTX MAPPED PAGE AREA OVERLAPS DDT AREA>>
;JFN'S
BTBJFN: BLOCK 1 ;JFN FOR BIT TABLE FILE
INJFN: BLOCK 1 ;JFN FOR INPUT FILE FOR RELEASE COMMAND
OUTJFN: BLOCK 1 ;JFN FOR OUTPUT FILE FOR LOST-PAGES.BIN
DAJFN: BLOCK 1 ;JFN OF FILE BEING READ BY SCAN COMMAND
FDJFN: BLOCK 1 ;JFN OF DIRECTORY BEING CHECKED
;FLAGS - SET ACCORDING TO COMMAND TYPED
REBLDF: BLOCK 1 ;REBUILD BITTAB IF NON-0
CHKFLF: BLOCK 1 ;CHECK FILES IF NON-0, ELSE DIRECTORIES ONLY
;COUNTS OF ERRORS FOUND BY BUILD
;ZSTART THRU ZEND ARE ZEROED BY BUILD
ZSTART:
NBAD: BLOCK 1 ;ALL ERRORS
NDE: BLOCK 1 ;BAD PAGE TABLE ADDRESSES IN FDB'S
NPTTE: BLOCK 1 ;BAD PAGE TABLE TABLE ADDRESSES IN FDB'S
NBPT: BLOCK 1 ;FAILURES TO READ PAGE TABLES
NBPTT: BLOCK 1 ;FAILURES TO READ PAGE TABLE TABLES
NBPTE: BLOCK 1 ;BAD ADDRESSES IN PAGE TABLES
NBPTTE: BLOCK 1 ;BAD ADDRESSES IN PAGE TABLE TABLES
NIDA: BLOCK 1 ;ILLEGAL ADDRESSES
NMDA: BLOCK 1 ;MULTIPLY ASSIGNED ADDRESSES
NSDA: BLOCK 1 ;SEARCHED-FOR ADDRESSES FOUND
NDSKER: BLOCK 1 ;DISK READ ERRORS
NNBT: BLOCK 1 ;ADDRESSES NOT IN BIT TABLE
; (BELONGING TO A FILE, BUT NOT ASSIGNED)
NABAT: BLOCK 1 ;ASSIGNED PAGES THAT ARE MARKED AS BAD
ZEND=.-1
;MISCELLANEOUS STORAGE
DIRORA: DIRORG ;POINTER TO BASE OF MAPPED DIR
SVEND: BLOCK 1 ;END OF BAT PAIR
HFLAGS: BLOCK 1 ;FLAGS FROM HOME BLOCK
LOSTOT: BLOCK 1 ;NUMBER LOST PAGES
NLINB==^D80/5 ;SIZE OF INPUT LINE BUFFER
LINBUF: BLOCK NLINB
PAGNN: BLOCK 1 ;CURRENT OFFSET IN INDEX BLOCK (PAGE NO. IN FILE)
DALIST: BLOCK 1 ;AOBJN POINTER TO DATAB
DASIZ==2000
TMPBUF: ;TEMPORARY STRING BUFFER
DATAB: BLOCK DASIZ ;LIST OF DISK ADDRESSES BEING LOOKED FOR VIA SCAN COMMAND
PDLEN==100
PDL: BLOCK PDLEN ;STACK
DIRNAM: BLOCK 21 ;NAME OF CURRENT DIRECTORY
DIRNUM: BLOCK 1 ;NUMBER OF CURRENT DIRECTORY
STRNAM: BLOCK 10 ;STRUCTURE NAME STRING
STRHOM: BLOCK 10 ;STR NAME ACTUALLY IN HOME BLOCK
JOBNO: BLOCK 1 ;NUMBER OF THIS JOB
ZUSED: BLOCK 1 ;NO. PAGES USED BEFORE CHECKD RAN
WRTLPF: BLOCK 1 ;WRITE LOST-PAGES.BIN IF .NE. 0
LPFHED: BLOCK 5 ;HEADER ON LOST-PAGES FILE
SYMTOP: BLOCK 1 ;ADDRESS OF END OF SYMBOL TABLE
STRDEV: BLOCK 1 ;CURRENT STR (DEVICE DESIGNATOR)
OVERHD: BLOCK 1 ;COUNT OF USED PAGES NOT ASSIGNED TO FILES
BATCNT: BLOCK 1 ;COUNT OF BAD PAGES (DECREMENTED WHEN
; THE PAGE IS USED BY A FILE)
PAGCNT: BLOCK 1 ;COUNT OF FILE PAGES FOR THE CURRENT FILE
TOTPGS: BLOCK 1 ;TOTAL FILE PAGES IN USE
NAMBUF: BLOCK 10 ;BUFFER FOR STR NAME STRINGS
IDZB:! ;BEGIN OF ID ZERO AREA
UNITID: BLOCK 4 ;UNIT ID BUFFER
OWNRID: BLOCK 4 ;OWNER ID BUFFER
IDZZ==.-1 ;END OF ID ZERO AREA
NPG4SW: BLOCK 1 ;NUMBER OF PAGES FOR SWAPPING
NPGFES: BLOCK 1 ;NUMBER OF PAGES FOR FRONT-END
MNTBLK: BLOCK 50 ;STORAGE FOR MOUNTING STRS
HOMARG: BLOCK 4 ;ARG BLOCK FOR MODIFYING HOME BLOCK
RNUBLK: BLOCK .MSRLN ;BLOCK FOR .MSRNU FCN
STRMNT: BLOCK 1 ;DEVICE DESIGNATOR OF MOUNTED STR.
FCNBLK: BLOCK 4 ;FUNCTION BLOCK FOR COMND
SAVREP: BLOCK 1 ;REPARSE PDL POINTER
SAVRET: BLOCK 1 ;REPARSE RETURN ADDRS
OKFLG: BLOCK 1 ;FLAG FOR FNDSTR
PSFLG: BLOCK 1 ;-1 IF THIS IS REALLY PS:
;THE FOLLOWING LOCATIONS ARE USED IN DIRECTORY SCANNING (GTFILE) TO CONVERT
;DIRECTORY NUMBER TO FILE NAME
ROOTDR: BLOCK 20 ;PLACE FOR STR:<ROOT-DIRECTORY>
ROOTPT: BLOCK 1 ;POINTER TO END OF ABOVE STRING
FILNAM: BLOCK 25 ;PLACE FOR STR:<DIRECTORY>SUBDIR.DIRECTORY
DOTPTR: BLOCK 1 ;POINTER TO LAST DOT
BRKPTR: BLOCK 1 ;POINTER TO LEFT BRACKET
;OVERHEAD IS ALL PAGES USED AS FOLLOWS:
; HOME BLOCKS
; SWAPPING SPACE
; PAGE TABLE TABLE
; PAGE TABLE
; MARKED AS BAD AND NOT USED BY ANY OF THE ABOVE OR AS A FILE PAGE
;PAGNN SERVES AS A COUNTER INTO A FILE. IT IS USED IN MRKBTB TO
;TELL WHAT PAGE AN ERROR IS IN.
;IF THE FILE IS LONG, THE PAGE NUMBER IS INCREMENTED ONCE FOR EVERY
;ENTRY IN A PAGE TABLE AND 1000 FOR EVERY ENTRY IN THE PAGE TABLE TABLE
;THAT IS ZERO. THUS WITH A SPARSE FILE, PAGNN HAS THE SAME VALUE AS IF
;IT WERE NOT SPARSE. PAGNN IS -1 WHEN MRKBTB IS CALLED FOR ANY OTHER
;PAGE (PAGE TABLE, SWAPPING SPACE)
;VALUES FOR FILE CURRENTLY BEING SCANNED
;KEEP THESE IN ORDER
DEFVER: BLOCK 1 ;VERSION
DEFNAM: BLOCK 1 ;NAME
DEFEXT: BLOCK 1 ;EXTENSION
BLOCK 4
;INTERRUPT LOCATIONS
;PC'S SAVED HERE
RET1: BLOCK 1
RET2: BLOCK 1
RET3: BLOCK 1
; [LOCATION WHERE PC STORED BY LEVEL]
LEVTAB: RET1
RET2
RET3
; [LEVEL,,INTERRUPT ADDRESS]
CHNTAB: XWD 2,BADINT ;UNKNOWN CHANNEL
XWD 1,CONTC ;^C
XWD 3,SUMINT ;^A
XX==3
REPEAT ^D36-3,<2,,DSPINT+XX
XX=XX+1>
; * * * *
;THIS PAGE REFLECTS SPECIFIC KNOWLEDGE OF THE TYPES OF DISKS THAT ARE
;SUPPORTED. IT, AND THE ASSOCIATED HOME BLOCK CODE, SHOULD BE REPLACED
;BY AN MSTR THAT OBTAINS THE SAME DATA FOR THE SPECIFIC DRIVE.
; * * * *
;DATA FOR RP04 AND RP05
SECPG0==PGSIZ/NWSEC ;SECTORS PER PAGE
SECCY0==^D19*^D20 ;SECTORS PER CYLINDER
LPPCT0==0 ;LOST SECTORS PER CYL
PAGCY0==SECCY0/SECPG0 ;PAGES PER CYLINDER
CYLUN0==^D400 ;CYLINDERS PER UNIT
SECUN0==SECCY0*CYLUN0 ;SECTORS PER UNIT
BTWCY0==<PAGCY0+^D35>/^D36 ;NUMBER BIT WORDS IN BIT TABLE FOR A CYLINDER
MINFP0==PAGCY0/3 ;MINIMUM FREE PAGES FOR FREE CHOICE ALLOCATION
; IN DSKASN
;DATA FOR RP06
SECPG1==PGSIZ/NWSEC ;SECTORS PER PAGE
SECCY1==^D19*^D20 ;SECTORS PER CYLINDER
LPPCT1==0 ;LOST SECTORS PER CYL
PAGCY1==SECCY1/SECPG1 ;PAGES PER CYLINDER
CYLUN1==^D800 ;CYLINDERS PER UNIT
SECUN1==SECCY1*CYLUN1 ;SECTORS PER UNIT
BTWCY1==<PAGCY1+^D35>/^D36 ;NUMBER OF BIT WORDS PER CYLINDER IN BIT TABLE
MINFP1==PAGCY1/3 ;MINIMUM FREE PAGES FOR FREE CHOICE ALLOCATION
; IN DSKASN
;DATA FOR RM03
SECPG3==PGSIZ/NWSEC ;SECTORS PER PAGE
LPPCT3==2 ;LOST SECTORS PER CYL
SECCY3==<^D5*^D30>-LPPCT3 ;SECTORS PER CYLINDER
PAGCY3==SECCY3/SECPG3 ;PAGES PER CYLINDER
CYLUN3==^D820 ;CYLINDERS PER UNIT
SECUN3==SECCY3*CYLUN3 ;SECTORS PER UNIT
BTWCY3==<PAGCY3+^D35>/^D36 ;NUMBER OF BIT WORDS PER CYLINDER IN BITTABLE
MINFP3==PAGCY3/3 ;MINIMUM FREE PAGES FOR FREE CHOICE ALLOCATION
;DATA FOR RP07
SECPG2==PGSIZ/NWSEC ;SECTORS PER PAGE
LPPCT2==0 ;LOST SECTORS PER CYL
SECCY2==<^D30*^D30>-LPPCT2 ;SECTORS PER CYLINDER
PAGCY2==SECCY2/SECPG2 ;PAGES PER CYLINDER
CYLUN2==^D558 ;CYLINDERS PER UNIT
SECUN2==SECCY2*CYLUN2 ;SECTORS PER UNIT
BTWCY2==<PAGCY2+^D35>/^D36 ;NUMBER OF BIT WORDS PER CYLINDER IN BITTABLE
MINFP2==PAGCY2/3 ;MINIMUM FREE PAGES FOR FREE CHOICE ALLOCATION
;RP04 AND RP05
DSKSZ0::SECPG0 ;SECTORS PER PAGE
SECCY0 ;SECTORS PER CYLINDER
PAGCY0 ;PAGES PER CYLINDER
CYLUN0 ;CYLINDERS PER UNIT
SECUN0 ;SECTORS PER UNIT
BTWCY0 ;BIT WORDS IN BIT TABLE PER CYLINDER
MINFP0 ;MINIMUM FREE PAGES FOR FREE CHOICE ALLOCATION
LPPCT0 ;LOST SECTORS PER CYL
; IN DSKASN
;RP06
DSKSZ1::SECPG1 ;SECTORS PER PAGE
SECCY1 ;SECTORS PER CYLINDER
PAGCY1 ;PAGES PER CYLINDER
CYLUN1 ;CYLINDERS PER UNIT
SECUN1 ;SECTORS PER UNIT
BTWCY1 ;BIT WORDS IN BIT TABLE PER CYLINDER
MINFP1 ;MINIMUM FREE PAGES FOR FREE CHOICE ALLOCATION
LPPCT1 ;LOST SECTORS PER CYL
;RP07
DSKSZ2::SECPG2 ;SECTORS PER PAGE
SECCY2 ;SECTORS PER CYLINDER
PAGCY2 ;PAGES PER CYLINDER
CYLUN2 ;CYLINDERS PER UNIT
SECUN2 ;SECTORS PER UNIT
BTWCY2 ;BIT WORDS IN BIT TABLE PER CYLINDER
MINFP2 ;MINIMUM FREE PAGES FOR FREE CHOICE ALLOCATION
LPPCT2 ;LOST SECTORS PER CYL
;RM03
DSKSZ3::SECPG3 ;SECTORS PER PAGE
SECCY3 ;SECTORS PER CYLINDER
PAGCY3 ;PAGES PER CYLINDER
CYLUN3 ;CYLINDERS PER UNIT
SECUN3 ;SECTORS PER UNIT
BTWCY3 ;BIT WORDS IN BITTABLE
MINFP3 ;MINIMUM FREE PAGES FOR FREE CHOICE ALLOCATION
LPPCT3 ;LOST SECTORS PER CYL
; IN DSKASN
DEFINE SAVEQ<
JSP CX,SAVQ>
SAVQ:: PUSH P,Q1 ;SAVE Q1-Q3
PUSH P,Q2
PUSH P,Q3
PUSHJ P,0(CX) ;CONTINUE ROUTINE, EXIT VIA .+1
RESTQ:: SKIPA ;NON-SKIP RETURN
AOS -3(P) ;SKIP RETURN
POP P,Q3
POP P,Q2
POP P,Q1
RET
DEFINE SAVET<
JSP CX,SAVT>
SAVT:: PUSH P,T1 ;SAVE T1-T4
PUSH P,T2
PUSH P,T3
PUSH P,T4
PUSHJ P,0(CX) ;CONTINUE ROUTINE, RETURN VIA .+1
RESTT: SKIPA ;NO-SKIP RETURN
AOS -4(P) ;PASS ALONG SKIP RETURN
POP P,T4
POP P,T3
POP P,T2
POP P,T1
RET
;MACRO TO PRINT AN ERROR MESSAGE AND TRANSFER. IF THE MSG FIELD IS
;SPECIFIED, IT IS PRINTED. IF FILFLG IS NON-BLANK, THE FILE SPEC POINTED
;TO BY DIRNAM, DEFNAM, ETC., IF PRINTED AT THE END OF THE MESSAGE.
;A JSERR IS DONE TO GET THE LAST ERROR. IF AN ADDRESS IS SPECIFIED, A
;JRST TO IT IS GENERERATED. NOTE THAT THIS CODE IS NOT SKIPPABLE.
DEFINE PNTERR (MSG,ADDR,FILFLG)<
IFNB <MSG>,<
HRROI T1,[ASCIZ/
? CHECKD: MSG /]
PSOUT ;PRINT THE MESSAGE IF ANY
IFNB <FILFLG>,<CALL PNTFIL>> ;PRINT THE FILE NAME IF REQUESTED
JSERR ;DO STANDARD JSYS ERROR PRINTING
IFNB <ADDR>,<JRST ADDR> ;JRST TO SPECIFIED ADDRESS IF ANY
>
DEFINE RETERR (MSG)<
JRST [ TMSG <
? CHECKD: MSG
>
RET]
>
;ERROR - MACRO TO PRINT ERROR AND GO TO SPECIFIED LOCATION
;USED IN PARSING CODE WHEN COMND RETURNS CM%NOP
DEFINE ERROR (ADDR,MSG)<
JRST [ HRROI T1,[ASCIZ/ MSG/]
CALL ERRDRV ;;CALL DRIVER ROUTINE
JRST ADDR]>
;BITS+N CONTAINS A WORD WITH A 1 IN BIT N
XX==0
BITS:: REPEAT ^D36,<EXP 1B<XX>
XX=XX+1>
;DIRECTORY RELATED DEFSTR'S
;COPIED FROM PROLOG.MAC
;DIRECTORY HEADER (FOR PAGE 0; FIRST 3 WORDS ARE REPEATED ON
;SUBSEQUENT PAGES)
DEFSTR DRTYP,0,17,18 ;BLOCK TYPE OF DIRECTORY (.TYDIR)
DEFSTR DRVER,0,23,6 ;VERSION # OF DIRECTORY
DEFSTR DRHLN,0,35,12 ;LENGTH OF HEADER AREA
DEFSTR DRRPN,1,17,18 ;RELATIVE PAGE # WITHIN DIRECTORY
DEFSTR DRNUM,1,35,18 ;DIRECTORY NUMBER
DEFSTR DRFFB,.DRFFB,35,36 ;FIRST FREE BLOCK ON THIS PAGE
DEFSTR DRSBT,3,35,36 ;ADDRESS OF BOTTOM OF SYMBOL TABLE
DEFSTR DRSTP,4,35,36 ;ADDRESS OF TOP OF SYMBOL TABLE
DEFSTR DRFTP,5,35,36 ;ADDRESS OF LAST USED WORD + 1
DEFSTR DRFBT,6,35,36 ;POINTER TO FREE POOL BIT TABLE
DEFSTR DRDPW,7,35,36 ;DEFAULT FILE PROTECTION
DEFSTR DRPRT,10,35,36 ;DEFAULT DIRECTORY PROTECTION
DEFSTR DRPOW,10,23,6 ;OWNER FIELD
DEFSTR DRPGP,10,29,6 ;GROUP FIELD
DEFSTR DRPWL,10,35,6 ;WORLD FIELD
DEFSTR DRDBK,11,35,36 ;BACKUP SPECIFICATION
DEFSTR DRLIQ,12,35,36 ;LOGIN DISK QUOTA
DEFSTR DRLOQ,13,35,36 ;LOGGED OUT QUOTA
DEFSTR DRDCA,14,35,36 ;CURRENT DIR ALLOCATION
DEFSTR DRNAM,15,35,36 ;POINTER TO NAME STRING
DEFSTR DRPSW,16,35,36 ;POINTER TO PASSWORD STRING
DEFSTR DRPRV,17,35,36 ;PRIVILEGE BITS
DEFSTR DRMOD,20,35,36 ;MODE BITS
DEFSTR DRDAT,21,35,36 ;TIME AND DATE OF LAST LOGIN
DEFSTR DRUGP,22,35,36 ;USER GROUPS
DEFSTR DRDGP,23,35,36 ;DIRECTORY GROUPS
DEFSTR DRUDT,24,35,36 ;LAST UPDATE TIME OF DIR
DEFSTR DRSDC,25,35,18 ;COUNT OF SUBDIRECTORIES
DEFSTR DRSDM,25,17,18 ;MAXIMUM NUMBER OF SUBDIRECTORIES
DEFSTR DRCUG,26,35,36 ;CRDIR ALLOWED SPECIFYING THESE USER GRPS
.DIHL0==:100 ;LENGTH OF DIR PAGE 0 HEADER (+ SPARES)
.DIHL1==:3 ;LENGTH OF HEADER FOR DIR PAGES 1 & UP
.DRFFB==:2 ;OFFSET OF FIRST FREE BLOCK POINTER
;GENERAL FORMAT FOR ALL BLOCKS
DEFSTR BLKTYP,0,17,18 ;TYPE CODE FOR STANDARD FORMAT BLOCKS
;NMTYP, EXTYP, ACTYP, SYMTY, DRTYP,
;UNTYP, FBTYP, AND FRTYP
DEFSTR BLKVER,0,23,6 ;VERSION NUMBER OF BLOCK
DEFSTR BLKLEN,0,35,12 ;LENGTH OF STANDARD FORMAT BLOCK
;SYMBOL TABLE
; SYMBOL TABLE HEADER
DEFSTR SYMTY,0,17,18 ;SYMBOL TABLE TYPE CODE (.TYSYM)
DEFSTR SYMDN,0,35,18 ;DIR NUMBER OF SYMBOL TABLE
; SYMBOL TABLE ENTRIES
SY%ET==:7B2 ;SYMBOL TABLE ENTRY TYPE MASK
.SYMAD==:0 ;POSITION OF ADDRESSES IN SYMBOL TABLE
.SYMVL==:1 ;POSITION OF SYMBOL HASH VALUE WORD
.SYMLN==:2 ;# OF WORDS IN A SYMBOL TABLE ENTRY
DEFSTR SYMET,.SYMAD,2,3 ;SYMBOL TABLE ENTRY TYPE
DEFSTR SYMAD,.SYMAD,35,33 ;ADDRESS OF BLOCK IN DIR FOR THIS SYM
DEFSTR SYMVL,.SYMVL,35,36 ;FIRST 5 CHARACTERS OF NAME OR ACCOUNT
.ETNAM==:0 ;ENTRY TYPE OF NAME
.ETUNS==:2 ;ENTRY TYPE OF USER NAME
.ETACT==:4 ;ENTRY TYPE OF ACCOUNT
;NAME BLOCK
DEFSTR NMTYP,0,17,18 ;NAME BLOCK TYPE CODE (.TYNAM)
DEFSTR NMLEN,0,35,12 ;LENGTH OF NAME BLOCK
DEFSTR NMVAL,1,35,36 ;FIRST 5 CHARACTERS OF NAME STRING
;EXTENSION BLOCK
DEFSTR EXTYP,0,17,18 ;EXTENSION BLOCK TYPE CODE (.TYEXT)
DEFSTR EXLEN,0,35,12 ;LENGTH OF EXTENSION BLOCK
;ACCOUNT STRING BLOCK
DEFSTR ACTYP,0,17,18 ;ACCOUNT STRING BLOCK TYPE CODE (.TYACT)
DEFSTR ACLEN,0,35,12 ;LENGTH OF ACCOUNT BLOCK
DEFSTR ACSHR,1,35,36 ;SHARE COUNT OF ACCOUNT STRING
.ACVAL==2 ;START OF ACCOUNT STRING
DEFSTR ACVAL,.ACVAL,35,36 ;FIRST 5 CHARACTERS OF ACCOUNT STRING
;USER NAME STRING BLOCK
DEFSTR UNTYP,0,17,18 ;USER STRING BLOCK TYPE CODE (.TYUNS)
DEFSTR UNLEN,0,35,12 ;LENGTH OF USER NAME BLOCK
DEFSTR UNSHR,1,35,36 ;SHARE COUNT OF USER NAME STRING
DEFSTR UNVAL,2,35,36 ;FIRST 5 CHARS OF USER NAME STRING
;FREE POOL BLOCK
.FRNFB==:1 ;OFFSET OF NEXT FREE BLOCK POINTER
.FRHLN==:2 ;LENGTH OF FREE BLOCK HEADER
DEFSTR FRTYP,0,17,18 ;FREE BLOCK TYPE CODE (.TYFRE)
DEFSTR FRVER,0,23,6 ;VERSION # OF FREE BLOCK
DEFSTR FRLEN,0,35,12 ;LENGTH OF THIS FREE BLOCK
DEFSTR FRNFB,.FRNFB,35,36 ;POINTER TO NEXT FREE BLOCK
;FDB DEFINITIONS
DEFSTR FBTYP,.FBHDR,17,18 ;FDB TYPE CODE (.TYFDB)
DEFSTR FBVER,.FBHDR,23,6 ;VERSION # OF FDB (0 := PRE-V2)
DEFSTR FBLEN,.FBHDR,35,12 ;LENGTH OF FDB
DEFSTR FBFLG,.FBCTL,35,36 ;FLAGS
MSKSTR (FBTMP,.FBCTL,FB%TMP)
MSKSTR (FBPRM,.FBCTL,FB%PRM)
MSKSTR (FBNEX,.FBCTL,FB%NEX)
MSKSTR (FBDEL,.FBCTL,FB%DEL)
MSKSTR (FBNXF,.FBCTL,FB%NXF)
MSKSTR (FBLNG,.FBCTL,FB%LNG)
MSKSTR (FBSHT,.FBCTL,FB%SHT)
MSKSTR (FBDIR,.FBCTL,FB%DIR)
MSKSTR (FBNOD,.FBCTL,FB%NOD)
DEFSTR FBEXL,.FBEXL,35,33 ;LINK TO NEXT EXTENSION FDB
DEFSTR FBADR,.FBADR,35,36 ;DISK ADDRESS OF INDEX BLOCK
DEFSTR FBPRT,.FBPRT,35,36 ;PROTECTION OF THE FILE
DEFSTR FBCRE,.FBCRE,35,36 ;TIME AND DATE OF LAST WRITE
DEFSTR FBLW0,.FBUSE,17,18 ;VER #0 LAST WRITER DIR #
DEFSTR FBAT0,.FBUSE,35,18 ;VER #0 AUTHOR DIR #
DEFSTR FBAUT,.FBAUT,35,36 ;POINTER TO AUTHOR STRING
DEFSTR FBLWR,.FBLWR,35,36 ;POINTER TO LAST WRITER STRING
DEFSTR FBGEN,.FBGEN,17,18 ;GENERATION # OF FILE
DEFSTR FBDRN,.FBDRN,35,18 ;DIR NUMBER (IF THIS IS A DIR FILE)
DEFSTR FBACT,.FBACT,35,36 ;ACCOUNT # OR POINTER TO ACCOUNT BLOCK
DEFSTR FBGNR,.FBBYV,5,6 ;GENERATION RETENTION COUNT
DEFSTR FBBSZ,.FBBYV,11,6 ;BYTE SIZE OF DATA IN FILE
DEFSTR FBMOD,.FBBYV,17,4 ;MODE OF LAST WRITE TO FILE
DEFSTR FBNPG,.FBBYV,35,18 ;# OF PAGES IN FILE
DEFSTR FBSIZ,.FBSIZ,35,36 ;# OF BYTES IN THE FILE
DEFSTR FBCRV,.FBCRV,35,36 ;CREATION TIME AND DATE OF FILE
DEFSTR FBWRT,.FBWRT,35,36 ;DATE AND TIME OF LAST USER WRITE
DEFSTR FBREF,.FBREF,35,36 ;TIME AND DATE OF LAST NON-WRITE ACCESS
DEFSTR FBNWR,.FBCNT,17,18 ;# OF WRITES TO FILE
DEFSTR FBNRF,.FBCNT,35,18 ;# OF REFERENCES TO FILE
DEFSTR FBBK0,.FBBK0,35,36 ;BACKUP WORD 0
DEFSTR FBBK1,.FBBK1,35,36 ;BACKUP WORD 1
DEFSTR FBBK2,.FBBK2,35,36 ;BACKUP WORD 2
DEFSTR FBBK3,.FBBK3,35,36 ;BACKUP WORD 3
DEFSTR FBBK4,.FBBK4,35,36 ;BACKUP WORD 4
DEFSTR FBUSW,.FBUSW,35,36 ;USER SETTABLE WORD
DEFSTR FBGNL,.FBGNL,35,33 ;LINK TO NEXT GENERATION
DEFSTR FBNAM,.FBNAM,35,36 ;POINTER TO NAME STRING
DEFSTR FBEXT,.FBEXT,35,36 ;POINTER TO EXTENSION STRING
.FBLN0==:30 ;MINIMUM LENGTH OF AN FDB
;BLOCK TYPE CODES - FOUND IN LEFT HALF OF WORD 0 OF THE BLOCK
.TYNAM==:400001 ;BLOCK TYPE OF NAME STRING
.TYEXT==:400002 ;BLOCK TYPE OF EXTENSION STRING
.TYACT==:400003 ;BLOCK TYPE OF ACCOUNT STRING
.TYUNS==:400004 ;BLOCK TYPE OF USER NAME STRING
.TYFDB==:400100 ;BLOCK TYPE OF FDB
.TYLAC==:400200 ;BLOCK TYPE OF LEGAL ACCOUNT LIST
.TYDIR==:400300 ;BLOCK TYPE OF DIRECTORY BLOCK
.TYSYM==:400400 ;BLOCK TYPE OF SYMBOL TABLE
.TYFRE==:400500 ;BLOCK TYPE OF BLOCK ON THE FREE LIST
.TYFBT==:400600 ;BLOCK TYPE OF FREE STORAGE BIT TABLE
.TYGDB==:400700 ;BLOCK TYPE OF GROUP DESCRIPTOR BLOCK
;HOME BLOCK DEFINITIONS - COPIED FROM <2-MONITOR>DSKAL1.MAC
CODHOM==:707070 ;HOME BLOCK SPECIAL CODE
HBLEN==:200 ;LENGTH OF HOME BLOCK
HM1BLK==:1 ;BLOCK # OF FIRST HOME BLOCK
HM2BLK==:^D10 ;BLOCK # OF SECOND HOME BLOCK
HOMNAM==:0 ;SIXBIT /HOM/
HOMID==:1 ;SIXBIT /ID/
HOMPHY==:2 ;PHYSICAL ADR'S OF HOME BLOCKS
HOMSNM==:3 ;SIXBIT /STRUCTURE NAME/
HOMLUN==:4 ;XWD TOTAL PACKS, LOGICAL PACK #
HOMHOM==:5 ;BLOCK # OF HOME BLK,, BLK # OF OTHER HB
HOMP4S==:6 ;# OF PAGES FOR SWAPPING ON EACH UNIT
HOMFST==:7 ;FIRST SWAPPING TRACK ON EACH UNIT
HOMRXB==:10 ;ADR OF INDEX BLOCK OF ROOT DIRECTORY
HOMBXB==:11 ;INDEX BLOCK ADR OF BACKUP FILE
HOMFLG==:12 ;FLAGS
HOMSIZ==:13 ;SIZE OF A UNIT IN SECTORS (BLOCKS)
HOMBTB==:14 ;SIZE OF TOP HALF OF BIT TABLE (NUMBER OF TRACKS)
HOMFE0==:61 ;FE FILE SYSTEM WORD ONE (SECTOR #)
HOMFE1==:62 ;FE FILE SYSTEM WORD TWO (# OF SECTORS)
HOMUID==:165 ;UNIT ID
HOMOID==:170 ;OWNER ID
HOMFSN==:173 ;FILE SYSTEM TYPE
HOMCOD==:176 ;0 ,, CODHOM
HOMSLF==:177 ;THIS HOME BLOCK #
;DATA AND MACROS FOR COMMAND PARSER (USES COMND JSYS)
;TB - MACRO TO SET UP COMMAND TABLE
DEFINE TB (DAT,TXT)<
XWD [ASCIZ /TXT/],DAT>
;ADDRESSES FOR HANDLING EACH COMMAND
CMDTAB: CMDSIZ-1,,CMDMAX-1 ;NUMBER COMMANDS, MAXIMUM NUMBER
TB (.CHECK,CHECK) ;CHECK (BITTABLE/DIRECTORY)
TB (.CREAT,CREATE) ;CREATE NEW FILE SYSTEM
TB (.EXIT,EXIT) ;EXIT FROM CHECKD TO MONITOR
TB (.HELP,HELP) ;PRINT HELP TEXT
TB (.LIMIT,LIMIT) ;CONTROL SIZE OF DIRECTORIES
TB (.EXIT,QUIT) ;synonym for EXIT
TB (.REBLD,REBUILD) ;REBUILD BIT TABLE
TB (.RECNS,RECONSTRUCT) ;RECONSTRUCT ROOT-DIRECTORY
TB (.RLEAS,RELEASE) ;RELEASE LOST PAGES
TB (.SCAN,SCAN) ;SCAN FILE FOR PAGE NUMBERS
TB (.UNLIM,UNLIMIT) ;LET DIRECTORIES GROW LARGE
CMDSIZ==.-CMDTAB
CMDMAX==CMDSIZ ;MAXIMUM NUMBER OF COMMANDS
NCHPW==5 ;NUMBER OF CHARACTERS PER WORD
PROMPT: ASCIZ /CHECKD>/ ;PROMPT
CMDBLK: BLOCK .CMGJB+5 ;COMMAND STATE BLOCK (LEAVE ROOM FOR GROWTH)
GJFSIZ==.GJBFP+2
GTJBLK: BLOCK GJFSIZ ;GTJFN BLOCK (USED BY COMND)
BUFSIZ==150
BUFFER: BLOCK BUFSIZ ;BUFFER USER TYPES COMMAND INTO
ATMSIZ==BUFSIZ
ATMBUF: BLOCK ATMSIZ ;BUFFER THAT COMND STORES LAST FIELD INTO
;GTJFN BLOCK FOR LOST-PAGES.BIN (RELEASE COMMAND)
RLSGTJ: GJ%OLD!GJ%PHY ;OLD FILE ONLY
.PRIIN,,.PRIOU ;INPUT/OUTPUT JFN
-1,,STRNAM ;DEFAULT STRUCTURE
0 ;NO DEFAULT DIRECTORY
-1,,DIRNAM ;DEFAULT FILENAME
-1,,[ASCIZ/BIN/] ;DEFAULT EXTENSION
0 ;NO DEFAULT PROTECTION
0 ;NO DEFAULT ACCOUNT NUMBER
0 ;NO JFN SPECIFIED
;FORMAT OF LOST-PAGES.BIN FILE
.LPFLG==0 ;FLAG WORD
.LPMJK==<252525,,'LPF'> ;MAJIK CONSTANT IN FLAG WORD
.LPTAD==1 ;DATE-TIME STAMP
.LPSTR==2 ;ASCIZ STR NAME
.LPCNT==4 ;NUMBER OF ENTRIES
.LPDTA==5 ;BEGINNING OF DATA
;ALL COMMANDS RETURN HERE TO RE-START CHECKD AND DISMOUNT
; ANY PREVIOUSLY MOUNTED STRUCTURE.
RESTRT: SKIPN JOBNO ;ARE WE JOB 0
JRST QUIT ;YES - JUST EXIT
CALL DISMNT ;DISMOUNT IF NECESSARY
CALL RESET ;RESET STORAGE
MOVEI T1,1 ;TURN OFF PSI CHANNELS
DTI
MOVEI T1,3 ;FOR ^A AND ^C
DTI
TMSG <
>
JRST START ;GO RESTART PROGRAM
;SPECIAL ENTRY IF REBUILDING BIT TABLE AUTOMATICALLY
REBST: SETOM REBLDF ;INDICATE REBUILD REQUESTED
JRST START0 ;COMMON ENTRY
;NORMAL ENTRY
START: HLRZ T1,.JBSA ;GET ADDR OF 1ST LOCATION AFTER CHECKD
CAIL T1,FSTPAG ;OVERLAPPING?
JRST [ TMSG <?CHECKD program overlaps FSTPAG> ;YES
HALTF]
;IT SEEMS THAT CHECKD IS RUNNING OUT OF ADDRESS SPACE...
;IF YOU GET THE ABOVE MESSAGE, YOU HAVE A LOT OF WORK TO DO
SETZM REBLDF ;DEFAULT IS NO REBUILD BITTAB
START0: MOVE P,[IOWD PDLEN,PDL]
CALL RESET
SETOM CHKFLF ;DEFAULT IS CHECK FILES
SETZM DIRNUM ;INITIALIZE DIRECTORY NUMBER
SETZM TOTPGS ;INITIALIZE TOTAL FILE PAGES
SETZM ZUSED ;CLEAR INFO ABOUT STG
SETOM WRTLPF ;DEFAULT IS WRITE LOST PAGES FILE
SETZM STRMNT ;NO STRUCTURE MOUNTED YET
GJINF
MOVEM T3,JOBNO
MOVEI T1,.FHSLF
RPCAP
SKIPE JOBNO ;SKIP IF JOB 0
JRST STRT1
MOVX T3,SC%WHL!SC%OPR ;ENABLE CAPS
EPCAP
JRST STRT2
STRT1: TXNN T3,SC%WHL!SC%OPR ;CHECK ENABLED CAPS
JRST [ TMSG <?WHEEL or OPERATOR capability required
>
JRST QUIT]
TXNN T2,SC%CTC ;CHECK FOR ^C CAP
JRST [ TMSG <? ^C capability not enabled
>
HALTF
JRST START] ;MAKE CONTINUE RESTART
MOVX T3,SC%CTC!SC%WHL!SC%OPR
EPCAP ;ENABLE ^C CAP ALSO
STRT2: SETZM DALIST ; NO DISC ADDRESS LIST
;SET UP INTERRUPT SYSTEM
MOVEI T1,.FHSLF ;T1/FORK HANDLE
CIS ;CLEAR THE INTERRUPT SYSTEM
EIR ;ENABLE INTERRUPTS
MOVE T2,[XWD LEVTAB,CHNTAB] ;DECLARE LEVTAB AND CHNTAB
SIR
MOVNI T2,1 ;T2/CHANNEL NUMBERS
DIC ;DEACTIVATE ALL CHANNELS
MOVX T2,1B1+1B2 ;T2/CHANNEL NUMBERS
AIC ;ACTIVATE CHANNELS FOR TERM INTS
MOVE T1,[XWD 1,2] ;CONTROL-A ON CHANNEL 2 FOR STATUS REPORT
ATI ;ASSIGN ^A TO CHANNEL 2
SKIPN JOBNO ;IF JOB 0,
JRST DOJOB0 ; DO SPECIAL ROUTINE
MOVE T1,[XWD 3,1] ;ASSIGN ^C TO CHANNEL 1
ATI
;FALL INTO PARSE
; ..
;HERE TO START A NEW COMMAND. SET UP THE COMMAND STATE BLOCK
PARSE: MOVEI T2,CMDBLK ;POINT TO START OF COMMAND STATE BLOCK
MOVE T1,[.PRIIN,,.PRIOU] ;JFN'S FOR USER INPUT AND OUTPUT
MOVEM T1,.CMIOJ(T2)
HRROI T1,BUFFER ;POINTER TO START OF USER INPUT
MOVEM T1,.CMBFP(T2)
MOVEM T1,.CMPTR(T2) ;POINTER TO NEXT FIELD
MOVEI T1,BUFSIZ*NCHPW ;SPACE REMAINING IN BUFFER
MOVEM T1,.CMCNT(T2)
SETZM .CMINC(T2) ;NUMBER OF UNPARSED CHARACTERS
HRROI T1,ATMBUF ;POINTER TO ATOM BUFFER
MOVEM T1,.CMABP(T2)
MOVEI T1,ATMSIZ*NCHPW ;NUMBER CHARACTERS IN ATOM BUFFER
MOVEM T1,.CMABC(T2)
MOVEI T1,GTJBLK ;ADDRESS OF GTJFN BLOCK
MOVEM T1,.CMGJB(T2)
;HERE WHEN ERROR OCCURS AND NEED TO START OVER. REINIT THE COMND JSYS
PARSE1: MOVE P,[IOWD PDLEN,PDL] ;RESET STACK
HRROI T1,PROMPT ;POINTER TO PROMPT STRING
CALL CMDINI ;INIT COMND (SETUP REPARSE)
;HERE WHEN USER RUBOUTS INTO PREVIOUSLY GOTTEN TEXT
MOVE T1,[CZ%NCL+.FHSLF]
CLZFF ;RELEASE ALL JFNS
MOVEI T1,[FLDDB.(.CMKEY,,CMDTAB)] ;T1/ADDRESS OF FDB
CALL COMNDX ;LOOK FOR A KEYWORD
ERROR PARSE1,<Not a CHECKD command> ;NO. START OVER
HRRZ T1,(T2) ;YES. GO PROCESS IT
JRST (T1)
;SPECIAL JOB 0 ENTRY POINT TO CALL ROUTINES NECESSARY
;ACCORDING TO AUTOMATIC STARTUP
DOJOB0: MOVE T1,[ASCII "PS"] ;SET DEFAULT STR
MOVEM T1,STRNAM ; NAME STRING
SETOM PSFLG ;SAY REALLY DOING PS:
CALL SETSTR ;SET UP DEVICE DESIGNATOR
CALL CLRCDE ;CLEAR MONITOR FLAGS
;BEFORE STARTING
SETOM WRTLPF ;TURN ON LOST PAGES FILE
SKIPE REBLDF ;REBUILDING?
CALL BTBINI ;YES - INIT BITTABLE
CALL QDONE ;SCAN DIRECTORIES
MOVX T1,.SFCDE ;SETUP IN CASE OF ERRORS
MOVEI T2,1
SKIPN WRTLPF ;WAS THIS TURNED OFF?
SMON ;YES - SET FLAG THEN
JRST QUIT ;THROUGH - EXIT
;ROUTINE TO CLEAR SF%CDE AND SF%BTE FLAGS
CLRCDE: MOVX T1,.SFCDE ;FLAG TO CLEAR
MOVEI T2,0
SMON ;CLEAR IT
MOVX T1,.SFBTE ;OTHER FLAG
SMON
RET ;DONE - RETURN
;DRIVER FOR "ERROR" MACRO - T1/ POINTER TO ASCIZ ERROR MESSAGE
ERRDRV: ESOUT ;OUTPUT ERROR STRING TO TTY
CALL CRLF ;OUTPUT CRLF
MOVE T1,[CZ%NCL+.FHSLF] ;DUMP ALL CLOSED JFN'S
CLZFF
RET
;ROUTINE TO SETUP MOUNTED STRUCTURE DEVICE DESIGNATOR
;USES MNTBLK TO GET CORRECT STRING
SETMNT: SKIPN T1,MNTBLK+.MSTAL ;ALIAS IF PRESENT
MOVE T1,MNTBLK+.MSTNM ;ELSE USE NAME STRING
STDEV ;GET DEVICE DESIGNATOR
JSHLT ;CANT HAPPEND (WE JUST MOUNTED IT)
MOVEM T2,STRMNT ;SAVE IT
MOVE T2,MNTBLK+.MSTNM ;SAVE ACTUAL STR NAME
HRROI T1,STRHOM
MOVEI T3,0
SOUT
TMSG <
[>
MOVE T1,MNTBLK+.MSTNM ;ACTUAL NAME
PSOUT
TMSG <: Mounted>
SKIPN MNTBLK+.MSTAL ;SEE IF ALIAS
JRST STMNT1 ;NO - CONTINUE
TMSG < as >
MOVE T1,MNTBLK+.MSTAL
PSOUT ;PRINT IT
MOVEI T1,":"
PBOUT
HRROI T1,STRNAM ;COPY TO STRNAM
MOVE T2,MNTBLK+.MSTAL ; THE ACTUAL STR NAME NOW
MOVEI T3,0 ; IN USE BY THE SYSTEM
SOUT
STMNT1: TMSG <]
>
RET
;ROUTINE TO DISMOUNT ANY STRUCTURE MOUNTED BY CHECKD
DISMNT: SKIPN T2,STRMNT ;DEVICE DESIGNATOR OF STR MNTED
RET ;NONE - RETURN
MOVEM T2,MNTBLK ;SAVE FOR MSTR
SETZM STRMNT ;SAY NO LONGER MOUNTED
TMSG <
[Dismounting structure - >
HRROI T1,STRHOM ;PUBLISH NAME
PSOUT
TMSG <:]
>
MOVE T1,[1,,.MSDIS] ;FUNCTION TO DISMOUNT STR
MOVEI T2,MNTBLK ;ADDRS OF ARGS
MSTR ;DO FUNCTION
ERJMP [JSERR
JRST .+1]
RET ;RETURN (DONE)
;SETSTR - ROUTINE TO SET UP WORKING STRUCTURE INFO
SETSTR: SKIPE T2,STRMNT ;MOUNTED A STR?
JRST STSTR1 ;YES - ALREADY HAVE DEVICE DESIG
HRROI T1,STRHOM ;COPY NAME FOR LATER INFO
HRROI T2,STRNAM
MOVEI T3,0
SOUT ;...
HRROI T1,STRNAM ;NO - GET STRING TYPED
STDEV ;CONVERT TO DEVICE DESIGNATOR
JRST [ JSERR ;REPORT ERROR
JRST RESTRT]
STSTR1: MOVEM T2,STRDEV ;SAVE
TMSG <
[Working on structure - >
HRROI T1,STRHOM ;PRINT STR NAME
PSOUT
TMSG <:]
>
SKIPE ZUSED ;CHECK IF HERE YET
RET ;YES - RETURN
MOVE T1,STRDEV ;GET DEVICE DESIGNATOR
GDSKC ;GET DISK SPACE
MOVEM T1,ZUSED
RET ;RETURN
;GDNAM - ROUTINE TO WRITE CURRENT DIRECTORY NAME INTO DIRNAM
;RETURNS +1: FAILURE,
; T1/ERROR CODE
; +2: SUCCESS
;WRITES STRUCTURE:<DIRECTORY> IN DIRNAM
;REQUIRES DIRNUM TO HAVE THE 36-BIT DIRECTORY NUMBER
GDNAM: HRROI T1,DIRNAM ;GET THE NAME OF THIS DIRECTORY
MOVE T2,DIRNUM ;T2/ DIRECTORY NUMBER
DIRST ;WRITE ITS NAME
RET ;FAILED. RETURN FAILURE
RETSKP ;SUCCEEDED
;FRSDIR - GET FIRST DIRECTORY ON THE STRUCTURE
; CALL FRSDIR
;RETURNS +1: FAILURE
; +2: SUCCESS
;RETURNS WITH DIRNUM SET UP
FRSDIR: HRROI T2,[ASCIZ/<*>/] ;ASK FOR ALL DIRECTORIES
CALL ADDSTR ;ADD STRUCTURE STRING
MOVX T1,RC%AWL!RC%EMO ;T1/ ALLOW WILD CARD, NO RECOGNITION
RCDIR ;GET FIRST DIRECTORY NUMBER
ERJMP [ PNTERR(<Unable to reference directory files>)
JSERR
RET]
TXNE T1,RC%AMB!RC%NOM!RC%NMD ;ANY ERRORS?
JRST [ PNTERR(<Unable to reference directory files>)
RET]
MOVEM T3,DIRNUM ;NO. SAVE DIRECTORY NUMBER
RETSKP
;NXTDIR - GET NEXT DIRECTORY
; CALL NXTDIR
;RETURNS +1: FAILURE OR DONE
; +2: SUCCESS
;RETURNS WITH DIRNUM SET UP
NXTDIR: MOVX T1,RC%EMO!RC%AWL!RC%STP ;T1/ NO RECOGNITION, ALLOW WILD CARDS, STEP
HRROI T2,ATMBUF ;POINT TO STR:<*>
MOVE T3,DIRNUM ;T3/ DIRECTORY WE GOT BEFORE
RCDIR ;GET THE NEXT DIRECTORY
ERJMP [ PNTERR(<Failed to get next directory>)
SETZM DIRNUM
RET]
TXNE T1,RC%NOM!RC%AMB ;DID WE GET A STRANGE ERROR?
JRST [ PNTERR(<Failed to get next directory>)
SETZM DIRNUM
RET]
TXNE T1,RC%NMD ;NO MORE DIRECTORIES?
JRST [ SETZM DIRNUM
RET]
MOVEM T3,DIRNUM ;NO. SAVE DIRECTORY NUMBER
RETSKP
;CKDIR - ROUTINE TO DO DIRECTORY CONSISTENCY CHECK AND REBUILD
;IF THERE ARE ANY ERRORS
; DIRECTORY NUMBER IS IN "DIRNUM"
CKDIR: MOVE T2,DIRNUM ;GET DIRECTORY NUMBER
MOVX T1,DD%CHK ;CHECK ONLY
DELDF
ERJMP CKDIR1 ;ERROR - INFORM WORLD
RET ;OK - RETURN
CKDIR1: TMSG <% Rebuilding symbol table for >
HRROI T1,DIRNAM ;PRINT NAME
PSOUT
MOVE T2,DIRNUM ;GET NUMBER AGAIN
MOVX T1,DD%RST ;REBUILD FCN
DELDF ;TRY IT
ERJMP CKDIR2 ;CAN'T REBUILD
TMSG < [OK]
>
RET ;SAY OK AND RETURN
CKDIR2: TMSG < [FAILED]
>
RET ;RETURN
;ROUTINE TO GET CONNECTED STRUCTURE STRING INTO STRNAM
GETCON: GJINF ;GET CONNECTED STR ID
HLRZS T2 ;STRUCTURE UNIQUE CODE
HRLI T2,.DVDES ;MAKE INTO DEVICE DESIGNATOR
HRROI T1,STRNAM
DEVST ;CONVERT TO STRING
JRST GETCN1 ;NOT CONNECTED - FIX
RET ;RETURN
GETCN1: SETO T1, ;SAY THIS JOB
HRROI T2,T4 ;ONE WORD INTO T4
MOVX T3,.JILNO ;LOGGED IN DIR #
GETJI
JSHLT
MOVEM T4,FCNBLK ;SAVE IT
SETZM FCNBLK+1 ;NO PASSWORD
SETOM FCNBLK+2 ;THIS JOB
MOVE T1,[AC%CON+3]
MOVEI T2,FCNBLK ;ADDRS OF ARGS
ACCES ;CONNECT TO LOGGED IN DIR
ERJMP [JSHLT]
JRST GETCON ;LOOP BACK AND TRY AGAIN
;ROUTINE TO DO CONFIRMATION AND GET STRUCTURE NAME STRING
FCNFRM: HRROI T1,[ASCIZ /FOR/]
CALL CMDNOI ;XTRA GUIDE WORD
CONFRM: CALL GETCON ;GET CONNECTED STRUCTURE
HRROI T1,STRNAM ;POINT TO DEFAULT
CALL CMDSTR ;GET STRUCTURE STRING
HRROI T1,STRNAM ;PLACE TO STORE STRUCTURE NAME
HRROI T2,ATMBUF ;COPY STRING TYPED BY USER
MOVEI T3,0
SOUT ;SLOW
CALL CMDEOL ;PARSE TO EOL
JRST PARSE1 ;ERROR
RET
;ROUTINE TO PARSE STRUCTURE NAME STRING (DEFALUT IN T1)
CMDSTR: MOVEM T1,FCNBLK+.CMDEF ;SAVE DEFAULT
MOVX T2,<FLD(.CMFLD,CM%FNC)+<CM%SDH!CM%HPP!CM%DPP>>
MOVEM T2,FCNBLK ;SETUP FUNCTION
HRROI T1,[ASCIZ "STRUCTURE NAME"]
MOVEM T1,FCNBLK+.CMHLP ;SETUP HELP TEXT
SETZM FCNBLK+.CMDAT ;NO XTRA DATA
MOVEI T1,FCNBLK ;FUNCTION BLOCK
CALL COMNDX
ERROR PARSE1,<Invalid structure name>
SKIPN CMDBLK+.CMINC ;ANY REMAINING CHARS
RET ;NO - RETURN
MOVE T3,CMDBLK+.CMPTR ;YES - GET POINTER
ILDB T2,T3 ;GET NEXT CHARACTER
CAIE T2,":" ;SEE IF A COLON?
RET ;NO - OK RETURN
MOVEM T3,CMDBLK+.CMPTR ;SKIP OVER CHARACTER
SOS CMDBLK+.CMINC
RET ; AND RETURN
;GENERAL COMND UTILITIES
;SET UP AND EXECUTE COMND JSYS
; T1/ ADDRESS OF FUNCTION DESCRIPTOR BLOCK
;RETURNS +1: PARSE FAILED (ITRAP OR CM%NOP SET)
; +2: PARSE SUCCEEDED, T1,T2,T3 AS RETURNED BY COMND JSYS
COMNDX: MOVE T2,T1 ;MOVE FDB ADDRESS TO T2
MOVEI T1,CMDBLK ;GET COMND STATE BLOCK ADDR IN T1
COMND ;THE ONLY COMND JSYS IN CHECKD
ERJMP R
TXNE T1,CM%NOP ;PARSE OK?
RET ;NO
RETSKP ;YES
; COMNDE - PRINT ERROR MESSAGE FOR COMND
; T2/ ERROR CODE (RETURNED BY COMND)
; RETURNS +1: ALWAYS
COMNDE: HRROI T1,[ASCIZ/ /]
ESOUT ;SET UP BEGINNING OF ERROR MESSAGE
MOVEI T1,.PRIOU
HRLI T2,.FHSLF
SETZ T3,
ERSTR ;PRINT ERROR MESSAGE
JFCL
JFCL
CRLF: TMSG <
>
RET
;INIT COMND AND SETUP REPARSE TO BE THE RETURN ADDRS
;OF THE CALLER. C(T1) := POINTER TO PROMPT STRING
CMDINI: MOVEM T1,CMDBLK+.CMRTY ;SETUP PROMPT
POP P,SAVRET ; AND RETURN ADDRS
MOVEM P,SAVREP ;SAVE PDL FOR REPARSE
MOVEI T1,REPARS ;SETUP REPARSE ADDRS
MOVEM T1,CMDBLK+.CMFLG
MOVEI T1,[FLDDB.(.CMINI)] ;INIT FUNCTION
CALL COMNDX
JFCL
JRST @SAVRET ;RETURN
REPARS: MOVE P,SAVREP ;RESET PDL
JRST @SAVRET ; RETURN TO CALLER OF CMDINI
;NOISE PARSE ROUTINE
; C(T1) := GUIDE WORD STRING
CMDNOI: MOVEM T1,FCNBLK+.CMDAT ;SAVE TEXT STRING
MOVX T1,<FLD(.CMNOI,CM%FNC)>
MOVEM T1,FCNBLK ;SET UP FUNCTION
MOVEI T1,FCNBLK ;FUNCTION
CALL COMNDX
JRST [ CALL COMNDE ;ERROR, TYPE MESSAGE
JRST PARSE1]
RET ;RETURN
;CHECK FOR EOL (RETURN +1 IF NONE)
CMDEOL: MOVEI T1,[FLDDB.(.CMCFM)]
CALL COMNDX ;CHECK CONFIRMATION
JRST COMNDE ;ERROR, TYPE MESSAGE AND RETURN
RETSKP ;YES - SKIP RETURN
;ROUTINE TO WRITE A HEADER FOR THE LOST-PAGES FILE
LPFWRT: SETZM LPFHED+.LPSTR ;CLEAR STR NAME
SETZM LPFHED+.LPSTR+1
MOVE T1,[.LPMJK] ;MAJIK CONSTANT
MOVEM T1,LPFHED+.LPFLG
GTAD ;GET CURRENT DATE & TIME
MOVEM T1,LPFHED+.LPTAD
HRROI T1,LPFHED+.LPSTR ;POINT TO STR NAME
HRROI T2,STRHOM ;POINT TO NAME STRING
MOVEI T3,0 ;OUTPUT TILL NULL
SOUT
MOVE T1,LOSTOT ;LOST PAGES COUNT
MOVEM T1,LPFHED+.LPCNT
MOVE T1,OUTJFN
MOVE T2,[POINT 36,LPFHED]
MOVNI T3,.LPDTA ;HEADER SIZE
SOUT
RET ;DUMP AND RETURN
;ROUTINE TO CHECK LOST-PAGE FILE HEADER
LPFCHK: SETZM DIRNAM ;CLEAR STR NAME AREA
SETZM DIRNAM+1
MOVE T1,INJFN ;INPUT JFN
MOVE T2,[POINT 36,LPFHED]
MOVNI T3,.LPDTA ;SIZE OF RECORD
SIN ;READ IT
ERJMP [JSHLT]
MOVE T1,LPFHED+.LPFLG ;GET FLAG WORD
CAME T1,[.LPMJK] ;CHECK CONSTANT
JRST [ TMSG <?File not in correct format>
JRST LPFCHE]
HRROI T1,STRHOM ;CHECK MATCH OF STR
HRROI T2,LPFHED+.LPSTR
STCMP
JUMPN T1,[TMSG <?File is for structure >
HRROI T1,LPFHED+.LPSTR
PSOUT
JRST LPFCHV]
LPFCH1: TMSG <File written on: >
MOVEI T1,.PRIOU
MOVE T2,LPFHED+.LPTAD ;FILE DATE AND TIME
MOVEI T3,0 ;USE DEFAULT
ODTIM
TMSG < , contains >
MOVEI T1,.PRIOU
MOVE T2,LPFHED+.LPCNT
MOVEI T3,^D10 ;DECIMAL NUMBER
NOUT
JFCL
TMSG < entries.
>
RETSKP ;GOOD RETURN
LPFCHE: TMSG < , Aborting...
>
RET ;ERROR RETURN
LPFCHV: TMSG <
>
HRROI T1,[ASCIZ "Do you want to proceed anyway? "]
CALL YESNO ;GET CONFIRMATION
JUMPL T1,LPFCH1 ;YES - USE THIS FILE
RET ;NO - TERMINATE
;ROUTINE TO ADD STRUCTURE NAME TO BEGINNING OF STRING
;ACCEPTS:
; T2/ POINTER TO EXISTING STRING
; CALL ADDSTR
;RETURNS +1: ALWAYS,
; T2/ POINTER TO STRING WITH STRUCTURE IN FRONT
ADDSTR: STKVAR <GJSTR>
MOVEM T2,GJSTR ;SAVE POINTER TO STRING
HRROI T1,ATMBUF ;BUILD FILESPEC HERE
HRROI T2,STRNAM ;STRUCTURE NAME STRING
MOVEI T3,0
SOUT ;COPY STRUCTURE NAME
MOVEI T2,":" ;APPEND COLON TO DEVICE NAME
IDPB T2,T1
MOVE T2,GJSTR
SOUT ;COPY REMAINDER OF NAME
HRROI T2,ATMBUF ;COMPLETE NAME
RET ;RETURN WITH CORRECT POINTER
;ROUTINE TO CHECK FOR PS:
PSCHK: SETZM PSFLG ;NOT PS: YET
HRROI T1,STRNAM ;NAME OF STRUCTURE
HRROI T2,[ASCIZ "PS"]
STCMP ;COMPARE STRINGS
JUMPN T1,R ;NOT PS - NON SKIP
SETZM OKFLG ;FLAG FOR FNDSTR
CALL FNDSTR ;SEE IF THERE IS A DISMOUNTED
SETO T1, ;CANT HAPPEN (ASSUME PS)
JUMPE T1,R ;NEED TO MOUNT THIS PS
SETOM PSFLG ;THIS IS THE REAL PS:
RETSKP ;SKIP RETURN
;ROUTINE TO SCAN ALL DISK DRIVES LOOKING FOR STRUCTURE
;NAMED IN STRNAM AND CHECKING TO SEE IF IT IS DISMOUNTED
; RETURNS +1 IF ERROR
; RETURNS +2 C(T1) := -1 IF STR ALREADY MOUNTED
; C(T2) := 0 IF NEED TO MOUNT STR (MNTBLK SETUP)
FNDSTR: STKVAR <NUNITS,DEVSAV>
FNDST0: SETOM RNUBLK+.MSRCH ;INIT FOR FIRST UNIT
SETOM RNUBLK+.MSRCT
SETOM RNUBLK+.MSRUN
SETOM MNTBLK+.MSTNU ;INIT # OF UNITS IN STR
SETZM NUNITS ;INIT NUMBER OF UNITS FOUND
FNDST1: CALL GTUSTS ;GET UNIT STATUS
JRST FNDST3 ;NO MORE UNITS
CALL STRMAT ;MATCH STRUCTURE WANTED
JRST FNDST1 ;NO - TRY NEXT
SKIPL MNTBLK+.MSTNU ;FIRST TIME HERE
JRST FNDST2 ;NO - JUST SETUP UNIT
HRRZ T1,RNUBLK+.MSRNS ;YES - GET # OF UNITS IN STR
CAILE T1,10 ;MAX NUMBER WE CAN HANDLE
RETERR <More than 8. units in structure>
MOVEM T1,MNTBLK+.MSTNU
SETOM MNTBLK+.MSTUI ;INIT MOUNT TABLE TO -1
MOVE T1,[MNTBLK+.MSTUI,,MNTBLK+.MSTUI+1]
BLT T1,MNTBLK+.MSTUI+.MSTNO*10-1
;CLEAR TABLE
FNDST2: HRRZ T1,RNUBLK+.MSRNS ;GET # OF UNITS
CAME T1,MNTBLK+.MSTNU ;SAME AS BEFORE?
RETERR <Ambiguous number of units found>
HLRZ T1,RNUBLK+.MSRNS ;GET LOGICAL UNIT NUMBER
IMULI T1,.MSTNO ;CALC OFFSET INTO TABLE
ADDI T1,MNTBLK+.MSTUI
SKIPL .MSTCH(T1) ;UNIT PREVIOUSLY NOT FOUND?
RETERR <Multiple logical units found>
HRLI T1,RNUBLK+.MSRCH ;SET UP XFER WORD
MOVEI T2,.MSTUN(T1)
BLT T1,0(T2) ;XFER DISK ADDRESS
AOS NUNITS ;INCR NUMBER OF PACKS SO FAR
JRST FNDST1 ;GET MORE
;HERE WHEN NO MORE UNITS FOUND
FNDST3: SKIPE T1,NUNITS ;FOUND ANYTHING?
JRST FNDST8 ;YES - GO ON
HRROI T1,STRNAM ;SEE IF ALREADY ON-LINE
STDEV
RETERR <Structure not found>
MOVEM T2,DEVSAV ;SAVE DEVICE DESIG FOR DISMOUNT
SKIPN OKFLG ;WANT TO WARN USER
JRST [ SETO T1, ;DON'T MOUNT ANYTHING
RETSKP] ;GOOD RETURN
HRROI T1,[ASCIZ "% Structure already mounted. Forcibly dismount and proceed? "]
CALL YESNO
JUMPE T1,R ;DON'T PROCEDE
HRROI T1,STRHOM ;COPY NAME TO HERE
HRROI T2,STRNAM ; FOR DISMOUNT MSG
MOVEI T3,0
SOUT
MOVE T1,DEVSAV ;SETUP DEVICE DESIGNATOR
MOVEM T1,STRMNT
MOVEM T1,MNTBLK ;SETUP FOR GET STR STATUS
HRROI T1,STRNAM ;PUT STRUCTURE-ID HERE
MOVEM T1,MNTBLK+.MSGSI
MOVE T1,[.MSGLN,,.MSGSS]
MOVEI T2,MNTBLK ;FUNCTION BLOCK
MSTR ;GET STR ID
ERJMP [JSHLT] ;LOSE IF ERROR
CALL DISMNT ;DISMOUNT STR
JRST FNDST0 ;AND START OVER
FNDST8: CAME T1,MNTBLK+.MSTNU ;FOUND CORRECT NUMBER
RETERR <Structure missing one or more units>
HRROI T1,STRNAM ;SET NAME INTO BLOCK
MOVEM T1,MNTBLK+.MSTNM
SETZM MNTBLK+.MSTAL ;NO ALIAS
SETZ T1, ;SAY NEED TO MOUNT
RETSKP ;GIVE GOOD RETURN
;ROUTINE TO READ-NEXT-UNIT STATUS
GTUSTS: HRROI T1,NAMBUF ;PLACE FOR STRUCTURE NAME
MOVEM T1,RNUBLK+.MSRSN
SETZM RNUBLK+.MSRSA ;DONT CARE ABOUT ALIAS
MOVE T1,[.MSRLN,,.MSRNU] ; LEN,,FCN
MOVEI T2,RNUBLK ;ADDRS OF ARGS
MSTR ;GET STATUS
ERJMP [MOVEI T1,.FHSLF ;OURSELVES
GETER
HRRZ T1,T2
CAIE T1,MSTX18 ;NO MORE UNITS?
JSERR ;ERROR
RET] ;NO - RETURN
RETSKP ;GOOD RETURN
;ROUTINE WHICH SKIPS IFF CURRENT UNIT IS PART OF STRUCTURE WE
;WANT.
STRMAT: MOVE T1,RNUBLK+.MSRST ;GET UNIT STATUS
TXNE T1,MS%HBB ;VALID HOME BLOCKS?
JRST STMAT1 ;GIVE WARNING
TXNE T1,MS%MNT!MS%OFL!MS%DIA
RET ;MOUNTED, OFF-LINE, OR DIAG
HRROI T1,NAMBUF ;CONSIDER THIS NAME
HRROI T2,STRNAM ;REQUESTED STRUCTURE
STCMP ;MATCH STRINGS
JUMPN T1,R ;RETURN IF NO MATCH
RETSKP ;SKIP IF MATCH
STMAT1: TMSG <% Unit >
MOVE T2,RNUBLK+.MSRUN
MOVE T3,[1,,10]
CALL TTNOUT ;PRINT UNIT #
TMSG < on channel >
MOVE T2,RNUBLK+.MSRCH
CALL TTNOUT ;AND CHANNEL
TMSG < does not have valid home blocks - ignored.
>
RET ;RETURN ERROR
;ROUTINE TO INITIALIZE A STRUCTURE FROM INFORMATION GIVEN
;BY THE USER. C(T1) := FLAGS,,FCN
STRINI: HLLM T1,MNTBLK+.MSINU ;STORE FLAGS AND FUNCTION
HRRZ T2,MNTBLK+.MSINU ;GET NUMBER OF UNITS
SOS T2 ; -1
IMULI T2,.MSINO ;WORDS / UNIT
SETZM MNTBLK+.MSIST(T2) ;CLEAR STATUS WORD
HRROI T1,STRNAM ;SET UP NAME STRING
MOVEM T1,MNTBLK+.MSINM
MOVE T1,NPG4SW ;# PAGES FOR SWAPPING
MOVEM T1,MNTBLK+.MSISW(T2)
MOVE T1,NPGFES ;# PAGES FOR FRONT-END
MOVEM T1,MNTBLK+.MSIFE(T2)
MOVEI T1,MNTBLK+.MSIUI(T2)
HRLI T1,UNITID ;UNIT ID STRING
BLT T1,MNTBLK+.MSIUI+2(T2) ;MOVE STRING (12 CHARS)
MOVEI T1,MNTBLK+.MSIOI(T2)
HRLI T1,OWNRID ;OWNER ID STRING
BLT T1,MNTBLK+.MSIOI+2(T2) ;MOVE IT
HRLZI T1,.MSIOI+3(T2) ;SIZE OF ARG LIST
HRRI T1,.MSINI ; SIZE ,, FUNCTION
MOVEI T2,MNTBLK ;POINT TO ARG BLOCK
MSTR ;TRY TO MOUNT , ETC.
ERJMP [JSERR ;REPORT FAILURE
RET]
CALL SETMNT ;SET MOUNTED STR
RETSKP ;GOOD RETURN
;INIT STRUCTURE PARAMETERS (SET DEFAULTS)
STRDEF: SETZM NPG4SW ;ASSUME NO SWAPPING
SETZM NPGFES ;AND NO FRONT-END FILE SYSTEM
SETZM IDZB ;CLEAR ID FIELDS
MOVE T1,[IDZB,,IDZB+1]
BLT T1,IDZZ ;...
RET ;RETURN
;ROUTINE TO MOUNT STRUCTURE FOR EXCLUSIVE USE
XMNTA: TDZA T1,T1 ;OK IF MOUNTED ENTRY
XMNT: SETO T1, ;MUST FIND OFF-LINE
MOVEM T1,OKFLG ;SAVE FLAG FOR FNDSTR
CALL FNDSTR ;FIND STUCTURE
JRST RESTRT ; PROBLEM - START OVER
JUMPL T1,R ;RETURN IF ALREADY MOUNTED
HRROI T1,[ASCIZ /CHECKD/]
MOVEM T1,MNTBLK+.MSTAL ;SETUP ALIAS FOR CHECKD
MOVX T1,MS%XCL!MS%IGN ;EXCLUSIVE USE, IGNORE ERRORS
HLLM T1,MNTBLK+.MSTNU ;SET FLAGS
HRRZ T1,MNTBLK+.MSTNU ;CALC SIZE OF BLOCK
IMULI T1,.MSTNO
ADDI T1,.MSTUI ; PLUS CONSTANT SIZE
HRLZS T1 ;MOVE TO LHS
HRRI T1,.MSMNT ;MOUNT FUNCTION
MOVEI T2,MNTBLK ;POINT TO ARG BLOCK
MSTR
ERJMP [JSERR ;REPORT LOSAGE
JRST RESTRT] ;START OVER
CALL SETMNT ;SET STRUCTURE MOUNTED
HRROI T1,[ASCIZ /CHECKD/]
MOVEM T1,MNTBLK+.MSDEV ;SET UP ALIAS NAME
MOVE T1,[1,,.MSIMC] ;INCREMENT MOUNT COUNT FOR THIS STR
MOVEI T2,MNTBLK ;POINT TO ARG BLOCK
MSTR
ERJMP [JSERR ;REPORT LOSAGE
JRST RESTRT] ;START OVER
RET ;RETURN
;CREATE NEW FILE SYSTEM
;ACCEPT FILE STRUCTURE DESCRIPTION AND BUILD A NEW STRUCTURE
;ON THE SPECIFIED UNITS. (.MSINI FUNCTION)
.CREAT: HRROI T1,[ASCIZ /NEW FILE SYSTEM FOR/]
CALL CMDNOI ;PRINT GUIDE WORDS
CALL CONFRM ;GET STR NAME AND CONFIRM
CALL STRDEF ;SET DEFAULTS
HRROI T1,[ASCIZ /Enter alias: /]
CALL CMDINI ;INIT AND PROMPT
HRROI T1,[ASCIZ /CHECKD/]
CALL CMDSTR ;PARSE STRUCTURE NAME
HRROI T1,DIRNAM ;PLACE TO STORE ALIAS
HRROI T2,ATMBUF ;WHAT HE TYPED
MOVEI T3,0
SOUT
CALL CMDEOL ;PARSE TO EOL
JRST PARSE1 ; ERROR
CREAT1: HRROI T1,[ASCIZ /How many units in this structure? /]
CALL CMDINI ;PRINT PROMPT
MOVEI T1,[FLDDB.(.CMNUM,,^D10)]
CALL COMNDX ;GET DECIMAL NUMBER
ERROR CREAT1,<Invalid decimal number>
CAIG T2,8 ;AND IN RANGE
CAIGE T2,1
ERROR CREAT1,<Number not in range 1-8>
MOVEM T2,MNTBLK+.MSINU ;SAVE NUMBER OF UNITS
CALL CMDEOL ;GET <CR>
JRST CREAT1 ;TRY AGAIN
CALL CNFINF ;GET CONFIG INFO
MOVEI Q1,MNTBLK+.MSISU ;BEGINNING OF UNIT INFO
HRRZ Q2,MNTBLK+.MSINU ;COUNT OF UNITS
CREAT2: CALL GETUNI ;GET UNIT INFO
ADDI Q1,.MSINO ;STEP TO NEXT
SOJG Q2,CREAT2 ;LOOP TILL DONE
SETO T1, ;UNMAP HELP BUFFER
MOVE T2,[.FHSLF,,<HBUF>B44]
MOVX T3,PM%CNT+4
PMAP
;..
;..
CREAT3: HRROI T1,[ASCIZ /Number of pages to allocate for swapping? /]
CALL CMDINI ;PRINT PROMPT
MOVEI T1,[FLDDB.(.CMNUM,CM%SDH,^D10,<0 for no swapping space or
a decimal number between 2000 and 40000>,3050)]
CALL COMNDX
SKIPA ;GIVE ERROR IF PARSE FAILED
SKIPGE T2 ; AND IN RANGE
ERROR CREAT3,<Invalid decimal number>
JUMPE T2,CRT3A ;ZERO IS OK
CAIG T2,^D40000 ;VALIDATE RANGE
CAIGE T2,^D2000
ERROR CREAT3,<Swapping space value not in range 2000. to 40000.>
CRT3A: MOVEM T2,NPG4SW ;SAVE FOR LATER
CALL CMDEOL
JRST CREAT3
CREAT4: HRROI T1,[ASCIZ /Number of pages to allocate for the Front End File System? /]
CALL CMDINI ;PRINT PROMPT
MOVEI T1,[FLDDB.(.CMNUM,CM%SDH,^D10,<0 for no front end file system or
a decimal number between 250 and 10000>,950)]
CALL COMNDX
SKIPA ;GIVE ERROR IF PARSE FAILED
SKIPGE T2
ERROR CREAT4,<Invalid decimal number>
JUMPE T2,CRT4A ;ZERO IS OK
CAIG T2,^D10000 ;CHECK RANGE
CAIGE T2,^D250
ERROR CREAT4,<Value not in range 250. to 10000.>
CRT4A: MOVEM T2,NPGFES ;SAVE NUMBER
CALL CMDEOL
JRST CREAT4 ;TRY AGAIN
GJINF ;GET USER NAME
MOVE T2,T1
HRROI T1,NAMBUF
MOVEM T1,FCNBLK+.CMDEF ;SET UP DEFAULT POINTER
DIRST ; INTO NAMBUF
JSHLT
MOVX T1,<FLD(.CMFLD,CM%FNC)+<CM%SDH!CM%HPP!CM%DPP>>
MOVEM T1,FCNBLK ;SETUP FCN
SETZM FCNBLK+.CMDAT ;NO XTRA DATA
HRROI T1,[ASCIZ "NAME OF USER OWNING STRUCTURE"]
MOVEM T1,FCNBLK+.CMHLP ;SETUP HELP TEXT
CREAT5: HRROI T1,[ASCIZ "Owner name? "]
CALL CMDINI ;PROMPT
MOVEI T1,FCNBLK ;SETUP SPECIAL FUCNTION BLOCK
CALL COMNDX ;GET RESPONSE
ERROR CREAT5,<Invalid owner name string>
HRROI T2,ATMBUF ;RESPONSE
HRROI T1,OWNRID ;COPY TO OWNER ID
MOVEI T3,^D13 ;MAX CHARS
MOVEI T4,0 ;OR NULL (WHICHEVER COMES FIRST)
SOUT
SKIPN T3
ERROR CREAT5,<Name string greater than 12. characters>
CALL CMDEOL ;GRNTEE EOL
JRST CREAT5
;NOW TRY TO INIT/MOUNT THE STRUCTURE
HRROI T1,UNITID ;SETUP UNIT ID STRING
HRROI T2,STRNAM ;TO BE STRUCTURE NAME
MOVEI T3,0
SOUT ;...
HRROI T1,DIRNAM ;ALIAS TEXT STRING
MOVEM T1,MNTBLK+.MSIAL ;SET UP ALIAS
MOVX T1,<FLD(.MSCRE,MS%FCN)+MS%XCL>
CALL STRINI ;INIT STRUCTURE
JRST PARSE1 ;FAILED
JRST RESTRT ;OK - GET NEXT COMMAND
;ROUTINE TO GET CHANNEL AND UNIT NUMBER FOR A DRIVE
; C(Q1) := POINTER TO 3-WORD DRIVE INFO BLOCK
GETUNI: HRROI T2,[ASCIZ /Channel , Drive for logical unit /]
HRROI T1,TMPBUF ;TEMP BUFFER
MOVEI T3,0
SOUT
HRRZ T2,MNTBLK+.MSINU ;CALC UNIT #
SUB T2,Q2
MOVEI T3,8 ;OCTAL
NOUT
JFCL
HRROI T2,[ASCIZ /: /]
MOVEI T3,0
SOUT
GETUN1: HRROI T1,TMPBUF ;POINT TO GENERATED PROMPT
CALL CMDINI ;PRINT PROMPT
CALL SPCNUM ;SPECIAL NUMBER ROUTINE
JRST GETUN1 ;ERROR RETURN
CAIG T2,7 ;CHECK RANGE
CAIGE T2,0
ERROR GETUN1,<Channel number not in range 0-7>
MOVEM T2,.MSICH(Q1) ;STORE IN PROPER PLACE
MOVEI T1,[FLDDB.(.CMCMA)]
CALL COMNDX
ERROR GETUN1,<Comma expected between channel and drive numbers>
CALL SPCNUM ;GET DRIVE NUMBER
JRST GETUN1 ;INVALID NUMBER
CAIG T2,7
CAIGE T2,0
ERROR GETUN1,<Drive number not in range 0-7>
MOVEM T2,.MSIUN(Q1) ;STORE IT
SETOM .MSICT(Q1) ;CONTROLLER # TO -1
CALL CMDEOL ;GRNTEE EOL
JRST GETUN1 ;ERROR
RET ;OK - RETURN
;SPECIAL NUMBER ROUTINE WITH VERY LONG HELP TEXT
SPCNUM: MOVX T1,<FLD(.CMNUM,CM%FNC)+CM%HPP!CM%SDH>
MOVEM T1,FCNBLK ;SETUP FUNCTION
HRROI T1,HBUF ;POINT TO HELP TEXT
MOVEM T1,FCNBLK+.CMHLP
MOVEI T1,8 ;SETUP RADIX
MOVEM T1,FCNBLK+.CMDAT
SETZM FCNBLK+.CMDEF ;NO DEFAULT
MOVEI T1,FCNBLK ;T2/ FUNCTION BLOCK
CALL COMNDX
SKIPA ;FAILED
RETSKP ;GOOD RETURN
TMSG <
?Invalid octal number
>
RET ;ERROR RETURN
;ROUTINE TO SETUP STRING CONTAINING AVAILABLE UNIT INFO
CNFINF: SAVEQ ;SAVE Q1-Q3
HRROI Q1,HBUF ;POINT TO BUFFER BEG
MOVE T1,Q1 ;GET FIRST STRING
HRROI T2,HHDR ;POINT TO HEADER
MOVEI T3,0
SOUT
MOVEM T1,Q1 ;SAVE PNTR SO FAR
SETOM RNUBLK+.MSRCH ;INIT FOR FIRST UNIT
SETOM RNUBLK+.MSRCT
SETOM RNUBLK+.MSRUN
CNFIN1: CALL GTUSTS ;GET UNIT STATUS
JRST CNFIN3 ;NO MORE - DONE
MOVE Q2,RNUBLK+.MSRST ;GET STATUS
TXNE Q2,MS%MNT ;MOUNTED STR?
JRST CNFIN1 ;YES IGNORE
LDB T3,[POINTR (Q2,MS%TYP)]
HRROI T2,[ASCIZ "UNK "]
MOVE T1,Q1 ;GET OUTPUT PNTR
CAIG T3,MXUTYP ;VALID TYPE?
MOVE T2,UNTYTB(T3) ;GET NAME OF UNIT TYPE
MOVEI T3,0
SOUT ;DUMP IT
;..
;..
MOVEI T3,8 ;SPACE OVER
CALL SPACN
MOVE T2,RNUBLK+.MSRCH ;GET CHANNEL NUMBER
MOVEI T3,8
NOUT ;CONVERT TO NUMBER
JFCL
MOVEI T3,6 ;SPACES
CALL SPACN
MOVE T2,RNUBLK+.MSRUN ;GET UNIT NUMBER
MOVEI T3,8
NOUT
JFCL
MOVEI T3,2
CALL SPACN ;MOVE OVER
HRROI T2,NAMBUF ;ASSUME STR NAME
TXNE Q2,MS%HBB ;VALID HOME BLOCKS?
HRROI T2,[ASCIZ "Bad home blocks"]
TXNE Q2,MS%DIA ;MAINT MODE?
HRROI T2,[ASCIZ "Maintenance mode"]
TXNE Q2,MS%OFL ;OFF-LINE
HRROI T2,[ASCIZ "Off-line"]
MOVEI T3,^D20 ;MAX CHARS
MOVEI T4,0 ;TERMINATOR
SOUT ;DUMP STRING SO FAR
MOVNI T2,1 ;BACKUP OVER NULL
ADJBP T2,T1
MOVE T1,T2 ;RESTORE BP
AOS T3 ;ACCOUNT FOR IT
CALL SPACN ;T3 HAS CHARS REMAINING
TXNE Q2,MS%DIA!MS%OFL!MS%HBB
JRST CNFIN2 ;NO MORE INFO
HLRZ T2,RNUBLK+.MSRNS ;GET LOGICAL UNIT #
MOVEI T3,12 ;DECIMAL
NOUT
JFCL
MOVEI T2," "
IDPB T2,T1 ;PUT IN SPACE
MOVEI T2,"("
IDPB T2,T1 ;AND PAREN
HLRZ T2,RNUBLK+.MSRNS ;GET UNIT # AGAIN
AOS T2 ;CHANGE TO ORDINAL
NOUT ;DUMP IT
JFCL
HRROI T2,[ASCIZ " of "]
MOVEI T3,0
SOUT
HRRZ T2,RNUBLK+.MSRNS ;GET # OF UNITS IN STR
MOVEI T3,^D10
NOUT ;DUMP IT
JFCL
MOVEI T2,")" ;CLOSE PAREN
IDPB T2,T1
CNFIN2: MOVEI T2,15 ;CR
IDPB T2,T1 ;OUTPUT
MOVEI T2,12 ;LF
IDPB T2,T1
MOVEM T1,Q1 ;SAVE PNTR
JRST CNFIN1 ;GET NEXT
CNFIN3: MOVEI T2,15 ;XTRA CRLF
IDPB T2,Q1
MOVEI T2,12
IDPB T2,Q1 ;...
MOVEI T2,0 ;TIE OFF STRING
IDPB T2,Q1
RET ;RETURN
;UNIT INFO TABLES
UNTYTB: -1,,[ASCIZ "UNK "] ;0 - UNKNOWN
-1,,[ASCIZ "RP04"] ;1 - RP04
-1,,[ASCIZ "UNK "] ;2 - UNKNOWN
-1,,[ASCIZ "UNK "] ;3 - UNKNOWN
-1,,[ASCIZ "UNK "] ;4 - UNKNOWN
-1,,[ASCIZ "RP05"] ;5 - RP05
-1,,[ASCIZ "RP06"] ;6 - RP06
-1,,[ASCIZ "RP07"] ;7 - RP07
-1,,[ASCIZ "UNK "] ;10
-1,,[ASCIZ "RM03"] ;11 - RM03
MXUTYP==.-UNTYTB ;MAX UNIT TYPE
;HELP MESSAGE HEADER
HHDR: ASCIZ "
Pair of octal numbers from one of the following:
Type Channel Drive Structure name Logical unit
---- ------- ----- -------------- ------------
"
;ROUTINE TO OUTPUT # SPACES IN T3
SPACN: MOVEI T2,40 ;SPACE
IDPB T2,T1
SOJG T3,.-1
RET
;COMMON ROUTINE FOR CHECK COMMAND
.CHECK: MOVEI T1,[FLDDB.(.CMKEY,,CKTAB)] ;SECONDARY KEYTABLE
CALL COMNDX
ERROR PARSE1,<Not a CHECKD command>
HRRZ T1,(T2) ;GET DISPATCH
JRST (T1) ;PROCESS
;CHECK COMMAND KEYWORD TABLE
CKTAB: 2,,2 ;SIZE OF TABLE
TB (.BITAB,BITTABLE) ;CHECK BITTABLE CONSISTENCY
TB (.DIREC,DIRECTORY) ;CHECK DIRECTORY CONSISTENCY
;CHECK (CONSISTENCY OF) BITTABLE
;USER WANTS TO CHECK BIT TABLE.
; THIS IS THE STANDARD OPTION WHEN RUNNING FROM JOB 0.
;GET CONFIRMATION. USE DEFAULT FLAG SETTINGS.
.BITAB: HRROI T1,[ASCIZ /CONSISTENCY OF/]
CALL CMDNOI ;NOISE WORDS
CALL CONFRM ;GET STR AND CONFIRM
CALL PSCHK ;SEE IF THIS IS PS:
CALL XMNT ;NO - MOUNT FOR EXCLUSIVE ACCESS
CALL SETSTR ;SET CURRENT STR ETC.
SETOM WRTLPF ;TURN ON LOST-PAGES FILE
CALL QDONE ;SCAN DIRECTORIES
SKIPN PSFLG ;WAS THIS THE REAL PS:
JRST RESTRT ;NO - RESTART CHECKD
SKIPE WRTLPF ;STILL FOUND ERRORS?
CALL CLRCDE ;PS IS OK - CLEAR MONITOR FLAGS
JRST RESTRT ; AND RESTART
;CHECK (CONSISTENCY OF) DIRECTORY
;USER WANTS TO CHECK DIRECTORY CONSISTENCY. GET CONFIRMATION
.DIREC: HRROI T1,[ASCIZ /CONSISTENCY OF/]
CALL CMDNOI ;GUIDE WORDS
CALL CONFRM ;GET STR AND CONFIRM
CALL PSCHK ;SEE IF THE PS:
CALL XMNTA ;NO - CHECK MOUNTED
CALL SETSTR ;SET CURRENT STR
;GET THE FIRST DIRECTORY NUMBER AND STORE IT IN DIRNUM
CALL FRSDIR ;GET FIRST DIRECTORY
JRST RESTRT ;FAILED.
;HAVE A DIRECTORY NUMBER. CHECK DIRECTORY'S CONSISTENCY
.DIRLP: CALL GDNAM ;GET THE DIRECTORY NAME
JRST .DIRL1 ;SKIP IF ERROR
CALL CKDIR ;CHECK AND REBUILD IF NECESSARY
.DIRL1:
CALL NXTDIR ;GET THE NEXT DIRECTORY
JRST RESTRT ;FAILED OR DONE. START OVER
JRST .DIRLP
;EXIT (TO MONITOR)
;USER WANTS TO QUIT. GET CONFIRMATION AND EXIT
.EXIT: HRROI T1,[ASCIZ /TO MONITOR/]
CALL CMDNOI
MOVEI T1,[FLDDB. (.CMCFM)] ;T1/ADDRESS OF FUNCTION DESCRIPTOR BLOCK
CALL COMNDX ;GET CONFIRMATION
ERROR PARSE1,<Invalid command confirmation> ;NO
CALL RESET
JRST QUIT
;HELP
;USER WANTS AN EXPLANATION. GET CONFIRMATION AND PRINT HELP TEXT
.HELP: MOVEI T1,[FLDDB. (.CMCFM)] ;T1/ ADDRESS OF FDB
CALL COMNDX ;GET CONFIRMATION
ERROR PARSE1,<Invalid command confirmation> ;NO. PRINT ERROR
HRROI T1,HLPMSG
PSOUT ;TYPE THE HELP MESSAGE TO USER'S TTY
JRST PARSE1
;TEXT FOR HELP MESSAGE
HLPMSG: ASCIZ/ TOPS-20 CHECKD
CHECKD is a program to check the filesystem and bittable for consistent
data. CHECKD is also capable of rebuilding the bittable from the
directory information and of scanning for files which use particular
disk addresses. Commands are in the general form:
Keyword [optional arg] structure-name
Command Description
------- -----------
CHECK BITTABLE Check the consistency of the bit table by comparing
the pages marked as assigned against those pointed to
by the file system. Also writes lost page addresses
in a file.
CHECK DIRECTORY Check just directory information on the specified
structure.
LIMIT
UNLIMIT Control whether directories may contain huge amounts
of files or not. Use LIMIT to guarantee that a
particular structure can be used on small and large
systems. Use UNLIMIT to allow directories to grow
large on a structure. Note that if a directory grows
large, the structure will no longer be usable on a
small system.
REBUILD Rebuild bittable from directory information on the
specified structure.
RECONSTRUCT Reconstructs the <ROOT-DIRECTORY> on the specified
structure and then rebuilds the bit table.
CREATE Accepts configuration information for a file
structure and then creates a new file system on the
specified units.
SCAN Read a file of disk addresses and then scan the
directories for the specified addresses. When each
address is found, prints the name of the file that
uses that address.
EXIT Exit from CHECKD.
RELEASE Deassign the pages whose addresses are contained
in the specified file.
/
;LIMIT/UNLIMIT (NUMBER OF FILES PER DIRECTORY ON STRUCTURE
.LIMIT: MOVX T1,MS%LIM ;SET MS%LIM
JRST LIM1
.UNLIM: MOVEI T1,0 ;CLEAR MS%LIM
JRST LIM1
LIM1: STKVAR <NEWVAL>
MOVEM T1,NEWVAL
HRROI T1,[ASCIZ /NUMBER OF FILES PER DIRECTORY ON/]
CALL CMDNOI ;NOISE WORDS
CALL CONFRM ;GET STR AND CONFIRM
CALL SETSTR ;SET CURRENT STR
CALL HOMEIN ;READ HOME BLOCKS (OF FIRST PACK)
JRST RESTRT ;GIVE UP IF CAN'T
MOVE T2,HFLAGS ;GET OLD VALUE OF LIMIT BIT
HRROI T1,[ASCIZ /[Directories were unlimited]
/]
TXNE T2,MS%LIM ;ANNOUNCE OLD VALUE
HRROI T1,[ASCIZ /[Directories were limited]
/]
PSOUT
HRROI T1,STRNAM ;GET POINTER TO STRUCTURE NAME
MOVEM T1,HOMARG+.MSHNM ;STORE STRUCTURE BEING MODIFIED
MOVEI T2,HOMFLG ;WORD WE WANT TO MODIFY
MOVE T3,NEWVAL ;GET NEW VALUE FOR MS%LIM BIT
MOVX T4,MS%LIM ;SPECIFY WHICH BIT TO MODIFY
DMOVEM T1,HOMARG ;STORE ARGS IN ARG BLOCK
DMOVEM T3,HOMARG+.MSHVL
DMOVE T1,[EXP <4,,.MSHOM>,HOMARG]
MSTR ;MODIFY HOME BLOCK
ERCAL JSERR0 ;FAILED, PRINT REASON
JRST RESTRT ;RESTART
;REBUILD (BIT TABLE).
;USER WANTS TO REBUILD THE BIT TABLE. GET CONFIRMATION AND SET FLAG
.REBLD: HRROI T1,[ASCIZ /BIT TABLE OF/]
CALL CMDNOI ;NOISE WORDS
CALL CONFRM ;GET STR AND CONFIRM
CALL PSCHK ;CHECK FOR PS:
CALL XMNT ;NOT PS - MUST MOUNT IT
CALL SETSTR ;SET CURRENT STR
SETOM REBLDF ;YES. SET FLAG FOR QDONE CODE
CALL BTBINI ;INIT BITTABLE
CALL QDONE
SKIPN PSFLG ;WAS THIS THE PS:?
JRST RESTRT ;NO - RESTART WHEN DONE
CALL CLRCDE ;YES - CLEAR MONITOR FLAG
JRST RESTRT ;AND RESTART
;ROUTINE TO INIT STRUCTURE BITTABLE
BTBINI: MOVX T1,DA%INI ;T1/INITIALIZE BIT TABLE
MOVE T2,STRDEV ;T2/STRUCTURE NUMBER
DSKAS ;INITIALIZE A PRIVATE COPY OF THE BIT TABLE
JRST [ TMSG<
?Failed to initialize bit table
>
JSERR
JRST RESTRT]
RET ;RETURN
;RECONSTRUCT (ROOT-DIRECTORY)
;USER WANTS TO TRY TO RECOVER A LOST FILE SYSTEM. FIRST COPY THE
;BACKUP COPY OF THE ROOT-DIRECTORY AND THEN REBUILD THE BITTABLE.
.RECNS: MOVEI T1,[FLDDB.(.CMKEY,,RECTAB)] ;SECONDARY KEYTABLE
CALL COMNDX
ERROR PARSE1,<Not a valid RECONSTRUCT option>
HRRZ T1,(T2) ;GET DISPATCH
JRST (T1) ;PROCESS
; TABLE OF OPTIONS FOR RECONSTRUCTION
RECTAB: 2,,2
TB (.RECIT,INDEX-TABLE)
TB (.RECRD,ROOT-DIRECTORY)
; RECONSTRUCT ROOT-DIRECTORY
.RECRD: HRROI T1,[ASCIZ /OF/]
CALL CMDNOI ;PRINT GUIDE WORDS
CALL CONFRM ;GET STRUCTURE AND CONFIRM
CALL PSCHK ;IS THIS THE PRIMARY PUBLIC STR
SKIPA ;NO - MUST GET EXCLUSIVE ACCESS
ERROR PARSE1,<Cannot reconstruct PS: during time-sharing>
SETZM OKFLG ;OK IF ON-LINE (MSG LATER)
CALL FNDSTR ;FIND STRUCTURE (SET UP MNTBLK)
JRST PARSE1 ;REASON ALREADY GIVEN
JUMPL T1,[ERROR PARSE1,<Cannot reconstruct mounted structure>]
CALL STRDEF ;SET UP DEFAULTS
HRROI T1,[ASCIZ /CHECKD/]
MOVEM T1,MNTBLK+.MSIAL ;SET UP ALIAS
MOVX T1,MS%XCL+<FLD(.MSRRD,MS%FCN)> ;FCN FOR RECONSTRUCT
CALL STRINI ;INIT STRUCTURE
JRST PARSE1 ;FAILURE
TMSG <[Reconstruction phase 1 complete]
>
CALL SETSTR ;SET CURRENT STRUCTURE
SETOM REBLDF ;FLAG FOR QDONE REBUILD
CALL BTBINI ;INIT BITTABLE
CALL QDONE ;SCAN DIRECTORIES
JRST RESTRT ;RESTART PROGRAM
; RECONSTRUCT INDEX-TABLE
.RECIT: HRROI T1,[ASCIZ /OF/]
CALL CMDNOI ;PRINT GUIDE WORDS
CALL CONFRM ;GET STRUCTURE AND CONFIRM
CALL PSCHK ;IS THIS THE PRIMARY PUBLIC STR
SKIPA ;NO - MUST GET EXCLUSIVE ACCESS
ERROR PARSE1,<Cannot reconstruct PS: during time-sharing>
SETOM OKFLG ;ASK ABOUT DISMOUNTING IF NOW MOUNTED
CALL FNDSTR ;FIND STRUCTURE (SET UP MNTBLK)
JRST PARSE1 ;REASON ALREADY GIVEN
JUMPL T1,[ERROR PARSE1,<Cannot reconstruct mounted structure>]
CALL STRDEF ;SET UP DEFAULTS
HRROI T1,[ASCIZ /CHECKD/]
MOVEM T1,MNTBLK+.MSIAL ;SET UP ALIAS
MOVX T1,MS%XCL+<FLD(.MSRIX,MS%FCN)> ;FCN FOR RECONSTRUCT
CALL STRINI ;INIT STRUCTURE
JRST PARSE1 ;FAILURE
TMSG <[Reconstruction complete]
>
JRST RESTRT ;DONE
;RELEASE (LOST PAGES)
;USER WANTS TO RELEASE LOST PAGES. THESE ARE PAGES MARKED IN THE BIT
;TABLE AS USED AND NOT POINTED TO BY ANY FILE. A PREVIOUS CALL TO
;CHECKD HAS PRODUCED A FILE OF THESE PAGES. GET CONFIRMATION AND SET
;FLAGS AS NEEDED
.RLEAS: STKVAR<DSKAD2,SAVCHN>
HRROI T1,[ASCIZ /LOST PAGES FROM/]
CALL CMDNOI ;PRINT NOISE WORDS
MOVE T1,[RLSGTJ,,GTJBLK] ;COPY SPECIAL JFN BLOCK TO COMND'S JFN
BLT T1,GTJBLK+.GJJFN-1 ; BLOCK TO SPECIFY DEFAULT FILE
CALL GETCON ;SET UP CONNECTED STR
HRROI T1,DIRNAM ;BUILD DEFAULT FILESPEC
HRROI T2,STRNAM
MOVEI T3,0
SOUT
MOVEI T2,"-"
IDPB T2,T1
HRROI T2,[ASCIZ "LOST-PAGES"]
SOUT ;STR:STR-LOST-PAGES.BIN
MOVEI T1,[FLDDB.(.CMFIL)] ;T1/ADDRESS OF FUNCTION DESCRIPTOR BLOCK
CALL COMNDX ;GET INPUT FILE SPEC, DEFAULTING TO LOST-PAGES.BIN
JRST [ CALL COMNDE ;ERROR, TYPE MESSAGE
JRST PARSE1]
HRRZM T2,INJFN ;YES. SAVE THE FILE'S JFN
CALL FCNFRM ;(FOR) STR: & CONFIRM
CALL PSCHK ;OK IF PS
CALL XMNTA ;MOUNT IF NOT ON LINE
CALL SETSTR ;SET CURRENT STRUCTURE
MOVE T1,INJFN ;T1/JFN FOR INPUT FILE
MOVE T2,[44B5+1B19]
OPENF ;OPEN THE INPUT FILE
JRST [ PNTERR(<Failed to open lost pages file>)
MOVE T1,INJFN ;T1/JFN OF INPUT FILE
RLJFN ;RELEASE THE JFN
JFCL ;IGNORE FAILURE
JRST PARSE1] ;GO START PARSE AGAIN
CALL LPFCHK ;CHECK FILE FORMAT
JRST [ MOVE T1,INJFN ;INPUT JFN
RLJFN ;FLUSH IT
JFCL
JRST RESTRT] ;FORGET IT
SETZM LOSTOT ;CLEAR COUNT
;READ DISK ADDRESSES FROM FILE. EACH ADDRESS IS A SECTOR NUMBER RELATIVE
;TO START OF STRUCTURE. DEASSIGN VIA DSKAS JSYS.
RLSPG1: MOVE T1,INJFN ;T1/JFN OF INPUT FILE
BIN ;READ ONE ADDRESS
ERJMP RLSPG2 ;ERROR OR EOF
JUMPE T2,[TMSG <% Zero word -- ignored
>
JRST RLSPG1]
MOVE T1,T2 ;T1/SECTOR NUMBER
MOVEM T1,DSKAD2
TXO T1,DA%DEA
MOVE T2,STRDEV ;T2/STRUCTURE NUMBER
DSKAS
JRST [ TMSG <%Failed to deassign lost page at disk address>
MOVE T2,DSKAD2 ;T2/FAILING ADDRESS
MOVEI T3,10 ;T3/OCTAL RADIX
CALL TTNOUT ;PRINT THE ADDRESS THAT FAILED
JRST RLSPG1] ;IGNORE THE FAILURE
AOS LOSTOT ;COUNT SUCCESS
JRST RLSPG1 ;LOOP UNTIL EOF
;COME HERE ON ERROR OR END OF FILE - CHECK WHICH
RLSPG2: MOVE T1,INJFN
GTSTS ;GET FILE STATUS
TXNN T2,GS%EOF
JRST [ TMSG <?Error while reading >
MOVEI T1,.PRIOU
MOVE T2,INJFN
MOVEI T3,0
JFNS ;PRINT FILE NAME
TMSG < , Aborting...
>
JRST .+1]
TMSG < Released >
MOVEI T1,.PRIOU
MOVE T2,LOSTOT
MOVEI T3,^D10
NOUT ;TELL HOW MANY
JFCL
TMSG < pages
>
HRRZ T1,INJFN ;GET JFN BACK
SETZM T2 ;DELETE ALL GENERATIONS OF ** TCO 4.2496 **
DELNF ; THE LOST PAGES FILE ** TCO 4.2496 **
JSERR
HRRZ T1,INJFN
CLOSF
JFCL
JRST RESTRT ;DONE - RESTART
;SCAN (FOR DISK ADDRESSES FROM FILE) FILE-SPECIFICATION
;USER WANTS TO SEARCH A FILE CONTAINING DISK ADDRESSES THAT ARE ASSIGNED
;TO MORE THAN ONE FILE. EACH TIME A FILE IS FOUND TO POINT TO ONE OF THESE
;ADDRESSES A MESSAGE WILL BE PRINTED. GET THE NAME OF THE FILE TO BE
;READ AND CONFIRMATION. SET FLAGS AS NEEDED.
.SCAN: HRROI T1,[ASCIZ /FOR DISK ADDRESSES IN/]
CALL CMDNOI ;PRINT NOISE WORDS
MOVEI T1,[FLDDB.(.CMIFI)] ;T1/ADDRESS OF FDB
CALL COMNDX ;GET FILE TO SCAN
JRST [ CALL COMNDE ;ERROR, REPORT AND START OVER
JRST PARSE1]
HRRZM T2,DAJFN ;YES. SAVE THE JFN
CALL FCNFRM ;GET STR AND CONFIRM
CALL PSCHK ;OK IF PS:
CALL XMNTA ;MOUNT IF NOT ONLINE
CALL SETSTR ;SET CURRENT STR
SETOM CHKFLF ;YES. SET FLAG FOR QDONE CODE
MOVE T1,DAJFN ;T1/JFN
MOVE T2,[XWD 70000,200000]
OPENF
JRST [ PNTERR(<Failed to open specified file>)
MOVE T1,DAJFN
RLJFN
JFCL
JRST PARSE1]
MOVSI P1,-DASIZ
;..
;READ EACH ADDRESS AND STORE 2 WORDS PER ADDRESS:
;1) SOFTWARE ADDRESS
;2) GIVEN ADDRESS
;..
RDDALP: MOVE T1,DAJFN
CALL RDLIN ;READ ONE ADDRESS
MOVE T1,[POINT 7,LINBUF]
SETZ Q1, ;ASSUME SOFTWARE ADDRESS
RDDL1: ILDB T2,T1
CAIN T2," " ;FLUSH SPACES
JRST RDDL1
CAIE T2,"Z"-100 ;EOF?
CAIN T2,0
JRST RDDAW ;YES, DONE
CAIN T2,"H" ;HARDWARE ADDRESS?
JRST [ SETO Q1, ;YES
JRST RDDL1]
CAIN T2,"S" ;SOFTWARE ADDRESS?
JRST [ SETZ Q1, ;YES
JRST RDDL1]
CAIL T2,"0" ;OCTAL DIGIT?
CAILE T2,"7"
JRST [ TMSG <?Octal number required.
>
JRST RDDALP] ;TRY AGAIN
BKJFN ;BACKUP THE POINTER OVER FIRST DIGIT
JFCL
MOVEI T3,^D8 ;READ NUMBER IN OCTAL
NIN
JRST [ JSERR
TMSG <?Octal number required.
>
JRST RDDALP]
MOVE T1,T2
MOVEM T1,DATAB+1(P1) ;STORE GIVEN ADDRESS
SKIPE Q1 ;USE GAVE SOFTWARE ADDRESS?
JRST [ TXO T1,DA%CNV+DA%HWA
MOVE T2,STRDEV ;T2/STRUCTURE NUMBER
DSKAS ;NO, CONVERT
JSERR
JRST .+1]
MOVEM T1,DATAB(P1) ;STORE SOFTWARE ADDRESS
AOBJN P1,.+1
AOBJN P1,RDDALP
TMSG <?Table full.
>
;REACHED END OF FILE. EACH ADDRESS HAS BEEN WRITTEN IN 2 FORMS IN THE
;DATAB ARRAY. STORE AOBJN POINTER TO DATAB IN DALIST.
RDDAW: HLRES P1 ;NEGATIVE OF SPACE REMAINING
MOVNS P1 ;SPACE REMAINING
SUBI P1,DASIZ ;NEGATIVE OF SPACE USED
HRLZM P1,DALIST ;(-SPACE USET4,,0)
MOVE T1,DAJFN ;T1/JFN FOR INPUT FILE
CLOSF ;CLOSE THE FILE
JFCL ;IGNORE FAILURE
CALL QDONE ;NO MORE QUESTIONS
JRST RESTRT ;DONE - RESTART
;HERE WHEN USER HAS REQUESTED BITTABLE, REBUILT4, OR SCAN
;FLAGS INDICATE WHAT FUNCTIONS TO PERFORM
QDONE: CALL HOMEIN ;GO COMPUTE HOME BLOCK STUFF
JRST QDON1 ;ERROR
CALL BATIN ;GO GET THE BAT BLOCKS
TMSG <
>
CALL INIBTB ;INITIALIZE LOCAL COPY OF BIT TABLE
CALL SCANDI ;GO SCAN ALL THE DIRECTORIES
SKIPN DALIST ;SCANNING FOR DISK ADDRESSES?
SKIPN CHKFLF ;NO. CHECKING FILES?
JRST QDON1 ;SCANNING OR NOT CHECKING FILES. DON'T DO
; BIT TABLE STUFF
CALL FINBTB ;YES, DO SUMMARY, ETC.
QDON1: CALL RESET
RET ;RETURN TO CALLER
QUIT: MOVEI T1,1 ;T1/CODE FOR ^A
DTI ;DEASSIGN ^A FROM CHANNEL 2
SKIPN JOBNO ;CAME FROM JOB 0?
HALTF ;YES. ^C WASN'T ASSIGNED
MOVEI T1,3 ;T1/CODE FOR ^C
DTI ;DEASSIGN ^C FROM CHANNEL 1
HALTF
JRST .-1
;ROUTINE TO READ IN THE HOME BLOCKS AND SET NSSUN AND FSSUN
HOMEIN: MOVEI T1,1 ;READ IN FIRST HOME BLOCK
CALL GETHOM
JRST HOMIN2 ;FAILED, TRY SECOND HOME BLOCK
;TEMPORARY
HOMIN1:
MOVEI T2,SECPAG
MOVE T1,BATBUF+HOMSIZ ;GET # OF PAGES FOR SWAPPING PER UNIT
CAIN T1,SECUN0 ;IS THIS AN RP04 OR RP05
JRST [ HRLI T2,DSKSZ0 ;YES. POINT TO THAT DATA
JRST HOMIN3]
CAMN T1,[SECUN1] ;IS THIS AN RP06?
JRST [ HRLI T2,DSKSZ1 ;YES. POINT TO THAT DATA
JRST HOMIN3]
CAMN T1,[SECUN2] ;IS THIS AN RP07?
JRST [ HRLI T2,DSKSZ2 ;YES. POINT TO THAT DATA
JRST HOMIN3]
CAMN T1,[SECUN3] ;IS THIS AN RM03?
JRST [ HRLI T2,DSKSZ3 ;YES. POINT TO THAT DATA
JRST HOMIN3]
TMSG <
? HOMEIN: Unknown disk drive type
>
RET ;ERROR RETURN
HOMIN3: BLT T2,LPPCYL ;COPY THE RIGHT SIZE DATA
MOVE T1,BATBUF+HOMFLG ;GET HOME BLOCK FLAGS
MOVEM T1,HFLAGS ;REMEMBER THEM
MOVE T1,BATBUF+HOMP4S ;GET # OF PAGES FOR SWAPPING PER UNIT
IMUL T1,SECPAG ;GET # OF SWAPPING SECTORS
MOVEM T1,NSSUN
MOVE T1,BATBUF+HOMFST ;GET FIRST SWAPPING CYLINDER
IMUL T1,SECCYL ;CONVERT TO SECTOR
MOVEM T1,FSSUN ;SECTOR OFFSET FOR SWAPPING SPACE
HLRZ T1,BATBUF+HOMLUN ;GET NUMBER OF PACKS IN SYSTEM STR
MOVEM T1,NPACKS
SETZM LOTRK ;FIRST CYLINDER IS ALWAYS 0
IMUL T1,CYLUNT ;COMPUTE LAST CYLINDER
MOVEM T1,HITRK ;HITRK = NTKUN*NPACKS
SKIPN T1,BATBUF+HOMBTB ;SEE IF SIZE OF BIT TABLE IS DEFINED
JRST [ MOVEI T1,OLDTOP ;NO. MUST HAVE BEEN BUILT BY OLD MONITOR
MOVEM T1,BTBTOP ;SAVE OLD SIZE OF TOP HALF OF BIT TABLE
MOVEI T1,OLDBOT ; AND OLD SIZE OF BOTTOM HALF
MOVEM T1,BTBBOT
JRST HOMIN4]
MOVEM T1,BTBTOP ;BUILT BY RELEASE 2 OR LATER. SAVE SIZE
; OF TOP HALF OF BIT TABLE
IMUL T1,BTWCYL ;COMPUTE NUMBER OF BIT WORDS IN BOTTOM
MOVEM T1,BTBBOT ; AND SAVE IT
HOMIN4: ADD T1,BTBTOP ;COMPUTE TOTAL SPACE IN FILE
CAILE T1,BTBMAX ;WILL IT FIT IN ADDRESS SPACE?
JRST [ TMSG<
? HOMEIN: Bit table too large
>
RET]
ADDI T1,<PGSIZ-1> ;ROUND UP TO NEXT PAGE
IDIVI T1,PGSIZ ;COMPUTE NUMBER OF PAGES IN FILE
MOVEM T1,BTBPGS ;SAVE SIZE OF BIT TABLE FILE
RETSKP
HOMIN2: MOVEI T1,12 ;SECOND HOME BLOCK
CALL GETHOM ;READ IT IN
JRST NOHOME ;FAILED
JRST HOMIN1 ;SUCCESS
NOHOME: TMSG <HOMEIN: Could not find a valid home block>
RET
GETHOM: TXO T1,<FLD .DOPSR,DOP%AT> ;LOGICAL ADDRESS
MOVE T4,STRDEV ;GET STRUCTURE NUMBER
TXO T1,DOP%SN ;SET MASK TO ALL ONES
MOVEI T2,NWSEC ;LENGTH OF BLOCK
MOVEI T3,BATBUF ;ADR OF AREA TO READ INTO
DSKOP
JUMPN T1,R ;IF ERROR, RETURN
MOVS T1,BATBUF+HOMNAM ;CHECK CONSISTENCY
CAIE T1,'HOM'
RET
MOVE T1,BATBUF+HOMCOD ;AND SPECIAL CODE
CAIE T1,CODHOM
RET
RETSKP ;HOME BLOCK OK
;ROUTINE TO READ IN ALL OF THE BAT BLOCKS AND SET UP THE
;ERROR PAIRS
BATIN: STKVAR <LSTSEC,SAVWRK>
MOVE T1,NPACKS ;# OF PACKS IN STRUCTURE
IMUL T1,SECUNT ;COMPUTE SECTORS IN STRUCTURE
MOVEM T1,LSTSEC ;SAVE IT
MOVEI Q1,2 ;FIRST BAT ADDRESS
MOVEM P1,SAVWRK ;SAVE PERMANENT REG
MOVEI P1,BPRBLK ;START OF TABLE
GETBAT: MOVE T1,Q1 ;DISK ADDRESS
TXO T1,<FLD .DOPSR,DOP%AT> ;LINEAR ADDRESS
MOVE T4,STRDEV ;GET STRUCTURE NUMBER
TXO T1,DOP%SN ;SET TO -1
MOVEI T2,NWSEC ;SIZE OF A BLOCK
MOVEI T3,BATBUF ;BUFFER FOR THE BAT BLOCK
DSKOP ;GET THE BLOCK
JUMPN T1,TRY2 ;IF BAT4, TRY SECONDARY
MOVS T1,BATBUF ;GET HEADER WORD
CAIE T1,'BAT' ; A BAT BLOCK?
JRST TRY2 ;NO. TRY SECONDARY
MOVE T1,BATBUF+BATCOD ;SEE IF UNIQUE CODE IS THERE
CAIE T1,CODE ;IS IT?
JRST TRY2 ;NO. TRY SECONDARY THEN
GOTBAT: MOVEI T4,BATBUF ;T4/ADDRESS OF START OF BAT BLOCK
LOAD T2,BTHCT,(T4) ;GET NUMBER OF PAIRS WRITTEN INITIALLY
LOAD T3,BTMCT,(T4) ;GET NUMBER OF PAIRS MONITOR HAS WRITTEN
ADD T2,T3 ;TOTAL PAIRS WRITTEN
CAILE T2,MAXPAR ;DID BLOCK OVERFLOW?
MOVEI T2,MAXPAR ;YES. ONLY LOOK AT VALID PART THEN
MOVEM T2,OVERHD ;COUNT THESE AS OVERHEAD UNLESS THEY ARE
; FOUND TO BE ASSIGNED LATER
MOVEM T2,BATCNT ;KEEP A SEPARATE COUNT, TOO
JUMPE T2,NONE ;IF NONQ1, GO TO NEXT UNIT
MOVEI T3,BATBUF+4 ;FIRST BAD PAIR IN BLOCK
NXTPR: LOAD T4,ADD27,(T3) ;GET STARTING ADDRESS IF NEW FORMAT
LOAD T1,BADT,(T3) ;GET TYPE FIELD
SKIPN T1 ;OLD FORMAT?
LOAD T4,ADD18,(T3) ;YES, GET OLD STYLE ADDRESS INSTEAD
ADD T4,Q1 ;MAKE IT A LINEAR ADDRESS
SUBI T4,2 ;REMOVE BIAS FOR BAT BLOCK
MOVE T1,T4 ;COPY THE ADDRESS
PUSH P,T2 ;SAVE T2
IDIV T1,SECPAG ;ROUND DOWN ADDRESS TO A PAGE BOUNDARY
IMUL T1,SECPAG ;TO CATCH ERRORS IN MIDDLE OF A PAGE
POP P,T2 ;RESTORE THE AC
MOVEM T1,0(P1) ;SAVE AS FIRST ADDRESS OF REGION
MOVE T1,0(T3)
LSH T1,-^D27 ;GET COUNT OF BAD BLOCKS
ADDI T4,0(T1) ;CALCULATE LAST ONE
MOVEM T4,1(P1) ;FINISH OFF PAIR
ADDI P1,2 ;NEXT PAIR IN BUFFER
ADDI T3,2 ;NEXT PAIR IN BAT BLOCK
SOJG T2,NXTPR ;DO ALL PAIRS
NONE: ADD Q1,SECUNT ;NEXT PACK
CAMGE Q1,LSTSEC ;OVER THE LAST PACK IN THE STRUCTURE?
JRST GETBAT ;NO. GO DO IT
MOVEM P1,SVEND ;YES. SAVE END
MOVE P1,SAVWRK ;RESTORE PERMANENT REG
RET ;AND DONE
;PRIMARY BAT BLOCK WAS BAD. TRY THE SECONDARY
TRY2: MOVE T1,Q1 ;GET ADDRESS
ADDI T1,11 ;GET UP TO THE SECONDARY
MOVE T4,STRDEV ;GET STRUCTURE NUMBER
TXO T1,DOP%SN ;SET TO ONES
TXO T1,<FLD .DOPSR,DOP%AT> ;LINEAR ADDRESS
DSKOP ;READ IN THE SECONDARY
JUMPN T1,NONE ;IF ERROR, NONE THERE
MOVS T1,BATBUF
CAIE T1,'BAT' ;A GOOD BAT BLOCK?
JRST NONE ;NO. GIVE UP
MOVE T1,BATBUF+BATCOD ;UNLIKELY CODE
CAIE T1,CODE ;GOOD?
JRST NONE ;NO. NO BAT BLOCKS
JRST GOTBAT ;YES, USE THIS ONE
;INIBTB - INITIALIZE THE BIT TABLE
;ACCEPTS: NONE
; CALL INIBTB
;RETURNS +1:ALWAYS
;THIS ROUTINE INITIALIZES THE LOCAL COPY OF THE BIT TABLE USING THE SAME CODE
;AS THE MONITOR USES IN DSKAL1. FIRST IT INITIALIZES THE TABLE SO THAT ALL
;PAGES ARE FREE. THEN IT ASSIGNS THE SPECIAL SYSTEM BLOCKS ON EVERY PACK
;AND CALLS SWPASN TO ASSIGN THE SWAPPING SPACE
INIBTB: SAVEQ
STKVAR <LSTPAG>
MOVE T1,PAGCYL ;GET NUMBER OF PAGES PER CYLINDER
MOVN T2,BTBTOP ;GET SIZE OF TOP HALF OF BIT TABLE
HRLZS T2 ;T2/(-COUNT,,OFFSET IN TOP HALF)
INIBT2: MOVEI T3,0(T2) ;GET OFFSET
ADDI T3,LOCBTB ;ADDRESS OF CURRENT WORD
MOVEM T1,0(T3) ;STORE FULL COUNT FOR EACH CYLINDER
AOBJN T2,INIBT2 ;GO TO NEXT WORD
MOVE T2,BTBTOP ;START AT BEGINNING OF BIT PART OF BIT TABLE
ADDI T2,LOCBTB ;COMPUTE ADDRESS OF FIRST BIT WORD
INIBT1: SETOM 0(T2) ;INIT ONE BIT WORD
SUBI T1,^D36 ;REDUCE COUNT OF PAGES (1 BIT PER PAGE)
CAILE T1,^D36 ;LAST WORD?
AOJA T2,INIBT1 ;NO. GO INITIALIZE IT
MOVN T1,BITS-1(T1) ;LAST WORD PARTIALLY FULL. SET ONLY VALID BITS
MOVEM T1,1(T2) ;STORE LAST WORD FOR FIRST CYLINDER
MOVEI T1,LOCBTB ;CONSTRUCT STARTING LOCATIONS FOR BLT
HRLS T1 ;(START OF TABLE,,START OF TABLE)
MOVE T3,BTBTOP ;GET SIZE OF TOP HALF OF BIT TABLE
HRLS T3 ; IN BOTH HALVES
ADD T1,T3 ;(START OF BOTTOM HALF,,START OF BOTTOM HALF)
ADD T1,BTWCYL ;(START OF BOTTOM HALF,,2ND GROUP OF WORDS)
MOVEI T2,LOCBTB ;CONSTRUCT LIMIT FOR BLT
ADD T2,BTBTOP ;POINT TO BOTTOM HALF OF BIT TABLE
ADD T2,BTBBOT ;POINT JUST BEYOND END
SUBI T2,1 ;POINT TO LAST WORD FOR LIMIT OF BLT
BLT T1,0(T2) ;COPY GROUPS OF BIT WORDS TO REST OF TABLE
;ASSIGN THE HOME BLOCKS
SETZM NBAD ;INITIALIZE COUNT OF ERRORS
SETOM PAGNN ;INDICATE NOT A FILE PAGE
MOVSI Q3,-NHOME ;Q3/(-COUNT,,OFFSET TO HOME TABLE)
SETOM LSTPAG ;INITIALIZE LAST PAGE ASSIGNED
;LOOP OVER SPECIAL SECTORS IN HOME BLOCK TABLE
HOMAS1: MOVE T1,HOME(Q3) ;GET SECTOR NUMBER WITHIN UNIT
IDIV T1,SECPAG ;CONVERT TO PAGE
CAMN T1,LSTPAG ;SAAME AS LAST PAGE ASSIGNED?
JRST HOMAS3 ;YES. DON'T ASSIGN IT AGAIN
;ASSIGN THIS PAGE FOR ALL UNITS
MOVEM T1,LSTPAG ;SAVE LAST PAGE ASSIGNED
MOVN Q2,NPACKS ;NO. GET NUMBER OF UNITS IN STRUCTURE
HRLZS Q2 ;Q2/(-COUNT,,UNIT NUMBER)
HOMAS2: MOVEI T1,0(Q2) ;GET UNIT NUMBER
IMUL T1,SECUNT ;COMPUTE FIRST SECTOR IN THIS UNIT
ADD T1,HOME(Q3) ;T1/SECTOR TO ASSIGN
MOVX F,MR%SPC ;INDICATE SPECIAL BLOCKS
CALL MRKBTB ;ASSIGN PAGE
JFCL ;IGNORE FAILURE. ERROR HAS BEEN REPORTED
AOBJN Q2,HOMAS2 ;LOOP TO NEXT UNIT IN STRUCTURE
HOMAS3: AOBJN Q3,HOMAS1 ;LOOP TO NEXT SPECIAL SECTOR
SKIPE NBAD ;DID WE GET ANY ERRORS?
JRST [ TMSG <- - - - - - -
> ;YES. PRINT DIVIDER TO SEPARATE FROM FILE OUTPUT
SETZM NBAD ;RESET COUNT
JRST .+1]
CALL SWPASN ;MARK THE SWAPPING PAGES
RET
;DSKASA - ASSIGN PAGE IN LOCAL BIT TABLE
;ACCEPTS:
; 1/SECTOR NUMBER RELATIVE TO START OF STRUCTURE
; CALL DSKASA
;RETURNS +1: ILLEGAL ADDRESS OR ADDRESS ALREADY ASSIGNED
; T4/ERROR CODE
; +2: SUCCESS, PAGE ASSIGNED
;THIS ROUTINE ASSIGNS A PAGE IN THE LOCAL BIT TABLE USING THE SAME METHOD
;AS THE MONITOR USES IN DSKAL1. IT ASSIGNS THE PAGE CONTAINING THE
;SPECIFIED SECTOR. IF THE PAGE IS ALREADY ASSIGNED, IT TAKES THE ERROR
;RETURN.
DSKASA:
SETZ T4, ;INITIALIZE ERROR FLAG
IDIV T1,SECCYL ;T1/CYLINDER, T2/SECTOR WITHIN CYLINDER
CAML T1,LOTRK ;NON-NEGATIVE CYLINDER NUMBER?
CAML T1,HITRK ;WITHIN STRUCTURE'S LIMITS?
JRST DSKAS1 ;RETURN ILLEGAL ADDRESS
CAML T1,BTBTOP ;WITHIN TOP HALF OF BIT TABLE?
JRST DSKAS1 ;NO. RETURN ILLEGAL ADDRESS
MOVE T3,PAGCYL ;GET PAGES PER CYLINDER
IMUL T3,SECPAG ;COMPUTE NUMBER SECTORS IN COMPLETE PAGES
CAML T2,T3 ;IS THIS SECTOR WITHIN A FULL PAGE (POSSIBLE
; EXTRA SECTORS AT END OF CYLINDER)?
JRST DSKAS1 ;NO. RETURN ILLEGAL ADDRESS
MOVE T4,T1 ;4/CYLINDER NUMBER
IDIV T2,SECPAG ;CONVERT SECTOR TO PAGE WITHIN CYLINDER
JUMPN T3,DSKAS1 ;MUST BE ON PAGE BOUNDARY
IDIVI T2,^D36 ;GET INDEX TO BIT WORD WITHIN CYLINDER
IMUL T1,BTWCYL ;OFFSET IN BOTTOM FOR THIS CYLINDER
ADD T1,T2 ;OFFSET IN BOTTOM FOR THIS PAGE
ADD T1,BTBTOP ;OFFSET IN BIT TABLE FOR BIT WORD
MOVE T3,BITS(T3) ;BIT FOR THIS PAGE
TDNN T3,LOCBTB(T1) ;IS PAGE ALREADY ASSIGNED?
JRST DSKAS2 ;YES. REPORT MULTIPLY ASSIGNED ADDRESS
ANDCAM T3,LOCBTB(T1) ;NO. ASSIGN IT
SOS LOCBTB(T4) ;REDUCE FREE COUNT
RETSKP
DSKAS1: MOVX T4,ER%IDA ;INDICATE ILLEGAL ADDRESS
RET
DSKAS2: MOVX T4,ER%MDA ;INDICATE MULTIPLY ASSIGNED
RET
;ROUTINE TO ASSIGN THE SWAPPING BLOCKS
; CALL SWPASN
;RETURNS +1: ALWAYS
SWPASN: MOVN P1,NPACKS ;SET UP AN AOBJN POINTER
HRLZS P1 ;FOR ALL PACKS IN SYSTEM
SETZM NBAD ;INITIALIZE COUNT OF ERRORS
SETOM PAGNN ;INDICATE NOT A FILE PAGE
SWPAS1: MOVE P2,SECUNT ;GET # OF SECTORS PER UNIT
IMULI P2,0(P1) ;GET LOGICAL ADR OF START OF THIS PACK
ADD P2,FSSUN ;GET START OF SWAPPING SPACE ON UNIT
MOVE P3,NSSUN ;GET # OF SWAPPING SECTORS PER UNIT
ADD P3,SECPAG ;MAKE SURE TO EVEN UP TO FULL PAGE
SUBI P3,1
IDIV P3,SECPAG ;GET # OF PAGES FOR SWAPPING
JUMPE P3,SWPAS3 ;IF NO SWAPPING SKIP UNIT
SWPAS2: MOVE T1,P2 ;GET NEXT PAGE TO BE ASSIGNED
MOVX F,MR%SWP ;INDICATE THIS IS SWAPPING SPACE
CALL MRKBTB ;ASSIGN THE PAGE
JFCL ;IGNORE FAILURE. ERROR HAS BEEN REPORTED
ADD P2,SECPAG ;STEP TO THE NEXT PAGE
SOJG P3,SWPAS2 ;LOOP BACK FOR ALL PAGES ON UNIT
SWPAS3: AOBJN P1,SWPAS1 ;LOOP BACK FOR ALL UNITS
SKIPE NBAD ;DID WE GET ANY ERRORS?
JRST [ TMSG <- - - - - - -
> ;PRINT DIVIDER TO SEPARATE FROM FILE OUTPUT
SETZM NBAD ;RESET COUNT OF ERRORS
JRST .+1]
RET ;AND RETURN
;SCAN ALL DIRECTORIES. CALLS SCANFD WITH ONE DIRECTORY, LOOPS THROUGH ALL DIRECTORIES
SCANDI:
;SET UP STR:<ROOT-DIRECTORY> IN ROOTDR
HRROI T1,ROOTDR ;T1/ DESTINATION POINTER
HRROI T2,STRNAM ;T2/ SOURCE IS STRUCTURE NAME
SETZ T3, ;T3/ STOP ON NULL
SOUT ;PUT STRUCTURE NAME IN ROOTDR
MOVEI T2,":" ;T2/ A COLON
IDPB T2,T1 ;ADD A COLON AFTER STRUCTURE
HRROI T2,[ASCIZ/<ROOT-DIRECTORY>/]
SETZ T3, ;STOP ON NULL
SOUT ;ADD <ROOT-DIRECTORY> TO STRUCTURE
MOVEM T1,ROOTPT ;SAVE POINTER TO END
CALL FRSDIR ;GET THE FIRST DIRECTORY
RET ;FAILED. QUIT
SCAND2: CALL GDNAM ;GET NAME & NUMBER
JRST SCAND1 ;SKIP IF ERROR
CALL CKDIR ;CHECK AND REBUILD IF NECESSARY
CALL SCANFD ;SCAN THIS DIRECTORY
SCAND1: CALL NXTDIR ;GET NEXT DIRECTORY
RET ;FAILED OR DONE
JRST SCAND2 ;GO CHECK THIS ONE
;SCAN ONE DIRECTORY. CALLS SCAN3 FOR A SYMBOL TABLE ENTRY, LOOPS THROUGH
;ALL SYMBOL TABLE ENTRIES
;DIRNUM/DIRECTORY NUMBER
SCANFD: HRRZ T1,DIRNUM ;USE NUMBER ONLY (ON THIS STR)
CALL SETFD ; MAP THE APPROPRIATE DIRECTORY
;DIRORG IS STARTING LOCATION
RET ;FAILED TO MAP OR HEADER WAS BAD
MOVE T1,[POINT 7,DIRNAM]
MOVEI T2,DIRORG
LOAD T2,DRNUM,(T2) ; GET DIRECTORY NUMBER
HRL T2,STRDEV ; ADD STR UNIQUE CODE
DIRST ;PUT NAME OF DIRECTORY IN DIRNAM
JFCL
MOVEI T2,0
IDPB T2,T1 ;TERMINATE WITH NULL
MOVEI T4,DIRORG
LOAD T1,DRSTP,(T4) ;GET LAST WORD USED BY SYMBOL TABLE
MOVEM T1,SYMTOP
LOAD T4,DRSBT,(T4) ;GET ADDRESS OF START OF SYMBOL TABLE
;NOTE: ASSUMES HEADER IS 2 WORDS
SCAN1: ADDI T4,.SYMLN ; STEP TO NEXT SYMBOL
CAMGE T4,SYMTOP ; REACHED END OF SYMBOL TABLE?
JRST SCAN2 ; NO
;END OF SYMBOL TABLE. UNMAP THE DIRECTORY
CALL UNMAPD ;UNMAP THE DIRECTORY
RET
SCAN2: MOVE T3,T4 ; GET POINTER TO SYMBOL
ADDI T3,DIRORG ; GET ABS ADR OF SYMBOL
LOAD T1,SYMET,(T3) ; GET ENTRY TYPE
JUMPN T1,SCAN2A ; IF NOT A NAME, SKIP IT
LOAD T1,SYMAD,(T3) ; GET ADDRESS OF FDB
ADDI T1,DIRORG ; GET ABS ADR OF FDB
LOAD T2,FBNAM,(T1) ; GET POINTER TO NAME STRING
ADDI T2,DIRORG+1 ; GET ABS ADR OF START OF STRING
HRROM T2,DEFNAM
PUSH P,T4 ; SAVE POINTER TO SYMBOL TABLE
LOAD T4,SYMAD,(T3) ; GET RELATIVE ADR OF FDB FROM SYMBOL TABLE
CALL SCAN3 ; GO DO NAME CHAIN
POP P,T4 ; GET BACK INDEX INTO SYMBOL TABLE
SCAN2A: JRST SCAN1 ; LOOP BACK FOR ALL SYMBOLS
;MAP ONE DIRECTORY INTO THIS FORK
; T1/DIRECTORY NUMBER
SETFD: PUSH P,T1 ;SAVE DIRNUM
CALL GTFILE ;GET JFN ON DIRECTORY FILE
HRRZ T1,FDJFN ;OPEN THE DIRECTORY FILE
MOVE T2,[440000,,OF%RD+OF%THW]
OPENF
JRST [ TMSG <OPENF failed on directory >
HRROI T1,DIRNAM ;T1/POINTER TO DIRECTORY NAME
PSOUT ;PRINT DIRECTORY
TMSG< - Skipped>
JSERR ;OPEN FAILET4, GO TYPE OUT ERROR
POP P,T1 ;RESTORE DIRECTORY NUMBER
RET]
HRLZ T1,FDJFN ;NOW MAP IN DIRECTORY
MOVE T2,[.FHSLF,,DIRORG/1000]
MOVE T3,[PM%CNT+PM%RD+NDIRPG]
PMAP
POP P,T1 ;GET BACK DIR #
CALL DR0CHK ;CHECK CONSISTENCY OF HEADER
JRST [ CALL UNMAPD ;BAD HEADER. UNMAP THE DIRECTORY
CALLRET BADBLK] ;HEADER IS BAD
RETSKP
;ROUTINE TO UNMAP A DIRECTORY
UNMAPD: SETO T1, ;PMAP -1 TO DIRORG
MOVE T2,[.FHSLF,,DIRORG/1000]
MOVE T3,[PM%CNT+PM%RD+NDIRPG]
PMAP ;UNMAPPED!
HRRZ T1,FDJFN ;T1/ JFN
CLOSF ;CLOSE THIS FILE
JFCL
RET ;AND EXIT
;GTFILE - GET FILE NAME FOR THIS DIRECTORY AND GET A JFN ON IT
;ASSUMES DIRNAM POINTS TO STR:<DIRECTORY>
; CALL GTFILE
;RETURN +1: ALWAYS
; FDJFN/ JFN FOR DIRECTORY FILE
GTFILE: MOVE T1,[POINT 7,DIRNAM] ;POINT TO STR:<DIRECTORY>
SETZM DOTPTR ;INDICATE DOT NOT FOUND YET
SETZM BRKPTR ;INDICATE BRACKET NOT FOUND YET
GTFIL1: ILDB T2,T1 ;GET NEXT CHARACTER IN STRING
CAIN T2,"<" ;LEFT BRACKET?
JRST [ MOVEM T1,BRKPTR ;YES. SAVE ITS POINTER
JRST GTFIL1] ;GO GET NEXT CHARACTER
CAIN T2,"." ;IS IT A DOT?
JRST [ MOVEM T1,DOTPTR ;YES. SAVE ITS POINTER
JRST GTFIL1] ;GO GET NEXT CHARACTER
CAIE T2,">" ;IS IT A RIGHT BRACKET?
JRST GTFIL1 ;NO. GO GET NEXT CHARACTER
SKIPN DOTPTR ;FOUND RIGHT BRACKET. HAVE WE SEEN A DOT?
JRST GTFIL2 ;NO. MUST BE IN <ROOT-DIRECTORY>
;HERE WHEN THIS IS A SUBDIRECTORY. ;WE HAVE STR:<DIRECTORY.SUBDIRECTORY>.
;CONVERT TO STR:<DIRECTORY>SUBDIRECTORY.DIRECTORY
DPB T2,DOTPTR ;REPLACE DOT WITH RIGHT BRACKET
MOVEI T2,"." ;GET A DOT
DPB T2,T1 ;REPLACE RIGHT BRACKET WITH DOT
HRROI T2,[ASCIZ/DIRECTORY/] ;T2/ SOURCE IS THIS STRING
SETZ T3, ;T3/ STOP ON NULL
SOUT ;FORM STR:<DIR>SUBDIR.DIRECTORY
HRROI T2,DIRNAM ;SET UP POINTER TO DIRECTORY
JRST GTFIL3 ;GO GET JFN
;HERE WHEN DIRECTORY IS IN ROOT-DIRECTORY. FORM STR:<ROOT-DIRECTORY>DIR.DIRECTORY
GTFIL2: MOVE T1,ROOTPT ;POINT TO END OF STR:<ROOT-DIRECTORY>
MOVE T2,BRKPTR ;POINT TO LEFT BRACKET
MOVEI T3,^D40 ;DIRECTORY NAME <=39 CHARACTERS
MOVEI T4,">" ;STOP ON RIGHT BRACKET
SOUT ;COPY DIRECTORY NAME
SETOM T3 ;BACK UP POINTER OVER THE BRACKET
IBP T3,T1
MOVEM T3,T1 ;T1/ DESTINATION IS END OF DIRECTORY NAME
HRROI T2,[ASCIZ/.DIRECTORY/] ;T2/ POINTER TO SOURCE
SETZ T3, ;T3/ STOP ON NULL
SOUT ;COPY ".DIRECTORY" TO END OF STRING
HRROI T2,ROOTDR ;POINT TO START OF THIS STRING
JRST GTFIL3 ;GO GET JFN
;T2 POINTS TO FILE SPEC. GET A JFN ON THIS DIRECTORY FILE
GTFIL3: MOVX T1,GJ%PHY!GJ%SHT ;PHYSICAL ONLY, SHORT BLOCK
GTJFN ;GET A JFN
JSHLT ;FAILURE
HRRZM T1,FDJFN ;SAVE JFN
RET
;DO ONE NAME. STARTS WITH FDB FOR ONE NAME. CALLS SCAN7 TO DO ALL GENERATIONS FOR
;ONE EXTENSION. LOOPS THROUGH ALL EXTENSIONS FOR ONE NAME
; T4/OFFSET IN DIRECTORY OF FDB
SCAN3: SKIPN T4
RET
ADDI T4,DIRORG ; GET ABS ADR OF FDB
MOVE T1,T4
;NOTE: REPEATED BELOW
CALL FDBCHK ; MAKE SURE THIS IS A GOOD FDB
CALLRET BADBLK ; IT IS NOT
LOAD T1,FBEXT,(T4) ; GET ADR OF EXT STRING
ADDI T1,DIRORG+1
HRROM T1,DEFEXT
PUSH P,T4
SUB T4,DIRORA ; GET RELATIVE ADR OF FDB
CALL SCAN7
POP P,T4
LOAD T4,FBEXL,(T4) ; STEP TO NEXT EXT
JRST SCAN3
;DO ONE EXTENSION. CALLS BUILD FOR ONE FDB. LOOPS THROUGH ALL VERSIONS.
; T4/OFFSET IN DIRECTORY OF FDB
SCAN7: SKIPN T4
RET
ADDI T4,DIRORG ; GET ABS ADR OF FDB
MOVE T1,T4
CALL FDBCHK ; CHECK THE QUALITY OF THIS FDB
CALLRET BADBLK ; NO GOOD
LOAD T1,FBGEN,(T4) ; GET VERSION #
HRRM T1,DEFVER
PUSH P,T4
CALL BUILD ; DO ONE VERSION
POP P,T4
LOAD T4,FBGNL,(T4) ; STEP TO NEXT GENERATION FDB
JRST SCAN7
;BADBLK - PRINT MESSAGE ABOUT BAD BLOCK IN DIRECTORY
BADBLK: TMSG < in directory >
HRROI T1,DIRNAM ;T1/POINTER TO DIRECTORY NAME
PSOUT ;PRINT DIRECTORY NAME
TMSG <
>
RET
;ROUTINE CALLED FOR EACH FILE--FIND ALL ADDRESSES IN PT'S OF FILE
; T4/ADDRESS OF FDB
BUILD: STKVAR<DSKAD1,FDBCNT,PAGNO>
SKIPN CHKFLF ;RETURN IMMED IF NOT CHECKING FILES
RET
SKIPE T1,.FBADR(T4) ;GET DISK ADDRESS OF INDEX BLOCK
TLNE T1,(FILNB) ;IS IT A NEW FILE?
RET ; NO DISC ADDRESS
SETZM ZSTART ;CLEAR COUNTS OF ERRORS
MOVE T2,[XWD ZSTART,ZSTART+1]
BLT T2,ZEND
SETZM PAGCNT ;INIT COUNT OF FILE PAGES FOR THIS FILE
LOAD T3,FBNPG,(T4) ;GET COUNT IN FDB OF FILE PAGES
MOVEM T3,FDBCNT ;SAVE IT FOR CHECKING LATER
SETOM PAGNN ;INDICATE NOT IN FILE PAGE
MOVE T3,.FBCTL(T4) ;GET FLAGS IN FDB
TXNE T3,FB%LNG ;IS THIS A LONG FILE?
JRST BUILNG ;YES. GO DO THE PAGE TABLE TABLE
MOVX F,MR%PT ;INDICATE THIS IS PAGE TABLE
CALL MRKBTB ;MARK BIT TABLE TO SHOW PAGE USED BY
; INDEX BLOCK
JRST [ AOS NDE ;FAILED. INDICATE BAD ADDRESS FOR PAGE TABLE
JRST BUILD1]
SETZM PAGNN ;INITIALIZE FILE PAGE NUMBER
CALL MRKPT ;MARK BIT TABLE TO SHOW PAGES POINTED
; TO BY THE PAGE TABLE
JRST BUILD1 ;GO PRINT ERRORS IF ANY
;SCAN LONG FILE
; T1/DISK ADDRESS OF PAGE TABLE TABLE
BUILNG: MOVEM T1,DSKAD1 ;SAVE ADDRESS OF PAGE TABLE TABLE
MOVX F,MR%PTT ;INDICATE THIS IS A PAGE TABLE TABLE
CALL MRKBTB ;MARK BIT TABLE TO SHOW PAGE USED BY
; PAGE TABLE TABLE
JRST [ AOS NPTTE ;INDICATE BAD ADDRESS FOR PAGE TABLE TABLE
JRST BUILD1] ;GIVE UP ON THIS FILE
MOVEI T2,PTT ;T2/WHERE TO READ PAGE TABLE TABLE INTO
CALL DSKRED ;READ THE PAGE TABLE TABLE
JRST [ AOS NBPTT ;INDICATE PAGE TABLE TABLE UNREADABLE
AOS NBAD ;INCREMENT COUNT OF ALL ERRORS
JRST BUILD1] ;GIVE UP ON THIS FILE
MOVEI T1,PTT ;T1/ADDRESS OF WHERE TO LOOK FOR PTT
CALL CHKCSM ;CHECK/RESET CHECKSUM
JRST [ AOS NBPTT ;NO GOOD
AOS NBAD
JRST BUILD1]
SETZM PAGNN ;INITIALIZE COUNT OF FILE PAGES
MOVSI P1,-1000 ;P1/(-COUNT,,OFFSET IN PAGE TABLE TABLE)
;LOOP THROUGH ENTRIES IN PAGE TABLE TABLE MARKING BIT TABLE FOR PAGE USED
;BY PAGE TABLE AND PAGES USED BY FILE AS INDICATED BY PAGE TABLE
BUILN1: MOVE T1,PTT(P1) ;GET DISK ADDRESS OF NEXT PAGE TABLE
TLZ T1,(ADRMSK) ;GET STORAGE ADR
JUMPE T1,[MOVEI T1,1000 ;INCREMENT COUNT OF PAGES BY
ADDM T1,PAGNN ; SIZE OF PAGE TABLE
JRST BUILN2] ;GO TO NEXT ENTRY IN PAGE TABLE TABLE
MOVEM T1,PTT(P1)
MOVE T2,PAGNN ;SAVE CURRENT FILE PAGE NUMBER
MOVEM T2,PAGNO
SETOM PAGNN ;INDICATE IN PAGE TABLE
MOVX F,MR%PT ;INDICATE THIS IS A PAGE TABLE
CALL MRKBTB ;MARK BIT TABLE TO SHOW PAGE USED BY PAGE TABLE
JRST [ AOS NBPTTE ;INDICATE BAD ADDRESS IN PAGE TABLE TABLE
MOVE T2,PAGNO ;RESTORE FILE PAGE NUMBER
MOVEM T2,PAGNN
JRST BUILN2] ;GO TO NEXT ENTRY IN PTT
MOVE T2,PAGNO ;RESTORE FILE PAGE NUMBER
MOVEM T2,PAGNN
CALL MRKPT ;MARK BIT TABLE TO SHOW PAGES POINTED
; TO BY PAGE TABLE
BUILN2: SKIPN NIDA ;QUIT IMMED IF SEEN ILLEG ADDRESSES
AOBJN P1,BUILN1 ;GO TO NEXT ENTRY IN PAGE TABLE TABLE
;PAGE TABLE TABLE IS DONE
JRST BUILD1
;HERE WHEN ALL PAGES FOR A FILE HAVE BEEN ASSIGNED AND ERROR COUNTS
;INCREMENTED. FIX PAGE COUNT IF NEEDED AND REPORT SUMMARY OF ERRORS
;IF ANY.
BUILD1: MOVE T2,PAGCNT ;GET LOCAL COUNT OF FILE PAGES
ADDM T2,TOTPGS ;INCREMENT TOTAL FOR ALL FILES
SKIPG T1,NBAD ;DID WE GET ANY ERRORS ON THIS FILE?
JRST [ SKIPE DALIST ;NO. ARE WE SEARCHING?
RET ;YES. DON'T FIX THE PAGE COUNT
CAME T2,FDBCNT ;DOES LOCAL COUNT AGREE WITH THE FDB?
CALL FIXCNT ;NO. FIX IT IN THE FDB
RET]
;PRINT SUMMARY OF ERRORS FOR THIS FILE
TMSG <Summary for file >
CALL PNTFIL ;PRINT THE FILE SPEC
TMSG <
>
;THE COUNTS THAT ARE REPORTED HERE HAVE BEEN INCREMENTED BY MRKPT,
;MRKBTB AND BUILD. THEY WERE CLEARED BY THE BLT IN BUILD AND THUS
;CONTAIN THE ERROR COUNTS FOR THE CURRENT FILE ONLY.
MOVE T3,[XWD 4,12]
SKIPN T2,NDE
JRST BAD0
CALL TTNOUT
TMSG < Faulty page table addresses in FDB
>
BAD0: SKIPN T2,NPTTE
JRST BAD0A
MOVE T3,[4,,12]
CALL TTNOUT
TMSG <Faulty long file page table addresses in FDB
>
;..
;..
BAD0A: MOVE T3,[XWD 4,12]
SKIPN T2,NBPTE
JRST BAD1
CALL TTNOUT
TMSG < Faulty addresses in page table
>
BAD1: SKIPN T2,NBPT
JRST BAD2
MOVE T3,[XWD 4,12]
CALL TTNOUT
TMSG < Page tables unreadable
>
BAD2: SKIPN T2,NBPTTE
JRST BAD2A
MOVE T3,[XWD 4,12]
CALL TTNOUT
TMSG < Faulty addresses in long file page table
>
BAD2A: SKIPN T2,NBPTT
JRST BAD3
MOVE T3,[XWD 4,12]
CALL TTNOUT
TMSG < Long file page tables unreadable
>
BAD3: SKIPN T2,NIDA
JRST BAD4
MOVE T3,[XWD 4,12]
CALL TTNOUT
TMSG < Illegal addresses
>
BAD4: SKIPN T2,NMDA
JRST BAD5
MOVE T3,[XWD 4,12]
CALL TTNOUT
TMSG < Multiply assigned addresses
>
BAD5: SKIPN T2,NSDA
JRST BAD6
MOVE T3,[XWD 4,12]
CALL TTNOUT
TMSG < Search addresses found
>
;..
;..
BAD6: SKIPN T2,NDSKER ;DISK ERRORS?
JRST BAD7 ;NO
MOVE T3,[4,,12]
CALL TTNOUT
TMSG < Disk read errors
>
BAD7: SKIPN T2,NNBT ;PAGES ASSIGNED TO FILES BUT NOT IN BIT TABLE?
JRST BAD8 ;NO
MOVE T3,[4,,12]
CALL TTNOUT
TMSG < File addresses not in bit table
>
BAD8: SKIPN T2,NABAT ;ANY ASSIGNED PAGES THAT ARE BAD?
JRST BAD9 ;NO.
MOVE T3,[4,,12]
CALL TTNOUT ;OUTPUT DISK ADDRESS
TMSG < Assigned pages marked in BAT blocks
>
BAD9: TMSG <- - - - - - -
>
RET
;PNTFIL - PRINT FILE SPEC
PNTFIL: HRROI T1,DIRNAM
PSOUT ;PRINT STR:<DIRECTORY>
MOVE T1,DEFNAM
PSOUT ;PRINT THE FILE NAME
MOVEI T1,"."
PBOUT
MOVE T1,DEFEXT
PSOUT ;PRINT EXTENSION
MOVEI T1,"."
PBOUT
HRRZ T2,DEFVER
MOVEI T1,.PRIOUT
MOVEI T3,^D10
NOUT ;PRINT VERSION
JFCL
RET
;MRKPT - MARK THE BIT TABLE FOR ONE PAGE TABLE
;ACCEPTS:
; T1/DISK ADDRESS OF INDEX BLOCK
; F/MR%PT (PASSED TO MRKBTB)
;RETURNS +1:ALWAYS
;THIS ROUTINE IS CALLED DURING THE BITTABLE, REBUILD, AND SCAN FUNCTIONS.
;GIVEN THE DISK ADDRESS OF A PAGE TABLE (INDEX BLOCK), IT READS THE
;PAGE TABLE AND SCANS THE ADDRESSES IN IT. FOR EACH NON-ZERO ADDRESS
;IT CALLS MRKBTB TO ASSIGN THE PAGE POINTED TO BY THE ADDRESS
MRKPT: PUSH P,T1
MOVEI T2,PT ;T2/STARTING ADDRESS TO READ INTO
CALL DSKRED ;READ INDEX BLOCK
JRST [ AOS NBPT ;INCREMENT COUNT OF UNREADABLE PAGE TABLES
AOS NBAD ;INCREMENT TOTAL COUNT OF ERRORS
POP P,T1 ;RESTORE DISK ADDRESS
RET] ;IGNORE THIS PAGE TABLE
MOVEI T1,PT ;T1/ADDRESS OF PAGE TABLE
CALL CHKCSM ;CHECK/RESET CHECKSUM
JRST [ AOS NBPT ;INCREMENT COUNT OF UNREADABLE PAGE TABLES
AOS NBAD ;INCREMENT TOTAL COUNT OF ERRORS
POP P,T1 ;RESTORE DISK ADDRESS
RET] ;IGNORE THIS PAGE TABLE
;LOOP THROUGH WORDS IN PAGE TABLE
MOVSI P2,-1000 ;P2/(-COUNT,,OFFSET INTO PT)
MRKPT1: MOVE T1,PT(P2) ;GET NEXT ADDRESS FROM PAGE TABLE
TLZ T1,(ADRMSK) ;GET STORAGE ADR
JUMPE T1,MRKPT2 ;SKIP IF ZERO
MOVEM T1,PT(P2) ;SAVE ADDRESS OF PAGE IN FILE
CALL MRKBTB ;ASSIGN PAGE IN BOTH BIT TABLES
AOS NBPTE ;FAILED. INCREMENT COUNT OF BAD ADDRESSES IN PT
MRKPT2: AOS PAGNN ;POINT TO NEXT FILE PAGE
SKIPN NIDA ;QUIT IMMED IF SEEN ILLEG ADDRESSES
AOBJN P2,MRKPT1 ;GO TO NEXT ENTRY
;END OF PAGE TABLE
POP P,T1 ;RESTORE ADDRESS OF INDEX BLOCK
RET
;MRKBTB - MARK THE BIT TABLE FOR ONE PAGE
;ACCEPTS:
; T1/DISK ADDRESS TO MARK IN BIT TABLE
; F/FLAG INDICATING WHAT CALLED THIS ROUTINE (MEANINGFUL ONLY IF
; PAGNN IS NEGATIVE)
;RETURNS +1:DISK ADDRESS BAD
; 1/DISK ADDRESS WITH BITS 0-14 TURNED OFF
; +2:DISK ADDRESS GOOD
; 1/DISK ADDRESS WITH BITS 0-14 TURNED OFF
;THIS ROUTINE IS CALLED DURING THE BITTABLE, REBUILD, AND SCAN FUNCTIONS
;WHEN A PAGE HAS BEEN IDENTIFIED AS IN USE (FILE PAGE, SWAP PAGE, ETC.)
;ACTION DEPENDS ON FUNCTION:
;SCAN - SEE IF THIS ADDRESS IS BEING SEARCHED FOR
;BITTABLE - ASSIGN PAGE IN LOCAL BIT TABLE
;REBUILD - ASSIGN PAGE IN LOCAL AND SYSTEM BIT TABLE
;THIS ROUTINE PRINTS ONE-LINE MESSAGES THAT CONTAIN THE DISK ADDRESS AND
;DESCRIPTION OF HOW THE PAGE IS USED
MRKBTB: TLZ T1,(DSKMSK)
SAVET
STKVAR <ASAVE>
MOVEM T1,ASAVE ;SAVE DISK ADDRESS
SKIPGE PAGNN ;FILE PAGE?
JRST [ AOS OVERHD ;NO. COUNT AS OVERHEAD
JRST MRKBT5]
AOS PAGCNT ;YES. COUNT AS FILE PAGE
MRKBT5: CALL SEEADR ;SEE IF ADDRESS IS MARKED IN BAT BLOCKS
JRST [ MOVX T4,ER%BAT ;INDICATE THIS IS A BAD BLOCK
SOS OVERHD ;PREVIOUSLY COUNTED AS OVERHEAD. PAGE
; IS IN USE
SOS BATCNT ;DECREMENT COUNT OF UNUSED BAD PAGES
JRST BATA] ;GO REPORT IT
MRKBT4: SKIPN T2,DALIST ;AOBJN POINTER TO LIST OF ADDRESSES INPUT
; VIA SCAN COMMAND
JRST MRKBT1 ;NOT SCANNING FOR DISK ADDRESSES
;SCANNING FOR ADDRESSES CONTAINED IN DATAB LIST. SEE IF THIS ADDRESS
;IS IN THE LIST.
CAMN T1,DATAB(T2)
JRST SDA ; ADDRESS IS BEING SEARCHED
AOBJN T2,.+1
AOBJN T2,.-3
RETSKP ;NOT IN THE LIST. DON'T TRY TO MARK BIT TABLE
;DOING BIT TABLE CONSISTENCY CHECK. ASSIGN THIS PAGE IN BOTH BIT TABLES
;T1/SECTOR NUMBER RELATIVE TO START OF STRUCTURE
MRKBT1: CALL DSKASA ;ASSIGN IN LOCAL BIT TABLE
JRST [ TXNE T4,ER%IDA ;FAILED. ILLEGAL ADDRESS?
JRST IDA ;YES. GO REPORT ERROR
TXNE T4,ER%MDA ;NO. PAGE NOT AVAILABLE?
JRST MDA ;YES. GO REPORT ERROR
TMSG <
% DSKASA returned unknown error
>
JRST .+1]
MOVE T1,ASAVE ;T1/SECTOR NUMBER
MOVE T2,STRDEV ;T2/STRUCTURE 0
DSKAS ;TRY TO ASSIGN THE PAGE
RETSKP ;FAILED. GOOD.
;TRIED TO ASSIGN PAGE IN SYSTEM BIT TABLE AND SUCCEEDED. THIS IS AN
;ERROR BECAUSE SYSTEM SHOULD HAVE KNOWN ABOUT THE FILE PAGE
SKIPE REBLDF ;IF REBUILDING, BIT TABLE HAS BEEN INITIALIZED
RETSKP ; SO IGNORE
;..
;..
;ERROR CONDITIONS. T4 CONTAINS ERROR FLAG. IF ERROR WAS ILLEGAL ADDRESS
;OR MULTIPLY ASSIGNED, TAKE NON-SKIP RETURN SO CALLER CAN INCREMENT COUNT
;OF FAULTY ADDRESSES. IF ADDRESS IS MARKED IN BAT BLOCKS, CONTINUE
;AS IF NOTHING HAD HAPPENED.
;PAGE IS NOT ASSIGNED IN SYSTEM BIT TABLE
TMSG <Disk address >
MOVE T2,ASAVE ;T2/SECTOR NUMBER
MOVEI T3,10 ;T3/RADIX
CALL TTNOUT ;PRINT THE SECTOR NUMBER
TMSG < not in bit table >
SETZ T4, ;INDICATE NOT AN ERROR TO AVOID FAILURE RETURN
AOS NNBT ;INCREMENT COUNT OF NOT IN BT'S
JRST MRKBTP
;DISK ADDRESS IS INVALID
IDA: TMSG <Illegal disk address >
MOVE T2,ASAVE ;T2/SECTOR NUMBER
MOVEI T3,10
CALL TTNOUT
AOS NIDA ;INCREMENT COUNT OF ILLEGAL ADDRESS
SETZM WRTLPF ;SUPPRESS LOST-PAGES FILE, ETC.
JRST MRKBTP
;THIS ADDRESS IS BEING SEARCHED FOR VIA SCAN COMMAND.
SDA: TMSG <Found disk address >
MOVE T2,DATAB+1(T2)
MOVEI T3,10
CALL TTNOUT
SETZ T4, ;INDICATE NOT AN ERROR TO AVOID NON-SKIP RETURN
AOS NSDA ;INCREMENT THE COUNT OF ADDRESSES FOUND
JRST MRKBTP
;PAGE WAS ALREADY ASSIGNED.
MDA: TMSG <Multiply assigned disk address >
MOVE T2,ASAVE ;T2/SECTOR NUMBER
MOVEI T3,10
CALL TTNOUT
AOS NMDA ;INCREMENT COUNT OF MULTIPLY ASSIGNED ADDRESSES
SETZM WRTLPF ;SUPPRESS LOST-PAGES FILE, ETC.
JRST MRKBTP
;THIS DISK ADDRESS IS RECORDED IN THE BAT BLOCKS.
BATA: TMSG <Disk address >
MOVE T2,ASAVE ;GET SECTOR NUMBER
MOVEI T3,10 ;T3/OCTAL
CALL TTNOUT ;PRINT THE ADDRESS
TMSG < marked in BAT blocks>
AOS NABAT ;INCREMENT COUNT OF BAD ADDRESSES
JRST MRKBTP ;GO PRINT THE FILE PAGE
;PRINT FILE PAGE WHERE ERROR OCCURRED
MRKBTP: AOS NBAD ;INCREMENT COUNT OF TOTAL ERRORS
SKIPGE T2,PAGNN ;GET PAGE NUMBER
JRST MRKBT2 ;NEGATIVE MEANS NOT A FILE PAGE
TMSG <: File page >
MOVEI T3,10 ;T3/RADIX
CALL TTNOUT ;PRINT PAGE NUMBER
JRST MRKBT3
;NOT A FILE PAGE. F INDICATES WHAT IT IS.
MRKBT2: TXNE F,MR%PT ;IS THIS A PAGE TABLE?
JRST [ TMSG <: Page table> ;PAGE TABLE
JRST MRKBT3]
TXNE F,MR%PTT ;NO. IS IT A PAGE TABLE TABLE?
JRST [ TMSG <: Long file page table>
JRST MRKBT3] ;PAGE TABLE TABLE
TXNE F,MR%SWP ;NO. IS IT SWAPPING SPACE?
JRST [ TMSG <: Swapping space>
JRST MRKBT3]
TXNE F,MR%SPC ;NO. IS IT A SPECIAL BLOCK?
JRST [ TMSG <: Special system blocks>
JRST MRKBT3]
MRKBT3: TMSG <
>
JUMPE T4,RSKP ;IF NOT REALLY AN ERROR, TAKE SKIP RETURN
TXNN T4,ER%BAT ;WAS IT A BAD ADDRESS
RET ;NO. TAKE ERROR RETURN
MOVE T1,ASAVE ;RESTORE SECTOR NUMBER
JRST MRKBT4 ;GO CONTINUE
;FIXCNT - FIX THE COUNT OF FILE PAGES FOR ONE FILE
;ACCEPTS:
; NOTHING IN AC'S, BUT DIRNAM,DEFNAM,DEFEXT,DEFVER MUST BE SET UP
;RETURNS +1:ALWAYS
;CALLED BY BUILD WHEN A FILE'S PAGE COUNT IN THE FDB DISAGREES WITH
;LOCAL COUNT OF DATA PAGES. DOES OPENF AND CLOSF TO FORCE THE UPDATE.
;NOTE THAT THE COUNT WILL NOT BE UPDATED IF ANYONE ELSE HAS THE FILE OPEN
;UNTIL THE LAST CLOSE OCCURS. IN THE CASE OF ROOT-DIRECTORY.DIRECTORY
;AND SOME OTHERS THAT ARE NEVER CLOSED, THE COUNT WILL NOT BE UPDATED
FIXCNT: STKVAR<JFN1>
MOVEI T1,GTJBLK ;T1/ ADDRESS OF GTJFN BLOCK
MOVX T2,GJ%OLD!GJ%PHY ;OLD FILE
HRR T2,DEFVER ;VERSION NUMBER OF THIS FILE
MOVEM T2,.GJGEN(T1) ;(FLAGS,,VERSION NUMBER)
MOVE T2,[.NULIO,,.NULIO] ;NULL DEVICE FOR INPUT AND OUTPUT
MOVEM T2,.GJSRC(T1) ;(INPUT JFN,,OUTPUT JFN)
SETZM .GJDEV(T1) ;NO DEFAULT DEVICE
SETZM .GJDIR(T1) ;NO DEFAULT DIRECTORY
MOVE T2,DEFNAM ;POINTER TO CURRENT FILENAME
MOVEM T2,.GJNAM(T1) ;MAKE THIS THE DEFAULT
MOVE T2,DEFEXT ;POINTER TO CURRENT EXTENSION
MOVEM T2,.GJEXT(T1) ;MAKE THIS THE DEFAULT
SETZM .GJPRO(T1) ;NO DEFAULT PROTECTION
SETZM .GJACT(T1) ;NO DEFAULT ACCOUNT STRING
SETZM .GJJFN(T1) ;NO SPECIFIC JFN
HRROI T2,DIRNAM ;T2/ STR:<DIRECTORY>
GTJFN ;GET A JFN ON THE CURRENT FILE
JRST [ PNTERR (<Unable to fix count for file>,FIXCN1,FILE)]
HRRZS T1 ;T1/JFN WITHOUT FLAGS
MOVEM T1,JFN1 ;SAVE IT
MOVX T2,OF%RD!OF%PDT ;T2/READ ACCESS, DON'T CHANGE ACCESS DATE
OPENF ;OPEN THE FILE
JRST [ MOVE T1,JFN1 ;FAILED. T1/JFN
TXO T2,OF%THW!OF%RD!OF%PDT ;T2/THAWED, READ, DON'T CHANGE DATE
OPENF ;OPEN IT THAWED THIS TIME
JRST [ PNTERR (<Unable to fix count for file>,FIXCN1,FILE)]
JRST .+1] ;SUCCEEDED
MOVE T1,JFN1 ;T1/JFN
MOVEI T4,.FBBYV ;OFFSET TO BE CHANGED
STOR T4,CF%DSP,T1 ;SAVE IT IN T1
MOVX T2,FB%PGC ;T2/MASK FOR PAGE COUNT FIELD
MOVE T3,PAGCNT ;T3/NEW PAGE COUNT TO BE STORED
CHFDB ;PUT CORRECT PAGE COUNT IN FDB
ERJMP [PNTERR (<Unable to fix count for file>,,FILE)
JRST .+1]
MOVE T1,JFN1 ;T1/JFN
CLOSF ;CLOSE THE FILE
JFCL ;IGNORE FAILURE
FIXCN1: RET
;CHECK CHECKSUM IF NEW FORMAT XB'S
; T1/ LOCATION OF XB
CHKCSM: PUSH P,Q1
PUSH P,T1 ;SAVE XB LOCATION
HRRZ T2,T1
ADD T2,[XBCKSM] ;GET EXISTING CHECKSUM FROM XB
MOVEI T1,Q1 ;PUT IT INTO Q1
CALL LDXBD
MOVE T1,0(P)
CALL DOCSM ;COMPUTE CHECKSUM
SETCA Q1, ;SUBTRACT CHECKSUMS (1'S COMPL)
ADD T1,Q1
POP P,0(P)
POP P,Q1
CAME T1,[-1] ;0? (OR -0)
JUMPN T1,[TMSG < Checksum incorrect
>
RET]
JRST RSKP
;COMPUTE CHECKSUM
; T1/ ADDRESS OF PT
DOCSM: MOVSI T4,-1000
SETZ T3, ;COMPUTE CHECKSUM IN C
HRLI T1,T4 ; T1 = 0(T4)
JCRY0 .+1
DOCSM1: MOVE T2,@T1
TLZ T2,(ADRMSK) ;LOOK ONLY AT ADDRESS PART OF WORD
SKIPN T2 ;EMPTY?
HRRZ T2,T4 ;YES, USE INDEX IN CHECKSUM
ADD T3,T2
JCRY0 [AOJA T3,.+1] ;DO END-AROUND CARRY
AOBJN T4,DOCSM1
MOVE T1,T3 ;RETURN CHECKSUM IN T1
RET
;LOAD/STORE DATA IN INDEX BLOCK.
;SINCE THE STORAGE ADDRESS IS ONLY 23 BITS, THE REMAINING PORTION
;OF EACH WORD CAN BE USED TO STORE USEFUL INFORMATION, E.G. A
;CHECKSUM OF THE INDEX BLOCK. THESE ROUTINES PACK AND UNPACK
;THE DATA FROM THE XB USING B0-8 OF SUCCESSIVE WORDS.
; T1/ ADDRESS OF WORD(S)
; T2/ NUMBER OF XB WORDS,,XB ADDRESS + OFFSET
; CALL STXBD/LDXBD
; RETURN +1 ALWAYS, DATA MOVED BETWEEN XB AND C(C(T1))
;STORE DATA INTO INDEX BLOCK
STXBD: HRLI T1,(<POINT 9,0>) ;INIT PTR TO CALLERS DATA
STXBD1: ILDB T3,T1 ;GET BYTE FROM CALLER
DPB T3,[POINT 9,0(T2),8] ;PUT IT IN XB
AOBJN T2,STXBD1 ;INCREMENT THROUGH XB
RET
;LOAD FROM XB
LDXBD: HRLI T1,(<POINT 9,0>) ;INIT PTR TO CALLERS STORAGE
LDXBD1: LDB T3,[POINT 9,0(T2),8] ;GET BYTE FROM XB
IDPB T3,T1 ;PUT IT IN CALLERS STORAGE
AOBJN T2,LDXBD1 ;SCAN THROUGH XB
RET
;ITEMS IN INDEX BLOCK VECTOR
XBCKSM==<-4,,0> ;CHECKSUM--4 WORDS BEGINNING AT 0
DSKRED: PUSH P,T1
MOVE T3,T2
TLZ T1,(ADRMSK)
MOVE T4,STRDEV ;GET STRUCTURE NUMBER
TXO T1,DOP%SN ;SET TO ALL ONES
TXO T1,<FLD .DOPSR,DOP%AT>
MOVEI T2,1000 ;WORD COUNT
DSKOP
SKIPE T1
AOSA NDSKER ;DSK READ ERR
AOS -1(P)
POP P,T1
MOVE T2,T3
RET
DSKWRT: PUSH P,T1
MOVE T3,T2
TLZ T1,(ADRMSK)
TXO T1,<FLD .DOPSR,DOP%AT>
MOVE T4,STRDEV ;GET STRUCTURE NUMBER
TXO T1,DOP%SN ;SET TO -1
MOVX T2,DOP%WR+1000
DSKOP
SKIPE T1
JRST [ AOS NDSKER
TMSG <Disk write error
>
JRST .+1]
POP P,T1
MOVE T2,T3
RET
;FINBTB - CALLED WHEN DONE. PRINTS COUNTS OF FREE AND USED PAGES
;BEFORE AND AFTER THE ASSIGNMENTS
FINBTB: TMSG <
Local count of file pages: >
MOVE T2,TOTPGS ;GET COUNT OF FILE PAGES
MOVEI T3,12 ;DECIMAL RADIX
CALL TTNOUT
TMSG <
Local count of overhead pages: >
MOVE T2,OVERHD ;GET COUNT OF OVERHEAD PAGES
MOVEI T3,12 ;DECIMAL RADIX
CALL TTNOUT ;PRINT THE COUNT
TMSG <
Local count of used pages: >
MOVE P1,LOTRK
SUB P1,HITRK
HRLZS P1
HRR P1,LOTRK ;LOTRK-HITRK ,, LOTRK
SETZ T2,
ADD T2,LOCBTB(P1) ;COUNT FREE PAGES FOR CYLINDER
AOBJN P1,.-1
MOVNS T2 ;NEGATIVE OF TOTAL FREE
MOVE T3,HITRK
IMUL T3,PAGCYL ;GET TOTAL PAGES
ADD T2,T3 ;TOTAL USED
ADD T2,BATCNT ;ADD PAGES THAT ARE MARKED BAD BUT NOT
; USED BY A FILE
MOVEI T3,12
CALL TTNOUT ;PRINT LOCAL COUNT OF USED PAGES
TMSG <
>
SKIPE REBLDF ;REBUILDING BIT TABLE?
JRST FINBT1 ;YES. NEXT COUNT IS MEANINGLESS
TMSG<
System count before CHECKD: >
MOVE T2,ZUSED ;SYSTEM'S COUNT OF USED AT BEGINNING
MOVEI T3,12
CALL TTNOUT ;PRINT ORIGINAL COUNT
FINBT1: TMSG <
System count after CHECKD: >
MOVE T1,STRDEV ;DEVICE DESIGNATOR FOR STR
GDSKC ;GET SYSTEM COUNTS
MOVE T2,T1 ;GET COUNT OF USED
CALL TTNOUT ;PRINT CURRENT COUNT
TMSG <
>
;GENERATE LOST PAGES LIST. MAP SYSTEM BIT TABLE AND COMPARE WITH
;LOCALLY GENERATED VERSION. OUTPUT DIFFERENCES.
; ..
SKIPN REBLDF ;ARE WE REBUILDING THE BIT TABLE?
JRST FNDLS8 ;NO.
MOVX T1,DA%WRT ;T1/WRITE THE BIT TABLE
MOVE T2,STRDEV ;T2/STRUCTURE 0
DSKAS ;COPY PRIVATE COPY OF BIT TABLE TO FILE
JRST [ PNTERR(<Failed to write bit table file>)
JSERR
RET]
RET ;SUCCESS. DON'T DO THE REST
;HERE WHEN NOT REBUILDING THE BIT TABLE. GET A JFN ON BIT TABLE FILE,
;OPEN IT AND MAP IT TO OUR ADDRESS SPACE
FNDLS8: PUSH P,P1 ;SAVE AC
HRROI T2,[ASCIZ /<ROOT-DIRECTORY>DSKBTTBL/]
CALL ADDSTR ;ADD STRUCTURE NAME
MOVX T1,GJ%OLD!GJ%SHT!GJ%PHY
GTJFN ;GET JFN ON BIT TABLE FILE
JRST [ PNTERR(<GTJFN failure for <ROOT-DIRECTORY>DSKBTTBL>)
RET]
MOVEM T1,BTBJFN ;SAVE THE JFN
MOVEI T2,OF%RD+OF%THW ;T1/READ ACCESS, THAWED
OPENF ;OPEN THE BIT TABLE FILE
JRST [ PNTERR(<OPENF failure for <ROOT-DIRECTORY>DSKBTTBL>)
RET]
HRLZ T1,BTBJFN ;SOURCE (PAGE 0 OF BIT TABLE FILE)
MOVE T2,[.FHSLF,,SYSBTB/PGSIZ] ;DESTINATION (SYSBTB AREA OF THIS FORK)
MOVE T3,BTBPGS ;NUMBER OF PAGES IN FILE
TXO T3,PM%CNT+PM%RD+PM%CPY ;MAP WITH COPY-WRITE
PMAP ;MAP BIT TABLE FILE TO CORE STARTING AT SYSFCT
SETZM OUTJFN ;NO FILE YET
SETZM LOSTOT ;INIT COUNT OF LOST PAGES
MOVN P1,HITRK ;SETUP TO SCAN ALL TRACKS
HRLZS P1
;LOOP THROUGH PAGES IN BIT TABLE, COMPARING WITH LOCAL COPY. REPORT
;INCONSISTENCIES AND FIX WHERE NECESSARY
FNDLS1: MOVE T1,LOCBTB(P1) ;GET OUR COUNT
CAME T1,SYSBTB(P1) ;AGREES WITH SYSTEM?
JRST [ CALL FNDLS2 ;NO, FIGURE OUT DIFFERENCE
JRST FNDLS1] ;TRY AGAIN
AOBJN P1,FNDLS1 ;DO ALL TRACKS
; ..
;ALL CYLINDERS HAVE BEEN CHECKED. WRITE FILE OF LOST PAGES IF THERE
;ARE ANY. NOTE THAT WRITING IS SUPPRESSED IF ERRORS HAVE OCCURRED.
; ..
SKIPG LOSTOT ;ANY LOST PAGES?
JRST [ TMSG <There are no lost pages.
> ;NO. DON'T CREATE LOST-PAGES FILE
JRST FNDLSX]
;OPEN A FILE AND DUMP LOST PAGES LIST
TMSG <There are >
MOVE T2,LOSTOT
MOVEI T3,^D10 ;OUTPUT IT IN DECIMAL
CALL TTNOUT
TMSG < lost pages
>
SKIPN WRTLPF ;WRITE FILE?
JRST [ TMSG <%Suppressed writing of lost pages file , too many errors
>
SKIPE JOBNO ;SKIP IF JOB 0
SKIPN STRMNT ; OR NO MOUNTED STR
JRST FNDLSX ;THEN DONE
TMSG <% Warning -- structure still mounted with exclusive access
so that errors may be fixed.
>
SETZM STRMNT ;CLEAR FLAG
JRST FNDLSX] ;FINISH UP
HRROI T1,ATMBUF ;BUILD FILESPEC HERE
HRROI T2,STRHOM ;START WITH STR NAME
MOVEI T3,0
SOUT
MOVEI T2,"-"
IDPB T2,T1
HRROI T2,[ASCIZ /LOST-PAGES.BIN/]
SOUT ;COMPLETE SPEC
MOVX T1,GJ%FOU!GJ%SHT!GJ%PHY
HRROI T2,ATMBUF ;FILESPEC TEXT PNTR
GTJFN ;GET A JFN FOR LOST PAGES FILE
JRST [ PNTERR(<GTJFN failure for lost pages file>,FNDLS9)]
MOVEM T1,OUTJFN ;SAVE JFN FOR LOST PAGES FILE
MOVE T2,[44B5+OF%WR] ;T2/36-BIT BYTES, WRITE ACCESS
OPENF ;OPEN IT
JRST [ PNTERR(<Failed to open lost pages file>,FNDLS9)]
TMSG<
Addresses are in file >
MOVEI T1,.PRIOU
MOVE T2,OUTJFN ;HAVE OUTPUT FILE?
MOVX T3,1B2+1B5+1B8+1B11+1B14+1B35
JFNS ;PRINT NAME
TMSG <
>
CALL LPFWRT ;WRITE THE HEADER
MOVE T1,OUTJFN ;THE DESTINATION
MOVE T2,[POINT 36,LOSBUF] ;POINT TO LIST
MOVE T3,LOSTOT ;GET NUMBER OF LOST PAGES
CAILE T3,MAXLOS ;MORE THAN THE BUFFER SIZE?
MOVEI T3,MAXLOS ;YES, DON'T WRITE MORE THAN WAS REMEMBERED
MOVN T3,T3 ;MAKE NEGATIVE
SOUT ;WRITE THE FILE
ERJMP [PNTERR (<Output error or quota exceeded>,FNDLS9)]
MOVE T1,OUTJFN
CLOSF
JFCL
JRST FNDLSX
FNDLS9: TMSG <
?File was not written
>
;UNMAP THE BIT TABLE AND CLOSE THE FILE
FNDLSX: SETO T1,
MOVE T2,[.FHSLF,,SYSBTB/PGSIZ]
MOVE T3,BTBPGS ;NUMBER OF PAGES
TXO T3,PM%CNT
PMAP ;UNMAP SYSTEM BIT TABLE PAGES
MOVE T1,BTBJFN
CLOSF
JFCL
POP P,P1 ;RESTORE AC
RET
;FIND DIFFERENCE IN BITS, COMPUTE CORRESPONDING ADDRESS
FNDLS2: HRRZ T4,P1 ;GET TRACK NUMBER
IMUL T4,BTWCYL ;COMPUTE INDEX TO BIT TABLE
ADD T4,BTBTOP ;POINT INTO BOTTOM HALF
MOVN T1,BTWCYL ;GET NUMBER OF BIT WORDS PER CYLINDER
HRL T4,T1 ;T4/(-COUNT,,T1DDRESS OF BIT WORD)
FNDLS4: MOVE T1,LOCBTB(T4) ;GET OUR BIT WORD
XOR T1,SYSBTB(T4) ;GET DIFFERENCE
JFFO T1,FNDLS3 ;JUMP IF HAVE A DIFFERENCE
AOBJN T4,FNDLS4 ;DIFFERENCE NOT IN THAT WORT4, TRY NEXT
;HERE WHEN THE LOCAL AND SYSTEM BIT TABLES DISAGREE IN FREE PAGE COUNT FOR
;A TRACK AND EITHER
; 1) ALL THE BIT WORDS FOR THAT CYLINDER AGREE
; OR
; 2) ONE OR MORE PAGES ARE MARKED AS ASSIGNED IN THE LOCAL BIT AND
; FREE IN THE SYSTEM BIT TABLE
;NOTE THAT THE LATTER SHOULD NOT OCCUR SINCE IT SHOULD HAVE PRODUCED A
;'NOT IN BIT TABLE' MESSAGE EARLIER AND BEEN CORRECTED.
;IF PAGES ARE MARKED AS FREE IN THE LOCAL TABLE AND ASSIGNED IN THE SYSTEM
;TABLE, THEY WILL BE IDENTIFIED AS LOST PAGES
FNDLS7: TMSG <?Bit tables inconsistent at cylinder >
HRRZ T2,P1 ;GET CYLINDER NUMBER
MOVEI T3,10 ;T3/OCTAL
CALL TTNOUT ;PRINT THE CYLINDER NUMBER
MOVE T1,LOCBTB(P1) ;COPY THE LOCAL (PRESUMED CORRECT) COUNT
MOVEM T1,SYSBTB(P1) ; TO THE SYSTEM COUNT. NOTE: DOES NOT CHANGE
; THE COPY ON THE DISK
TMSG <
>
RET
FNDLS3: MOVSI T1,(1B0) ;GET BIT
MOVN T3,T2
LSH T1,0(T3)
TDNE T1,SYSBTB(T4) ;BIT WAS OFF IN SYSTEM (PAGE ASSIGNED)?
JRST FNDLS7 ;NO. PAGE SHOULD HAVE BEEN ASSIGNED
IORM T1,SYSBTB(T4) ;NOTE PAGE NOW NOT ASSIGNED
AOS SYSBTB(P1) ;ADJUST COUNT
HRRZ T1,P1 ;GET TRACK NUMBER
IMUL T1,SECCYL ;GET SECTOR COUNT
HLRE T3,T4 ;GET INDEX TO BIT TABLE
ADD T3,BTWCYL
IMULI T3,^D36 ;COMPUTE PAGE WITHIN TRACK
ADD T2,T3
IMUL T2,SECPAG ;COMPUTE SECTOR WITHIN TRACK
ADD T1,T2 ;DSKADR = TRACK ADR + SEC WITHIN TRK
CALL SEEADR ;SEE IF A BAT BLOCK
RET ;YES. DONT PUT IT IN LOST FILE
AOS T2,LOSTOT ;COUNT IT
CAILE T2,MAXLOS ;STILL ROOM?
JRST [ HRROI T1,[ASCIZ /
?Lost pages buffer full, further lost pages will be ignored.
/]
CAIN T2,MAXLOS+1 ;FIRST TIME?
PSOUT ;YES. TELL HIM
RET] ;AND GIVE UP
MOVEM T1,LOSBUF-1(T2) ;STORE LOST PAGE
RET
;ROUTINE TO SEE IF A DISK ADDRESS IS A BAT BLOCK
; T1/ DISK ADDRESS
;
;RETURUNS +1: A BAT BLOCK
; +2: NOT A BAT BLOCK
SEEADR: PUSH P,T3 ;SAVE T3
PUSH P,T1 ;SAVE T1
PUSH P,T2
IDIV T1,SECCYL ;FIND THE NUMBER OF CYL'S
IMUL T1,LPPCYL ;FIND OFFSET
POP P,T2 ;RESTORE T2
ADD T1,0(P) ;GET THE REAL DISK ADDRESS
MOVEI T3,BPRBLK ;START OF THE PAIRS
SEEIF: CAMN T3,SVEND ;AT THE END?
JRST [ POP P,T1 ;YES. RESTORE T1
POP P,T3 ;RESTORE T3
AOS (P) ;BUMP RETURN
RET] ;AND RETURN GOOD
CAML T1,0(T3) ;NO. WITHIN RANGE?
CAMLE T1,1(T3) ;STILL?
SKIPA ;IS NOT IN RANGE
JRST [ POP P,T1 ;RESTORE T1
POP P,T3 ;RESTORE T3
RET] ;RETURN
ADDI T3,2 ;NEXT PAIR
JRST SEEIF ;GO SEE IF THE NEXT PAIR IN ONE
;OUTPUT NUMBER IN B TO TERMINAL
; 2/NUMBER
; 3/RADIX
TTNOUT: MOVEI T1,101
NOUT
JFCL
RET
;READ LINE INTO LINE BUFFER
; T1/ JFN FROM WHICH TO READ
RDLIN: PUSH P,Q1
HRLZ T4,T1 ;T4=INJFN,,OUTJFN
HRRI T4,.PRIOU
MOVEI T1,T2 ;T1=ADR OF PARAMETER BLOCK
MOVEI T2,4 ;B=COUNT OF PARAMETERS
MOVSI T3,(RD%BRK+RD%RAI+RD%BEL+RD%JFN) ;C=FLAGS, BREAK ON EOL AND USE JFNS
HRROI Q1,LINBUF ;E=PTR TO LINE BUFFER
MOVEI Q2,NLINB*5 ;F=MAX BYTE COUNT
TEXTI
JSHLT
TLNN T3,(RD%BTM) ;TERMINATED PROPERLY?
JFCL ;NO, MUST BE END OF FILE
MOVE T1,Q1 ;RETURN UPDATED BFR PTR
POP P,Q1
RET
;GET YES/NO ANSWER FROM TERMINAL. C(T1) := PROMPT STRING
YESNO: STKVAR <ANSWER,QUEST>
MOVEM T1,QUEST ;SAVE FOR ERROR
YESNO1: MOVE T1,QUEST ;GET PROMPT STRING
CALL CMDINI ;INIT CMD AND PROMPT
MOVEI T1,[FLDDB.(.CMKEY,,YESNOT)]
CALL COMNDX ;GET RESPONSE
ERROR YESNO1,<Invalid response>
MOVEM T2,ANSWER ;SAVE ANSWER
CALL CMDEOL ;GRNTEE CR
JRST YESNO1 ;ERROR
MOVE T2,ANSWER ;PICKUP RESPONSE
HRRE T1,0(T2) ;RETURN -1 FOR YES, 0 FOR NO
RET
YESNOT: 2,,2 ;COUNT OF ENTRIES
TB (0,NO)
TB (-1,YES)
;ROUTINES TO CHECK CONSISTENCY OF DIRECTORY AND FDB'S
;ROUTINE TO CHECK THE CONSISTENCY OF THE HEADER ON THE FIRST DIR PAGE
;ASSUMES DIR IS MAPPED
;ACCEPTS IN T1/ DIR NUMBER
; CALL DR0CHK
;RETURNS +1: HEADER IS SCREWED UP
; +2: OK
;DOES NOT SAVE TEMPORARY ACS
DR0CHK: MOVE T4,DIRORA ;GET BASE ADR OF MAPPED DIR AREA
LOAD T2,DRNUM,(T4) ;GET DIR NUMBER
CAME T1,T2 ;DO THE DIRECTORY NUMBERS MATCH?
JRST DR0CHB ;NO
LOAD T2,DRTYP,(T4) ;GET BLOCK TYPE
CAIE T2,.TYDIR ;IS BLOCK TYPE CORRECT?
JRST DR0CHB ;NO
LOAD T2,DRRPN,(T4) ;GET RELATIVE PAGE #
JUMPN T2,DR0CHB ;MUST BE 0
LOAD T2,DRSTP,(T4) ;GET TOP OF SYMBOL TABLE
SOS T2 ;GET LAST WORD USED
LSH T2,-PGSFT ;TURN IT INTO PAGE #
CAIL T2,NDIRPG ;WITHIN BOUNDS?
JRST DR0CHB ;NO
LOAD T2,DRFFB,(T4) ;GET ADR OF FIRST FREE BLOCK
TRZ T2,777 ;IT MUST POINT ONTO THIS PAGE
JUMPN T2,DR0CHB
LOAD T1,DRNAM,(T4) ;NOW CHECK NAME BLOCK
JUMPE T1,DR0CH1 ;DONT WORRY IF NO NAME
CALL NAMCHK ;MAKE SURE THIS IS A NAME BLOCK
RET ;NO
DR0CH1: LOAD T1,DRPSW,(T4) ;GET PASSWORD POINTER
JUMPE T1,DR0CH2 ;COULD BE 0
CALL NAMCHK ;CHECK BLOCK TYPE
RET ;FAILED CHECK
DR0CH2: RETSKP ;EVERYTHING IS IN ORDER
DR0CHB: TMSG <DR0CHK: Illegal format for page 0>
RET
;FDBCHK - ROUTINE TO CHECK AN FDB
;ACCEPTS IN T1/ ABSOLUTE ADR OF FDB
; CALL FDBCHK
;RETURNS +1: BAD FDB
; +2: FDB OK
;ALL ACS ARE SAVED AND RESTORED
FDBCHK: SAVET ;SAVE ALL ACS USED
STKVAR <FDBCHA,FDBCHF>
MOVEM T1,FDBCHA ;SAVE ADR OF FDB
CALL ADRCHK ;CHECK THIS ADDRESS
JRST FDBBAD ;NOT GOOD
LOAD T2,FBTYP,(T1) ;GET BLOCK TYPE
LOAD T3,FBLEN,(T1) ;GET LENGTH OF BLOCK
CAIL T3,.FBLN0 ;MUST BE GREATER THAN GROUND 0 LENGTH
CAIE T2,.TYFDB ;BLOCK TYPE MUST BE "FDB"
JRST FDBBAD ;BAD FDB
LOAD T1,FBNAM,(T1) ;GET POINTER TO NAME STRING
JUMPE T1,FDBBAD ;MUST ALWAYS BE SET UP
CALL NAMCHK ;CHECK NAME
RET ;BAD
MOVE T1,FDBCHA ;GET BACK FDB ADR
LOAD T1,FBEXT,(T1) ;GET POINTER TO EXT STRING
JUMPE T1,FDBCH2 ;MIGHT NOT BE SET UP YET
CALL EXTCHK ;CHECK EXT BLOCK
RET ;BAD
FDBCH2: MOVE T1,FDBCHA ;GET FDB ADR AGAIN
LOAD T1,FBACT,(T1) ;GET POINTER TO ACCOUNT STRING
JUMPLE T1,FDBCH3 ;SEE IF THERE IS AN ACCOUNT STRING
CALL ACTCHK ;YES, CHECK ITS BLOCK TYPE
RET ;BAD
FDBCH3: MOVE T1,FDBCHA ;GET BACK FDB ADDR
LOAD T2,FBVER,(T1) ;GET VERSION #
CAIGE T2,1 ;VER #1 OR LATER?
JRST FDBCH6 ;OLDER - JUST EXIT
LOAD T1,FBLWR,(T1) ;GET LAST WRITER STRING
JUMPE T1,FDBCH5 ;IGNORE OF NONE
CALL UNSCHK ;CHECK ITS BLOCK TYPE
RET ;BAD
FDBCH5: MOVE T1,FDBCHA ;FDB ADDRS AGAIN
LOAD T1,FBAUT,(T1) ;GET AUTHOR STRING
JUMPE T1,FDBCH6 ;ALL DONE IF NONE
CALL UNSCHK ;CHECK ITS BLOCK TYPE
RET ;BAD
FDBCH6: RETSKP ;FDB LOOKS OK
FDBBAD: TMSG <FDBBAD: Illegal format FDB>
RET
;ROUTINE TO CHECK A NAME BLOCK
;ACCEPTS IN T1/ RELATIVE ADR OF NAME BLOCK
; CALL NAMCHK
;RETURNS +1: BAD BLOCK TYPE
; +2: OK
;ALL ACS SAVED AND RESTORED
NAMCHK: SAVET ;SAVE ALL ACS
ADD T1,DIRORA ;MAKE ADDRESS ABSOLUTE
CALL ADRCHK ;CHECK THIS ADDRESS
JRST NAMBAD ;NO GOOD
LOAD T2,NMTYP,(T1) ;GET BLOCK TYPE
LOAD T3,NMLEN,(T1) ;GET LENGTH
CAIL T3,2 ;MUST BE AT LEAST 2 WORDS LONG
CAIE T2,.TYNAM ;AND MUST BE A NAME BLOCK
JRST NAMBAD ;LOSE
RETSKP ;NAME BLOCK OK
NAMBAD: TMSG <NAMBAD: Illegal format for name block>
RET
;ROUTINE TO CHECK AN EXTENSION BLOCK
;ACCEPTS IN T1/ RELATIVE ADR OF EXTENSION BLOCK
; CALL EXTCHK
;RETURNS +1: BAD BLOCK
; +2: OK
;SAVES AND RESTORES ALL ACS
EXTCHK: SAVET
ADD T1,DIRORA ;MAKE ADDRESS ABSOLTE
CALL ADRCHK ;SEE IF ADR IS GOOD
JRST EXTBAD ;NO GOOD
LOAD T2,EXTYP,(T1) ;GET TYPE
LOAD T3,EXLEN,(T1) ;AND LENGTH
CAIL T3,2 ;LENGTH MUST BE AT LEAST 2
CAIE T2,.TYEXT ;EXTENSION TYPE OK?
JRST EXTBAD ;NO GOOD
RETSKP ;OK
EXTBAD: TMSG <EXTBAD: Illegal format for extension block>
RET
;ROUTINE TO CHECK AN ACCOUNT STRING BLOCK
;ACCEPTS IN T1/ RELATIVE ADR OF ACCOUNT STRING BLOCK
; CALL ACTCHK
;RETURNS +1: BAD ACCOUNT BLOCK
; +2: OK
;SAVES AND RESTORES ALL ACS
ACTCHK: SAVET
ADD T1,DIRORA ;GET ABS ADR
CALL ADRCHK ;CHECK ADR
JRST ACTBAD ;BAD ADR
LOAD T2,ACTYP,(T1) ;GET BLOCK TYPE
LOAD T3,ACLEN,(T1) ;AND LENGTH
CAIL T3,3 ;MUST BE AT LEAST 3 WORDS LONG
CAIE T2,.TYACT ;ACCOUNT BLOCK TYPE?
JRST ACTBAD ;NO
RETSKP ;OK
ACTBAD: TMSG <ACTBAD: Illegal format for account block>
RET
;ROUTINE TO CHECK A USER NAME STRING BLOCK
;ACCEPTS IN T1/ RELATIVE ADR OF NAME STRING BLOCK
; CALL UNSCHK
;RETURNS +1: BAD USER NAME BLOCK
; +2: OK
;SAVES AND RESTORES ALL ACS
UNSCHK: SAVET
ADD T1,DIRORA ;GET ABS ADDR
CALL ADRCHK ;CHECK ADDR
JRST UNSBAD ;BAD ADDRS
LOAD T2,UNTYP,(T1) ;GET BLOCK TYPE
LOAD T3,UNLEN,(T1) ; AND LENGTH
CAIL T3,3 ;MUST BE AT LEAST 3
CAIE T2,.TYUNS ;USER NAME BLOCK TYPE?
JRST UNSBAD ;SOMETHING WRONG
RETSKP ;GIVE GOOD RETURN
UNSBAD: TMSG <UNSBAD: Illegal format for user name block>
RET
;ROUTINE TO CHECK THAT AN ADR IS WITHIN THE DIR BOUNDS
;ACCEPTS IN T1/ ABS ADR TO BE CHECKED
; CALL ADRCHK
;RETURNS +1: ILLEGAL ADR
; +2: OK
ADRCHK: MOVE T2,DIRORA ;GET UPPER BOUNDS
ADD T2,[NDIRPG*PGSIZ]
CAML T1,DIRORA ;ABOVE LOWER LIMIT?
CAML T1,T2 ;AND BELOW UPPER LIMIT?
RET ;NO
RETSKP ;YES, ADR IS OK
;CALLED AT STARTUP AND EXIT. CLOSE ALL FILES, RELEASE ALL JFN'S, CLEAR
;DEFAULT FILESPEC
RESET: MOVNI T1,1
CLOSF ;CLOSE ALL OPEN FILES
JFCL
MOVE T1,[CZ%NCL+.FHSLF]
CLZFF ;RELEASE ALL JFNS
SETZM DEFVER
MOVE T1,[XWD DEFVER,DEFVER+1]
BLT T1,DEFEXT+4
SETZM PSFLG ;RESET PS FLAG
RET
DSPINT: REPEAT ^D36,<
CALL BADINT>
;USER TYPED CTRL/A
SUMINT: SKIPN DIRNUM ;ONLY IF ACTUALLY DOING SOMWTHING
DEBRK
PUSH P,T1
PUSH P,T2
PUSH P,T3
TMSG <Working on directory >
MOVEI T1,101
MOVE T2,DIRNUM
DIRST
JFCL
TMSG <
>
POP P,T3
POP P,T2
POP P,T1
DEBRK
BADINT: PUSH P,T1
PUSH P,T2
PUSH P,T3
TMSG <
Unexpected interrupt, channel >
HRRZ T2,-3(P) ;GET PC OF DISPATCH IN DSPINT
SUBI T2,DSPINT+1 ;MAKE RELATIVE
MOVEI T1,.PRIOU
MOVEI T3,^D8
NOUT ;TYPE CHANNEL NUMBER
JFCL
TMSG <
>
POP P,T3
POP P,T2
POP P,T1
POP P,0(P)
DEBRK ;IGNORE IT
;USER TYPED CTRL/C
CONTC: SKIPE REBLDF ;REBUILDING BIT TABLE?
JRST NOCNTC ;YES - SPECIAL WARNING
CALL DISMNT ;NO - DISMOUNT STR IF ANY
TMSG <^C
>
JRST QUIT
NOCNTC: PUSH P,T1 ;SAVE AN AC
TMSG <% Cannot interrupt bit table rebuild, ignored ...
>
POP P,T1
DEBRK
END <4,,ENTVEC>