TITLE FRECOR -- Program to figure out where all the Free Core went SUBTTL C.D.O'Toole/CDO 24-Feb-80 ;THIS SOFTWARE IS FURNISHED UNDER A LICENSE AND MAY ONLY BE USED ; OR COPIED IN ACCORDANCE WITH THE TERMS OF SUCH LICENSE. ;COPYRIGHT (C) 1979,1980 BY DIGITAL EQUIPMENT CORPORATION SEARCH MACTEN, UUOSYM SALL ;VERSION STUFF FCREDT==1 ;EDIT NUMBER FCRVER==703 ;MAJOR VERSION FCRMIN==0 ;MINOR VERSION FCRWHO==0 ;WHO LAST EDITTED LOC 137 VRSN. FCR RELOC ;CHANNELS XPN==0 ;FOR READING CRASHES ;AC DEFINITIONS F==0 ;A FLAG REG FL.EOL==1B0 ;END OF LINE SEEN FL.ETX==1B1 ;END OF PHYSICAL LINE SEEN FL.RSC==1B2 ;HAVE GETONE USE RESCAN LAST CHARACTER FL.UPZ==1B3 ;^Z TYPED, EXIT AFTER COMMAND T1==1 ;TEMPORARY ACS FOR ANY SUBROUTINE T2==2 T3==3 T4==4 T5==5 CH==6 ;CHARACTER HOLDER UU==7 ;FOR LUUO HANDLER UA==10 ;HOLDS LUUO EFFECTIVE ADDRESS J==11 ;HOLDS JOB NUMBER FOR LOOPS P1==12 ;PRESERVED ACS FOR ANY COMMAND PROCESSOR P2==13 P3==14 P4==15 P5==16 P==17 .PSECT CODE ;START CODE PSECT AT FYSORG SUBTTL Macros and other stuff DEFINE FORMAT(A),< ..N==0 IRP A,< IFN ..N, IFE ..N&1,,> IFN ..N&1, ..N==..N+1 > LIST SALL > DEFINE TEXT.(A), DEFINE GTTAB(ENTRY),< MOVE T1,[ENTRY] XLIST PUSHJ P,GTBSPY HALT . LIST SALL > OPDEF DEC [001000,,0] ;OUTPUT DECIMAL NUMBER OPDEF OCT [002000,,0] ;OUTPUT OCTAL NUMBER OPDEF SIX [003000,,0] ;OUTPUT SIXBIT VALUE OPDEF PER [004000,,0] ;OUTPUT FRECOR NUMBERS AS PERCENT OPDEF CRLF [005000,,0] ;DO A CRLF OPDEF OCT4 [006000,,0] ;OUTPUT OCTAL * 4 OPDEF GTTO [007000,,0] ;GETTAB VALUE IN OCTAL OPDEF GTTD [010000,,0] ;GETTAB VALUE IN DECIMAL OPDEF GTTA [011000,,0] ;GETTAB VALUE AS ASCII WORD OPDEF GTTD2 [012000,,0] ;GETTAB VALUE, DECIMAL, 2 DIGITS DEFINE MSYM(NAME,VALUE), MSYM MONITR,0 ;SYMBOLIZE LOCATION 0 OF THE MONITOR MSYM NUMTAB,410 ;WHERE .GTSLF LIVES MSYM DEVNAM,0 ;SIXBIT DEVICE NAME IN DDB MSYM DEVSER,3 ;LINK TO NEXT DDB MSYM DEVMOD,4 ;DEVICE MODE WORD MSYM DEVXTR,13 ;POINTER TO CDT IF A MPX DDB MSYM STRNAM,0 ;NAME OF STRUCTURE MSYM STRSYS,1 ;LH LINK TO NEXT STRUCTURE MSYM STRUNI,2 ;LH LINKS TO FIRST UNIT IN STRUCTURE MSYM UNINAM,0 ;NAME OF UNIT MSYM UNISTR,4 ;CONTINUE UNITS IN STRUCTURE MSYM UNISPU,50 ;SPT SIZE IN THIS WORD MSYM UNIWPS,50 ;SAT SIZE IN IT TOO MSYM UNISPT,102 ;LINK TO SPT MSYM UNISAB,53 ;LINK TO SAB RING MSYM SABRNG,0 ;LINK TO NEXT SAB IN RING MSYM PTRSYS,0 ;LINK TO NEXT PTR COPY BLOCK MSYM .LBNHS,0 ;POINTER TO NEXT ENQ/DEQ LOCK BLOCK MSYM .LBLEN,1 ;L.H. = LENGTH OF THIS LOCK BLOCK MSYM .LBNQ,2 ;POINTER TO FIRST ENQ/DEQ QUEUE BLOCK MSYM .LBNMS,7 ;L.H. = LENGTH OF MASK BLOCK MSYM .QBNQ,2 ;POINTER TO NEXT ENQ/DEQ QUEUE BLOCK MSYM .QBMSK,6 ;POINTER TO MASK BLOCK FOR THIS Q-BLOCK MSYM .CBNHB,0 ;POINTER TO NEXT CACHE BLOCK MSYM .CBNAB,2 ;POINTER TO NEXT ACTIVE CACHE BLOCK MSYM .CBDAT,6 ;ADDRESS OF CACHED BLOCK MSYM .CBLEN,10 ;LENGTH OF A CACHE BLOCK MSYM .CTNXT,2 ;POINTER TO NEXT CONTEXT BLOCK MSYM .CTBPR,42 ;BEGINNING OF PARAMETER AREA MSYM .CXSCX,2 ;POINTER TO SAVED CONTEXT MSYM .CXPIA,43 ;POINTER TO SAVED JBTPIA MSYM .CTSIZ,200 ;SIZE OF A CONTEXT BLOCK MSYM AHBNXT,0 ;POINTER TO NEXT ALLOCATION HEADER BLOCK MSYM AHBAEB,14 ;ALLOCATION HEADER EXTENT BLOCK POINTER MSYM AEBNXT,0 ;POINTER TO NEXT EXTENT BLOCK MSYM AEBBMP,5 ;BITMAP TO EXTENT MSYM ETDOBK,51 ;DTE OUTPUT BUFFER MSYM ETDIBK,52 ;DTE INPUT BUFFER MSYM UBLSIZ,223 ;SIZE OF DTE BUFFER MINUS HEADER MSYM MS.MEM,<3,,0> ;SECTION FOR PAGTAB/MEMTAB ;SYMBOLS NOT GETTAB'ABLE PDBLEN==110 ;WORDS IN A PDB DSKDDS==66 ;WORDS IN A DISK DDB MPXLEN==23 ;WORDS IN A MPX DDB SPROTO==36 ;WORDS IN A MAG TAPE LABEL DDB STRLEN==27 ;WORDS IN STR DATA BLOCK SPTFIR==0 ;SPT OVERHEAD SABBIT==5 ;SAB OVERHEAD LNMLEN==4 ;WORDS IN A LOGICAL NAME TABLE PTHLEN==5+2 ;WORDS IN A PATH BLOCK PTRCOR==3*4 ;WORDS IN A UPDATE FILE POINTER COPY BLOCK NWSCTX==30 ;WORDS IN A SAVED CONTEXT BLOCK .PDSCX==37 ;WORD IN PDB THAT POINTS TO CONTEXT BLOCK .PDSAC==76 ;FIRST CONTEXT .PDCTC==77 ;CURRENT CONTEXT DVDSK==200000 ;BIT IN DEVMOD FOR DSK DEVICE SHRSEG==200000 ;BIT IN JBTSTS FOR A SEGMENT SAYING SHARABLE QBSIZE==7 ;SIZE OF ENQ/DEQ QUEUE BLOCK ;PAGTAB DEFINITIONS PAGTAB==374000 ;WHERE IT LIVES (ON KS'S ANYWAY) PT.FRE==400000 ;ON THE FREE LIST PT.LPH==200000 ;LOCKED PHYSICALLY CONTIGUOUS PT.LEV==100000 ;LOCKED IN EVM PT.LIP==040000 ;LOCKED IN PLACE PT.NXM==020000 ;NON-EXISTANT PT.MON==010000 ;BELONGS TO THE MONITOR PT.IPC==004000 ;BELONGS TO IPCF PT.TNC==002000 ;TEMPORARILY UNCACHED (1099 ONLY) ;THINGS THAT CAN'T REALLY CHANGE, JUST MADE SYMBOLIC DSKBLK==200 ;SIZE OF A DISK BLOCK NBCSHE==20 ;NUMBER OF DISK BLOCKS TO CACHE FOR "READ" COMMAND ;STORAGE OPNBLK: EXP 17,0,0 ;DUMP MODE, STR FILLED IN, NO BUFFERS LUKBLK: BLOCK 4 ;LOOKUP BLOCK EXEDIR: BLOCK DSKBLK ;EXE DIRECTORY DCACHD: BLOCK NBCSHE*DSKBLK ;SPACE FOR THE CACHE DCACHE: BLOCK NBCSHE ;SPACE FOR CACHE POINTERS PDL: BLOCK 50 ;A STACK SAVCHR: BLOCK 1 ;SAVED CHARACTER FROM GETONE LOCORE: BLOCK 1 ;COPY OF MONITOR "LOCORE" FRUSED: BLOCK 1 ;COPY OF "FRUSED" FREPTR: BLOCK 1 ;COPY OF "FREPTR" RNGTAB: BLOCK 1 ;ADDRESS OF RANGE TABLE PDBPTR: BLOCK 1 ;ADDRESS OF JBTPDB FOR NULL JOB JBTMXL: BLOCK 1 ;HIGHEST JOB+SEGN JOBMAX: BLOCK 1 ;NUMBER OF JOBS (0-N) FREAVB: BLOCK 1 ;NUMBER OF CHUNKS POSSIBLE FRERTN: BLOCK 1 ;NUMBER OF CHUNKS RETURNED PGTLEN: BLOCK 1 ;NUMBER OF PAGES DESCRIBED BY PAGTAB EPTADR: BLOCK 1 ;BOOT CPU'S EPT EPMADR: BLOCK 1 ;BOOT CPU'S EXEC MAP JBTUPM: BLOCK 1 ;WHERE JBTUPM IS JBTAD2: BLOCK 1 ;WHERE JBTAD2 IS JBTADR: BLOCK 1 ;WHERE JBTADR IS JBTSTS: BLOCK 1 ;WHERE JBTSTS IS FYSORG: EXP 314000 ;ORIGIN OF PER-PROCESS AREA PITSIZ: BLOCK 1 ;SIZE OF JBTPIA ENTRY PTBADR: BLOCK 1 ;ADDRESS OF PAGTAB ON THIS SYSTEM ERPTSZ: BLOCK 1 ;SIZE OF DAEMON ERROR ENTRY ESVIDX: BLOCK 1 ;START OF ERROR TABLE ERPTMX: BLOCK 1 ;MAXIM EPKIDX: BLOCK 1 ;INDEX INTO TABLE ERPTBK: BLOCK 10 ;THE BLOCK SUBTTL Entry Point and Main Command Dispatch FRECOR: JFCL ;NO CCL ENTRY RESET ;START FRESH MOVE P,[IOWD 50,PDL] ;GET A STACK MOVE T1,[PUSHJ P,UUOCON] ;HOW TO GET TO THE LUUO HANDLER MOVEM T1,41 ;STORE IN JOBDAT MOVEI T1,CODE-1 ;HIGHEST ADDRESS WHERE I'LL PUT MONITOR DATA CORE T1, ;ASK FOR IT ALL HALT . ;WHAT NXTCOM: OUTSTR [ASCIZ/FRECOR>/] ;PROMPT THE OPERATOR SETZB F,SAVCHR ;CLEAR FLAGS, NO SAVED CHARACTER NOW PUSHJ P,GETSIX ;GET COMMAND AND MASK JUMPE T1,NULCMD ;NULL COMMAND MOVE T3,[-NUMCMD,,CMDTBL] ;GET AOBJN TO COMMAND TABLE PUSHJ P,TABSRC ;LOOK IT UP IN THE TABLE SKIPA T2,[NUMCMD] ;ILLEGAL COMMAND MOVEI T2,NUMCMD+1 ;AMBIGUOUS COMMAND PUSHJ P,@CMDDSP(T2) ;EXECUTE IT MAIN.1: PUSHJ P,FLUSH ;EAT UP REST OF INPUT LINE TLNN F,(FL.UPZ) ;YES, WAS END A CONTROL-Z JRST NXTCOM ;NO, GET ANOTHER COMMAND MONRT. ;YES, EXIT NOW JRST FRECOR ;RESTART PROGRAM ON CONTINUE NULCMD: TLNN F,(FL.EOL) ;JUST AN EMPTY LINE PUSHJ P,BADFMT ;NO, COMPLAIN JRST MAIN.1 ;THEN FLUSH INPUT LINE DEFINE COMNDS,< XLIST X DDT, X FIND, X HELP, X MONITOR, X READ, LIST SALL > DEFINE X(CMD,STR),<> CMDTBL: COMNDS ;GENERATE THE COMMAND TABLE NUMCMD==<.-CMDTBL> ;NUMBER OF COMMANDS DEFINE X(CMD,STR), CMDDSP: COMNDS ;GENERATE THE DISPATCH TABLE EXP ILLCMD ;TYPE OUT ILLEGAL COMMAND EXP AMBIGC ;TYPE OUT AMBIGUOUS COMMAND DEFINE X(CMD,STR), CMDHLP: COMNDS ;GENERATE THE HELP DESCRIPTORS SUBTTL Random Error Message Printers for Command Scanner BADEXE: OUTSTR [ASCIZ/?Bad EXE Header code - Not an EXE file/] JRST ERRXIT ;END LINE AND RETURN COMEXE: OUTSTR [ASCIZ/?EXE Directory is too complex/] JRST ERRXIT ;END LINE AND RETURN AMBIGA: OUTSTR [ASCIZ/?Ambiguous Argument - "/] JRST ILSXIT ;FINISH ERROR MESSAGE ILLARG: OUTSTR [ASCIZ/?Unknown Argument - "/] JRST ILSXIT ;FINISH ERROR MESSAGE NOARGS: TLNN F,(FL.EOL) ;END OF INPUT JRST BADFMT ;NO, GIVE DIFFERENT ERROR OUTSTR [ASCIZ/?Missing Argument/] JRST ERRXIT ;END LINE AND RETURN JUNK: OUTSTR [ASCIZ/?Junk after end of command - "/] SKIPA ;OUTPUT OFFENDING CHARACTER BADFMT: OUTSTR [ASCIZ/?Command Error - "/] CAIGE CH,40 ;A REGULAR CHARACTER JRST [OUTCHR ["^"] ;NO, OUTPUT UP-ARROW ADDI CH,100 ;MAKE A REAL LETTER JRST .+1] ;RETURN INLINE OUTCHR CH ;OUTPUT OFFENDING CHARACTER JRST ILLXIT ;FINISH UP AND RETURN AMBIGC: OUTSTR [ASCIZ/?Ambiguous Command - "/] SKIPA ;SKIP OVER OTHER MESSAGE ILLCMD: OUTSTR [ASCIZ/?Unknown Command - "/] ILSXIT: PUSHJ P,SIXOUT ;APPEND COMMAND TYPED ILLXIT: OUTCHR [""""] ;CLOSE QUOTES ERRXIT: CRPOPJ: OUTSTR [BYTE (7)15,12,0] POPJ P, SUBTTL The "FIND" Command %FIND: SKIPN PGTLEN ;DO WE KNOW ABOUT PAGTAB YET JRST [OUTSTR[ASCIZ/?Use READ or MONITOR command first/] JRST ERRXIT] ;END LINE AND RETURN PUSHJ P,GETNUO ;GET OCTAL PAGE NUMBER SKIPGE P2,T1 ;COPY INTO P2 FOR LATER USE JRST NOARGS ;IF -1, BAD ARGUMENTS (OR NONE) MOVE P1,T1 ;COPY NUMBER PUSHJ P,CMDEND ;NO MORE ARGUMENTS JRST JUNK ;ISN'T PUSHJ P,PGFTCH ;FETCH THE PAGTAB ENTRY FOR IT TLNE T1,PT.FRE ;A FREE PAGE JRST [OUTSTR[ASCIZ/Page is on the Free List/] JRST CRPOPJ] ;END LINE AND RETURN TLNE T1,PT.NXM ;NON-EXISTANT JRST [OUTSTR[ASCIZ/Page is off-line/] JRST CRPOPJ] ;END LINE AND RETURN TLNE T1,PT.MON ;BELONG TO THE MONITOR JRST [OUTSTR[ASCIZ/Page belongs to the Monitor/] JRST CRPOPJ] ;END LINE AND RETURN TLNE T1,PT.IPC ;BELONG TO IPCF JRST [OUTSTR[ASCIZ/Page in somebody's IPCF queue/] JRST CRPOPJ] ;END LINE AND RETURN TLNE T1,PT.LPH!PT.LEV!PT.LIP ;ANY LOCK BITS OUTSTR [ASCIZ/Page is locked /] TLNE T1,PT.LPH ;PHYSICALLY CONTIGUOUS OUTSTR [ASCIZ/physically contiguously/] TLNE T1,PT.LEV ;IN EVM OUTSTR [ASCIZ/in EVM/] TLNE T1,PT.LIP ;IN PLACE OUTSTR [ASCIZ/in place/] TLNE T1,PT.LPH!PT.LEV!PT.LIP ;ANY OF THE ABOVE OUTSTR [ASCIZ/ for /] MOVE J,JOBMAX ;START AT HIGHEST JOB NUMBER FIND.1: HRRZ T1,@JBTUPM ;PAGE NUMBER OF UPMP CAIN T1,(P2) ;THIS THE ONE WE'RE LOOKING FOR JRST [OUTSTR[ASCIZ/UPMP of /] JRST FIND.5] ;PRETTY UP OUTPUT AND DONE SOJG J,FIND.1 ;LOOK AT ALL UPMP'S MOVEI J,1 ;START LOOKING AT ALL JOBS/SEGMENTS FIND.2: MOVSI T1,SHRSEG ;SHARABLE SEGMENT BIT CAMLE J,JOBMAX ;IS THIS A SEGMENT TDNE T1,@JBTSTS ;YES, IS IT SHARABLE SKIPN @JBTADR ;CHECK IF IN CORE JRST FIND.4 ;NON-SHARABLE SEGMENTS ARE COUNTED IN JOB LOW SEG LDB P1,[POINT 13,@JBTUPM,35] ;JBYHSA CAMG J,JOBMAX ;IS THIS A HIGH SEGMENT LDB P1,[POINT 13,@JBTAD2,35] ;JBYLSA FIND.3: CAIN P1,(P2) ;IS THIS THE PAGE WE'RE LOOKING FOR JRST FIND.5 ;FOUND PUSHJ P,PGFTCH ;GET PAGTAB ENTRY FOR PAGE IN JOB/SEGMENT HRRZ P1,T1 ;GET LINK TO NEXT PAGE IN SEGMENT/JOB JUMPN P1,FIND.3 ;CONTINUE WITH JOB/SEGMENT FIND.4: CAMG J,JBTMXL ;OFF THE END OF JOBS/SEGMENTS AOJA J,FIND.2 ;NO, LOOK AT NEXT ONE OUTSTR [ASCIZ/?Not found for any job or segment/] JRST CRPOPJ ;END LINE AND RETURN FIND.5: CAMLE J,JOBMAX ;JOB OR SEGMENT SKIPA T1,[[ASCIZ/Segment /]] MOVEI T1,[ASCIZ/Job /] FORMAT <,,,,< (>,,< octal)>> JRST CRPOPJ ;END LINE AND RETURN POPJ P, SUBTTL The "READ" Command %READ: PUSHJ P,GETFN ;GO GET THE FILE TO READ POPJ P, ;ALREADY GAVE ERROR PUSHJ P,CMDEND ;REALLY OUGHT TO BE THE END JRST JUNK ;ISN'T OPEN XPN,OPNBLK ;OPEN THE STR POPJ P, ;FAILED LOOKUP XPN,LUKBLK ;GET THE FILE POPJ P, ;FAILED IN XPN,IOLST1 ;READ EXE DIRECTORY, PAGE 0 INTO 1000 CAIA ;OK SO FAR HALT . ;WHAT MOVE T1,[1140,,140] ;140 FROM EXE FILE INTO MY 140 BLT T1,777 ;GET ALL OF PAGE 0 BUT JOBDAT IN XPN,IOLST2 ;GET REST OF FILE LOW SEGMENT CAIA ;OK SO FAR HALT . ;WHAT HLRZ T1,EXEDIR ;GET EXE HEADER CODE CAIE T1,1776 ;BETTER BE JRST BADEXE ;BAD DIRECTORY FORMAT HRRZ T1,EXEDIR ;GET LENGTH OF DIRECTORY CAIL T1,DSKBLK ;CHECK AGAINST SPACE ALLOCATED JRST COMEXE ;TOO COMPLEX MOVEI T1,DCACHD ;POINT TO THE DATA BUFFERS MOVSI T2,-NBCSHE ;NUMBER OF BUFFERS HRROM T1,DCACHE(T2) ;MARK ENTRY AVAILABLE ADDI T1,DSKBLK ;STEP TO NEXT BUFFER AOBJN T2,.-2 ;PRIME THE TABLES JRST MONCOM ;JOIN COMMON CODE IOLST1: IOWD 1000,EXEDIR ;EXE DIRECTORY (CLOBBER SOME OF DCACHD) IOWD 1000,1000 ;PAGE 0 INTO PAGE 1 0 IOLST2: IOWD 313000,1000 ;ENTIRE LOW SEGMENT NOW 0 SUBTTL The "MONITOR" Command %MONIT: PUSHJ P,CMDEND ;NO ARGUMENTS JRST JUNK ;JUNK ON THE LINE SETZM EXEDIR ;NO EXE DIRECTORY NOW MOVE T1,[%CNSIZ] ;SIZE OF THE MONITOR GETTAB T1, ;DON'T USE SIMULATOR, WANT REAL CURRENT HALT . ;WHAT MOVEI T1,-1(T1) ;WANT HIGHEST ADDRESS CAILE T1,377777 ;LESS THAN 128K? MOVEI T1,377777 ;NO, GO FOR THE MAX MOVE T2,T1 ;SAVE ADDRESS SPY T1, ;SPY ON THE MONITOR HALT . ;WHAT MOVE T1,[400140,,140] ;MONITOR 140 TO MY 140 BLT T1,(T2) ;COPY SO WE DON'T GET CONFUSED BY CHANGES MOVSI T1,1 ;NOW GET RID OF THE SPY SEGMENT CORE T1, ;GOOD BYE HALT . ;WHAT JRST MONCOM ;JOIN COMMON CODE SUBTTL Check Out the Free Core MONCOM: FORMAT <,,,,,,,> FORMAT <,,,,,,,> OUTCHR [11] ;ALIGN WITH A TAB GTTAB %CNMON ;GET MONTH NUMBER OUTSTR MONTAB-1(T1) ;OUTPUT MONTH FORMAT << >,,<,>,> FORMAT << >,,<:>,,<:>,> FORMAT <,,,> GTTAB %CNNWC ;AMOUNT OF CORE POSSIBLE LSH T1,-^D9 ;TO NUMBER OF PAGES MOVEM T1,PGTLEN ;STORE LENGTH OF PAGTAB GTTAB %CNBCP ;FIND A BOOT CPU LSH T1,1 ;*2 FOR CPU SPECIFIC GETTABS MOVE P1,T1 ;SAVE IT ADD T1,[%CCTOS] ;FIND EPT ADDRESS PUSHJ P,GTBSPY ;GET IT (SHOULD SMARTEN UP GTTAB MACRO) HALT . ;WHAT? MOVEM T1,EPTADR ;SAVE FOR LATER ADDI T1,1000 ;OFFSET TO EXEC MAP MOVEM T1,EPMADR ;SAVE FOR LATER MOVE T1,[%CCTYP] ;FIND CPU TYPE ADD T1,P1 PUSHJ P,GTBSPY ;GET IT HALT . ;WHAT? CAIE T1,.CCKLX ;KL-10 SYSTEM? SKIPA T1,[PAGTAB] ;NO, GET KS PAGTAB OFFSET MOVSI T1,(MS.MEM) ;YES, GET PAGTAB/MEMTAB SECTION MOVEM T1,PTBADR ;WHERE PAGTAB STARTS ON THIS MACHINE GTTAB %VMPPB ;GET BEGINNING OF PER-PROCESS AREA MOVEM T1,FYSORG ;SAVE IT GTTAB %CNSJN ;GET JOB/SEGMENT INFORMATION SOS T1 ;DECREMENT TO HIGHEST JOB NUMBER HRRZM T1,JOBMAX ;STORE HLRE T2,T1 ;GET NUMBER OF SEGMENTS MOVNS T2 ;FROM AOBJN TYPE TO A REAL NUMBER ADDI T2,(T1) ;NUMBER OF JOBS + SEGMENTS MOVEM T2,JBTMXL ;STORE FOR GETTAB SIMULATOR GTTAB %CNPDB ;FIND OUT BASE OF PDB'S MOVEM T1,PDBPTR ;STORE IT TOO GTTAB <.GTIDX,,.GTSLF> ;BASE OF RANGE TABLE FOR GETTABS HRRZM T1,RNGTAB ;STORE THAT TOO GTTAB <.GTUPM,,.GTSLF> ;BASE OF JOB UPMP TABLE HRRZS T1 ;ISOLATE ADDRESS ADD T1,[Z MONITR(J)] ;FUTURE INDIRECT REFERENCES MOVEM T1,JBTUPM ;STORE ADDRESS OF JBTUPM GTTAB <.GTSTS,,.GTSLF> ;BASE OF JOB STATUS TABLE HRRZS T1 ;ISOLATE ADDRESS ADD T1,[Z MONITR(J)] ;FUTURE INDIRECT REFERENCES MOVEM T1,JBTSTS ;STORE ADDRESS OF JBTSTS GTTAB <.GTADR,,.GTSLF> ;BASE OF JOB ADDRESS TABLE HRRZS T1 ;ISOLATE ADDRESS ADD T1,[Z MONITR(J)] ;FUTURE INDIRECT REFERENCES MOVEM T1,JBTADR ;STORE ADDRESS OF JBTADR GTTAB <.GTPRV,,.GTSLF> ;HACK COMING HRRZS T1 ;ISOLATE ADDRESS SUB T1,JOBMAX ;JBTAD2 IS NOT GETTABABLE SUB T1,JOBMAX ;BUT IT IS JBTPRV-2*JOBN SUBI T1,2 ;ACCOUNT FOR TWICE THE NULL JOB REMOVED ABOVE ADD T1,[Z MONITR(J)] ;FUTURE INDIRECT REFERENCES MOVEM T1,JBTAD2 ;STORE IT (HACK) GTTAB %CNFRE ;POINTER TO FREE CORE BIT MAP MOVEM T1,FREPTR ;STORE HLRE T1,T1 ;SIZE OF TABLE MOVNS T1 ;TO A REAL NUMBER IMULI T1,^D36 ;TO CHUNKS AVAILABLE MOVEM T1,FREAVB ;STORE FOR PERCENT COMPUTATIONS GTTAB %CNLOC ;WHERE FREE CORE STARTS MOVEM T1,LOCORE ;STORE GTTAB %CNFRU ;CURRENT AMOUNT USED MOVEM T1,FRUSED ;STORE FORMAT <,,< Words = >,,,> PUSHJ P,RTNPDB ;ACCOUNT FOR PDB SPACE PUSHJ P,RTNPSI ;GET PSISER DATA BASE PUSHJ P,RTNSTR ;GET STR DATA BASE, SAT, SPT PUSHJ P,RTNCPY ;RETURN UPDATE FILE RIB POINTERS PUSHJ P,RTNDDB ;ANY DDBS CARVED OUT OF FREE SPACE PUSHJ P,RTNIPC ;DO IPCF RECEIVE QUEUES PUSHJ P,RTNLNM ;RETURN JOBS LOGICAL NAME TABLES PUSHJ P,RTNPTH ;RETURN PATH BLOCKS FOR EXE'S FROM SFD'S PUSHJ P,RTNCTX ;RETURN SAVED CONTEXT BLOCKS PUSHJ P,RTNENQ ;RETURN ENQ/DEQ LOCK BLOCKS PUSHJ P,RTNNET ;NETSER STUFF PUSHJ P,RTNDTE ;RETURN DTESER STUFF PUSHJ P,RTNCSH ;RETURN DISK CACHE STUFF PUSHJ P,RTNEBM ;RETURN EXTENSIBLE BITMAP MEMORY PUSHJ P,RTNDAE ;RETURN DAEMON ERROR STUFF PUSHJ P,RTNNRT ;*** MUST BE LAST *** RETURN NRTSER STUFF JRST LEFT ;TELL WHATS LEFT OVER ;HERE TO ACCOUNT FOR PDB SPACE USED BY JOBS RTNPDB: MOVEI P1,PDBLEN ;NUMBER OF WORDS IN A PDB MOVE P2,PDBPTR ;ADDR OF JBTPDB MOVSI P3,'PDB' ;TEXT FOR TYPEOUT RTNCOM: MOVE J,JOBMAX ;FOR ALL JOBS SETZM FRERTN ;START COUNTS FRESH RTNC.1: DMOVE T1,P1 ;SIZE AND JBTXXX BASE ADDI T2,(J) ;FOR JOB N HRRZ T2,MONITR(T2) ;GET TABLE ADDRESS SKIPE T2 ;ANY THERE PUSHJ P,GIVWDS ;YES, RETURN IT SOJGE J,RTNC.1 ;GET ALL INCLUDING THE NULL JOB FORMAT <,,< Space is >,> JRST CRPOPJ ;CRLF AND EXIT ;HERE TO ACCOUNT FOR PSISER DATA BASE RTNPSI: GTTAB %CNPIL ;LENGTH OF PSI DATA BASE MOVE P1,T1 ;COPY SIZE MOVEM T1,PITSIZ ;SAVE FOR LATER GTTAB %CNPIA ;ADDRESS OF JBTPIA MOVE P2,T1 ;COPY IT MOVSI P3,'PSI' ;TEXT FOR TYPE OUT JRST RTNCOM ;USE COMMON CODE ;HERE TO ACCOUNT FOR PATH BLOCKS FOR EXE FILES RUN FROM SFD'S RTNPTH: SETZM FRERTN ;START FRESH MOVE J,JBTMXL ;HIGHEST SEGMENT NUMBER PTH.1: GTTAB <-1,,.GTPPN> ;JBTPPN FOR EXE FILE SKIPN T2,T1 ;COPY ADDRESS JRST PTH.2 ;NEVER MIND MOVEI T1,PTHLEN ;NUMBER OF WORDS TO RETURN TLNN T2,-1 ;WAIT, IS THAT REALLY A PPN LIKE THE OLD DAYS PUSHJ P,GIVWDS ;NOPE, RETURN IT PTH.2: CAMLE J,JOBMAX ;INTO REAL JOB TABLES YET SOJA J,PTH.1 ;NO, KEEP GOING FORMAT <,> JRST CRPOPJ ;RETURN ;HERE TO ACCOUNT FOR JOB LOGICAL NAME TABLE RTNLNM: SETZM FRERTN ;START FRESH MOVE J,JOBMAX ;FOR ALL JOBS LNM.1: GTTAB <-1,,.GTDVL> ;LOGICAL NAME TABLE HRRE T2,T1 ;WHERE IT IS MOVEI T1,LNMLEN ;NUMBER OF WORDS SKIPLE T2 ;IS THERE ONE PUSHJ P,GIVWDS ;YES, RETURN IT SOJG J,LNM.1 ;GET ALL JOBS FORMAT <,> JRST CRPOPJ ;RETURN ;HERE TO ACCOUNT FOR COPIES OF RIB POINTERS FOR UPDATE FILES RTNCPY: SETZM FRERTN ;START FRESH GTTAB %LDPTR ;GET POINTER TO FIRST UPDATE FILE RIB POINTER COPY HLRZ P1,T1 ;COPY IT CPY.1: JUMPE P1,CPY.2 ;ALL DONE MOVE T2,P1 ;ADDRESS OF BLOCK MOVEI T1,PTRCOR ;SIZE OF THE BLOCK PUSHJ P,GIVWDS ;RETURN THE SPACE HLRZ P1,PTRSYS(P1) ;STEP TO NEXT BLOCK JRST CPY.1 ;GET THEM ALL CPY.2: FORMAT <,> JRST CRPOPJ ;AND RETURN ;HERE TO ACCOUNT FOR SAVED CONTEXT BLOCKS RTNCTX: SETZM FRERTN ;START FRESH MOVE J,JOBMAX ;FOR EACH JOB CTX.1: MOVE P1,J ;COPY JOB NUMBER ADD P1,PDBPTR ;ADDRESS OF JBTPDB FOR JOB HRRZ P1,MONITR(P1) ;GET ADD OF PDB ITSELF JUMPE P1,CTX.5 ;NONE, GET ANOTHER JOB HRRZ T2,MONITR+.PDSCX(P1) ;GET ADDRESS OF SAVED CONTEXT BLOCK JUMPE T2,CTX.2 ;NONE MOVEI T1,NWSCTX ;WORDS IN A CONTEXT BLOCK CAMGE T2,FYSORG ;MIGHT BE IN FUNNY SPACE PUSHJ P,GIVWDS ;ISN'T, RETURN LOW CORE CTX.2: MOVE P3,MONITR+.PDCTC(P1) ;GET CURRENT CONTEXT MOVE T2,MONITR+.PDSAC(P1) ;GET START OF CONTEXT CHAIN CTX.3: SKIPN P2,T2 ;COPY ADDRESS JRST CTX.5 ;NONE? MOVEI T1,.CTSIZ ;NUMBER OF WORDS TLNN T2,-1 ;NZS ADDRESS? PUSHJ P,GIVWDS ;RETURN THEM REPEAT 0,< ;THIS DOESN'T WORK? MOVE T1,P2 ;ADDRESS OF THIS BLOCK ADDI T1,.CTBPR+.CXPIA ;OFFSET TO POINTER TO SAVED JBTPIA BLOCK PUSHJ P,WDFTCH ;GET IT SKIPN T2,T1 ;COPY ADDRESS JRST CTX.3A ;NOTHING MOVE T1,PITSIZ ;SIZE OF A BLOCK PUSHJ P,GIVWDS ;RETURN IT >; END REPEAT 0 CTX.3A: REPEAT 0,< ;THIS DOESN'T WORK? CAMN P2,P3 ;THE "CURRENT" CONTEXT? JRST CTX.4 ;YES, IGNORE SAVED CONTEXT BLOCK MOVE T1,P2 ;ADDRESS OF THIS BLOCK ADDI T1,.CTBPR+.CXSCX ;OFFSET TO POINTER TO SAVED CONTEXT BLOCK PUSHJ P,WDFTCH ;GET IT SKIPN T2,T1 ;COPY ADDRESS JRST CTX.4 ;NOTHING THERE, DON'T TRY TO RETURN IT MOVEI T1,NWSCTX ;WORDS IN A CONTEXT BLOCK CAMGE T2,FYSORG ;MIGHT BE IN FUNNY SPACE PUSHJ P,GIVWDS ;ISN'T, RETURN LOW CORE >; END REPEAT 0 CTX.4: MOVE T1,P2 ;ADDRESS OF THIS BLOCK ADDI T1,.CTNXT ;OFFSET TO LINK WORD PUSHJ P,WDFTCH ;GET IT MOVE T2,T1 ;COPY ADDRESS JRST CTX.3 ;GIVE IT BACK CTX.5: SOJG J,CTX.1 ;AND GET ALL THE JOBS FORMAT <,> JRST CRPOPJ ;AND RETURN ;HERE TO ACCOUNT FOR STUFF REQUIRED BY DISK STRUCTURES RTNSTR: GTTAB %LDSTR ;FIRST STRUCTURE IN SYS HLRZ P1,T1 ;PUT IN SAFER PLACE SETZ P5, ;CLEAR TOTAL COUNT STR.1: JUMPE P1,STR.7 ;DONE IF LAST STR SKIPN STRNAM(P1) ;A REAL STRUCTURE THERE JRST STR.6 ;NO, DON'T BOTHER SETZM FRERTN ;START COUNTS OVER FOR EACH STR MOVE T2,P1 ;WHERE STR DATA BLOCK IS MOVEI T1,STRLEN ;AND HOW LONG IT IS CAML T2,LOCORE ;MOUNTED AT ONCE TIME PUSHJ P,GIVWDS ;NO, REMOVE THE CORE HLRZ P2,STRUNI(P1) ;STEP TO FIRST UNIT IN STR STR.2: JUMPE P2,STR.5 ;LAST UNIT, GO TO NEXT STR MOVEI T1,UNISAB(P2) ;GET ADDRESS OF WORD WE WANT PUSHJ P,WDFTCH ;GET IT SKIPE P3,T1 ;GET SAT BLOCK TABLE ADDRESS TLZE P3,-1 ;SKIP THIS IF ITS NOT IN SECTION 0 JRST STR.4 ;SKIP THIS WHOLE SAT MOVE J,P3 ;COPY WHERE RING STARTS LDB P4,[POINT 9,UNIWPS(P2),8] ;GET SIZE OF SAT ON THIS UNIT STR.3: MOVE T2,P3 ;ADDR OF SAB MOVEI T1,SABBIT(P4) ;SPACE ALLOCATED CAML T2,LOCORE ;FROM ONCE PUSHJ P,GIVWDS ;NO, RETURN THE SPACE MOVE P3,SABRNG(P3) ;TO NEXT SAB IN RING JUMPE P3,STR.3A ;CHECK LINK WORD CAIE P3,(J) ;BACK WHERE WE STARTED JRST STR.3 ;NOPE, DO THE NEXT ONE JRST STR.4 ;DONE WOTH SAB RING, GET SPT STR.3A: FORMAT <<SAB Ring Messed Up for >,,,> STR.4: MOVEI T1,UNISPT(P2) ;ADDRESS OF THE SPT PUSHJ P,WDFTCH ;GET IT TLZE T1,-1 ;UNLESS IN A NON-ZERO SECTION JRST STR.4A ;SKIP THE SPT MOVE T2,T1 ;SAVE A COPY LDB T1,[POINT 8,UNISPU(P2),17] ;SIZE OF THE SPT ON THIS UNIT ADDI T1,SPTFIR+1 ;PLUS OVERHEAD CAML T2,LOCORE ;IN FREE CORE PUSHJ P,GIVWDS ;RETURN IT STR.4A: MOVEI T1,UNISTR(P2) ;WORD WE WANT PUSHJ P,WDFTCH ;GET IT HLRZ P2,T1 ;STEP TO NEXT UNIT IN STRUCTURE JRST STR.2 ;AND DO THAT ONE STR.5: SKIPN T1,FRERTN ;DON'T BOTHER IF NO SPACE RECLAIMED JRST STR.6 ;NONE, TRY ANOTHER ADD P5,T1 ;ACCUMULATE TOTAL FORMAT <,,<: >,,< Words>,> STR.6: HLRZ P1,STRSYS(P1) ;TO NEXT FILE STRUCTURE JRST STR.1 ;AND DO IT STR.7: FORMAT <,> JRST CRPOPJ ;AND RETURN ;HERE TO ACCOUNT FOR ENQ/DEQ LOCK BLOCKS RTNENQ: GTTAB %CNHSH ;-LEN,,ADDR OF HSHTAB HLRE J,T1 ;GET -VE LENGTH MOVMS J ;MAKE +VE MOVEI P1,-1(T1) ;POINT TO LAST ENTRY IN HSHTAB ADDI P1,(J) ;... SETZM FRERTN ;START FRESH ENQ.1: HRRZ P2,.LBNHS(P1) ;FIRST LOCK BLOCK OFF THIS ENTRY ENQ.2: CAIN P2,(P1) ;CHAIN ENDS WHEN WE GET BACK TO HSHTAB JRST ENQ.5 ;LOOK AT NEXT HSHTAB ENTRY HRRZ P3,.LBNQ(P2) ;FIRST Q-BLOCK ENQ.3: CAIN P3,(P2) ;BACK TO THE LOCK BLOCK JRST ENQ.4 ;YES, DONE WITH Q-BLOCKS MOVE T2,P3 ;ADDR OF Q-BLOCK MOVEI T1,QBSIZE ;AND LENGTH OF IT HRRZ P4,.QBMSK(P3) ;POINT TO ANY MASK BLOCK OWNED HRRZ P3,.QBNQ(P3) ;NEXT Q-BLOCK IN CHAIN PUSHJ P,GIVWDS ;RETURN THIS BLOCK JUMPE P4,ENQ.3 ;GET NEXT Q-BLOCK IF NO MASK BLOCK MOVE T2,P4 ;ADDRESS OF IT HLRZ T1,.LBNMS(P2) ;LENGTH OF IT PUSHJ P,GIVWDS ;RETURN MASK BLOCK JRST ENQ.3 ;AND CHECK OUT NEXT Q-BLOCK ENQ.4: MOVE T2,P2 ;ADDRESS OF THE BLOCK HLRZ T1,.LBLEN(P2) ;LENGTH OF THE BLOCK PUSHJ P,GIVWDS ;RETURN THE SPACE HRRZ P2,.LBNHS(P2) ;NEXT BLOCK IN THE CHAIN JRST ENQ.2 ;CHECK IT OUT ENQ.5: SOS P1 ;BACK DOWN HSHTAB SOJG J,ENQ.1 ;TRY NEXT ENTRY FORMAT <,> JRST CRPOPJ ;AND RETURN ;HERE TO ACCOUNT FOR DDB'S BUILT IN FREE CORE ;WARNING: ; DO NOT RETURN NETWORK DDB'S IN THIS ROUTINE RTNDDB: FORMAT <,> SETZM FRERTN ;START FRESH GTTAB %CNDEV ;START OF DDB CHAIN HLRZ P2,T1 ;SAVE ADDRESS OF FIRST DDB DDB.1: CAMGE P2,LOCORE ;IN FREE SPACE JRST DDB.2 ;NO, TRY ANOTHER CAIL P2,400000 ;UP IN MONITORS HIGHSEG (DSKDDB) JRST DDB.3 ;YES, QUIT NOW, MAY LOSE SOME DDBS FORMAT << >,,< at >,,< size >> HLLZ T4,DEVNAM(P2) ;GET WHAT IT IS MOVE T2,P2 ;ADDRESS FOR RETURN SETZ T1, ;IN CASE WE DON'T KNOW ABOUT IT MOVE T3,DEVMOD(P2) ;GET DEVMOD TLNE T3,DVDSK ;IS IT A "FAKE" DISK DDB JRST [MOVEI T1,DSKDDS ;YES, GET DISK DDB SIZE JRST DDB.0] ;AND RETURN THE SPACE MOVSI T3,-NUMDVS ;NUMBER HARD-WIRED CAME T4,DVSNMS(T3) ;LOOK FOR IT AOBJN T3,.-1 ;TRY NEXT SKIPGE T3 ;KNOWN XCT DVSLDS(T3) ;YES, GET SIZE VALUE DDB.0: FORMAT <,,,> SKIPE T1 ;KNOW THE SIZE PUSHJ P,GIVWDS ;YES, RETURN SOME DDB.2: HLRZ P2,DEVSER(P2) ;STEP TO NEXT DEVICE JUMPN P2,DDB.1 ;LOOK AT IT DDB.3: FORMAT <,> JRST CRPOPJ ;RETURN DVSNMS: SIXBIT /MPX/ ;MPX DEVICE SIXBIT /'LA/ ;MTA LABEL DDB SIXBIT /'LB/ ;MTB LABEL DDB SIXBIT /'LC/ ;MTC LABEL DDB SIXBIT /'LD/ ;MTD LABEL DDB SIXBIT /'LE/ ;MTE LABEL DDB SIXBIT /'LF/ ;MTF LABEL DDB NUMDVS==.-DVSNMS ;NUMBER KNOWN DVSLDS: PUSHJ P,DVSMPX ;MPX IS SPECIAL MOVEI T1,SPROTO ;LENGTH OF A MAG TAPE LABEL DDB MOVEI T1,SPROTO ;LENGTH OF A MAG TAPE LABEL DDB MOVEI T1,SPROTO ;LENGTH OF A MAG TAPE LABEL DDB MOVEI T1,SPROTO ;LENGTH OF A MAG TAPE LABEL DDB MOVEI T1,SPROTO ;LENGTH OF A MAG TAPE LABEL DDB MOVEI T1,SPROTO ;LENGTH OF A MAG TAPE LABEL DDB DVSMPX: MOVEI T1,MPXLEN ;SIZE OF MPX DDB FORMAT <,,,> PUSHJ P,GIVWDS ;RETURN DDB HLRZ T2,DEVXTR(P2) ;ADDRESS OF CDT SKIPE T1,T2 ;MIGHT NOT BE ANY HLRZ T1,MONITR(T2) ;LENGTH OF CDT FORMAT << CDT at >,,< size >> POPJ P, ;RETURN TO GIVE BACK CDT INSTEAD OF DDB ;HERE TO ACCOUNT FOR IPCF RECEIVE QUEUES RTNIPC: FORMAT <,> SETZM FRERTN ;START FRESH MOVE J,JOBMAX ;GET ALL JOBS IPC.1: GTTAB <-1,,.GTIPP> ;IPCF POINTERS FOR JOB (J) HLRZ P2,T1 ;GET ADDRESS OF FIRST MESSAGE ANDI T1,777 ;ISOLATE COUNT OF MESSAGES JUMPE T1,IPC.3 ;NONE, GET NEXT JOB FORMAT << Job >,,< has >,,< messages>,> IPC.2: JUMPE P2,IPC.3 ;NEXT JOB MOVE T2,P2 ;FOR RETURN SKIPGE MONITR+.IPCFP(P2) ;SKIP IF NOT ON DISK JRST [SETZ T1, ;NOT IN CORE, GET A ZERO JRST IPC.2A] ;CONTINUE MOVEI T1,IP.CFV ;PAGE MODE? TDNE T1,MONITR+.IPCFL(P2) ;IN PACKET HEADER? JRST [LDB T1,[POINT 21,MONITR+.IPCFP(P2),35] ;GET PAGE NUMBER FORMAT << Page >,,< is in-core>,> SETZ T1, ;ZERO LENGTH JRST IPC.2A] ;CONTINUE LDB T1,[POINT 10,MONITR+.IPCFP(P2),12] ;GET LENGTH IPC.2A: ADDI T1,.IPCFC+1 ;PLUS OVERHEAD PUSHJ P,GIVWDS ;RETURN IT IPC.2B: HLRZ P2,MONITR+.IPCFL(P2) ;LINKED THROUGH LH OF FLAG WORD JRST IPC.2 ;AND TRY THAT IPC.3: SOJG J,IPC.1 ;GET ALL THE JOBS FORMAT <,> JRST CRPOPJ ;RETURN ;HERE TO ACCOUNT FOR NETWORK FREE CORE ;ASSUMPTIONS: ; NETSER HAS "PARANOID" AND "P$COR" TURNED ON ; %NTMEM IS NOT GETTABABLE BUT IS "NETGTT-1" (HACK) RTNNET: GTTAB <.GTNTP,,.GTSLF> ;ADDRESS OF NETGTT TLNN T1,777000 ;CHECK TABLE LENGTH POPJ P, ;ZERO, GETTAB REMOVED MOVEI P1,-1(T1) ;POINT TO %NTMEM ( I KNOW ) SETZM FRERTN ;START COUNT FRESH NET.1: HRRZ P1,MONITR(P1) ;NEXT ITEM ON NETWORK LIST JUMPE P1,NET.3 ;DONE ON ZERO LINK MOVEI T1,1 ;THERE IS NO COUNT WORD, MUST COMPUTE LENGTH MOVEI T2,(P1) ;WHERE IT STARTS MOVEI T3,(P1) ;AND A WORKING COPY NET.2: MOVE T4,MONITR(T3) ;GET A WORD CAME T4,[SIXBIT/NETMEM/] ;THIS PATTERN IS THE LAST WORD OF THE SPACE AOJA T1,[AOJA T3,NET.2] ;NOT END, COUNT WORD AND GO TO NEXT ONE PUSHJ P,GIVWDS ;RETURN THE SPACE JRST NET.1 ;AND GET NEXT CHUNK NET.3: FORMAT <,,< (NETSER Claims it knows >,,<)>,> POPJ P, ;DONE WITH NETWORKS ;HERE TO ACCOUNT FOR NRTSER FREE CORE (AS MUCH AS WE CAN) ;NOTE: NRTSER USES NO LINKED LISTS TO KEEP TRACK OF ALLOCATED ;CORE. WE DEPEND ON HIM STORING THE ADDRESS OF EVERY CHUNK ;OF MEMORY ALLOCATED IN HIS "CHANNEL TABLE". RTNNRT: SETZM FRERTN ;START COUNTS FRESH GTTAB %DNNCH ;GET ADDRESS OF NRTSER'S CHANNEL TABLE POINTER MOVE P1,MONITR(T1) ;GET THE TABLE ADDRESS HRRZ T2,MONITR+3(T1) ;GET POINTER TO NRTSER'S SAB HLRZ T1,MONITR-1(T2) ;GET CHECK WORD CAIE T1,'NRT' ;SHOULD BE THIS POPJ P, ;NOPE HRRZ T1,MONITR-1(T2) ;GET LENGTH ADDI T1,1 ;ACCOUNT FOR NRTSER'S LEADING TAG WORD SUBI T2,1 ;POINT AT REAL START OF BLOCK PUSHJ P,GIVWDS ;RETURN THE SPACE HLRZ T1,MONITR-1(P1) ;GET THE LH OF FIRST WORD CAIE T1,'NRT' ;SHOULD BE THIS POPJ P, ;NOT, WE DON'T KNOW WHAT TO DO HERE HRRZ T1,MONITR-1(P1) ;GET LENGTH OF HIS TABLE MOVN T2,T1 ;NEGATE LENGTH HRL P1,T2 ;MAKE AN AOBJN POINTER ADDI T1,1 ;ACCOUNT FOR NRTSER'S LEADING TAG WORD MOVEI T2,-1(P1) ;POINT AT REAL START OF BLOCK PUSHJ P,GIVWDS ;RETURN THE SPACE NRT.1: SKIPN T2,MONITR(P1) ;GET AN ENTRY FROM CHANNEL TABLE JRST NRT.2 ;NOTHING THERE HLRZ T1,MONITR-1(T2) ;GET THE CHECK WORD CAIE T1,'NRT' ;NRTSER'S TAG? JRST NRT.2 ;NOPE, LEAVE IT ALONE HRRZ T1,MONITR-1(T2) ;GET SIZE OF BLOCK ADDI T1,1 ;ACCOUNT FOR NRTSER'S LEADING TAG WORD MOVEI T2,-1(T2) ;POINT AT REAL START OF BLOCK PUSHJ P,GIVWDS ;RETURN THE SPACE NRT.2: AOBJN P1,NRT.1 ;LOOP FOR ALL ENTRIES FORMAT <,> JRST CRPOPJ ;RETURN ;HERE TO ACCOUNT FOR HASH BLOCKS IN THE DISK CACHE AND THE DATA ;BLOCKS (KS ONLY). RTNCSH: GTTAB %LDCHD ;GET HEADER OF CACHE LIST MOVE P1,T1 ;SAVE IT HERE SETZM FRERTN ;START COUNTS FRESH MOVEI T1,.CBNHB(P1) ;POINTER TO FREE LIST MOVE P2,T1 ;SAVE START PUSHJ P,WDFTCH ;GET IT CSH.1: CAMN T1,P2 ;HIT THE END YET? JRST CSH.2 ;YES MOVE P3,T1 ;SAVE BLOCK ADDRESS ADDI T1,.CBDAT ;OFFSET TO DATA BLOCK PUSHJ P,WDFTCH ;GET IT MOVE T2,T1 ;COPY ADDRESS MOVEI T1,DSKBLK ;SIZE OF A BLOCK TLNN T2,-1 ;NON-ZERO SECTION? PUSHJ P,GIVWDS ;RETURN BLOCK MOVEI T1,.CBLEN ;LENGTH OF BLOCK MOVE T2,P3 ;BLOCK ADDRESS MOVEI T1,.CBNHB(P3) ;LINK TO NEXT BLOCK PUSHJ P,WDFTCH ;GET IT JRST CSH.1 ;CHECK IT CSH.2: MOVEI T1,.CBNAB(P1) ;POINTER TO ACTIVE LIST PUSHJ P,WDFTCH ;GET IT CSH.3: CAMN T1,P2 ;HIT THE END YET? JRST CSH.4 ;YES MOVE P3,T1 ;SAVE BLOCK ADDRESS ADDI T1,.CBDAT ;OFFSET TO DATA BLOCK PUSHJ P,WDFTCH ;GET IT MOVE T2,T1 ;COPY ADDRESS MOVEI T1,DSKBLK ;SIZE OF A BLOCK TLNN T2,-1 ;NON-ZERO SECTION? PUSHJ P,GIVWDS ;RETURN BLOCK MOVEI T1,.CBLEN ;LENGTH OF BLOCK MOVE T2,P3 ;BLOCK ADDRESS PUSHJ P,GIVWDS ;RETURN IT MOVEI T1,.CBNAB(P3) ;LINK TO NEXT BLOCK PUSHJ P,WDFTCH ;GET IT JRST CSH.3 ;CHECK IT CSH.4: FORMAT <,> JRST CRPOPJ ;RETURN ;HERE TO ACCOUNT FOR EXTENSIBLE BITMAP MEMORY BLOCKS RTNEBM: SETZM FRERTN ;START COUNTS FRESH GTTAB %CNAHB ;GET FIRST ALLOCATION HEADER BLOCK MOVE P1,T1 ;SAVE IT HERE EBM.1: MOVE P2,MONITR+AHBAEB(P1) ;GET FIRST EXTENT BLOCK EBM.2: HLRE T1,MONITR+AEBBMP(P2) ;GET LENGTH OF BITMAP MOVMS T1 ;MAKE +VE ADDI T1,AEBBMP+1 ;INCLUDE HEADER MOVE T2,P2 ;ADDRESS OF EXTENT BLOCK CAML T2,LOCORE ;DON'T RETURN ASSEMBLED-IN BLOCKS CAML T2,FYSORG ;... SKIPA ;NO GOOD PUSHJ P,GIVWDS ;RETURN THE SPACE MOVE P2,MONITR+AEBNXT(P2) ;GET LINK TO NEXT BLOCK JUMPN P2,EBM.2 ;JUMP FOR NEXT ONE MOVE P1,MONITR+AHBNXT(P1) ;GET NEXT HEADER BLOCK JUMPN P1,EBM.1 ;JUMP FOR NEXT ONE FORMAT <,> JRST CRPOPJ ;RETURN ;HERE TO ACCOUNT FOR ANY MESSAGE BUFFERS USED FOR DECNET OVER DTE. RTNDTE: SETZM FRERTN ;START COUNT FRESH GTTAB %DNETH ;GET POINTER TO DTE TABLE SKIPN P1,T1 ;COPY ADDRESS, SKIP IF THERE IS ONE POPJ P, ;NONE GTTAB %CNCPU ;NUMBER OF CPU'S MOVNS T1 ;NEGATE HRL P1,T1 ;BUILD AN AOBJN WORD DTE.1: MOVE P2,MONITR(P1) ;GET ADDRESS OF A DTE BLOCK HRLI P2,-4 ;MAXIMUM OF 4 DTE'S DTE.2: MOVE P3,MONITR(P2) ;GET DTE CONTROL BLOCK ADDRESS MOVEI T1,UBLSIZ+6 ;SIZE SKIPE T2,MONITR+ETDOBK(P3) ;AN OUTPUT BUFFER? PUSHJ P,GIVWDS ;YES, RETURN IT MOVEI T1,UBLSIZ+6 ;SIZE SKIPE T2,MONITR+ETDIBK(P3) ;AN INPUT BUFFER? PUSHJ P,GIVWDS ;YES, RETURN IT AOBJN P2,DTE.2 ;LOOP FOR DTE'S ON THIS CPU AOBJN P1,DTE.1 ;LOOP FOR ALL DTE'S FORMAT <,> JRST CRPOPJ ;RETURN SETZM FRERTN ;START COUNT FRESH ;HERE TO ACCOUNT FOR ANY FREE CORE USED BY DAEMON ERROR ENTRIES ;RIGHT NOW ONLY CODE 30 (KLEERR) AND INDIRECTLY CODE NN (SYSTEM ;ERROR BLOCKS). RTNDAE: POPJ P, ;DONE GTTAB %LDESZ ;GET LENGTH OF ERPTBK ENTRY SKIPN T1 ;ANYTHING? MOVEI T1,2 ;NO, USE OLD DEFAULT MOVEM T1,ERPTSZ ;SAVE SIZE GTTAB %LDERT ;ADDRESS OF ERPTBK SKIPN T1 ;ANYTHING? HALT . ;NO, HANDLE SOME DAY MOVEM T1,ESVIDX ;SAVE GTTAB %LDPT1 ;POINTER TO EXTRACT ENTRIES PUSHJ P,WDFTCH ;FETCH THE WORD SKIPN T1 ;IF INITIAL IS ZERO MOVE T1,ERPTSZ ;OTHER ENTRY IS BLANK MOVEI T3,(T1) ;COPY INITIAL OFFSET GTTAB %LDLTH ;GET MAX TABLE LENGTH MOVEM T1,ERPTMX ;SAVE IT TOO GTTAB %CNFRE ;POINTER TO FREE CORE BIT MAP ;HERE TO REPORT STUFF LEFT OVER LEFT: SKIPN FRUSED ;ANYTHING LEFT OVER? JRST LEFT.4 ;NOPE FORMAT <,,,,< Chunks (>,,< Words) unaccounted for:>,> MOVE P1,FREPTR ;AOBJN FOR BIT MAP ADDI P1,MONITR ;OFFSET FOR WHERE WE PUT THE MONITOR HRLI P1,(POINT 1,0) ;LOOK AT A BIT AT A TIME MOVE J,FREAVB ;MAX POSSIBLE( i.e. NUMBER OF BITS TO LOOK AT) MOVE P2,LOCORE ;WHERE THEY ARE SETZB P3,P4 ;CLEAR COUNTERS LEFT.1: ILDB T1,P1 ;GET A BIT JUMPN T1,[AOS P3 ;COUNT SPACE TAKEN SKIPN P4 ;FIRST 1 BIT SEEN MOVE P4,P2 ;YES, REMEMBER WHERE IT STARTS JRST LEFT.2] ;AND GET ANOTHER BIT JUMPE P4,LEFT.2 ;END OF A TAKEN SLOT FORMAT << >,,< Words @ >,,,> SETZB P3,P4 ;START LOOKING AGAIN LEFT.2: ADDI P2,4 ;STEP TO NEXT ADDRESS SOJG J,LEFT.1 ;GET ALL THE BITS JUMPE P4,LEFT.3 ;ANY AT THE END FORMAT << >,,< Words @ >,,,> LEFT.3: POPJ P, ;RETURN LEFT.4: OUTSTR [ASCIZ / All free core accounted for! /] POPJ P, ;RETURN SUBTTL The "HELP" Command %HELP: OUTSTR [ASCIZ/Commands are:/] MOVEI P2,CMDHLP ;FIRST HELP TEXT SKIPA P1,[-NUMCMD,,CMDTBL] ;AOBJN FOR MAIN COMMAND TABLE HLPCOM: OUTSTR [ASCIZ/Arguments are:/] ;COMMON PART OF HELP TEXT FOR OTHER COMMAND PROCESSORS ; P1 = AOBJN TO COMMAND TABLE ; P2 = ADDRESS OF PARALLEL HELP TEXT TABLE HELP.1: OUTSTR [BYTE (7)15,12,11,0] ;CR,LF,TAB MOVE T1,(P1) ;GET A COMMAND FROM THE TABLE PUSHJ P,SIXOUT ;OUTPUT IT OUTCHR [11] ;ALIGN WITH A TAB OUTSTR @(P2) ;TEXT FOR IT AOS P2 ;STEP TO NEXT HELP TEXT AOBJN P1,HELP.1 ;AND TRY ANOTHER JRST CRPOPJ ;END LINE AND RETURN SUBTTL The "DDT" Command %DDT: PUSHJ P,FLUSH ;NO ARGUMENTS HRRZ T1,74 ;ADDRESS OF DDT JUMPN T1,(T1) ;GO TO IT OUTSTR [ASCIZ/?DDT not loaded/] JRST CRPOPJ ;RETURN SUBTTL Some Input Subroutines ;SUBROUTINE TO INPUT A SINGLE CHARACTER INTO CH ; PUSHJ P,GETONE ; RETURN HERE IF A SPECIAL CHARACTER ; RETURN HERE IF A NUMBER ; RETURN HERE IF A LETTER ;IF FL.RSC IS ON, THIS GETS THE LAST CHARACTER (TERMINATOR OF PREVIOUS) GETONE: TLNE F,(FL.EOL) ;END OF LINE SEEN JRST GETO.2 ;YES, RETURN LINE FEED TLZE F,(FL.RSC) ;WANT OLD CHARACTER AGAIN JRST [MOVE CH,SAVCHR ;YES, GET SAVED CHARACTER JRST GETO.B] ;AND PROCESS IT INCHWL CH ;NO, GET A CHARACTER GETO.A: MOVEM CH,SAVCHR ;SAVE FOR RESCAN GETO.B: JUMPE CH,GETONE ;IGNORE NULLS CAIN CH,15 ;CARRIAGE RETURN ?? JRST GETONE ;YES, PITCH THOSE CAIE CH,7 ;^G ?? CAIN CH,13 ;^K ?? JRST GETO.1 ;YES, MARK END OF TEXT AND RETURN LINE FEED CAIN CH,14 ;^L ?? JRST GETO.1 ;YES, MARK END OF TEXT AND RETURN LINE FEED CAIE CH,12 ;LINE FEED ?? CAIN CH,33 ;ALTMODE ?? JRST GETO.1 ;YES, MARK END OF TEXT AND RETURN LINE FEED CAIN CH,32 ;^Z ?? JRST GETO.0 ;YES, LIGHT LOTS OF BITS FOR ^Z CAIN CH,11 ;A TAB SKIPA CH,[" "] ;YES, CONVERT TO SPACE CAIN CH," " ;A SPACE POPJ P, ;YES, TAKE "SPECIAL" RETURN CAIE CH,"!" ;LOOK FOR COMMENTS CAIN CH,";" ;... JRST GETO.2 ;FAKE AN END OF LINE CAIG CH,"9" ;LOOK FOR DIGITS CAIGE CH,"0" ;... SKIPA ;NOT A DIGIT JRST CPOPJ1 ;TAKE "DIGIT" EXIT CAIG CH,"Z"+40 ;LOWER CASE LETTER CAIGE CH,"A"+40 ;... SKIPA ;NOT LOWER CASE SUBI CH," " ;CONVERT TO UPPER CASE CAIG CH,"Z" ;NOW DO LETTER CHECK CAIGE CH,"A" ;... POPJ P, ;MUST BE A SPECIAL CPOPJ2: AOS (P) ;TAKE "LETTER" EXIT CPOPJ1: AOS (P) ;LOTS OF SKIP RETURNS CPOPJ: POPJ P, ;RETURN GETO.0: TLO F,(FL.UPZ) ;MARK ^Z FOR JMF GETO.1: TLO F,(FL.ETX) ;MARK REAL END OF TEXT GETO.2: TLO F,(FL.EOL) ;LIGHT FAKE END OF LINE MOVEI CH,12 ;RETURN LINE FEED POPJ P, ;TAKE "SPECIAL" RETURN GETO.3: PUSHJ P,CRPOPJ ;END ECHOING WITH CR,LF JRST GETO.1 ;AND MARK LINE AS COMPLETE ;SUBROUTINE TO SEARCH A TABLE FOR A COMMAND OR ARGUMENT ;CALL: T1 = ITEM IN SIXBIT ; T2 = MASK FOR CHARACTERS TYPED ; T3 = AOBJN POINTER FOR TABLE TO SEARCH ;RTNS: CPOPJ = NOT IN THE TABLE ; CPOPJ1 = AMBIGUOUS ; CPOPJ2 = FOUND IT ;RETURNS T1 INTACT, T2 = RELATIVE INDEX FOR COMMAND, CLOBBERS T3,T4,T5 TABSRC: MOVEI T4,(T3) ;SAVE TABLE START ADDRESS PUSH P,T2 ;SAVE MASK TO USE SETZ T2, ;CLEAR FOUND INDICATOR TABS.1: MOVE T5,(T3) ;GET AN ITEM CAMN T1,T5 ;EXACT MATCH JRST [MOVEI T2,(T3) ;YES, MARK WHERE WE FOUND IT JRST TABS.3] ;AND EXIT ANDCM T5,(P) ;MASK TO AS MANY CHARS AS IN T1 CAME T1,T5 ;NOW DO WE HAVE A MATCH JRST TABS.2 ;NO, TRY NEXT ENTRY IN TABLE JUMPN T2,[POP P,(P) ;IF ALREADY HAVE 1 MATCH JRST CPOPJ1] ;GIVE AMBIGUOUS RETURN MOVEI T2,(T3) ;SAVE ADDRESS OF THIS MATCH TABS.2: AOBJN T3,TABS.1 ;AND LOOK SOME MORE TABS.3: POP P,(P) ;CLEAN STACK NOW JUMPE T2,CPOPJ ;RETURN IF NEVER FOUND ONE SUBI T2,(T4) ;COMPUTE RELATIVE OFFSET OF COMMAND JRST CPOPJ2 ;AND GIVE LOTS OF SKIP RETURNS ;SUBROUTINE TO EAT UP THE REST OF THE INPUT LINE FLUSH: TLZ F,(FL.EOL!FL.RSC) ;CLEAR SCANNER FLAGS TLNE F,(FL.ETX) ;REACHED END OF LINE YET POPJ P, ;YES, RETURN PUSHJ P,GETONE ;GET A CHARACTER JFCL ;IGNORE VARIOUS RETURNS JFCL ;... JRST FLUSH ;NOW LOOK FOR END OF LINE ;SUBROUTINE TO ENSURE THAT NO GARBAGE FOLLOWS LAST ARGUMENT OF A COMMAND ;CALLED BY VARIOUS COMMAND PROCESSORS AFTER READING LAST ARGUMENT BUT BEFORE ; EXECUTING THE COMMAND ITSELF. ;RTNS: CPOPJ JUNK AFTER COMMAND ; CPOPJ1 NOTHING BUT END OF LINE CMDEND: TLO F,(FL.RSC) ;GET LAST ARGUMENT TERMINATOR CMDE.1: PUSHJ P,GETONE ;GET A CHARACTER JRST CMDE.2 ;SPECIAL, CHECK IT OUT POPJ P, ;NUMBER, JUNK POPJ P, ;SPECIAL, JUNK CMDE.2: CAIN CH," " ;SPACE AFTER COMMAND JRST CMDE.1 ;ALLOW SPACES BEFORE ANY COMMENTS TLNE F,(FL.EOL) ;END OF LINE AOS (P) ;YES, NO JUNK POPJ P, ;RETURN ;SUBROUTINE TO GET A SIXBIT WORD FROM THE INPUT STREAM INTO "T1" ; ALSO RETURNS MASK FOR POSSIBLE COMMAND IN "T2" ;CLOBBERS T3 GETSIX: MOVE T3,[POINT 6,T1] ;PRIME THE BYTE POINTER SETZ T1, ;AND THE RECEIVING WORD SETO T2, ;AND THE EVENTUAL COMMAND MASK TLO F,(FL.RSC) ;START WITH LAST TERMINATOR GETS.1: PUSHJ P,GETONE ;GET A CHARACTER JRST GETS.2 ;SPECIAL, GO LOOK JRST [JUMPE T1,CPOPJ ;NUMBERS CANNOT BE THE FIRST IN A COMMAND JRST .+1] ;BUT CAN BE PARTS OF IT (e.g. CPU0, RPE4) SUBI CH,40 ;TO SIXBIT TLNE T3,770000 ;GOT THEM ALL YET IDPB CH,T3 ;NO, INSERT NEW CHARACTER LSH T2,-6 ;ADJUST MASK FOR NEW CHARACTER JRST GETS.1 ;AND GET ANOTHER GETS.2: CAIN CH," " ;STOP ON A BLANK JUMPE T1,GETS.1 ;YES, IGNORE LEADING BLANKS POPJ P, ;RETURN WITH T1,T2 SET UP ;SUBROUTINE TO GET A NUMERIC ARGUMENT FROM THE INPUT STREAM INTO "T1" ;RTNS: T1 .LT. 0 IF NO DIGITS FOUND ;CLOBBERS T2,T3 GETNUM: SKIPA T2,[^D10] ;DEFAULT RADIX GETNUO: MOVEI T2,^D8 ;HERE FOR OCTAL INPUT SETO T1, ;NO DIGITS SEEN YET TLO F,(FL.RSC) ;START WITH LAST TERMINATOR GETN.1: PUSHJ P,GETONE ;GET A CHARACTER JRST GETN.2 ;A SPECIAL, CHECK IT OUT SKIPA ;A NUMBER, INCLUDE IT JRST GETN.3 ;A LETTER, CHECK FOR K OR P MOVEI T3,-"0"(CH) ;CONVERT TO ASCII CAIL T3,(T2) ;RADIX CHECK JRST GETN.4 ;ILLEGAL ( NO 8'S OR 9'S IN OCTAL ) SKIPGE T1 ;ANY DIGITS SO FAR TDZA T1,T1 ;NO, THIS IS THE FIRST IMULI T1,(T2) ;"SHIFT" PREVIOUS SUM ADDI T1,(T3) ;AND INCLUDE THE NEW DIGIT JRST GETN.1 ;GET MORE GETN.2: CAIN CH,"#" ;INPUTTING OCTAL JRST [JUMPGE T1,GETN.4 ;CAN'T CHANGE RADIX IN THE MIDDLE OF THE STREAM CAIN T2,^D8 ;ALREADY DONE THIS ONCE POPJ P, ;YES, CAN'T TYPE TWO OF THEM MOVEI T2,^D8 ;NEW RADIX JRST GETN.1] ;AND GET ANOTHER DIGIT CAIN CH," " ;A BLANK JUMPL T1,GETN.1 ;YES, IGNORE LEADING BLANKS ALWAYS POPJ P, ;STOP ON A SPECIAL OR OTHER BLANKS GETN.3: JUMPL T1,CPOPJ ;ERROR IF NO DIGITS YET SETO T3, ;FLAG INVALID LETTER CAIN CH,"K" ;ALLOW "K" MOVEI T3,^D10 ;*1024 IF "K" CAIN CH,"P" ;ALLOW "P" MOVEI T3,^D9 ;*512 IF "P" JUMPL T3,GETN.4 ;ILLEGAL IF NEITHER LSH T1,(T3) ;ADJUST APPROPRIATELY SETZM SAVCHR ;EAT UP THE "P" OR "K" POPJ P, ;RETURN WITH NUMBER IN T1 GETN.4: SETO T1, ;ANYTHING ILLEGAL, RETURN -1 POPJ P, ;RETURN ;SUBROUTINE TO SET UP OPEN/LOOKUP BLOCKS WITH FILE NAME ENTERED GETFN: SETZB T1,OPNBLK+1 ;CLEAR STRUCTURE MOVSI T2,'EXE' ;EXTENSION DEFAULT DMOVEM T1,LUKBLK ;CLEAR FILE NAME, SET EXTENSION SETZ T2, ;ANOTHER 0 DMOVEM T1,LUKBLK+2 ;CLEAR REST OF SHORT LOOKUP BLOCK GETF.1: PUSHJ P,GETSIX ;GET NEXT ARGUMENT JUMPE T1,GETF.2 ;NO MORE, LOOK FOR ERRORS CAIN CH,":" ;DEVICE TERMINATOR JRST [SKIPE OPNBLK+1 ;ALREADY HAVE A DEVICE NAME JRST BADFMT ;YES, SAY ILLEGAL CONSTRUCTION MOVEM T1,OPNBLK+1 ;STORE IT SETZM SAVCHR ;EAT UP THE COLON JRST GETF.1] ;AND GET NEXT FIELD MOVEM T1,LUKBLK ;STORE FILE NAME (MUST BE ONE) TLNE F,(FL.EOL) ;END OF LINE SEEN JRST GETF.2 ;YES, CHECK RESULTS CAIE CH,"[" ;ONLY PPN SPEC CAN BE LEFT JRST CPOPJ1 ;RETURN NOW, GIVE RIGHT ERROR MESSAGE SETZM SAVCHR ;EAT THE "[" PUSHJ P,GETNUO ;GET OCTAL PROJECT NUMBER TLNN T1,-1 ;SMALL NUMBERS ONLY CAIE CH,"," ;BETTER BE JRST BADFMT ;ILLEGAL HRRE T1,T1 ;EXTEND SIGN JUMPLE T1,BADFMT ;THIS IS BAD TOO HRLM T1,LUKBLK+3 ;STORE IT SETZM SAVCHR ;EAT THE COMMA PUSHJ P,GETNUO ;GET THE PROJECT NUMBER TLNE T1,-1 ;SMALL HERE TOO JRST BADFMT ;NO GOOD JUMPLE T1,BADFMT ;THIS IS REAL BAD HRRM T1,LUKBLK+3 ;STORE THAT CAIN CH,"]" ;ALLOW CLOSURE SETZM SAVCHR ;BUT DON'T REQUIRE IT GETF.2: MOVSI T1,'DSK' ;DEFAULT DEVICE SKIPN OPNBLK+1 ;UNLESS STR GIVEN MOVEM T1,OPNBLK+1 ;ISN'T, FILL IT IN SKIPN LUKBLK ;GOTTA HAVE A FILE NAME JRST NOARGS ;COMPLAIN JRST CPOPJ1 ;RETURN SUBTTL Some Output Subroutines ;SUBROUTINE TO OUTPUT SIXBIT VALUE IN AC "T1" SIXOUA: SKIPA T2,@UA ;LUUO, GET SIXBIT VALUE SIXOUT: MOVE T2,T1 ;COPY SIXBIT OVER SIXOU1: JUMPE T2,CPOPJ ;ALL DONE AT END OF SIXBIT WORD SETZ T1, ;CLEAR RECEIVING AC LSHC T1,6 ;BRING IN A CHARACTER MOVEI T1," "(T1) ;TO ASCII OUTCHR T1 ;OUTPUT IT JRST SIXOU1 ;AND GET THEM ALL ;SUBROUTINE TO OUTPUT "T1" IN CORRECT RADIX DECOU2: CAIGE T1,^D10 ;2 DIGIT MINIMUM OUTCHR ["0"] ;OUTPUT LEADING ZERO JRST DECOUT ;NOW OUTPUT DECIMAL NUMBER DECOUA: SKIPA T1,@UA ;LUUO, GET NUMBER OCTOUA: SKIPA T1,@UA ;LUUO, GET NUMBER DECOUT: SKIPA T3,[^D10] ;GET RADIX OCTOUT: MOVEI T3,10 ;GET RADIX JUMPL T1,[OUTCHR ["-"] ;NEGATIVE VALUE MOVMS T1 ;OUTPUT "-" AND POSITIVE NUMBER JRST OCTOU1] ;RESUME INLINE OCTOU1: IDIVI T1,(T3) ;STRIP DIGIT PUSH P,T2 ;SAVE IT SKIPE T1 ;WAS THAT ALL PUSHJ P,OCTOU1 ;NO, GET ANOTHER POP P,T1 ;RESTORE CHARACTER MOVEI T1,"0"(T1) ;TO ASCII OUTCHR T1 ;OUTPUT IT POPJ P, ;AND RETURN ;SUBROUTINE TO OUTPUT "T1" AS ASCII WORD ASCOUT: SETZ T2, ;MAKE SURE THERE'S A NULL AT THE END OUTSTR T1 ;OUTPUT T1 AND MAYBE T2 POPJ P, ;RETURN ;SUBROUTINE TO OUTPUT FREE CORE NUMBERS AC A PERCENTAGE PERCNT: SKIPGE T1,FRUSED ;GET AMOUNT TAKEN OUTCHR ["-"] ;NEGATIVE, OUTPUT MINUS MOVMS T1 ;MAKE POSITIVE NUMBER IMULI T1,^D10000 ;SCALE IDIV T1,FREAVB ;COMPUTE PERCENTAGE IDIVI T1,^D100 ;UN-SCALE IDIVI T2,^D10 ;AND 2 HUNDREDTHS DIGITS FORMAT <,,<.>,,,,<%>> POPJ P, ;AND RETURN SUBTTL Some Random (or stolen) Subroutines ;SUBROUTINE TO RETURN "FREE" CORE ;ENTER GIVWDS: T1=# WDS. TO RETURN, T2=START ADR. OF CORE GIVWDS: ADDI T1,3 ;CONVERT TO # 4WD. BLOCKS ASH T1,-2 SUB T2,LOCORE ;GET ADR. RELATIVE TO START OF TABLE MOVN T3,T1 ADDM T3,FRUSED ;DECREMENT FREE-CORE USED ADDM T1,FRERTN ;INCREMENT AMOUNT RETURNED LSH T2,-2 ;/4 TO CONVERT TO BITS IDIVI T2,^D36 ;COMPUTE WORD LOC, STARTING BIT HRLS T2 ;WORD POSITION IN BOTH HALVES ADD T2,FREPTR ;SET AOBJN WORD FOR TABLE ;FALL INTO SETZRS ;SUBROUTINE TO SET ZEROS IN A TABLE ;ARG T1=HOW MANY BITS TO CLEAR ; T2=AOBJN POINTER FOR TABLE ; T3=POSITION IN WORD OF FIRST BIT TO CLEAR ; (0=BIT 0, 1=BIT 1, ETC.) SETZRS: EXCH T1,T3 ;SET ACS FOR CLRBTS MOVEI T4,^D36 ;ADJUST FOR 1ST WORD SUBM T4,T1 HRRZ T4,T2 ;SET T4 FOR CLRBTS PUSH P,T2 ;SAVE AOBJN WORD PUSHJ P,CLRBTS ;CLEAR SOME BITS HALT . ;STOPCD BAC HERE POP P,T2 ;RESTORE AOBJN WORD HLRE T3,T2 ;LENGTH OF POINTER SUB T2,T3 ;COMPUTE TOP OF TABLE CAILE T4,(T2) ;FINAL ADR PAST TOP? HALT . ;STOPCD PTT HERE POPJ P, ;NO, GOOD RETURN ;SUBROUTINE TO SET UP A BIT MASK FOR IORM OR ANDCAM INTO A TABLE ;ENTER WITH T1=POSITION (36=BIT0, 1=BIT35) AND T3=HOW MANY ;AFTER THE FIRST CALL USE BITMS2, T3=COUNT RETURNS T1=MASK, ;T3=REMAINING COUNT ROUTINE HAS RETURNED FINAL MASK IF ;T3 .LE. 0 ASSUMES T4=ADR IN TABLE, BITMS2 INCREMENTS T4 BITMSK: PUSH P,T1 ;SAVE POSITION MOVN T1,T3 ;- COUNT CAILE T3,^D36 ;MORE THAN 1 WORD? MOVNI T1,^D36 ;YES, SETTLE FOR A WORD (OR LESS) MOVSI T2,400000 ;SET TO PROPOGATE A MASK ASH T2,1(T1) ;GET THE RIGHT NUMBER OF BITS SETZ T1, LSHC T1,@0(P) ;POSITION THE BITS IN T1 (=MASK) SUB T3,0(P) ;REDUCE THE COUNT TO THE NEW VALUE POP P,T2 ;RESTORE T2 POPJ P, ;RETURN ;HERE AFTER FIRST CALL, MASK STARTS AT BIT 0 BITMS2: SETO T1, ;MASK STARTS AT BIT 0 MOVNI T2,-^D36(T3) ;SET UP SHIFT CAIGE T3,^D36 ;DONT SHIFT IS .GE. 36 LSH T1,(T2) ;POSTION THE MASK SUBI T3,^D36 ;REDUCE THE COUNT AOJA T4,CPOPJ ;UPDATE THE POSITION AND RETURN ;ROUTINE TO CLEAR BITS FROM A TABLE ;ENTER T1=POSITION, T3=COUNT, T4=TABLE ADR (POSITION=36 IF BIT0, 1 IF BIT35) ;RETURNS POPJ IF BIT ALREADY 0, POPJ1 OTHERWISE CLRBTS: PUSHJ P,BITMSK ;GENERATE A MASK CLRBT1: MOVE T2,MONITR(T4) ;WORD TO CLEAR BITS FROM TDC T2,T1 ;ARE THE BITS ALREADY OFF? TDNE T2,T1 POPJ P, ;YES, RETURN NON-SKIP MOVEM T2,MONITR(T4) ;NO, NOW THEY ARE JUMPLE T3,CPOPJ1 ;DONE IF COUNT .LE. 0 PUSHJ P,BITMS2 ;GENERATE MASK FOR NEXT WORD JRST CLRBT1 ;AND GO CLEAR THOSE BITS ;SUBROUTINE TO PERFORM GETTAB VIA SPY IF POSSIBLE ;ARGS T1=GETTAB ARG ;VALUES T1=GETTAB VALUE GTBSPY: SKIPGE T1 ;WANT JOB NUMBER (- INDEX) HRLI T1,(J) ;YES, INSERT IT SKIPN NUMTAB ;HAVE GETTAB STUFF YET JRST [GETTAB T1, ;NO, GET IT FROM CURENT MONITOR POPJ P, ;IT FAILED JRST CPOPJ1] ;GIVE GOOD RETURN PUSH P,P1 ;SAVE P REGS PUSH P,P2 ;... PUSH P,P3 ;... HRRZI P1,(T1) ;P1=TABLE NUMBER ADD P1,NUMTAB ;ADDR OF PTR FOR THIS TABLE LDB P3,[POINT 3,MONITR(P1),11] ;GET TYPE OF TABLE CAIN P3,.SLIXP ;IS DATUM IN THE PDB? JRST GTBPDB ;YES, GO GET IT CAIN P3,.SLIXS ;INDEXED BY JOB OR SEGMENT NUMBER? SKIPA P2,JBTMXL ;YES, MAX IS JOBN+SEGN-1 LDB P2,[POINT 9,MONITR(P1),8] ;NO. GET MAX ITEM VALUE CAIE P3,.SLIXR ;IS THIS A RANGED GETTAB? JRST GTBSP1 ;NO, P2 CONTAINS 0,,MAX SKIPN P3,RNGTAB ;DO WE HAVE THE ADDRESS OF RNGTAB? JRST GTBSP3 ;NO, FAIL ADDI P2,(P3) ;ADD OFFSET INTO RNGTAB FOR THIS ENTRY MOVE P2,MONITR(P2) ;GET MIN,,MAX FROM RNGTAB ENTRY GTBSP1: HLRZ P3,T1 ;GET ITEM NUMBER CALLER WANTS CAILE P3,(P2) ;.LE. MAX? JRST GTBSP3 ;NO, FAIL MOVSS P2 ;EXCHANGE MIN AND MAX CAIGE P3,(P2) ;AND .GE. MIN? JRST GTBSP3 ;NO, FAIL HRRZ T1,MONITR(P1) ;GET BASE OF TABLE WANTED ADD T1,P3 ;PLUS INDEX WANTED CAMGE T1,FYSORG ;IN HIGH SEG? SKIPA T1,MONITR(T1) ;GET DATA ITEM PUSHJ P,WDFTCH ;YES, GET IT GTBSP2: AOS -3(P) ;GIVE GOOD RETURN GTBSP3: POP P,P3 ;RESTORE P REGS POP P,P2 ;... POP P,P1 ;... POPJ P, ;RETURN GTBPDB: SKIPN PDBPTR ;IS JBTPDB BASE AVAILABLE? JRST GTBSP3 ;NO, FAIL HLRZS T1 ;JOB NUMBER ADD T1,PDBPTR ;PLUS JBTPDB ADDRESS HRRZ T1,MONITR(T1) ;GET ADDRESS OF WD 0 OF JOBS PDB JUMPE T1,GTBSP2 ;NO JOB THERE, RETURN 0 ADD T1,MONITR(P1) ;ADD ON ITEM NUMBER MOVE T1,MONITR(T1) ;GET THE WORD FROM THE PDB JRST GTBSP2 ;GIVE GOOD RETURN ;SUBROUTINE TO RETURN THE CONTENTS OF PAGTAB FOR A SPECIFIC PAGE ;ARGS P1 = PAGE NUMBER ;RETURN T1 = BITS FROM PAGTAB PGFTCH: CAML P1,PGTLEN ;RANGE CHECK IT JRST [MOVSI T1,PT.NXM ;OUT OF RANGE, SAY NXM POPJ P,] ;AND RETURN MOVE T1,P1 ;COPY PAGE NUMBER ADD T1,PTBADR ;ADD ADDRESS OF PAGTAB ; JRST WDFTCH ;FALL INTO WORD FETCH ROUTINE ;SUBROUTINE TO FETCH A SPECIFIC WORD FROM THE MONITOR HIGH SEGMENT ;ARGS T1 = ADDRESS (1B0 ON IF WANT PHYSICAL 22 BIT ADDRESS) ;RETURN T1 = THE CONTENTS WDFTCH: SKIPN EXEDIR ;RUNNING FROM AN EXE FILE JRST [MOVE T2,[PEEK T1,] ;NO, GET IT FROM RUNNING MONITOR TLZE T1,(1B0) ;WANT PHYSICAL ADDRESS TRO T2,UU.PHY ;YES, DO PHYSICAL ONLY PEEK XCT T2 ;GET THE WORD POPJ P,] ;AND RETURN TLZE T1,(1B0) ;WANT PHYSICAL WORD JRST [IDIVI T1,1000 ;SPLIT INTO PAGE AND OFFSET INTO PAGE JRST WDFPHY] ;AND BYPASS EPT RELOCATION CAMGE T1,FYSORG ;IN LOW MONITOR LOW SEGMENT? JRST [MOVE T1,MONITR(T1) ;YES, ALREADY HAVE THAT SOMEWHERE POPJ P,] ;RETURN IDIVI T1,1000 ;SPLIT INTO PAGE AND OFFSET INTO PAGE LDB T3,[POINT 9,T1,26] ;GET SECTION NUMBER ANDI T1,777 ;KEEP JUST IN-SECTION PAGE CAILE T3,1 ;SECTION 0 AND 1 ARE EASY JRST [ADD T3,EPTADR ;FOR OTHERS, MUST LOOK IN SECTAB HRRZ T3,MONITR+540(T3) ;GET SECTAB ENTRY LSH T3,9 ;CONVERT TO ADDRESS OF SECTION MAP ADD T1,T3 ;OFFSET IN SECTION MAP FOR OUR ADDRESS TLO T1,(1B0) ;PHYSICAL REFERENCE PUSH P,T2 ;SAVE OFFSET PUSHJ P,WDFTCH ;RECURSE TLZ T1,-1 ;CLEAR MAP BITS POP P,T2 ;RESTORE OFFSET JRST WDFPHY] ;CONTINUE ADD T1,EPMADR ;RELOCATE INTO THE EXEC MAP LDB T1,[POINT 13,MONITR(T1),35] ;GET PAGE NUMBER WDFPHY: HRRZ T3,EXEDIR ;NUMBER OF WORDS IN EXE DIRECTORY MOVNI T3,-1(T3) ;DON'T COUNT HEADER WORD HRLZS T3 ;FORM AOBJN WDFT.1: HRRZ T4,EXEDIR+2(T3) ;GET CORE ADDRESS FROM DESCRIPTOR CAILE T4,(T1) ;PAST THE ONE WE WANT HALT . ;WORD NOT IN FILE LDB T5,[POINT 9,EXEDIR+2(T3),8] ;GET REPEATER ADDI T5,1(T4) ;FIRST PAGE NOT IN POINTER CAIL T1,(T5) ;PAGE IN THIS POINTER AT ALL JRST [ADD T3,[1,,1] ;ADJUST FOR DOUBLE WORD ENTRIES AOBJN T3,WDFT.1 ;GET ANOTHER POINTER HALT .] ;WORD NOT IN FILE SUBI T1,(T4) ;HOW FAR INTO POINTER ADD T1,EXEDIR+1(T3) ;HOW FAR INTO THE FILE PROPER TLZ T1,-1 ;KEEP IT REASONABLE (FLAG BITS) LSH T1,^D9 ;CONVERT TO A PAGE NUMBER IN THE FILE ADDI T1,(T2) ;INCLUDE WORD OFFSET NOW IDIVI T1,DSKBLK ;NOW CONVERT TO BLOCK NUMBER AND OFFSET INTO BLOCK MOVSI T3,-NBCSHE ;SEARCH FOR BLOCK IN IN-CORE CACHE HLRZ T4,DCACHE(T3) ;BLOCK DESCRIBED IN CACHE CAIE T4,(T1) ;IS THIS IT AOBJN T3,.-2 ;NO, KEEP LOOKING JUMPL T3,WDFT.2 ;FOUND ONE, UPDATE LEAST RECENTLY USED TABLES HRLM T1,DCACHE+NBCSHE-1 ;STORE BLOCK NUMBER IN LAST (OLDEST) HRRZ T3,DCACHE+NBCSHE-1 ;WHERE DATA IS TO BE READ SOS T3 ;-1 FOR THE IOWD HRLI T3,-DSKBLK ;NUMBER OF WORDS SETZ T4, ;LAST IOWD USETI XPN,1(T1) ;POSITION FILE IN XPN,T3 ;READ BLOCK INTO CACHE CAIA ;READ OK HALT . ;DISK I/O READ ERROR MOVEI T3,NBCSHE-1 ;INDEX WHERE FOUND (READ) WDFT.2: HRRZS T3 ;ISOLATE INDEX CAIG T3,NBCSHE/3 ;DON'T RIPPLE IF ALREADY CLOSE TO START OF TABLE JRST WDFT.3 ;THIS MIGHT NOT BE TOO GOOD WITH A SMALL "NBCSHE" PUSH P,DCACHE(T3) ;SAVE ENTRY FOUND MOVE T4,DCACHE-1(T3) ;COMPRESS TABLE SO LEAST USED IS LAST MOVEM T4,DCACHE(T3) ;MOVE UP ENTRIES BELOW ONE FOUND SOJG T3,.-2 ;SO NEW ONE CAN BE FOUND QUICKLY POP P,DCACHE(T3) ;PUT NEW ONE AT THE FRONT WDFT.3: HRRZ T1,DCACHE(T3) ;GET ADDRESS OF DATA IN THIS BUFFER ADD T1,T2 ;PLUS OFFSET INTO BUFFER MOVE T1,(T1) ;FETCH IT POPJ P, ;AND RETURN SUBTTL Local UUO Handler UUOCON: LDB UU,[POINT 9,40,8] ;GET OPCODE HRRZ UA,40 ;GET EFFECTIVE ADDRESS CAILE UU,UUOMAX ;RANGE CHECK HALT . ;WHAT SKIPGE UU,UUODSP-1(UU) ;FAST UUO (DOESN'T CLOBBER REGS) JRST (UU) ;YES, GO RIGHT TO IT PUSH P,T1 ;SAVE ALL THE TEMP REGS PUSH P,T2 ;... PUSH P,T3 ;... PUSH P,T4 ;... PUSH P,T5 ;... PUSHJ P,(UU) ;CALL ROUTINE POP P,T5 ;NOW UNDO ALL THAT POP P,T4 ;... POP P,T3 ;... POP P,T2 ;... POP P,T1 ;... POPJ P, ;AND RETURN UUODSP: EXP DECOUA ;001 - OUTPUT DECIMAL NUMBER EXP OCTOUA ;002 - OUTPUT OCTAL NUMBER EXP SIXOUA ;003 - OUTPUT SIXBIT VALUE EXP PERCNT ;004 - FREE CORE STATS SETZ CRPOPJ ;005 - OUTPUT A CRLF EXP [MOVE T1,@UA ;006 - OUTPUT OCTAL NUMBER * 4 LSH T1,2 JRST OCTOUT] EXP [JSP T2,GTTOUT ;007 - OUTPUT GETTAB VALUE AS OCTAL EXP OCTOUT] EXP [JSP T2,GTTOUT ;010 - OUTPUT GETTAB VALUE AS DECIMAL EXP DECOUT] EXP [JSP T2,GTTOUT ;011 - OUTPUT GETTAB VALUE AS ASCII WORD EXP ASCOUT] EXP [JSP T2,GTTOUT ;012 - OUTPUT GETTAB VALUE, DECIMAL, 2 DIGITS EXP DECOU2] UUOMAX==<.-UUODSP> ;HIGHEST LUUO GTTOUT: MOVE T1,@UA ;GET GETTAB ARGUMENT PUSHJ P,GTBSPY ;GET VALUE HALT . ;WHAT JRST @0(T2) ;TO CORRECT OUTPUT ROUTINE MONTAB: ASCII /Jan/ ASCII /Feb/ ASCII /Mar/ ASCII /Apr/ ASCII /May/ ASCII /Jun/ ASCII /Jul/ ASCII /Aug/ ASCII /Sep/ ASCII /Oct/ ASCII /Nov/ ASCII /Dec/ XLIST ;FORCED OUT LITERAL POOL HERE LIT LIST .ENDPS ;END OF THE CODE PSECT END FRECOR ;END OF THIS PROGRAM