Google
 

Trailing-Edge - PDP-10 Archives - BB-4170G-SM - sources/jsysa.mac
There are 53 other files named jsysa.mac in the archive. Click here to see a list.
;<3A.MONITOR>JSYSA.MAC.25, 20-Jul-78 08:26:26, Edit by ENGEL
;FIX BAD HRRI AT CRJB5Y
;<3A.MONITOR>JSYSA.MAC.24, 11-Jul-78 13:40:55, Edit by PORCHER
;TCO 1896 - ADD CODE TO HANDLE ABRBITRARY USAGE ENTRIES 5000-9999
;<3A.MONITOR>JSYSA.MAC.23, 23-Jun-78 07:53:41, EDIT BY MILLER
;FIX PLOCK0 NOT TO CALL FKHPTN
;<3A.MONITOR>JSYSA.MAC.22, 19-Jun-78 13:15:39, Edit by HELLIWELL
;ADD SAVEPQ AT PLOCK0
;<1BOSACK>JSYSA.MAC.1000,  5-Jun-78 18:49:44, EDIT BY BOSACK
;<3A.MONITOR>JSYSA.MAC.20, 11-Jun-78 17:18:06, Edit by HELLIWELL
;<3A.MONITOR>JSYSA.MAC.19, 11-Jun-78 17:17:05, Edit by HELLIWELL
;INCREMENT P2 IN LOOP AT LOCK4 IN PLOCK JSYS
;<3A.MONITOR>JSYSA.MAC.18,  9-Jun-78 14:18:38, EDIT BY MILLER
;FIX UP PMCRPS TO ONLY UPDATE COUNT ON ERROR
;<3A.MONITOR>JSYSA.MAC.17,  8-Jun-78 17:08:35, EDIT BY MILLER
;MORE FIXES FOR NEW PMCTL CODE
;<3A.MONITOR>JSYSA.MAC.16,  8-Jun-78 16:07:10, EDIT BY MILLER
;TCO 1893. ENCHANCE PMCTL FUNCTION TO READ PAGE STATE
;<3A.MONITOR>JSYSA.MAC.15, 26-May-78 16:03:52, Edit by HELLIWELL
;MAKE PLOCK0 SUBR RETURN OKINT ON ERRORS
;<3A.MONITOR>JSYSA.MAC.14, 25-May-78 13:44:02, Edit by HELLIWELL
;MAKE PLOCK0 GLOBAL
;<3A.MONITOR>JSYSA.MAC.13, 25-May-78 13:39:55, Edit by HELLIWELL
;MAKE PLOCK0 SUBROUTINE SO VB10 CODE CAN LOCK PAGES
;<3A.MONITOR>JSYSA.MAC.12, 23-May-78 13:45:28, EDIT BY MILLER
;CHANGE CALL LODPPG TO CALL LODPPS
;<3A.MONITOR>JSYSA.MAC.11, 23-May-78 11:14:51, EDIT BY MILLER
;MORE FIXES TO PLOCK
;<3A.MONITOR>JSYSA.MAC.10, 23-May-78 10:30:12, EDIT BY MILLER
;FIX TYPEOS
;<3A.MONITOR>JSYSA.MAC.9, 23-May-78 10:25:02, EDIT BY MILLER
;FIX PLOCK TO ALLOW LOCKING OF MULTIPLE PHYSICAL PAGES
;<3A.MONITOR>JSYSA.MAC.8, 18-May-78 12:45:59, EDIT BY MILLER
;TCO 1189. ADD NEW SMON AND TMON FUNCTIONS FOR STATUS REPROTING
;<3A.MONITOR>JSYSA.MAC.7, 26-Apr-78 16:38:23, EDIT BY MILLER
;DON'T SCAN DIR BLOCKS IF USER NUMBER GIVEN TO VERACT
;<3A.MONITOR>JSYSA.MAC.6,  2-Mar-78 17:47:01, EDIT BY MILLER
;ACCOUNT FOR NEW SKIP RETURN FROM TTDIBE
;<3A.MONITOR>JSYSA.MAC.5,  2-Mar-78 17:02:41, EDIT BY MILLER
;CHANGE CALL TO TTDOBE
;<3A.MONITOR>JSYSA.MAC.4, 17-Feb-78 09:02:21, EDIT BY MILLER
;FIX ERROR RETURN FOR PMAP TO APPEND FILE
;<3A.MONITOR>JSYSA.MAC.3, 15-Feb-78 08:12:31, EDIT BY MILLER
;USE SYMBOLIC OFFSETS IN PMCTL ERROR FUNCTION
;<3A.MONITOR>JSYSA.MAC.2,  3-Feb-78 11:31:57, EDIT BY MILLER
;FIXES TO "READ ERROR" FUNCTION OF PMCTL
;<3A.MONITOR>JSYSA.MAC.1, 23-Jan-78 20:47:32, EDIT BY MILLER
;ADD PLOCK JSYS CODE. FINISH PMCTL- ADD READ ERROR FUNCTION
;<3-MONITOR>JSYSA.MAC.525, 17-Nov-77 12:16:24, EDIT BY KIRSCHEN
;FIX CLOBBERED AC IN RELDAL WHEN DEASSIGNING ALL DEVICES
;<3-MONITOR>JSYSA.MAC.524, 11-Nov-77 14:59:46, EDIT BY KIRSCHEN
;REMOVE SYMBOL FROM .SETER FOR DOCUMENTATION CONSISTENCY
;<3-MONITOR>JSYSA.MAC.523,  9-Nov-77 21:04:39, EDIT BY MILLER
;MAKE LOGIN GET DEFAULT ACCOUNT IF USER 3=0
;<3-MONITOR>JSYSA.MAC.522,  9-Nov-77 15:05:22, EDIT BY MILLER
;TURN OFF WHELL IF SETACT FAILS IN .LOGIN
;<3-MONITOR>JSYSA.MAC.521,  7-Nov-77 20:36:28, EDIT BY HURLEY
;FIX GTDIR TO RETURN UPDATE GROUP COUNT CORRECTLY EVEN IF DIR IS SICK
;<3-MONITOR>JSYSA.MAC.520,  7-Nov-77 13:03:05, EDIT BY KIRSCHEN
;MORE COPYRIGHT UPDATING...
;<3-MONITOR>JSYSA.MAC.519,  2-Nov-77 01:14:49, Edit by LCAMPBELL
;FIX ADDRESS BREAK
;<3-MONITOR>JSYSA.MAC.518, 28-Oct-77 16:46:33, EDIT BY KIRSCHEN
;MORE MAKING OPERATOR VALID FOR WHEELS
;<3-MONITOR>JSYSA.MAC.517, 20-Oct-77 11:29:31, EDIT BY KIRSCHEN
;FIX WRONG CODE GETTING SDB ADDRESS IN VACCT AT SCNDNO+3
;<3-MONITOR>JSYSA.MAC.516, 18-Oct-77 16:45:39, EDIT BY KIRSCHEN
;MAKE OPERATOR A VALID ACCOUNT FOR ENABLED WHEELS (EVEN IF NOT OTHERWISE VALID)
;<3-MONITOR>JSYSA.MAC.515, 12-Oct-77 13:53:21, EDIT BY KIRSCHEN
;UPDATE COPYRIGHT FOR RELEASE 3
;<3-MONITOR>JSYSA.MAC.514, 30-Sep-77 21:30:30, EDIT BY DBELL
;MAKE ALLOC JSYS CHECK FOR UNASSIGNED JOBS.  TCO 1868.
;<3-MONITOR>JSYSA.MAC.513, 21-Sep-77 14:38:40, EDIT BY HURLEY
;<3-MONITOR>JSYSA.MAC.512, 21-Sep-77 14:30:20, EDIT BY HURLEY
;FIX GTDIR TO WORK IF USER SUPPLIES PASSWORD IN AC 3
;<3-MONITOR>JSYSA.MAC.511,  9-Sep-77 14:05:13, EDIT BY HURLEY
;SPEED UP VERACT
;<3-MONITOR>JSYSA.MAC.510,  7-Sep-77 14:18:02, EDIT BY P.HURLEY
;<3-MONITOR>JSYSA.MAC.509, 26-Aug-77 09:06:27, Edit by MACK
;BIT DEFINITION AC%MCH ADDED
;<3-MONITOR>JSYSA.MAC.508, 17-Aug-77 14:27:06, EDIT BY HURLEY
;<3-MONITOR>JSYSA.MAC.507, 17-Aug-77 13:14:33, Edit by MACK
;VERACT SCANS FOR WILDCARD USER NAMES CORRECTLY
;<3-MONITOR>JSYSA.MAC.506, 16-Aug-77 13:48:30, Edit by MACK
;VERACT BUG FIX
;SETJB NO LONGER MAKES USAGE FILE ENTRY FOR SESSION REMARKS
;<3-MONITOR>JSYSA.MAC.505, 16-Aug-77 12:51:50, Edit by MACK
;VERACT BUG FIXES
;<3-MONITOR>JSYSA.MAC.504, 16-Aug-77 09:26:49, Edit by MACK
;VERACT DOES CORRECT CHECK FOR EXPIRED ACCTSR OR EXPIRED CSHACT
;<3-MONITOR>JSYSA.MAC.503, 15-Aug-77 09:10:05, EDIT BY MILLER
;TCO 1852. GIVE ARGX06 IF PMAP ARG PAGE # > 777777
;<3-MONITOR>JSYSA.MAC.502, 12-Aug-77 17:30:34, Edit by LCAMPBELL
;ADD FUNCTION TO ADBRK TO RETURN ADDRESS OF BROKEN INSTRUCTION
;<3-MONITOR>JSYSA.MAC.501, 11-Aug-77 12:08:36, Edit by MACK
;TCO 1822 - VERACT BECOMES KEEPER OF CSHACT (CACHED ACOUNT)
;<3-MONITOR>JSYSA.MAC.499, 11-Aug-77 10:50:43, EDIT BY HURLEY
;ADD SUPPORT FOR WILD CARDED USER NAME STRINGS IN ACCOUNT VALIDATION
;<3-MONITOR>JSYSA.MAC.498, 11-Aug-77 09:34:25, EDIT BY HURLEY
;MAKE ERSTR GET ERRMES.BIN FROM SYSTEM:
;<3-MONITOR>JSYSA.MAC.497, 10-Aug-77 14:22:56, Edit by MACK
;SETJB MAKES USAGE FILE ENTRY WHEN JOB SESSION REMARK CHANGES
;<3-MONITOR>JSYSA.MAC.496, 10-Aug-77 12:06:48, EDIT BY HURLEY
;ALLOW VACCT TO BE EXECUTED BY NON-PRIVELEGED USERS
;<3-MONITOR>JSYSA.MAC.495,  8-Aug-77 14:37:12, Edit by HESS
;FIX UFWFET TO ALLOW CORRECT USE OF USER EFFECTIVE ADDRS COMP
;<3-MONITOR>JSYSA.MAC.494,  8-Aug-77 11:03:30, Edit by MACK
;TURN ON CORRECT USER CAPABILITIES IN LOGIN ONLY AFTER ACCOUNT HAS BEEN VALIDATED
;<3-MONITOR>JSYSA.MAC.493,  6-Aug-77 14:51:38, Edit by LCAMPBELL
;FIX ABRED FUNCT. OF ADBRK TO ONLY RETURN ADDRESS IN 2
;<3-MONITOR>JSYSA.MAC.492,  5-Aug-77 15:25:45, Edit by HESS
;<3-MONITOR>JSYSA.MAC.491,  5-Aug-77 10:17:41, Edit by MACK
;PUT SETACT BUFFER BACK TO OLD SIZE
;<3-MONITOR>JSYSA.MAC.490,  4-Aug-77 18:56:51, Edit by HESS
;<3-MONITOR>JSYSA.MAC.489,  4-Aug-77 12:19:00, Edit by MACK
;INCREASE SIZE OF SETACT BUFFER FOR ACCOUNT (ACTBUF)
;MAKE ENACT CODE TURN ON AVALON WHEN ACCOUNT VALIDATION ENABLED
;<3-MONITOR>JSYSA.MAC.488,  3-Aug-77 15:00:02, EDIT BY KIRSCHEN
;MAKE GACCT CALL MAPJSB INSTEAD OF SETJSB
;<3-MONITOR>JSYSA.MAC.487,  3-Aug-77 13:33:36, Edit by LCAMPBELL
;FIX .ABRED FUNCTION OF ADBRK
;<3-MONITOR>JSYSA.MAC.486,  3-Aug-77 11:52:32, Edit by HESS
;RE-ARRANGE USAGE CODE
;<3-MONITOR>JSYSA.MAC.485,  2-Aug-77 09:20:59, Edit by HESS
;ADD SETUP FOR CTIMON (CONNECT TIME OF DAY)
;<3-MONITOR>JSYSA.MAC.484,  1-Aug-77 16:10:09, Edit by MACK
;GTDIR RETURNS THE CORRECT STRING IF NO DEFAULT ACCOUNT EXISTS
;<3-MONITOR>JSYSA.MAC.483,  1-Aug-77 09:33:26, Edit by HESS
;ADD NEW USAGE ITEM TYPES TO UTYPTB (VERSION # , SPACE FILL)
;<3-MONITOR>JSYSA.MAC.482, 31-Jul-77 14:37:51, Edit by LCAMPBELL.ADBRK
;DON'T CLEAR ADDRESS BREAK ON .RESET, IT'S A BAD IDEA
;<3-MONITOR>JSYSA.MAC.481, 30-Jul-77 01:45:29, EDIT BY CROSSLAND
;REMOVE SPECIAL CHECKS FOR NVT'S
;<3-MONITOR>JSYSA.MAC.480, 29-Jul-77 14:41:01, Edit by LCAMPBELL.ADBRK
;CLEAR ADDRESS BREAKS IN .RESET
;<3-MONITOR>JSYSA.MAC.479, 29-Jul-77 11:36:38, Edit by HESS
;ADD BATCH/TS BIT TO USAGE HEADER
;<3-MONITOR>JSYSA.MAC.478, 28-Jul-77 17:11:19, EDIT BY HURLEY
;MAKE LOWERCASE PASSWORDS WORK
;<3-MONITOR>JSYSA.MAC.477, 28-Jul-77 13:43:51, Edit by MACK
;MAKE CACCT JSYS RETURN ERROR CODE FROM ROUTINES IT CALLS
;<3-MONITOR>JSYSA.MAC.475, 27-Jul-77 23:13:47, EDIT BY CLEMENTS.CALVIN
; Change XBLTUM to BLTUM in CRJOB
;<3-MONITOR>JSYSA.MAC.474, 27-Jul-77 21:09:03, Edit by LCAMPBELL
;CHANGE CALLING SEQUENCE FOR SETBRK TO BE JSP T4,SETBRK
;<3-MONITOR>JSYSA.MAC.473, 27-Jul-77 14:58:45, Edit by MACK
;TCO 1822 - ADD USAGE JSYS ROUTINE UFNENA TO ENABLE ACCOUNT VALIDAITON
;<3-MONITOR>JSYSA.MAC.472, 27-Jul-77 10:18:21, EDIT BY HURLEY
;CLEANUP
;<3-MONITOR>JSYSA.MAC.471, 26-Jul-77 17:47:17, EDIT BY HURLEY
;FIXED GTDIR TO RETURN THE CORRECT NUMBER OF ARGUMENTS
;<3-MONITOR>JSYSA.MAC.470, 26-Jul-77 10:00:14, EDIT BY HURLEY
;CLEANUP
;<3-MONITOR>JSYSA.MAC.469, 25-Jul-77 18:58:34, Edit by LCAMPBELL
;FIX ADDRESS BREAK
;<3-MONITOR>JSYSA.MAC.468, 25-Jul-77 17:05:01, Edit by MACK
;TCO 1822 - GTDIR ADDITION TO HANDLE DEFAULT DIR ACCOUNT
;VERACT LETS WHOPER USE ANY VALID ACCOUNT ON SYSTEM
;<3-MONITOR>JSYSA.MAC.467, 25-Jul-77 12:17:16, Edit by HESS
;ADD INPUT AND OUTPUT SPOOLER RECORDS TO USAGE JSYS
;<3-MONITOR>JSYSA.MAC.466, 24-Jul-77 20:17:08, Edit by LCAMPBELL
;<3-NSW-MONITOR>JSYSA.MAC.2, 22-Jul-77 23:52:36, EDIT BY CLEMENTS
;<3-NSW-MONITOR>JSYSA.MAC.1, 22-Jul-77 22:54:20, EDIT BY CLEMENTS
; MOVE TIMER AND LGTAD OUT TO TIMER.MAC
;<3-MONITOR>JSYSA.MAC.464, 22-Jul-77 14:29:42, EDIT BY HURLEY
;MAKE ALL USERS HAVE MD%SA PRIVILEGE
;<3-MONITOR>JSYSA.MAC.463, 21-Jul-77 19:48:50, EDIT BY HURLEY
;<3-MONITOR>JSYSA.MAC.462, 21-Jul-77 17:36:27, Edit by MACK
;VERACT BUG FIX
;<3-MONITOR>JSYSA.MAC.461, 21-Jul-77 13:45:51, EDIT BY OPERATOR
;FIXED LOGIN'S COUNT FOR COPYING TO USRNAM
;<3-MONITOR>JSYSA.MAC.460, 21-Jul-77 10:57:31, Edit by MACK
;VERACT BUG FIX
;<3-MONITOR>JSYSA.MAC.459, 20-Jul-77 20:03:07, EDIT BY HALL
;TCO 1813 - MAKE GTDIR SUCCEED IF CALLER CAN ACCESS SUPERIOR DIRECTORY
;<3-MONITOR>JSYSA.MAC.458, 20-Jul-77 15:11:31, Edit by MACK
;<3-MONITOR>JSYSA.MAC.457, 20-Jul-77 14:33:22, Edit by MACK
;TCO 1822 - VERACT COMPARES ACCOUNT AGAINST ACCTSR BEFORE SCANNING DATA BASE
;<3-MONITOR>JSYSA.MAC.455, 20-Jul-77 13:35:46, Edit by HESS
;<3-MONITOR>JSYSA.MAC.454, 19-Jul-77 16:46:04, Edit by HESS
;<3-MONITOR>JSYSA.MAC.453, 19-Jul-77 11:28:12, Edit by HESS
;ADD DISK USAGE RECORD TO USAGE (ALSO .USTAB DATA TYPE)
;<3-MONITOR>JSYSA.MAC.452, 15-Jul-77 11:55:13, Edit by MACK
;SETACT BUG FIX (BAD BLT)
;<3-MONITOR>JSYSA.MAC.451, 15-Jul-77 11:06:42, Edit by HESS
;POKE JOB 0 WHEN USAGE QUEUE IS FULL
;<3-MONITOR>JSYSA.MAC.450, 15-Jul-77 10:17:39, EDIT BY HALL
;TCO 1813 - MOVE CRDIR TO JSYSF
;<3-MONITOR>JSYSA.MAC.449, 14-Jul-77 19:58:38, Edit by MACK
;<3-MONITOR>JSYSA.MAC.448, 14-Jul-77 19:50:16, Edit by MACK
;SETACT CLEARS ACTBUF BEFORE COPYING ACCOUNT STRING
;<3-MONITOR>JSYSA.MAC.447, 14-Jul-77 18:58:58, Edit by MACK
;.CACCT CALLS  USTDIR BEFORE LOGCJM
;<3-MONITOR>JSYSA.MAC.446, 14-Jul-77 16:06:32, Edit by HESS
;<3-MONITOR>JSYSA.MAC.445, 14-Jul-77 14:29:26, Edit by MACK
;TCO 1822 - .CACCT NOW CALLS SETDIR FOR CALL TO SETACT
;<3-MONITOR>JSYSA.MAC.444, 13-Jul-77 19:36:18, EDIT BY HURLEY
;<3-MONITOR>JSYSA.MAC.443, 13-Jul-77 17:33:07, Edit by MACK
;TCO 1822 - LOGIN UNLOCKS AND THEN LOCKS DIR AROUND CALL TO SETACT
;VERACT ALSO CHECKS FOR SPECIAL OPERATOR ACCOUNT BEFORE GIVING BAD RETURN
;<3-MONITOR>JSYSA.MAC.442, 13-Jul-77 15:19:13, Edit by HESS
;<3-MONITOR>JSYSA.MAC.441, 13-Jul-77 12:15:19, Edit by HESS
;ADD GENERAL USAGE CALL CODE (.USENT)
;<3-MONITOR>JSYSA.MAC.440, 13-Jul-77 08:23:03, Edit by MACK
;TCO 1822 - FIX VALUE PLACED IN ACCTSL IN SETACT:
;<3-MONITOR>JSYSA.MAC.439, 12-Jul-77 17:56:35, Edit by HESS
;<3-MONITOR>JSYSA.MAC.438, 12-Jul-77 12:41:29, EDIT BY HALL
;TCO 1740 - MAKE SOBE AND SOBF HANDLE LCKTTY FAILURE CONSISTENT WITH
;	CHKTTR FAILURE
;<3-MONITOR>JSYSA.MAC.437, 11-Jul-77 23:45:33, EDIT BY CROSSLAND
;TCO 1841 FIX SFCOC,SFMOD AND SFPAR TO NOT CLOBBER AC 1 ON ERRORS
;<3-MONITOR>JSYSA.MAC.436, 11-Jul-77 14:44:33, Edit by LCAMPBELL
;<3-MONITOR>JSYSA.MAC.435, 11-Jul-77 14:11:58, Edit by LCAMPBELL
;TCO 1838 - Address break
;<3-MONITOR>JSYSA.MAC.434, 11-Jul-77 11:50:01, Edit by HESS
;ADD FUNCTION TO USAGE JSYS TO SET CHECKPOINT INTERVAL
;<3-MONITOR>JSYSA.MAC.433, 11-Jul-77 08:27:22, Edit by MACK
;CHANGE STKVAR TO TRVAR IN SETACT
;<3-MONITOR>JSYSA.MAC.432, 10-Jul-77 23:04:39, EDIT BY CROSSLAND
;FIX CRJOB NO PASSWORD CHECK IN LOGIN
;<3-MONITOR>JSYSA.MAC.431,  7-Jul-77 22:01:32, Edit by MACK
;SETACT AND .LOGIN CHANGE FOR CALL TO SETACT
;<3-MONITOR>JSYSA.MAC.429,  7-Jul-77 17:47:13, Edit by HESS
;<3-MONITOR>JSYSA.MAC.428,  7-Jul-77 16:24:55, Edit by MACK
;VERACT BUG FIXES
;<3-MONITOR>JSYSA.MAC.427,  7-Jul-77 13:18:49, Edit by HESS
;<3-MONITOR>JSYSA.MAC.426,  7-Jul-77 08:14:29, Edit by HESS
;REMOVE CKPSIZ
;<3-MONITOR>JSYSA.MAC.425,  6-Jul-77 16:24:58, EDIT BY HURLEY
;<3-MONITOR>JSYSA.MAC.424,  6-Jul-77 15:29:35, Edit by HESS
;<3-MONITOR>JSYSA.MAC.423,  6-Jul-77 14:21:47, EDIT BY MILLER
;CHANGE STRX DEFSTR TO VASTRX
;<3-MONITOR>JSYSA.MAC.422,  6-Jul-77 13:39:26, Edit by MACK
;<3-MONITOR>JSYSA.MAC.421,  6-Jul-77 13:27:24, Edit by MACK
;<3-MONITOR>JSYSA.MAC.420,  6-Jul-77 12:27:59, Edit by MACK
;TCO 1822 - CHANGE CACCT TO VALIDATE ACCOUNTS
;<3-MONITOR>JSYSA.MAC.419,  6-Jul-77 08:31:37, Edit by MACK
;VACCT FIXES
;<3-MONITOR>JSYSA.MAC.418,  5-Jul-77 17:16:01, EDIT BY HURLEY
;TCO 1834 - ADD SUPPORT FOR .CDLEN IN GTDIR
;<3-MONITOR>JSYSA.MAC.417,  5-Jul-77 11:29:50, Edit by HESS
;CHANGE USAGE HEADER DEFS AND DEFINE CKPSIZ FOR MEXEC
;<3-MONITOR>JSYSA.MAC.416,  5-Jul-77 10:58:06, Edit by MACK
;<3-MONITOR>JSYSA.MAC.415,  4-Jul-77 19:32:09, EDIT BY CROSSLAND
;FIX COMMENTS IN ACCES JSYS
;<3-MONITOR>JSYSA.MAC.414,  3-Jul-77 17:59:01, Edit by HESS
;<3-MONITOR>JSYSA.MAC.413,  3-Jul-77 14:07:22, Edit by HESS
;<3-MONITOR>JSYSA.MAC.412,  3-Jul-77 13:57:20, Edit by HESS
;<3-MONITOR>JSYSA.MAC.411, 30-Jun-77 13:15:19, Edit by MACK
;VERACT BUG FIXES
;<3-MONITOR>JSYSA.MAC.410, 29-Jun-77 08:50:55, Edit by HESS
;<3-MONITOR>JSYSA.MAC.409, 29-Jun-77 07:29:52, Edit by MACK
;VACCT JSYS BUG FIXES
;<3-MONITOR>JSYSA.MAC.408, 28-Jun-77 16:39:55, Edit by HESS
;<3-MONITOR>JSYSA.MAC.407, 28-Jun-77 12:02:30, Edit by MACK
;TCO 1822 - ADD VACCT JSYS
;<3-MONITOR>JSYSA.MAC.406, 28-Jun-77 11:30:02, EDIT BY OSMAN
;MAKE NIN NOT SAY "?END OF INPUT FILE REACHED" ON PREMATURE END OF BYTE STRING
;<3-MONITOR>JSYSA.MAC.405, 27-Jun-77 20:20:57, Edit by HESS
;<3-MONITOR>JSYSA.MAC.404, 27-Jun-77 20:09:53, Edit by HESS
;<3-MONITOR>JSYSA.MAC.403, 27-Jun-77 13:10:07, Edit by HESS
;REMOVE REFS TO OLD ACCOUNTING INFO IN JSB
;<3-MONITOR>JSYSA.MAC.402, 27-Jun-77 11:58:24, Edit by HESS
;FIX DEFERRED SPOOLING BIT IN SJBTAB CODE
;<3-MONITOR>JSYSA.MAC.401, 23-Jun-77 17:00:51, Edit by HESS
;<3-MONITOR>JSYSA.MAC.400, 22-Jun-77 15:23:49, Edit by MACK
;BUG FIXES TO ENACT
;<3-MONITOR>JSYSA.MAC.399, 21-Jun-77 04:07:58, EDIT BY CROSSLAND
;BUG FIXES TO CRJOB
;REMOVE TCO 1829
;<3-MONITOR>JSYSA.MAC.398, 20-Jun-77 22:34:08, Edit by HESS
;<3-MONITOR>JSYSA.MAC.396, 20-Jun-77 17:46:34, Edit by MACK
;TCO 1822 - ADDED ENACT JSYS
;<3-MONITOR>JSYSA.MAC.395, 20-Jun-77 12:57:52, Edit by MACK
;TCO 1822 - ADDED SETJB FUNCTION SJBSRM TO SET JOB SESSION REMARK
;<3-MONITOR>JSYSA.MAC.393, 20-Jun-77 06:36:40, EDIT BY CROSSLAND
;TCO 1829 ADD AC%CKP AND AC%NOC TO ACCES
;<3-MONITOR>JSYSA.MAC.392, 17-Jun-77 17:50:06, Edit by HESS
;<3-MONITOR>JSYSA.MAC.391, 17-Jun-77 00:25:03, EDIT BY CROSSLAND
;FIX UP CALL TO NVTDET
;<3-MONITOR>JSYSA.MAC.390, 16-Jun-77 16:50:27, Edit by HESS
;TCO 1821 - ADD USAGE JSYS
;<1MURPHY>JSYSA.MAC.3, 16-Jun-77 14:22:09, EDIT BY MURPHY
;TCO #1823 - PMAP
;<3-MONITOR>JSYSA.MAC.388, 15-Jun-77 11:53:34, Edit by MACK
;<3-MONITOR>JSYSA.MAC.387, 15-Jun-77 11:47:18, Edit by MACK
;TCO 1822 - CHANGE SMON AND TMON TO RETURN ACCOUNT VALIDATION STATUS
;<3-MONITOR>JSYSA.MAC.386, 13-Jun-77 22:47:33, EDIT BY CROSSLAND
;TCO 1816 ZERO T3  (DEFERED INTERRUPT MASK) BEFORE DOING STIW IN RESET JSYS
;<3-MONITOR>JSYSA.MAC.385, 11-Jun-77 10:45:59, EDIT BY HALL
;TCO 1813- MADE DIRST CALL JFNSSD INSTEAD OF JFNSS TO ALLOW DOTS IN
;	DIRECTORY NAMES
;<3-MONITOR>JSYSA.MAC.384, 11-Jun-77 03:35:52, EDIT BY CROSSLAND
;MORE TCO 1742 DEBUGGING
;<2-PERF>JSYSA.MAC.345, 27-May-77 18:00:40, EDIT BY HURLEY
;<2-PERF>JSYSA.MAC.344, 26-May-77 17:54:40, EDIT BY MURPHY
;<2-PERF>JSYSA.MAC.343, 26-May-77 14:55:41, EDIT BY HURLEY
;ADDED CONNECTED DIRECTORY NAME STRING TO JSB
;<3-MONITOR>JSYSA.MAC.382,  3-Jun-77 10:27:02, EDIT BY HALL
;FIX TYPOS IN LEN'S EDIT
;<3-MONITOR>JSYSA.MAC.381,  2-Jun-77 22:40:29, EDIT BY BOSACK
;RETURN SUBDIR QUOTA AND CREATABLE USER GROUPS FROM GTDIR
;<3-MONITOR>JSYSA.MAC.380,  1-Jun-77 16:10:20, EDIT BY MILLER
;DON'T ALLOW PROXY CONNECT OF JOB 0
;<3-MONITOR>JSYSA.MAC.379, 10-May-77 13:07:50, EDIT BY HURLEY
;FIX ACCOUNT STRINGS OF 5 CHARACTERS TO HAVE A NULL AFTER THEM
;<3-MONITOR>JSYSA.MAC.378,  8-May-77 18:06:43, EDIT BY CROSSLAND
;<3-MONITOR>JSYSA.MAC.377, 29-Apr-77 10:14:09, EDIT BY CROSSLAND
;MORE TCO 1742 MERGE ARPANET CODE.
;<3-MONITOR>JSYSA.MAC.376,  5-Apr-77 15:21:37, EDIT BY HALL
;TCO 1740 - MAKE RELD SEE IF DEVICE IS ASSIGNED BEFORE DEASSIGNING IT
;	(WAS TRYING TO DEALLOCATE TERMINAL THAT WASN'T ACTIVE)
;<3-MONITOR>JSYSA.MAC.375, 17-Mar-77 15:13:14, Edit by MCLEAN
;FIX SNOOP FOR EXTENDED ADDRESSING
;<3-MONITOR>JSYSA.MAC.374,  9-Mar-77 16:05:52, EDIT BY HALL
;TCO 1740 - MADE RELD INTERRUPTIBLE WHEN WAITING FOR TERMINAL'S LOCK
;	COUNT TO GO TO 0
;<3-MONITOR>JSYSA.MAC.373, 28-Feb-77 11:26:13, EDIT BY HURLEY
;ADD TEST IN SCHEDULER TO NOT SCHEDULE A JOB OUT OF UTREP (UTEST)
;<3-MONITOR>JSYSA.MAC.372, 28-Feb-77 04:40:07, EDIT BY CROSSLAND
;TCO 1743  ADD CRJOB
;TCO 1742 ADD MERGE ARPANET CODE IN SMON AND TMON
;<3-MONITOR>JSYSA.MAC.371, 25-Feb-77 13:08:54, EDIT BY HALL
;TCO 1740 - BUG FIX IN STI
;<3-MONITOR>JSYSA.MAC.370, 24-Feb-77 16:10:57, EDIT BY HALL
;TCO 1740 - FIXED TYPO IN STI, MOVED ASND TO JSYSF BECAUSE NEEDS DEV
;<3-MONITOR>JSYSA.MAC.369, 23-Feb-77 20:16:04, EDIT BY HALL
;TCO 1740 - CHANGES TO ALL TELETYPE-RELATED JSYS'S FOR TELETYPE REORGANIZATION
;<3-MONITOR>JSYSA.MAC.368, 23-Feb-77 18:10:50, EDIT BY HURLEY
;<3-MONITOR>JSYSA.MAC.367, 23-Feb-77 15:13:03, EDIT BY HURLEY
;FIX UP .SNPAD FUNCTION TO RETURN BEST SYMBOL INSTEAD OF EXACT ONLY
;<3-MONITOR>JSYSA.MAC.366, 14-Feb-77 11:17:41, EDIT BY HURLEY
;<3-MONITOR>JSYSA.MAC.365,  8-Feb-77 00:46:50, Edit by MCLEAN
;REMOVE DTFLG
;<3-MONITOR>JSYSA.MAC.364,  7-Feb-77 19:14:21, EDIT BY HURLEY
;<3-MONITOR>JSYSA.MAC.363,  7-Feb-77 08:30:38, EDIT BY HURLEY
;<3-MONITOR>JSYSA.MAC.362,  7-Feb-77 08:27:09, EDIT BY HURLEY
;TCO 1731 - ADD THE UTEST JSYS
;<3-MONITOR>JSYSA.MAC.361, 29-Jan-77 17:10:31, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.360, 26-Jan-77 14:31:10, EDIT BY HURLEY
;TCO 1722 - ADD FUNCTION 7 (.SNPAD) TO SNOOP JSYS
;<3-MONITOR>JSYSA.MAC.359, 24-Jan-77 10:07:34, EDIT BY HURLEY
;MAKE ALPHA-NUMERIC ACCOUNTS ALWAYS LEGAL
;<3-MONITOR>JSYSA.MAC.358, 23-Jan-77 15:33:15, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.357, 23-Jan-77 15:02:12, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.356, 18-Jan-77 10:02:37, EDIT BY HURLEY
;FIXED ASND TO NOT FAIL IF DEVICE CANNOT BE DISMOUNTED
;<3-MONITOR>JSYSA.MAC.355, 16-Jan-77 00:08:22, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.354, 13-Jan-77 18:01:24, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.353, 11-Jan-77 00:07:07, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.352, 10-Dec-77 15:46:43, Edit by MCLEAN
;TCO 1708 ADD FLOCK TO PRARG
;<3-MONITOR>JSYSA.MAC.351,  5-Jan-77 16:21:39, EDIT BY HALL
;BUG FIX IN SPACS AND COMMENTS IN RFMOD
;<3-MONITOR>JSYSA.MAC.350,  5-Jan-77 14:46:34, Edit by HESS
;TCO 1705 - CORRECT TIME ZONE INFO IN FE
;<3-MONITOR>JSYSA.MAC.349,  3-Jan-77 16:03:40, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.348, 30-Dec-76 15:07:50, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.347, 30-Dec-76 15:06:50, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.346, 27-Dec-76 17:33:24, EDIT BY HURLEY
;<2-MONITOR>JSYSA.MAC.340,  9-Dec-76 18:04:40, EDIT BY MILLER
;PREVENT CPMAP FROM ITRAP'ING
;<2-MONITOR>JSYSA.MAC.339,  8-Dec-76 14:48:06, EDIT BY BOSACK
;<3-MONITOR>JSYSA.MAC.343,  2-Dec-76 03:34:25, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.342, 30-Nov-76 12:12:13, EDIT BY MILLER
;FIX TYPEO IN CPMAP
;<3-MONITOR>JSYSA.MAC.341, 27-Nov-76 23:24:34, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.340, 27-Nov-76 17:39:37, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.339, 27-Nov-76 14:33:36, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.338, 26-Nov-76 17:46:14, Edit by MCLEAN
;<3-MONITOR>JSYSA.MAC.337, 26-Nov-76 17:44:52, Edit by MCLEAN
;TCO 1669 EXTENDED ADDRESSING
;<2-MONITOR>JSYSA.MAC.335, 23-Nov-76 09:11:34, EDIT BY MILLER
;ADD TRVAR TO RPACS JSYS TO MAKE CPMAP WORK RIGHT
;<2-MONITOR>JSYSA.MAC.334, 21-Nov-76 19:59:13, EDIT BY BOSACK
;<2-MONITOR>JSYSA.MAC.333, 21-Nov-76 19:50:30, EDIT BY BOSACK
;<2-MONITOR>JSYSA.MAC.332, 18-Nov-76 20:16:37, EDIT BY KIRSCHEN
;MOVE MSTR CODE TO SEPARATE MODULE
;<2-MONITOR>JSYSA.MAC.331, 18-Nov-76 13:37:55, Edit by HURLEY
;<2-MONITOR>JSYSA.MAC.330, 18-Nov-76 13:05:37, Edit by HURLEY
;MORE TIME ZONE EDITS
;<2-MONITOR>JSYSA.MAC.329, 17-Nov-76 15:16:15, EDIT BY KIRSCHEN
;MORE OF EDIT TO FIX RACE IN DISMOUNT CODE
;<2-MONITOR>JSYSA.MAC.328, 16-Nov-76 17:50:20, Edit by HESS
;CHANGE STRINI TO FIX <ROOT-DIRECTORY> ON DISK.
;<2-MONITOR>JSYSA.MAC.327, 16-Nov-76 17:37:35, EDIT BY BOSACK
;<2-MONITOR>JSYSA.MAC.326, 16-Nov-76 14:27:56, Edit by MACK
;TCO 1666 - ADD TIME ZONE FUNCTIONS TO SMON AND TMON
;<2-MONITOR>JSYSA.MAC.323, 16-Nov-76 11:20:59, EDIT BY KIRSCHEN
;CHECK FOR CORRECT UNIT WITHIN STRUCTURE WHEN MOUNTING
;<2-MONITOR>JSYSA.MAC.322, 15-Nov-76 16:32:09, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.321, 15-Nov-76 12:37:33, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.320, 15-Nov-76 10:50:52, EDIT BY KIRSCHEN
;FIX RACE IN DISMOUNT CODE
;<2-MONITOR>JSYSA.MAC.319, 14-Nov-76 19:37:27, EDIT BY HURLEY
;REMOVE CNDIR AND UPDATE GTDIR TO CONFORM TO THE RELEASE 2 SPEC
;<2-MONITOR>JSYSA.MAC.318, 14-Nov-76 13:47:52, EDIT BY BOSACK
;<2-MONITOR>JSYSA.MAC.317, 13-Nov-76 17:33:30, EDIT BY BOSACK
;<2-MONITOR>JSYSA.MAC.316, 13-Nov-76 16:18:49, EDIT BY BOSACK
;ADD PMCTL
;<2-MONITOR>JSYSA.MAC.315, 12-Nov-76 10:56:18, Edit by HESS
;ADD NEW ERROR CODES IN .MSINC & .MSDEC FUNCTIONS OF MSTR
;<2-MONITOR>JSYSA.MAC.314, 11-Nov-76 16:39:34, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.313, 11-Nov-76 16:23:30, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.312, 10-Nov-76 16:58:24, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.311, 10-Nov-76 11:46:17, EDIT BY KIRSCHEN
;FIX CLEANUP PROCEDURES ON ERRORS DURING MOUNTING
;<2-MONITOR>JSYSA.MAC.310, 10-Nov-76 10:08:36, Edit by HESS
;ADD JSVAR FACILITY TO WRTHOM
;<2-MONITOR>JSYSA.MAC.309,  9-Nov-76 17:25:54, EDIT BY HURLEY
;<2-MONITOR>JSYSA.MAC.308,  9-Nov-76 15:44:14, EDIT BY HURLEY
;FIXED .MSGSU BUG IF STR NOT IN USE BY A JOB
;<2-MONITOR>JSYSA.MAC.307,  9-Nov-76 13:07:02, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.306,  9-Nov-76 11:08:54, EDIT BY KIRSCHEN
;ADD CNVINF ROUTINE TO CONVERT ASCII ID FIELDS TO PDP-11 ASCII
;<2-MONITOR>JSYSA.MAC.305,  8-Nov-76 15:36:31, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.304,  8-Nov-76 13:15:23, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.303,  8-Nov-76 13:08:46, EDIT BY KIRSCHEN
;MISC BUG FIXES IN MAKHOM, RENAME SOME MSTR ERROR LABELS
;<2-MONITOR>JSYSA.MAC.302,  5-Nov-76 16:16:18, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.301,  5-Nov-76 12:21:23, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.300,  5-Nov-76 11:12:28, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.299,  5-Nov-76 11:06:19, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.298,  5-Nov-76 10:54:07, EDIT BY KIRSCHEN
;RE-WRITE HOME BLOCKS WITH FE-FILESYSTEM POINTER AFTER WRITING HOME BLOCKS
;<2-MONITOR>JSYSA.MAC.297,  4-Nov-76 17:06:00, EDIT BY KIRSCHEN
;REMEMBER EXCLUSIVE MOUNTS IN THE JOB'S JSB IN CASE JOB LOGS OUT
;<2-MONITOR>JSYSA.MAC.296,  4-Nov-76 15:58:52, EDIT BY HURLEY
;RETURN MOUNTED, ACCESSED, AND CONNECTED FLAGS IN .MSGSU FUNCTION
;<2-MONITOR>JSYSA.MAC.295,  4-Nov-76 15:24:49, EDIT BY MILLER
;TCO 1649. MAKE PMAP NOINT WHEN MODIFYING MAP COUNTS/MAPS
;<2-MONITOR>JSYSA.MAC.294,  4-Nov-76 13:56:13, EDIT BY HURLEY
;<2-MONITOR>JSYSA.MAC.293,  4-Nov-76 11:16:44, EDIT BY KIRSCHEN
;MORE MSTR CLEANUP
;<2-MONITOR>JSYSA.MAC.292,  3-Nov-76 13:29:27, EDIT BY KIRSCHEN
;MAKE CHKNAM FORM A GOOD POINTER TO STR NAME
;<2-MONITOR>JSYSA.MAC.291,  3-Nov-76 11:37:24, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.290,  3-Nov-76 11:17:30, EDIT BY KIRSCHEN
;MOVE CALL TO MAKHOM FROM HOMCHK TO MSTMNT
;<2-MONITOR>JSYSA.MAC.289,  2-Nov-76 15:35:34, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.288,  2-Nov-76 12:12:18, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.287,  2-Nov-76 11:44:42, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.286,  1-Nov-76 16:38:44, EDIT BY KIRSCHEN
;STORE STR # BEFORE CHECKING FOR PS IN MSTDIS
;<2-MONITOR>JSYSA.MAC.285,  1-Nov-76 15:53:07, EDIT BY KIRSCHEN
;ADD RECONSTRUCTION OF ROOT-DIRECTORIES FOR MSTR JSYS
;<2-MONITOR>JSYSA.MAC.284,  1-Nov-76 14:47:38, EDIT BY KIRSCHEN
;DO NOT ALLOW MS%DIS TO BE SET FOR THE PUBLIC STRUCTURE
;<2-MONITOR>JSYSA.MAC.283,  1-Nov-76 10:31:27, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.282, 31-Oct-76 14:52:44, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.281, 31-Oct-76 14:45:14, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.280, 31-Oct-76 14:35:47, EDIT BY HURLEY
;<2-MONITOR>JSYSA.MAC.279, 30-Oct-76 15:23:38, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.278, 30-Oct-76 12:42:05, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.277, 29-Oct-76 16:24:27, EDIT BY KIRSCHEN
;CALL BLDNEW,BLDSDB INSTEAD OF CRTSTR, ADDSTR
;<2-MONITOR>JSYSA.MAC.276, 29-Oct-76 11:48:07, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.275, 29-Oct-76 11:01:34, EDIT BY KIRSCHEN
;CHANGE MOUNT CODE TO USE ADDSTR/CRTSTR ROUTINES IN DSKAL1
;<2-MONITOR>JSYSA.MAC.274, 29-Oct-76 10:30:44, EDIT BY HURLEY
;FIX UNACC TO NOT LOCK JSSTLK
;<2-MONITOR>JSYSA.MAC.273, 29-Oct-76 09:30:37, Edit by HESS
;CHANGE INITING FORK TO JOB # IN SDB
;<2-MONITOR>JSYSA.MAC.272, 28-Oct-76 17:43:43, EDIT BY KIRSCHEN
;FIX MOUNT BUG RESULTING IN FREE SPACE CLOBBERAGE
;<2-MONITOR>JSYSA.MAC.271, 27-Oct-76 16:01:05, EDIT BY KIRSCHEN
;ADD CAPABILITY TO MOUNT STR'S WITH "EXCLUSIVE" ACCESS
;<2-MONITOR>JSYSA.MAC.270, 26-Oct-76 13:24:42, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.269, 26-Oct-76 10:31:26, EDIT BY KIRSCHEN
;MOVE MNTBTB TO MSTR FROM CREIDX; MORE GENERAL MSTR IMPROVEMENTS
;<2-MONITOR>JSYSA.MAC.268, 25-Oct-76 11:08:25, EDIT BY KIRSCHEN
;USE FREE BLOCK FOR LOCAL STORAGE IN MSTMNT, INSTEAD OF STKVAR
;<2-MONITOR>JSYSA.MAC.267, 22-Oct-76 14:46:18, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.266, 22-Oct-76 12:27:13, EDIT BY KIRSCHEN
;MOVE ALL HOME BLOCK CHECKING IN MSTR INTO NEW ROUTINE HOMCHK
;<2-MONITOR>JSYSA.MAC.265, 21-Oct-76 11:32:23, EDIT BY KIRSCHEN
;IGNORE JOBS NOT LOGGED IN WHEN GETTING STRUCTURE USERS
;<2-MONITOR>JSYSA.MAC.264, 21-Oct-76 10:56:35, EDIT BY KIRSCHEN
;MORE MSTR CODE REORGANIZATION
;<2-MONITOR>JSYSA.MAC.263, 20-Oct-76 12:37:38, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.262, 20-Oct-76 12:14:18, EDIT BY KIRSCHEN
;BREAK OUT SOME CODE IN NEW ROUTINE STRINI FOR INITIALIZING STR'S
;RETURN  CORRECT # OF UNITS IN READ UNIT STATUS
;<2-MONITOR>JSYSA.MAC.261, 19-Oct-76 11:52:06, EDIT BY KIRSCHEN
;PASS UNIT # WITHIN STR TO MAKHOM
;<2-MONITOR>JSYSA.MAC.260, 18-Oct-76 18:22:55, EDIT BY HURLEY
;SPEED UP DIRST
;<2-MONITOR>JSYSA.MAC.259, 18-Oct-76 11:56:30, EDIT BY KIRSCHEN
;MOVE HOME BLOCK CREATION FROM MSTR TO NEW ROUTINE MAKHOM
;<2-MONITOR>JSYSA.MAC.258, 16-Oct-76 11:05:09, EDIT BY HALL
;TEMPORARILY MADE MSTR JFCL WHEN CHKBT FAILS
;<2-MONITOR>JSYSA.MAC.257, 15-Oct-76 11:07:28, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.256, 15-Oct-76 10:52:11, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.255, 15-Oct-76 10:47:17, EDIT BY KIRSCHEN
;MAKE VALIDATION OF THE STRUCTURE NAME A SUBROUTINE IN MSTMNT
;<2-MONITOR>JSYSA.MAC.254, 14-Oct-76 19:44:29, EDIT BY HURLEY
;TCO 1599 - ADD A LOGIN MESSAGE TO QUASAR FOR EACH JOB LOGGING IN
;<2-MONITOR>JSYSA.MAC.253, 14-Oct-76 16:15:17, EDIT BY HURLEY
;MAKE SPACE BE A LEGAL TERMINATOR FOR DEVICE NAME IN STDEV
;<2-MONITOR>JSYSA.MAC.252, 14-Oct-76 15:41:55, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.251, 14-Oct-76 11:19:24, EDIT BY KIRSCHEN
;ALLOCATE # OF PAGES GIVEN BY USER FOR FE FILE SYSTEM ON STR INITIALIZATION
;<2-MONITOR>JSYSA.MAC.250, 13-Oct-76 13:42:55, EDIT BY HURLEY
;REMAIN ENABLED DURING BOUTS IN EFACT JSYS
;<2-MONITOR>JSYSA.MAC.249, 13-Oct-76 09:58:03, EDIT BY KIRSCHEN
;CALL FEFSYS WHEN INITIALIZING A STRUCTURE
;<2-MONITOR>JSYSA.MAC.248, 12-Oct-76 15:19:47, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.247, 12-Oct-76 11:58:39, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.246, 12-Oct-76 11:18:37, EDIT BY KIRSCHEN
;CHECK FOR -1,,ADR IN FNDSTR
;<2-MONITOR>JSYSA.MAC.245, 11-Oct-76 09:55:34, EDIT BY KIRSCHEN
;ON DISMOUNT, FIX DEV TABLES WHILE NOSKED
;<2-MONITOR>JSYSA.MAC.244, 11-Oct-76 08:08:45, EDIT BY HURLEY
;<2-MONITOR>JSYSA.MAC.243,  8-Oct-76 13:27:37, EDIT BY KIRSCHEN
;FIX SOME STR INITIALIZATION BUGS INTRODUCED WHEN IDXTAB WAS MADE A FILE
;<2-MONITOR>JSYSA.MAC.242,  8-Oct-76 11:43:06, EDIT BY KIRSCHEN
;ACCEPT DEVICE DESIGNATORS AS WELL AS STRINGS FOR MSTR FUNCTIONS
;<2-MONITOR>JSYSA.MAC.241,  8-Oct-76 10:37:50, EDIT BY KIRSCHEN
;FIX CLEAN UP WHEN MNTER6 WAS CALLED ON MOUNT ERRORS
;<2-MONITOR>JSYSA.MAC.240,  7-Oct-76 15:23:11, EDIT BY KIRSCHEN
;CHANGES TO HANDLE THE INDEX TABLE AS A FILE
;FIX BUG IN STR INITIALIZATION - USE SIXBIT STR NAME IN HOME BLOCK
;<2-MONITOR>JSYSA.MAC.239,  6-Oct-76 15:16:41, EDIT BY HURLEY
;<2-MONITOR>JSYSA.MAC.238,  6-Oct-76 08:36:50, EDIT BY HURLEY
;MADE BIN1 GIVE ERROR RETURN ON EOF
;<2-MONITOR>JSYSA.MAC.237,  5-Oct-76 17:11:01, EDIT BY HALL
;FIXED ACCES TO CHECK FOR VALID JOB NUMBER
;<2-MONITOR>JSYSA.MAC.236,  5-Oct-76 14:18:31, EDIT BY MILLER
;CHANGE MSTR FUNCTIONS TO USE ASCIZ STRINGS INSTEAD OF SIXBIT
;<2-MONITOR>JSYSA.MAC.235,  5-Oct-76 13:05:55, EDIT BY HALL
;MADE ACCES TEST FOR CONNECT FUNCTION IF ANOTHER JOB IS SPECIFIED
;<2-MONITOR>JSYSA.MAC.234,  4-Oct-76 14:20:48, EDIT BY HURLEY
;TCO 1563 - MAKE SFCOC, SFMOD, SFPOS ALLOW .NULIO AS A DESIGNATOR
;<2-MONITOR>JSYSA.MAC.233,  4-Oct-76 14:14:59, EDIT BY MILLER
;TCO 1555. PREVENT PT CREATES ON INPUT
;CHANGED MSTR FUNCTIONS TO USE ASCIZ STRINGS INSTEAD OF SIXBIT
;<2-MONITOR>JSYSA.MAC.232,  1-Oct-76 12:09:36, EDIT BY HALL
;FIXED TYPO IN LOGIN EDIT
;<2-MONITOR>JSYSA.MAC.231,  1-Oct-76 12:01:39, EDIT BY HALL
;FIX TO ACCES - MOVED TEST FOR UNACCESS TO AFTER CHECK ON JOB NUMBER
;<2-MONITOR>JSYSA.MAC.230,  1-Oct-76 11:48:42, EDIT BY HALL
;MADE LOGIN STORE LOGGED IN DIRECTORY NUMBER AS ACCESSED
;<2-MONITOR>JSYSA.MAC.229,  1-Oct-76 11:21:59, EDIT BY HALL
;MADE ACCES GO TO MRETN ON SUCCESS
;<2-MONITOR>JSYSA.MAC.228,  1-Oct-76 10:40:22, EDIT BY HALL
;MADE ERSTR LOOK ON PS FOR ERRMES.BIN
;<2-MONITOR>JSYSA.MAC.227, 30-Sep-76 18:08:54, Edit by HESS
;CHANGE STDEVP TO USE RETURN FROM DEVLUX AS UNIQUE CODE
;<2-MONITOR>JSYSA.MAC.226, 30-Sep-76 17:45:17, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.225, 30-Sep-76 15:54:44, EDIT BY KIRSCHEN
;BUG FIXES IN ACCESS, FIXJOB, MOUNT-COUNT MANIPULATION
;<2-MONITOR>JSYSA.MAC.224, 30-Sep-76 13:01:23, EDIT BY HALL
;BUG FIXES IN ACCES (UNACC CALL) AND LOGIN (ARGUMENT FOR GTSTOF)
;<2-MONITOR>JSYSA.MAC.223, 29-Sep-76 17:31:53, EDIT BY KIRSCHEN
;MAKE DISMOUNT CODE RELEASE JSB STR BLOCK IF FREED
;<2-MONITOR>JSYSA.MAC.222, 29-Sep-76 17:19:31, EDIT BY KIRSCHEN
;FIX FIXJOB TO USE UNIQUE CODE INSTEAD OF STRUCTURE NUMBER
;<2-MONITOR>JSYSA.MAC.221, 29-Sep-76 15:18:01, EDIT BY HALL
;MADE UNACCESS A SEPARATE ROUTINE. REMOVED ALL REFERENCES TO JSSTR.
;MADE ACCES CALL FUTILI ROUTINES WITH UNIQUE CODE
;<2-MONITOR>JSYSA.MAC.220, 29-Sep-76 14:39:40, EDIT BY HALL
;MADE ACCES WAIT IF PASSWORD IS BAD
;<2-MONITOR>JSYSA.MAC.219, 29-Sep-76 13:50:07, EDIT BY KIRSCHEN
;FIX ALL CALLS TO GTSTOF TO PROVIDE STRUCTURE UNIQUE CODE
;<2-MONITOR>JSYSA.MAC.218, 28-Sep-76 17:02:10, EDIT BY HALL
;FIXED BUG IN UNACCESS CODE
;<2-MONITOR>JSYSA.MAC.217, 28-Sep-76 16:04:51, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.216, 28-Sep-76 12:02:41, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.215, 28-Sep-76 11:19:00, EDIT BY KIRSCHEN
;ADD GET STRUCTURE USERS FUNCTION OF MSTR
;<2-MONITOR>JSYSA.MAC.214, 27-Sep-76 18:22:45, EDIT BY HALL
;ADDED UNACCESS FUNCTION TO ACCES JSYS
;<2-MONITOR>JSYSA.MAC.213, 27-Sep-76 12:04:27, EDIT BY KIRSCHEN
;ISOLATE CODE TO INCREMENT/DECREMENT MOUNT COUNTS IN SEPARATE ROUTINES
;<2-MONITOR>JSYSA.MAC.212, 24-Sep-76 17:28:36, EDIT BY KIRSCHEN
;UNLOCK THE STRUCTURE LOCK AFTER CALLING FNDSTR
;<2-MONITOR>JSYSA.MAC.211, 24-Sep-76 16:32:33, Edit by HESS
;<2-MONITOR>JSYSA.MAC.210, 24-Sep-76 09:14:40, Edit by HESS
;<2-MONITOR>JSYSA.MAC.209, 23-Sep-76 17:12:39, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.208, 23-Sep-76 17:09:04, EDIT BY KIRSCHEN
;FIX TYPO IN PREVIOUS EDIT
;<2-MONITOR>JSYSA.MAC.207, 23-Sep-76 16:56:50, Edit by HESS
;CHANGE DEVICE DESIGNATORS FOR STURCTURES
;<2-MONITOR>JSYSA.MAC.206, 23-Sep-76 16:47:12, EDIT BY KIRSCHEN
;VALIDATE # OF PAGES FOR SWAPPING WHEN INITIALIZING A STRUCTURE
;<2-MONITOR>JSYSA.MAC.205, 23-Sep-76 16:05:46, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.204, 23-Sep-76 15:00:37, EDIT BY KIRSCHEN
;ISSUE MESSAGE TO JOBS USING A STRUCTURE THAT IS DISMOUNTED
;<2-MONITOR>JSYSA.MAC.203, 22-Sep-76 10:34:09, EDIT BY KIRSCHEN
;PROVIDE # OF PAGES FOR SWAPPING TO CRTHOM ROUTINE WHEN INIT'ING A STR
;<2-MONITOR>JSYSA.MAC.202, 20-Sep-76 14:55:42, EDIT BY KIRSCHEN
;RETURN STR NAME FROM HOME BLOCK, NOT SDB IN MSTRUS
;<2-MONITOR>JSYSA.MAC.201, 20-Sep-76 10:55:04, EDIT BY HALL
;FIX TYPO IN FNDSTR
;<2-MONITOR>JSYSA.MAC.200, 20-Sep-76 10:45:39, EDIT BY HALL
;FIXED DIRST CHECK FOR FILES-ONLY DIRECTORY
;<2-MONITOR>JSYSA.MAC.199, 20-Sep-76 10:35:01, EDIT BY KIRSCHEN
;DO NOT PERMIT DISMOUNT OF THE PRIMARY PUBLIC STRUCTURE
;<2-MONITOR>JSYSA.MAC.198, 17-Sep-76 15:37:18, EDIT BY KIRSCHEN
;FIX SETUP OF DEVICE TABLES IN MOUNT CODE
;<2-MONITOR>JSYSA.MAC.197, 16-Sep-76 17:11:08, EDIT BY HALL
;MADE DIRST FAIL IF USER NUMBER IS GIVEN AND DIRECTORY IS FILES-ONLY
;<2-MONITOR>JSYSA.MAC.196, 16-Sep-76 15:35:32, EDIT BY KIRSCHEN
;LOCK DEVLCK IN MOUNT CODE TO PREVENT RACES
;<2-MONITOR>JSYSA.MAC.195, 16-Sep-76 14:22:13, EDIT BY KIRSCHEN
;MAKE .MSRNU RETURN UNIT TYPE FOR OFF-LINE UNITS
;<2-MONITOR>JSYSA.MAC.194, 16-Sep-76 13:32:38, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.193, 16-Sep-76 09:56:40, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.192, 14-Sep-76 12:31:38, EDIT BY KIRSCHEN
;FIX TYPOS IN FNDSTR ROUTINE, AND MISC BUGS IN MSTDIS
;<2-MONITOR>JSYSA.MAC.191, 13-Sep-76 16:45:45, EDIT BY HALL
;MADE CRDIR NOT CHECK FOR WHEEL. DONE AT CRDIR0 NOW DEPENDING ON FUNCTION
;DESIRED
;<2-MONITOR>JSYSA.MAC.190, 13-Sep-76 13:50:22, EDIT BY KIRSCHEN
;REWRITE FNDSTR ROUTINE; FIX MSTDIS BUGS AND MSTMNT ERROR HANDLING
;<2-MONITOR>JSYSA.MAC.189, 10-Sep-76 12:29:47, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.188, 10-Sep-76 12:16:45, EDIT BY KIRSCHEN
;ADD INITIAL DISMOUNT CODE
;<2-MONITOR>JSYSA.MAC.187,  9-Sep-76 15:30:22, EDIT BY KIRSCHEN
;DO NOT PERMIT INCREMENTING MOUNT COUNT IF MS%DIS IS ON
;<2-MONITOR>JSYSA.MAC.186,  8-Sep-76 11:05:23, EDIT BY HALL
;MADE CHKPSX GLOBAL
;<2-MONITOR>JSYSA.MAC.185,  2-Sep-76 12:15:51, EDIT BY HURLEY
;MAKE STDEV SCAN FOR COLON IN DEVICE STRING
;<2-MONITOR>JSYSA.MAC.184, 26-Aug-76 14:05:15, EDIT BY MILLER
;FIX CPMAP AND PMAP CODE TO DO READ ACCESS CHECKING CORRECTLY
;<2-MONITOR>JSYSA.MAC.183, 24-Aug-76 12:56:57, EDIT BY KIRSCHEN
;TEMPORARILY COMMENT OUT CALL TO FEFSYS IN .MSMNT
;<2-MONITOR>JSYSA.MAC.182, 23-Aug-76 10:23:13, EDIT BY HALL
;MADE STDEV CLEAR AC 2 BEFORE CALLING CHKLND
;<2-MONITOR>JSYSA.MAC.181, 20-Aug-76 17:18:33, Edit by HESS
;<2-MONITOR>JSYSA.MAC.180, 20-Aug-76 15:17:09, EDIT BY KIRSCHEN
;MAKE .CRDIR CALL CPYUSR INSTEAD OF CPYFUS
;<2-MONITOR>JSYSA.MAC.179, 18-Aug-76 08:41:28, Edit by HESS
;<2-MONITOR>JSYSA.MAC.178, 17-Aug-76 12:24:18, EDIT BY HURLEY
;TCO # 1497 - CLEAR LH OF TTFORK WHEN TTY IS DEASSIGNED
;REMOVE THE STDIR JSYS FROM SPOOL
;<2-MONITOR>JSYSA.MAC.177, 17-Aug-76 11:55:49, Edit by HESS
;TCO 1496 - AUTHOR/LAST-WRITER STRINGS (SET UP USRNAM IN .LOGIN)
;<2-MONITOR>JSYSA.MAC.176, 13-Aug-76 17:48:25, Edit by HESS
;<2-MONITOR>JSYSA.MAC.175, 12-Aug-76 18:07:10, EDIT BY HALL
;FIX TO ACCES0. MADE .ACCES CALL NEW ACCES0 CODE. MOVED CNVSTD TO
;FUTILI
;<2-MONITOR>JSYSA.MAC.174, 12-Aug-76 16:31:54, Edit by HESS
;<2-MONITOR>JSYSA.MAC.173, 11-Aug-76 21:47:51, Edit by HESS
;<2-MONITOR>JSYSA.MAC.172, 11-Aug-76 21:10:35, Edit by HESS
;TCO 1488 - ADD PPNST & STPPN
;<2-MONITOR>JSYSA.MAC.171, 11-Aug-76 18:36:19, EDIT BY HALL
;FIXES TO ACCES0 AND CNVSTD
;<2-MONITOR>JSYSA.MAC.170, 11-Aug-76 15:50:32, EDIT BY HESS
;FIX LOGIN TO CONVERT THE USER # TO A DIRECTORY #
;<2-MONITOR>JSYSA.MAC.169, 11-Aug-76 12:10:53, EDIT BY HURLEY
;MAKE SPOOL CONFORM TO RELEASE 2
;<2-MONITOR>JSYSA.MAC.168, 11-Aug-76 11:21:50, EDIT BY HALL
;FIXES TO ACCES0 PLUS MADE LOGIN STORE ONLY IN RH OF JOBDIR
;ALSO MADE LOGIN NOT STORE IN GROUPS
;<2-MONITOR>JSYSA.MAC.167, 10-Aug-76 19:09:29, EDIT BY HALL
;MISCELLANEOUS FIXES TO ACCES0
;<2-MONITOR>JSYSA.MAC.166,  9-Aug-76 14:59:30, EDIT BY HALL
;FIX TO ACCES0 TO SET UP ARGS FOR STRCMP CORRECTLY
;<2-MONITOR>JSYSA.MAC.165,  9-Aug-76 14:48:52, EDIT BY HALL
;CHANGED CALLS TO DIRCHK TO USE NEW BITS. CHANGED DELDF NOT TO MAKE
;SPECIAL CHECKS FOR CONNECTED AND LOGGED IN DIRECTORY (DIRCHK DOES IT)
;<2-MONITOR>JSYSA.MAC.164,  9-Aug-76 12:55:41, EDIT BY HALL
;DELETED SOME OLD ERROR CODE IN ACCES0 THAT IS NO LONGER CALLED
;<2-MONITOR>JSYSA.MAC.163,  9-Aug-76 12:24:27, EDIT BY HALL
;ADDED CODE TO ACCES0 TO HANDLE CONNECTING FOR ANOTHER JOB. ALSO BUG
;FIXES IN ACCES0
;<2-MONITOR>JSYSA.MAC.162,  8-Aug-76 19:44:17, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.161,  8-Aug-76 17:07:54, EDIT BY KIRSCHEN
;GET UNIT # CORRECTLY IN CALL TO BLDSTU IN .MSINI/.MSMNT CODE
;<2-MONITOR>JSYSA.MAC.160,  8-Aug-76 12:54:47, EDIT BY HALL
;FIXED TYPOS IN ACCES0
;<2-MONITOR>JSYSA.MAC.159,  7-Aug-76 20:10:47, EDIT BY KIRSCHEN
;SET UP UNIQUE CODE EARLIER IN MOUNT CODE
;<2-MONITOR>JSYSA.MAC.158,  6-Aug-76 17:35:39, EDIT BY HALL
;<2-MONITOR>JSYSA.MAC.157,  6-Aug-76 17:18:53, EDIT BY HALL
;CHANGES TO ACCES0 TO ADD ABILITY TO CONNECT FOR ANOTHER JOB
;<2-MONITOR>JSYSA.MAC.156,  6-Aug-76 13:34:10, EDIT BY HALL
;CHANGES TO ACCES0
;<2-MONITOR>JSYSA.MAC.155,  6-Aug-76 13:20:58, EDIT BY HALL
;FIXED TYPO IN PREVIOUS EDIT
;<2-MONITOR>JSYSA.MAC.154,  6-Aug-76 13:12:45, EDIT BY HALL
;ADDED CNVSTD ROUTINE
;<2-MONITOR>JSYSA.MAC.153,  6-Aug-76 12:00:10, EDIT BY HURLEY
;<2-MONITOR>JSYSA.MAC.152,  5-Aug-76 19:05:42, EDIT BY HALL
;FIXED ACCES0 NOT TO CALL ULKSTR BECAUSE USTDIR DOES IT NOW
;<2-MONITOR>JSYSA.MAC.151,  5-Aug-76 10:54:39, EDIT BY KIRSCHEN
;BUF FIXES TO .MSINI CODE
;<2-MONITOR>JSYSA.MAC.150,  4-Aug-76 18:17:29, EDIT BY HALL
;FIXED TYPOS IN PREVIOUS EDIT
;EDIT BY HALL (FORGOT THE ;D)
;MAJOR CHANGES TO ACCES0 TO REFLECT CHANGES IN CALLED ROUTINES
;AND CLEAN UP ERROR HANDLING
;<2-MONITOR>JSYSA.MAC.148,  4-Aug-76 14:04:43, EDIT BY HURLEY
;<2-MONITOR>JSYSA.MAC.147,  4-Aug-76 09:19:12, EDIT BY KIRSCHEN
;FIX SETDIR CALL IN MSTMNT
;<2-MONITOR>JSYSA.MAC.146,  3-Aug-76 22:30:48, EDIT BY HURLEY
;<2-MONITOR>JSYSA.MAC.145,  3-Aug-76 20:57:37, EDIT BY HURLEY
;<2-MONITOR>JSYSA.MAC.144,  3-Aug-76 19:48:57, EDIT BY HURLEY
;EXPAND DIRECTORY NUMBERS TO 36 BITS
;<2-MONITOR>JSYSA.MAC.143,  3-Aug-76 13:58:15, EDIT BY KIRSCHEN
;MORE CODE TO IMPLEMENT STRUCTURE INITIALIZATION
;<2-MONITOR>JSYSA.MAC.142,  2-Aug-76 19:39:56, EDIT BY HURLEY
;<2-MONITOR>JSYSA.MAC.141,  2-Aug-76 16:51:42, EDIT BY HALL
;CHANGED REFERENCE TO NMVAL TO NUMVAL
;<2-MONITOR>JSYSA.MAC.140,  2-Aug-76 11:23:56, EDIT BY HALL
;FIXED TYPO IN ACCES
;<2-MONITOR>JSYSA.MAC.139,  2-Aug-76 09:17:04, EDIT BY KIRSCHEN
;FIX .MSMNT BUG DUE TO CODE REORGANIZATION
;<2-MONITOR>JSYSA.MAC.138,  1-Aug-76 18:24:51, EDIT BY HALL
;CHANGES TO LOGIN TO HANDLE STORING GROUP POINTER IN JSB TABLE
;CHANGES TO ACCES CODE NOT YET CALLED
;<2-MONITOR>JSYSA.MAC.137, 30-Jul-76 15:42:49, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.136, 30-Jul-76 15:33:56, EDIT BY KIRSCHEN
;MAKE .MSIMC/.MSDMC USE PROPER SLOT IN JSB
;<2-MONITOR>JSYSA.MAC.135, 30-Jul-76 11:33:07, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.134, 30-Jul-76 10:25:18, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.133, 30-Jul-76 10:19:53, EDIT BY KIRSCHEN
;ADD FIRST STRUCTURE INITIALIZATION CODE
;<2-MONITOR>JSYSA.MAC.132, 29-Jul-76 13:27:19, EDIT BY MILLER
;FIX MULTIPLE PAGE TABLE PMAP FOR DELETE CASE
;<2-MONITOR>JSYSA.MAC.131, 28-Jul-76 14:37:26, EDIT BY KIRSCHEN
;REORGANIZE SOME .MSMNT CODE
;<2-MONITOR>JSYSA.MAC.130, 26-Jul-76 13:07:21, EDIT BY KIRSCHEN
;ADD .MSIMC/.MSDMC ROUTINES
;<2-MONITOR>JSYSA.MAC.129, 25-Jul-76 13:03:45, EDIT BY HALL
;FIXED CHANGE IN CNDIR FOR OTHER JOB'S CONNECTING
;<2-MONITOR>JSYSA.MAC.128, 24-Jul-76 11:48:08, EDIT BY HALL
;TEMPORARY CODE IN CNDIR TO FAKE CONNECTING TO STRUCTURE 0, .DELDF TO
;CHECK CONNECTED STRUCTURE AND DIRECTORY, .LOGIN TO CONNECT TO STRUCTURE 0
;<2-MONITOR>JSYSA.MAC.127, 23-Jul-76 12:36:17, EDIT BY KIRSCHEN
;CHANGE ALGORITHM FOR GENERATING UNIQUE CODE FOR A STRUCTURE
;<2-MONITOR>JSYSA.MAC.126, 23-Jul-76 09:32:55, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.125, 23-Jul-76 09:23:00, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.124, 22-Jul-76 10:07:55, EDIT BY KIRSCHEN
;CHECK HOME BLOCKS IN MSTRUS ROUTINE
;<2-MONITOR>JSYSA.MAC.123, 21-Jul-76 10:42:10, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.122, 21-Jul-76 10:36:14, EDIT BY KIRSCHEN
;FIX BUGS IN MSTMNT
;<2-MONITOR>JSYSA.MAC.121, 19-Jul-76 15:03:41, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.120, 19-Jul-76 14:05:07, EDIT BY KIRSCHEN
;ADD CHRCHK ROUTINE
;<2-MONITOR>JSYSA.MAC.119, 19-Jul-76 12:34:54, EDIT BY KIRSCHEN
;ADD CODE TO CHECK BAT BLOCKS IN MSTRUS; CHECK DEVICE NAME IN MSTMNT
;<2-MONITOR>JSYSA.MAC.118, 19-Jul-76 09:18:38, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.117, 19-Jul-76 09:15:13, EDIT BY KIRSCHEN
;ADD .MSGSS FUNCTION OF MSTR
;<2-MONITOR>JSYSA.MAC.116, 16-Jul-76 10:33:25, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.115, 16-Jul-76 10:12:45, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.113, 15-Jul-76 13:17:13, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.112, 15-Jul-76 11:52:42, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.111, 15-Jul-76 11:35:33, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.110, 15-Jul-76 11:13:08, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.109, 15-Jul-76 10:50:23, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.108, 15-Jul-76 10:48:30, EDIT BY KIRSCHEN
;ADD .MSSSS FUNCTION
;<2-MONITOR>JSYSA.MAC.107, 15-Jul-76 09:38:29, EDIT BY KIRSCHEN
;FIX MSTRUS BUGS
;<2-MONITOR>JSYSA.MAC.106,  9-Jul-76 15:44:52, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.105,  9-Jul-76 12:43:53, EDIT BY KIRSCHEN
;FIX BUGS IN MSTRUS
;<1MILLER>JSYSA.MAC.6, 13-Jul-76 18:58:43, EDIT BY MILLER
;FIX .SPACS
;<1MILLER>JSYSA.MAC.5, 13-Jul-76 17:40:42, EDIT BY MILLER
;FIX UP CPMAP AND ALL OF ITS CALLERS
;<2-MONITOR>JSYSA.MAC.104,  8-Jul-76 14:32:53, EDIT BY KIRSCHEN
;FIX SYMBOL CONFLICT IN MSTRUS ROUTINE
;<2-MONITOR>JSYSA.MAC.103,  8-Jul-76 12:56:46, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.102,  8-Jul-76 12:45:36, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.101,  8-Jul-76 12:36:12, EDIT BY KIRSCHEN
;ADD MSTRUS FUNCTION TO MSTR
;<2-MONITOR>JSYSA.MAC.100,  8-Jul-76 11:24:41, EDIT BY KIRSCHEN
;ADD MSTRHB ROUTINE
;<2-MONITOR>JSYSA.MAC.99,  8-Jul-76 10:25:02, EDIT BY KIRSCHEN
;FIX REFERENCE TO STRFK DEFSTR
;<2-MONITOR>JSYSA.MAC.98,  7-Jul-76 14:43:00, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.97,  7-Jul-76 14:28:23, EDIT BY KIRSCHEN
;STORE UNIQUE CODE IN SDB WHEN MOUNTING A STRUCTURE
;<1MILLER>JSYSA.MAC.3,  8-Jul-76 19:02:59, EDIT BY MILLER
;<1MILLER>JSYSA.MAC.2,  8-Jul-76 08:06:25, EDIT BY MILLER
;CHECK FOR MOUNTABLE STRUCTURE ON RETURN FROM STRDMO
;<1MILLER>JSYSA.MAC.1,  7-Jul-76 14:05:20, EDIT BY MILLER
;FIX PMAP TO ACQUIRE FILE LOCKS IN SDB FOR DSK FILES
;<2-MONITOR>JSYSA.MAC.95,  7-Jul-76 11:20:47, EDIT BY KIRSCHEN
;ADD FLAGS TO CALL TO CHKBT; FIX UP ERROR HANDLING
;<2-MONITOR>JSYSA.MAC.94,  7-Jul-76 10:39:39, EDIT BY KIRSCHEN
;ADD CHECK FOR SAME UNIT TYPE WHEN MOUNTING A STRUCTURE
;<2-MONITOR>JSYSA.MAC.93,  6-Jul-76 12:03:19, EDIT BY KIRSCHEN
;CHANGE SDB REFERENCES IN MSTMNT TO USE DEFSTR FIELDS
;<2-MONITOR>JSYSA.MAC.92,  1-Jul-76 22:35:28, EDIT BY BOSACK
;TCO 1461 - MAKE .DELDF ARGUMENTS MORE LIKE RELEASE 2
;<2-MONITOR>JSYSA.MAC.91,  1-Jul-76 11:31:49, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.90,  1-Jul-76 11:14:26, EDIT BY KIRSCHEN
;ADD CODE TO FIX A BAD HOME BLOCK DURING A STRUCTURE MOUNT
;<2-MONITOR>JSYSA.MAC.89, 30-Jun-76 10:42:30, EDIT BY KIRSCHEN
;PROVIDE PHYSICAL UNIT NUMBER TO SETSTR CALL IN MSTR .MSMNT FUNCTION
;<2-MONITOR>JSYSA.MAC.88, 29-Jun-76 13:57:25, EDIT BY KIRSCHEN
;MAKE MSTR .MSMNT FUNCTION CHECK BAT BLOCKS ON STRUCTURE BEING MOUNTED
;<2-MONITOR>JSYSA.MAC.24, 21-Jun-76 12:44:53, EDIT BY MILLER
;DI MANUAL MERGE OF 1B CHANGES
;<1B-MONITOR>JSYSA.MAC.85, 16-Jun-76 13:49:38, EDIT BY OSMAN
;TCO 1382 (CHANGES MADE SO STI ALWAYS WORKS FOR WHEEL OR OPR)
;<1B-MONITOR>JSYSA.MAC.84, 15-JUN-76 17:44:13, EDIT BY HURLEY
;<1B-MONITOR>JSYSA.MAC.83, 15-JUN-76 17:21:05, EDIT BY HURLEY
;TCO # 1425 - MOVE APPEND ACCESS CHECK FROM JFNOFN TO .PMAP
;TCO # 1423 - DONT SEND MESSAGE TO ALLOCATOR IF DEV IS STILL OPENED
;<1B-MONITOR>JSYSA.MAC.82, 15-JUN-76 16:40:31, EDIT BY HALL
;TCO 1302. CHANGE PA%PLD TO PM%PLD
;<1B-MONITOR>JSYSA.MAC.81, 11-JUN-76 19:06:19, EDIT BY HALL
;CHANGED ERROR RETURN FROM SETDIR AT .GTDIR TO ASSUME ERROR CODE IN AC 1
;<1B-MONITOR>JSYSA.MAC.80,  9-JUN-76 14:56:26, EDIT BY HALL
;ADDED RANGE CHECK ON CHANNEL NUMBER IN TIMER JSYS
;<1B-MONITOR>JSYSA.MAC.79,  9-JUN-76 10:58:19, EDIT BY HALL
;FIXED CHANGED MADE IN VERSION 73 TO HANDLE ERROR RETURN FROM NIN - 
;WAS CLOBBERING AC 1
;<1B-MONITOR>JSYSA.MAC.78,  8-JUN-76 14:44:32, EDIT BY HURLEY
;<1B-MONITOR>JSYSA.MAC.77,  8-JUN-76 13:43:46, EDIT BY KIRSCHEN
; MOVE RCDIR JSYS TO JSYSF
;<1B-MONITOR>JSYSA.MAC.76,  8-JUN-76 13:42:43, EDIT BY KIRSCHEN
;<1B-MONITOR>JSYSA.MAC.75,  8-JUN-76 13:00:29, EDIT BY KIRSCHEN
;TCO 1323 - ADD RCDIR JSYS
;<1B-MONITOR>JSYSA.MAC.74,  7-JUN-76 15:06:59, EDIT BY HURLEY
;TCO # 1354 - FIX PRARG SO THAT IT DOESNT GIVE RELBAD BUGCHKS
;<1B-MONITOR>JSYSA.MAC.73,  7-JUN-76 14:54:22, EDIT BY HURLEY
;TCO # 1353 - MAKE A FAILURE TO WRITE INTO THE FACT FILE NOT LEAVE
;		THE FACT FILE LOCKED
;<1B-MONITOR>JSYSA.MAC.72,  1-JUN-76 16:43:50, EDIT BY KIRSCHEN
;<1B-MONITOR>JSYSA.MAC.71,  1-JUN-76 12:47:53, EDIT BY KIRSCHEN
;TCO 1323 - ADD ACCES JSYS
;<2-MONITOR>JSYSA.MAC.23, 17-Jun-76 11:57:06, EDIT BY MILLER
;REMOVE SJFN. ADD MLJFN
;<2-MONITOR>JSYSA.MAC.22,  9-JUN-76 11:04:56, EDIT BY HALL
;FIXED NIN TO RETURN CORRECTLY ON AN ERROR
;<2-MONITOR>JSYSA.MAC.21,  7-JUN-76 11:09:10, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.20,  2-JUN-76 12:45:22, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.19,  1-JUN-76 14:20:49, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.18, 28-MAY-76 09:56:59, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.17, 28-MAY-76 09:30:29, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.16, 28-MAY-76 08:51:02, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.15, 26-MAY-76 09:15:17, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.14, 25-MAY-76 15:05:01, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.13, 25-MAY-76 13:00:23, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.12, 25-MAY-76 12:57:26, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.11, 25-MAY-76 12:39:28, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.10, 25-MAY-76 11:34:37, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.9, 24-MAY-76 17:02:59, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.8, 24-MAY-76 16:47:31, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.7, 24-MAY-76 16:43:02, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.6, 24-MAY-76 16:35:56, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.5, 24-MAY-76 16:32:58, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.4, 24-MAY-76 16:18:17, EDIT BY KIRSCHEN
;<2-MONITOR>JSYSA.MAC.3, 24-MAY-76 15:35:34, EDIT BY KIRSCHEN
;BEGIN ADDING CODE FOR MSTR
;<1B-MONITOR>JSYSA.MAC.70, 19-MAY-76 12:49:49, EDIT BY MILLER
;TCO 1302. ADD PRELOADING OF PAGES ON A PMAP
;<2-MONITOR>JSYSA.MAC.1, 10-MAY-76 14:43:18, EDIT BY KIRSCHEN
;ADDED STRUCTURE NUMBER 0 IN B BEFORE ALL CALLS TO SETDIR
;<1MONITOR>JSYSA.MAC.69, 23-MAR-76 19:14:33, EDIT BY HURLEY
;<1MONITOR>JSYSA.MAC.68, 23-MAR-76 15:33:07, EDIT BY HURLEY
;TCO 1209 - MAKE STDEV ALLOW A COLON AS A TERMINATOR
;TCO 1207 - MAKE ERJMP WORK AFTER SFCOC, SFMOD, AND SFPOS
;<1MONITOR>JSYSA.MAC.67, 22-MAR-76 13:40:00, EDIT BY MILLER
;TCO 1145. ADD IFN DTFLG CONDITIONAL
;<1MONITOR>JSYSA.MAC.66, 16-MAR-76 13:37:04, EDIT BY KIRSCHEN
;TCO 1178 - PREVENT LOGINS UNLESS AT LEAST ONE JOB SLOT LEFT
;<1MONITOR>JSYSA.MAC.65,  9-MAR-76 15:11:17, EDIT BY HURLEY
;TCO 1170 - ALLOW MAINTAINENCE PRIV'S TO DO SNOOP FUNCTION 6
;<1MONITOR>JSYSA.MAC.64,  2-MAR-76 14:33:40, EDIT BY MILLER
;TCO 1146. MAKE NIN RETURN OVERFLOW CONDITION
;<1MONITOR>JSYSA.MAC.63,  2-MAR-76 13:49:24, EDIT BY MILLER
;TCO 1145. ENABLE/DISABLE REMOTE ANSWER
;<2MONITOR>JSYSA.MAC.62, 16-FEB-76 17:46:25, EDIT BY MURPHY
;TCO #1097 - INCREASE FREE MONITOR VAS
;<2MONITOR>JSYSA.MAC.61, 13-FEB-76 17:10:42, EDIT BY MURPHY
;TCO #1057 - CHECK FOR 0 COUNT TO PMAP
;<2MONITOR>JSYSA.MAC.60, 16-JAN-76 17:49:41, EDIT BY MURPHY
;<2MONITOR>JSYSA.MAC.59,  9-JAN-76 11:04:54, EDIT BY HURLEY

;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 BY DIGITAL EQUIPMENT CORPORATION, MAYNARD, MASS.

	SEARCH PROLOG,ACTSYM
	TTITLE JSYSA
	SWAPCD

;THIS FILE CONTAINS CODE WHICH IMPLEMENTS VARIOUS JSYSES.  THIS
;CODE DOES NOT REQUIRE ANY SPECIAL AC DEFINITIONS.  SOME JSYSES,
;PARTICULARLY FILE-RELATED ONES, USE THE GTJFN AC DEFINITIONS, AND
;THESE ARE GENERALLY IN FJSYS.

EXTN <HOMSNM,HM1BLK,HM2BLK>	;DEFINED ELSEWHERE
EXTN <MXSTRU>
EXTN <LODPPS,ULDPAG>		;FOR LOCK JSYS ONLY
EXTN <DEQERR>			;IN APRSRV, TO GET ERROR BLOCK

RS(FACTSW)			; Fact switches

RS TADIDT,1			;INITIAL DAY AND TIME

PPNLH==:4			;SYSTEM DEFINED PPN LHS

;MACROS TO DEFINE PARALLEL FLAG AND FUNCTION TABLES FOR SETJB
; FLAG TABLE (SJBTBF) VALUES:
;	1 - MEANS ANY JOB CAN SET THE PARAMETER
;	0 - MEANS ONLY THE OWNER JOB CAN SET THE PARAMETER

DEFINE SJTBL <
	SJTB1 (1,<CALL SJBDEN>)	;;0 - SET DEFAULT MAGTAPE DENSITY
	SJTB1 (1,<STOR T3,JSMTP,(T1)>)	;;1 - SET MAGTAPE DEFAULT PARITY
	SJTB1 (1,<CALL SJBDM>)	;;2 - SET MAGTAPE DEFAULT DATA MODE
	SJTB1 (1,<STOR T3,JSMTR,(T1)>)	;;3 - SET MAGTAPE DEFAULT RECORD SIZE
	SJTB1 (1,<STOR T3,JSDFS,(T1)>)	;;4 - SET DEFERRED SPOOLING
	SJTB1 (0,<CALL SJBSRM>)	;;5 - SET SESSION REMARK
	>

DEFINE SJTB1 (FLG,INSTR) <
	EXP FLG>

SJBTBF:	SJTBL			;GENERATE FLAG TABLE

DEFINE SJTB1 (FLG,INSTR) <
	INSTR>

SJBTAB:	SJTBL			;GENERATE FUNCTION TABLE

MAXSJF==.-SJBTAB		;MAXIMUM SETJB FUNCTION CODE

SJ%OWN==:1B0			;IF SET, THEN SETTING PARAMETERS IN OWN JOB


;BIT FOR SETACT (SET ACCOUNT) AND VERACT (VERIFY ACCOUNT)

AC%MCH==:1B1			;ACCOUNT MATCHES ACCTSR
;ROUTINES USED BY IO CONVERSION JSYSES TO DO LOGICAL BIN AND BOUT.
;REAL BIN AND BOUT IS DONE IF THE SOURCE/DESTINATION IS A JFN.
;IF IT IS A STRING POINTER, WE DO THE ILDB/IDPB HERE IN ORDER
;THAT THE 'PREVIOUS CONTEXT' IS STILL THE JSYS'S CALLER.

;LOCAL BOUT
; A (PREVIOUS CONTEXT)/ JFN OR STRING PTR
; B/ BYTE
;	CALL BOUTA
; RETURN +1 ALWAYS

BOUTA::	PUSH P,A
	UMOVE A,1		; Output designator
	TLNN A,777777		; String pointer?
	JRST [	BOUT		;NO, CAN DO BOUT
		POP P,A
		RET]
	TLC A,777777		; Yes
	TLCN A,777777		; Lh = -1?
	HRLI A,440700		; Yes. fill in
	XCTBU [IDPB B,A]
	UMOVEM A,1
	PUSH P,B
	SETZ B,
	XCTBU [IDPB B,A]
	POP P,B
	POP P,A
	RET

;LOCAL BIN

;RETURNS +1:	ERROR OR EOF
;	 +2:	BYTE IN B

BIN1::	PUSH P,A
	UMOVE A,1
BIN1Y:	TLNN A,777777
	JRST [	BIN		;NOT STRING PTR, DO REGULAR BIN
		 ERJMP PA1	;ERROR OR EOF
		JRST BIN1X]
	TLC A,777777
	TLCN A,777777
	HRLI A,440700
	XCTBU [ILDB B,A]
	UMOVEM A,1
BIN1X:	CAIN T2,.CHCRT		;IGNORE ALL CR
	JRST BIN1Y
	POP P,A
	RETSKP
;PASSWORD CHECK FOR INTERNAL USE
; A/ directory number
; B/ password string ptr
;RETURNS +1:	INVALID PASSWORD
;		A=0,	CALLER MUST DISMS FOR 3 SEC
;		A=-1,	NO PASSWORD WAS GIVEN, NO NEED FOR 3 SEC WAIT

PASSWC::SE1CAL
	PUSH P,B
	CALL SETDIR
	 JRST [	POP P,B
		RET]
	POP P,B
	CALL CHKPSX
	CAIA
	AOS 0(P)
	ULKDIR
	RET

CHKPSW:	UMOVE B,2
CHKPSX::SAVEQ
	JUMPE B,RETO		;IF NO PASSWORD STRING, RETURN
	PUSH P,B
	MOVE B,DIRORA		;GET ADDRESS OF MAPPED DIR
	LOAD B,DRPSW,(B)	;GET ADDRESS OF PASSWORD STRING
	JUMPE B,[SUB P,BHC+1
		JRST RETZ]
	ADD B,DIRORA		;GET ABSOLUTE ADDRESS OF PASSWORD STRING
	MOVE C,1(B)
	TLNN C,774000
	JRST [	SUB P,BHC+1
		JRST RETZ]	; Null password never matches
	MOVSI A,(POINT 7,0(B),35)
	POP P,C
	TLC C,-1		; SEE IF LH = -1
	TLCN C,-1
	HRLI C,(<POINT 7,0>)	;YES, SET UP BYTE POINTER
	MOVEI Q1,MAXLC		;SET UP LIMIT OF CHARACTERS
CHKPS1:	XCTBU [ILDB D,C]
	CAIL D,"A"+40		;LOWERCASE?
	CAILE D,"Z"+40
	SKIPA
	SUBI D,40		;YES, CONVERT IT TO UPPERCASE
	ILDB Q3,A
	CAME D,Q3
	JRST CHKPS2		;NO MATCH, GO READ REST OF STRING
	JUMPE D,RSKP		;MATCH
	SOJG Q1,CHKPS1		;COUNT DOWN MAX STRING LENGTH
	JRST RETZ		;STRING TOO LONG

CHKPS2:	CAIN Q1,MAXLC		;FIRST CHARACTER?
	JUMPE D,RETO		;YES, IF NULL, THEN DONT NEED TO WAIT
CHKPS3:	JUMPE D,RETZ		;END OF USER'S STRING?
	SOJLE Q1,RETZ		;NO, READ ALL CHARACTERS YET?
	XCTBU [ILDB D,C]	;NO, READ WHOLE STRING TO FOUL PAGE
	JRST CHKPS3		;  FAULT WATCHERS
; CALL TO ACCESS DIRECTORIES
;
; ACCEPTS IN 1/ FLAGS,, N
;	     2/ ADDRESS OF ARGUMENT BLOCK
; ARGBLK: DIRECTORY DESIGNATOR
;	  POINTER TO PASSWORD STRING
;	  JOB NUMBER (-1 FOR SELF)

.ACCES::MCENT			;MONITOR CONTEXT ENTRY
	CALL ACCES0		;CALL ROUTINE TO DO THE WORK
	 ITERR			;ILLEGAL INSTRUCTION TRAP
	MRETNG			;SUCCESS RETURN (+1)
;ACCES0 - DOES THE WORK FOR .ACCES

;ACCEPTS: SAME AS .ACCES

;RETURNS +1: FAILED, ERROR CODE IN AC 1
;	 +2: SUCCEEDED

;REGISTER USAGE:

;	Q1/ADDRESS OF ARGUMENT BLOCK IN USER'S SPACE
;	Q2/DIRECTORY NUMBER
;	Q3/STRUCTURE NUMBER (OFFSET IN STRTAB)
;	P1/ADDRESS OF START OF MAPPED DIRECTORY
;	P2/FLAG INDICATING WHETHER PRIVILEGE IS SUFFICIENT
;	P3/JOB NUMBER FOR WHICH CALLED
;	P4/OFFSET IN STRUCTURE TABLES IN JSB FOR THIS STRUCTURE
;	P5/STRUCTURE UNIQUE CODE

ACCES0:	STKVAR<ACCFLG,<ACCNAM,MAXLW>>

;CHECK FOR ERRORS

	UMOVE T1,1		;GET FLAGS,,LENGTH OF ARGUMENT BLOCK
	TXNN T1,AC%CON!AC%OWN!AC%REM ;WAS ANY FUNCTION REQUESTED?
	RETBAD(ACESX5)		;NO. ERROR
	HLLZM T1,ACCFLG		;SAVE FLAGS
	HRRZ T2,T1		;GET LENGTH OF ARGUMENT BLOCK
	CAIG T2,.ACJOB		;IS IT LONG ENOUGH FOR ALL ARGUMENTS?
	RETBAD (ACESX1)		;NO. RETURN ERROR
	MOVE T1,JOBNO		;GET THIS JOB'S NUMBER
	HRRZ T2,JOBDIR(T1)	;GET THIS JOB'S DIRECTORY NUMBER
	SKIPN T2		;IS IT LOGGED IN?
	RETBAD(CNDIX5)		;NO. ERROR

;GET USER'S LOGGED IN DIRECTORY NAME TO CHECK AGAINST LATER

	HRLI T2,USRLH		;MAKE IT A USER NUMBER
	MOVEI T1,ACCNAM		;T1/DESTINATION ON STACK
	HRLI T1,(POINT 7,0)
	DIRST			;CONVERT TO DIRECTORY NAME ON PS:
	 RETBAD

;GET STRUCTURE UNIQUE CODE, STRUCTURE NUMBER, AND DIRECTORY NUMBER

	UMOVE Q1,2		;GET ADDRESS OF ARGUMENT BLOCK
	UMOVE T1,.ACDIR(Q1)	;GET STRUCTURE AND DIRECTORY OR BYTE POINTER
	CALL CNVSTD		;GET (STRUCTURE,,DIRECTORY)
	 RETBAD
	HRRZ Q2,T1		;SAVE DIRECTORY NUMBER
	HLRZ P5,T1		;SAVE UNIQUE CODE
	CALL SETDIR		;MAP THE DIRECTORY AND GO NOINT
	 RETBAD			;FAILED
	MOVE P1,DIRORA		;POINT TO START OF DIRECTORY
	LOAD Q3,CURSTR		;GET STRUCTURE NUMBER FOR MAPPED DIRECTORY
;SEE WHAT JOB THIS IS FOR

	UMOVE T1,.ACJOB(Q1)	;GET JOB NUMBER FOR WHICH THIS IS TO BE DONE
	CAME T1,[-1]		;DID USER SPECIFY 'THIS JOB'?
	CAMN T1,JOBNO		; OR JOB NUMBER SAME AS THE USER'S?
	SKIPA			;YES
	JRST ACCES7		;NO. GO DO IT SEPARATELY

;FOR THIS JOB. SEE IF USER WANTS TO DO UNACCESS

	MOVE T2,ACCFLG		;GET INPUT FLAGS
	TXNN T2,AC%REM		;UNACCESS REQUESTED?
	JRST ACCES1		;NO.
	LOCK JSSTLK		;LOCK THE JSB STORAGE LOCK
	SETZ T1,		;T1/OFFSET TO MAPPED JSB (NONE FOR THIS JOB)
	CALL UNACC		;DO IT
	 JRST [	UNLOCK JSSTLK	;ULOCK THE JSB
		CALL USTDIR	;UNLOCK THE DIRECTORY
		RETBAD ]	;RETURN FAILURE
	UNLOCK JSSTLK		;UNLOCK THE JSB SPACE
	CALL USTDIR		;UNLOCK THE DIRECTORY
	RETSKP			;SUCCESS

;NOT UNACCESS. SEE IF USER HAS PRIVILEGES OR CORRECT PASSWORD

ACCES1:	MOVE T1,CAPENB		;GET ENABLED CAPABILITIES OF THIS FORK
	TXNE T1,SC%WHL!SC%OPR	;WHEEL OR OPERATOR?
	JRST [	SETZM P2	;YES. INDICATE OK TO DO THIS
		JRST ACCES3]
	UMOVE T2,.ACPSW(Q1)	;GET POINTER TO PASSWORD IN USER'S SPACE
	SKIPN T2		;IS THERE A PASSWORD?
	JRST [	MOVX P2,1B0	;NO. INDICATE NOT OK TO DO THIS
		JRST ACCES3]
	CALL CHKPSX		;CHECK THE PASSWORD FROM USER'S ADDRESS SPACE
	 JRST [	MOVX P2,1B1	;FAILED. INDICATE NOT OK TO DO THIS
		JRST ACCES3]
	SETZM P2		;OK. INDICATE ACCESS OK

;P2 IS NON-ZERO IF HAVEN'T YET PROVED RIGHT TO DO THIS, 0 IF OK TO DO THIS
;IF NOT OK SO FAR, CHECK FOR SPECIAL CASE WHERE USER'S NAME AND THAT OF
;DIRECTORY BEING REQUESTED MATCH, THE OBJECT DIRECTORY IS ON A DOMESTIC
;STRUCTURE, AND THE OWNER FIELD OF THE DIRECTORY PROTECTION ALLOWS CONNECTING

ACCES3:	SKIPN P2		;IS USER ALLOWED TO DO THIS FUNCTION?
	JRST ACCES8		;YES.
	MOVE T1,STRTAB(Q3)	;NO. POINT TO SDB FOR THIS STRUCTURE
	MOVE T1,SDBSTS(T1)	;GET STATUS OF THIS STRUCTURE
	TXNN T1,MS%DOM		;IS IT MOUNTED DOMESTIC?
	JRST ACCES8		;NO. SPECIAL CASE DOESN'T APPLY
	MOVE T1,P1		;POINT TO START OF DIRECTORY
	LOAD T1,DRPOW,(T1)	;GET OWNER PROTECTION BITS
	TXNN T1,DP%CN		;SEE IF CONNECT IS SET
	JRST ACCES8		;NO. SPECIAL CASE DOESN'T APPLY
	MOVEI T1,ACCNAM		;T1/POINTER TO USER'S NAME AS SET
	HRLI T1,(POINT 7,0)	; BY DIRST
	MOVE Q1,P1		;POINT TO START OF DIRECTORY
	OPSTR <ADD Q1,>,DRNAM,(Q1) ;GET NAME OF DIRECTORY
	AOS Q1			;POINT BEYOND HEADER TO ACTUAL NAME STRING
	MOVE T2,[POINT 7,0(Q1)]	;T2/POINTER TO NAME OF REQUESTED DIRECTORY
	CALL STRCMP		;SEE IF USER NAME MATCHES REQUESTED DIRECTORY
	 JRST ACCES8		;NO. SPECIAL CASE DOESN'T APPLY
	SETZ P2,		;YES. INDICATE OK TO DO THIS

;DECIDE WHAT USER WANTS TO DO

ACCES8:	MOVE T1,ACCFLG		;GET FLAGS INDICATING WHAT TO DO
	TXNN T1,AC%OWN		;GAIN OWNERSHIP (GROUPS)?
	JRST ACCES4		;NO. GO SEE IF CONN
;USER WANTS TO 'ACCESS' THE DIRECTORY - GAIN ITS GROUPS

	MOVE T1,P1		;POINT TO START OF DIRECTORY THAT IS MAPPED
	LOAD T1,DRMOD,(T1)	;GET MODE OF DIRECTORY
	TXNE T1,MD%FO		;IS IT FILES-ONLY?
	JRST [	MOVEI T1,ACESX7	;YES. CAN'T ACCESS IT
		JRST ACCER2]
	SKIPE P2		;NO. DO WE HAVE ACCESS?
	 JRST [	MOVEI T1,CNDIX1	;NO. ASSUME INVALID PASSWORD
		TXNE P2,1B0	;DID USER GIVE A PASSWORD?
		MOVEI T1,ACESX3	;NO. SAY PASSWORD IS REQUIRED
		JRST ACCER2]
	LOCK JSSTLK		;LOCK JSB STRUCTURE DATA
	MOVE T1,P5		;YES. T1/STRUCTURE UNIQUE CODE
	CALL GTSTOF		;GET OFFSET IN JSB FOR THIS STRUCTURE
	 JRST [	UNLOCK JSSTLK	;UNLOCK THE JSB STRUCTURE DATA
		JRST ACCER2]	;NO ROOM FOR AN ENTRY
	MOVEM T2,P4		;SAVE OFFSET
	LOAD T1,JSGRP,(P4)	;GET GROUPS PREVIOUSLY SET UP
	SKIPE T1		;WERE THERE ANY?
	CALL RELGRP		;YES. RELEASE THE SPACE USED BY THE LIST
				; OF GROUPS
	CALL CPYUGP		;COPY THE LIST OF USER GROUPS
	 SETZ T1,		;NONE THERE. CLEAR POINTER
	STOR T1,JSGRP,(P4)	;STORE POINTER IN JSB
	STOR Q2,JSADN,(P4)	;SAVE 'ACCESSED' DIRECTORY
	UNLOCK JSSTLK		;UNLOCK THE JSB STRUCTURE DATA

;SEE IF USER WANTS TO CONNECT

ACCES4:	MOVE T1,ACCFLG		;GET FLAGS INDICATING WHAT TO DO
	TXNE T1,AC%CON		;CONNECT
	JRST ACCES5		;YES
	CALL USTDIR		;NO. UNMAP THE DIRECTORY
	RETSKP			;TAKE SUCCESS RETURN

;USER WANTS TO CONNECT

ACCES5:	SKIPN P2		;WAS PASSWORD OK (OR PRIVILEGE SUFFICIENT)?
	JRST ACCES6		;YES. PROCEED
	MOVX T2,DC%CN		;T2/CONNECT ACCESS
	CALL DIRCHK		;CHECK FOR ABILITY TO CONNECT TO THIS DIRECTORY
	 JRST [	MOVEI T1,CNDIX1	;NO. ASSUME INVALID PASSWORD
		TXNE P2,1B0	;DID USER GIVE A PASSWORD?
		MOVEI T1,ACESX3	;NO. SAY PASSWORD IS REQUIRED
		JRST ACCER2]
ACCES6:	STOR P5,JSUC		;NO. STORE CONNECTED STRUCTURE UNIQUE CODE
	STOR Q2,JSDIR		;STORE CONNECTED DIRECTORY NUMBER
	CALL CPYCDN		;GO COPY CONNECTED DIR STRING TO JSB
	CALL USTDIR		;UNLOCK THE DIRECTORY (LOCKED BY SETDIR)
				; GO GO OKINT
	RETSKP			;TAKE SUCCESS RETURN
;USER WANTS TO CONNECT FOR ANOTHER JOB

ACCES7:	MOVEM T1,P3		;SAVE OBJECT JOB NUMBER
	CALL USTDIR		;UNLOCK THE DIRECTORY (LOCKED BY SETDIR)
				; AND GO OKINT
	SKIPN P3		;VALID JOB #
	RETBAD (ARGX07)		;NO. CAN'T DIDDLE JOB 0
	MOVE T1,ACCFLG		;SEE WHAT WE WANT TO DO
	TXNN T1,AC%CON		;CONNECT?
	RETBAD(ACESX4)		;NO. CAN'T DO THIS FOR ANOTHER JOB
	MOVE T1,CAPENB		;GET ENABLED CAPABILITIES
	TXNN T1,SC%WHL!SC%OPR	;WHEEL OR OPERATOR?
	RETBAD(CAPX1)		;NO. REQUIRED FOR THIS FUNCTION
	MOVE T1,P3		;T1/JOB NUMBER
	CALL CKJBLI		;SEE IF VALID AND LOGGED IN
	RETBAD			;NO. OBJECT JOB MUST BE LOGGED IN
	MOVE T1,P3		;T1/JOB NUMBER FOR WHICH CONNECTING
	CALL SETJSB		;MAP THE OBJECT JOB'S JSB (RETURNS OFFSET IN T1)
	MOVEM T1,P1		;SAVE OFFSETFOR ADDRESSING OBJECT JSB
	STOR P5,JSUC,(P1)	;STORE CONNECTED STRUCTURE UNIQUE CODE
	STOR Q2,JSDIR,(P1)	;STORE CONNECTED DIRECTORY NUMBER
	SETZRO JSCDF,(P1)	;MARK THAT THE DIR STRING IN JSB IS NO GOOD
	CALL CLRJSB		;UNMAP THE OBJECT JSB
	HLRE A,JOBPT(P3)	;GET TTY OF OBJECT JOB
	JUMPL A,ACCES9		;IF DETACHED, SKIP MESSAGE
	TXO A,1B18		;MAKE LINE NUMBER INTO DESIGNATOR
	HRROI B,[ASCIZ/
[CONNECTED TO /]
	SETZ C,
	SOUT			;TYPE OUT CONNECTED MESSAGE
	HRL T2,P5		;GET STRUCTURE UNIQUE CODE
	HRR T2,Q2		;T2/(STRUCTURE UNIQUE CODE,,DIRECTORY)
	DIRST			;PRINT STRUCTURE AND DIRECTORY NAMES
	JFCL
	HRROI B,[ASCIZ/]
/]
	SOUT
ACCES9:	RETSKP
;FAILURE

;USER GAVE WRONG PASSWORD

ACCER2:	MOVEM T1,Q1		;SAVE ERROR CODE
	ULKDIR			;UNLOCK THE DIRECTORY AND STRUCTURE
	CAIN T1,CNDIX1		;IS ERROR THAT PASSWORD WAS BAD?
	JRST [	MOVEI T1,^D3000 ;YES. WAIT A WHILE TO FOIL PASSWORD THIEVES
		DISMS
		JRST .+1]
	MOVE T1,Q1		;RESTORE ERROR CODE
	OKINT			;SETDIR WENT NOINT
	RETBAD			;TAKE ERROR RETURN


;ROUTINE TO COPY THE CONNECTED DIRECTORY NAME INTO THE JSB

CPYCDN:	SETZRO JSCDF		;MARK THAT THE CURRENT STRING IS INVALID
	LOAD T1,JSCDS		;GET THE CURRENT STRING POINTER
	JUMPE T1,[MOVEI T2,MAXLW+1 ;IF NONE, GET SPACE FOR ONE
		CALL ASGJFR
		 RET		;IF NO ROOM, DONT BOTHER
		STOR T1,JSCDS	;REMEMBER THE STRING POINTER
		JRST .+1]
	MOVE T4,DIRORA		;NOW GET THE POINTER TO THE DIR NAME
	LOAD T2,DRNAM,(T4)	;FROM CURRENT MAPPED DIR
	ADD T2,DIRORA		;GET ABSOLUTE ADDRESS
	MOVSI T3,(<POINT 7,0(T2),35>)
	HRLI T1,(POINT 7,0,35)	;GET BYTE POINTERS TO BOTH STRINGS
CPYCDL:	ILDB T4,T3		;COPY STRING
	IDPB T4,T1		; FROM DIR HEADER TO JSB
	JUMPN T4,CPYCDL		;LOOP BACK TIL NULL FOUND
	SETONE JSCDF		;MARK THAT THE STRING IS VALID
	RET			;AND RETURN
;UNACC - UNACCESS A DIRECTORY

;ACCEPTS IN T1/	OFFSET TO JSB (0 FOR THIS JOB)
;		JSSTLK MUST BE LOCKED BY THE CALLER OF THIS ROUTINE

;RETURNS +1: FAILS 
;	 +2: SUCCESS

;DIRECTORY MUST BE MAPPED

UNACC::
	SAVEQ
	MOVEM T1,Q3		;SAVE OFFSET TO MAPPED JSB
	MOVE T1,DIRORA		;POINT TO START OF DIRECTORY
	LOAD Q1,DRNUM,(T1)	;GET DIRECTORY NUMBER
	LOAD Q2,CURUC		;GET UNIQUE CODE FOR MAPPED DIRECTORY
	MOVE T1,Q2		;GET UNIQUE CODE TO LOOK FOR
	MOVE T2,Q3		;GET OFFSET TO MAPPED JSB
	CALL FNDSTM		;GET POINTER TO JSB BLOCK FOR THIS STRUCTURE
	 RETBAD (ACESX6)
	LOAD T1,JSADN,(T2)	;GET ACCESSED DIRECTORY
	CAME T1,Q1		;DID USER ACCESS THIS DIRECTORY?
	RETBAD (ACESX6)
	SETZRO <JSADN>,(T2)	;YES. CLEAR ACCESSED DIRECTORY NUMBER
	OPSTR <SKIPE T1,>,JSGRP,(T2) ;WERE THERE ANY GROUPS?
	JRST [	JUMPN Q3,.+1	;IF ANOTHER JSB, DO NOT FREE GROUP SPACE
		SETZRO <JSGRP>,(T2) ;YES. CLEAR THE POINTER
		CALL RELGRP	;RELEASE FREE SPACE
		JRST .+1]
	MOVE T1,Q2		;T1/STRUCTURE UNIQUE CODE
	MOVE T2,Q3		;GET OFFSET TO JSB
	CALL FRJSSO		;REMOVE ENTRY IN JSB FOR THIS STRUCTURE IF POSSIBLE
	RETSKP			;SUCCESS
;JSYS TO SET/CLEAR ADDRESS BREAK
;CALLING SEQUENCE:
;ACCEPTS IN	1/ FUNCTION CODE,,PROCESS HANDLE
;	ADBRK
;RETURNS +1: ALWAYS
;USAGE OF ACS 2 AND 3 ARE DETERMINED BY THE FUNCTION CODE

.ADBRK::MCENT
	UMOVE T1,1		;GET FUN. CODE, FORK HANDLE
	HLRZ T2,T1		;ISOLATE FUNCTION CODE
	JUMPL T2,[ITERR (ARGX02)] ;INVALID FUNCTION CODE
	CAILE T2,.ABGAD		;IN RANGE?
	ITERR (ARGX02)		;NOPE
	HRRZ P1,T1		;PRESERVE FORK HANDLE IN P1
	CALL @[	IFIW!ABSET
		IFIW!ABRED
		IFIW!ABCLR
		IFIW!ABGAD](T2)	;DISPATCH ON FUNCTION CODE
	 ITERR			;ERROR RETURN
	MRETNG			;GOOD

;SET USER ADDRESS BREAK

ABSET:	CALL BRKAVL		;ADDRESS BREAK AVAILABLE?
	 RETBAD (ABRKX1)	;NO, MUST BE SM10
	UMOVE P2,2		;GET ADDRESS
	UMOVE P3,3		; AND FLAGS
	LSH P3,-<^D35-^L<AB%XCT>> ;RIGHT-JUSTIFY FLAGS (ASSUMES AB%XCT IS
				; RIGHTMOST FLAG BIT)
	CALL FLOCK		;LOCK FORK STRUCTURE
	MOVE T1,P1		;GET FORK HANDLE
	CALL SETLFK		;MAP PROCESS'S PSB
	MOVEM P2,ADRBRK(T1)	;STUFF ADDRESS INTO PSB
	STOR P3,ABFLG,(T1)	; AND FLAGS TOO
	CAIN P1,.FHSLF		;SETTING MY OWN BREAK?
	 CALL [	DMOVE T1,P2	;YES, GET ARGS FOR SETBRK
		JSP T4,SETBRK	; AND POKE THE CPU
		RET]
	CALL CLRLFK		;UNMAP PSB
	CALL FUNLK		;UNLOCK FORK STRUCTURE
	RETSKP			;AND RETURN

;READ USER ADDRESS BREAK

ABRED:	CALL BRKAVL		;ADDRESS BREAK AVAILABLE?
	 RETBAD (ABRKX1)	;NO, QUIT NOW
	CALL FLOCK		;LOCK FORK STRUCTURE
	MOVE T1,P1		;GET FORK HANDLE
	CALL SETLFK		;MAP PSB
	MOVE T2,ADRBRK(T1)	;GET BREAK INFO
	ANDX T2,EXPCBT		;MASK OUT ALL BUT 23-BIT ADDRESS
	LOAD T3,ABFLG,(T1)	;GET FLAGS
	LSH T3,<^D35-^L<AB%XCT>> ;PUT BITS IN RIGHT PLACE (ASSUMES AB%XCT
				; IS RIGHTMOST FLAG BIT)
	XCTU [	DMOVEM T2,2]	;RETURN ANSWERS TO USER
	CALL CLRLFK		;UNMAP PSB
	CALL FUNLK		;UNLOCK
	RETSKP

;CLEAR USER ADDRESS BREAK

ABCLR:	CALL BRKAVL		;BREAK AVAILABLE?
	 RETBAD (ABRKX1)	;NO, MUST BE SM10
	CALL FLOCK		;LOCK FORK STRUCTURE
	MOVE T1,P1		;GET FORK HANDLE
	CAIN T1,.FHSLF		;CLEARING OUR OWN BREAKS?
	 CALL [	SETZB T1,T2	;YES, POKE THE CPU NOW
		JSP T4,SETBRK	; ..
		RET]
	CALL SETLFK		;MAP PSB
	SETZM ADRBRK(T1)	;CLEAR OUT ADDRESS BREAK INFO
	CALL CLRLFK		;UNMAP PSB
	CALL FUNLK
	RETSKP

;READ ADDRESS OF INSTRUCTION WHICH CAUSED LAST ADDRESS BREAK
; (RFSTS GIVES ADDRESS OF NEXT INSTRUCTION TO BE EXECUTED,
; WHICH IS USELESS IF THE ADDRESS BREAK WAS CAUSED BY A 
; PC-CHANGING INSTRUCTION)

ABGAD:	CALL BRKAVL		;ADDRESS BREAK AVAILABLE?
	 RETBAD (ABRKX1)	;NO, QUIT
	CALL FLOCK		;LOCK FORK STRUCTURE
	MOVE T1,P1		;GET FORK HANDLE
	CALL SETLFK		;MAP ITS PSB
	MOVE T2,ADRBK1(T1)	;GET ADDR OF BROKEN INSTRUCTION
	UMOVEM T2,2		;RETURN TO USER
	CALL CLRLFK		;UNMAP PSB
	CALL FUNLK		;UNLOCK FORK STRUCTURE
	RETSKP			;GIVE GOOD RETURN
;JSYS TO ALLOCATE DEVICES TO A JOB OR TO THE DEVICE ALLOCATOR POOL

;CALLING SEQUENCE:
;ACCEPTS IN 1/	FUNCTION CODE
;	    2/	DEVICE DESIGNATOR
;	    3/	JOB NUMBER, -1, OR -2
;	ALLOC
;RETURNS +1:	ERROR - CODE IN AC 1
;	 +2:	SUCCESSFUL

.ALLOC::MCENT			;ENTER JSYS
	UMOVE T1,1		;GET FUNCTION CODE
	CAIE 1,.ALCAL		;IS THIS A LEGAL FUNCTION?
	RETERR (ALCX1)		;NO, ILLEGAL FUNCTION CODE
	MOVE T1,CAPENB		;THIS FUNCTION REQUIRES PRIVILEGES
	TRNN T1,SC%WHL!SC%OPR	;WHEEL OR OPERATOR?
	RETERR (ALCX2)		;NO, NOT ENOUGH PRIVILEGES
	UMOVE T1,2		;GET DEVICE DESIGNATOR
	CALL CHKDES		;IS THIS A LEGAL DEVICE?
	 RETERR ()		;NO, GIVE USER AN ERROR RETURN
	TLNN T3,(DV%AS)		;IS THIS AN ASSIGNABLE TYPE DEVICE?
	RETERR (ALCX3)		;NO, MUST BE ASSIGNABLE
	CALL LCKDVL		;LOCK UP THE DEVICE LOCK
	XCTU [HRRZ T3,3]	;GET ARGUMENT
	HLRZ T4,DEVUNT(T2)	;GET OWNER OF THIS DEVICE
	CAIN T3,-2		;REQUESTING DEVICE FOR ALLOC POOL?
	JRST ALCAL1		;YES, GO PERFORM THAT FUNCTION
	CAIN T3,-1		;REQUESTING THAT THIS DEVICE BE FREED?
	JRST ALCAL2		;YES, GO FREE IT UP
	CAIGE T3,NJOBS		;LEGAL JOB NUMBER?
	SKIPGE JOBRT(T3)	;AND JOB ASSIGNED?
	RETERR (ALCX4,<UNLOCK DEVLCK>) ;NO
	CAMN T3,T4		;ALREADY ASSIGNED TO THIS JOB?
	JRST ALCAL0		;YES
	CAIE T4,-1		;IS THIS DEVICE AVAILABLE?
	CAIN T4,-2		;OR IN ALLOCATOR'S POOL?
	SKIPA			;YES
	RETERR (ALCX5,<UNLOCK DEVLCK>) ;NO
	HRLM T3,DEVUNT(T2)	;GIVE THIS DEVICE TO THE JOB SPECIFIED
ALCAL0:	MOVX T1,D1%ALC		;SET THE ALLOCATED FLAG
	IORM T1,DEVCH1(T2)	;...
ALCALR:	UNLOCK DEVLCK		;RELEASE THE DEVICE LOCK
	SMRETN
ALCAL1:	MOVX T1,D1%ALC		;SET THE ALLOCATED FLAG
	IORM T1,DEVCH1(T2)	;...
	CAIE T4,-1		;IS THE DEVICE FREE?
	RETERR (ALCX6,<UNLOCK DEVLCK>) ;NO, TELL CALLER
	HRLM T3,DEVUNT(T2)	;YES, GIVE IT TO ALLOCATOR POOL
	JRST ALCALR		;GO SET ALLOCATED BIT

ALCAL2:	MOVX T1,D1%ALC		;CLEAR THE ALLOCATED FLAG
	ANDCAM T1,DEVCH1(T2)	;...
	CAIE T4,-2		;IS DEVICE IN THE POOL NOW?
	RETERR (ALCX6,<UNLOCK DEVLCK>) ;NO, TELL CALLER
	HRLM T3,DEVUNT(T2)	;YES, PUT IT IN FREE POOL
	JRST ALCALR		;GO RETURN
;SET THE DEVICE TABLES LOCK.
;MUST BECOME NOINT SO CONTROL DOESN'T RETURN TO USER WITH LOCK
;SET.

LCKDVL:: NOINT
	SE1CAL
	AOSN DEVLCK		;ATTEMPT LOCK
	RET			;SUCESS
	OKINT			;FAILURE, RE-ENABLE INTERRUPTS
	CAIA			;SO USER CAN BREAK OUT WITH ^C
	JRST LCKDVL		;WAIT SHORT TIME THEN TRY AGAIN
	CBLK1			;THIS RETURNS .-1
; Change account

.CACCT::MCENT
	STKVAR <CACUSR>
	MOVE A,JOBNO
	MOVE B,JOBDIR(A)	;GET LOGIN DIRECTORY NUMBER
	TRNN B,777777
	RETERR(CACTX2)
	HRLI B,USRLH		;MAKE IT A 36-BIT USER NUMBER
	MOVEM B,CACUSR		;SAVE IT
	MOVE A,B
	CALL CNVDIR		;CONVERT THIS TO A DIR NUMBER
	CALL SETDIR		;MAP IN DIRECTORY
	 RETERR ()		;SETDIR FAILURE
	UMOVE A,1
	MOVE B,CACUSR		;GET BACK USER NUMBER
	CALL SETACT
	 RETERR( ,<CALL USTDIR>)
	CALL USTDIR
	CALL LOGCJM
	MOVE A,TODCLK
	MOVEM A,CONSTO
	CALL LGTAD		;GET DATE/TIME
	MOVEM A,CTIMON		;SAVE IN JSB
	MOVE A,JOBNO
	SETZM JOBRT(A)
	SMRETN

; INTERNAL ROUTINE TO SET AN ACCOUNT
; CALL:	A/ POINTER TO AN ACCOUNT STRING OR 5B2+ACCOUNT NUMBER
;	B/ 36-BIT USER NUMBER
;	CALL SETACT
; RETURNS: +1	ERROR
;	   +2	SUCCESS

SETACT:	TRVAR <<ACTBUF,MAXLW+1>,ACTLN,PTR,USER>
	MOVEM B,USER		;SAVE USER NUMBER
	MOVEM A,PTR		;SAVE THE POINTER
	SETZM ACTBUF
	MOVEI A,ACTBUF
	HRLS A
	AOS A
	MOVEI B,ACTBUF
	ADDI B,MAXLW
	BLT A,0(B)		;CLEAR THE BUFFER
	MOVE B,PTR
	CAML B,[5B2]
	CAMLE B,[6B2-1]
	JRST SETAC1		;NOT A NUMBER
	TLZ B,700000		;NUMBER, CONVERT IT TO A STRING
	HRROI A,ACTBUF
	AOS A			;STRING STARTS PAST FIRST WORD IN ACTBUF
	MOVEI C,12		;NUMBERS ARE DECIMAL
	NOUT			;DO THE CONVERSION
	 RETBAD ()		;FAILED
	IBP A			;STEP PAST NULL SO COUNT IS RIGHT
	HRRZ B,A		;GET THE LENGTH OF THE STRING
	SUBI B,ACTBUF		;IN FULL WORDS ONLY
	AOS B			;CORRECT THE COUNT
	MOVEM B,ACTLN		;SAVE IT
	SOS B
	MOVNS B
	HRLZ A,B		;MAKE THIS LOOK LIKE A LOOKUP PTR
	HRRI A,ACTBUF
	JRST SETAC2

SETAC1:	MOVEI A,ACTBUF
	CALL CPYFU1		;COPY ACCOUNT STRING
	JRST [	BUG(CHK,CPYUF1,<CACCT: IMPOSSIBLE FAILURE OF CPYFU1.>)
		RETBAD (CACTX1)]
	HLRE B,A
	MOVNS B
	MOVEM B,ACTLN		;STRING LENGTH IN FULL WORDS
SETAC2:	MOVE B,A		;B/ POINTER TO STRING
	MOVE A,USER		;GET USER NUMBER
	CALL VERACT		;VALIDATE THE ACCOUNT
	 RETBAD ()		;ERROR, RETURN
	MOVEM A,PTR		;SAVE INFO RETURNED BY VERACT
	MOVEM B,USER		; ...
	TXNE A,AC%MCH		;ACCOUNT MATCH ACCTSR?
	RETSKP			;YES, RETURN NOW
	MOVE B,ACTLN		;GET BACK STRING LENGTH
	ADDI B,2		;# FULL WORDS PLUS REMAINDER
	MOVEM B,ACCTSL		;SET UP COUNT OF WORDS IN ACCOUNT STRING
	HRROI A,ACCTSR
	MOVEI B,ACTBUF
	HRLI B,(<POINT 7,0,35>)	;POINT TO START OF ACCOUNT TEXT STRING
	MOVEI C,MAXLC+1
	MOVEI D,.CHNUL		;TERMINATE ON NULL BYTE
	SOUT			;COPY VALIDATED STRING TO JSB
	 ERJMP [RETBAD ()]
	MOVE A,USER		;GET THIS ACCOUNT'S EXPIRATION DATE
	MOVEM A,ACCTSX		;PUT IT IN JSB
	RETSKP			;GIVE GOOD RETURN
;SPECIAL ROUTINE USED BY LOGIN TO FIND AND USE THE DEFAULT
;ACCOUNT FOR THIS LOGIN. DIRECTORY MUST BE MAPPED AND LOCKED.

SETACL:	TRVAR <<ACTBUF,MAXLW+1>,ACTLN,PTR,USER>
	SETZB D,1+ACTBUF	;INIT COUNTS AND STRING
	MOVEM B,USER		;SAVE USER NUMBER
	MOVE C,DIRORA		;GET DIR BASE ADDRESS
	LOAD B,DRACT,(C)	;GET DEFAULT ACCOUNT STRING
	JUMPE B,SETAL1		;IF NONE, GO ON
	ADD B,DIRORA		;GET POINTER TO BLOCK
	HRRZ A,0(B)		;GET SIZE OF BLOCK
	SOS A			;COUNT OF WORDS IN ACCOUNT STRING
	MOVE D,A		;SAVE COUNT
	AOS B			;POINT TO START OF STRING
	MOVEI C,1+ACTBUF	;POINT TO WHERE IT WILL GO
	CALL XBLTA		;MOVE STRING TO STACK
SETAL1:	MOVEM D,ACTLN		;SAVE SIZE OF STRING
	MOVNI D,-1(D)		;GET -NWORDS+1
	MOVSI A,0(D)		;TO LH OF A
	HRRI A,ACTBUF		;FORM LOOKUP POINTER
	CALLRET SETAC2		;AND CONTINUE IN MAIN ROUTINE
; Clear input buffer

.CFIBF::MCENT
	CALL CHKTTY
	 JRST MRETN
	CALL LCKTTY		;POINT TO DYNAMIC DATA, PREVENT DEALLOCATION
	 ITERR (TTYX01,<CALL ULKTTY>) ;FAIL IF NOT ACTIVE
	CALL TTCIB0
	CALL ULKTTY		;ALLOW DEALLOCATION
	JRST MRETN

; Clear file output buffer

.CFOBF::MCENT
	CALL CHKTTY
	 JRST MRETN
	CALL LCKTTY		;POINT TO DYNAMIC DATA, ALLOW DEALLOCATION
	 ITERR (TTYX01,<CALL ULKTTY>) ;NOT ACTIVE. FAIL
	CALL TTCOBF
	CALL ULKTTY		;ALLOW DEALLOCATION
	JRST MRETN
; Connect to directory
; Call:	1	; Directory number
;			;B0 - CHECK PSWD ONLY AND DON'T CONNECT
;			;B1 - DON'T CONNECT
;	2	; String pointer to password
;	CNDIR
; Return
;	+1	; Error
;	+2	; Ok

.CNDIR::MCENT
	ITERR (CNDIX7)		;CNDIR WAS REPLACED BY ACCES
;CRJOB -- CREATE A JOB OTHER THAN THIS ONE

;CALL:	1		;FLAG BITS
;	2		;POINTER TO ARGUMENT BLOCK
;	CRJOB
;RETURNS:
;	+1		;ERROR
;	+2		;SUCCESS
;	IN 1		;JOB NUMBER OF NEWLY CREATED JOB
;
;FLAGS IN AC1:
;B0	CJ%LOG		;ON - TRY TO LOG THE NEW JOB IN
;			;OFF - CREATE AN UN-LOGGED-IN JOB
;B1	CJ%NAM		;ON - USE NAME AND PASSWORD IN ARG BLOCK
;			;OFF - LOG IN AS SAME USER AS EXECUTOR OF CRJOB
;B2-3	CJ%ACT		;ACCOUNT FIELD. 0 - USE CURRENT ACCOUNT
;			;1 - USE ACCOUNT SUPPLIED IN ARG BLOCK
;			;2 - USE DEFAULT ACCOUNT OF NEW JOB'S USER
;B4	CJ%ETF		;ON - PUT EXEC IN TOP FORK OF NEW JOB
;			;OFF - FILE REQUESTED BY B5 IS IN TOP FORK
;B5	CJ%FIL		;ON - FILENAME IN ARG BLOCK SHOULD BE GET'ED
;			;OFF - JUST AN EXEC. NO FILE.
;B6	CJ%ACS		;ON - IF B5 IS ON, PUT AC'S FROM ARG INTO FORK
;			;     WHICH HAS THE FILE GET'ED INTO IT
;B7	CJ%OWN		;ON - MAINTAIN OWNERSHIP OF THE NEW JOB
;			;OFF - DISOWN THE NEW JOB
;B8	CJ%WTA		;ON - WAIT TILL ATTACHED BEFORE RUNNING NEW JOB
;B9	CJ%NPW		;ON - NO PASSWORD CHECK IN NEW JOB LOGIN
;			;     (REQUIRES WHEEL/OPER, OR B1 OFF)
;B10	CJ%NUD		;ON - NO UPDATE OF LAST-LOGIN DATE.
;B11	CJ%SPJ		;ON - DO SPJFN WITH ARG IN ARG BLOCK
;B12	CJ%CAP		;ON - SET NEW JOB'S CAPMSK RH TO MY CURRENT
;			;     CAPENB RH, UNTIL IT LOGS IN.
;B13	CJ%CAM		;CAPABILITY MASK AFTER LOGIN
;B14	CJ%SLO		;SIGNAL THE SUPPLIED PID AT LOGOUT TIME
;B17	CJ%DSN		;ON - DISOWN EXISTING JOB (IF IT'S MINE), JOB
;			;     NUMBER IS IN AC 3
;IN PARAMETER BLOCK:
;WD0	.CJNAM		;STRING POINTER TO NAME FOR LOGIN
;WD1	.CJPSW		;STRING POINTER TO PASSWORD FOR LOGIN
;WD2	.CJACT		;ACCOUNT DESIGNATOR/STRING POINTER FOR LOGIN
;WD3	.CJFIL		;STRING POINTER TO FILENAME TO GET
;WD4	.CJSFV		;SFRKV OFFSET TO START FILE
;WD5	.CJTTY		;TTY DESIGNATOR, OR NULL DESIGNATOR, FOR CTTY
;WD6	.CJTIM		;TIME LIMIT (NOT IMPLEMENTED)
;WD7	.CJACS		;POINTER TO 16 WORDS OF AC'S FOR FORK
;WD8	.CJEXF		;EXEC FLAGS, FOR AC1 OF STARTED EXEC
;WD9	.CJPRI		;PRIMARY JFN'S FOR SPJFN IN NEW JOB
;WD10	.CJCPU		;CPU LIMIT (ZERO MEANS NONE)
;WD11	.CJCAM		;CAPABILITY MASK
;WD12	.CJSLO		;PID TO SEND LOGOUT MSG TO
.CRJOB::MCENT			;CREATE JOB JSYS
CRJOB1:	NOINT			;PROTECT THE CRJLCK RESOURCE
	LOCK (CRJLCK,<JRST CRJLKF>)
	SETZM CRJANS		;CLEAR THE RESULT COMMUNICATION WD
	MOVE T1,JOBNO		;GET MY JOB NUMBER
	MOVEM T1,CRJONJ		;FOR CREATEE TO SEE
	MOVE T1,CAPENB		;AND MY CAPS
	MOVEM T1,CRJOJC		; ..
	UMOVE Q1,1		;FLAGS FROM CALLER
	MOVEM Q1,CRJAC1		;STORE THEM FOR NEW JOB
	TXNE Q1,CJ%DSN		;REQUEST TO DISOWN A JOB?
	JRST CRJDSN		;YES.
	TXNN T1,SC%WHL+SC%OPR	;IS THIS A PRIVILEGED JOB?
	TXNE Q1,CJ%LOG+CJ%ETF	;NO. MUST HAVE EXEC IN TOP FK, OR LOGIN
	SKIPA			;OK.
	JRST CRJILG		;NO GOOD. GIVE ILLEG COMBINATION ERROR.
	UMOVE Q2,2		;OK, GET POINTER TO ARG BLOCK
	SETOM CRJTTY		;ASSUME DETACHED NEW JOB
	UMOVE T1,.CJTTY(Q2)	;GET THE TTY DESIGNATOR
	CAIN T1,.NULIO		;NUL DESIGNATOR?
	JRST CRJB1A		;YES. OK.
	CAIL T1,400000		;NO, SEE IF IT'S A VALID TTY
	CAIL T1,400000+NLINES	; ..
	JRST CRJTTX		;NOT A LEGAL TTY NUMBER
	MOVE T2,T1		;GET TTY DESIGNATOR IN T2
	SUBI T2,400000		;TTY NUMBER IS A REAL TTY.
	NOSKED			;CHECK TO SEE IF IT'S AVAILABLE.
	CALL GTCJOB		;STABLE STATE OF TTFORK...
	 JRST CRJOTX		;TTY NOT ASSIGNED
	CAMN T3,JOBNO		;IS THE TTY ASSIGNED TO ME?
	CAMN T2,CTRLTT		;AND NOT MY CONTROLLING TERMINAL?
CRJOTX:	JRST [	OKSKED		;NOT A VALID TTY FOR THIS USE
		JRST CRJTTX]	;FAIL.
	PUSHJ P,CHKDEV		;SEE IF IT'S ASSIGNED TO ME
	  JRST CRJOTX		;IT'S NOT.
	TXNN T3,DV%ASN		;ASSIGNED?
	JRST CRJOTX		;NO.
	UMOVE Q1,T1		;RESTORE AC'S CLOBBERED ABOVE
	UMOVE Q2,T2
	UMOVE T1,.CJTTY(Q2)	;GET TTY DESIGNATOR AGAIN
	ANDI T1,377777		;JUST THE LINE NUMBER
	MOVEM T1,CRJTTY		;STORE THE TTY TO START JOB ON
	OKSKED			;LET TTFORK CHANGE NOW
	TRO T1,400000		;AND NOW RELEASE IT FROM THIS JOB
	RELD
	 JFCL
;FALL THRU
;FALLS THRU FROM ABOVE
CRJB1A:	JE CJ%LOG,Q1,CRJOB4	;JUMP IF NOT LOGGING IN
	TXNN Q1,CJ%NAM		;USING SUPPLIED PASSWORD AND NAME?
	JRST CRJOB2		;NO, USE MINE.
	UMOVE T2,.CJNAM(Q2)	;GET THE SUPPLIED NAME STRING
	MOVEI T1,CRJUSR-1	;WHERE TO PUT THE TEXT
	PUSHJ P,CPYFU1		;COPY THE STRING
	 JRST CRJCPX		;FAILED?
	UMOVE T2,.CJPSW(Q2)	;COPY THE PASSWORD
	MOVEI T1,CRJPSW-1	;TO HERE
	PUSHJ P,CPYFU1		; ..
	 JRST CRJCPX		;CAN'T?
	JRST CRJOB4		;OK, HAVE NAME AND PASSWORD NOW

;HERE'S THE FAIL PATH ON THE LOCK MACRO ABOVE.
CRJLKF:	OKINT
	MOVEI T1,CRJLCK		;WAIT, INTERRUPTABLE, FOR THE LOCK
	PUSHJ P,DISL
	JRST CRJOB1		;AND GO GRAB IT NOW.

;HERE TO COPY MY OWN NAME AND PASSWORD FOR NEW JOB. ACTUALLY,
; JUST PUT MY NAME IN, AND CAUSE LOGIN TO NOT CHECK PASSWORD.
CRJOB2:	HRRZ T2,JOBNO		;THIS JOB NUMBER
	HRRZ T2,JOBDIR(T2)	;HERE IS MY LOGGED IN USER NUMBER
	HRLI T2,USRLH		;MAKE A USER NUMBER
	HRROI T1,CRJUSR		;PUT THE NAMESTRING HERE
	DIRST			;CONVERT TO STRING
	 JRST CRJXXX		;FAILED
;FALL THRU TO ACCOUNT HANDLING
;FALLS THRU FROM ABOVE

;NOW GET THE ACCOUNT FOR NEW JOB
CRJOB4:	SETZM CRJACT		;DEFENSIVE CHECKS ON ACCOUNT.
	LOAD T1,CJ%ACT,Q1	;SEE WHERE TO GET ACCOUNT FROM
	TRNE T1,.CJUDA		;WANT DEFAULT ACCOUNT?
	JRST CRJB5Z		;YES. NOTHING TO SET UP.
	TRNE T1,.CJUAA		;NO, MINE, OR SUPPLIED?
	JRST CRJOB5		;SUPPLIED.
;GET STRING ACCOUNT FOR CURRENT JOB
CRJB4A:	MOVE T1,[XWD ACCTSR,CRJACT+1]
	BLT T1,CRJACT+10	;COPY THE ACCOUNT STRING
	JRST CRJB5S		;DONE WITH THE ACCOUNT

;HERE IF ACCOUNT WAS SUPPLIED IN ARG BLOCK.
CRJOB5:	UMOVE T2,.CJACT(Q2)	;GET ACCT NUMBER/POINTER FROM BLOCK
	MOVE T1,T2		;SEE IF NUMERIC OR STRING
	TLC T1,(5B2)		; ..
	TLNE T1,(7B2)		; ..
	JRST CRJB5A		;STRING.
	MOVEM T2,CRJACT		;NUMERIC.
	JRST CRJB5Z		;DONE WITH ACCOUNT

CRJB5A:	MOVEI T1,CRJACT		;COPY STRING TO HERE + 1
	PUSHJ P,CPYFU1		; ..
	 JRST CRJCPX		;CAN'T COPY IT?
CRJB5S:	MOVE T1,[000700,,CRJACT] ;MUST BE POSITIVE NUMBER
	MOVEM T1,CRJACT		;POINTER TO THE ACCOUNT
CRJB5Z:	JRST CRJB5I		;DONE WITH ACCOUNT. GO LOOK FOR INFERIOR
;MORE CRJOB. HERE TO DEAL WITH INFERIOR FORK
CRJB5I:	UMOVE T2,.CJEXF(Q2)	;GET FLAGS FOR EXEC, IN CASE NEEDED
	MOVEM T2,CRJEXF		;SAVE FOR LATER
	UMOVE T2,.CJSFV(Q2)	;START FORK VECTOR OFFSET
	HRRZM T2,CRJEVO		;SAVE THAT TOO
	UMOVE T2,.CJPRI(Q2)	;AND PRIMARY JFN'S, MAYBE NEEDED TOO
	MOVEM T2,CRJPJF		; ..
	TXNN Q1,CJ%FIL		;IS THERE A FILE TO RUN?
	JRST CRJB5Y		;NO.
	MOVEI T1,CRJFIL-1	;YES, GET ITS FILE NAME
	UMOVE T2,.CJFIL(Q2)	;FROM HERE IN ARG BLOCK
	MOVEI T3,<5*40>-1	;CHARACTERS THAT CAN FIT IN STORAGE BLK
	PUSHJ P,CPYFU2		;COPY THE STRING
	 JRST CRJCPX		;CAN'T?
	TXNN Q1,CJ%ACS		;WANT THE AC'S SET UP?
	JRST CRJB5C		;NO
	MOVEI T1,20		; Length of AC block
	UMOVE T2,.CJACS(Q2)	;YES. GET THE POINTER TO THEM
	XMOVEI T3,CRJFAC		; Place to store user's
	CALL BLTUM
CRJB5C:
CRJB5Y:	;END OF CODE DEALING WITH THE INFERIOR FORK TO RUN
	UMOVE T2,.CJCAM(Q2)	;CAPABILITIES MASK FOR LOGIN
	TXNN Q1,CJ%CAM		;SUPPLIED?
	SETO T2,0		;NO, ASSUME ALL BITS ALLOWED
	MOVEM T2,CRJCAM		;SAVE TO MASK AT LOGIN TIME
	UMOVE T2,.CJSLO(Q2)	;A PID TO SIGNAL AT LOGOUT TIME
	TXNN Q1,CJ%SLO		;UNLESS NOT TO USE ONE
	MOVEI T2,0		;IN WHICH CASE, USE ZERO
	MOVEM T2,CRJSLO		;SAVE IT
	UMOVE T2,.CJCPU(Q2)	;CPU LIMIT TO APPLY (ZERO IF NONE)
	MOVEM T2,CRJCPU		; ..
;FALL THRU
;FALLS THRU FROM ABOVE
;HERE TO ACTUALLY PUT IN THE REQUEST FOR SCHEDULER TO START THE JOB
	MOVSI T1,-2		;FLAG OF -2 FOR JOBSRT MEANS CRJOB
	HRRI T1,JOBSRT		;AND SCHED LEVEL CODE ADDR
	CALL SCDRQ7		;REQUEST IT.
	MOVEI T1,CRJANS		;NOW WAIT FOR AN ANSWER.
	CALL DISN		; ..
	MOVE T1,CRJANS		;WHAT HAPPENED?
	JUMPGE T1,CRJXXX	;IF PLUS, IT FAILED.
	HLRZ T1,CRJONJ		;IT SUCCEEDED. GET THE JOB NUMBER
	UMOVEM T1,1		;RETURN IT TO THE CALLER.
CRJXIT:	UNLOCK CRJLCK		;RELEASE THE STORAGE LOCK
	SMRETN			;SUCCESS RETURN.

CRJDSN:	UMOVE T1,3		;GET JOB NUMBER TO DISOWN
	CAIL T1,0		;A LEGAL JOB NUMBER?
	CAIL T1,NJOBS		; ..
	JRST CRJILG		;NO. ILLEGAL ARG FAILURE
	NOSKED			;FREEZE THE OWNERSHIP TABLE
	HRRZ T2,JOBONT(T1)	;GET THE JOB'S OWNER
	CAMN T2,JOBNO		;IS IT ME?
	SETOM JOBONT(T1)	;YES. I GIVE IT UP.
	OKSKED			;FREE THE TABLE
	CAME T2,JOBNO		;WAS IT OK?
	JRST CRJILG		;NO. FAIL.
	JRST CRJXIT		;YES. GIVE SUCCESS RETURN.

CRJCPX:				;COPY OF USER STUFF FAILED
CRJILG:	MOVEI T1,CRJBX1		;ILLEGAL PARAMETER OR BIT COMBINATION
	JRST CRJXXX
CRJTTX:	MOVEI T1,CRJBX4		;BAD TTY REQUESTED
CRJXXX:	UNLOCK CRJLCK		;FREE THE STORAGE BLOCK
	OKINT
	JRST MRETNE		;RETURN FAIL, ERROR NUMBER IN 1
; Delete deleted files
; 1/ DD%DTF (B0) = DELETE ;T FILES ALSO
;	2/	DIRECTORY NUMBER

.DELDF::MCENT
	STKVAR <DELDSD>	;DIRECTORY NUMBER SPECIFIED
	UMOVE A,2		;GET THE DIRECTORY NUMBER
	MOVEM A,DELDSD		;SAVE THE STRUCTURE/DIRECTORY NUMBER
	CALL SETDIR
	 ITERR(DELDX2)		;NO SUCH USER
	MOVX B,DC%CN		;REQUIRES OWNER ACCESS
	CALL DIRCHK		;SEE IF USER CAN CONNECT (AND THUS OWN DIRECTORY)
	 JRST [	ULKDIR		;UNLOCK DIR
		ITERR(DELDX1)]	;ERROR
DELDF1:	CALL USTDIR
	MOVE A,DELDSD		;GET THE DIRECTORY NUMBER
	XCTU [HLLZ F,A]		;GET FLAGS
	TXZ F,1B17		;DON'T ALLOW DELETE ALL
	CALL DELDEL
	 ITERR ()		;ERROR OCCURED DURING EXPUNGE
	JRST MRETN
; Device to string
; Call:	1	; Destination designator
;	2	; Device designator
;	DEVST
; Return
;	+1	; Ok

.DEVST::MCENT
	UMOVE A,2
	CALL CHKDEV
	 JRST [	CAIE A,DEVX2
		RETERR()
		JRST .+1]
	MOVE C,DEVNAM(B)
	CALL DEVST0		;COPY NAME STRING TO USER SPACE
	SMRETN

;ROUTINE TO COPY STR NAME TO USER STRING
;ACCEPTS IN C/	SIXBIT STR NAME

DEVST0:	SETZ B,
	LSHC B,6		;GET NEXT BYTE
	JUMPE B,DEVST1
	ADDI B,40
	CALL BOUTA
	JRST DEVST0

DEVST1:	RET

; Dismiss until input buffer is empty

.DIBE::	MCENT
DIBE1:	UMOVE T1,1		;GET DESIGNATOR
	CALL CHKTTR
	 JRST MRETN
	CALL LCKTTY		;POINT TO DYNAMIC DATA, PREVENT DEALLOCATION
	 ITERR (TTYX01,<CALL ULKTTY>) ;NOT ACTIVE. FAIL
	CALL TTDIBE
	 JRST DIBE1		;NEED TO RETRY
	CALL ULKTTY		;ALLOW DEALLOCATION
	JRST MRETN
; Directory number to string conversion
; Call:	1	; Sink designator
;	2	; Directory number
;	DIRST
; Return
;	+1	; Error
;	+2	; Ok

.DIRST::MCENT
	UMOVE A,2		;GET DIR NUMBER
	CALL DIRST0		;DO THE WORK
	 RETERR ()		;FAILED
	SMRETN			;SUCCESSFUL

DIRST0:	STKVAR <<DIRSTN,MAXLW>,DIRSTR>
	MOVEM A,DIRSTR		;SAVE THE DIRECTORY NUMBER
	CALL GDIRST		;GET POINTER TO NAME STRING INTO A
	 RETBAD ()
	XMOVEI B,1(A)		;COPY NAME STRING TO STACK
	XMOVEI C,DIRSTN
	LOAD A,NMLEN,(A)	;GET NUMBER OF WORDS
	SOS A
	CALL XBLTA
	LOAD B,CURSTR		;GET CURRENT STR #
	MOVE C,DEVNAM+DVXST0(B)	;GET SIXBIT STR DEVICE NAME
	CALL USTDIR		;UNLOCK THE DIR
	HLRZ A,DIRSTR		;GET DIR NUMBER BACK AGAIN
	CAIN A,USRLH		;IS THIS A USER NUMBER?
	 JRST DIRST1		;YES, DONT PUT ON THE PUNCTUATION
	CALL DEVST0		;OUTPUT THE STR NAME TO THE USER
	MOVEI B,":"		;NOW SOME PUNCTUATION
	CALL BOUTA
	MOVEI B,"<"		;AND THE DIR DELIMITER
	CALL BOUTA
DIRST1:	MOVEI A,DIRSTN		;GET POINTER TO STRING
	SOS A			;ADR-1
	CALL JFNSSD		;NOW OUTPUT THE DIR NAME
	MOVEI B,">"		;AND CLOSE WITH CLOSE BRACKET
	HLRZ A,DIRSTR		;GET STRUCTURE NUMBER AGAIN
	CAIE A,USRLH		;USER NUMBER?
	CALL BOUTA		;NO, OUTPUT THE CLOSE BRACKET
	RETSKP

; Dismiss until output buffer is empty

.DOBE::	MCENT
DOBE1:	UMOVE T1,1		;GET DESIGNATOR
	CALL CHKTTR
	 JRST MRETN
	CALL LCKTTY		;POINT TO DYNAMIC DATA, PREVENT DEALLOCATION
	 ITERR (TTYX01,<CALL ULKTTY>) ;NOT ACTIVE. FAIL
	CALL TTDOBE
	 JRST DOBE1		;NEED TO RETRY
	CALL ULKTTY		;ALLOW DEALLOCATION
	JRST MRETN
; Enter fact file
; Call:	LH(1)	; Minus entry size
;	RH(1)	; Location of entry
;	EFACT
; Return
;	+1	; Error
;	+2	; Ok

.EFACT::MCENT
	MOVE B,CAPENB
	MOVE C,0(P)		;GET CALLER'S PC
	TXNE C,UMODF		;CALLED FROM MONITOR?
	TXNE B,SC%WHL!SC%OPR	;NO, PRIVILEGED?
	SKIPA B,FACTSW		;YES, OK SO FAR
	RETERR(EFCTX1)
	TLNN B,(SF%FAC)
	SMRETN			; Fact file not on
	HLRO B,A		; Get size
	CAMG B,[-^D64]
	RETERR(EFCTX2)		; Too big
	NOINT
	PUSH P,CAPENB		; Save current caps
	MOVEI A,SC%WHL+SC%OPR	; Set bits to ensure access to
	IORM A,CAPENB		; Accounts directory and fact file
	MOVEI C,^D30
EFACT2:	HRROI B,FCTFIL		;GET POINTER TO NAME OF FACT FILE
	MOVSI A,(GJ%PHY!GJ%SHT)
	GTJFN
	 JRST EFACT3
	PUSH P,1
	MOVE 2,[XWD 440000,20000]
	OPENF			; Open for append
	JRST EFACT4
EFACT6:	POP P,1
	UMOVE C,1
	UMOVE B,(C)
	HLRE D,C
	MOVNS D
	DPB D,[POINT 6,B,35]
	JRST .+2
EFACT1:	UMOVE B,(C)
	BOUT
	ERJMP [	BUG(CHK,EFACF3,<EFACT: FAILED TO WRITE INTO FACT FILE>)
		JRST EFCT1A]
	AOBJN C,EFACT1
EFCT1A:	CLOSF
	BUG(CHK,EFACF1,<EFACT: CLOSF FAILED TO CLOSE FACT FILE.>)
	POP P,CAPENB		; Restore caps
	SMRETN
EFACT4:	CAIE A,OPNX9
	SETZ C,
	POP P,1
	RLJFN
	 JFCL
	SOJLE C,EFACT3
	MOVEI A,^D4000
	DISMS
	JRST EFACT2

EFACT3:	HRROI 2,FCTFIL		;GET POINTER TO NAME OF FACT FILE
	MOVSI 1,(GJ%FOU!GJ%PHY!GJ%SHT)
	GTJFN
	 JRST EFACT9
	MOVEI C,^D30
EFACT8:	PUSH P,1
	MOVE 2,[XWD 440000,20000]
	OPENF
	JRST EFACT5
	JRST EFACT6

EFACT5:	CAIE A,OPNX9
	JRST EFACT7
	SOJLE C,EFACT7
	MOVEI A,^D4000
	DISMS
	POP P,1
	JRST EFACT8

EFACT7:	POP P,1
	RLJFN
	JFCL
EFACT9:	POP P,CAPENB		; Restore caps
	RETERR(EFCTX3)
; Error number to string
; Call:	1	; Output designator
;	2	; Error number
;	3	; -NCHARS,,CTRL BITS
;	ERSTR

.ERSTR::MCENT
	CALL FLOCK		;LOCK FORK STRUCTURE
	HLRZ 1,2
	CALL SETLFK		; Map psb of the fork
	UMOVE B,3
	HRLZI C,ERRSAV(1)
	HRRI C,4
	TRNN B,1B19
	BLT C,10
	XCTU [HRRZ C,2]
	CAIN C,777777
	MOVE C,LSTERR(1)
	CALL [	SAVET		;UNLOCK AND UNMAP PSB HERE
		CALL CLRLFK	;BUT PRESERVE ACS
		CALLRET FUNLK]
	MOVE A,C		;SEE IF THIS IS A LEGAL ERROR CODE
	TRZ A,77777		;MASK OFF LOW ORDER BITS
	CAIE A,.ERBAS		;IS THIS LEGAL
	JRST MRETN		;NO, MUST HAVE CORRECT BASE ADDRESS
	ANDI C,077777		;FLUSH NON-SIGNIFICANT BITS
	JUMPE C,MRETN		;0 IS ILLEGAL ERROR CODE

; We now have error number in c, parameters in 4-10, bits and count in b

	PUSH P,B
	HRROI 2,[ASCIZ /SYSTEM:ERRMES.BIN/]
	MOVSI 1,(GJ%OLD!GJ%PHY!GJ%SHT)
	GTJFN			; Get jfn for error mnemonics
	JRST NOFIL
	MOVE 2,[XWD 440000,200000]
	PUSH P,1
	OPENF
	JRST [	POP P,1
		RLJFN
		JFCL
		JRST NOFIL]
	POP P,1
	BIN			;GET FIRST WORD WHICH IS MAX ERR NUM
	 ERJMP NOFIL2		;IF END OF FILE, FAIL
	CAMLE C,B		;THIS ONE WITHIN RANGE?
	JRST NOFIL2		;NO, FAIL
	; ..
;ERSTR...

	RIN			; Read byte number of message
	 ERJMP NOFIL2		; IF ERROR, FAIL
	JUMPE 2,NOFIL2
	PUSH P,2
	MOVEI 2,7
	SFBSZ
	 RETERR()
	POP P,2
	SFPTR			; Start reading here
	 JRST NOFIL2
	POP P,C
	HLRES C
	MOVMS C			;ALLOW + OR - NCHARS
	SKIPE C
	AOS C
CPYER1:	BIN
	 ERJMP ERSTDN		;IF EOF, THEN DONE
	CAIN 2,"@"
	JRST ERSTDN
	CAIN 2,"_"
	JRST EXPND
	CALL ERST9
	JRST ERSTDS
	JRST CPYER1
NOFIL:	POP P,B
	MOVE D,[POINT 7,[ASCIZ /CANNOT FIND ERROR MESSAGE FILE/]]
NOFILL:	ILDB B,D
	JUMPE B,MRETN
	CALL ERST9
	 JRST MRETN
	JRST NOFILL

EXPND:	MOVEI D,0
	BIN
	 ERJMP ERSTDN
	CAIN B,"_"
	JRST CPYER1
EXPND1:	CAIG 2,"9"
	CAIGE 2,"0"
	JRST EXPNDD
	IMULI D,^D10
	ADDI D,-60(B)
	BIN
	 ERJMP ERSTDN
	JRST EXPND1
;ERSTR...

EXPNDD:	CAIN B,"E"
	JRST EXPEXP
	CAIL D,5
	JRST EXPND
	CAIN B,"A"
	JRST EXPASC
	CAIN B,"O"
	JRST EXPOCT
	CAIN B,"D"
	JRST EXPDEC
	CAIN B,"H"
	JRST EXPHLF
	CAIN B,"F"
	JRST EXPFLT
	CAIN B,"L"
	JRST EXPLOC
	CAIN B,"N"
	JRST EXPJFN
	CAIE B,"@"
	JRST EXPND
	JRST ERSTDN

EXPEXP:	JRST EXPND

EXPASC:	MOVE B,ERRSAV(D)
	CALL ERST9
	 JRST ERSTD0
	JRST EXPND

EXPOCT:	MOVE B,ERRSAV(D)
	MOVEI D,10
	CALL ERNOUT
	 JRST ERSTD0
	JRST EXPND

EXPDEC:	MOVE B,ERRSAV(D)
	MOVEI D,12
	CALL ERNOUT
	 JRST ERSTD0
	JRST EXPND
;ERSTR...

ERNOUT:	PUSH P,A
	MOVE A,B
	CALL ERNOU1
	SOS -1(P)
	POP P,A
	RETSKP

ERNOU1:	IDIV A,D
	HRLM B,(P)
	JUMPE A,.+3
	CALL ERNOU1
	RET
	HLRZ B,(P)
	ADDI B,"0"
	JRST ERST9

EXPHLF:	MOVE D,ERRSAV(D)
	PUSH P,D
	HLRZ B,D
	MOVEI D,10
	CALL ERNOUT
	 JRST ERSTD1
	POP P,D
	MOVEI B,","
	CALL ERST9
	 JRST ERSTD0
	CALL ERST9
	JRST ERSTD0
	HRRZ B,D
	MOVEI D,10
	CALL ERNOUT
	 JRST ERSTD0
	JRST EXPND

EXPFLT:
EXPLOC:
EXPJFN:	JRST EXPND

ERSTD1:	POP P,D
	JRST ERSTD0

ERSTDN:	AOS -1(P)
ERSTDS:	AOS -1(P)
ERSTD0:
NOFIL2:	CLOSF
	JFCL
	JRST MRETN

NOFIL1:	RLJFN
	 JFCL
	JRST MRETN
; GET ACCOUNT
;
; CALL:	1/ JOB NUMBER OR -1 FOR SELF
;	2/ POINTER TO E TO WHERE TO STORE STRING (IF ANY)
;	GACCT
; RETURNS
;	+1 ALWAYS, 2/ 5B2+NUMERIC ACCOUNT #, OR
;		      UPDATED POINTER TO ACCOUNT STRING AT E

.GACCT::MCENT			;MONITOR CODE ENTRY
	UMOVE T1,1		;GET JOB NUMBER
	CAMN T1,[-1]		;SELF SPECIFIED ?
	MOVE T1,JOBNO		;YES, GET JOB NUMBER
	CAIL T1,0		;NOT SELF - WAS JOB NUMBER REQUEST
	CAIL T1,NJOBS		; A LEGAL JOB NUMBER ?
	ITERR (GACCX1)		;NO - INVALID JOB NUMBER SPECIFIED

; CHECK PRIVILEGES IF NOT THIS JOB

	CAMN T1,JOBNO		;THIS JOB ?
	JRST GACC10		;YES, DO NOT CHECK CAPABILITY
	MOVE T2,CAPENB		;GET CAPABILITIES
	TXNN T2,SC%CNF!SC%WHL!SC%OPR ;HAVE CONFIDENTIAL INFORMATION ACCESS ?
	ITERR (GACCX3)		;NO, CONFIDENTIAL INFORMATION ACCESS REQUIRED

; SEE IF REQUESTED JOB EXISTS AND MAP JSB

GACC10:	CALL MAPJSB		;GO MAP JSB FOR REQUESTED JOB
	 ITERR (GACCX2)		;NO SUCH JOB
	MOVEM T1,P1		;SAVE OFFSET TO JSB

; HERE FOR ALPHANUMERIC ACCOUNTS

GACC20:	UMOVE T1,2		;GET POINTER TO USER'S STRING BUFFER
	MOVEI T2,ACCTSL(P1)	;POINT TO STRING
	CALL CPYTUS		;COPY ACCOUNT STRING TO USER SPACE

; UNMAP JSB AND RETURN

GACC30:	CALL CLRJSB		;UNMAP THE JSB
	JRST MRETN		;SUCCESS RETURN
; Get last error
; Call:	1	; Fork designator
;	GETER

.GETER::MCENT
	CALL FLOCK
	CALL SETLFK
	MOVE B,LSTERR(1)
	XCTU [HRL B,1]
	UMOVEM B,2
	CALL CLRLFK
	CALL FUNLK
	JRST MRETN
; Get tab settings

.GTABS::MCENT
	CALL CHKTTR
	 JRST [	XCTU [SETZB A,2]
		UMOVEM A,3
		UMOVEM A,4
		JRST MRETN]
	CALL TTGTBS
	UMOVEM 1,2
	UMOVEM 3,3
	UMOVEM 4,4
	JRST MRETN

; Read time and date
; Call:	RTAD
; Return
;	+1
;	1	; Current date and time or -1 if not set

.GTAD::	MCENT
	CALL LGTAD		;DO THE WORK
	UMOVEM A,1
	JRST MRETN
; Get directory info
; Call:	1	; Directory number
;	2	; Pointer to parameter block
;	3	; String pointer for password
;	GTDIR

.GTDIR::MCENT
	UMOVE Q3,2		;GET POINTER TO PARAMETER BLOCK
	XCTU [SKIPG Q2,.CDLEN(Q3)] ;GET LENGTH OF ARGUMENT BLOCK
	MOVEI Q2,.CDDGP+1	;IF NONE SET UP, USE THIS ONE
;MAKE GTDIR RETURN DIR GROUP INFO IF FIRST WORD OF ARG BLOCK = 0
	SETZ P1,		;INITIALIZE PRIVILEGE FLAG
	UMOVE A,1		;GET DIRECTORY NUMBER
	JUMPE A,GTDIR2		;IF 0, THEN GO GET DEFAULTS
	STKVAR <GTDINO>
	MOVEM A,GTDINO		;SAVE DIRECTORY NUMBER
	MOVX B,DC%CN		;SEE IF USER HAS CONNECT PRIVILEGES
	CALL SUPCHK		;SEE IF HAVE ACCESS TO SUPERIOR
	 JRST GTDIR6		;FAILED.
	MOVE A,GTDINO		;SUCCEEDED. GET DIRECTORY NUMBER
	CALL SETDIR		;MAP THE DIRECTORY
	 ITERR ()		;FAILED. RETURN ERROR
	JRST GTDIR3		;GO GET THE INFO
GTDIR6:	MOVE A,GTDINO		;A/ DIRECTORY NUMBER
	CALL SETDIR		;MAP IN THE DIRECTORY
	 ITERR()		;FAILED
	MOVE B,CAPENB
	TRNE B,SC%WHL!SC%OPR
	JRST GTDIR3		; WHEEL OR OPERATOR
	MOVX B,DC%CN		;SEE IF USER HAS OWNER ACCESS TO DIR
	CALL DIRCHK		;...
	 JRST [	UMOVE B,3	;SEE IF USER HAS GIVEN THE PASSWORD
		CALL CHKPSX
		 ITERR(GTDIX1,<ULKDIR
			MOVE T2,T1
			MOVEI T1,^D3000	;WAIT 3 SECS
			SKIPN T2	;UNLESS NO PASSWORD GIVEN
			DISMS>)		;ILLEGAL PASSWORD GIVEN
		JRST .+1]	;USER GAVE THE CORRECT PASSWORD
	SETO P1,		;MARK ONLY LIMITED ACCESS
GTDIR3:	MOVE A,DIRORA		; GET BASE OF MAPPED DIR AREA
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	JUMPN P1,GTDIR4		;IF NOT PRIVILEGED, DONT GIVE PASSWORD
	UMOVE C,3
	TLC C,-1		;SEE IF LH = -1
	TLCN C,-1
	HRLI C,(<POINT 7,0>)	;YES, SET UP BYTE POINTER
GTDIR1:	LOAD B,DRPSW,(A)	;GET POINTER TO NAME STRING
	ADD B,DIRORA		;MAKE IT ABSOLUTE
	MOVSI Q1,(POINT 7,0(B),35) ;SET UP STRING POINTER TO NAME STR
	UMOVEM C,.CDPSW(Q3)	;SAVE STARTING BYTE POINTER TO PSW
GTDIR0:	UMOVEM C,3		;SAVE UPDATED BYTE POINTER FOR USER
	ILDB D,Q1		;GET NEXT CHARACTER OF PASSWORD
	XCTBU [IDPB D,C]	;STORE CHAR IN USER SPACE
	JUMPN D,GTDIR0		;LOOP BACK TIL NULL IS SEEN
GTDIR4:	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	LOAD D,DRLIQ,(A)	;GET LOGGED IN QUOTA
	UMOVEM D,.CDLIQ(Q3)
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	LOAD D,DRPRV,(A)	;GET PRIVILEGE BITS
	UMOVEM D,.CDPRV(Q3)	;GIVE PRIVILEGE BITS TO USER
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	LOAD D,DRMOD,(A)	;MODE BITS
	TXO D,MD%SA		;ALWAYS SET STRING ACCOUNTS ALLOWED BIT
	UMOVEM D,.CDMOD(Q3)
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	LOAD D,DRLOQ,(A)	;MAX DISK ALLOCATION ALLOWED
	UMOVEM D,.CDLOQ(Q3)
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	LOAD D,DRNUM,(A)	;DIRECTORY NUMBER
	UMOVEM D,.CDNUM(Q3)
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	LOAD D,DRDPW,(A)	;DEFAULT FILE PROTECTION WORD
	UMOVEM D,.CDFPT(Q3)
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	LOAD D,DRPRT,(A)	;DIRECTORY PROTECTION
	UMOVEM D,.CDDPT(Q3)
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	LOAD D,DRDBK,(A)	;BACKUP SPEC, (# OF GEN'S TO KEEP)
	TLZ D,(7B2)		;DONT RETURN THE 5B2 BITS
	UMOVEM D,.CDRET(Q3)
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	LOAD D,DRDAT,(A)	;TIME AND DATE OF LAST LOGIN
	UMOVEM D,.CDLLD(Q3)
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	LOAD A,DRUGP,(A)	;USER GROUPS
	UMOVE B,.CDUGP(Q3)	;GET POINTER TO BLOCK TO RECEIVE LIST
	CALL GTDGRP		;GET BITS FROM LIST
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	MOVE A,DIRORA
	LOAD A,DRDGP,(A)	;DIRECTORY GROUPS
	UMOVE B,.CDDGP(Q3)	;GET POINTER TO USER BLOCK
	CALL GTDGRP		;GET 36 BIT WORD
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	MOVE A,DIRORA		;GET DIR BASE ADDR
	LOAD B,DRSDM,(A)	;GET SUBDIR QUOTA
	UMOVEM B,.CDSDQ(Q3)	;RETURN TO USER
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	LOAD A,DRCUG,(A)	;GET POINTER TO CREATABLE USER GRPS
	UMOVE B,.CDCUG(Q3)	;GET POINTER TO USERS BLOCK
	CALL GTDGRP		;RETURN GROUPS
	SOJLE Q2,GTDIR5		;RUN OUT OF ARGUMENT BLOCK YET?
	MOVE B,DIRORA
	LOAD B,DRACT,(B)	;NO, GET POINTER TO DEFAULT DIR ACCOUNT
	JUMPE B,[MOVEI B,[0]-1	;RETURN A NULL IF NO DEFAULT ACT SET UP
		 JRST GTDIR7]
	ADD B,DIRORA		;GET ABS ADR OF ACCOUNT IN DIR
GTDIR7:	MOVEI C,.CDDAC(Q3)	;PLACE TO PUT USER7'S UPDATED PTR
	UMOVE A,.CDDAC(Q3)	;POINTER TO BLOCK TO RECEIVE ACCOUNT
	CALL CPYTU1		;RETURN ACCOUNT TO USER
GTDIR5:	ULKDIR
	JRST MRETN

GTDIR2:	MOVE T1,[5B2+.STDFP]	;GET DEFAULT FILE PROTECTION
	UMOVEM T1,.CDFPT(Q3)	;RETURN VALUE TO USER BLOCK
	MOVE T1,[5B2+.STDDP]	;GET DEFAULT DIR PROTECTION
	UMOVEM T1,.CDDPT(Q3)
	MOVE T1,[.STDBS]	;GET DEFAULT BACKUP SPECIFICATION
	UMOVEM T1,.CDRET(Q3)
	MOVEI T1,.STDMX		;GET DEFAULT DISK QUOTAS
	UMOVEM T1,.CDLIQ(Q3)	;LOGGED IN QUOTA
	UMOVEM T1,.CDLOQ(Q3)	;LOGGED OUT QUOTA
	MOVEI T1,.STDSD		;GET DEFAULT SUBDIR QUOTA
	UMOVEM T1,.CDSDQ(Q3)	;RETURN IT
	JRST MRETN		;EXIT


;ROUTINE TO STORE GROUP LIST IN USER SPACE
;ACCEPTS IN A/	RELATIVE ADR OF LIST IN DIRECTORY
;	    B/	ADDRESS OF USER BLOCK TO RECEIVE LIST
;	CALL GTDGRP
;RETURNS +1:	ALWAYS

GTDGRP:	JUMPE B,R		;DO NOTHING IF USER DOESNT WANT LIST
	UMOVE C,0(B)		;GET LENGTH OF LIST AREA
	CAIG C,1		;ENOUGH ROOM FOR ANY GROUPS?
	RET			;NO
	JUMPE A,[MOVEI A,1	;IF NO GROUPS,
		UMOVEM A,0(B)	;RETURN CORRECT # IN BLOCK
		RET]
	SAVEQ
	MOVE Q3,B		;SAVE ADDRESS OF LIST AREA
	MOVEI Q2,1		;INIT COUNT TO HEADER COUNT
	ADD A,DIRORA		;GET ABS ADR OF LIST IN DIR
	LOAD D,BLKTYP,(A)	;CHECK LEGALITY OF BLOCK
	CAIE D,.TYGDB		;GROUP DESCRIPTOR BLOCK?
	JRST GTDGR4		;NO, RETURN NOTHING
	LOAD D,BLKLEN,(A)	;GET # OF GROUPS IN LIST
GTDGR2:	SOJLE D,GTDGR4		;CHECK IF DONE YET
	HLRZ Q1,1(A)		;GET FIRST GROUP NUMBER
	JUMPE Q1,GTDGR3		;IGNORE 0'S
	UMOVEM Q1,1(B)		;RETURN IT TO THE USER
	AOS Q2			;COUNT # OF GROUPS
	AOS B			;STEP USER LIST
	SOJLE C,GTDGR4		;ANY MORE ROOM IN USER BUFFER?
GTDGR3:	HRRZ Q1,1(A)		;GET NEXT GROUP NUMBER
	AOS A			;STEP POINTER TO DIR LIST
	JUMPE Q1,GTDGR2		;IGNORE ZEROES
	UMOVEM Q1,1(B)		;GIVE IT TO USER
	AOS Q2			;COUNT UP NUMBER OF GROUPS STORED
	SOJLE C,GTDGR4		;IF NO MORE ROOM, RETURN
	AOJA B,GTDGR2		;LOOP BACK FOR REST OF GROUPS

GTDGR4:	UMOVEM Q2,0(Q3)		;SAVE COUNT OF GROUPS STORED
	RET
;LOCK
;T1/ PHYSICAL PAGE(IF LK%PHY ON) OR -1 TO UNLOCK
;T2/ FKH,,PN		;NOW LIMITED TO .FHSLF
;T3/ FLAGS,,OPTIONAL REPEAT COUNT
;	LK%CNT - USE REPEAT COUNT IN RH(3)
;	LK%PHY - USE PHYSICAL PAGE IN 1 (IGNORED IF C(1) = -1)
;	LK%NCH - UNCACHE PAGES (IF LOCKING)
;	LK%AOL - ALLOW LOCKING IN OFFLINE MEMORY (IF LOCKING)

;RETURNS+1(ALWAYS):
;	PAGES LOCKED/UNLOCKED AS REQUESTED
;ITRAPS ON ERRORS
DEFSTR (LKOST,0,5,5)		;OLD PAGE STATE
DEFSTR (LKPGN,0,35,23)		;PAGE NUMBER
DEFSTR (LKUSE,0,0,1)		;ENTRY IN USE BIT

;Q1,2,3 ARE COPIES OF THE USERS ARGUMENTS

.PLOCK::MCENT
	MOVX T1,SC%WHL!SC%OPR!SC%MNT ;CHECK SPECIAL CAPABILITIES
	TDNN T1,CAPENB		; ...
	ITERR(CAPX2)		;NOT ENOUGH
	UMOVE Q1,1		;GET ARGUMENTS
	UMOVE Q2,2		; ...
	UMOVE Q3,3		; ...
	CALL PLOCK0		;DO THE WORK
	 ITERR()		;ERROR, TRAP
	JRST MRETN		;SUCCESS, RETURN TO USER

;ENTER HERE WITH:
;Q1/ PHYSICAL PAGE(IF LK%PHY ON) OR -1 TO UNLOCK
;Q2/ FKH,,PN		;NOW LIMITED TO .FHSLF
;Q3/ FLAGS,,OPTIONAL REPEAT COUNT
;	LK%CNT - USE REPEAT COUNT IN RH(3)
;	LK%PHY - USE PHYSICAL PAGE IN 1 (IGNORED IF C(1) = -1)
;	LK%NCH - UNCACHE PAGES (IF LOCKING)
;	LK%AOL - ALLOW LOCKING IN OFFLINE MEMORY (IF LOCKING)

PLOCK0::SAVEPQ
	HLRZ T1,Q2		;CHECK FOR THIS FORK ONLY
	CAIE T1,.FHSLF		; ...
	RETBAD (ARGX12)		;ERROR
	MOVE T1,FORKX		;GET INDEX OF THIS PROCESS
	HLL Q2,FKPGS(T1)	;GET SPTN OF PAGE TABLE
	TXNN Q3,LK%CNT		;USE USER SUPPLIED COUNT?
	HRRI Q3,1		;NO - USE 1
	HRRZ T1,Q3		;CHANGE OPERATION COUNT INTO
	SOSGE T1		;VERIFY REPEAT COUNT
	RETBAD (ILLX04)		;NO
	SETZM P4		;NO FREE SPACE BLOCK YET
	JUMPL Q1,LOCK0		;IF UNMAP, DON'T CHECK PHYSICAL PAGE
	TXNN Q3,LK%PHY		;USER GIVE PHYSICAL ADDRESS?
	JRST LOCK0		;NO
	ADD T1,Q1		;YES. COMPUTE LAST PAGE USED THEN
	CAMLE T1,NHIPG		;WITHIN BOUNDS?
	RETBAD (ILLX04)		;NO. CAN'T HAVE IT THEN
LOCK0:	HRRZ T1,Q3		;REPEAT COUNT AGAIN
	ADDI T1,(Q2)		;CHECK END OF GROUP
	CAILE T1,PGSIZ		; ...
	RETBAD (ILLX04)		;BEYOND PT
	NOINT			;NO INTERRUPTIONS FROM NOW ON
	; ..
;VERIFIED ALL ARGS. NOW DO LOADING

	SKIPL Q1		;DOING SOME FORM OF LOCKING?
	TXNN Q3,LK%PHY		;USER GIVING ADDRESSES?
	JRST LOCK2		;NO. GO ON TO FREE CHOICE
	MOVEI T2,1(Q3)		;GET SIZE OF BLOCK NEEDED
	CALL ASGJFR		;GET SOME FREE SPACE
	 RETBAD (MONX01,<OKINT>)		;CAN'T
	MOVE P4,T1		;SAVE BASE ADDRESS HERE
	MOVEI P2,1(P4)		;SET UP AT FIRST WORD

;HAVE FREE BLOCK. NOW ACQUIRE EACH PHYSICAL PAGE

	MOVE P1,Q1		;FIRST PHYSCIAL PAGE TO GET
	HRRZ P3,Q3		;COUNT TO GET
LOCK4:	MOVE T1,P1		;PAGE
	MOVEI T2,.MCPSO		;GET IT OFF-LINE
	CALL SETPST		;DO IT
	 JRST LCKERR		;CAN'T DO IT
	TXNN Q3,LK%AOL		;ALLOWING OFF-LINE?
	CAIN T1,.MCPSA		;NO. PAGE WAS ON-LINE?
	SKIPA			;YES. OKAY THEN
	JRST [	MOVEI T1,LOCKX1	;NO
		JRST LCKERR]	;AND DONE
	STOR P1,LKPGN,(P2)	;SAVE PAGE NUMBER
	STOR T1,LKOST,(P2)	;SAVE OLD STATE
	SETONE LKUSE,(P2)	;SAY IN USE
	ADDI P1,1		;NEXT PHYSICAL ADDRESS
	ADDI P2,1		;NEXT ENTRY IN JSB BLOCK
	SOJG P3,LOCK4		;GET THEM ALL

;ALL REQUESTED PHYSICAL PAGES NOW OFF-LINE. DO THE MAPPING

	TXO Q3,LK%AOL		;ALLOW OFF-LINE STORAGE
	; ..
LOCK2:	HRRZ P1,Q3		;GET COUNT
	SKIPE P2,P4		;HAVE A FREE BLOCK?
	ADDI P2,1		;YES. USE IT THEN
LOCKLD:	JUMPL Q1,[MOVE T1,Q2	;IF UNMAP. GET I.D.
		CALL ULDPAG	;UNLOAD IT IF NECESSARY
		 JFCL		;WILL GO
		JRST LOCKL1]	;AND PROCEED
	MOVE T2,Q1		;GET PHYSICAL PAGE NUMBER
	MOVE T1,Q2		;GET I.D.
	HLL T2,Q3		;COPY FLAGS
	SKIPN P2		;HAVE A BLOCK?
	TXOA T3,1B0		;NO. NO SPECIAL STATE THEN
	LOAD T3,LKOST,(P2)	;YES. GET OLD STATE 
	CALL LODPPS		;LOAD IT
	 JRST [	PUSH P,T1	;FAILED. SAVE ERROR CODE
		SETOM T1	;DO UNLOAD
		UMOVE T2,2
		UMOVE T3,3
		PLOCK		;DO IT
		POP P,T1	;GET BACK ERROR CODE
		JRST LCKERR]	;AND GO CLEAN UP IF NECESSARY
	JUMPN P2,[ADDI Q1,1	;NEXT PHYSICAL PAGE
		SETZM 0(P2)	;DID THAT ENTRY
		ADDI P2,1	;NEXT ENTRY
		JRST .+1]	;PROCEED
LOCKL1:	ADDI Q2,1		;NEXT PROCESS PAGE
	SOJG P1,LOCKLD		;DO ALL PAGES
	MOVEI T1,JSBFRE
	SKIPE T2,P4		;HAVE A BLOCK?
	CALL RELFRE		;YES. FREE IT
	RETSKP
;ERROR IN LOCKING PAGES.
;	T1/ ERROR CODE

LCKERR:	SKIPN P3,P4		;HAVE A BLOCK?
	RETBAD (,<OKINT>)		;NO. ALL DONE THEN
	PUSH P,T1		;SAVE ERROR CODE
	ADDI P3,1		;START HERE
	HRRZ P2,Q3		;COUNT
LCKER1:	SKIPN 0(P3)		;HAVE ANYTHING HERE?
	JRST LCKER2		;NO
	LOAD T2,LKOST,(P3)	;YES. GET PREVIOUS STATE
	LOAD T1,LKPGN,(P3)	;GET PAGE NUMBER
	CALL SETPST		;PUT IT BACK
	 JFCL
LCKER2:	ADDI P3,1		;NEXT ENTRY
	SOJG P2,LCKER1		;DO THEM ALL

;ALL PAGES RESTORED. FINISH UP

	MOVEI T1,JSBFRE		;POOL NAME
	MOVE T2,P4		;ADDRESS
	CALL RELFRE		;RELEASE BLOCK
	POP P,T1		;GET BACK ERROR CODE
	RETBAD (,<OKINT>)		;AND DONE
; Login
;ACCEPTS:
;	T1/USER NUMBER
;	T2/POINTER TO PASSWORD STRING
;	T3/5B2+ACCOUNT NUMBER
;		OR
;	   POINTER TO ACCOUNT STRING

;	LOGIN

;RETURNS +1: FAILURE
;		T1/ERROR CODE
;	 +2: SUCCESS
;		T1/DATE AND TIME OF LAST LOGIN
;		T2/UPDATED STRING POINTER
;		T3/UPDATED STRING POINTER (IF APPLICABLE)

;PSI OFF THROUGHOUT BECAUSE OF CALL SETDIR

.LOGIN::MCENT
	STKVAR <LOGUSR>
	MOVE A,JOBNO
	MOVEI B,777777
	TDNE B,JOBDIR(A)	; Is this job currently logged in?
	RETERR(LGINX5)
	SKIPN FREJOB		;ANY JOB SLOTS LEFT (1 NEEDED FOR ATTACH'ES)
	RETERR (LGINX6)		;NO, DO NOT ALLOW LOGINS.
	UMOVE A,1		;GET THE USER NUMBER
	MOVEM A,LOGUSR		;SAVE IT
	CALL CNVDIR		;CONVERT THIS NUMBER TO A DIRECTORY #
	MOVEM A,P1		;SAVE (STRUCTURE UNIQUE CODE,,DIRECTORY NUMBER)
	CALL SETDIR		; MAP IN THIS DIRECTORY AND GO NOINT
	 RETERR(LGINX3)
	MOVE Q1,DIRORA		; GET BASE ADR OF MAPPED DIR
	CALL CPYUGP		;GET A COPY OF USER GROUPS INTO JSB
	 MOVEI A,0		;NO GROUPS FOR THIS USER
	MOVEM A,Q2		;SAVE POINTER
	LOCK JSSTLK		;LOCK JSB STRUCTURE DATA
	HLRZ A,P1		;GET UNIQUE CODE FOR STRUCTURE
	CALL GTSTOF		;GET OFFSET IN JSB FOR THIS STRUCTURE
	 JRST [	UNLOCK JSSTLK	;NO SPACE. UNLOCK JSB STRUCTURE DATA
		CALL USTDIR	;UNLOCK DIRECTORY AND STRUCTURE LOCKED
		RETERR]		; BY SETDIR AND GO OKINT
	STOR Q2,JSGRP,(B)	;SAVE POINTER TO GROUPS
	HRRZ A,P1		;GET DIRECTORY NUMBER ON PS
	STOR A,JSADN,(B)	;INDICATE USER HAS ACCESSED THIS DIRECTORY
	UNLOCK JSSTLK		;UNLOCK THE JSB STRUCTURE DATA
	LOAD B,DRMOD,(Q1)	; GET MODE BITS
	MOVEM B,MODES
	TXNE B,MD%FO		;FILES ONLY DIRECTORY?
	RETERR(LGINX2,<ULKDIR>)	;CAN'T LOGIN TO FILES-ONLY DIRECTORY

;PASSWORD IS NOT REQUIRED IF CONTROLLING TTY IS A PTY AND EITHER:
; 1. THIS JOB BEING LOGGED IN AS SAME USER, OR
; 2. USER IS A SC%WHL OR SC%OPR
;CHECK FOR THESE CONDITIONS

	MOVE A,CTRLTT		;CTRL TTY OF THIS JOB
	CALL PTGETJ		;GET JOB NO. OF JOB OWNING PTY OR -1
	MOVE B,A
	JUMPL B,LOGI2		;JUMP IF NOT A PTY
	HRRZ D,JOBDIR(B)	;GET "WHO" OF CONTROLLING JOB
	XCTU [HRRZ C,1]	;GET "WHO" TRYING TO LOGIN HERE
	CAMN C,D		;SAME?
	JRST LOGI1		;YES, NO PASSWORD CHECK
	MOVE A,B		;CONTROLLING JOB NUMBER FOR CALL
	CALL GJCAPS		;GET CAPABILITIES OF CONTROLLING JOB
	MOVE B,A
	TXNE B,SC%WHL+SC%OPR	;CONTROLLING JOB HAS CAPABILITIES?
	JRST LOGI1		;YES, NO PASSWORD CHECK
;ALSO BYPASS PASSWORD CHECK IF IN THE MIDST OF CRJOB AND THE
;CREATOR OF THIS JOB ASKED FOR PASSWORD TO BE BYPASSED AND THE
;CREATOR WAS AN ENABLED WHEEL/OPERATOR.
LOGI2:	SKIPE T2,CRJFLG	;IS THIS A CRJOB INTERNAL LOGIN?
	TRNN T2,1		;YES. REQUESTED TO BYPASS PSWD CHK?
	SKIPA			;NO. SO CHECK IT.
	JRST LOGI1		;YES. BYPASS CHECKING PASSWORD.
	CALL CHKPSW
	 JRST LOGI3		;INCORRECT PASSWORD
	; ..
	; ..
LOGI1:	HLLOS CAPENB
	SETZM D			;ASSUME WE HAVE AN ACCOUNT STRING
	XCTU [SKIPN A,3]	;GET ACCOUNT STRING
	MOVEI D,1		;NONE THERE
	MOVE B,LOGUSR		;GET USER NUMBER
	XCT [	CALL SETACT
		CALL SETACL](D) ;EXECUTE PROPER ROUTINE
	 RETERR (,<HLLZS CAPENB ;TURN OFF PRIVILEGES
		 ULKDIR>)	;AND UNLOCK DIR
	CALL LGTAD		;DO LOCAL GTAD
	LOAD T2,DRDAT,(Q1)	;PICK UP LAST LOGIN D&T
	MOVEM T2,LSTLGN		;SAVE IT FOR GETJI
	JUMPL A,LOGI4		;DONT SET LOGIN TIME IF DAYTIME NOT SET
;DO NOT UPDATE LAST-LOGIN DATE IF REQUESTOR OF A PRIVILEGED CRJOB
;SAID NOT TO. THIS IS FOR SERVER LOGINS, SUCH AS FILE TRANSFER.
	SKIPE T3,CRJFLG	;IS IT A CRJOB?
	TRNN T3,2		;YES. NO-UPDATE BIT ON?
	SKIPA			;NO, SO UPDATE AS NORMAL
	JRST LOGI4		;YES. BYPASS THE UPDATE.
	STOR A,DRDAT,(Q1)	;UPDATE TIME
LOGI4:	XCTU [EXCH B,1]		;GET DIRECTORY TO LOG INTO
	MOVE A,JOBNO		;GET THIS JOB'S NUMBER
	HRRZM B,JOBDIR(A)	;SAVE AS LOGGED IN DIRECTORY
	MOVE A,STRTAB		;GET SDB ADDRESS OF STRUCTURE 0 (PUBLIC)
	LOAD A,STRUC,(A)	;GET ITS UNIQUE STRUCTURE CODE
	STOR A,JSUC		;SAVE AS CONNECTED STRUCTURE CODE
	STOR B,JSDIR		;MAKE THIS THE CONNECTED DIRECTORY
	CALL CPYCDN		;COPY THE CONNECTED DIR NAME TO JSB
	MOVE B,DIRORA		;POINTER TO DIRECTORY
	OPSTR <ADD B,>,DRNAM,(B) ;GET PNTR TO NAME STRING
				;COPY NAME STRING TO
	MOVEI C,USRNAM+1	; JSB STORAGE
	LOAD A,NMLEN,(B)	;GET NUMBER OF WORDS IN STRING
	AOS B			;UPDATE POINTER TO STRING
	HRRZM A,USRNAM		;SAVE LENGTH OF STRING
	SOS A			;COPY ALL BUT THE HEADER WORD
	CALL XBLTA		;COPY STRING
	REPEAT 0,<
	CALL TTWHOK		;IS IT OK TO BE A WHEEL ON THIS TTY?
	 JRST [	MOVEI T2,0	;NO. SO CLEAR RH CAPS.
		JRST LOGI1A]	; ..
	>
	LOAD T2,DRPRV,(Q1)	;GET PRIVILEGE BITS
LOGI1A:	HRRM T2,CAPMSK		;SETUP RH CAPS - LH SETUP AT JBFINI
	ULKDIR
	CALL LOGIMS		; SEND A LOGIN MESSAGE TO QUASAR
	 JFCL			; NO QUASAR
	CALL LOGONM		; Type logon message
	MOVE A,TODCLK		;UPTIME
	MOVEM A,CONSTO
	CALL LGTAD
	MOVEM A,CTIMON		;SAVE TIME ON
BP$020:				;(MOVE A,JOBNO): BREAKPOINT FOR CREATE MAIN FORK
				;ASSUMES FORKX HAS FORK INDEX, GETS JOB INDEX FORM FKJOB(FORKINDEX)
	MOVE A,JOBNO
	SETZM JOBRT(A)
	SETZM CAPENB
	SMRETN

;HERE IF INCORRECT PASSWORD

LOGI3:	ULKDIR
	MOVE B,A		;SAVE FLAG FROM CHKPSX
	MOVEI A,^D3000		;WAIT 3 SEC TO FOIL PASSWORD THIEVES
	SKIPN B			;DISMS ONLY IF NEEDED
	DISMS
	RETERR(LGINX4)
; Number input
; Call:	1	; Source designator
;	NIN
; Return
;	+1	; Error
;	+2	OK
;	2	NUMBER

.NIN::	MCENT
	CAILE 3,1
	CAILE 3,^D10
	JRST [	MOVEI A,IFIXX1	; Illegal radix
		UMOVEM A,3
		JRST EMRET0]	;STORE ERROR CODE AND MRETN
	MOVEI C,0
	SETZ P1,		;OVERFLOW FLAG
PLIN0:	CALL BIN1
	 JRST NINEOF		;END OF FILE
	JUMPE B,NINXX2		;IF B=0, END OF INPUT
	CAIN B,40
	JRST PLIN0		; Skip leading spaces
	CAIN B,"-"
	JRST MININ
	CAIN B,"+"
	JRST [	CALL BIN1
		 JRST NINEOF	;END OF FILE REACHED
		JRST .+1]
	CALL DIGIN1
	JRST NINXX2		;NO DIGITS SEEN
PLIN:	CALL NIN9
PLIN1:	UMOVEM C,2
	SKIPE P1		;FOUND AN OVERFLOW?
	JRST [	MOVEI A,IFIXX3	;YES
		JRST NINERR]
	SMRETN			;DONE

MININ:	CALL NIN91
	MOVNS C
	JRST PLIN1

;NO DIGITS SEEN

NINXX2:	MOVEI A,IFIXX2
	JRST NINERR

NINEOF:	MOVEI A,IOX4		;EOF SEEN
NINERR:	UMOVEM A,3		;RETURN ERROR CODE TO USER
	EMRETN			;GO STORE ERROR IN LSTERR AND TAKE ERROR RETURN
NIN9:	XCTU [MUL C,3]
	SKIPE C			;GOT SOME LOST BITS?
	SETOM P1		;YES. REMEMBER THE OVERFLOW
	LSH C,^D35		;GET READY TO ADJUST FOR LOSSAGE
	ADD D,C			;COMPLETE MULTIPLY
	EXCH C,D		;PRODUCT TO PROPER PLACES
	ADD D,D			;ADJUST SIGN
	ADD C,B			; Add in digit
NIN91:	CALL DIGIN
	RET
	JRST NIN9

DIGIN:	CALL BIN1
	 RET			;EOF REACHED
DIGIN1:	SUBI 2,60
	JUMPL 2,CPOPJ
	CAILE 2,^D9
	 JRST [	CAIL 2,"A"-60
		CAILE 2,"Z"-60
		 RET
		SUBI 2,"A"-"9"-1
		JRST .+1]
	XCTU [CAMGE 2,3]
	RETSKP
	RET
; Fixed point number output
; Call:	1		; Destination designator
;	2		; Number to be output
;	RH(3)		; Radix
;	3(0)		; 1 to treat number as 36 bit magnitude
;	3(1)		; 1 to always print some kind of sign
;	3(2)		; Right justify the number
;	3(3)		; Print leading zeros if any
;	3(4)		; Print something on errors
;	3(5)		; Print * on errors rather than whole number
;	3(11-17)	; Field width, 0 means large enough to hold all
;	NOUT
; Return
;	+1		; Error, bad radix, or number too big for field
;	+2		; Successful

.NOUT::	MCENT
	CALL NOUTX
	JRST [	MOVE A,LSTERR
		UMOVEM A,3
		JRST MRETN]
	SMRETN
NOUTX::	HRRZ D,C		; Get radix
	CAIL D,2
	CAILE D,^D10+^D26	; Must be 2 - 36
	JRST [	MOVEI A,NOUTX1
		MOVEM A,LSTERR
		RET]
	HLL D,C			; Save flags in d too
	LDB F,[POINT 8,D,17]	; Extract column width
	MOVEI Q3,1		; Initilize digit counter
	TLNN D,(1B0)		; Magnitude printout?
	CAIL B,0		; Or positive number?
	TLZA D,(1B6)		; Yes, remember not minus sign
	TLO D,(1B6+1B1)		; No, remember minus sign
	TLNE D,(1B6)		; - sign to be printed?
	MOVMS B			; Yes complement number
	TLNE D,(1B1)		; A sign of some sort to be printed?
NOUT1:	AOS Q3			; Yes, count as digit
	LSHC B,-^D35		; Make into double
	LSH C,-1		; Length dividend
	DIVI B,(D)		; Produce a digit
	PUSH P,C		; Save on stack
	JUMPN B,NOUT1		; Repeat until all digits generated
	CAIN F,0		; Zero field width specified?
	MOVE F,Q3		; Yes, make it same as number of digits
	TLNE D,(1B2)		; Right justify number?
NOUT2:	CAML Q3,F		; And filler needed?
	JRST NOUT3		; No
	TLNE D,(1B3)		; Yes. leading 0's?
	CALL SGNOUT		; Yes, output sign now
	MOVEI B," "		; Get a space
	TLNE D,(1B3)		; Unless 0's wanted
	MOVEI B,"0"		; Then get a 0
	CALL BOUTA		; Call bout so strings will work
	SOJA F,NOUT2		; Decrease remaining width and loop
NOUT3:	CAML F,Q3		; Sufficient room?
	JRST NOUT4		; Yes
	MOVEI B,NOUTX2		; Error
	MOVEM B,LSTERR
	TLNN D,(1B4)		; Print something anyway?
	JRST NOUT7		; No, go away
	TLNN D,(1B5)		; Asterisks?
	JRST NOUT4		; No, print the whole number
	MOVEI B,"*"		; Yes,
NOUT6:	SOJL F,NOUT7		; Column filled
	CALL BOUTA
	JRST NOUT6

NOUT7:	TLNE D,(1B1)		; If one position reserved for -,
	SOS Q3			; One less thing on stack
NOUT71:	SOJL Q3,CPOPJ
	POP P,B
	JRST NOUT71

NOUT4:	CALL SGNOUT		; Output sign before number
NOUT5:	SOJL Q3,NOUT8		; Any digits left?
	POP P,B			; Yes, get one
	ADDI B,"0"
	CAILE B,"9"
	ADDI B,"A"-"9"-1
	CALL BOUTA		; Print it
	SOJA F,NOUT5		; Decrease field width

NOUT8:	SKIPL F
	AOS (P)			; Skip if no error
	MOVEI B," "
	JRST NOUT6		; Insert trailing blanks if necessary

SGNOUT:	TLZN D,(1B1)		; Sign still needed?
	RET			; No, return immediately
	MOVEI B,"-"
	TLNN D,(1B6)
	MOVEI B,"+"
	CALL BOUTA
	SOS Q3			; Decrement digit count
	SOS F			; Decrement remaining field width
	RET
; Pmap jsys
; Call:	1	; Page ident (frk.pn or jfn.pn)
;	2	; Page ident
;	3	; Bits 2,3,4 to set page table access
;		;1B0 + COUNT TO DO MULTIPLE PAGES
;	PMAP

.PMAP::	MCENT
	TRVAR <SID,DID,CNT,JF1,PMTS,PMTA,PMTD,PMTL,PMTC>

;SID - CURRENT SOURCE IDENT	;DID - CURRENT DEST IDENT
;CNT - CURRENT REMAINING COUNT	;JF1 - JFN WHICH HAS STRUCTURE LOCK
;PMTS - INTERLOOP SOURCE ID	;PMTA - INTERLOOP ACCESS
;PMTD - INTERLOOP DEST ID	;PMTL - LOCAL DEST ID
;PMTC - COUNT FOR PMAPCL

	DMOVEM A,SID		;SAVE ARGS
	MOVEI Q2,1		;ASSUME COUNT IS 1
	TXNE C,1B0		;UNLESS B0 SET
	HRRZ Q2,C		;IN WHICH CASE COUNT IS IN 3
	JUMPE Q2,MRETN		;REJECT 0 COUNT
	CAIN Q2,1		;ONE PAGE PMAP?
	JRST [	CALL PMAP0	;YES, GET RIGHT TO IT
		JRST MRETN]
	MOVEM Q2,CNT		;SAVE TOTAL COUNT

;SEE IF SOURCE OR DESTINATION WILL GO OFF END OF PAGE TABLE
;WHILE DOING COUNT.  IF SO, DO IN PARTS WHICH INVOLVE ONLY
;ONE PAGE TABLE

PMAPC3:	MOVE A,SID		;GET SOURCE IDENT
	CAMN A,[-1]		;DELETE?
	JRST PMAPC4		;YES
	ANDI A,777		;GET PAGE NUMBER WITHIN PAGE TABLE
	MOVN A,A		;COMPUTE 1000-PAGENO TO SEE
	ADDI A,1000		; HOW MANY PAGES CAN BE DONE IN THIS PT
	CAMGE A,Q2		;MORE THAN REQUIRED BY COUNT?
	MOVE Q2,A		;NO, REDUCE COUNT
PMAPC4:	MOVE A,DID		;GET DESTINATION
	ANDI A,777		;GET PAGE NUMBER WITHIN PAGE TABLE
	MOVN A,A		;COMPUTE 1000-PAGENO TO SEE
	ADDI A,1000		; HOW MANY PAGES CAN BE DONE IN THIS PT
	CAMGE A,Q2		;MORE THAN REQUIRED BY COUNT?
	MOVE Q2,A		;NO, REDUCE COUNT
	CAMN Q2,CNT		;WAS COUNT REDUCED?
	JRST [	CALL PMAP0	;DO ALL OF CNT
		JRST MRETN]
	CALL PMAP0		;DO THIS GROUP
	MOVE A,SID		;GET SOURCE
	CAME A,[-1]		;IF DELETE DON'T UPDATE IT
	ADDM Q2,SID		;UPDATE IDENTIFIERS FOR PAGES JUST DONE
	ADDM Q2,DID
	MOVN Q2,Q2		;UPDATE TOTAL COUNT FOR PAGES JUST DONE
	ADDB Q2,CNT
	JUMPLE Q2,MRETN		;ANY MORE TO DO?
	MOVEI A,-1		;YES. CHECK FOR OVERLFOW OF PAGE NUMBER
	TDNE A,SID		;DID THIS ONE OVERFLOW?
	TDNN A,DID		;NO. HOW ABOUT THIS ONE?
	ITERR (ARGX06)		;YES TO ONE OF THEM
	JRST PMAPC3		;NO. GO ON THEN
;PMAP...

;THE FOLLOWING DOES ALL THE WORK, ASSUMING THAT THE COUNT
;DOES NOT CAUSE EITHER IDENTIFIER TO GO OFF THE END OF A PAGE TABLE

PMAP0:	SETZM JF1		;NONE HERE
	MOVE A,DID		;GET DESTINATION IDENT
	SKIPL SID		;IS SOURCE IDENT A FILE?
	JUMPGE A,[MOVEI A,PMAPX2 ;NO, IF DEST NOT A FILE THEN ERROR
		JRST PMAPER]
	UMOVE B,3		;GET USER REQUESTED ACCESS
	CALL CPMAP		; Convert to ptn.pn and get access
	 MOVEM D,JF1		;RETURNS LOCKED JFN
	JUMPE A,PMPER1		;IF ZERO, COULDN'T GET IT
	TLNN C,(PM%WT)
	JRST PMPER1		; MUST BE ABLE TO WRITE DESTINATION
	MOVEM A,PMTD		; Save destination ptn.pn
	MOVE A,SID		; Get source designator
	CAMN A,[-1]		; Delete wanted?
	JRST [	SETZB A,C	;YES, 0 IDENT AND ACCESS
		JRST PMAP1]	; Then skip the following
	UMOVE B,3		;GET USER REQUESTED ACCESS
	CALL CPMAP		; Convert source and get it's access
	 JRST [	MOVEM D,JF1	;SAVE LOCKED JFN
		TXNN B,READF	;HAVE READ ACCESS TO THE FILE?
		JRST PMPER1	;NO. ERROR
		JRST .+1]	;YES. ALLOW THE MAP THEN
	JUMPE A,PMPER1		;COULDN'T GET IT
PMAP1:	MOVEM C,PMTA		;SAVE ACCESS
	MOVEM A,PMTS		;AND PTN.PN
	SKIPGE DID		; Is "to" a file?
	 JRST PMAP2		; No, ok to do
	; ..
	; ..
;DESTINATION IS FILE, SO ACCESS OF EACH FILE PAGE TO BE AFFECTED
;MUST BE CHECKED.  THE FILE PAGE MUST BE PRIVATE.  THIS
;LOOP USES MSCANP WHICH SCANS FOR A NON-0 PAGE AND RETURNS ITS
;ACCESS.  THIS MAKES FOR MINIMUM OVERHEAD WHEN MAPPING INTO
;PAGES WHICH ARE ALREADY EMPTY.

	MOVE A,PMTD		;GET DESTINATION IDENT
	MOVE Q1,Q2		;GET COUNT FOR LOOP
PMAPC1:	MOVEM A,PMTL		;SAVE IDENT
	MOVE B,Q1		;GET REMAINING COUNT FOR CALL
	CALL MSCANP		;FIND NON-EMPTY PAGE AND RETURN ACCESS
	JUMPE B,PMAPC6		;NONE
	EXCH B,Q1		;SAVE UPDATED COUNT, GET ORIG COUNT
	SUB B,Q1		;COMPUTE NUMBER OF PAGES SKIPPED
	ADDM B,PMTL		;UPDATE IDENT FOR PAGES SKIPPED
	TLNN A,(PA%PRV)		; Better be private
	 JUMPN A,[MOVEI A,PMAPX2; Or empty
		JRST PMAPER]	; Else error
	MOVE A,PMTL		;RECOVER IDENT
	ADDI A,1		;GO TO NEXT PAGE
	SOJG Q1,PMAPC1		;DO ALL PAGES

;EACH SOURCE PAGE MUST ALSO BE CHECKED.  SOURCE PAGE MUST BE
;PRIVATE (I.E. OWNED BY FORK) BECAUSE OWNERSHIP WILL BE TRANSFERRED
;TO FILE.

PMAPC6:	MOVE A,PMTS		;GET SOURCE IDENT
	JUMPE A,PMAP55		;IF DELETING, NO FURTHER CHECK NEEDED
	MOVE Q1,Q2		;GET COUNT FOR LOOP
PMAPC5:	MOVEM A,PMTL		;SAVE IDENT
	MOVE B,Q1		;GET REMAINING COUNT FOR CALL
	CALL MSCANP		;FIND NON-EMPTY PAGE AND RETURN ACCESS
	JUMPE B,PMAP55		;NONE
	EXCH B,Q1		;SAVE UPDATED COUNT, GET ORIG COUNT
	SUB B,Q1		;COMPUTE NUMBER OF PAGES SKIPPED
	ADDM B,PMTL		;UPDATE IDENT FOR PAGES SKIPPED
	TLNN A,(PA%PRV)		;PRIVATE?
	JUMPN A,[MOVEI A,PMAPX2	;NO, IF NOT EMPTY THEN ERROR
		JRST PMAPER]
	MOVE A,PMTL			;RECOVER IDENT
	ADDI A,1		;GO TO NEXT PAGE
	SOJG Q1,PMAPC5		;DO ALL PAGES
PMAP55:	NOINT			;MUST BE NOINT AT PMAP5
	JRST PMAP5
;DESTINATION IS FORK.  PRESENT CONTENTS OF EACH PAGE WILL BE
;REMOVED, SO IT IS NECESSARY TO UPDATE MAP COUNT FOR FILES WHOSE
;PAGES ARE UNMAPPED.  FOR EFFICIENCY IN THE CASE WHERE FORK MAP
;IS EMPTY, MSCANP IS USED TO SCAN FOR NON-EMPTY PAGES.

PMAP2:	SKIPGE A,SID		;IS FROM A FILE?
	JRST PMAP4		; No.
	HLRZS A			; Yes, get jfn
	IMULI A,MLJFN		; CONVERT TO INTERNAL INDEX
	MOVSI B,0(Q2)		;UPDATE MAP COUNT BY NUMBER OF PAGES
	ASH B,1			; IN REQUEST
	ADDM B,FILLFW(A)	; Increment count of reasons for opening
PMAP4:	NOINT			;MUST BE NOINT WHEN DIDDLING MAP COUNTS
	MOVE Q1,Q2		;GET COUNT FOR PAGE SCAN LOOP
	SETO Q3,		;INIT OFN/JFN ASSOCIATION TO NIL
	SETZM PMTC		;INIT PMAPCL COUNT
	MOVE A,PMTD		;GET DESTINATION IDENT
PMAPC2:	MOVEM A,PMTL		;SAVE IDENT
	MOVE B,Q1		;GET REMAINING COUNT FOR CALL
	CALL MSCANP		;FIND NON-0 PAGE AND GET ACCESS
	JUMPE B,PMAP5		;NONE
	EXCH B,Q1		;SAVE UPDATED COUNT
	SUB B,Q1		;COMPUTE NUMBER OF PAGES SKIPPED
	ADDM B,PMTL		;UPDATE IDENT FOR PAGES SKIPPED
	JUMPE A,PMAP3		; Jump if empty
	TLNE A,(PA%PRV)
	JRST PMAP3		; Or if private
	MOVE A,PMTL		; Is indirect or share
	CALL MRPT		; Get it's id
	 JRST PMAP3		; Not file
	HLRZ B,A		;GET OFN
	CAIN B,0(Q3)		;QUICK CHECK - SAME AS LAST ONE?
	JRST [	HLLZ A,Q3	;YES, GET SAME JFN AS LAST ONE
		JRST PMAP6]
	MOVE Q3,B		;NOT SAME OFN, REMEMBER THIS ONE
	CALL OFNJFX		; Convert to jfn
	 JRST [	SETO Q3,	;NO JFN, FORGET OFN TOO
		JRST PMAP3]
	HLL Q3,A		;REMEMBER JFN/OFN ASSOCIATION
PMAP6:	HLRZ A,A		;GET JFN OF PAGE
	IMULI A,MLJFN		;CONVERT TO INTERNAL INDEX
	HLRZ C,FILLFW(A)	;GET JFN SHARE COUNT
	SUBI C,2		;REDUCE FOR PAGE BEING REMOVED
	JUMPE C,[MOVE B,PMTD	; COUNT NOW 0. GET DEST IDENT
		CALL PMAPCL	;MUST REMOVE PAGES BEFORE COUNT GOES
		MOVX B,FRKF	; TO 0.  UNRESTRICT JFN SO NEXT CLZFF
		ANDCAM B,FILSTS(A) ; GETS IT
		SETO Q3,	;FORGET THIS JFN
		JRST .+1]	;NOW OK TO REDUCE COUNT
	HRLM C,FILLFW(A)	;SET REDUCED COUNT
PMAP3:	MOVE A,PMTL		;RECOVER IDENT
	ADDI A,1		;GO TO NEXT PAGE
	SOJG Q1,PMAPC2		;DO ALL PAGES
	; ..
	; ..
;NOW CALL KERNAL ROUTINE TO CHANGE THE ACTUAL MAPS

PMAP5:	MOVE A,PMTS
	MOVE C,PMTA
	MOVE B,PMTD
	TXO C,PM%TPU+PM%CPY	;RETAIN USER-TRAP AND WRITE-COPY BITS
	XCTU [AND C,3]
	MOVE 4,Q2		;GET COUNT
	CALL MSETPT		;DO MULTIPLE PT SET
	OKINT			;NOW MAP AND JFN MAP COUNTS MUST AGREE
	MOVE A,PMTD		;GET IDENTIFIER FOR DESTINAITION
	SKIPL DID		;DESTINATION MUST BE A PROCESS
	JRST PMAP7		;IF NOT, CAN'T PRELOAD PAGES
	MOVE B,Q2		;GET REPEAT COUNT
	UMOVE C,C		;GET USER'S FLAGS
	TXNE C,PM%PLD		;WANT TO PRELOAD ALL OF THESE PAGES?
	CALL PREPG		;YES. REQUEST SWAP IN THEN
	 JFCL			;DON'T CARE
PMAP7:	CALL PMAPRL		;RELEASE FILE LOCKS
	RET
;ERROR RETURN FROM PMAP

PMPER1:	MOVEI A,PMAPX1		;CONVENIENT ERROR PLACE
PMAPER:	MOVEM A,LSTERR
	MOVEM B,ERRSAV
	CALL PMAPRL		;GO RELEASE ANY FILE LOCKS
	JRST ITRAP

;ROUTINE TO RELEASE ANY ACCUMULATED FILE LOCKS

PMAPRL:	SKIPE A,JF1		;HAVE ONE HERE?
	CALL LUNLK0		;YES. UNLOCK IT THEN
	RET			;DONE
;GET IDENT AND ACCESS

CPMAP:	JUMPL A,FRKMAP
	PUSH P,A		;SAVE THE JFN
	TXNN B,PM%WT		;DID USER WANT WRITE?
	SETZ B,			;NO. PREVENT PT CREATES
	CALL JFNOF4		;GET OFN AND STATUS
	 JRST [	SUB P,BHC+1
		CAIE A,LNGFX1	;COULDN'T CREATE PT?
		JRST PMAPER	;NO. GENERAL ERROR
		SETZ A,		;YES. RETURN CONDITION
		RETSKP]		;SAYING IT IS A PROCESS
	EXCH A,0(P)		;SAVE OFN, GET BACK JFN
	HLRZS A			;JFN ONLY
	IMULI A,MLJFN		;MAKE IT AN INTERNAL VALUE
	CALL STRDMO		;VERIFY AND LOCK UP STRUCTURE
	 JRST [	SUB P,BHC+1	;CLEAN UP STACK
		JRST PMAPER]	;AND GIVE PROPER ERROR
	MOVE D,A		;REMEMBER THIS JFN HAS STRUCTURE LOCK
	POP P,A			;GET BACK ID
	TXNN B,<RNDF>		;OPENED FOR APPEND MODE?
	JRST [	MOVE A,D	;GET BACK JFN
		CALL LUNLK0	;FREE STRUCTURE LOCK
		MOVEI A,PMAPX2	;THIS IS NOT ALLOWED
		JRST PMAPER]
	MOVSI C,(PM%RWX)		;GIVE ALL ACCESS
	TXNN B,WRTF		;UNLESS FILE NOT OPEN FOR WRITE
	TLZ C,(PM%WT)		;IN WHICH CASE DISALLOW WRITE
	RET

FRKMAP:	CALL FKHPTN
	 ITERR ()		;INVALID
	MOVSI C,(PM%RWX)
	RETSKP			;SAY IS A FORK HANDLE

;REMOVE PAGES FROM PAGE TABLE AS FAR AS IT HAS BEEN SCANNED.
;DONE BECAUSE CANNOT WAIT UNTIL END OF SCAN WHEN JFN COUNT GOES
;TO 0.
; B/ DEST IDENT
; Q2/ ORIGINAL PAGE COUNT
; Q1/ CURRENT PAGE COUNT (PAGES LEFT TO SCAN)
;	CALL PMAPCL
; RETURN +1, PRESERVED ALL AC'S.

PMAPCL:	SAVET
	MOVEI A,0		;SAY CLEAR MAP
	ADD B,PMTC		;UPDATE ID BY NUMBER ALREADY CLEARED
	MOVEI D,1(Q2)		;COMPUTE NUMBER OF PAGES SCANNED
	SUB D,Q1
	SUB D,PMTC		;LESS THOSE ALREADY DONE
	ADDM D,PMTC		;UPDATE RUNNING COUNT
	CALLRET MSETPT		;CLEAR THEM
;JSYS TO CONVERT PPN (TOPS10) TO STRING
;ACCEPTS IN T1/ OUTPUT DESIGNATOR
;	    T2/ PPN (MUST BE 4,,#)
;	    T3/ POINTER TO DEVICE/STR NAME
;	PPNST
;RETURNS +1 ALWAYS T3/ UPDATED POINTER

.PPNST::MCENT
	XCTU [HLRZ T1,2]	;GET LHS OF PPN
	CAIE T1,PPNLH		;VALID PPN?
	ITERR (PPNX1)		;NO
	UMOVE T1,3		;GET STRING PNTR
	CALL STDEV0		;CONVERT TO DEVICE DESIGNATOR
	 ITERR ()		;RETURN ERROR
	HLRZ T2,T1		;CHECK DEVICE TYPE
	CAIE T2,.DVDES+.DVDSK	;GRNTEE DISK!
	ITERR (PPNX2)		;VALID FOR DISK/STR ONLY
	HRRZS T1		;STR UNIQUE CODE ONLY
	CAIN T1,-1		;WAS IT DSK:
	LOAD T1,JSUC		;YES - GET CONNECTED STR
	HRLZS T1		;NOW MAKE INTO 36-BIT DIR #
	XCTU [HRR T1,2]		;GET RHS OF PPN
	CALL DIRST0		;CONVERT TO STRING
	 ITERR ()		;PROBLEM WITH DIR?
	JRST MRETN		;GIVE RETURN
;JSYS TO PERFORM VARIOUS CONTROL/STATUS OPERATIONS ON PHYSICAL MEMORY

;1/ FLAGS(FUTURE),,FUNCTION CODE
;2/ +ARGLIST LENGTH
;3/ ARGLIST ADDRESS
;	PMCTL
;RETURNS+1:
;	FUNCTION PERFORMED/INFORMATION RETURNED
;ITRAPS ON ASSORTED ERRORS


;AC USAGE WITHIN PMCTL:
;Q1/ FUNCTION CODE
;Q2/ ARGLIST LENGTH
;Q3/ ARGLIST
;THE VALUES IN Q1-3 ARE VALIDATED IN THE ENTRY SEQUENCE

.PMCTL::MCENT
	MOVE T1,CAPENB		;GET ENABLED SPECIAL CAPABILITIES
	TXNN T1,SC%WHL!SC%OPR!SC%MNT ;APPROPRIATE CAPABILITIES?
	ITERR (CAPX2)		;NO
	UMOVE Q1,1		;GET FUNCTION CODE
	JUMPL Q1,PMCILF		;CHECK IF VALID
	CAILE Q1,PMCMXF		; ...
PMCILF:	ITERR (ARGX02)		;INVALID FUNCTION
	UMOVE Q2,2		;GET ARGLIST LENGTH
	HLRZ T1,PMCDSP(Q1)	;GET MINIMUM REQUIRED
	CAMLE T1,Q2		;GREATER THAN REQUIRED?
	ITERR (ARGX04)		;NO - TOO SMALL
	UMOVE Q3,3		;GET ARGUMENT LIST ADDRESS
	HRRZ T1,PMCDSP(Q1)	;GET FUNCTION DISPATCH
	JRST (T1)		;AND DO IT

;FUNCTION TABLE - ENTRIES ARE XWD MIN ARGLIST,FUNCTION

PMCDSP:	XWD 1,PMCRCE		;READ CACHE ENABLE
	XWD 1,PMCSCE		;SET CACHE ENABLE
	XWD 2,PMCRPS		;READ SPECIAL PAGE STATUS
	XWD 2,PMCSPS		;SET SPECIAL PAGE STATUS
	XWD 12,PMCRME		;READ MEMORY ERROR INFORMATION
PMCMXF==.-PMCDSP-1	;MAXIMUM FUNCTION CODE

;HERE TO RETURN THE STATE OF THE CACHE ENABLES

PMCRCE:	SKIPE T1,CASHF		;ZERO IF OFF
	MOVX T1,MC%CEN		;NONZERO IF ON
	UMOVEM T1,.MCCST(Q3)	;STORE RESULT
	MRETNG
;HERE TO SET THE CACHE ENABLES. IF THE CURRENT STATE IS THE SAME AS
;THE REQUESTED STATE, NOTHING IS DONE (PREVENTING USELESS UNLOADS)

PMCSCE:	UMOVE T1,.MCCST(Q3)	;GET USERS REQUESTED STATE
	TXNN T1,MC%CEN		;WANT CACHE ON?
	JRST PMCSC1		;NO.
	SKIPN CASHF		;YES - IS IT ALREADY ON?
	CALL CASHON		;MUST TURN IT ON NOW
	MRETNG

PMCSC1:	SKIPE CASHF		;WANT CACHE OFF, IS IT?
	CALL CASHOF		;NO - DO IT NOW
	MRETNG

;HERE TO READ THE SPECIAL PAGE STATUS OF A PHYSICAL PAGE

PMCRPS:	UMOVE T1,.MCPPN(Q3)	;GET USER'S ARGS
	HLRE T2,T1		;GET REPEAT COUNT OF PAGES
	MOVMS T2		;GET COUNT GIVEN BY USER
	CAIGE Q2,1(T2)		;ENOUGH ROOM FOR ARGS?
	ITERR (ARGX04)		;NO. GIVE ERROR THEN
	MOVE Q2,T1		;YES. PROCEED
	MOVE P1,Q3		;COPY ARG
PMCRP1:	HRRZ T1,Q2		;GET PAGE NUMBER
	CALL GETPST		;CALL KERNAL ROUTINE
	  ITERR(ARGX06,<UMOVEM Q2,.MCPPN(Q3)>) ;INVALID PAGE NUMBER
	UMOVEM T2,.MCPST(P1)	;STORE RESULT
	ADDI P1,1		;NEXT OFFSET
	AOBJN Q2,PMCRP1		;DO ALL REQUESTED PAGES
	MRETNG

;HERE TO SET THE SPECIAL PAGE STATUS OF A PHYSICAL PAGE

PMCSPS:	UMOVE T1,.MCPPN(Q3)	;GET USERS PAGE NUMBER
	UMOVE T2,.MCPST(Q3)	;GET NEW SPECIAL PAGE STATE
	CALL SETPST		;CALL KERNAL ROUTINE
	  ITERR ()		;ERROR CODE IN T1
	MRETNG			;SUCCESS
;HERE TO READ INFORMATION ABOUT SYSTEM MEMORY ERRORS

PMCRME:	SETZM P1		;NO ENTRIES FOUND YET
PMCRM1:	MOVEI T1,.PMMER		;GET A MEMORY ERROR ENTRY
	CALL DEQERR		;GET IT
	 JRST [	JUMPN P1,PMCRM0	;IF FOUND SOME, NOW DONE
		ITERR (PMCLX4)]	;OTHERSWISE, ERROR
	LOAD T2,SBSCN,(T1)	;GET CONTROLLER
	HRLI T2,<.PMMER_^D9>+12	;TYPE AND COUNT
	UMOVEM T2,.PMMTP(Q3)	;STORE IN USER SPACE
	MOVE T2,SBSERA(T1)	;GET ERG
	UMOVEM T2,.PMMRG(Q3)	;STORE IT
	LOAD T2,SBSSY,(T1)	;SYNDROME
	UMOVEM T2,.PMMSY(Q3)
	LOAD T2,SBSBN,(T1)	;BLOCK NUMBER
	UMOVEM T2,.PMMBN(Q3)
	LOAD T2,SBSSB,(T1)	;SPARE BIT NUMBER
	UMOVEM T2,.PMMSB(Q3)
	MOVE T2,SBSEAD(T1)	;ERROR ADDRESS
	UMOVEM T2,.PMMEA(Q3)
	PUSH P,T1		;SAVE BLOCK NUMBER
	XMOVEI T2,SBSSER(T1)	;FIRST SERIAL NUMBER
	MOVEI T3,.PMMSN(Q3)	;USER ADDRESS
	MOVEI T4,.PMMNS		;REPEAT COUNT
PMCRM2:	LDB T1,[POINT ^D32,0(T2),35] ;GET SERIAL NUMBER
	UMOVEM T1,0(T3)		;STORE IN USER SPACE
	ADDI T3,1		;NEXT USER ADDRESS
	ADDI T2,1		;NEXT SERIAL NUMBER
	SOJG T4,PMCRM2		;DO ALL SERIAL NUMBER
	POP P,T1		;BLOCK ADDRESS
	CALL RELRES		;FREE IT
	SUBI Q2,12		;USED THIS MANY WORDS
	ADDI Q3,12		;AND NOW POINT HERE
	CAIL Q2,12		;ROOM FOR ANOTHER?
	AOJA P1,PMCRM1		;YES. GET IT
PMCRM0:	UMOVEM Q2,2		;UPDATED COUNT
	UMOVEM Q3,3		;UPDATED POINTER
	MRETNG			;DONE
;JSYS TO SET AND READ ARGUMENTS FOR A PROCESS
;ACCEPTS IN 1/	FUNCTION CODE ,, FORK HANDLE
;	    2/	ADR OF ARG BLOCK
;	    3/	LENGTH OF ARG BLOCK
;	PRARG
;RETURNS +1:	ALWAYS 
;	    3/	COUNT OF WORDS IN ARGUMENT BLOCK

.PRARG::MCENT
	CALL FLOCK		;LOCK THE FORK STRUCTURE
	UMOVE Q2,2		;GET ADR OF ARG BLOCK
	XCTU [HRRZ Q3,3]	;GET LENGTH OF BLOCK
	XCTU [HRRZ T1,1]	;GET FORK HANDLE
	CALL SETLFK		;MAP IN PSB OF THIS FORK
	MOVE Q1,T1		;SAVE INDEX FOR LATER
	XCTU [HLRZ T1,1]	;GET FUNCTION CODE
	CAIN T1,.PRARD		;READ?
	JRST PRARGR		;YES, GO RETURN BLOCK
	CAIE T1,.PRAST		;SET?
	ITERR (PRAX1,<CALL CLRLFK
			CALL FUNLK>) ;NO, GIVE ERROR RETURN
	MOVEI T1,JSBFRE		;YES, FIRST GIVE BACK OLD SPACE
	MOVE T2,PRARGP(Q1)	;SEE IF THERE IS ANY
	JUMPE T2,PRARG1		;NO IF ZERO
	SETZM PRARGP(Q1)	;ZERO THE OLD POINTER
	CALL RELFRE		;RELEASE OLD SPACE
PRARG1:	JUMPE Q3,PRARGC		;JUST CLEARING THE ARG BLOCK?
	MOVE T2,Q3		;NO, GET SOME SPACE FOR NEW BLOCK
	CAILE T2,PRAMAX		;IS THIS A LEGAL SIZE?
	ITERR (PRAX3,<CALL CLRLFK
			CALL FUNLK>) ;NO, PRARG BLOCK TOO LARGE
	AOS T2			;ADD ONE FOR HEADER
	CALL ASGJFR		;GET SPACE IN JSB
	 ITERR (PRAX2,<CALL CLRLFK
			CALL FUNLK>) ;NOT ENOUGH ROOM FOR THIS SIZE BLK
	MOVEM T1,PRARGP(Q1)	;STORE ADR OF BLOCK IN PSB
PRARSL:	UMOVE T3,0(Q2)		;GET FIRST WORD OF BLOCK
	AOS T1			;STEP POINTER TO FREE BLOCK
	AOS Q2			;AND POINTER TO USER BLOCK
	MOVEM T3,0(T1)		;STORE WORD IN BLOCK
	SOJG Q3,PRARSL		;LOOP UNTIL ALL WORDS STORED
PRARGC:	CALL CLRLFK		;UNMAP PSB
	CALL FUNLK
	JRST MRETN		;AND EXIT

;READ ARGUMENT BLOCK

PRARGR:	XCTU [SETZM 3]		;ASSUME NO DATA AVAILABLE
	SKIPN T1,PRARGP(Q1)	;GET POINTER TO BLOCK IF ANY
	JRST PRARRD		;NONE, GO RETURN 0
	HRRZ T2,0(T1)		;GET LENGTH OF BLOCK
	SOJLE T2,PRARRD		;SKIP HEADER WORD
	UMOVEM T2,3		;STORE COUNT OF WORDS AVAILABLE
PRARRL:	SOJL Q3,PRARRD		;ANY MORE TO DO?
	MOVE T3,1(T1)		;YES, GET NEXT WORD
	UMOVEM T3,0(Q2)		;STORE WORD IN USER BLOCK
	AOS T1			;STEP POINTER TO JSB BLOCK
	SOSLE T2		;ANY MORE WORDS IN BLOCK?
	AOJA Q2,PRARRL		;YES, GO STORE THEM
PRARRD:	CALL CLRLFK		;UNMAP PSB
	CALL FUNLK
	JRST MRETN		;AND RETURN
; Release device
; 1/ DEVICE DESIGNATOR, OR -1 TO RELEASE ALL DEVICES
;	RELD
; Returns
;	+1	; Error, bad designator or not assigned to this job
;	+2	; Ok.

.RELD::	MCENT
	STKVAR <RELDSV,RELDIX>
	MOVEM T1,RELDSV		;SAVE DEVICE DESIGNATOR
RELD1:	CALL LCKDVL		;LOCK DEVICE LOCK, GO NOINT
	CAMN 1,[-1]		;ALL ASSIGNED DEVICES?
	JRST RELDAL		;YES. GO DO THEM
	CALL CHKDEV		;DO WE HAVE ACCESS TO THIS DEVICE?
	 RETERR(,<UNLOCK DEVLCK>) ;NO.
	MOVEM T2,RELDIX		;SAVE INDEX TO DEVICE TABLES
	HLRZ T1,DEVUNT(T2)	;GET OWNING JOB
	CAIN T1,-1		;IS THERE ONE?
	JRST RELD2		;NO. DON'T BOTHER TO DEASSIGN IT
	CALL RELDEV		;GO RELEASE THIS DEVICE
	 JRST RELDWT		;FAILED
	HRRZ P3,P4		;DEVICE ONLY
	MOVE T2,RELDIX		;T2/ INDEX TO DEVICE TABLES
	CALL DSMNT0		;AND DISMOUNT DEVICE
	 JFCL
RELD2:	UNLOCK DEVLCK
	OKINT
	SMRETN

;RELEASING ALL DEVICES ASSIGNED TO THIS JOB

RELDAL:
	MOVSI Q1,-NDEV		;SET UP AOBJN POINTER 
RELDA3:	MOVE B,Q1		;SET UP FOR CALL TO RELDEV
	HLRZ A,DEVUNT(B)	;GET OWNING JOB
	CAME A,JOBNO		;THIS JOB?
	JRST RELDA4		;NO. ON TO NEXT DEVICE
	CALL RELDEV		;YES. RELEASE IT
	 JRST RELDWT		;FAILED. GO WAIT UNTIL IT CAN SUCCEED
	HRRZ P3,P4		;ADDRESS ONLY
	CALL DSMNT0		;AND DISMOUNT DEVICE
	 JFCL
RELDA4:	AOBJN Q1,RELDA3
	JRST RELD2		;GO UNLOCK AND EXIT

;FAILED TO RELEASE THE DEVICE. WAIT IF NECESSARY

RELDWT:	TXZN T1,1B0		;NEED TO WAIT?
	RETERR (,<UNLOCK DEVLCK
		  OKINT>)	;NO. FAIL
	UNLOCK DEVLCK		;YES. UNLOCK DEVICE TABLES
	OKINT			;LET USER CTRL/C OUT
	HRL T1,T2		;T1/ (LINE NUMBER,,ADDRESS)
	MDISMS			;WAIT UNTIL IT'S POSSIBLE
	MOVE T1,RELDSV		;RESTORE DEVICE DESIGNATOR
	JRST RELD1		;GO TRY AGAIN
;RELDEV - RELEASE DEVICE AND SEND MESSAGE TO ALLOCATOR IF NECESSARY

;ACCEPTS:
;	T2/ INDEX TO DEVICE TABLES

;	CALL RELDEV

;RETURNS +1: FAILED
;		T1/ ERROR CODE
;			OR
;		    1B0 + ADDRESS OF SCHEDULER ROUTINE FOR DISMS
;	 +2: SUCCEEDED

RELDEV::STKVAR <RELDIX>
	LDB D,[POINT 9,DEVCHR(B),17] ;GET DEVICE TYPE NUMBER
	MOVX C,DV%OPN
	TDNE C,DEVCHR(B)	;IS DEVICE OPENED?
	JRST [	MOVX C,DV%ASN	;YES. DON'T RELEASE IT YET
		ANDCAM C,DEVCHR(B) ;INDICATE NO LONGER ASSIGNED
		RETSKP]		;RETURN SUCCESS
	HRRZ C,DEVUNT(B)	;GET THE UNIT NUMBER
	CAIN D,.DVTTY		;IS THIS A TTY?
	JRST RELDD3		;YES.  GO DO SPECIAL PROCESSING
RELDD0:	MOVX C,DV%ASN		;INDICATE NO LONGER ASSIGNED
	ANDCAM C,DEVCHR(B)
	MOVE D,DEVCH1(B)	;GET CHARACTERISTICS WORD
	MOVEI C,-1		;SET UP TO RETURN DEVICE TO FREE POOL
	TLNE D,(D1%ALC)		;IS THIS DEVICE AN ALLOCATED DEVICE
	MOVEI C,-2		;YES, RETURN IT TO ALLOCATOR
	HRLM C,DEVUNT(B)	 ;MARK THAT DEVICE IS FREE
	TLNN D,(D1%ALC)		;ALLOCATED DEVICE?
	JRST RELDD1		;NO, DONT PUT IN MESSAGE
	JUMPE Q1,RELDD1		;IF NO MESSAGE, DONT STORE DEVTYP
	MOVE A,DEVCHR(B)	;SET UP DEVICE DESIGNATOR
	TLZ A,777000
	TLO A,.DVDES
	HRR A,DEVUNT(B)		;GET UNIT NUMBER
	CALL ALCMES
	 JFCL
RELDD1:	RETSKP


RELDD3:	CAMN C,CTRLTT		;YES. IS IT THIS JOB'S CONTROLLING TTY?
	RETSKP			;YES. DON'T DEASSIGN IT
	MOVEM B,RELDIX		;SAVE INDEX TO DEVICE TABLES
	MOVE B,C		;B/ TERMINAL NUMBER
	CALL TTYDEA		;DEALLOCATE ITS DYNAMIC DATA
	 RETBAD			;FAILED. RETURN FAILURE
RELDD4:	MOVE B,RELDIX		;RESTORE INDEX TO DEVICE TABLES
	JRST RELDD0		;FINISH PROCESSING
; Reset jsys
; Call:	RESET
; Closes all files, resets tty status etc

.RESET::MCENT
	MOVNI A,4
	KFORK			; Kill all inferior forks
	MOVE A,FORKX		; GET FORK NUMBER OF THIS FORK
	CALL PIDRFK		; GO DELETE TEMPORARY PIDS OF THIS FORK
	MOVE A,FORKX
	CALL ENQFKR		; DEQ ALL ENQ'D REQUESTS FOR THIS FORK
	SKIPE SNPPGS		; THIS FORK HAVE ANY BREAK POINTS IN?
	CALL SNPREL		; YES, GO RELEASE THEM
	SKIPGE CTRLTT
	 JRST RSTFK		; Skip tty reset if not ctrltt
	MOVEI A,101
	MOVE B,NORMTF		; Normal modes
	SFMOD
RSTFK:	MOVEI A,400000
	CIS
	DIR
	SETZB T2,T3		;ZERO BOTH INTERRUPT AND DEFERRED WORD MASK
	STIW
	MOVNI 2,1
	DIC
	MOVE 1,[CZ%ABT+400000]	;SAY DELETE NONX FILES
	CLZFF
	RWSET			;RELEASE WORKING SET
	SKIPL PATADR		;FORCED NON-COMPATIBILITY?
	SETZM PATADR		;NO, CLEAR COMPAT ENTRY VECTOR
	MOVNI A,1		;SET UP TO RELEASE ALL HANDLES
	RFRKH			;FREE FORK HANDLES
	 JFCL			;?
	SETZM JTTRW		;CLEAR JSYS TRAP WORD
	MOVEI T1,77		;UNASSIGNED CHANNEL
	STOR T1,JTMCN		;TO JSYS TRAP PSI CHANNEL
	SETOM JTLCK		;CLEAR JSYS TRAP LOCK
	JRST MRETN
; Read control character output control

.RFCOC::MCENT
	CALL CHKTTR
	 JRST RFCOC1
	CALL LCKTTY		;POINT TO DYNAMIC DATA, PREVENT DEALLOCATION
	 ITERR (TTYX01,<CALL ULKTTY>) ;NOT ACTIVE. FAIL
	CALL TTRCOC
	UMOVEM 1,2
	UMOVEM 3,3
	CALL ULKTTY		;ALLOW DEALLOCATION
	JRST MRETN

RFCOC1:	MOVE A,[BYTE (2)2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2]
	UMOVEM A,2
	UMOVEM A,3
	JRST MRETN

;RFMOD JSYS - Read TERMINAL mode

;ACCEPTS:
;	T1/ SOURCE DESIGNATOR

;	RFMOD

;RETURNS +1: ALWAYS,
;		T2/ JFN MODE WORD

;NOTE: IF T1 POINTS TO A NON-TERMINAL, CERTAIN DEFAULTS ARE RETURNED
;IN PARTICULAR, WHEN CHKTTR FAILS, AC 'STS' HAS, IN BITS 32-35
;THE MODE BITS FROM THE OPENF. SINCE STS=P1, THIS CODE RETURNS BITS 32-35 IN P1

.RFMOD::MCENT
	SETZ P1,		;INITIALIZE P1 TO 0
	CALL CHKTTR
	 JRST RFMOD1
	CALL LCKTTY		;POINT TO DYNAMIC DATA, PREVENT DEALLOCATION
	 ITERR (TTYX01,<CALL ULKTTY>) ;NOT ACTIVE. FAILED
	CALL TTRMOD
	UMOVEM 1,2
	CALL ULKTTY		;ALLOW DEALLOCATION
	JRST MRETN

RFMOD1:	MOVE A,P1
	ANDI A,17
	ADD A,[^D66B10+^D72B17+^D7B3]
	UMOVEM A,2
	JRST MRETN

; Read file position

.RFPOS::MCENT
	CALL CHKTTR
	 JRST [	XCTU [SETZM 2]
		JRST MRETN]
	CALL LCKTTY		;POINT TO DYNAMIC DATA, PREVENT DEALLOCATION
	 ITERR (TTYX01,<CALL ULKTTY>) ;NOT ACTIVE. FAILED
	CALL TTRPOS
	CALL ULKTTY		;ALLOW DEALLOCATION
	UMOVEM 1,2
	JRST MRETN
; Read map
; Call:	LH(1)	; Fork handle
;	RH(1)	; Page number
;	RMAP
; Retrn
;	+1
;	LH(1)	; Jfn
;	RH(1)	; Page number
;	2	; Access read, write,execute,nonexistent in bits 2-5

.RMAP::	MCENT
	CALL FRKMAP		; Convert frk.pn to ptn.pn
	 JFCL			;WILL SUCCEED
	CALL MRPT		; Call map routine
	 JRST RMAPFK
	PUSH P,B
	CALL OFNJFN
RMAP0:	 SETO A,		; Unidentifiable
RMAP1:	POP P,B
	UMOVEM A,1
	UMOVEM B,2
	JRST MRETN

RMAPFK:	PUSH P,B
	JUMPE A,RMAP0
	CALL PTNFKH
	JRST RMAP1
; Read accessiblity of page
; Call:	LH(A)	; Fork or file handle
;	RH(A)	; Page number
;	RPACS

.RPACS::MCENT
	TRNE 1,777000
	SKIPGE 1
	JRST RPACS1
	HLRZS A
	IMULI A,MLJFN		; CONVERT TO INTERNAL INDEX
	MOVE A,FILSTS(A)
	TXNN A,LONGF
	JRST [	XCTU [SETZM 2]	; File not long
		JRST MRETN]
	UMOVE 1,1
RPACS1:	TRVAR <JF1>		;REMEMBER STR LOCK HERE
	SETZM JF1		;NO STR LOCK YET
	SETZ B,			;NO PT CREATES PLEASE
	CALL CPMAP
	 MOVEM D,JF1		;MUST RELEASE THIS STR LOCK
	SKIPE T1		;FOUND A MATCH?
	CALL MRPACS
	UMOVEM 1,2
	SKIPE A,JF1		;SEE IF A STR LOCK TO RELEASE
	CALL LUNLK0		;YES. GO DO IT
	JRST MRETN
; Set last error
; Accepts 1: Flags,,fork designator
;	  2: Error code
;	  4-10: For ERRSAV if B0 of 1 is on
; Returns
;	+1 Always

.SETER::MCENT
	CALL FLOCK		; Lock things down
	MOVE P1,T1		; Flags,,fork
	MOVE P2,T2		; Error code
	HRRZS T1		; Just fork handle
	CALL STJFKR		; Get job fork index
	 ITERR FRKHX1,<CALL FUNLK> ; Bad handle
	CALL SKIIF		; Must be self or lower
	 ITERR FRKHX2,<CALL FUNLK>
	MOVE P3,T1		; Save fork's job index
	CALL SETLF1		; Map PSB
	MOVE Q1,T1		; Save offset to PSB of fork
	TLNE P1,(1B0)		; Not setting ERRSAV?
	 CAMN P3,FORKN		; Or me?
	  JRST SETE1		; Yes
	MOVES PSBPGA(Q1)	; Touch it, going NOSKED
       NOSKED
	HRRZ 7,SYSFK(P3)	; Get FORKX (7 is Q3 or FX)
	CALL CHKWT		; Must not be running
	 JRST SETE3		; Which he is
SETE1:	MOVEM P2,LSTERR(Q1)	; Save into PSB
	TLNN P1,(1B0)		; Doing ERRSAV?
	 JRST SETE2		; No
	MOVEI T1,10-4		; # of words to copy
	MOVEI T2,4		; From user acs
	MOVEI T3,ERRSAV(Q1)
	CALL BLTUM
	CAMN P3,FORKN		; Me?
	 JRST SETE2		; Yes
       OKSKED
SETE2:	CALL CLRLFK		; Unmap PSB
	CALL FUNLK
	MRETNG

SETE3: OKSKED
	CALL CLRLFK
	ITERR FRKHX4,<CALL FUNLK> ; Moving violation
; SET JOB PARAMETERS
;ACCEPTS IN 1/	JOB NUMBER
;	    2/	FUNCTION CODE
;	    3/	VALUE OR POINTER TO ARG BLOCK
;	SETJB
;RETURNS +1:	ALWAYS

.SETJB::MCENT
	SETZ T4,		;LOCAL FLAG AC
	UMOVE T1,1		;GET JOB NUMBER
	CAMN T1,[-1]		;SELF?
	MOVE T1,JOBNO		;YES, GET OWN JOB NUMBER
	SKIPL T1		;CHECK FOR LEGALITY
	CAIL T1,NJOBS
	ITERR (SJBX4)		;ILLGEAL JOB NUMBER
	SKIPGE JOBRT(T1)	;JOB LOGGED IN?
	ITERR (SJBX5)		;NO, JOB NOT LOGGED IN
	CAME T1,JOBNO		;OUR OWN JOB?
	JRST [	MOVE T2,CAPENB	;NO, CHECK FOR PROPER PRIVILEGES
		TXNN T2,SC%WHL!SC%OPR
		ITERR (SJBX6)	;NOT PRIVILEGED
		JRST STJB1]	;OK
	TXO T4,SJ%OWN		;SETTING PARAMETERS IN OUR OWN JOB
STJB1:	CALL SETJSB		;MAP IN JSB OF JOB
	MOVEM T1,P1		;SAVE JSB OFFSET
	XCTU [HRRZ T2,2]	;GET FUNCTION CODE
	UMOVE T3,3		;GET VALUE
	CAIL T2,MAXSJF		;LEGAL FUNCTION CODE?
	ITERR (SJBX1,<CALL CLRJSB>) ;ILLEGAL FUNCTION CODE
	TXNN T4,SJ%OWN		;OUR OWN JOB?
	CALL SJBCHK		;NO, SEE IF JOB CAN DO THIS FUNCTION
	XCT SJBTAB(T2)		;PERFORM THE FUNCTION
	CALL CLRJSB		;UNMAP JSB
	JRST MRETN		;SUCCESSFUL

SJBCHK:	SKIPN SJBTBF(T2)	;CAN THE JOB PERFORM THIS FUNCTION?
	ITERR (SJBX8,<CALL CLRJSB>) ;NO
	RET			;YES, GO DO IT

SJBDEN:	SKIPL T3		;NEGATIVE VALUE IS ILLEGAL
	CAILE T3,MTMXDN		;LEGAL DENSITY?
	ITERR (SJBX2,<CALL CLRJSB>) ;ILLEGAL DENSITY
	STOR T3,JSMTD,(T1)	;STORE DENSITY
	RET

SJBDM:	SKIPL T3		;DONT ALLOW NEGATIVE VALUES
	CAILE T3,MTMXDM		;LEGAL DATA MODE?
	ITERR (SJBX3,<CALL CLRJSB>) ;ILLEGAL DATA MODE
	STOR T3,JSMTM,(T1)	;YES, SAVE DATA MODE
	RET
; SET JOB SESSION REMARK

SJBSRM:	MOVE T1,T3		;USER'S POINTER TO REMARK
	CALL CPYFUS		;GET THE REMARK
	 ITERR (MONX02,<CALL CLRJSB>)
	UMOVEM T3,3		;RETURN USER'S UPDATED POINTER
	HRRZ T2,T1		;POINTER TO REMARK
	MOVE T4,T1		;SAVE IT IN T4 FOR NOW
	MOVEI T1,MAXLW+1	;REMARK LENGTH
	MOVEI T3,JSSRM(P1)	;PLACE TO PUT REMARK IN JSB
	CALL XBLTA		;PUT REMARK IN THE JSB
	MOVEI T1,JSBFRE
	MOVE T2,T4		;FREE UP JSB FREE SPACE FOR REMARK
	CALL RELFRE
	OKINT			;CPYFUS WENT NOINT
	RET
; Set control character output control

.SFCOC::MCENT
	CAIN 1,.NULIO		;IS THIS THE NULL DESIGNATOR
	JRST MRETN		;YES, ALLOW IT WITHOUT DOING ANYTHING
	CALL CHKTTY
	 EMRETN ()
	CALL LCKTTY		;POINT TO DYNAMIC DATA, PREVENT DEALLOCATION
	 ITERR (TTYX01,<CALL ULKTTY>) ;NOT ACTIVE. FAIL
	UMOVE 1,2
	UMOVE 3,3
	CALL TTSCOC
	CALL ULKTTY		;ALLOW DEALLOCATION
	JRST MRETN

; Set file modes

.SFMOD::MCENT
	CAIN 1,.NULIO		;IS THIS THE NULL DESIGNATOR
	JRST MRETN		;YES, ALLOW IT WITHOUT DOING ANYTHING
	CALL CHKTTY
	 EMRETN ()
	CALL LCKTTY		;POINT TO DYNAMIC DATA, PREVENT DEALLOCATION
	 ITERR (TTYX01,<CALL ULKTTY>) ;NOT ACTIVE. FAIL
	UMOVE 1,2
	CALL TTSMOD
	CALL ULKTTY		;ALLOW DEALLOCATION
	JRST MRETN

; Set file position

.SFPOS::MCENT
	CAIN 1,.NULIO		;IS THIS THE NULL DESIGNATOR
	JRST MRETN		;YES, ALLOW IT WITHOUT DOING ANYTHING
	CALL CHKTTY
	 EMRETN ()
	CALL LCKTTY		;POINT TO DYNAMIC DATA, PREVENT DEALLOCATION
	 ITERR (TTYX01,<CALL ULKTTY>) ;NOT ACTIVE. FAIL
	UMOVE 1,2
	CALL TTSPOS
	CALL ULKTTY		;ALLOW DEALLOCATION
	JRST MRETN
; Set fact switch
;ACCEPTS IN 1/	FUNCTION CODE
;	    2/	NEW SETTING
;	SMON
; Traps if process hasn't wheel/operator privilege

.SMON::	MCENT
	MOVE C,CAPENB
	TXNN C,SC%WHL!SC%OPR
	ITERR(SMONX1)
	UMOVE T1,1		;GET FLAG TO BE SET
	CAIN T1,.SFRMT		;SETTING REMOTE LOGIN STATUS?
	CALL [	SAVET		;YES
		XCTU [SKIPE 2]	;DOING ENABLE?
		CALLRET DTRMEN	;YES. TELL FE
		CALLRET DTRMDS]	;NO. TELL FE
	JUMPL T1,SMONER		;FUNCTION CODE MUST BE POSITIVE
	CAIL T1,^D36		;IS IT A BIT IN FACTSW?
	JRST SMON2		;NO, GO CHECK FUNCTION CODE
	IDIVI T1,^D36		;YES, GET BIT POSITION
	MOVX T1,1B0		;SET UP TO BUILD MASK
	MOVNS T2
	LSH T1,0(T2)		;GET MASK
	XCTU [SKIPE 2]		;SETTING THE BIT?
	JRST [	IORM T1,FACTSW	;YES, DO SO
		JRST MRETN]
	ANDCAM T1,FACTSW	;NO, CLEAR IT
	JRST MRETN

SMON2:	CAILE T1,^D35+NSMON2	;IS IT TOO BIG A CODE?
SMONER:	ITERR(SMONX2)		;YES, RETURN FAILURE
	SUBI T1,^D36		;SHIFT CODE DOWN BY 36 FOR TABLE
	LSH T1,1		;DOUBLE THE CODE
	UMOVE T2,2		;GET USER'S VALUE FOR THE FUNCTION
	SKIPE T2		;IF ZERO, DO EVEN DISPATCH
	TRO T1,1		;IF NONZERO, DO ODD DISPATCH
	XCT SMON2T(T1)		;DO THE FUNCTION
	JRST MRETN

;TABLE FOR SMON FUNCTION CODES .GE. 36

SMON2T:	SETZM NETON		;CODE 36, VALUE 0
	SETOM NETON		;CODE 36, VALUE NON-ZERO
	JFCL			;CODE 37, VALUE ZERO
	AOS IMPDRQ		;CODE 37, VALUE NON-ZERO
	JFCL			;CODE 38, VALUE ZERO
	CALL HSTINJ		;CODE 38, VALUE NON-ZERO
	MOVEM T2,TIMZON		;CODE 39, VALUE ZERO
	MOVEM T2,TIMZON		;CODE 39, VALUE NON-ZERO
	MOVEM T2,NLHOST		;CODE 40, VALUE ZERO
	MOVEM T2,NLHOST		;CODE 40, VALUE NON-ZERO
	SETZM AVALON		;CODE 41, VALUE ZERO
	SETOM AVALON		;CODE 41, VALUE NON-ZERO
	CALL UNGEN		;CODE 42, ZERO. TURN OFF STATUS REPROTING
	CALL GENGEN		;CODE 42, NON-ZERO. ENABLE REPORTING
NSMON2==<.-SMON2T>/2		;MAXIMUM CODE VALUE LESS 36

HSTINJ: CALL HSTINI		;JACKET ROUTINE FOR HSTINI
	JFCL			; WHICH HAS A SKIP RETURN
	RET

SETZON:	MOVEM T2,TIMZON		;STORE VALUE (OR 0)
	CALLRET DTTIME		;SEND NEW INFO TO FE
;THE SNOOP JSYS

;ACCEPTS IN AC1/	FUNCTION CODE
;	AC2-AC4/	FUNCTION DEPENDENT ARGUMENTS
;		SNOOP
;RETURNS +1:		ERROR - ERROR CODE IN T1
;	 +2:		SUCCESSFUL

;SNOOP DATA BASE

REPEAT 0,<

SNPBPP:
		+--------------------+--------------------+
		!SNPBN:             !SNPBL:             !
		!    BREAK POINT #   !   LINK TO NEXT BP  !
		+--------------------+--------------------+
		!SNPBTI:				  !
		!  INSTRUCTION TO TRANSFER TO BP ROUTINE  !
		+-----------------------------------------+
		!SNPBRI:				  !
		!     REPLACED INSTRUCTION FROM MONITOR   !
		+-----------------------------------------+
		!SNPB1:				  !
		!              JRST MONADR+1              !
		+-----------------------------------------+
		!SNPB2:				  !
		!	       JRST MONADR+2		  !
		+-----------------------------------------+



		+--------------------+--------------------+
SNPPGS:		!SNPPC:	     !SNPPA:		  !
		!  # OF PAGES LOCKED !  ADR OF FIRST PAGE !
		+--------------------+--------------------+

		+--------------------+--------------------+
SNPLST:		!SNPFLG:	     !SNPLNK:		  !
		!  BREAK POINT FLAGS !  LINK TO FIRST BP  !
		+--------------------+--------------------+

>
;SNOOP DATA STRUCTURE DEFINITIONS

DEFSTR	(SNPBN,0,17,18)	;BREAK POINT NUMBER
DEFSTR	(SNPBL,0,35,18)	;LINK TO NEXT BREAK POINT OF FORK
	SNPBP==1		;WHERE TO JUMP TO ON A BREAK POINT
	SNPBII==SNPBP+1		;INDEX OF REPLACED INSTRUCTION
DEFSTR	(SNPBTI,SNPBP,35,36)	;TRANSFER INSTRUCTION TO BP ROUTINE
DEFSTR	(SNPBRI,SNPBP+1,35,36)	;REPLACED INSTRUCTION
DEFSTR	(SNPB1,SNPBP+2,35,36)	;JRST MONADR+1
DEFSTR	(SNPB2,SNPBP+3,35,36)	;JRST MONADR+2

	SNPBSZ==5		;LENGTH OF A BREAK POINT BLOCK

DEFSTR	(SNPPC,SNPPGS,17,18)	;COUNT OF SNOOP PAGES LOCKED DOWN
DEFSTR	(SNPPA,SNPPGS,35,18)	;ADDRESS OF FIRST PAGE LOCKED DOWN

DEFSTR	(SNPFLG,SNPLST,17,18)	;BREAK POINT FLAGS FOR THIS FORK
DEFSTR	(SNPLNK,SNPLST,35,18)	;LINK TO FIRST BREAK POINT FOR FORK


;BREAK POINT FLAGS IN SNPFLG

	SN.BRK==1		;BREAK POINTS HAVE BEEN INSERTED
	SN.SML==2		;SWAPPABLE MONITOR IS LOCKED DOWN


;BREAK POINT PAGE ASSIGNMENTS

	SNPBPS==:1000		;LEN OF BREAK POINT PAGE (MUST BE 1000)
NRP (SNPBPP,SNPBPS)		;BREAK POINT PAGE

	SNPDPC==8		;NUMBER OF PAGES FOR USER CODE
	SNPDPS==:1000*SNPDPC	;LENGTH OF SNOOP VIRTUAL AREA
NRP (SNPDAT,SNPDPS)		;DATA PAGES FOR USER CODE

;CAUTION:  SNPBPP AND SNPDAT MUST BE CONTIGUOUS FOR SCHED TEST. (CHKSNP)

NR (SNPFTB,<<SNPDPC+^D35>/^D36>) ;FREE PAGES TABLE
NR (SNPBPC,1)			;COUNT OF USERS USING SNOOP FACILITY
NR (SNPLOK,1)			;LOCK FOR SNOOP DATA BASE
NR (SNPFRE,1)			;FREE LIST FOR BREAK POINTS

RS (SNPCNT,1)			;# OF BREAK POINTS CURRENTLY INSERTED
;SNOOP JSYS DISPATCH ROUTINE

.SNOOP::MCENT			;ENTER THE JSYS
	MOVE T2,CAPENB		;GET ENABLED CAPABILITIES
	XCTU [HRRZ T1,1]	;GET FUNCTION CODE
	CAIN T1,.SNPSY		;IS THIS A SYMBOL LOOKUP?
	JRST SNPFN6		;YES, DONT LOCK UP DATA BASE
	CAIN T1,.SNPAD		;IS THIS AN ADDRESS LOOKUP?
	JRST SNPFN7		;YES, GO LOOK IT UP
	TRNN T2,SC%WHL!SC%OPR	;IS THE USER PROPERLY PRIVILEGED?
	RETERR (SNOPX1)		;NO, GIVE ERROR RETURN
	CAIL T1,SNPDTL		;IS THIS A LEGAL FUNCTION
	RETERR (SNOPX2)		;NO, GIVE ERROR RETURN
	SKIPN SNPPGS		;PAGES ALREADY LOCKED DOWN?
	SKIPL SNPDTB(T1)	;NO, SHOULD THEY BE LOCKED DOWN?
	SKIPA			;ALL OK
	RETERR (SNOPX3)		;PAGES NOT LOCKED AND SHOULD BE!
	HRRZ T1,SNPDTB(T1)	;FIND TRANSFER ADDRESS
	NOINT			;LOCK UP THE DATA BASE
	LOCK SNPLOK		;...
	CALL (T1)		;GO DO THE FUNCTION
	 JRST [	UNLOCK SNPLOK	;ERROR DURING FUNCTION
		OKINT		;UNLOCK LOCKS
		RETERR ()]	;AND GIVE ERROR RETURN TO USER
	UNLOCK SNPLOK		;OK RETURN
	OKINT			;UNLOCK
	SMRETN			;GIVE USER THE SKIP RETURN


SNPDTB:	SNPFN0			;DECLARE CODE AND LOCK INTO MONITOR
	400000,,SNPFN1		;LOCK DOWN SWAPPABLE MONITOR
	400000,,SNPFN2		;DEFINE A BREAK POINT
	400000,,SNPFN3		;INSERT ALL BREAK POINTS
	400000,,SNPFN4		;REMOVE ALL BREAK POINTS
	SNPFN5			;REMOVE ALL BP'S AND UNLOCK EVERYTHING
SNPDTL==.-SNPDTB
;SNOOP JSYS FUNCTION 0 - DECLARE CODE AND LOCK INTO MONITOR VIRT MEMORY

SNPFN0:	STKVAR <SNPF0C,SNPF0S,SNPF0D>
	SKIPE SNPPGS		;USER ALREADY LOCKED DOWN SOME PAGES?
	RETBAD (SNOPX4)		;YES, THEN THIS IS ILLEGAL
	MOVE T1,FORKX		;GET OUR FORK NUMBER
	HLL T1,FKPGS(T1)	;GET PTN OF FORK
	XCTU [HRR T1,3]	;GET PAGE NUMBER OF DATA
	TRNE T1,777000		;IS THIS A LEGAL PAGE #?
	RETBAD (SNOPX5)		;NO
	MOVEM T1,SNPF0S		;SAVE SOURCE IDENTIFIER
	XCTU [HRRZ T2,2]	;GET COUNT OF PAGES TO BE LOCKED
	JUMPE T2,[RETBAD (SNOPX6)] ;ZERO PAGES IS NOT ALLOWED
	MOVEM T2,SNPF0C		;SAVE IT FOR LATER
	CALL VALPAG		;VALIDATE THAT PAGES ARE PRIVATE
	 RET			;ILLEGAL PAGE ACCESS
	MOVE T1,SNPF0C		;GET COUNT OF PAGES DESIRED
	CALL SNPFFP		;FIND A CONSEQUTIVE BLOCK OF FREE PAGES
	 RET			;NOT ENOUGH FREE PAGES
	STOR T1,SNPPA		;STORE START ADR OF LOCKED PAGES
	MOVE T2,SNPF0C		;GET NUMBER OF PAGES TO BE LOCKED
	STOR T2,SNPPC		;REMEMBER HOW MANY WERE LOCKED
	CALL SNPASP		;ASSIGN THESE PAGES FOR US
	LOAD T2,SNPPA		;GET MONITOR VIRTUAL PAGE NUMBER AGAIN
	MOVEM T2,SNPF0D		;SAVE DESTINATION IDENTIFIER
	MOVE T1,SNPF0S		;GET SOURCE IDENTIFIER
	XCTU [HRRZM T2,2]	;RETURN MONITOR ADDRESS TO USER
SNPF0A:	TRZ T1,777000		;GUARANTEE A LEGAL PAGE #
	LSH T2,PGSFT		;GET ADDRESS FROM PAGE #
	HRLI T2,(PM%RD!PM%WT!PM%EX)
	CALL SETIOP		;LOCK IT INTO MONITOR
	BUG(CHK,SNPLKF,<SNPFN0: CANNOT LOCK DOWN PAGE INTO MONITOR>)
	AOS T1,SNPF0S		;GET NEXT SOURCE IDENTIFIER
	AOS T2,SNPF0D		;GET NEXT DESTINATION IDENTIFIER
	SOSLE SNPF0C		;ANY MORE TO BE DONE?
	JRST SNPF0A		;YES, GO LOCK OTHER PAGES
	AOSE SNPBPC		;IS BREAK POINT PAGE LOCKED DOWN YET?
	RETSKP			;YES, DONT LOCK AGAIN
	MOVEI T1,SNPBPP		;GET PAGE ADDRESS OF BREAK POINT PAGE
	LSH T1,-PGSFT		;GET PAGE NUMBER
	HRL T1,MMSPTN		;SET UP PTN,,PN FOR LOCKING
	CALL MLKPG		;LOCK DOWN BREAK POINT PAGE
	RETSKP			;GIVE OK RETURN TO USER
;ROUTINE TO VALIDATE THAT ALL PAGES TO BE LOCKED ARE PRIVATE OR CPW
;ACCEPTS IN T1/	IDENTIFIER FOR USER PAGES
;	    T2/	COUNT OF PAGES
;	CALL VALPAG
;RETURNS +1:	ILLEGAL PAGE TYPE
;	 +2:	OK

VALPAG:	STKVAR <VALPGI,VALPGC>
	MOVEM T1,VALPGI		;SAVE IDENTIFIER
	MOVEM T2,VALPGC		;AND COUNT
VALPG1:	MOVE T1,VALPGI		;GET IDENTIFIER OF NEXT PAGE
	CALL MRPACS		;GET PAGE ACCESS BITS
	TLNN T1,(1B9!1B10)	;PRIVATE OR COPY ON WRITE?
	RETBAD (SNOP18)		;NO, GIVE ERROR RETURN TO USER
	HRRZ T1,VALPGI		;GET ADDRESS OF PAGE
	HRRI T2,1(T1)		;STEP TO NEXT PAGE
	HRRM T2,VALPGI		;...
	LSH T1,PGSFT		;MAKE PAGE # INTO ADDRESS
	XCTU [MOVES 0(T1)]	;WRITE INTO PAGE TO MAKE IT PRIVATE
	SOSLE VALPGC		;ANY MORE TO BE DONE?
	JRST VALPG1		;YES, GO TEST OTHER PAGES
	RETSKP			;NO, ALL DONE

;SNOOP JSYS FUNCTION 1 - LOCK DOWN THE SWAPPABLE MONITOR

SNPFN1:	LOAD T1,SNPFLG		;GET FLAGS FOR THIS FORK
	TROE T1,SN.SML		;IS IT ALREADY LOCKED DOWN?
	RETSKP			;YES, DONT DO IT AGAIN
	STOR T1,SNPFLG		;NO, STORE UPDATED FLAGS
	CALL SWPMLK		;LOCK DOWN SWAPPABLE MONITOR
	RETSKP			;GIVE OK RETURN
;SNOOP JSYS FUNCTION 2 - DEFINE A BREAK POINT

SNPFN2:	STKVAR <SNPF2N,SNPF2I,SNPF2A>
	LOAD T1,SNPFLG		;GET SNOOP FLAGS FOR THIS FORK
	TRNE T1,SN.BRK		;ARE THE BREAK POINTS INSERTED?
	RETBAD (SNOPX7)		;YES, GIVE ERROR RETURN
	UMOVE T1,2		;GET BREAK POINT NUMBER
	MOVEM T1,SNPF2N		;SAVE BREAK POINT NUMBER
	CALL SNPBPR		;RELEASE THIS BREAK POINT
	UMOVE T4,4		;GET TRANSFER INSTRUCTION FROM USER
	JUMPE T4,RSKP		;IF NO INST, THEN EXIT
	MOVEM T4,SNPF2I		;SAVE INSTRUCTION FOR LATER
	UMOVE T4,3		;GET ADDRESS IN MONITOR
	MOVEM T4,SNPF2A		;SAVE ADDRESS FOR LATER ALSO
	MOVE T1,0(T4)		;GET INSTRUCTION
	MOVE T2,1(T4)		;AND INSTRUCTION+1
	TLNE T1,777000		;IS THIS INST 0?
	TLNN T2,777000		;OR THIS ONE?
	RETBAD (SNOPX8)		;YES, THIS IS NOT LEGAL PLACE FOR BP
	MOVEI T1,SNPBPP		;NOW CHECK IF A BP ALREADY ON THIS LOC
	MOVEI T2,SNPBPS/SNPBSZ	;GET # OF POSSIBLE BP'S
SNPF2L:	LOAD T3,SNPB1,(T1)	;GET ADDRESS OF BP
	JUMPE T3,SNPF2D		;IF 0, THEN NO BP DEFINED HERE
	HRRZI T3,-1(T3)		;GET ADDRESS OF BP IN MONITOR
	CAIN T3,0(T4)		;SAME AS ONE BEING DEFINED?
	RETBAD (SNOP17)		;YES, 2 BP'S ON SAME ADR IS ILLEGAL
SNPF2D:	MOVEI T1,SNPBSZ(T1)	;STEP TO NEXT BP
	SOJG T2,SNPF2L		;LOOP BACK UNTIL ALL BP'S ARE CHECKED
	HRRZ T1,SNPFRE		;GET POINTER TO FIRST FREE BP
	JUMPE T1,[RETBAD (SNOPX9)] ;IF 0, THEN NONE LEFT
	LOAD T2,SNPBL,(T1)	;GET POINTER TO SECOND FREE BP
	HRRM T2,SNPFRE		;MAKE FREE LIST POINT TO 2ND BP
	MOVE T3,SNPF2N		;GET BREAK POINT NUMBER
	STOR T3,SNPBN,(T1)	;SAVE BREAK POINT NUMBER
	LOAD T3,SNPLNK		;GET POINTER TO USER'S 1ST BP
	STOR T3,SNPBL,(T1)	;PUT NEW BP AT START OF LIST
	STOR T1,SNPLNK		;...
	MOVE T2,SNPF2A		;GET ADDRESS TO BE PATCHED AGAIN
	MOVE T3,0(T2)		;GET INSTRUCTION BEING REPLACED
	STOR T3,SNPBRI,(T1)	;AND REPLACED INSTRUCTION
	MOVE T4,SNPF2I		;GET BACK INSTRUCTION FROM USER
	STOR T4,SNPBTI,(T1)	;STORE TRANSFER INSTRUCTION
	MOVSI T3,(JRST)		;SET UP JRST .+1
	HRRI T3,1(T2)		;...
	STOR T3,SNPB1,(T1)	;STORE JRST .+1 INSTRUCTION INTO BLOCK
	HRRI T3,2(T2)		;SET UP JRST .+2
	STOR T3,SNPB2,(T1)	;STORE IT IN BP BLOCK ALSO
	RETSKP			;GIVE OK RETURN
;ROUTINE TO RETURN A BREAK POINT TO FREE POOL

;ACCEPTS IN T1/	BREAK POINT NUMBER OR -1 FOR ALL BREAK POINTS
;	CALL SNPBPR
;RETURNS +1:	ALWAYS

SNPBPR:	MOVEI T2,SNPLST		;SET UP TO GET FIRST BP ON LIST
SNPBR1:	MOVE T4,T2		;SAVE LAST POINTER
	LOAD T2,SNPBL,(T2)	;GET NEXT BP ON LIST
	JUMPE T2,R		;IF 0, BP WAS NOT FOUND
	LOAD T3,SNPBN,(T2)	;GET NUMBER OF THIS BP
	CAME T1,T3		;A MATCH?
	JUMPG T1,SNPBR1		;NO, LOOP BACK TIL ONE FOUND
	LOAD T3,SNPBL,(T2)	;GET FORWARD POINTER
	STOR T3,SNPBL,(T4)	;PUT IT IN LAST BP FORWARD POINTER
	HRRZ T3,SNPFRE		;GET FIRST FREE BP
	HRRM T2,SNPFRE		;PUT THIS BP ON FREE LIST
	STOR T3,SNPBL,(T2)	;MAKE THIS BP POINT TO OTHER FREE BP'S
	MOVEI T3,0		;CLEAR OUT JRST A+1 WORD
	STOR T3,SNPB1,(T2)	;  TO FLAG THAT BP IS ON FREE LIST
	JRST SNPBPR		;LOOP BACK UNTIL ALL BP'S SCANNED
;SNOOP JSYS FUNCTION 3 - INSERT BREAK POINTS

SNPFN3:	LOAD T1,SNPFLG		;GET FLAGS
	TROE T1,SN.BRK		;BREAK POINTS INSERTED YET?
	RETBAD (SNOP10)		;YES, ERROR
	STOR T1,SNPFLG		;NO, STORE UPDATED FLAGS
	CALL SWPMWE		;WRITE ENABLE THE SWAPPABLE MONITOR
	LOAD T1,SNPLNK		;GET POINTER TO FIRST BP OF USER
SNPF3A:	JUMPE T1,SNPF3B		;0 MEANS AT END OF BP LIST
	LOAD T2,SNPB1,(T1)	;GET ADDRESS+1 OF WHERE TO PUT BP
	HRRZS T2
	MOVE T3,-1(T2)		;GET INSTRUCTION BEING REPLACED
	CAME T3,SNPBII(T1)	;IS IT SAME AS ORIGINAL
	BUG(CHK,SNPIC,<SNPFN3: INSTRUCTION BEING REPLACED HAS CHANGED>)
	MOVSI T3,(JRST)		;SET UP JRST BP INSTRUCTION
	HRRI T3,SNPBP(T1)	;GET ADDRESS OF BP CODE
	MOVEM T3,-1(T2)		;INSERT THE BREAK POINT
	AOS SNPCNT		;COUNT UP # OF BP'S INSERTED
	LOAD T1,SNPBL,(T1)	;GET POINTER TO NEXT BP
	JRST SNPF3A		;LOOP BACK TIL ALL BP'S ARE INSERTED

SNPF3B:	CALL SWPMWP		;WRITE PROTECT THE SWAPPABLE MONITOR 
	RETSKP			;GIVE OK RETURN



;SNOOP JSYS FUNCTION 4 - REMOVE ALL BREAK POINTS

SNPFN4:	LOAD T1,SNPFLG		;GET FLAGS
	TRZN T1,SN.BRK		;WERE BP'S INSERTED
	RETBAD (SNOP11)		;NO, GIVE ERROR RETURN
	STOR T1,SNPFLG		;STORE UPDATED FLAGS
	CALL SWPMWE		;WRITE ENABLE SWAPPABLE MONITOR
	LOAD T1,SNPLNK		;GET LINK TO FIRST BP
SNPF4A:	JUMPE T1,SNPF4B		;0 MEANS END OF LIST
	LOAD T2,SNPBRI,(T1)	;GET REPLACED INSTRUCTION
	LOAD T3,SNPB1,(T1)	;GET ADRRESS+1 OF BP
	HRRZS T3
	MOVEM T2,-1(T3)		;PUT BACK INSTRUCTION
	SOSGE SNPCNT		;COUNT DOWN # OF BP'S INSERTED
	JRST SNPF4C		;OVERLY DECREMENTED
SNPF4D:	LOAD T1,SNPBL,(T1)	;GET POINTER TO NEXT BP IN LIST
	JRST SNPF4A		;LOOP BACK TIL ALL BP'S ARE REMOVED

SNPF4B:	CALL SWPMWP		;WRITE PROTECT THE SWAPPABLE MON AGAIN
	RETSKP			;AND EXIT

SNPF4C:	BUG(CHK,SNPODB,<SNPF4C: COUNT OF INSERTED BREAK POINTS OVERLY DECREMENTED>)
	SETZM SNPCNT		;FIX UP COUNT
	JRST SNPF4D		;AND CONTINUE ON
;SNOOP JSYS FUNCTION 5 - RELEASE ALL STORAGE

SNPFN5:	STKVAR <SNPF5C,SNPF5D>
	SKIPN SNPPGS		;PAGES LOCKED DOWN?
	RETSKP			;NO, THEN NOTHING TO DO
	LOAD T1,SNPFLG		;GET FLAGS
	TRNE T1,SN.BRK		;BREAK POINTS IN?
	CALL SNPFN4		;YES, REMOVE THEM
	JFCL
	SETO T1,		;RELEASE ALL BREAK POINTS
	CALL SNPBPR		;   BACK TO FREE POOL
	LOAD T1,SNPPC		;GET NUMBER OF PAGES TO UNLOCK
	MOVEM T1,SNPF5C		;SAVE COUNT
	LOAD T2,SNPPA		;GET MONITOR VIRTUAL PAGE NUMBER
	MOVEM T2,SNPF5D		;SAVE DESTINATION IDENTIFIER
	JUMPLE T1,SNPF5B	;IF NONE LOCKED, DONT UNLOCK ANY
SNPF5A:	MOVEI T1,0		;0 MEANS UNLOCK
	LSH T2,PGSFT		;CREATE AN ADDRESS FROM THE PAGE #
	HRLI T2,(PM%RD!PM%WT!PM%EX)
	CALL SETIOP		;UNLOCK PAGES
	BUG(CHK,SNPUNL,<SNPF5A: CANNOT UNLOCK SNOOP PAGE>)
	AOS T2,SNPF5D		;UPDATE DESTINATION
	SOSLE SNPF5C		;ANY MORE PAGES TO BE DONE?
	JRST SNPF5A		;LOOP BACK FOR ALL PAGES
	LOAD T1,SNPPA		;NOW RELEASE SNOOP DATA PAGES
	LOAD T2,SNPPC
	CALL SNPRLP		;FOR OTHERS TO USE
SNPF5B:	SETZM SNPPGS		;FLAG THAT NO PAGES ARE LOCKED
	LOAD T1,SNPFLG		;GET FLAGS BACK
	TRNE T1,SN.SML		;DID THIS USER LOCK SWAPPABLE MONITOR?
	CALL SWPMUL		;YES, UNLOCK IT
	SOSL SNPBPC		;ANY OTHER USERS OF SNOOP?
	RETSKP			;NO
	MOVEI T1,SNPBPP		;GET ADR OF SNOOP BP PAGE
	LSH T1,-PGSFT		;MAKE IT A PAGE NUMBER
	HRL T1,MMSPTN		;GET PTN OF MONITOR MAP
	CALL MULKPG		;UNLOCK THE BP PAGE
	RETSKP			;AND EXIT
;SNOOP JSYS FUNCTIONS 6 AND 7 - SYMBOL TABLE LOOKUPS

SNPFN7:	TDZA F,F		;REMEMBER THAT AN ADDRESS IS GIVEN
SNPFN6:	SETO F,			;USER IS SUPPLYING A SYMBOL
	TRNN T2,SC%WHL!SC%OPR!SC%MNT
	RETERR (SNOPX1)		;MUST HAVE PRIVILEGES
	SETZ Q1,		;INITIALIZE ANSWER ACS
	SETO Q2,
	MOVSI Q3,400000		;LARGEST NEGATIVE VALUE
	UMOVE T1,3		;GET PROGRAM NAME (IF ANY)
	TLNE T1,740000		;SEE IF IT IS A PROGRAM NAME
	RETERR (SNOP12)		;IT ISNT, USER IS CONFUSED
	HRRZ T3,.JBSYM		;GET START OF SYMBOL TABLE
	HLRO T2,.JBSYM		;GET NEGATIVE LENGTH
	HRROI T4,1(T2)		;DECREMENT COUNT BY 1
	MOVNS T4		;GET POSITIVE LENGTH OF SYMBOL TABLE-1
SNPF6A:	ADD T3,T4		;GET POINTER TO NEXT PROGRAM NAME
	JUMPE T1,SNPF6B		;IF NO PROGRAM NAME, GO LOOK FOR SYMBOL
	HLRE T4,0(T3)		;GET COUNT TO NEXT PROGRAM NAME
	CAMN T1,-1(T3)		;IS THIS A MATCH OF PROGRAM NAMES
	JRST SNPF6F		;YES, NOW GO LOOK FOR SYMBOL VALUE
	SUB T2,T4		;STEP TO NEXT PROGRAM AREA
	JUMPN T4,SNPF6A		;PAST END?
	RETERR (SNOP13)		;YES, PROGRAM NAME NOT FOUND

SNPF6F:	SKIPE T4		;IS THIS THE LAST PROGRAM
	MOVE T2,T4		;NO, GET LENGTH OF THIS SYMBOL AREA
SNPF6B:	UMOVE T1,2		;GET SYMBOL (OR ADDR) TO BE LOOKED UP
	SKIPE F			;LOOKING UP A SYMBOL?
	TLZ T1,740000		;YES, CLEAR SYMBOL TYPE
SNPF6C:	MOVE T4,0(T3)		;GET ADDRESS FROM SYMBOL TABLE
	JUMPE F,SNPF6G		;IF ADDRESS DESIRED, GO TO SNPF6G
	MOVE T4,-1(T3)		;GET SYMBOL FROM TABLE
	TLZN T4,740000		;CLEAR OUT SYMBOL TYPE FIELD
	JRST SNPF6D		;DONT LOOK AT PROGRAM NAMES
SNPF6G:	JUMPN F,SNPF6J		;LOOKING UP AN ADDRESS?
	CAMLE T4,T1		;YES, LESS THAN THE DESIRED ONE?
	JRST SNPF6J		;NO
	CAMGE T4,Q3		;YES, IS IT THE CLOSEST ONE SO FAR?
	JRST SNPF6J		;NO
	MOVE P1,-1(T3)		;SEE IF THIS IS A SUPPRESSED SYMBOL
	TLNE P1,(1B0)		;...
	JRST SNPF6J		;SYMBOL IS SUPPRESSED, IGNORE IT
	MOVE Q3,T4		;YES, REMEMBER THIS ADDRESS
	MOVE Q1,-1(T3)		;AND REMEMBER THE RADIX-50 SYMBOL ALSO
SNPF6J:	CAMN T1,T4		;IS THIS AN EXACT MATCH?
	JRST SNPF6E		;YES, GO GET THE VALUE
SNPF6D:	SUBI T3,2		;STEP TO NEXT SYMBOL IN TABLE
	AOS T2			;DECREMENT LENGTH COUNTER
	AOJL T2,SNPF6C		;LOOP BACK TIL END OF TABLE
	SKIPGE Q2		;VALUE FOUND?
	JRST SNPF6I		;NO, EXACT MATCH NOT FOUND
	UMOVEM Q1,2		;YES, RETURN IT TO USER
	SKIPN F			;FUNCTION 7?
	XCTU [SETZM 3]		;YES, THE OFFSET IS 0
	SMRETN			;AND GIVE SUCCESSFUL RETURN
SNPF6I:	SKIPN Q1		;FOUND AN ANSWER?
	RETERR (SNOP14)		;NO, RETURN THAT SYMBOL NOT FOUND
	UMOVEM Q1,2		;YES, RETURN THE SYMBOL
	SUB T1,Q3		;GET OFFSET
	UMOVEM T1,3		;RETURN THE DIFFERENCE TO THE USER
	SMRETN

SNPF6E:	MOVE T4,0(T3)		;GET VALUE OF SYMBOL
	JUMPN F,SNPF6H		;IF SYMBOL DESIRED, GO TO SNPF6H
	MOVE T4,-1(T3)		;GET SYMBOL FROM SYMBOL TABLE
	TLNE T4,(1B0)		;SUPPRESSED SYMBOL?
	JRST SNPF6D		;YES, SKIP IT
SNPF6H:	EXCH Q1,T4		;SAVE ANSWER
	CAMN Q1,T4		;SAME VALUE?
	AOJA Q2,SNPF6D		;YES, THIS IS NEVER AN ERROR
	AOJE Q2,SNPF6D		;IF FIRST VALUE FOUND, CONTINUE LOOKING
	RETERR (SNOP16)		;MULTIPLY DEFINED VARIABLE
;SNOOP JSYS UTILITY ROUTINES

;ROUTINE TO RELEASE ALL SNOOP RESOURCES ON A RESET JSYS

;	CALL SNPREL
;RETURNS +1 ALWAYS

SNPREL::NOINT			;LOCK UP THE LOCKS
	LOCK SNPLOK		;...
	CALL SNPFN5		;GO RELEASE ALL RESOURCES
	JFCL
	UNLOCK SNPLOK		;UNLOCK THE DATA BASE
	OKINT
	RET			;AND RETURN
;ROUTINE TO FIND CONSECUTIVE FREE PAGES FOR USER CODE TO BE LOCKED INTO

;ACCEPTS IN T1/	COUNT OF PAGES DESIRED
;	CALL SNPFFP
;RETURNS +1:	NO FREE SPACE LEFT, ERROR CODE IN T1
;	 +2:	SUCCESSFUL - PAGE # OF FIRST PAGE IN T1

SNPFFP:	STKVAR <SNPFFC,SNPFFM>
	MOVEM T1,SNPFFC		;SAVE COUNT
	CAILE T1,SNPDPC		;IS THIS REQUEST REASONABLE?
	JRST SNPFF4		;NO, NOT ENOUGH SNOOP PAGES
	MOVEI T1,SNPDAT		;GET START OF DATA AREA
	LSH T1,-PGSFT		;TURN IT INTO A PAGE NUMBER
	MOVEI T2,SNPDPC(T1)	;GET END OF DATA AREA+1
	SUB T2,SNPFFC		;CALCULATE END OF SEARCH VALUE
	MOVEM T2,SNPFFM		;SAVE CUT OFF POINT
	SETZB T3,T4		;INITIALIZE ACS FOR SEARCH
	MOVSI T2,400000		;START AT BIT 0 OF FIRST WORD IN TABLE
SNPFF1:	AOS T4			;KEEP TRACK OF PAGES SCANNED
	TDNN T2,SNPFTB(T3)	;IS THIS PAGE AVAILABLE?
	JRST SNPFF3		;NO, GO INIT COUNTERS
	CAML T4,SNPFFC		;SEEN ENOUGH FREE PAGES YET?
	RETSKP			;YES, RETURN TO CALLER
SNPFF2:	ROT T2,-1		;SHIFT BIT TO NEXT POSITION
	JUMPG T2,SNPFF1		;LOOP BACK FOR REST OF COUNT
	AOJA T3,SNPFF1		;JUST MOVED TO NEXT WORD, INC INDEX

SNPFF3:	ADD T1,T4		;UPDATE POINTER TO FIRST FREE PAGE
	SETZ T4,		;START COUNTER OVER AT 0
	CAMG T1,SNPFFM		;IS THE SEARCH FINISHED?
	JRST SNPFF2		;NO, GO SEARCH SOME MORE
SNPFF4:	RETBAD (SNOP15)		;YES, NO ROOM TO LOCK PAGES INTO

;ROUTINE TO ASSIGN AND RELEASE PAGES IN SNOOP POOL

;ACCEPTS IN T1/	PAGE NUMBER OF FIRST PAGE IN GROUP
;	    T2/	NUMBER OF PAGES IN GROUP
;	CALL SNPASP OR SNPRLP
;RETURNS +1:	ALWAYS

SNPASP:	SKIPA T4,[ANDCAM T3,SNPFTB(T1)]
SNPRLP:	MOVE T4,[IORM T3,SNPFTB(T1)]
	STKVAR <SNPARC>
	MOVEM T2,SNPARC		;SAVE NUMBER OF PAGES IN GROUP
	MOVEI T2,SNPDAT		;GET START OF DATA AREA
	LSH T2,-PGSFT		;TURN IT INTO A PAGE NUMBER
	SUB T1,T2		;GET A RELATIVE PAGE NUMBER
	IDIVI T1,^D36		;GET INDEX INTO TABLE
	MOVNS T2		;GET NEGATIVE BIT POSITION FOR SHIFT
	MOVSI T3,400000		;START AT BIT 0
	LSH T3,0(T2)		;GET FIRST BIT TO BE SET OR CLEARED
SNPAR1:	XCT T4			;SET OR CLEAR THE BIT
	ROT T3,-1		;MOVE TO NEXT BIT
	SKIPG T3		;TIME TO INCREMENT INDEX?
	AOS T1			;YES
	SOSLE SNPARC		;DECREMENT COUNT
	JRST SNPAR1		;LOOP BACK FOR ALL BITS
	RET			;ALL DONE
;ROUTINE TO INITIALIZE THE SNOOP FUNCTION AND DATA BASE

;	CALL SNPINI
;RETURNS +1 ALWAYS

SNPINI::SETZM SNPBPP		;ZERO BREAK POINT PAGE
	MOVE T1,[SNPBPP,,SNPBPP+1]
	BLT T1,SNPBPP+SNPBPS-1
	MOVEI T1,SNPBPP		;GET POINTER TO FIRST BP BLOCK
	MOVEM T1,SNPFRE		;SET UP FREE LIST
	MOVEI T2,SNPBPS/SNPBSZ	;GET MAX NUMBER OF BREAK POINTS
SNPIN1:	MOVEI T3,SNPBSZ(T1)	;GET ADDRESS OF NEXT BREAK POINT
	MOVEM T3,0(T1)		;MAKE THIS BP POINT TO NEXT BP
	MOVE T1,T3		;STEP TO NEXT BP
	SOJG T2,SNPIN1		;LOOP TIL ALL BP'S LINKED
	SETZM -SNPBSZ(T1)	;PUT A ZERO AT END OF LIST
	SETOM SNPFTB		;NOW INIT FREE PAGES TABLE
	MOVE T1,[SNPFTB,,SNPFTB+1]
	MOVEI T2,<<SNPDPC+^D35>/^D36>
	CAILE T2,1		;ONLY ONE WORD TABLE?
	BLT T1,SNPFTB-1+<<SNPDPC+^D35>/^D36>
	SETOM SNPBPC		;INIT COUNT OF SNOOP USERS
	SETZM SNPCNT		;INITIALIZE COUNT OF INSERTED BP'S
	SETOM SNPLOK		;INIT SNOOP DATA BASE LOCK
	RET			;AND EXIT
;SOBE - Skip if output buffer is empty

;ACCEPTS:
;	DEVICE DESIGNATOR

;	SOBE

;RETURNS +1: OUTPUT BUFFER IS NOT EMPTY
;		T2/ NUMBER OF BYTES IN BUFFER
;	 +2: ERROR OR OUTPUT BUFFER IS EMPTY
;		T2/ 0 IF EMPTY 
;			OR
;		    ERROR CODE IF ERROR

.SOBE::	MCENT
	CALL CHKTTR
	 JRST SOBE1
	CALL LCKTTY		;POINT TO DYNAMIC DATA, PREVENT DEALLOCATION
	JRST [	CALL ULKTTY	;NOT ACTIVE. ALLOW DEALLOCATION
		MOVEI A,TTYX01	;SET ERROR TO 'LINE IS NOT ACTIVE'
		JRST SOBE1]	;GO RETURN ERROR CODE
	CALL TTSOBE
	JRST [	UMOVEM A,B
		CALL ULKTTY	;ALLOW DEALLOCATION
		JRST EMRET1]
	CALL ULKTTY		;ALLOW DEALLOCATION
	SETZM A			;INDICATE NO CHARACTERS IN BUFFER
SOBE1:	UMOVEM A,B		;RETURN ERROR CODE OR 0
	SMRETN

; Skip if output buffer full

;ACCEPTS:
;	DEVICE DESIGNATOR

;	SOBF

;RETURNS +1: OUTPUT BUFFER IS NOT FULL OR ERROR
;		T2/ NUMBER OF BYTES IN BUFFER
;			OR
;		   0 IF ERROR
;	 +2: ERROR OR OUTPUT BUFFER IS FULL
;		T2/ COUNT IF NO ERROR

.SOBF::	MCENT
	CALL CHKTTR
	JRST [	SETZ A,		;NOT A TERMINAL. RETURN COUNT OF 0
		JRST SOBF1]
	CALL LCKTTY		;POINT TO DYNAMIC DATA, PREVENT DEALLOCATION
	 JRST [	CALL ULKTTY	;NOT ACTIVE. ALLOW DEALLOCATION
		SETZ A,		;SET COUNT TO 0
		JRST SOBF1]
	CALL TTSOBF		;GO TEST BUFFER COUNT
	 JRST [	CALL ULKTTY	;NOT FULL. ALLOW DEALLOCATION
		 JRST SOBF1]	;RETURN +1 WITH COUNT
	UMOVEM 1,2		;FULL. Return count of bytes in buffer
	CALL ULKTTY		;ALLOW DEALLOCATION
	SMRETN
SOBF1:	UMOVEM 1,2		; Return count of bytes in buffer
	JRST MRETN
; Set accessibility of a page
; Call:	LH(A)	; Fork or file handle
;	RH(A)	; Page number
;	SPACS

.SPACS::MCENT
	TRVAR <JFHDL>		;REMEMBER JFN WITH STRUCTURE LOCK
	SETZM JFHDL		;ASSUME NO STR LOCK TO RELEASE
	SETZ B,			;NO PT CREATES
	CALL CPMAP		; Convert to ptn.pn
	 MOVEM D,JFHDL		;REMEMBER STR LOCK
	JUMPE A,SPACER		;IF NO MATCH,ERROR
	XCTU [SKIPGE 1]		;FORK HANDLE?
	JRST SPACFK		;YES
	TXNN B,WRTF		; MUST BE ABLE TO WRITE
SPACER:	JRST [	MOVEI A,SPACX1
		MOVEM A,LSTERR
		SKIPE A,JFHDL	;LOCKED A STR?
		CALL LUNLK0	;YES. UNLOCK IT
		JRST ITRAP]
	MOVSI C,160000
	JRST SPAC1

;FORK HANDLE WAS SPECIFIED

SPACFK:	PUSH P,A		; Save page handle
	CALL MRPACS		; Get access of page
	TLNN A,(1B5)
	JRST SPACER		; Non-existent page
	TLNE A,(1B10)
	JRST SPACPR		; Private page
	PUSH P,A		; Save access
	MOVE A,-1(P)		; Get back the page handle
	CALL MRPT		; Get map contents
	 JRST SPACP1		; Indirect or shared to fork
	CALL OFNJFN		; Convert to jfn.pn
	JRST SPACCF		; Closed file
	SETZ B,			;NO PT CREATES
	CALL CPMAP		; Get allowable access
	 MOVEM D,JFHDL		;REMEMBER STR LOCK
	SUB P,BHC+1
	JRST SPAC2

SPACCF:	POP P,C
	AND C,[XWD 160000,0]
	JRST SPAC2

SPACP1:	SUB P,BHC+1
SPACPR:	MOVSI C,160000
SPAC2:	TLO C,1400
	POP P,A
SPAC1:	UMOVE B,2
	AND B,C
	CALL MSPACS
	SKIPE A,JFHDL		;HAVE A STR LOCK TO RELEASE?
	CALL LUNLK0		;YES. FREE IT
	JRST MRETN
;SPOOL JSYS

;ACCEPTS IN 1/	LENGTH ,, FUNCTION CODE
;	    2/	LOCATION OF ARGUMENT BLOCK
;	SPOOL
;RETURNS +1:	ERROR - ERROR CODE IN AC 1
;	 +2:	SUCCESSFUL

.SPOOL::MCENT			;ENTER JSYS
	XCTU [HRRZ T1,1]	;GET FUNCTION CODE
	CAILE T1,.SPLRD		;LEGAL FUNCTION?
	RETERR (SPLX1)		;NO
	XCTU [HLRZ T2,1]	;GET LENGTH
	HLRZ T3,SPLTAB(T1)	;GET DESIRED LENGTH
	CAMGE T2,T3		;USER SUPPLY ENOUGH ARGS?
	RETERR (SPLX2)		;NO, ILLEGAL LENGTH
	UMOVE Q1,2		;GET ADDRESS OF ARG BLOCK
	HRRZ T1,SPLTAB(T1)	;GET ADDRESS OF ROUTINE TO CALL
	JRST 0(T1)		;DISPATCH

SPLTAB:	3,,SPOOL0		;(0) DEFINE INPUT SPOOLING SET
	2,,SPOOL1		;(1) SET SPOOL DIRECTORY FOR A DEVICE
	2,,SPOOL2		;(2) READ SPOOL DIRECTORY FOR A DEVICE

SPOOL0:	UMOVE T1,0(Q1)		;GET DEVICE DESIGNATOR
	CAME T1,[600000+.DVCDR,,-1]
	RETERR (SPLX3)		;ILLEGAL DEVICE DESIGNATOR
	MOVEI T1,JSBFRE		;PREPARE TO RELEASE OLD STRING IF ANY
	HRRZ T2,JSCDR		;GET OLD STRING POINTER
	SKIPE T2		;WAS THERE AN OLD STRING?
	CALL RELFRE		;YES, RELEASE IT
	UMOVE T1,1(Q1)		;GET STRING POINTER
	CALL CPYFU0		;COPY STRING INTO JSB
	 RETERR ()		;ERROR
	HRRZM T1,JSCDR		;STORE STRING ADDRESS
	XCTU [HRRZ T1,2(Q1)]	;GET VERSION NUMBER OF FIRST FILE
	JUMPE T1,[RETERR (SPLX5)] ;0 IS ILLEGAL
	SOS T1			;IT GET INCREMENTED BEFORE BEING USED
	HRLM T1,JSCDR		;STORE IT IN JSB
	SMRETN			;GIVE OK RETURN
SPOOL1:	MOVE T1,CAPENB		;CHANGING DIR # IS PRIVILEGED
	TRNN T1,SC%WHL!SC%OPR	;WHEEL OR OPER?
	RETERR (SPLX4)		;NO, MUST BE PRIVILEGED
	UMOVE T1,0(Q1)		;GET DEVICE DESIGNATOR
	CALL CHKDES		;CHECK THIS DESIGNATOR
	 RETERR			;NO, ILLEGAL DESIGNATOR
	UMOVE T4,1(Q1)		;GET DIR NUMBER
	HLL T1,DEVCHR(T2)	;SET UP DESIGNATOR
	TLZ T1,777000		;...
	MOVSI T2,-NDEV		;SET UP TO LOOP THRU DEVICES
SPOL1L:	HLL T3,DEVCHR(T2)	;SET UP DESIGNATOR
	TLZ T3,777000		;...
	HRR T3,DEVUNT(T2)	;GET UNIT NUMBER
	CAMN T1,T3		;IS THIS THE CORRECT DEVICE?
	MOVEM T4,DEVCH2(T2)	;YES, STORE NEW DIR #
	AOBJN T2,SPOL1L		;LOOP FOR ALL DEVICES
	SMRETN			;AND EXIT

SPOOL2:	UMOVE T1,0(Q1)		;GET DEVICE DESIGNATOR
	CALL CHKDES		;CHECK ITS LEGALITY
	 RETERR			;BAD DESIGNATOR
	MOVE T3,DEVCH2(T2)	;GET DIR NUMBER
	JUMPN T3,SPOL2A		;IF SET, RETURN VALUE
	MOVX T1,RC%EMO		;EXACT MATCH ONLY
	HRROI T2,[ASCIZ/PS:<SPOOL>/]	;GET DEFAULT VALUE
	RCDIR			;GET THE DIRECTORY NUMBER
	TXNE T1,RC%NOM!RC%AMB	;NO MATCH OR AMBIGUOUS?
	RETERR (SPLX6)		;YES
SPOL2A:	UMOVEM T3,1(Q1)		;STORE ANSWER
	SMRETN
; Set tab stops

.STABS::MCENT
	CALL CHKTTY
	 JRST MRETN
	UMOVE 1,2
	UMOVE 3,3
	UMOVE 4,4
	CALL TTSTBS
	JRST MRETN
; Set time and date
; Call:	1	; Date and time in standard format
;	STAD
; Return
;	+1	; Can't set because not wheel or opr
;	+2	; Ok

.STAD::	MCENT
	MOVE B,CAPENB
	TRNN B,SC%WHL!SC%OPR
	SKIPGE TADIDT
	JRST STAD1
	MOVEI A,STADX1
	RETERR()

STAD1:	CALL LGTAD		;GET CURRENT DATE/TIME
	MOVEM A,CKPDTL		;SAVE AS LAST DATE/TIME
	UMOVE A,1		;RE-FETCH USER ARG
	MOVE B,TODPWL		;JIFFIES SINCE STARTUP (BY POWERLINE)
	MUL B,[1B17]		;SHIFT BINARY POINT
	DIV B,JFDAY		;COMPUTE DAYS AND FRACTION SINCE STARTUP
	CAML C,JFDAY2		;ROUND
	AOS B
	SUB A,B			;COMPUTE ACTUAL SYSTEM STARTUP TAD
	MOVEM A,TADIDT		;SAVE IT
	SKIPN JOBNO		;IS THIS OTHER THAN JOB 0?
	SMRETN
	CALL DTTIME		;YES. SEND TIME TO ALL 11'S
	MOVEI T1,.USENT		;WRITE ENTRY FUNCTION
	MOVEI T2,TADLST		;ARG LIST
	USAGE			;LOG THIS FACT
	SMRETN

TADLST:	USENT. (.UTTAD,1,1)	;DATE-TIME CHANGE
	USDTL. (CKPDTL)		;OLD DATE/TIME
	0			;END OF LIST
; String to device
; Call:	1	; Device designator
;	STDEV
; Return
;	+1	; Error
;	+2	; Ok
;	2	; Device designator

.STDEV::MCENT
	UMOVE A,1
	CALL STDEV0		;DO THE WORK
	 JRST [	UMOVEM A,2	;RETURN ERROR CODE IN 2
		EMRETN ()]	;GIVE ERROR RETURN
	UMOVEM A,2		;RETURN DEVICE DESIGNATOR
	JRST SKMRTN		;GIVE SKIP RETURN

STDEV0:	CALL CPYFUS
	 RETBAD (GJFX22)	;JSB FULL
	MOVEI D,0		;SEE IF TERMINATED WITH A COLON
	MOVE B,A		;GET POINTER TO STRING
	HRLI B,(POINT 7,0,34)	;MAKE IT INTO A BYTE POINTER
STDEV1:	ILDB C,B		;SCAN FOR A COLON
	CAIE C,":"		;FOUND THE END OF THE DEVICE STRING?
	CAIN C," "		;EITHER COLON OR SPACE IS A TERMINATOR
	SKIPA			;YES, FOUND A TERMINATOR
	JUMPN C,STDEV1		;NO, AT END OF STRING?
	DPB D,B			;YES, PUT A NULL IN ON TOP OF COLON
	PUSH P,A
	SETZ B,			;INDICATE NO DIRECTORY SEARCH
	CALL CHKLND		; GO CHECK FOR A LOGICAL NAME FIRST
	CALL STDEVP		; GO SEE ABOUT A PHYSICAL DEVICE
	 SKIPA			; ERROR CODE IN A
	AOS -1(P)		;GIVE SKIP RETURN
	EXCH A,0(P)		;SAVE ANSWER, RESTORE PNTR
	MOVE B,A		; TO B
	MOVEI A,JSBFRE		;SAY JSB FREE SPACE
	CALL RELFRE		;RELEASE IT
	POP P,A			;RESTORE ANSWER (OR ERROR)
	RET			;RETURN


;ROUTINE TO GET PHYSICAL DEVICE DESIGNATOR
;ACCEPTS IN A/	STRING POINTER TO DEVICE NAME
;	CALL STDEVP
;RETURNS +1:	ERROR - ERROR CODE IN A
;	 +2:	OK, DEVICE DESIGNATOR IN A

STDEVP::CALL DEVLUX		; Look up the device name
	 JRST [	CAIE A,GJFX16
		JRST .+1
		MOVEI A,STDVX1
		RET]		; NO SUCH DEVICE
	HRRZ A,DEVUNT(B)
	HLRZ D,DEVCHR(B)	;GET DEVICE TYPE
	TRZ D,777000		;...
	CAIE A,-1		;SPECIAL CASE OF UNIT #
	CAIE D,.DVDSK		;CHECK FOR DISK (STR)
	JRST STDVP1		;NOT STRUCTURE - GO ON
	HRRZ A,C		;GET UNIQUE CODE
	HRLI A,.DVDES+.DVDSK	;RETURN STR DESIGNATOR
	RETSKP

STDVP1:	HRL A,D			;SET DEVICE TYPE
	TLO A,.DVDES		; SET DEVICE DESIGNATOR CODE
	RETSKP
; Simulate teletype input
; A/ DESIGNATOR (SHOULD BE TTY)
; B/ CHARACTER

.STI::	MCENT
	CALL CHKTTR		;MAKE SURE WE'RE DEALING WITH A TERMINAL
	 ITERR (TTYX1)		;NOT A TERMINAL OR NO SUCH TERMINAL
	MOVE T3,CAPENB		;WHEEL OR OPERATOR CAN DO IT
	TXNE T3,SC%WHL!SC%OPR
	JRST STI2
	MOVEM T2,Q1		;SAVE LINE NUMBER
	NOSKED			;GO NOSKED WHILE LOOKING AT LINE DATA
	CALL STADYN		;POINT TO DYNAMIC DATA
	 ITERR (TTYX01,<OKSKED>) ;NOT ACTIVE. ONLY PRIVILEGED CAN SEND TO IT
	CALL TTCKAD		;ACCEPTING ADVICE?
	 JRST [	CALL CHKTTY	;DO WE HAVE ACCESS?
		 ITERR (DESX2,<OKSKED>) ;NO. RETURN ERROR
		JRST .+1]	;YES. PROCEED
	OKSKED
	MOVE T2,Q1		;GET LINE NUMBER
STI2:	UMOVE T1,T2		;GET CHARACTER
	CALL TTSTI		;PUT CHARACTER IN INPUT BUFFER
	JRST MRETN
; Read fact switch
;ACCEPTS IN 1/	FUNCTION TO BE TESTED
;	TMON
;RETURNS +1:	ALWAYS - VALUE IN AC 2

.TMON::	MCENT
	UMOVE T1,1
	JUMPL T1,TMONER		;CODE MUST BE POSITIVE
	CAIL T1,^D36		;DOES IT FIT IN FLAG WORD?
	JRST TMON2		;NO, SEE IF OTHER CODE IS VALID
	MOVNS T1		;GET MASK
	MOVX T2,1B0
	LSH T2,0(T1)
	TDNN T2,FACTSW		;TEST BIT
TMONZ:	TDZA T1,T1		;BIT NOT SET
TMONO:	MOVEI T1,1		;BIT IS SET
TMONV:	UMOVEM T1,2		;RETURN VALUE
	JRST MRETN		;RETURN TO USER

TMON2:	CAIL T1,^D36+NTMON2	;LEGAL CODE FOR TMON?
TMONER:	ITERR (TMONX1)		;NO
	XCT TMON2T-^D36(T1)	;YES, GET THE VALUE
	JRST TMONV		;NON-SKIP RETURNS A VALUE
	JUMPE T1,TMONZ		;SKIPS RETURN 0 OR 1 ONLY
	JRST TMONO		;RETURN A ONE

;TABLE OF TMON FUNCTIONS

TMON2T:	SKIPA T1,NETON		;CODE 36 - IS NETWORK ON?
	JRST TMONER		;CODE 37 IS WRITE-ONLY
	JRST TMONER		;CODE 38 IS WRITE-ONLY
	MOVE T1,TIMZON		;39-RETURN LOCAL TIME ZONE
	MOVE T1,NLHOST		;40-RETURN LOCAL ARPANET HOST NUMBER
	MOVE T1,AVALON		;41-RETURN ACCOUNT VALIDATION STATUS
	MOVE T1,STSBLK		;42-RETURN VALUE OF STATUS REPORTING
NTMON2==.-TMON2T		;NUMBER OF LEGAL CODES OVER 36
;USAGE JSYS
;	1/ FLAGS,,FUNCTION
;	2/ ADDRS OF PARAMETERS

.USAGE::MOVE T3,FACTSW		;SEE IF ENABLED
	TXNN T3,SF%USG		;???
	JRST MRETN		;NO - JUST RETURN
	HRRZ T3,T1		;GET FUNCTION
	CAILE T3,MXUFN		;VALID?
	ITERR (ARGX02)
	CALL @UFCNTB(T3)	;DISPATCH
	 ITERR ()		;RETURN ERROR
	JRST MRETN		;RETURN

;USAGE FUNCTION TABLE

UFCNTB:	DTBDSP (UFNENT)		; 0 - MAKE ENTRY
	DTBDSP (UFNCLS)		; 1 - CLOSE OUT FILE
	DTBDSP (UFNCKP)		; 2 - PERFORM CHECKPOINT
	DTBDSP (UFNLGI)		; 3 - LOGIN
	DTBDSP (UFNLGO)		; 4 - LOGOUT
	DTBDSP (UFNCHG)		; 5 - SESSION CHANGE
	DTBDSP (UFNCKI)		; 6 - SET CHECKPOINT INTERVAL (MINS)
	DTBDSP (UFNENA)		; 7 - ENABLE ACCOUNT VALIDATION
   MXUFN==.-UFCNTB-1

;ROUTINE TO CHECK FOR PRIVS

USGPRV:	MOVE T2,CAPENB		;GET CAP'S
	MOVE T3,MPP		;LOOK BACK TO CALLERS PC
	MOVE T3,0(T3)		; FLAGS
	TXNE T3,UMODF		;CALLED FROM MONITOR?
	TXNE T2,SC%WHL!SC%OPR	; OR PRIV.
	RETSKP			;OK TO GO ON
	RETBAD (CAPX1)		;NEITHER - FAIL
;DEFINITIONS OF INTERNAL FORMAT OF SYSTEM-DATA FILE

;WORDS 0 & 1 ARE QUEUE HEADERS

DEFSTR (UHTYP,UQDAT+0,17,18)	;TYPE CODE
DEFSTR (UHLEN,UQDAT+0,35,18)	;ENTRY LENGTH
DEFSTR (UHTAD,UQDAT+1,35,36)	;ENTRY DATE/TIME
DEFSTR (UHDRV,UQDAT+2,5,6)	;DEC REVISION #
DEFSTR (UHCRV,UQDAT+2,11,6)	;CUST REVISION #
DEFSTR (UHTMT,UQDAT+2,17,6)	;TERMINAL TYPE CODE
DEFSTR (UHJNO,UQDAT+2,35,18)	;JOB #
DEFSTR (UHPNM,UQDAT+3,35,36)	;PROGRAM NAME (SIXBIT)
DEFSTR (UHPVR,UQDAT+4,35,36)	;PROGRAM VERSION NUMBER (STD FORM)
DEFSTR (UHMVR,UQDAT+5,35,36)	;MONITOR VERSION NUMBER (STD FORM)
DEFSTR (UHJTS,UQDAT+6,0,1)	;BATCH := 1 , T/S := 0
DEFSTR (UHULN,UQDAT+6,5,5)	;USER NAME STRING LEN
DEFSTR (UHSL1,UQDAT+6,11,6)	;STRING LENGTH #1 (ACCOUNT)
DEFSTR (UHSL2,UQDAT+6,17,6)	;STRING LENGTH #2 (SESSION REMARK)
DEFSTR (UHLNO,UQDAT+6,35,18)	;LINE NUMBER
DEFSTR (UHNOD,UQDAT+7,35,36)	;NODE NAME (SIXBIT)

UHNAM==UQDAT+10			;LOC OF FIRST WORD OF USER NAME
UHMIN==UQDAT+20			;MINIMUM ENTRY SIZE (FOR ASGSWP)

USQMAX==^D20			;MAX USAGE QUEUE LENGTH
;RECORD LENGTH TABLE

RECLTB:	0			;0 - ILLEGAL
	MOVEI T1,UHMIN+^D16	;1 - MONITOR RESTART
	MOVEI T1,UHMIN+^D22	;2 - SESSION RECORD
	0			;3 - ILLEGAL
	0			;4 - ILLEGAL
	MOVEI T1,UHMIN+^D2	;5 - DATE/TIME CHANGE
	0			;6 - BATCH PROCESSOR
	MOVEI T1,UHMIN+^D27	;7 - INPUT SPOOLER
	MOVEI T1,UHMIN+^D30	;8 - OUTPUT SPOOLER
	CALL UGETDL		;9 - DISK STORAGE USAGE
	0			;10 - DISK SPINDLE USAGE
	0			;11 - STRUCTURE MOUNT
	0			;12 - MAGTAPE MOUNT
	0			;13 - DECTAPE MOUNT (TOPS10)
	0			;14 - FILE COMMAND (TOPS10)
MXRCTP==.-RECLTB-1

;FORMAT TABLE INDEXED BY RECORD TYPE

UFNFRM:	0			;0 - ILLEGAL
	-UFRSTL,,UFRSTT		;1 - RESTART RECORD
	-UFLOGL,,UFLOGT		;2 - SESSION RECORD
	0			;3 - ILLEGAL
	0			;4 - ILLEGAL
	-UFTADL,,UFTADT		;5 - DATA/TIME CHANGE
	0			;6 - BATCH PROCESSOR
	-UFINPL,,UFINPT		;7 - INPUT SPOOLER
	-UFOUTL,,UFOUTT		;8 - OUTPUT SPOOLER
	-UFDSKL,,UFDSKT		;9 - DISK STORAGE USAGE
	0			;10 - DISK SPINDLE USAGE
	0			;11 - STRUCTURE MOUNT
	0			;12 - MAGTAPE MOUNT
	0			;13 - DECTAPE MOUNT (TOPS10)
	0			;14 - FILE COMMAND (TOPS10)
;TABLE FOR DATE/TIME CHANGE FORM

UFTADT:	[-1],,.USDTL		;DATE/TIME BEFORE CHANGE (MANDATORY)
UFTADL==.-UFTADT

;TABLE FOR SYSTEM RESTART FORM

UFRSTT:	[0,,SVN],,.USSNM	;SYSTEM NAME
	[EXP SVNM],,.USMVR	;MONITOR VERSION NUMBER
	SYSTAD,,.USMBD		;MONITOR BUILD DATE/TIME
	APRSER,,.USCP0		;SERIAL NUMBER (CPU0)
	[-1],,.USLCK		;DATE/TIME LAST CHECKPOINT (MAND.)
UFRSTL==.-UFRSTT

;TABLE OF SESSION RECORD ITEMS

UFLOGT:	[0,,ACCTSR],,.USACT	;ACCOUNT STRING
	[0,,JSSRM+1],,.USCOM	;SESSION REMARK
	CTIMON,,.USSST		;SESSION START TIME
	CONCON,,.USCCT		;CONSOLE CONNECT TIME
	JBRUNT,,.USRTM		;RUNTIME
	JBBNAM,,.USBJN		;BATCH JOB NAME
	JBBSEQ,,.USBSN		;BATCH SEQUENCE NUMBER
UFLOGL==.-UFLOGT		;LENGTH OF TABLE

CKOFF==:-UFLOGL+2		;OFFSET FROM END OF DATA FOR
				;BEGINNING OF CHECKPOINT DATA
CKITMS==:3			;NUMBER OF CHECKPOINT ITEMS

;TABLE FOR DISK USAGE STATISTICS

UFDSKT:	[-1],,.USSTR		;STRUCTURE NAME
	[-1],,.USDIR		;DIRECTORY NAME
	[-1],,.USNRF		;NUMBER OF ACCOUNTS
	[-1],,.USTUS		;TOTAL SPACE USED
	[-1],,.USTNF		;TOTAL NUMBER OF FILES
	[-1],,.USLIQ		;LOGGED IN QUOTA
	[-1],,.USLOQ		;LOGGED OUT QUOTA
	[-1],,.USLLI		;DATE/TIME LAST LOGIN
	[-1],,.USDSX		;STRUCTURE/DIRECTORY INFO WORD (SPECIAL)
	[-1],,.USDST		;DISK STATISTICS TABLE
UFDSKL==.-UFDSKT
;TABLE FOR INPUT SPOOLER RECORD (NO DEFAULTS)

UFINPT:	[-1],,.USACT		;ACCOUNT STRING
	[-1],,.USTXT		;SYSTEM/OPERATOR TEXT
	[-1],,.USSRT		;SPOOLER RUNTIME
	[-1],,.USSDR		;DISK READS
	[-1],,.USSDW		;DISK WRITES
	[-1],,.USJNM		;JOB NAME
	[-1],,.USQNM		;QUEUE NAME
	[-1],,.USSDV		;ACTUAL INPUT DEVICE
	[-1],,.USSSN		;SEQUENCE NUMBER
	[-1],,.USSUN		;SPOOLER UNITS (CARDS)
	[-1],,.USCRT		;DATE/TIME OF REQUEST
	[-1],,.USDSP		;DISPOSITION
	[-1],,.USPRI		;PRIORITY
UFINPL==.-UFINPT

;TABLE FOR OUTPUT SPOOLER RECORD (NO DEFAULTS)

UFOUTT:	[-1],,.USACT		;ACCOUNT STRING
	[-1],,.USTXT		;SYSTEM/OPERATOR TEXT
	[-1],,.USSRT		;SPOOLER RUNTIME
	[-1],,.USSDR		;DISK READS
	[-1],,.USSDW		;DISK WRITES
	[-1],,.USJNM		;JOB NAME
	[-1],,.USQNM		;QUEUE NAME
	[-1],,.USSDV		;ACTUAL OUTPUT DEVICE
	[-1],,.USSSN		;SEQUENCE NUMBER
	[-1],,.USSUN		;SPOOLER UNITS (OUTPUT)
	[-1],,.USCRT		;DATE/TIME OF REQUEST
	[-1],,.USDSP		;DISPOSITION
	[-1],,.USPRI		;PRIORITY
	[-1],,.USSNF		;NUMBER OF FILES PROCESSED
	[-1],,.USSCD		;SCHEDULED DATE/TIME
	[-1],,.USFRM		;FORMS TYPE
UFOUTL==.-UFOUTT
;PASS SPECIAL FUNCTION TO JOB 0 AND WAIT

UFNCLS:
UFNCKP:	CALL USGPRV		;VALIDATE PRIVS
	 RETBAD ()
UFNCK1:	NOINT			;BEST TO BE NOINT
	MOVEI T1,2		;GET 2 WORDS
	CALL ASGSWP		;FROM SWAPPABLE FREE SPACE
	 JRST [	CALL ASGWAT	;WAIT FOR STORAGE
		JRST UFNCK1]	;TRY AGAIN
	XCTU [HRRZ T2,1]	;RE-FETCH USER FUNCTION
	STOR T2,UQFCN,(T1)	;SAVE IN BLOCK
	LOCK (USGLOK)		;WANT DATA BASE LOCKED FOR THIS FCN
	CALL ONUSQ		;QUEUE UP MESSAGE
	OKINT
	AOS JB0FLG		;POKE JOB 0 FOR THESE
	MOVEI T1,USGWAT		;WAIT TILL FUNCTION DONE!
	MDISMS			;DISMISS
	RETSKP			;GOOD RETURN

;RESIDENT SCHEDULAR TEST TO WAIT FOR JOB 0 TO DO FUNCTION

	RESCD

USGWAT:	SKIPL USGLOK		;UNLOCKED?
	JRST 0(4)		;NO - WAIT SOME MORE
	JRST 1(4)		;YES - WAKEUP

	SWAPCD

;JACKET ROUTINE TO ENABLE ACCOUNT VALIDATION

UFNENA:	MOVE T1,CAPENB		;GET ENABLED CAPABILITIES
	TXNN T1,SC%WHL!SC%OPR	;WHOPER DOING THIS?
	ITERR (CAPX1)		;NO, RETURN ERROR
	CALL ENACT		;GO DO THE WORK
	 RETBAD ()
	RETSKP			;GIVE SUCCESSFUL RETURN
;ROUTINE TO SET CHECKPOINT INTERVAL

UFNCKI:	UMOVE T1,2		;GET USER ARGUMENT
	IMULI T1,^D60000	;CONVERT TO MS
	MOVEM T1,CKPINV		;SET INTERVAL
	RETSKP			;GOOD RETURN

;WRITE ENTRY INTO USAGE FILE

UFNENT:	CALL UFNINI		;BUILD HEADER
	 RETBAD ()		;ERROR
	LOAD T1,UHTYP,(Q1)	;GET ENTRY TYPE CODE
UFNEN0:	CAIL T1,.UTUSR		;USER-DEFINED ENTRY TYPE?
	 JRST [	CALL UFNFAR		;YES-- FILL ARBITRARY RECORD BLOCK
		 JRST UFNINX		;ERROR-- RETURN TO USER
		JRST UFNEN1]		;ENTRY ALL FINISHED-- PUT ON QUEUE
	MOVE T1,UFNFRM(T1)	;GET FORM POINTER
	CALL UFNFIL		;FILL IN FORM
	 JRST UFNINX		;MISSING ITEM
UFNEN1:	MOVE T1,Q1		;POINT TO RECORD FOR QUEUE
	CALL ONUSQ		;ENQUE MESSAGE
	OKINT			;DONE
	RETSKP			;...

;COMMON ROUTINE TO HANDLE ALL JOB LOGGING

UFNLGI:
UFNLGO:
UFNCHG:	SKIPN JOBNO		;IGNORE FOR JOB 0
	RETSKP
	CALL UFNINI		;INIT BLOCK
	 RETBAD ()		;PASS ERROR UP
	MOVEI T1,.UTSEN		;SESSION ENTRY TYPE CODE
	CALLRET UFNEN0		;FILL IN REMAINDER AND QUEUE IT
;ROUTINE TO FILL RECORD FROM TABLE SPECIFIED
;CALL:	T1/ -LEN,,TABLE-BEG
;	Q1/ POINTER TO BEGINNING OF BUFFER
;	Q2/ POINTER TO USER'S RECORD DESCRIPTOR BLOCK
;	Q3/ POINTER TO FIRST FREE DATA ITEM
;
;COPY DATA INTO BUFFER AND UPDATE HEADER TO SHOW LENGTH
;RETURN WITH Q3 UPDATED TO END OF BLOCK

UFNFIL:	TRVAR <UFCHI,STRLX>
	SETOM STRLX		;INIT INDEX
	MOVE T4,T1		;COPY TO T4
UFNFL1:	MOVEM T4,UFCHI		;SAVE INDEX
	HRRZ T1,0(T4)		;FETCH ITEM CODE
	HLRZ T2,0(T4)		;ADDRS OF DEFAULT ITEM
	MOVE T2,0(T2)		;SETUP DEFAULT
	CALL UFWFET		;GET WORD
	 RETBAD ()		;PASS UP ERROR
	LDB T3,[POINTR (T1,US%TYP)] ;GET DATA TYPE
	CAILE T3,MXUITP		;MAX USAGE ITEM TYPE?
	RETBAD (USGX03)		;ILLEGAL USAGE ITEM TYPE
	CALL @UTYPTB(T3)	;FILL IN DATA ITEM
	 RETBAD ()		;PASS ERROR UP
	MOVE T4,UFCHI		;RESTORE INDEX
	AOBJN T4,UFNFL1		;LOOP TILL ALL DONE

;HERE WHEN ALL DONE FILLING THE ENTRY

UFNFIE:	MOVE T1,Q3		;COPY POINTER
	SUBI T1,1(Q1)		;ACTUAL DATA LENGTH
	STOR T1,UHLEN,(Q1)	;STORE IN RECORD
	MOVE T1,UQDAT(Q1)	;COPY HEADER
	MOVEM T1,0(Q3)		;TO LAST WORD
	RETSKP

;STRING LENGTH TABLE

STRLNT:	STOR T2,UHSL1,(Q1)	;STORE IN STRING LEN #1
	STOR T2,UHSL2,(Q1)	;STORE IN STRING LEN #2

;USAGE ITEM TYPE TABLE

UTYPTB:	DTBDSP (UFLASC)		;0 - STRING
	DTBDSP (UFLSIX)		;1 - SIXBIT WORD
	DTBDSP (UFLOCT)		;2 - OCTAL WORD
	DTBDSP (UFLDEC)		;3 - DECIMAL WORD
	DTBDSP (UFLDAT)		;4 - DATE/TIME WORD
	DTBDSP (UFLTAB)		;5 - TABLE (SPECIAL)
	DTBDSP (UFLVER)		;6 - VERSION NUMBER
	DTBSKP			;7 - SPACE FILL (SKIP)
   MXUITP==.-UTYPTB-1
;ROUTINE TO STORE FULL WORDS
;T2 / DATA WORD

UFLVER:
UFLOCT:
UFLDEC:
UFLDAT:	MOVEM T2,0(Q3)		;SAVE WORD IN BUFFER
	AOJA Q3,RSKP		;ADVANCE POINTER AND RETURN

;ROUTINE TO STORE STRING
;T2 / STRING POINTER

UFLASC:	TLCE T2,-1		;CHECK FOR 0,,ADDRS
	TLC T2,-1		;NO - MUST BE BPNTR
	CALL UFCPY0		;COPY STRING INTO BLOCK
	 RET
	AOS T1,STRLX		;STEP INDEX
	XCT STRLNT(T1)		;STORE LENGTH
	RETSKP			;GOOD RETURN

;ROUTINE TO FILL IN TABLE INFO
;T2 / TABLE BASE ADDRS

UFLTAB:	ACVAR <Q1,Q2>		;SAVE Q1,Q2
	STKVAR <TBLCNT,TBLSTO>
	MOVE Q2,T2		;SAVE BASE ADDRS
	UMOVE T1,0(Q2)		;FETCH TABLE HEADER
	HRRZ T2,T1		;GET LENGTH OF ADDITIONAL ITEMS
	MOVNM T2,TBLCNT		;SAVE NEG COUNT
	HLRZ Q1,T1		;GET LENGTH OF TABLE

UFLTB1:	MOVEM Q3,TBLSTO		;SAVE ADDRS OF STRING LENGTH
	AOS Q3			;STEP TO NEXT LOC
	UMOVE T3,1(Q2)		;FETCH WORD FROM TABLE
	HRRZ T2,T3		;ADDRESS OF DATA ITEMS
	HRL T2,TBLCNT		;FORM -N,,ADDRS
UFLTB2:	UMOVE T1,0(T2)		;GET ITEM
	MOVEM T1,0(Q3)		;STORE IN BUFFER
	AOS Q3			;ADVANCE TO NEXT LOC
	AOBJN T2,UFLTB2		;LOOP OVER ALL ITEMS
	HLRO T2,T3		;GET POINTER TO STRING
	CALL UFCPY0		;COPY TO BUFFER
	 JFCL
	HRRZM T2,@TBLSTO	;STASH LENGTH
	AOS Q2			;STEP TO NEXT LOC
	SOJG Q1,UFLTB1		;LOOP OVER TABLE
	RETSKP			;DONE
;ROUTINE TO GET SIXBIT ARGUMENT, MAY BE POINTER TO AN ASCIZ STRING

UFLSIX:	HLRZ T1,T2		;CHECK FOR POINTER
	CAIE T1,-1
	CAIN T1,(POINT 7,,)
	JRST UFLSX0		;STRING - COPY IT FIRST
UFLSXX:	MOVEM T2,0(Q3)		;STORE WORD
	AOJA Q3,RSKP		;AND GIVE GOOD RETURN

;ASCIZ STRING POINTER - CONVERT TO SIXBIT

UFLSX0:	STKVAR <SIXBP>
	MOVE T1,T2		;COPY POINTER
	HRLI T1,(POINT 7,,)
	MOVEI T4,6		;MAX 6 CHARS
	SETZ T2,		;CLEAR ANSWER
	MOVE T3,[POINT 6,T2]
	MOVEM T3,SIXBP		;INIT OUTPUT BP
UFLSX1:	XCTBU [ILDB T3,T1]	;FETCH A CHAR
	JUMPE T3,UFLSXX		;DONE IF NULL
	SUBI T3,40		;CONVERT TO SIXBIT
	IDPB T3,SIXBP		;SAVE IN RESULT
	SOJG T4,UFLSX1		;LOOP TILL DONE
	JRST UFLSXX		;STORE RESULT
; UFNFAR -- FILL ARBITRARY RECORD FOR USER ENTRY TYPE
; 
; CALL:
;	Q1/ POINTER TO BEGINNING OF BUFFER
;	Q2/ POINTER TO USER'S RECORD DESCRIPTOR BLOCK
;	Q3/ POINTER TO FIRST FREE DATA ITEM
;
; RETURNS:
;	+1:	ERROR, CODE IN T1
;	+2:	SUCCESS, ENTRY READY TO PUT ON QUEUE
;
; DESTROYS T1-T4, Q3

UFNFAR:	CALL UFNFNA		;FIND THE "ARBITRARY RECORD TYPE" ITEM
				; RETURNS USER ADDRESS IN T3

;FORM AOBJN POINTER TO REMAINING DATA BLOCK IN Q3

	LOAD T1,UQLEN,(Q1)	;GET LENGTH OF DATA BLOCK
	ADD T1,Q1		;FIND END OF BLOCK
	SUBM Q3,T1		;GET -VE WORDS LEFT TO FILL IN T1
	HRL Q3,T1		;FORM AOBJN POINTER IN Q3

;LOOP THROUGH THE USER'S RECORD DESCRIPTOR BLOCK (T3) FOR ALL ITEMS
; AND STORE THEM IN DATA BLOCK (Q3)

UFNFA1:	UMOVE T1,0(T3)		;GET ITEM TYPE WORD
	JUMPE T1,UFNFIE		;END-- ALL DONE, COMPUTE LENGTH AND RETURN +2 FROM UFNFAR
	JUMPGE Q3,[RETBAD (ARGX05)] ;IF NO ROOM-- RDB MUST HAVE GROWN!!
	MOVEM T1,0(Q3)		;STORE THE ITEM TYPE WORD IN THE DATA BLOCK
	AOBJN Q3,.+1		;COUNT THAT WORD IN DATA BLOCK
	ADDI T3,2		;POINT TO NEXT USER ENTRY NOW

	LDB T4,[POINTR (T1,US%TYP)] ;EXTRACT ITEM TYPE
	CAIN T4,.USSPC		;SPACE FILL?
	 JRST UFNFA1		;YES-- NO DATA FOR THIS
	UMOVE T2,-1(T3)		;GET USER'S DATA WORD OR POINTER
	CAMN T2,[EXP -1]	;USER WANT DEFAULT VALUE FOR THIS ITEM?
	 RETBAD (USGX03)	;YES-- THERE ARE NO DEFAULTS IN ARBITRARY ENTRIES
	CAIN T4,.USASC		;ASCII STRING?
	 JRST UFNFA5		;YES-- MUST COPY WHOLE STRING

;ALL OTHER DATA TYPES ARE EXACTLY ONE WORD-- GET THE WORD AND PUT IT AWAY

	TXNE T1,US%IMM		;IMMEDIATE MODE DATA ITEM?
	 JRST UFNFA3		;YES-- WE HAVE THE DATA ITEM IN T2
	MOVX T2,<MOVE T2,@0>	;NO-- MUST PERFORM INDIRECT FETCH
	HRRI T2,-1(T3)		; VIA THE USER'S DATA WORD POINTER
	XCTUU T2		;FETCH USER'S DATA WORD TO T2
UFNFA3:	JUMPGE Q3,[RETBAD (ARGX05)] ;IF NO ROOM-- RDB MUST HAVE GROWN!!
	MOVEM T2,0(Q3)		;STORE THE USER'S DATA WORD IN DATA BLOCK
	AOBJN Q3,.+1		;COUNT THAT WORD IN DATA BLOCK
	JRST UFNFA1		;LOOP FOR ALL ITEMS

;ASCII STRING ITEM-- COPY THE ENTIRE STRING TO THE DATA BLOCK

UFNFA5:	LDB T1,[POINTR (T1,US%LEN)] ;GET LENGTH OF STRING IN BYTES
	ADDI T1,4		;ROUND UP
	IDIVI T1,5		; TO FULL WORDS
	UMOVE T2,-1(T3)		;GET ADDRESS OF STRING
UFNFA6:	JUMPLE T1,UFNFA1	;DONE IF NO MORE USER WORDS LEFT, GET NEXT ITEM
	UMOVE T4,0(T2)		;GET WORD FROM USER'S STRING
	ADDI T2,1		;BUMP USER STRING ADDRESS
	JUMPGE Q3,[RETBAD (ARGX05)] ;IF NO ROOM-- RDB MUST HAVE GROWN!!
	MOVEM T4,0(Q3)		;STORE IT IN DATA BLOCK
	AOBJN Q3,.+1		;COUNT THAT WORD IN DATA BLOCK
	SOJA T1,UFNFA6		;COUNT DOWN WORD COUNT, LOOP FOR ENTIRE STRING
;ROUTINE TO SETUP BLOCK OF STORAGE AND FILL IN HEADER INFO
;RETURNS: +1 ERROR CODE IN T1
;	  +2 NOINT
;	Q1/	STORAGE BLOCK FROM ASGSWP
;	Q2/	POINTER TO USER'S ARGLST
;	Q3/	POINTER TO FIRST FREE WORD IN BLOCK

UFNINI:	CALL USGPRV		;CHECK PRIVS
	 RETBAD ()
UFNIN0:	UMOVE Q2,2		;GET CALLER ARGS
	XCTU [HRRZ T2,0(Q2)]	;GET RECORD TYPE CODE
	CAIG T2,MXRCTP		;VALIDATE
	SKIPN T1,RECLTB(T2)	;SKIP IF VALID TYPE CODE
	 JRST [	CAIL T2,.UTUSR		;MAYBE IT'S A USER ENTRY 5000-9999
		CAILE T2,^D9999		; . . ?
		 RETBAD (USGX01)	;NO-- REALLY INVALID ENTRY TYPE
		CALL UFNINS		;USER ENTRY TYPE-- COMPUTE LENGTH
		JRST UFNI01]		;LENGTH OF USER ENTRY NOW IN T1
	XCT T1			;RETURNS LENGTH IN T1
UFNI01:	NOINT			;BEST BE NOINT
	MOVE T2,USQCNT		;SEE IF OVER QUEUE QUOTA
	CAIGE T2,USQMAX		;...
	CALL ASGSWP		;ALLOCATE STORAGE
	 JRST [	CALL ASGWAT	;WAIT FOR SOME
		JRST UFNIN0]	;START OVER
	MOVE Q1,T1		;SAVE POINTER TO BLOCK
	XCTU [HRRZ T1,1]	;GET USER FUNCTION AGAIN
	STOR T1,UQFCN,(Q1)	;STORE IN QUEUE HEADER
	UMOVE T2,0(Q2)		;GET ARG HEADER
	STOR T2,UHTYP,(Q1)	;STORE TYPE IN BLOCK
	LDB T1,[POINT 9,T2,8]	;GET DEC REV
	STOR T1,UHDRV,(Q1)
	LDB T1,[POINT 9,T2,17]	;GET CUST REV
	STOR T1,UHCRV,(Q1)
	GTAD			;CURRENT DATE/TIME
	STOR T1,UHTAD,(Q1)
	MOVE T1,JOBNO		;JOB NUMBER
	STOR T1,UHJNO,(Q1)
	SETZRO UHNOD,(Q1)	;NODE (ZERO FOR NOW)
	MOVE T1,[EXP SVNM]	;MONITOR VERSION NUMBER
	STOR T1,UHMVR,(Q1)
	MOVEI Q3,0		;INIT TO ZERO
	STOR Q3,UHJTS,(Q1)
	MOVE T1,CTRLTT		;CONTROLLING TERMINAL
	STOR T1,UHLNO,(Q1)	;SAVE
	JUMPL T1,[MOVEI Q3,'D'	;SAY DETACHED
		  JRST UFNIN1]
	CAMN T1,CTYLNO		;CTY?
	MOVEI Q3,'C'		;YES
	CAMGE T1,CTYLNO		;REAL TTY
	MOVEI Q3,'T'		;YES
	CALL PTYGBB		;SEE IF PTY
	 JRST [	SKIPN Q3	;ANYTHING?
		MOVEI Q3,'U'	;NO - UNKNOWN
		JRST UFNIN1]	;PROCEDE
	MOVEI Q3,'P'		;SAY ITS A PTY
	STOR T1,UHJTS,(Q1)	;STORE BATCH/TS FLAG
	;..
	;..

UFNIN1:	STOR Q3,UHTMT,(Q1)	;STORE TERMINAL TYPE CODE
	MOVEI T1,.USJTY		;JOB TYPE CODE
	LOAD T2,UHJTS,(Q1)	;USE DEFAULT
	CALL UFWFET		;GET ARG IF SUPPLIED
	 JRST [	CAIE T1,USGX02	; USE DEFAULT IF ITEM NOT FOUND
		JRST UFNINX	; ELSE ERROR
		JRST .+1]
	STOR T2,UHJTS,(Q1)	;NOW STORE ACTUAL WANTED
	MOVEI T1,.USPNM		;CALLING PROGRAM NAME
	MOVE T2,JOBNO		;DEFALUT TO SYSTEM NAME
	MOVE T2,JOBPNM(T2)	;...
	CALL UFWFET		;FIND ENTRY & FETCH
	 JRST [	CAIE T1,USGX02	;USE DEFAULT IF ITEM NOT FOUND
		JRST UFNINX	;ERROR EXIT
		JRST .+1]
	STOR T2,UHPNM,(Q1)	;STORE
	MOVEI T1,.USPVR		;PROGRAM VERSION
	MOVEI T2,0		;DEFAULT NONE
	CALL UFWFET
	 JRST [	CAIE T1,USGX02	;USE DEFAULT IF ITEM NOT FOUND
		JRST UFNINX	;ERROR EXIT
		JRST .+1]
	STOR T2,UHPVR,(Q1)	;STORE
	MOVEI T1,.USNM2		;USER NAME
	MOVEI T2,USRNAM+1	;DEFAULT
	MOVEI Q3,UHNAM(Q1)	;POINT TO NAME STRING ADDRS
	CALL UFCPYU		;COPY STRING
	 JRST [	CAIE T1,USGX02	;USE DEFAULT IF ITEM NOT FOUND
		JRST UFNINX	;ERROR EXIT
		CALL UFCPY0	;USE DEFAULT (IN T2)
		 JFCL		;WONT HAPPEN
		JRST .+1]
	STOR T2,UHULN,(Q1)	;STORE LENGTH
	RETSKP			;RETURN

;ERROR EXIT WITH OKINT (CODE IN T1)

UFNINX:	PUSH P,T1		;SAVE CODE
	MOVE T1,Q1		;POINT TO BLOCK
	LOAD T2,UQLEN,(T1)	;SETUP SIZE
	CALL RELSWP		;RELEASE SPACE
	OKINT			;ALLOW INTS
	POP P,T1		;RESTORE CODE
	RETBAD ()
; UFNINS -- COMPUTE DATA BLOCK LENGTH FOR ARBITRARY USER ENTRIES 5000-9999
;
; CALL:
;	Q2/	POINTER TO USER'S RECORD DESCRIPTOR BLOCK
;
; RETURNS:
;   +1:	ALWAYS
;	T1/	SIZE OF DATA BLOCK NEEDED (FOR ASGSWP)
;
; DESTROYS T1-T4

UFNINS:	CALL UFNFNA		;FIND FIRST ARBITRARY RECORD ITEM, USER ADDRESS IN T3
	MOVX T4,UHMIN+1		;START COUNT WITH REQUIRED PART OF DATA BLOCK

;LOOP THROUGH USER'S RECORD DESCRIPTOR BLOCK AND COUNT THE SIZE OF EACH ENTRY IN T4

UFNIS1:	UMOVE T1,0(T3)		;GET ITEM TYPE CODE WORD
	JUMPE T1,UFNIS9		;ZERO MEANS END-- COMPUTE SIZE AND RETURN
	ADDI T4,1		;COUNT THE ITEM TYPE WORD
	ADDI T3,2		;STEP TO NEXT USER ITEM NOW

	LDB T2,[POINTR (T1,US%TYP)] ;GET ITEM DATA TYPE
	CAIN T2,.USSPC		;SPACE FILL?
	 JRST UFNIS1		;YES-- NO DATA WORD FOR THIS
	CAIE T2,.USASC		;ASCII STRING?
	 AOJA T4,UFNIS1		;NO-- DATA IS EXACTLY ONE WORD, SO COUNT AND GET NEXT ITEM

;ASCII STRING-- SIZE IN WORDS IS ( <LENGTH IN BYTES> + 4 ) / 5

	LDB T1,[POINTR (T1,US%LEN)] ;GET LENGTH IN BYTES
	ADDI T1,4		;ROUND UP
	IDIVI T1,5		; TO FULL WORDS
	ADD T4,T1		;COUNT THE STRING LENGTH
	JRST UFNIS1		;LOOP FOR NEXT ITEM

;END OF BLOCK-- RETURN LENGTH IN T1

UFNIS9:	MOVE T1,T4		;COPY LENGTH
	RET			;RETURN +1 FROM UFNINS


; UFNFNA -- FIND FIRST ARBITRARY RECORD ENTRY
; CALL:	Q2/	POINTER TO USER RECORD DESCRIPTOR BLOCK
; RETURNS:
;  +1:	T3/	POINTER TO USER'S ARBITRARY RECORD DESCRIPTOR
; DESTROYS T1-T4

UFNFNA:	MOVE T3,Q2		;COPY BEGINNING OF USER REC DESC BLK
UFNFN1:	UMOVE T1,0(T3)		;GET AN ITEM CODE WORD
	JUMPE T1,UFNFN9		;ZERO IS END-- RETURN NOW
	LDB T2,[POINTR (T1,US%COD)] ;GET ITEM CODE
	CAIE T2,.USUAR		;ARBITRARY RECORD DELIMITER?
	 JRST [	ADDI T3,2		;NO-- BUMP TO NEXT ITEM
		JRST UFNFN1]		; AND GO ON LOOKING
UFNFN9:	RET			;YES-- RETURN FROM UFNFNA
;ROUTINE TO COPY STRING ARGUMENT INTO USAGE BLOCK
; CALL:	T1/	ITEM CODE
;	T2/	DEFAULT STRING PNTR
;	Q3/	DEST ADDRS
;
;RETURN +1	ERROR
;	+2	LENGTH IN T2, UPDATED ADDRS IN Q3

UFCPYU:	CALL UFWFET		;GET WORD (SHOULD BE POINTER)
	 RETBAD ()		;PASS ERROR UP
UFCPY0:	MOVEI T1,-1(Q3)		;POINT TO DESTINATION ADDRS
	TLNN T2,-1		;MAYBE 0,,ADDRS
	JRST UFCPY2		;YES - STRING IN MONITOR SPACE
	CALL CPYFU1		;COPY STRING FROM USER SPACE
	 JFCL			;CANT HAPPEN
UFCPYX:	IBP T2			;ADVANCE TO NULL
	MOVEI T1,1(T2)		;POINT TO WORD AFTER STRING
	SUBI T2,-1(Q3)		;NUMBER OF FULL WORDS
	MOVE Q3,T1		;RETURN UPDATED POINTER IN Q3
	RETSKP			;GOOD RETURN

UFCPY2:	HRLI T1,(<POINT 7,,35>)	;DESTINATION BP
	HRLI T2,(<POINT 7,,>)	;SOURCE BP
	SETZ T3,		;TERMINATE ON NULL
	SOUT			;COPY STRING
	MOVE T2,T1		;RETURN UPDATED STRING IN T2
	JRST UFCPYX		;COMMON EXIT

;ROUTINE TO FETCH LENGTH OF DISK USAGE BLOCK

UGETDL:	MOVEI T1,.USDST		;LOOK FOR THIS ITEM TYPE
	SETO T2,		;NO DEFAULT
	CALL UFWFET		;...
	 JRST [	MOVEI T1,UHMIN+^D24
		RET]		;RETURN DEFAULT
	UMOVE T3,0(T2)		;FETCH TABLE HEADER
	HRRZ T1,T3		;NUMBER OF DATA ITEMS PER ENTRY
	ADDI T1,MAXLW+1		; PLUS MAX STRING LENGTH+1
	HLRZS T3		;NUMBER OF TABLE ENTRIES
	IMUL T1,T3		;TOTAL ITEMS (MAX STORAGE)
	ADDI T1,UHMIN+^D24	; PLUS FIXED AMOUNT
	RET			;RETURN
;ROUTINE TO FIND ENTRY IN CALLER'S LIST
;   T1/ DESIRED ARG TYPE CODE
;RETURNS:  T1/ ITEM DESC
;	   T2/ DATA ENTRY
;	   T3/ POINTER TO ENTRY

USFFND:	MOVE T3,Q2		;COPY ARG BLOCK ADDRS
	MOVE T4,T1		;COPY ARG TO T4
USFFN1:	UMOVE T1,1(T3)		;FETCH ARG
	JUMPE T1,[RETBAD (USGX02)] ;NOT FOUND
	ADDI T3,2		;POINT TO DATUM
	LDB T2,[POINTR (T1,US%COD)] ;GET ITEM CODE
	CAME T2,T4		;CHECK MATCH
	JRST USFFN1		;NO - LOOP
 	UMOVE T2,0(T3)		;RETURN 2ND WORD
	CAMN T2,[-1]		;-1 GIVEN
	TXO T1,US%IMM		;YES - SET IMMED FLAG
	RETSKP			;GOOD RETURN

;ROUTINE TO FETCH WORD ITEM FROM ARGLIST (RETURN IN T2)
; CALL:	T1/ ITEM CODE
;	T2/ DEFAULT VALUE

UFWFET:	STKVAR <DFLT>
	MOVEM T2,DFLT		;SAVE DEFAULT VALUE
	CALL USFFND		;FIND ITEM
	 RETBAD (,<MOVE T2,DFLT>)
	LDB T4,[POINTR (T1,US%TYP)]
	TXNN T1,US%IMM		;IMMEDIATE CODE?
	CAIN T4,.USASC		;STRING TYPE?
	JRST UFWFT1		;YES - DONT FETCH WORD
	HRLI T3,(<MOVE T2,@0>)	;NO - FORM INDIRECT FETCH
	XCTUU T3		; AND GET ACTUAL VALUE
UFWFT1:	CAME T2,[-1]		;WANT DEFAULT?
	RETSKP			;NO - GOOD RETURN
	MOVE T2,DFLT		;YES - GET IT
	CAMN T2,[-1]		;DEFAULT ALLOWED?
	RETBAD (USGX03)		;NO RETURN ERROR
	RETSKP			;RETURN

;ROUTINE TO WAIT A BIT FOR FREE STORAGE

ASGWAT:	OKINT			;ALLOW INTS
	AOS JB0FLG		;POKE JOB 0
	MOVEI T1,^D1000		;WAIT 1 SEC
	DISMS
	RET			;RETURN
;ROUTINE TO QUEUE UP MESSAGE FOR JOB 0
; T1/ ADDRS OF MESSAGE

ONUSQ:	NOSKED			;PREVENT RACES
	AOS USQCNT		;INCREMENT
	SETZRO UQLNK,(T1)	;MARK END OF QUEUE
	MOVE T2,USGEND		;GET END POINTER
	STOR T1,UQLNK,(T2)	;STORE LINK TO NEXT ITEM
	MOVEM T1,USGEND		;NEW POINTER
	OKSKED
	RET			;RETURN

;ROUTINE TO REMOVE TOP ITEM FROM Q

OFFUSQ::NOSKED			;INTERLOCK
	SOS USQCNT		;DECREMENT
	SKIPN T1,USGBEG		;ANYTHING ON QUEUE?
	 JRST [	OKSKED			;NO--
		RET]			; JUST RETURN
	LOAD T2,UQLNK,(T1)	;GET POINTER TO NEXT
	MOVEM T2,USGBEG		;STORE NEW HEAD
	JUMPN T2,OFFUS1		;JUMP IF MORE ON LIST
	MOVEI T2,USGBEG-1	;RESET END
	MOVEM T2,USGEND		; ...
OFFUS1:	OKSKED			;ALLOW SCHED
	LOAD T2,UQLEN,(T1)	;GET LENGTH
	CALLRET RELSWP		;RELEASE BLOCK AND RETURN
; ENABLE ACCOUNT VALIDATION
; RETURNS: +1	ERROR, ERROR CODE IN AC1
;	   +2	SUCCESS

ENACT::STKVAR <<ENFDB,3>,ENJFN>
	LOCK ACTLCK
	MOVE T1,ACTOFN		;ACCOUNT DATA BASE OFN
	CAMN T1,[-1]		;IS AN OFN ASSIGNED YET?
	JRST ENAC0		;NO, JUST CONTINUE
	SETZ T1,		;UNMAP PAGE WITH HASH TABLE
	HRRZI T2,HSHPG
	CALL SETMPG
	SETZ T1,		;UNMAP ACCOUNT WINDOW PAGE
	HRRZI T2,ACTPG
	CALL SETMPG
	SETOM ACTPGN		;NO ACCT WINDOW PAGE MAPPED IN NOW
	MOVE T1,ACTOFN
	CALL RELOFN		;RELEASE THE OFN
	CAMGE T1,[-1]		;IS THE FILE COMPLETELY CLOSED?
	RETBAD (ENACX1,<UNLOCK ACTLCK>)	;NO, ERROR
	SETOM ACTOFN		;NOW WE HAVE NO OFN FOR ACCT DATA BASE

ENAC0:	MOVX T1,GJ%OLD+GJ%SHT+.GJDEF
	HRROI T2,[ASCIZ/PS:<SYSTEM>ACCOUNTS-TABLE.BIN/]
	GTJFN			;GET JFN FOR MOST RECENT DATA BASE
	 RETBAD (ENACX2,<UNLOCK ACTLCK>)
	MOVEM T1,ENJFN		;SAVE JFN FOR NOW
	MOVX T2,<3,,.FBCTL>	;GET FDB STATUS WORD AND XB DISK ADDRESS
	MOVEI T3,ENFDB		;PLACE TO PUT FDB INFO
	GTFDB
	 ERJMP ENACX		;CATCH ANY ERRORS
	MOVE T1,ENFDB		;EXAMINE FILE STATUS
	TXNE T1,FB%LNG		;IS IT A LONG FILE?
	RETBAD (ENACX3,<UNLOCK ACTLCK>)
	MOVEI T1,ENFDB
	MOVE T1,2(T1)		;GET XB DISK ADDRESS
	MOVEI T2,PSNUM		;AND STRUCTURE # OF PS:
	MOVEI T3,SYSTDN		;DIR # OF <SYSTEM>
	MOVE T4,[377777,,777777] ;INFINITE REMAINING QUOTA
	CALL ASGOFN		;GET AN OFN FOR THE DATA BASE
	 RETBAD (ENACX4,<UNLOCK ACTLCK>)
	MOVEM T1,ACTOFN		;SAVE THE NEW OFN
	HRLZS T1		;OFN,, PAGE ZERO
	MOVX T2,PM%RD		;READ ACCESS TO THE HASH PAGE
	HRRI T2,HSHPG
	CALL SETMPG		;MAP IN THE HASH TABLE AT HSHPG
	MOVE T1,ENJFN		;GET JFN FOR FILE
	RLJFN			;RELEASE IT
	 RETBAD ( ,<UNLOCK ACTLCK>)
	SETOM ACTPGN		;NO ACCT WINDOW PAGE MAPPED IN NOW
	SETOM AVALON		;ACCOUNT VALIDATION NOW TURNED ON
	UNLOCK ACTLCK		;ALL DONE FIDDLING WITH THESE PAGES NOW
	RETSKP			;GIVE GOOD RETURN

ENACX:	RETBAD ( ,<UNLOCK ACTLCK>)
;THE UTEST JSYS - BASIC UNIT TESTING FACILITY
;ACCEPTS IN 1/	FUNCTION CODE ,,  LENGTH OF ARGUMENT BLOCK
;	    2/	ADDRESS OF ARGUMENT BLOCK

;FUNCTION 0 = START TESTING
;	  1 = STOP TESTING

;ARGUMENT BLOCK:
;LOC 0/	ADDRESS OF MONITOR ROUTINE TO TEST
;LOC 1/	NUMBER OF WORDS TO BE TESTED
;LOC 2/	START OF BIT TABLE OF ADDRESSES TO BE TESTED
;	BIT = 0 MEANS DO NOT TEST THE CORRESPONDING LOCATION
;	BIT = 1 MEANS TEST THIS LOCATION

;ON THE STOP TESTING FUNCTION THE BIT TABLE IS MODIFIED TO CONTAIN:
;	BIT = 0 MEANS THIS LOCATION WAS EXECTUTED DURING THE TESTING
;	BIT = 1 MEANS THAT THIS LOCATION WAS NOT EXECUTED


.UTEST::MCENT
	NOINT			;DO NOT ALLOW INTERRUPTS 
	MOVE T1,CAPENB		;SEE IF THE CALLER IS PRIVILEGED
	TXNN T1,SC%WHL		;MUST BE A WHEEL
	ITERR (CAPX3)		;NOT A WHEEL, THIS JSYS IS NOT LEGAL
	XCTU [HLRZ T3,1]	;GET THE FUNCTION CODE
	CAIL T3,UTABLN		;IS THIS A LEGAL FUNCTION
	ITERR (UTSTX1)		;NO, GIVE ERROR
	XCTU [HRRZ T4,1]	;GET LENGTH OF ARG BLOCK
	UMOVE T1,2		;GET ADDRESS OF ARG BLOCK
	SUBI T4,2		;GET NUMBER OF WORDS TO TEST
	IMULI T4,^D36		;ONE BIT FOR EACH WORD
	SKIPG T4		;IS THERE AN ARG BLOCK?
	TDZA T2,T2		;NO
	UMOVE T2,1(T2)		;GET THE NUMBER OF WORDS FROM ARG BLOCK
	CAMG T4,T2		;TAKE THE SMALLER VALUE
	MOVE T2,T4		;...
	MOVE T3,UTAB(T3)	;GET DISPATCH ADDRESS
	CALL 0(T3)		;DO THIS FUNCTION
	 ITERR()		;FAILED
	MRETNG			;SUCCESS

UTAB:	UTEST0			;FUNCTION 0 - START TESTING
	UTEST1			;FUNCTION 1 - STOP TESTING
UTABLN==.-UTAB
;ROUTINE TO INSERT THE TEST INSTRUCTION INTO THE ROUTINE TO BE TESTED

;ACCEPTS IN T1/	ADR OF ARG BLOCK
;	    T2/	# OF BITS IN BIT TABLE

UTEST0:	CAIL T2,UTNPG*PGSIZ	;TOO LARGE A REQUEST?
	RETBAD (UTSTX2)		;YES, CANNOT DO THIS REQUEST
	NOSKED			;NOW SECURE THE INTERLOCK
	SKIPL UTLOCK		;IS THIS FEATURE AVAILABLE?
	RETBAD (UTSTX3,<OKSKED>) ;NO, ALREADY IN USE
	MOVE T3,FORKX		;YES, PUT OUR FORK NUMBER IN UTLOCK
	MOVEM T3,UTLOCK		;WE NOW OWN THE FACILITY
	OKSKED
	MOVSI P3,(<POINT 1,0(P2)>) ;SET UP TO SCAN BIT TABLE
	XCTU [HRRZ P1,0(T1)]	;GET ADDRESS OF MONITOR ROUTINE
	MOVEM P1,UTBASE		;SAVE FOR EXIT
	MOVEI P2,2(T1)		;GET START OF BIT TABLE
	MOVE P4,T2		;GET COUNT OF WORDS TO TEST
	MOVEM T2,UTLEN		;SAVE COUNT FOR EXIT
	MOVEI Q1,777(T2)	;LOCK DOWN THE BUFFER AREA
	LSH Q1,-PGSFT		;GET # OF PAGES NEEDED FOR BUFFER AREA
	SETZ Q2,
UT0L1:	MOVEI T1,UTPGS(Q2)	;GET ADR OF NEXT PAGE TO LOCK
	CALL MLKMA		;LOCK IT DOWN
	ADDI Q2,PGSIZ		;STEP TO NEXT PAGE
	SOJG Q1,UT0L1		;LOOP BACK TIL ALL PAGES LOCKED
	CALL SWPMWE		;WRITE ENABLE THE MONITOR
	MOVE T3,[CALL UTREP]	;GET THE INSTRUCTION TO BE INSERTED
	MOVEI T4,UTPGS		;GET START OF BUFFER AREA
UT0L2:	XCTBMU [ILDB T1,P3]	;GET NEXT BIT FROM USER BIT TABLE
	MOVE T2,(P1)		;GET NEXT INSTRUCTION FROM ROUTINE
	MOVEM T2,(T4)		;STORE IT IN THE BUFFER
	AOS T4			;STEP TO NEXT LOCATION IN BUFFER
	AND T2,[777000,,0]	;GET INSTRUCTION OPCODE
	CAMN T2,[ERJMP]		;IS THIS AN ERJMP OR ERCAL
	SETZ T1,		;YES, DO NOT TEST THIS LOCATION
	TLCE T2,777000		;IS THE OPCODE = 0?
	TLCN T2,777000		;OR 777?
	SETZ T1,		;YES, DO NOT CHANGE THIS LOCATION
	SKIPE T1		;SHOULD THIS LOCATION BE CHANGED?
	MOVEM T3,(P1)		;YES, PUT "CALL REP" IN ITS PLACE
	AOS P1			;STEP TO NEXT WORD IN ROUTINE
	SOJG P4,UT0L2		;LOOP BACK TIL ALL WORDS SET UP
	RETSKP			;DONE
;ROUTINE TO REMOVE THE TEST INSTRUCTION AND REPORT RESULTS

;ACCEPTS IN T1/	ADR OF ARG BLOCK
;	    T2/	# OF BITS IN BIT TABLE

UTEST1:	MOVE T3,UTLOCK		;SEE IF WE OWN THIS FACILITY
	CAME T3,FORKX		;...
	RETBAD (UTSTX3)		;WE DO NOT, SO DO NOT ALLOW THIS
	MOVE P1,UTBASE		;GET START ADR OF ROUTINE BEING TESTED
	MOVSI P3,(<POINT 1,0(P2)>) ;SET UP BYTE POINTER
	MOVEI P2,2(T1)		;GET POINTER TO THE START OF BIT MASK
	MOVE P4,T2		;GET # OF WORDS TO STORE BACK
	MOVE P5,UTLEN		;GET # OF WORDS IN ORIGINAL TEST CALL
	MOVEI T4,UTPGS		;GET START OF BUFFER
UT1L:	MOVE T2,(P1)		;GET INSTRUCTION FROM ROUTINE
	MOVE T3,(T4)		;GET ORIGINAL INSTRUCTION FROM BUFFER
	MOVEI T1,1		;START OFF WITH "UNEXECUTED" RESPONSE
	CAME T2,[CALL UTREP]	;DID THIS INST GET EXECUTED?
	TDZA T1,T1		;YES, RETURN 0 TO USER
	MOVEM T3,(P1)		;STORE ORIGINAL INSTRUCTION BACK
	SOSL P4			;USER WANT ANY MORE?
	XCTBMU [IDPB T1,P3]	;YES, STORE THE ANSWER
	AOS T4			;STEP TO NEXT WORD IN BUFFER
	AOS P1			;STEP TO NEXT WORD IN MONITOR
	SOJG P5,UT1L		;LOOP TIL ALL INSTRUCTIONS ARE RESTORED
	MOVEI P1,777-UTPGS(T4)	;NOW UNLOCK THE PAGES
	LSH P1,-PGSFT		;GET COUNT OF PAGES TO BE DONE
UT1LL:	MOVEI T1,<UTPGS_-PGSFT>-1(P1) ;GET PAGE #
	HRL T1,MMSPTN		;GET PTN OF MONITOR MAP
	CALL MULKPG		;UNLOCK THE PAGE
	SOJG P1,UT1LL		;LOOP TIL ALL PAGES UNLOCKED
	CALL SWPMWP		;WRITE PROTECT THE MONITOR AGAIN
	SETOM UTLOCK		;GIVE UP THE FACILITY
	RETSKP			;AND EXIT
;ROUTINE TO RELEASE THE UTEST RESOURCES ON A FORK KILL

UTREL::	SETZB T1,T2		;DO NOT GET ANY RESULTS BACK
	CALL UTEST1		;GO RELEASE THIS FACILITY
	 JFCL			;IF IT FAILS, WE CAN DO NOTHING
	RET			;DONE


;ROUTINE TO RETURN THE ORIGINAL VALUES TO THE TESTED ROUTINE

	RESCD

UTREP::	PUSH P,T1		;SAVE AN AC FOR SCRATCH
	SOS -1(P)		;GET ADDRESS OF CALLING INSTRUCTION
	HRRZ T1,-1(P)		;...
	SUB T1,UTBASE		;GET OFFSET INTO BUFFER
	MOVE T1,UTPGS(T1)	;GET THE ORIGINAL INSTRUCTION 
	MOVEM T1,@-1(P)		;RESTORE THE LOC TO ITS ORIGINAL STATE
	POP P,T1		;RESTORE THE SCRATCH AC
UTREPE::RET			;AND GO DO THE ACTUAL INSTRUCTION

	SWAPCD
; VALIDATE ACCOUNT
; CALL:	T1/ 36-BIT USER # OR DIRECTORY #
;	T2/ POINTER TO ACCOUNT STRING
;	VACCT
; RETURNS: +1	ALWAYS

.VACCT::MCENT
	STKVAR <VERNO,VERPTR>
	UMOVE T1,1		;GET USER OR DIR #
	MOVEM T1,VERNO		;SAVE FOR NOW
	HLRZS T1
	CAIN T1,USRLH		;IS IT A USER NUMBER?
	JRST [	MOVE T1,VERNO	;YES, GET WHOLE NUMBER
		CALL CNVDIR	;CONVERT IT TO A DIRECTORY NUMBER
		JRST VACCT1]	;AND CONTINUE
	MOVE T1,VERNO		;GET DIRECTORY NUMBER
VACCT1:	CALL SETDIR		;MAP IN THE DIRECTORY
	 ITERR ()		;ERROR, TELL USER
	UMOVE T1,2		;GET POINTER TO ACCOUNT STRING
	CALL CPYFUS		;DRAG IN THE ACCOUNT
	 ITERR (MONX02)		;ERROR, JSB FULL
	MOVEM T1,VERPTR		;SAVE LOOKUP POINTER TO ACCT STRING
	UMOVEM T3,2		;RETURN UPDATED POINTER TO USER
	MOVE T1,VERNO		;USER OR DIR #
	MOVE T2,VERPTR		;LOOKUP POINTER TO ACCOUNT STRING
	CALL VERACT		;GO VALIDATE THE ACOUNT
	 JRST VACCTX
VACCT2:	MOVEI T1,JSBFRE		;RELEASE CPYFUS'ED STRING
	MOVE T2,VERPTR
	CALL RELFRE
	CALL USTDIR		;UNMAP DIR
	OKINT			;CPYFUS WENT NOINT
	MRETNG			;SUCCESS RETURN

; CALL TO VERACT FAILED
; TRY TO VALIDATE SPECIAL OPERATOR ACCOUNT

VACCTX:	MOVEM T1,LSTERR		;SAVE ERROR CODE
	MOVE T1,JOBNO
	MOVE T1,JOBDIR(T1)	;GET THIS JOB'S LOGIN DIR NO
	CAIN T1,OPERDN		;VALIDATING FOR OPERATOR?
	JRST VACTX2		;YES, CHECK FOR SPECIAL OPER ACCOUNT
VACTX1:	MOVEI T1,JSBFRE		;RELEASE SPACE FOR CPYFUS'ED STRING
	MOVE T2,VERPTR
	CALL RELFRE
	CALL USTDIR		;UNMAP DIRECTORY
	OKINT			;CPYFUS WENT NOINT
	MOVE T1,LSTERR
	ITERR ( )		;ERROR RETURN

VACTX2:	MOVE T2,VERPTR
	AOS T2			;POINT TO ACCOUNT TO VALIDATE
	MOVE T1,[-2,,[ASCIZ/OPERATOR/]]
VACTX3:	MOVE T3,0(T1)		;GET NEXT WORD IN ACCT STRING
	CAME T3,0(T2)		;ACCOUNTS THE SAME SO FAR?
	JRST VACTX1		;NO, CLEAN UP AND RETURN ERROR
	AOS T2
	AOBJN T1,VACTX3		;SCAN SOME MORE
	JRST VACCT2		;USING SPECIAL ACCOUNT, GIVE OK RETURN
; INTERNAL ROUTINE TO VALIDATE AN ACCOUNT
; CALL:	T1/ 36-BIT USER OR DIRECTORY NUMBER
;	T2/ LOOKUP POINTER TO AN ACCOUNT STRING
;	CALL VERACT
; RETURNS: +1	FAILED, ERROR CODE IN T1
;	   +2	SUCCESS, T1/ AC%MCH => ACCOUNT MATCHES ACCTSR
;			 T2/ ACCOUNT EXPIRATION DATE

VR%USR==:1B0		;MEANS VALIDATING FOR A USER NUMBER
			;USED INTERNALLY BY VERACT IN FLAG AC Q1

VERACT::SKIPN AVALON		;ACCOUNT VALIDATION RUNNING?
	JRST [	SETZB T1,T2	;NO, GIVE GOOD RETURN IMMEDIATELY
		RETSKP]
	SAVEQ
	TRVAR <STRINX,VERABJ,VERHDR,VERLOC,VERLUK,VERNUM,<VERTMP,2>>
	SETZ Q1,		;INITIALIZE FLAG AC
	MOVEM T2,VERLUK		;SAVE LOOKUP PTR TO ACCT STRING
	MOVEM T1,VERNUM		;SAVE USER OR DIR #
	HLRZS T1
	CAIN T1,USRLH		;IS IT A USER NUMBER?
	JRST [	TXO Q1,VR%USR	;NOTE THAT A USER NUMBER WAS PASSED
		JRST VERAC1]	;AND CONTINUE
	CALL CNVSTR		;IS THIS A DIRECTORY #?
	 RETBAD ( ) 		;ERROR, RETURN
	MOVEM T1,STRINX		;SAVE STR: INDEX INTO STRTAB

; ARGUMENTS PASSED TO VERACT ARE OK
; HASH ACCOUNT STRING AND GO SCAN DATABASE

VERAC1:	MOVE T1,VERLUK		;LOOKUP PTR TO ACCOUNT STRING
	AOJ T1,			;MAKE IT POINT TO START OF ACCT STRING
	HLRZ T2,T1
	SOJ T2,
	HRLM T2,T1		;T1/ AOBJN PTR TO ACCT STRING
	MOVEM T1,VERABJ		;SAVE IT
	CALL CHKASR		;ACCOUNT MATCH ACCTSR?
	 JRST VERAC6		;NO, CONTINUE
	TRNE T1,-1		;MATCH - ACCOUNT EXPIRED?
	JRST BADRTE		;YES, GIVE INVALID RETURN
	JRST OKRET		;NO, GIVE GOOD RETURN

VERAC6:	CALL CHKCSH		;ACCOUNT MATCH CACHED ACCT IN JSB?
	 JRST VERAC0		;NO, GO SCAN DATA BASE
	TRNE T1,-1		;ACCOUNT EXPIRED?
	JRST BADRTE		;YES, GIVE INVALID RETURN
	JRST OKRET		;NO, GIVE GOOD RETURN
; HASH ACCOUNT AND GO SCAN DATA BASE

VERAC0:	MOVE T1,VERABJ		;AOBJN POINTER TO ACCOUNT
	CALL HSHNAM		;HASH ACCOUNT STRING
	CAILE T1,HASHLN		;VALID HASH VALUE?
	JRST [BUG (CHK,HSHERR,<VERACT - HASH VALUE OUT OF RANGE>)
		RETBAD (VACCX0)]
	MOVEI T2,HSHPG+1	;START OF HASH VALUES ON HSHPG
	ADD T2,T1		;HASH VALUE IS INDEX INTO TABLE
	MOVE T2,0(T2)		;GET HASH TABLE ENTRY
	JUMPE T2,BADRET		;IF NO ENTRY THERE, ACCOUNT IS INVALID
	LOCK ACTLCK		;PREVENT OTHER TWEAKING OF ACCT PAGES
VERAC2:	IDIVI T2,PGSIZ		;PAGE # WHERE THE ACCT BLK RESIDES IN THE DATA FILE
	MOVEM T3,VERLOC		;RELATIVE LOC ON PG WHERE ACCT BLK BEGINS
	CAMN T2,ACTPGN		;IS THIS PAGE ALREADY MAPPED IN?
	JRST VERAC3		;YES, JUST CONTINUE
	MOVEM T2,T3
	SKIPGE ACTPGN		;ANYTHING MAPPED INTO ACTPG YET?
	JRST VERAC5		;NO, JUST GO MAP IN NEW PAGE
	SETZ T1,		;UNMAP CURRENT WINDOW PAGE
	HRRZI T2,ACTPG		;START OF ACCOUNT WINDOW PAGE
	CALL SETMPG
VERAC5:	MOVEM T3,ACTPGN		;SAVE NEW PAGE # MAPPED IN
	HRRZ T1,T3
	HRL T1,ACTOFN		;T1/ OFN,,NEW PAGE #
	MOVX T2,PM%RD		;READ ACCESS TO WINDOW PAGE
	HRRI T2,ACTPG		;START ADDRESS OF WINDOW
	CALL SETMPG		;MAP IN PG CONTAINING ACCT BLOCK
VERAC3:	MOVEI T1,ACTPG
	ADD T1,VERLOC		;ADDRESS WHERE ACCOUNT BLOCK LIVES

; NOW HAVE PAGE W/ HASHED ACCT BLK MAPPED INTO ACTPG
; SEE IF ACCT STRINGS ARE THE SAME
; IF YES, CONTINUE - IF NO, GET NEXT CHAINED ACCOUNT

	MOVEM T1,VERHDR		;SAVE LOC WHERE HEADER BEGINS
	HLRO T2,VERABJ		;LENGTH OF ACCT NAME IN WORDS
	MOVNS T2		;MAKE IT POSITIVE
	LOAD T3,BKLEN,(T1)	;LENGTH OF THIS ACCOUNT BLOCK
	SUBI T3,4		;LENGTH OF THIS ACCT NAME
	CAMN T2,T3		;LENGTHS THE SAME?
	JRST VERAC7		;YES, SEE IF THIS IS THE DESIRED ACCOUNT
VERAC4:	MOVE T1,VERHDR		;GET ADR OF HEADER
	LOAD T2,ACPTR,(T1)	;PTR TO NEXT CHAINED ACCT BLK
	JUMPE T2,BADRET		;IF NO MORE ACCT BLKS, GIVE LOSING RETURN
	JRST VERAC2		;GO CHECK NEXT ACCOUNT BLOCK
; SEE IF THIS IS THE DESIRED ACCOUNT BLOCK
; IF YES, AND THE USER IS WHOPER, ACCEPT IT AS A VALID ACCOUNT
; IF USER ISN'T WHOPER, GO SCAN DATA BASE TO VALIDATE THE ACCOUNT

VERAC7:	MOVE T1,VERABJ		;SEE IF THIS IS THE DESIRED ACCT
	MOVE T2,VERHDR
	ADDI T2,4		;POINT TO THIS ACCOUNT NAME
	CALL CHKSAM		;IS THIS THE DESIRED ACCOUNT?
	 JRST VERAC4		;NO, GO LOOK AT THE NEXT CHAINED ONE
	MOVE T2,VERHDR		;THIS IS THE ACCOUNT
	CALL CHKEXP		;HAS IT EXPIRED?
	 JRST BADRTE		;YES, ACCOUNT IS INVALID
	MOVE T1,CAPENB		;GET ENABLED CAPABILITIES
	TXNN T1,SC%WHL!SC%OPR	;IS USER WHOPER?
	JRST VERAC8		;NO, GO SCAN DATA BASE
	MOVE T1,JOBNO
	SKIPN JOBDIR(T1)	;IS THE WHOPER JOB LOGGED IN?
	JRST VERAC8		;NO, GO SCAN DATA BASE
	MOVE T2,VERHDR		;YES, GET EXP DATE OF ACCOUNT
	LOAD T2,XPDAT,(T2)
	CALL CPYCSH		;SAVE ACCOUNT AND EXP DATE IN JSB CACHE
	SETZ T1,		;SAY ACCOUNT DOESN'T MATCH ACCTSR
	MOVE T2,VERHDR
	LOAD T2,XPDAT,(T2)	;GET EXPIRATION DATE AGAIN
	JRST OKRET		;AND GIVE GOOD RETURN
VERAC8:	CALL SCNACT		;GO SCAN DATA BASE
	 JRST BADRT0		;ACCOUNT INVALID OR EXPIRED
	MOVE Q2,T2		;ACCOUNT VALID, SAVE EXP DATE
	CALL CPYCSH		;SAVE ACCT AND EXP DATE IN JSB CACHE
	MOVE T2,Q2		;GET BACK EXPIRATION DATE
	SETZ T1,		;ACCOUNT DOESN'T MATCH ACCTSR
	JRST OKRET		;GIVE GOOD RETURN
; SEE IF AN ACCOUNT HAS EXPIRED
; CALL:	T2/ ADDRESS OF ACCOUNT DATA BLOCK
;	CALL CHKEXP
; RETURNS: +1	ENTRY EXPIRED
;	   +2	ENTRY NOT EXPIRED

CHKEXP:	LOAD T2,XPDAT,(T2)	;GET EXPIRATION DATE
CHKEX0:	JUMPE T2,RSKP		;IF 0, ENTRY NEVER EXPIRES
	GTAD			;GET CURRENT TIME AND DATE
	CAMG T2,T1		;HAS THE ENTRY EXPIRED?
	RETBAD (VACCX2)		;YES
	RETSKP			;NO, ENTRY STILL VALID

; SEE IF ACCOUNT MATCHES ACCTSR
;	CALL CHKASR
; RETURNS: +1	NO MATCH
;	   +2	MATCH, T1/ AC%MCH => MATCHES ACCTSR
;		   RH(T1)/ 0 => ACCOUNT NOT EXPIRED
;			   1 => ACCOUNT EXPIRED
;		       T2/ ACCOUNT EXPIRATION DATE
; CLOBBERS T1 THROUGH T4

CHKASR:	MOVE T1,JOBNO
	SKIPN JOBDIR(T1)	;IS THIS JOB LOGGED IN?
	RET			;NO, DON'T CHECK THE JSB
	MOVE T1,VERABJ		;AOBJN POINTER TO ACCOUNT
	HRRZI T2,ACCTSR		;ADDRESS OF ACCOUNT IN JSB
	CALL CHKSAM		;ACCOUNTS THE SAME?
	 RET			;NO, JUST RETURN
	MOVE T2,ACCTSX		;SAME - GET EXPIRATION DATE
	CALL CHKEX0		;ACCTSR EXPIRED?
	 JRST CHKAS1		;YES
	MOVX T1,AC%MCH
	RETSKP
CHKAS1:	HRRZI T1,1		;NOTE THAT ACCTSR HAS EXPIRED
	TXO T1,AC%MCH
	RETSKP			;AND RETURN

; SEE IF ACCOUNT MATCHES CACHED ACCOUNT (CSHACT)
;	CALL CHKCSH
; RETURNS: +1	NO MATCH
;	   +2	MATCH, RH(T1)/ 0 => ACCOUNT NOT EXPIRED
;			       1 => ACCOUNT EXPIRED
;			   T2/ ACCOUNT EXPIRATION DATE
; CLOBBERS T1 THROUGH T4

CHKCSH:	MOVE T1,JOBNO
	SKIPN JOBDIR(T1)	;JOB LOGGED IN?
	RET			;NO, DON'T CHECK THE JSB
	MOVE T1,VERABJ		;AOBJN POINTER TO ACCOUNT
	HRRZI T2,CSHACT		;ADDRESS OF CACHED ACCOUNT
	CALL CHKSAM		;ACCOUNTS THE SAME?
	 RET			;NO, JUST RETURN
	MOVE T2,CSHACX		;SAME - GET EXPIRATION DATE
	CALL CHKEX0		;CSHACT EXPIRED?
	 JRST CHKCS1		;YES
	SETZ T1,		;NO, SAY ACCOUNT NOT EXPIRED
	RETSKP			;AND GIVE GOOD RETURN

CHKCS1:	HRRZI T1,1		;SAY CSHACT EXPIRED
	RETSKP			;AND RETURN

; COPY VALID ACCOUNT TO CACHED ACCOUNT SLOT IN JSB
;  THE CACHED ACCOUNT IS CURRENTLY USED ONLY BY VERACT
;  TO REMEMBER THE MOST RECENTLY VALIDATED ACCOUNT
;
; CALL: T2/ ACCOUNT EXPIRATION DATE
;	CALL CPYCSH
;
; RETURNS: +1	ALWAYS
; CLOBBERS T1, T2, T3

CPYCSH:	MOVEM T2,CSHACX		;SAVE EXP DATE OF CACHED ACCOUNT
	HLRE T1,VERABJ
	MOVNS T1		;LENGTH OF ACCOUNT
	HRRZ T2,VERABJ		;ADDRESS OF VALID ACCOUNT
	MOVEI T3,CSHACT		;COPY ACCOUNT TO JSB
	CALL XBLTA
	RET			;AND RETURN
; SEE IF TWO STRINGS ARE THE SAME
; CALL:	T1/ AOBJN POINTER TO A STRING
;	T2/ ADDRESS OF ANOTHER STRING IN ACCOUNT WINDOW PAGE
;	CALL CHKSAM
; RETURNS: +1	NOT THE SAME
;	   +2	ACCOUNT STRINGS ARE THE SAME

CHKSAM:	MOVE T3,0(T2)		;GET NEXT WORD IN THE STRING
	CAME T3,(T1)		;ARE THEY THE SAME SO FAR?
	RET			;NO, RETURN NOW
	AOJ T2,			;POINT TO NEXT WORD IN THE STRING
	AOBJN T1,CHKSAM		;CONTINUE COMPARING STRINGS
	RETSKP			;ALL DONE, STRINGS ARE THE SAME

; HASH AN ACCOUNT STRING
; CALL:	T1/ AOBJN POINTER TO ACCOUNT STRING
;	CALL HSHNAM
; RETURNS: +1	ALWAYS, T1/ HASH VALUE

HSHNAM:	ASUBR <HSH1,HSH2,HSH3,HSH4>
	STKVAR <HSHTMP>
	HLRZ T4,T1		;GET STRING LENGTH
	CAIN T4,-1		;IS THE ACCOUNT ONE WORD LONG?
	JRST [	MOVE T3,0(T1)	;YES, GET THE STRING
		MOVEM T3,HSHTMP
		JRST HSHNM2]	;AND CONTINUE
	MOVE T3,0(T1)		;GET FIRST WORD OF STRING
	MOVEM T3,HSHTMP		;SAVE IT
	ADD T1,[1,,1]		;POINT TO NEXT WORD IN STRING
HSHNM1:	MOVE T3,0(T1)
	XORM T3,HSHTMP
	AOBJP T1,HSHNM2
	JRST HSHNM1		;CONTINUE XOR'ING WORDS IN THE STRING

HSHNM2:	MOVE T1,HSHTMP		;GET FINAL VALUE
	XOR T1,RANDOM
	MUL T1,RANDOM
	MOVMS T1
	IDIVI T1,HASHLN		;DIVIDE BY # OF POSSIBLE HASH VALUES
	MOVE T1,T2		;REMAINDER IS HASH VALUE
	DMOVE T2,HSH2		;RESTORE ORIGINAL VALUES
	MOVE T4,HSH4
	RET			;AND RETURN

RANDOM:	5*5*5*5*5*5*5*5*5*5*5*5*5*5*5

; ACCOUNT IS INVALID - CLEAN UP AND RETURN ERROR

BADRET:	SKIPA T1,[VACCX0]	;INVALID ACCOUNT
BADRTE:	MOVEI T1,VACCX2		;ACCOUNT HAS EXPIRED
BADRT0:	MOVE Q2,T1		;SAVE THE ERROR CODE FOR LATER
	HRRZ T1,VERNUM
	CAIN T1,OPERDN		;VALIDATING FOR THE OPERATOR?
	JRST BADRT2		;YES, CHECK FOR SPECIAL OPERATOR ACCOUNT
	MOVE T2,JOBNO		;SEE IF JOB IS LOGGED IN
	SKIPN JOBDIR(T2)	;IS IT LOGGED IN?
	CAIE T1,SYSTDN		;NO, IS THIS FOR DIRECTORY <SYSTEM>
	SKIPA			;NO
	JRST BADRT2		;YES, GO ALLOW THE USE OF "OPERATOR"
	MOVE T3,CAPENB		;GET ENABLED CAPABILITIES
	TXNE T3,SC%WHL!SC%OPR	;WHEEL OR OPERATOR ?
	SKIPN JOBDIR(T2)	;AND NOT LOGGED IN ?
	SKIPA			;YES
	JRST BADRT2		;GO CHECK FOR ACCOUNT "OPERATOR"
BADRT3:	TXNE Q1,VR%USR		;VALIDATING FOR A USER NUMBER?
	JRST BADRT1		;YES, PROCEED
	MOVE T1,STRINX
	CALL ULKSTR		;UNLOCK THE STRUCTURE
BADRT1:	UNLOCK ACTLCK		;UNLOCK HASH PAGE AND WINDOW PAGE
	MOVE T1,Q2		;GET BACK THE ERROR CODE
	RETBAD			;GIVE FAILURE RETURN

BADRT2:	MOVE T2,VERLUK
	AOS T2			;START OF ACCOUNT TO VALIDATE
	MOVE T1,[-2,,[ASCIZ/OPERATOR/]]
BADRT4:	MOVE T3,0(T1)		;GET NEXT WORD IN STRING
	CAME T3,0(T2)		;ACCOUNTS THE SAME SO FAR?
	JRST BADRT3		;NO, CLEAN UP AND RETURN ERROR
	AOS T2
	AOBJN T1,BADRT4		;SCAN SOME MORE
	SETZ T2,		;OPERATOR ACCOUNT NEVER EXPIRES
	CALL CPYCSH		;COPY OPERATOR ACCOUNT AND EXP DATE TO JSB
	SETZB T1,T2		;ACCOUNT MATCHES NOTHING IN THE JSB
				; AND OPERATOR ACCOUNT NEVER EXPIRES
	JRST OKRET		;USING SPECIAL ACCOUNT, GIVE OK RETURN

; ACCOUNT IS VALID - GIVE GOOD RETURN

OKRET:	TXNE Q1,VR%USR		;VALIDATING FOR A USER NO?
	JRST OKRT1		;YES, PROCEED
	DMOVEM T1,VERTMP	;SAVE THE ANSWER REGISTERS
	MOVE T1,STRINX
	CALL ULKSTR		;UNLOCK THE STRUCTURE
	DMOVE T1,VERTMP		;RESTORE ANSWER
OKRT1:	UNLOCK ACTLCK
	RETSKP			;SUCCESSFUL RETURN

VERACX:	BUG(CHK,CRSPAG,<VERACT - ACCOUNT DATA BLOCK CROSSES A PAGE BOUNDARY>)
	RETBAD (VACCX0)

VERAX1:	BUG(CHK,BADTAB,<VERACT - SPURIOUS HASH TABLE ENCOUNTERED>)
	RETBAD (VACCX0)
; SCAN DATA BASE FILE FOR A VALID USE OF AN ACCOUNT
;	CALL SCNACT
; RETURNS: +1	ACCOUNT NOT VALID FOR THIS USE
;	   +2	ACCOUNT VALID, T2/ EXPIRATION DATE
; AC USE:	Q2/ ADDRESS OF DATA BLOCK CURRENTLY BEING SCANNED

SCNACT:	STKVAR <NXTPG,TOTLEN,SCNACE>
	SETZM SCNACE		;ASSUME NO VALID ACCOUNTS
	MOVEI T1,ACTPG		;START OF ACCOUNT WINDOW PAGE
	ADDI T1,PGSIZ
	MOVEM T1,NXTPG		;IF DATA BLOCK CONTAINS THIS ADDRESS, BAD ERROR!
	MOVE Q2,VERHDR		;ADDRESS OF ACCOUNT HEADER
	LOAD T1,DATASZ,(Q2)	;GET LENGTH OF ALL DATA FOR THE ACCOUNT
	MOVEM T1,TOTLEN		;SAVE IT
SCNAC0:	LOAD T1,BKLEN,(Q2)	;LENGTH OF THIS BLOCK
	MOVEM T1,T2
	SOJ T1,
	ADD T1,Q2		;ADDRESS OF LAST WORD IN BLOCK
	CAML T1,NXTPG		;DOES BLOCK CROSS A PAGE BOUNDARY?
	JRST VERACX		;YES, GO BUGCHK
	ADD Q2,T2		;GET START OF NEXT DATA BLOCK
	MOVE T1,TOTLEN
	SUB T1,T2
	MOVEM T1,TOTLEN
	SKIPG TOTLEN		;DONE SCANNING ALL BLOCKS?
	JRST SCNAC2		;YES, ACCOUNT NOT VALID FOR THIS USE
	CAML Q2,NXTPG		;IS THIS BLOCK ON THE NEXT PAGE?
	JRST [	CALL SCNMAP	;YES, MAP IN NEW WINDOW PAGE
		MOVE Q2,ACTPG	;MAKE Q2 POINT TO TOP OF NEW PAGE
		JRST .+1]	;AND CONTINUE
	LOAD T1,BKTYP,(Q2)	;GET BLOCK TYPE
	CAIN T1,.TYNUL		;IS THIS A NULL BLOCK?
	JRST [	LOAD T2,BKLEN,(Q2) ;YES
		MOVE T1,TOTLEN
		SUB T1,T2
		MOVEM T1,TOTLEN	;ADJUST COUNT OF WORDS SCANNED
		CALL SCNMAP	;MAP IN NEXT PAGE
		MOVE Q2,ACTPG	;MAKE Q2 POINT TO FIRST BLOCK ON PAGE
		JRST SCNAC0]	;AND CONTINUE
	LOAD T1,BKTYP,(Q2)	;
	CAIN T1,.TYWUS		;WILDCARD USER?
	JRST SCNUSR		;YES, GO SCAN THE BLOCK
	CAILE T1,.TYALU		;SOME KIND OF USER DATA BLOCK?
	JRST SCNDIR		;NO, GO SCAN DIRECTORY BLOCKS
	CAILE T1,.TYACC		;REALLY A USER BLOCK?
	JRST SCNUSR		;YES, GO SCAN IT
	CAIE T1,.TYACC		;IS IT AN ACCOUNT BLOCK?
	JRST VERAX1		;NO, BAD BLOCK
	SKIPLE TOTLEN		;ALL BLOCKS SCANNED?
	JRST SCNAC0		;NO, GO LOOK AT NEXT BLOCK
SCNAC2:	MOVEI T1,VACCX0		;NO VALID ACCOUNTS
	SKIPE SCNACE		;WAS AN EXPIRED ONE FOUND?
	MOVEI T1,VACCX2		;YES, RETURN THIS ERROR CODE
	RETBAD
; SCANNING A USER BLOCK FOR A MATCH

SCNUSR:	CALL SCNUNO		;GO DO THE WORK
	 JRST SCNAC1		;NO MATCH OR ACCOUNT EXPIRED, GO LOOK AT NEXT BLOCK
	RETSKP			;MATCH, NOT EXPIRED, OK RETURN

; SCANNING A DIRECTORY BLOCK FOR A MATCH

SCNDIR:	TXNE Q1,VR%USR		;DOING A USER NUMBER?
	SKIPA T1,[VACCX0]	;YES. INVALID ACCOUNT THEN
	CALL SCNDNO		;GO DO THE WORK
	 JRST SCNAC1		;NO MATCH OR ACOUNT EXPIRED, GO LOOK AT NEXT BLOCK
	RETSKP			;MATCH, NOT EXPIRED,GIVE GOOD RETURN

SCNAC1:	CAIN T1,VACCX2		;DID THE ACCOUNT EXPIRE?
	SETOM SCNACE		;YES, REMEMBER THAT
	JRST SCNAC0		;LOOP BACK TO SEE IF A VALID ONE EXISTS

; SCANNING USER BLOCKS
; CALL: Q2/ ADDRESS OF DATA BLOCK CURRENTLY BEING SCANNED
; 	CALL SCNUNO
; RETURNS: +1	NO MATCH OR ACCOUNT EXPIRED
;	   +2	MATCH, T2/ 0 => ACCOUNT NEVER EXPIRES
;		    OR T2/ EXPIRATION DATE

SCNUNO:	LOAD T1,BKTYP,(Q2)	;GET THIS BLOCK TYPE
	CAIN T1,.TYALU		;"ALL USERS" BLOCK?
	JRST SCNUN0		;YES, SEE IF IT HAS EXPIRED
	CAIN T1,.TYUGP		;USER GROUP BLOCK?
	JRST SCNUN1		;YES, GO SCAN IT
	MOVE T2,DIRORA		;ADDRESS OF MAPPED-IN DIR
	LOAD T2,DRNAM,(T2)	;START OF LOGGED-IN DIRECTORY NAME
	ADD T2,DIRORA		;ADDRESS OF DRNAM BLOCK
	AOS T2			;POINT PAST BLOCK HEADER
	CAIN T1,.TYWUS		;WILD CARD STRING?
	JRST SCNUN2		;YES, GO HANDLE IT SPECIALLY
	LOAD T1,BKLEN,(Q2)	;BLOCK LENGTH
	SUBI T1,2		;GET USER NAME LENGTH TO COMPARE
	MOVNS T1		;MAKE IT NEGATIVE
	HRLZS T1
	MOVE T3,Q2
	ADDI T3,2		;ADDRESS OF START OF USER NAME
	HRR T1,T3		;NOW HAVE AOBJN POINTER TO NAME
	CALL CHKSAM		;USER NAMES THE SAME?
	 RETBAD (VACCX0)	;NO
	; ...
	; ...
SCNUN0:	MOVE T2,Q2		;A MATCH WAS FOUND
	CALL CHKEXP		;SEE IF ACCOUNT HAS EXPIRED FOR THIS USE
	 RETBAD (VACCX2)	;EXPIRED
	LOAD T2,XPDAT,(Q2)	;NOT EXPIRED, GET EXP DATE
	SETZ T1,		;ACCOUNT DOESN'T MATCH ONE IN THE JSB
	RETSKP			;GIVE MATCH RETURN

; TRY TO MATCH A USER GROUP NUMBER

SCNUN1:	LOAD T1,USRGP,(Q2)	;GET GROUP NUMBER
	CALL CHKUGP		;CHECK AGAINST GROUP #'S IN DIRECTORY
	 RETBAD (VACCX0)	;NO MATCH
	JRST SCNUN0		;MATCH, SEE IF ACCOUNT HAS EXPIRED

;WILD CARD USER NAME STRING

SCNUN2:	MOVSI T1,(POINT 7,0(T4)) ;SET UP BYTE POINTER TO NAME STRING
	MOVE T4,T2		;GET POINTER TO FIRST BYTE OF USER NAME
	MOVSI T2,(POINT 7,0)	;NOW SET UP A POINTER TO THE MASK STRING
	HRRI T2,2(Q2)		;GET ADR OF FIRST WORD OF MASK STRING
	CALL CHKWLD		;NOW COMPARE THE STRINGS FOR A MATCH
	 RETBAD (VACCX0)	;NO MATCH
	JRST SCNUN0		;MATCHED, GO SEE IF EXPIRED

; SCANNING DIRECTORY BLOCKS
; CALL: Q2/ ADDRESS OF DATA BLOCK CURRENTLY BEING SCANNED
;	CALL SCNDNO
; RETURNS: +1	NO MATCH OR ACCOUNT EXPIRED
;	   +2	MATCH, T2/ 0 => ACCOUNT NEVER EXPIRES
;		    OR T2/ EXPIRATION DATE

SCNDNO:	LOAD T1,SXSTR,(Q2)	;GET BLOCK'S STRUCTURE NAME
	CAMN T4,[-1]		;ALL STRUCTURES VALID?
	JRST SCNDN2		;YES, PROCEED
	MOVE T2,STRINX		;GET STRUCTURE NUMBER
	MOVE T2,STRTAB(T2)	;GET ADDRESS OF SDB FOR THIS STRUCTURE
	CAME T1,SDBNAM(T2)	;STRUCTURE NAMES MATCH?
	RETBAD (VACCX0)		;NO, RETURN IMMEDIATELY
SCNDN2:	LOAD T1,BKTYP,(Q2)	;GET BLOCK TYPE
	CAIN T1,.TYDGP		;DIRECTORY GROUP BLOCK?
	JRST SCNDN1		;YES, GO CHECK DIRECTORY GROUPS
	MOVE T2,DIRORA		;START OF MAPPED-IN DIRECTORY
	LOAD T2,DRNAM,(T2)
	ADD T2,DIRORA		;ADDRESS OF BLOCK WHERE DRNAM LIVES
	AOJ T2,			;POINT PAST BLOCK HEADER
	LOAD T1,BKLEN,(Q2)	;GET THIS BLOCK'S LENGTH
	SUBI T1,3		;LENGTH OF DIRECTORY NAME IN WORDS
	MOVNS T1		;MAKE IT NEGATIVE
	HRLZS T1
	MOVE T3,Q2
	ADDI T3,3		;ADDRESS OF START OF DIRECTORY NAME
	MOVE T4,0(T3)		;GET FIRST WORD OF DIR NAME
	CAMN T4,[-1]		;ALL DIRECTORIES VALID?
	JRST SCNDN0		;YES, PROCEED
	HRR T1,T3		;NOW HAVE AOBJN PTR TO DIRECTORY NAME
	CALL CHKSAM		;DIRECTORY NAMES THE SAME?
	 RETBAD (VACCX0)	;NO
SCNDN0:	MOVE T2,Q2		;A MATCH
	CALL CHKEXP		;ACCOUNT EXPIRED FOR THIS USE?
	 RETBAD (VACCX2)	;YES, GIVE NO-MATCH RETURN
	LOAD T2,XPDAT,(Q2)	;NOT EXPIRED, GET EXP DATE
	SETZ T1,		;ACCOUNT DOESN'T MATCH ACCTSR
	RETSKP			;GIVE MATCH RETURN
; TRY TO MATCH A DIRECTORY GROUP NUMBER

SCNDN1:	LOAD T1,USRGP,(Q2)	;GET GROUP NUMBER
	CALL CHKDGP		;GROUP NUMBER MATCH ONE IN DIR LIST?
	 RETBAD (VACCX0)	;NO MATCH
	JRST SCNDN0		;MATCH, CONTINUE

; UNMAP CURRENT ACCOUNT WINDOW PAGE AND MAP IN NEXT SEQUENTIAL PAGE
;	CALL SCNMAP
; CLOBBERS T1, T2, T3

SCNMAP:	SETZ T1,
	HRRZI T2,ACTPG		;ADDRESS OF WINDOW PAGE IN CORE
	CALL SETMPG		;UNMAP IT
	AOS ACTPGN		;GET SET TO MAP IN NEXT PAGE
	HRRZ T1,ACTPGN
	HRL T1,ACTOFN		;T1/ OFN,,NEW PAGE NUMBER
	MOVX T2,PM%RD		;READ ACCESS TO WINDOW
	HRRI T2,ACTPG
	CALL SETMPG		;MAP IN THE NEXT PAGE
	RET			;AND RETURN


	TNXEND

	END