Google
 

Trailing-Edge - PDP-10 Archives - bb-jr93d-bb - 7,6/ap014/once.x14
There are 3 other files named once.x14 in the archive. Click here to see a list.
TITLE	ONCE - ONCE ONLY OPERATOR DIALOGUE AND I/O DEVICE INITIALIZATION V100
SUBTTL	T. HASTINGS/CHW/RCC/AF/DAL	24 JUN 86
	SEARCH	F,S,BTSPRM
	$RELOC
	$LOW

	.DIRECTIVE	FLBLST		;CLEANER LISTINGS

;THIS SOFTWARE IS FURNISHED UNDER A LICENSE AND MAY ONLY BE USED
;  OR COPIED IN ACCORDANCE WITH THE TERMS OF SUCH LICENSE.
;
.CPYRT<1973,1986>
;COPYRIGHT (C) 1973,1974,1975,1976,1977,1978,1979,1980,1982,1984,1986
;BY DIGITAL EQUIPMENT CORP., MAYNARD, MASS.
;ALL RIGHTS RESERVED.


XP VONCE,100
		;PUT VERSION NUMBER IN GLOB LISTING AND LOADER STORAGE MAP



;"ONCE" SHOULD BE THE LAST LOADED PROGRAM (AFTER SYSMAK AND DDT)

; THUS IF IT OVERFLOWS INTO THE USER AREA NO HARM IS DONE.
;HOWEVER, SINCE THE DISK REFRESHING ROUTINES HAVE NOW
; BEEN MADE INTO SEPARATE SUBPROGRAMS FOR LEVEL C
; (FHDREF, MDFREF, DPDREF, ETC.), THEY MAY BE LOADED FOLLOWING ONCE.
;HOWEVER, HOWEVER, UNDER LEVEL D, "ONCE" MUST BE LOADED AFTER
; REFSTR AND ONCMOD SINCE ONCEND IS USED AS THE STARTING ADDRESS OF
; FREE CORE USED BY DATA STUCTURES CREATED DURING ONCE TIME.


;ONCE ONLY CODE IS DIVIDED INTO 3 PARTS
; 1. MANDATORY ONCE ONLY (LINKSR) - NO CTY NEEDED
;	(GOOD FOR REPEATED STARTUPS DURING DEBUGGING)
; 2. USUAL SHORT ONCE ONLY CODE (ONCE) - CTY FOR DATE AND TIME
; 3. OPTIONAL ONCE ONLY CODE - CTY DIALOG TO CHANGE MONITOR
;	OR REFRESH DISK(S) - (ALT-MODE INSTEAD OF CR AFTER TIME)

	DEFINE	SETTYO <PUSHJ P,OTSET>
	DEFINE	TYPE <PUSHJ P,COMTYO##>
	DEFINE	NEXTC <PUSHJ P,COMTYI##>
;INITIALIZE PRIORITY CHANNELS AND SETUP INTERRUPT SERVICE ROUTINE CHAIN

;LINK TO SERVICE ROUTINES


LINKSR::0			;CALLED WITH JSR FROM SYSINI
	SKIPN	JRSTI1		;BEEN THROUGH JRSTI1 ALREADY?
	JSR	JRSTI1		;SETUP LOCS 40 THRU 61 & TEST FOR 2 RELOC HARDWARE
	MOVE	P,.CPNPD##


;INITIALIZE DISK(S)

	PUSHJ	P,FILMAN##	;INITIALIZE ALL DISK(S)
				; BEFORE OVERWRITING ONCE WITH DDB'S

	MOVE	T1,JRSTI
	MOVEM	T1,LINKSR+1	;DO ONCE ONLY
	SKIPN	DEVLST##	;HAVE DEVICE DATA BLOCKS BEEN LINKED ?
	JRST	LINKDB##	;NO, GO LINK DATA BLOCKS
				;RETURN @LINKSR
				;MULTIPLE DEVICE DATA BLOCKS ARE CREATED
				;AS SPECIFIED BY SYSSIZ AND MAY ERASE PART
				;OF ONCE ONLY CODE
JRSTI:	JRST	@LINKSR		;YES, RETURN
;CODE TO SET MONITOR FOR DEBUGGING SESSION WITH EXEC DDT
;MAKE STARTUP BE FAST
;SYSTEM PROGRAMMER TYPES DEBUG$G TO START MONITOR
;ALLOW SAME COPY OF MONITOR TO BE USED FOR REGULAR SYSTEM
;SIMPLY BY NOT STARTING AT DEBUG.

DEBUG::	MOVEI	T1,DDTEND##	;END OF DDT
	HRRM	T1,PATSIZ	;INCLUDE DDT IN SYSTEM SIZE
IFN FTLOCK,<
	MOVEI	T1,0		;NO LIMIT TO AMOUNT OF LOCKED CORE
	HRRM	T1,LOKLIM##	;
>
	SETOM	ERROK##		;SHUT UP ONCMOD

; PATCH DDTCPU WITH A JFCL TO BYPASS SMP DEBUGGING FEATURES
IFN FTMP,<
DDTCPN:	APRID	T1		;READ CPU SERIAL NUMBER, ETC.
	ANDI	T1,ID.PSN	;MASK DOWN TO JUST SERIAL NUMBER
	MOVEI	T2,.C0CDB##	;START OF CPU DATA BLOCK CHAIN
DDTCP1:	CAMN	T1,.CPASN##-.CPCDB##(T2) ;FOUND OURS?
	JRST	DDTCP2		;YES
	HLRZ	T2,.CPCDB##-.CPCDB##(T2) ;LINK TO NEXT CDB
	JUMPN	T2,DDTCP1	;LOOP BACK
	MOVEI	T2,.C0CDB##	;NO CDB FOR OUR CPU SO USE THE FIRST ONE
DDTCP2:	MOVE	T1,.CPASN##-.CPCDB##(T2) ;GET CPU NUMBER
DDTCPU:	MOVEM	T1,DEBCPU##	;SAVE FOR DEBUGGING SMP
> ;END IFN FTMP

;PATCH DDTOPR - SIXBIT OPR FOR DEBUGGING
	SKIPA	T1,.+1		;OPR
DDTOPR:	SIXBIT	/CTY/		;ASSUME CTY - PATCH TO OTHER
	MOVEM	T1,DEVOPR##	;OPR SIXBIT NAME

	MOVSI	T1,(DF.SBD+DF.NAR)	;
	IORM	T1,DEBUGF##	;FLAG DEBUGGING MODE
				; SO WHY RELOAD, LONG DIALOG
				; UNITS OFF-LINE NOT ASKED
				;ALSO, CHANGES .SET CORMIN TO JUMP TO EDDT.
				; RETURN IS BY GOBACK$G
				;ALSO, NOTICES 21 NON-ZERO (OR S.S.6 ON KI-10)
				;  RETURN IS BY GOBACK$G
	MOVEI	T1,ST.NRT	;TURN OFF REMOTE
	IORM	T1,STATES##	;TTY'S
	JRST	SYSINI##	;START UP SYSTEM
SUBTTL	ONCE-ONLY/BOOTSTRAP INTERFACE -- ACCOUNT FOR CORE USAGE


; SUBROUTINE TO FIXUP SYSORG TO ACCOUNT FOR THE PRESENCE OF THE YET
; TO BE MAPPED BOOTSTRAP.  THIS MUST BE DONE IMMEDIATELY AFTER SETTING
; UP NXMTAB AND BEFORE ANY SECTION MAPS ARE ALLOCATED.  OTHERWISE,
; PORTIONS OF THE BOOTSTRAP MAY BE TAKEN FOR A SECTION MAP.

BOOTSZ:	SKIPN	P1,BOOTPA##	;PHYSICAL ADDRESS OF BOOT ORIGIN
	JRST	BOOTZA		;NOT THERE--GO ZERO ADDRESSES
	MOVE	U,P1		;COPY IT
	HRRI	U,.BTNAM(P1)	;POINT TO IDENTIFIER
	PUSHJ	P,REFMEM##	;FETCH
	CAME	T1,['BOOT  ']	;SANITY CHECK
	JRST	BOOTZA		;DON'T KNOW HOW WE WERE BOOTED
	HRRI	U,.BTSIZ(P1)	;OFFSET TO SIZE WORD
	PUSHJ	P,REFMEM##	;FETCH
	JUMPGE	T1,BOOTZA	;MUST BE NEGATIVE
	HLRE	T2,T1		;GET -PAGE COUNT
	MOVNS	T2		;MAKE POSITIVE
	HRRZ	T3,T1		;ISOLATE LENGTH IN WORDS
	ADDI	T3,PAGSIZ##	;ROUND UP A PAGE
	LSH	T3,W2PLSH##	;CONVERT TO A PAGE NUMBER
	CAME	T3,T2		;MUST MATCH
	JRST	BOOTZA		;NOT GOOD
	HLRES	T1		;GET -LENGTH IN PAGES
	LSH	T1,P2WLSH##	;CONVERT TO -WORD COUNT
	MOVEM	P1,SYSORG##	;START ALLOCATING AT BOTTOM OF BOOTSTRAP
	SUB	P1,T1		;DETERMINE END OF BOOTSTRAP
	MOVEM	P1,BTSPFF	;SAVE FOR KLUDGERY AT BOOTMP
	POPJ	P,		;RETURN

BOOTZA:	SETZM	BOOTPA##	;CLEAR PHYSICAL ADDRESS
	SETZM	BOOTVA##	;CLEAR VIRTUAL ADDRESS
	POPJ	P,		;RETURN

BTSPFF:	0			;FIRST PHYSICAL ADDRESS FOLLOWING BOOTSTRAP
				; USED TO FAKE OUT ONCMAP TO ALLOCATE THE
				; PHYSICAL PAGES CONTAINING THE BOOTSTRAP
SUBTTL	ONCE-ONLY/BOOTSTRAP INTERFACE -- MAP BOOTSTRAP


BOOTMP:	SKIPN	P1,BOOTPA##	;PHYSICAL ADDRESS OF BOOT ORIGIN
	POPJ	P,		;NOT THERE
	MOVE	U,P1		;COPY ADDRESS
	HRRI	U,.BTSIZ(P1)	;OFFSET TO SIZE WORD
	PUSHJ	P,REFMEM##	;FETCH
	HLLZ	P2,T1		;PRESERVE -LENGTH IN PAGES
IFN FTXMON,<
	MOVSI	T1,(MS.RLC)	;SECTION NUMBER FOR RELOCATABLE CODE
	PUSHJ	P,ALCSMP	;ALLOCATE A MAP IF NECESSARY
> ;END IFN FTXMON
	MOVE	T1,.CPEPT##	;POINT TO THIS CPU'S MAP
	ADDI	T1,SECTAB+(MS.RLC) ;OFFSET INTO THE SECTION MAP TABLE
	MOVE	T2,(T1)		;GET MAP POINTER
	MOVE	T1,.CPMAP##	;GET ADDRESS OF SECTION ZERO MAP
	MOVEM	T2,.EUPMP/PAGSIZ##(T1) ;MAKE THE MAP ADDRESSABLE
IFE FTXMON,<
	HRRZ	T2,MONVFF##	;GET FIRST FREE ABOVE HIGH SEGMENT
	LSH	T2,W2PLSH##	;CONVERT TO A PAGE NUMBER
	HRRI	T1,.EUPMP+1(T2)	;START HERE
	ADDI	T2,-PAGSIZ##	;GET -REMANING PAGE COUNT IN T2
	HRL	T1,T2		;MAKE AN AOBJN POINTER
> ;END IFE FTXMON
IFN FTXMON,<
	MOVSI	T1,-PAGSIZ##	;PAGES PER SECTION
	HRRI	T1,.EUPMP	;START OF SECTION MAP
> ;END IFN FTXMON
	HRR	P2,T1		;PRESERVE SECTION MAP ADDRESS
BOOTM1:	HLL	T2,P2		;GET -PAGE COUNT
BOOTM2:	SKIPE	(T1)		;PAGE IN USE?
	JRST	BOOTM1		;YES--TRY ANOTHER
	AOBJP	T1,BOOTZA	;GIVE UP IF SECTION IS FULL
	AOBJN	T2,BOOTM2	;LOOP FOR THE REQUIRED NUMBER OF PAGES
	ANDI	T1,PG.BDY##	;KEEP ONLY ENDING PAGE NUMBER
	HLRE	T2,P2		;GET -LENGTH IN PAGES
	ADDI	T2,(T1)		;COMPUTE STARTING VIRTUAL PAGE NUMBER
	LSH	T2,P2WLSH	;CONVERT TO AN ADDRESS
	HRLI	T2,(MS.RLC)	;INCLUDE SECTION NUMBER FOR RELOCATABLE CODE
	MOVEM	T2,BOOTVA##	;SAVE ADDRESS
	HLRE	T1,P2		;-PAGES NEEDED
	MOVNS	T1		;MAKE POSITIVE
	LSH	T1,P2WLSH	;CONVERT TO A WORD COUNT
	MOVSI	T2,(<PM.DCD>B2+PM.WRT+PM.PUB+PM.KPM+PM.SWB) ;DIRECT POINTER + WRITABLE
	PUSH	P,SYSORG##	;SAVE SYSORG
	PUSH	P,MONVFF##	;WILL BE CHANGED BY ONCMAP
	MOVE	T3,BTSPFF	;FIRST PHYSICAL ADDRESS FOLLOWING BOOTSTRAP
	MOVEM	T3,SYSORG##	;RESET SYSORG SO WE MARK THOSE PAGES AS TAKEN
	PUSHJ	P,ONCMAP##	;MAP THE PAGES
	POP	P,MONVFF##	;RESTORE FIRST FREE
	POP	P,SYSORG##	;RESTORE SYSORG
	MOVE	T1,P1		;GET STARTING PHYSICAL ADDRESS
	LSH	T1,W2PLSH##	;CONVERT TO A PAGE NUMBER
	HRLI	T1,(<PM.DCD>B2+PM.WRT+PM.PUB+PM.SWB) ;DIRECT POINTER + WRITABLE

BOOTM3:	MOVEM	T1,(P2)		;STORE IN SECTION MAP
	AOS	T1		;ADVANCE TO NEXT PAGE
	AOBJN	P2,BOOTM3	;LOOP
	CLRPGT	(0,.EUPMP)	;UPDATE CHANGES IN PAGER
IFE FTXMON,<
	MOVE	T1,BOOTVA##	;VIRTUAL ADDRESS OF BOOT
	HLRE	T1,.BTSIZ(T1)	;- LENGTH IN PAGES OF BOOT
	MOVMS	T1		;LENGTH IN PAGES
	LSH	T1,P2WLSH##	;LENGTH IN WORDS
	ADDM	T1,MONVFF##	;UPDATE TO REFLECT PAGES ALLOCATED FOR BOOT
>
	POPJ	P,		;DONE
SUBTTL	ONCE-ONLY/BOOTSTRAP INTERFACE -- COPY MONITOR FILESPEC


BOOTFX:	SKIPN	W,BOOTPA##	;PHYSICAL ADDRESS OF BOOT ORIGIN
	POPJ	P,		;NOT THERE
	MOVE	U,W		;COPY IT
	HRRI	U,.BTSIZ(W)	;POINT TO SIZE WORD
	PUSHJ	P,REFMEM##	;FETCH
	HRRI	U,.BTDEV(W)	;POINT TO START OF FILESPEC
	MOVSI	T2,-BOOTLN	;-LENGTH OF TRANSLATION TABLE
BOOTF1:	HLRZ	U,BOOTBL(T2)	;GET AN OFFSET
	ADD	U,W		;INDEX INTO BOOT VECTOR
	PUSHJ	P,REFMEM##	;FETCH WORD
	HRRZ	T3,BOOTBL(T2)	;GET STORAGE LOCATION
	MOVEM	T1,@T3		;SAVE WORD
	AOBJN	T2,BOOTF1	;LOOP
	POPJ	P,		;DONE


BOOTBL:	.BTDEV,,DEVICE		;DEVICE
	.BTFIL,,FNAME		;FILE NAME
	.BTEXT,,FEXT		;EXTENSION
	.BTPTH+0,,PPN		;PPN
	.BTPTH+1,,SFDLST+0	;SFD #1
	.BTPTH+2,,SFDLST+1	;SFD #2
	.BTPTH+3,,SFDLST+2	;SFD #3
	.BTPTH+4,,SFDLST+3	;SFD #4
	.BTPTH+5,,SFDLST+4	;SFD #5
BOOTLN==.-BOOTBL		;LENGTH OF TABLE
SUBTTL	ONCE-ONLY/BOOTSTRAP INTERFACE -- BUILD BOOTXT


BSTRNG:	JUMPE	W,CPOPJ		;RETURN IF COULDN'T FIND BOOTS
	MOVEI	T1,BOOTYO	;ROUTINE TO BUILD UP STRING
	MOVEM	T1,.CPTOA##	; SAVE AS TTY OUTPUT ROUTINE
	MOVE	T1,[POINT 7,BOOTXT##]	;BYTE POINTER
	MOVEM	T1,BOOTBP	;STORE THE POINTER
	MOVEI	T1,[ASCIZ ./D .];FIRST DO A DUMP
	PUSHJ	P,CONMES##	; ..
	SKIPN	T2,DEVICE	;A DEVICE SPECIFIED?
	POPJ	P,		;NO, LEAVE DEFAULT ALONE
	MOVEM	T2,STRMON##
	PUSHJ	P,PRNAME##	;YES--PUT IN COMMAND STRING
	MOVEI	T1,[ASCIZ /:/]	;DELIMIT WITH A COLON
	PUSHJ	P,CONMES##	; ..
	SKIPN	T2,FNAME	;FILE NAME?
	JRST	BSTRN2		;NO
	MOVEM	T2,FILMON##
	PUSHJ	P,PRNAME##	;PUT IN NAME
	HLLZ	T2,FEXT		;PICK UP EXTENSION
	JUMPE	T2,BSTRN2	;NONE--LOOK FOR PPN
	MOVEM	T2,EXTMON##
	LSH	T2,-6		;PUT IN A DOT
	TLO	T2,(16B5)	; ..
	PUSHJ	P,PRNAME##	;TOSS IN EXT
BSTRN2:	SKIPN	T2,PPN		;A PPN?
	JRST	BSTRN5		;NO
	MOVEM	T2,PPNMON##
	PUSHJ	P,PRLBK##	;FIRST A BRACKET
	HLRZ	T1,PPN		;GET PROJECT
	PUSHJ	P,PRTDI8##	;PRINT IN OCTAL
	PUSHJ	P,PRCOM##	;ADD A COMMA
	HRRZ	T1,PPN		;GET PROG NUMBER
	PUSHJ	P,PRTDI8##	;PRINT PROG
	PUSH	P,P1		;SAVE P1
	MOVSI	P1,-5		;SETUP AOBJN POINTER TO SFDLST
BSTRN3:	SKIPN	T2,SFDLST(P1)	;NEXT SFD SPECIFIED?
	JRST	BSTRN4		;NO
	PUSHJ	P,PRCOM##	;PRINT COMMA
	PUSHJ	P,PRNAME##	;PRINT SFD NAME 
	AOBJN	P1,BSTRN3	;LOOP FOR ALL
BSTRN4:	POP	P,P1		;RESTORE P1
	PUSHJ	P,PRRBK##	;ADD IN RIGHT SQUARE BRACKET
	MOVE	T1,[SFDLST,,SFDMON##] ;COPY SFD LIST TO
	BLT	T1,SFDMON##+4	;WHERE MONITOR WANTS IT
BSTRN5:	MOVEI	T3,15
	IDPB	T3,BOOTBP
	MOVEI	T3,0
	IDPB	T3,BOOTBP
	POPJ	P,0
BOOTYO:	IDPB	T3,BOOTBP	;STORE BYTE IN STRING
	POPJ	P,0		;RETURN

BOOTBP:	POINT	7,BOOTXT##	;RELOAD STRING POINTER
SUBTTL	ONCE-ONLY/BOOTSTRAP INTERFACE -- BUILD THE SSL


BLDSSL::SE1ENT			;ENTER SECTION ONE
	MOVEI	T1,.BTSSL	;OFFSET
	SKIPE	PRESSL		;USING THE PRESERVED SSL?
	PUSHJ	P,BTDATA##	;BOOTSTRAP AVAILABLE?
	  POPJ	P,		;NO
	MOVEI	T3,[ASCIZ/system search list/]
	PUSHJ	P,SETENT	;SET POINTERS
BLDSS1:	PUSHJ	P,NXTENT	;GET NEXT ENTRY
	  JRST	BLDSS2		;NO MORE DATA--ALL STRUCTURES VALID
	PUSHJ	P,FNSTR##	;DOES THIS STRUCTURE EXIST?
	  PUSHJ	P,BADSTR	;NO--COMPLAIN TO OPERATOR
	JRST	BLDSS1		;GO CHECK OUT THE NEXT STRUCTURE
BLDSS2:	PUSHJ	P,RSTENT	;RESET POINTERS
	SKIPN	PRECNT		;ANY ENTRIES FOUND?
	AOS	PREERR		;NO--CALL THIS AN ERROR
	SKIPN	PREERR		;ANY ERRORS?
	JRST	BLDSS3		;NO
	PUSHJ	P,BLDDSK	;TELL OPERATOR WE WILL USE DISK DATA BASE
	POPJ	P,		;GIVE UP
BLDSS3:	HLRZ	T1,SYSSTR##	;POINT TO START OF STR DB CHAIN
BLDSS4:	SETOM	STRSRC##(T1)	;EMPTY THE SSL
	HLRZ	T1,STRSYS##(T1)	;GET NEXT STR DB
	JUMPN	T1,BLDSS4	;LOOP
BLDSS5:	PUSHJ	P,NXTENT	;GET NEXT ENTRY
	  JRST	CPOPJ1		;RETURN
	PUSHJ	P,FNSTR##	;FIND THE STR DB
	  JRST	BLDSS5		;CAN'T HAPPEN
	HRRZ	T2,BLDPTR	;GET RELATIVE OFFSET IN TABLE
	MOVEM	T2,STRSRC##(P2)	;MAKE THAT THE POSITION IN THE SSL
	JRST	BLDSS5		;LOOP FOR THE NEXT STRUCTURE
BLDASL::SE1ENT			;ENTER SECTION ONE
	MOVEI	T1,.BTASL	;OFFSET
	SKIPE	PREASL		;USING THE PRESERVED ASL?
	PUSHJ	P,BTDATA##	;BOOTSTRAP AVAILABLE?
	  POPJ	P,		;NO
	MOVEI	T3,[ASCIZ/active swapping list/]
	PUSHJ	P,SETENT	;SET POINTERS
BLDAS1:	PUSHJ	P,NXTENT	;GET NEXT ENTRY
	  JRST	BLDAS2		;NO MORE DATA--ALL UNITS VALID
	MOVE	T2,T1		;PUT NAME IN PROPER PLACE
	PUSHJ	P,FNDUNI##	;DOES THIS UNIT EXIST?
	  JRST	[PUSHJ P,BADUNI	;NO--COMPLAIN TO OPERATOR
		 JRST  BLDAS1]	;GO CHECK OUT THE NEXT UNIT
	LDB	T1,UNYK4S##	;GET SWAPPING SPACE ALLOCATED ON UNIT
	SKIPG	T1		;HAVE ANY?
	PUSHJ	P,BLDSWP	;NO--COMPLAIN TO OPERATOR
	JRST	BLDAS1		;GO CHECK OUT THE NEXT UNIT
BLDAS2:	PUSHJ	P,RSTENT	;RESET POINTERS
	SKIPN	PRECNT		;ANY ENTRIES FOUND?
	AOS	PREERR		;NO--CALL THIS AN ERROR
	SKIPN	PREERR		;ANY ERRORS?
	JRST	BLDAS3		;NO
	PUSHJ	P,BLDDSK	;TELL OPERATOR WE WILL USE DISK DATA BASE
	POPJ	P,		;GIVE UP
BLDAS3:	HLRZ	T1,SYSUNI##	;POINT TO START OF UDB CHAIN
BLDAS4:	SETOM	UNISUN##(T1)	;EMPTY THE ASL
	HLRZ	T1,UNISYS##(T1)	;GET NEXT UDB
	JUMPN	T1,BLDAS4	;LOOP
BLDAS5:	PUSHJ	P,NXTENT	;GET NEXT ENTRY
	  JRST	CPOPJ1		;DONE
	MOVE	T2,T1		;PUT NAME IN PROPER PLACE
	PUSHJ	P,FNDUNI##	;FIND THE UDB
	  JRST	BLDAS5		;CAN'T HAPPEN
	HRRZ	T2,BLDPTR	;GET RELATIVE OFFSET IN TABLE
	MOVEM	T2,UNISUN##(U)	;MAKE THAT THE POSITION IN THE ASL
	JRST	BLDAS5		;LOOP FOR THE NEXT UNIT
BLDSDL::SE1ENT			;ENTER SECTION ONE
	MOVEI	T1,.BTSDL	;OFFSET
	SKIPE	PRESDL		;USING THE PRESERVED SDL?
	PUSHJ	P,BTDATA##	;BOOTSTRAP AVAILABLE?
	  POPJ	P,		;NO
	MOVEI	T3,[ASCIZ/system dump list/]
	PUSHJ	P,SETENT	;SET POINTERS
BLDSD1:	PUSHJ	P,NXTENT	;GET NEXT ENTRY
	  JRST	BLDSD2		;NO MORE DATA--ALL STRUCTURES VALID
	PUSHJ	P,FNSTR##	;DOES THIS STRUCTURE EXIST?
	  PUSHJ	P,BADSTR	;NO--COMPLAIN TO OPERATOR
	JRST	BLDSD1		;GO CHECK OUT THE NEXT STRUCTURE
BLDSD2:	PUSHJ	P,RSTENT	;RESET POINTERS
	SKIPN	PRECNT		;ANY ENTRIES FOUND?
	AOS	PREERR		;NO--CALL THIS AN ERROR
	SKIPN	PREERR		;ANY ERRORS?
	JRST	BLDSD3		;NO
	PUSHJ	P,BLDDSK	;TELL OPERATOR WE WILL USE DISK DATA BASE
	POPJ	P,		;GIVE UP
BLDSD3:	HLRZ	T1,SYSSTR##	;POINT TO START OF STR DB CHAIN
BLDSD4:	SETOM	STRSDL##(T1)	;EMPTY THE SDL
	HLRZ	T1,STRSYS##(T1)	;GET NEXT STR DB
	JUMPN	T1,BLDSD4	;LOOP
BLDSD5:	PUSHJ	P,NXTENT	;GET NEXT ENTRY
	  JRST	CPOPJ1		;DONE
	PUSHJ	P,FNSTR##	;FIND THE STR DB
	  JRST	BLDSD5		;CAN'T HAPPEN
	HRRZ	T2,BLDPTR	;GET RELATIVE OFFSET IN TABLE
	MOVEM	T2,STRSDL##(P2)	;MAKE THAT THE POSITION IN THE SDL
	JRST	BLDSD5		;LOOP FOR THE NEXT STRUCTURE
SUBTTL	ONCE-ONLY/BOOTSTRAP INTERFACE -- MISCELLANEOUS ROUTINES


; SET UP TO ACCESS BOOTSTRAP VECTOR ENTRIES
; CALL:	MOVE	T1, LENGTH OF TABLE
;	MOVE	T2, TABLE ADDRESS
;	MOVE	T3, IDENTIFYING TEXT (OR -1 IF NOT TO STORE ANY)
;	PUSHJ	P,SETENT
;	<RETURN>

SETENT:	ADJSP	T1,-1		;PREDECREMENT POINTER
	SUBI	T2,1		;PREDECREMENT ADDRESS
	MOVEM	T1,BLDPTR	;SAVE POINTER
	MOVEM	T1,SAVPTR	;MAKE A COPY
	MOVEM	T2,BLDTBL	;SAVE ADDRESS
	MOVEM	T2,SAVTBL	;MAKE A COPY
	SKIPL	T3		;STORE BUILD TEXT?
	MOVEM	T3,BLDTXT	;YES
	SETZM	PRECNT		;CLEAR COUNT OF ENTRIES FOUND
	SETZM	PREERR		;CLEAR ERROR FLAG
	POPJ	P,		;RETURN


; RESET THE VECTOR ENTRY POINTERS
; CALL:	PUSHJ	P,RSTENT
;	<RETURN>

RSTENT:	MOVE	T1,SAVPTR	;GET SAVED POINTER
	MOVEM	T1,BLDPTR	;RESET IT
	MOVE	T1,SAVTBL	;GET SAVED ADDRESS
	MOVEM	T1,BLDTBL	;RESER IT
	POPJ	P,		;RETURN


; RETRIEVE THE NEXT ENTRY
; CALL:	PUSHJ	P,NXTENT
;	  <NON-SKIP>		;RAN OUT OF DATA
;	<SKIP>			;T1 CONTAINS THE ENTRY

NXTENT:	MOVE	T1,BLDPTR	;GET AOBJN POINTER
	AOBJP	T1,CPOPJ	;RETURN IF DONE
	MOVEM	T1,BLDPTR	;UPDATE
	AOS	BLDTBL		;ADVANCE POINTER
	SKIPN	T1,@BLDTBL	;GET NEXT ENTRY
	JRST	NXTENT		;EMPTY SLOT--TRY AGAIN
	AOS	PRECNT		;COUNT THE ENTRY
	JRST	CPOPJ1		;RETURN
; TELL THE OPERATOR THE PRESERVED DATA CANNOT BE USED
; CALL:	PUSHJ	P,BLDDSK
;	<RETURN>

BLDDSK:	SKIPN	FSTTIM		;ONLY OUTPUT THE MESSAGE ONCE
	POPJ	P,
	MOVEI	T1,[ASCIZ /[Rebuilding the /]
	PUSHJ	P,ICONM		;TYPE TEXT
	MOVE	T1,BLDTXT	;GET TEXT
	PUSHJ	P,CONMES##	;TYPE IT
	MOVEI	T1,[ASCIZ/ from the HOMe blocks]
/]
	PUSHJ	P,CONMES##	;TYPE TEXT
	PJRST	CRLFOP##	;APPEND A CRLF AND RETURN


; TELL THE OPERATOR THAT A STRUCTURE OR LOGICAL UNIT IS MISSING
; CALL:	MOVE	T1, SIXBIT NAME
;	PUSHJ	P,BADSTR/BADUNI
;	<RETURN>

BADSTR:	SKIPA	T2,[[ASCIZ/%Structure /]]
BADUNI:	MOVEI	T2,[ASCIZ/%Logical unit /]
	AOS	PREERR		;FLAG THE ERROR
	PUSH	P,T1		;SAVE STRUCTURE OR LOGICAL UNIT NAME
	MOVE	T1,T2		;POINT TO TEXT
	PUSHJ	P,ICONM		;TYPE IT
	POP	P,T2		;GET STRUCTURE NAME BACK
	PUSHJ	P,PRNAME##	;TYPE IT
	MOVEI	T1,[ASCIZ/ missing from the /]
	PUSHJ	P,CONMES##	;TYPE TEXT
	MOVE	T1,BLDTXT	;GET IDENTIFIER
	PUSHJ	P,CONMES##	;TYPE IT
	PJRST	CRLFOP##	;APPEND A CRLF AND OUTPUT


; TELL THE OPERATOR A UNIT HAS NO SWAPPING SPACE ALLOCATED
; CALL:	MOVE	U, UDB ADDRESS
;	PUSHJ	P,BLDSWP
;	<RETURN>

BLDSWP:	AOS	PREERR		;FLAG THE ERROR
	MOVEI	T1,[ASCIZ/%No swapping space allocated on /]
	PUSHJ	P,ICONM		;TYPE TEXT
	MOVE	T2,UNINAM##(U)	;GET PHYSICAL UNIT NAME
	PUSHJ	P,PRNAME##	;TYPE IT
	SKIPN	UNIHID##(U)	;HAVE A UNIT-ID?
	PJRST	CRLFOP##	;NO--APPEND A CRLF AND OUTPUT
	MOVEI	T1,[ASCIZ/ (/]	;SEPARATE FROM
	PUSHJ	P,CONMES##	; PHYSICAL NAME
	MOVE	T2,UNIHID##(U)	;GET LOGICAL UNIT NAME
	PUSHJ	P,PRNAME##	;TYPE IT
	MOVEI	T1,[ASCIZ /)/]	;TERMINATE
	PUSHJ	P,CONMES##	;TYPE TEXT
	PJRST	CRLFOP##	;APPEND A CRLF AND OUTPUT
	SUBTTL	ONCE-ONLY HIDDEN SYMBOL TABLE SETUP

SYTBFX:	SKIPGE	P1,.JBSYM##	;GET POINTER TO SYMBOL TABLE
	JRST	SYTBF1		;A NON-EXTENDED SYMBOL TABLE
	SKIPN	U,P1		;COPY ADDRESS TO U, SKIP IF LOADED WITH SYMBOLS
	POPJ	P,		;NO SYMBOLS, NOT MUCH WE CAN DO
	HRRI	U,.SYSTB+.SYTYP(P1) ;GET FLAGS,,LENGTH OF DEFINED SYMBOL TABLE
	PUSHJ	P,REFMEM##	;FETCH THE CONTENTS
	AND	T1,[SY.LEN]	;KEEP JUST THE LENGTH
	PUSH	P,T1		;SAVE LENGTH
	MOVNS	T1		;GET -VE LENGTH OF SYMBOL TABLE
	MOVSM	T1,SYMPTR	;SAVE (NOTE ASSUMPTION ON .LT. 256K OF SYMBOLS)
	HRRI	U,.SYSTB+.SYADR(P1) ;GET ADDRESS OF DEFINED SYMBOL TABLE
	PUSHJ	P,REFMEM##	;FETCH THE CONTENTS
	HRRM	T1,SYMPTR	;SAVE IN-SECTION ADDRESS
	HRRI	U,.SYSTB+.SYSTL+.SYTYP(P1) ;GET FLAGS,,LENGTH OF UNDEFINED S.T.
	PUSHJ	P,REFMEM##	;FETCH THE CONTENTS
	AND	T1,[SY.LEN]	;KEEP JUST THE LENGTH
	ADDM	T1,(P)		;TOTAL LENGTH OF SYMBOL TABLE
	MOVNS	T1		;GET -VE LENGTH OF UNDEFINED SYMBOL TABLE
	MOVSM	T1,USYPTR	;SAVE
	HRRI	U,.SYSTB+.SYSTL+.SYADR(P1) ;GET ADDRESS OF UNDEFINED S.T.
	PUSHJ	P,REFMEM##	;FETCH THE CONTENTS
	HRRM	T1,USYPTR	;SAVE IN-SECTION ADDRESS
	MOVE	T2,T1		;COPY TO T2
	LSH	T2,W2PLSH##	;CONVERT TO STARTING PAGE NUMBER
	ADD	T1,(P)		;ADD IN LENGTH OF SYMBOL TABLE
	ADDI	T1,PG.BDY##	;ROUND UP TO END OF PAGE
	LSH	T1,W2PLSH##	;CONVERT TO ENDING PAGE NUMBER +1
	SUB	T1,T2		;NUMBER OF PAGES IN SYMBOL TABLE
	PUSHJ	P,MOVSTB	;MOVE THE SYMBOL TABLE
	ADJSP	P,-1		;CLEAN UP THE STACK
	DMOVE	T2,SYMPTR	;GET BACK PSEUDO .JBSYM/.JBUSY
	TRZ	T2,-1-PG.BDY##	;KEEP JUST IN-PAGE PORTION
	TRO	T2,MONORG	;RELOCATED .JBSYM
	TRZ	T3,-1-PG.BDY##	;KEEP JUST IN-PAGE PORTION
	TRO	T3,MONORG	;RELOCATED .JBUSY
	MOVEM	T2,.CPEDV##+.EDSYM ;STORE THE POINTERS
	MOVEM	T3,.CPEDV##+.EDUSY
	MAP	T1,.CPEDV##	;GET PHYSICAL EDV ADDRESS
	TLZ	T1,-1-MXSECN	;KEEP JUST ADDRESS
	MOVEM	T1,.JBEDV##	;INFORM DDT OF HIDDEN SYMBOL TABLE
	PJRST	SYTBBD		; AND ZAP OLD-STYLE POINTERS
;HERE FOR NON-EXTENDED SYMBOL TABLE (KS)

SYTBF1:	HLRE	T1,.JBSYM##	;GET LENGTH OF SYMBOL TABLE
	MOVMS	T1		;GET REAL LENGTH
	HRRZ	T2,.JBSYM##	;ADDRESS OF SYMBOL TABLE
	ADDI	T1,(T2)		;FIRST ADDRESS OUTSIDE OF THE SYMBOL TABLE
	SKIPN	T2,.JBUSY##	;IN CASE ANY UNDEF'S STILL LYING AROUND
	HRRZ	T2,.JBSYM##	;NONE, GET SYMBOL TABLE AGAIN
	ANDI	T2,-1-PG.BDY##	;MOVING WHOLE PAGES, ADJUST
	SUBI	T1,(T2)		;NOW KNOW NUMBER OF WORDS TO MOVE
	ADDI	T1,PG.BDY##	;BUT STILL HAVE TO ROUND IT UP
	LSH	T1,W2PLSH##	;NOW HAVE THE NUMBER OF PAGES
	CAILE	T1,SYMSIZ##	;ENOUGH SPACE (SYMBK1 IN COMMON.MAC)
	MOVEI	T1,SYMSIZ##	;NO, REDUCE TO MAXIMUM
	LSH	T2,W2PLSH##	;STARTING PAGE NUMBER
	PUSHJ	P,MOVSTB	;MOVE THE SYMBOL TABLE
	MOVE	T2,.JBSYM##	;GET .JBSYM
	MOVE	T3,.JBUSY##	;GET .JBUSY
	PJRST	FILEDX		;FILL IN EDV AND RETURN

;FINISH SYMBOL TABLE SETUP BY FILLING IN THE EXEC DATA VECTOR.

FILEDV:	DMOVE	T2,SYMPTR	;FETCH THE VALUES
FILEDX:	TRZ	T2,-1-PG.BDY##	;KEEP JUST IN-PAGE PORTION
	TRO	T2,MONORG	;RELOCATED .JBSYM
	TRZ	T3,-1-PG.BDY##	;KEEP JUST IN-PAGE PORTION
	TRO	T3,MONORG	;RELOCATED .JBUSY
	MOVEI	T1,[		;SUBROUTINE TO CALL
		MOVEM T2,.CPEDV##-.CPCDB##+.EDSYM(P1) ;STORE RELOCATED .JBSYM
		MOVEM T3,.CPEDV##-.CPCDB##+.EDUSY(P1) ;STORE RELOCATED .JBUSY
		MOVE T4,.CPSYB##+1 ;COUNT OF MAP WORDS TO REPLACE
		MOVEM T4,.CPSYB##-.CPCDB##+1(P1) ;STORE
		POPJ P,]
	PUSHJ	P,CPUAPP##	;FILL IN ALL CPU'S EDV'S
	PUSHJ	P,SETEDV##	;SETUP REMAINDER OF THE EDV
SYTBBD:	SETZM	.JBSYM##	;FORGET ABOUT THESE NOW (OR IF AN ERROR)
	SETZM	.JBUSY##	;...
	POPJ	P,		;RETURN

SYMPTR:	BLOCK	1		;COPY OF .JBSYM TO STUFF IN EDV
USYPTR:	BLOCK	1		;COPY OF .JBUSY TO STUFF IN EDV
;ROUTINE TO MOVE THE SYMBOL TABLE TO A HIDDEN PLACE.
;CALL:
;	T1/ NUMBER OF PAGES TO MOVE
;	T2/ FIRST PAGE TO MOVE
;	PUSHJ	P,MOVSTB
;RETURN:
;	CPOPJ ALWAYS

MOVSTB:	MOVEM	T1,.CPSYB##+1	;NUMBER OF PAGES IN HIDDEN SYMBOL TABLE
	PUSH	P,P1		;SAVE THE AC'S
	PUSH	P,P2		;...
	MOVN	P1,T1		;GET -VE NUMBER OF PAGES TO MOVE
	HRLZS	P1		;BUILD AN AOBJN WORD
	HRRI	P1,-1(T1)	;BACKWARDS INDEX FOR SYMBK1
	MOVE	P2,T2		;FIRST PAGE NUMBER
	ADDI	P2,-1(T1)	; PLUS COUNT-1 GIVES LAST PAGE NUMBER
	PUSH	P,MONVFF##	;GOING TO FAKE OUT ONCMAP, SAVE REAL ORIGIN
MOVST1:	MOVE	T1,P2		;PAGE OF SYMBOLS
	MOVE	T2,.CPMAP##	;MAP ADDRESS
	HRLI	T1,(<PM.DCD>B2)	;ALLOW ACCESS
	MOVEM	T1,.ECKSM/PAGSIZ##(T2) ;MAKE ADDRESSABLE

	MOVEI	T1,.EUPMP	;WHERE WE WANT IT TO BE MAPPED
	MOVEM	T1,MONVFF##	;SO WE DON'T CHEW UP LOTS OF VIRTUAL SPACE
	MOVEI	T1,PAGSIZ##	;ONLY ALLOCATE ONE PAGE AT A TIME
	MOVSI	T2,(<PM.DCD>B2+PM.WRT+PM.PUB)
	SKIPN	[CPUN##-1]
	TDO	T2,[PM.CSH]
	PUSHJ	P,ONCMAP##	;ALLOCATE A PAGE FROM SOMEWHERE
	HRLI	T1,.ECKSM	;OLD SYMBOL TABLE LOCATION (RE-MAPPED)
	HRRI	T1,.EUPMP	;NEW, SAFER, LOCATION
	BLT	T1,.EUPMP+PAGSIZ##-1 ;MOVE PART OF THE SYMBOL TABLE
	MOVE	T1,.CPMAP##	;GET MAP ADDRESS
	MOVE	T1,.EUPMP/PAGSIZ##(T1) ;GET MAP CONTENTS
	MOVEM	T1,SYMBK1##(P1)	;STORE SO DDT CAN RE-MAP IT IN
	ANDI	T1,17777	;ISOLATE PAGE NUMBER
	IDIVI	T1,^D36		;COMPUTE POSITION IN NXMTAB
;	MOVE	T2,BITTBL##(T2)	;GET BIT FOR PAGE
	MOVN	T3,T2		;BITTBL NOT SET UP YET
	MOVSI	T2,(1B0)	; SO WE MUST DO IT BY HAND
	LSH	T2,(T3)		;GET THE BIT
	IORM	T2,NXMTAB##(T1)	;MARK THE PAGE SO IT DOESN'T GET RE-USED
	SUBI	P1,2		;EFFECT A "BACKWARDS" AOBJN
	SUBI	P2,1		;NEXT PAGE OF THE SYMBOL TABLE
	AOBJN	P1,MOVST1	;MOVE THE WHOLE THING
	POP	P,MONVFF##	;BACK TO NORMAL ALLOCATION NOW
	POP	P,P2		;RESTORE AC'S
	POP	P,P1		;...
	POPJ	P,		;RETURN
	SUBTTL	COMPUTE MONITOR SYMBOL TABLE CHECKSUM, FIXUP PATSIZ

PATFIX:	SETZM	MSTCKS##	;INITIALIZE MONITOR SYMBOL TABLE CHECKSUM
	SKIPGE	P1,.JBSYM##	;GET POINTER TO SYMBOL TABLE
	JRST	PATFI1		;A NON-EXTENDED SYMBOL TABLE
	SKIPN	U,P1		;COPY ADDRESS TO U, SKIP IF LOADED WITH SYMBOLS
	POPJ	P,		;NO SYMBOLS, NOT MUCH WE CAN DO
	HRRI	U,.SYCNT(P1)	;GET LENGTH OF VECTOR
	PUSHJ	P,REFMEM##	;FETCH THE CONTENTS
	CAIGE	T1,.SYSTB+<.SYSTL*2> ;IS BLOCK LONG ENOUGH?
	STOPCD	SYTBBD,DEBUG,SYVCTS, ;++SYMBOL VECTOR TOO SHORT
	HRRI	U,.SYSTB+.SYTYP(P1) ;GET FLAGS,,LENGTH OF DEFINED SYMBOL TABLE
	PUSHJ	P,REFMEM##	;FETCH THE CONTENTS
	AND	T1,[SY.LEN]	;KEEP JUST THE LENGTH
	PUSH	P,T1		;SAVE LENGTH
	HRRI	U,.SYSTB+.SYADR(P1) ;GET ADDRESS OF DEFINED SYMBOL TABLE
	PUSHJ	P,REFMEM##	;FETCH THE CONTENTS
	MOVE	P1,T1		;COPY ADDRESS TO P1
	POP	P,P2		;LENGTH TO P2
	JRST	PATFI2		;PROCEED

PATFI1:	HLRE	P2,P1		;GET -VE LENGTH OF SYMBOL TABLE
	MOVMS	P2		;MAKE IT POSITIVE
	HRRZS	P1		;ISOLATE SYMBOL TABLE ADDRESS
PATFI2:	SKIPA	T1,[RADIX50 4,PAT] ;FIND "PAT" GLOBAL, SKIP AOS OF P1
PATLOP:	AOS	P1		;ADVANCE POINTER INTO SYMBOL TABLE
	PUSHJ	P,PATMAP	;MAP A WORD OF THE SYMBOL TABLE
	MOVE	T3,(T4)		;FETCH IT
	EXCH	T3,MSTCKS##	;SWAP WITH PREVIOUS CHECKSUM
	ROT	T3,1		;MUNGE IT AROUND
	ADD	T3,MSTCKS##	;ADD IN PREVIOUS CHECKSUM
	EXCH	T3,MSTCKS##	;PUT IT BACK
	TRNN	P2,1		;IS THIS THE SYMBOL VALUE WORD?
	SOJA	P2,PATLOP	;NO, GO DO IT
	PUSHJ	P,PATMA1	;MAP PREVIOUS WORD OF THE SYMBOL TABLE
	CAMN	T1,(T4)		;WAS THIS "PAT"?
	JRST	GOTPAT		;YES
PATLO1:	SOJG	P2,PATLOP	;GET NEXT SYMBOL,VALUE PAIR
	POPJ	P,		;NOT FOUND
GOTPAT:	PUSHJ	P,PATMAP	;MAP THE SYMBOL VALUE WORD
	HRRZ	T3,(T4)		;GET VALUE OF "PAT" SYMBOL
	HRRZ	T4,PATSIZ	;CHECK WITH PATCHED INDICATION
	CAILE	T3,(T4)		;USE MAX
	HRRM	T3,PATSIZ
	JRST	PATLO1		;GET NEXT SYMBOL,VALUE PAIR
;ROUTINE TO MAP A REFERENCE TO THE SYMBOL TABLE.  CALLED WITH ADDRESS
;OF WORD TO REFERENCE IN P1, RETURNS EXEC VIRTUAL ADDRESS OF THE WORD
;IN T4.

PATMA1:	MOVE	T3,P1		;GET ADDRESS
	SOSA	T3		;DECREMENT AND SKIP
PATMAP:	MOVE	T3,P1		;GET ADDRESS
	SKIPL	.JBSYM##	;USING EXTENDED SYMBOL TABLE?
	JRST	PATMA2		;YES
	HRRZ	T4,P1		;NO, JUST COPY THE ADDRESS (HALF-WORD ALWAYS)
	POPJ	P,		;RETURN

PATMA2:	IDIVI	T3,PAGSIZ##	;T3 GETS PAGE NUMBER, T4 GETS OFFSET IN PAGE
	MOVEI	T4,.ECKSM(T4)	;GET VIRTUAL ADDRESS
	CAMN	T3,PATSLT	;HAS IT CHANGED?
	POPJ	P,		;NO, NOTHING ELSE TO DO
	MOVEM	T3,PATSLT	;YES, REMEMBER FOR NEXT TIME
	EXCH	T4,.CPMAP##	;SAVE T4, GET EXEC MAP ADDRESS
	HRLI	T3,(<PM.DCD>B2+PM.PUB) ;GET BITS
	MOVEM	T3,.ECKSM/PAGSIZ##(T4) ;STORE ENTRY IN MAP
	EXCH	T4,.CPMAP##	;RESTORE T4, RESTORE EXEC MAP ADDRESS
	CLRPGT	(0,.ECKSM)	;FLUSH MAPPING
	POPJ	P,		;RETURN

PATSLT:	0
	SUBTTL	SET UP SYSSIZ, CHECK FOR BREAKPOINTS AND NO EDDT

PATSIZ::MOVEI	T1,PAT##	;SET SIZE OF SYSTEM TO BEGINING OF PATCH AREA IN CASE
	MOVEM	T1,SYSSIZ##	; ONCE ONLY DIALOG RESTARTED BEFORE OVERWRITTEN
				;PATSIZ SHOULD BE UPDATED EVERY TIME A PATCH IS MADE
PATSI3:	MOVSI	T2,-^D12	;NUMBER OF EDDT BREAKPOINTS
	CAIA			;ENTER LOOP
PATSI4:	ADDI	T2,$2B##-$1B##-1;OFFSET TO NEXT BREAKPOINT
	SKIPG	$1B##(T2)	;THIS BREAKPOINT SET?
	AOBJN	T2,PATSI4	;NO, CHECK THE REST
	JUMPGE	T2,PATNBK	;IF .GE. 0 THEN NO BREAKPOINTS SET
	CAIL	T1,DDTEND##	;YES--SEE IF EDDT
	JRST	PATNBK		;YES--CONSISTENT SO PROCEED
;HERE WHEN BREAKPOINTS BUT NO EDDT
	MOVEI	T1,[ASCIZ /?Breakpoints but no EDDT
Do you want to keep EDDT? (Y or <CR>) /]
	PUSHJ	P,YESNO		;ASK QUES. GET ANSWER
	  JRST	.+2		;NO--REMOVE BREAKPOINTS
	JRST	PATKBK		;YES--KEEP EDDT
	MOVEI	T1,[ASCIZ /Type "$B $P"
/]
	PUSHJ	P,ICONM		;OUTPUT STATEMENT
	PUSHJ	P,OPOUT		;ISSUE IT
	XCT	BPTXCT##	;FORCE A BREAKPOINT
	JRST	PATSI3		;CHECK AGAIN
PATKBK:	MOVEI	T1,DDTEND##	;KEEP EDDT
	MOVEM	T1,SYSSIZ##
PATNBK:	MOVSI	T2,(CAI)
	CAIL	T1,DDTEND##	;SEE IF EDDT INTACT
	TDZA	T3,T3		;YES--CLEAR MASK (PRESERVE DEBUGF BITS)
	SKIPA	T3,[DF.BPT]	;GET MASK OF ALL CPUS
	HLLM	T2,IOG5##	;LEAVE 401 ALONE
	ANDCAM	T3,DEBUGF##	;CLEAR CPU MASK IF NO EDDT
	PUSHJ	P,CPUDDT##	;MAKE SURE CPUS CAN ENTER EDDT
	POPJ	P,
	SUBTTL	THE ONCE-ONLY CODE

	ENTRY	ONCE
ONCE::	0
	MOVE	T1,[<PM.DCD>B2+PM.WRT+PM.PUB+NUPMPP##]
	MOVEM	T1,NLUPMP##+.UMUPM
	MOVEM	T1,NLUPMP##+.UMUPT
	MOVEM	T1,NLUPMP##+.UMUUP
IFN FTXMON,<
	MOVSI	T1,(LG.LAB+LG.LPC+1B8+1B11)
	MOVEM	T1,.USUPF	;TO DO A USERAC AND LOAD PCS=0 FOR THE NULL JOB
>
	CLRPGT	(0)

	MOVE	P,.CPNPD##	;WE NEED A PUSH DOWN LIST
HIDONE:	JFCL	HITHRU		;PATCHED TO A JRST WHEN THE HIGH SEGMENT HAS
				; BEEN MAPPED (TO MAKE RESTARTS WORK)
	MOVEI	T1,MONEND##-MONORG ;HIGHEST ADDRESS CONTAING DATA IN THE HI SEG
	TRZE	T1,PG.BDY##	;ROUND UP
	ADDI	T1,PAGSIZ##	;LENGTH OF THE HIGH SEGMENT IN WORDS
	MOVEM	T1,SYSLEN##	;STORE THE LENGTH OF THE HIGH SEGMENT
	PUSHJ	P,SUNXMT	;SETUP NXMTAB AND FIND HIGHEST EXISTANT PAGE
	MOVEM	T4,SYSORG##	;SAVE HIGHEST ADDR AS WHERE TO START ALLOCATING
	MOVSI	T1,(JFCL)	;PATCH OUT CALL TO SETUP NXMTAB TO READ IN
	MOVEM	T1,BNXMTS##	; BOOTS IF DEBUGGING
	PUSHJ	P,BOOTSZ	;FIXUP SYSORG TO ACCOUNT FOR UNMAPPED BOOTSTRAP
	PUSHJ	P,BOOTFX	;FIND OUT WHERE THE MONITOR WAS READ FROM
IFN FTXMON,<PUSHJ P,BOOTMP>	;MAP BOOT INTO THE MONITOR'S ADDRESS SPACE
	PUSHJ	P,PATFIX	;FIXUP "PAT" GLOBAL BEFORE MOVING SYMBOL TABLE

;THE ORDER IN WHICH THE VARIOUS PIECES OF THE MONITOR ARE MOVED AROUND
;IS VERY IMPORTANT DUE TO THE ORDERING OF THE PSECTS IN THE .EXE FILE.
;DON'T CHANGE THIS ORDER UNLESS YOU KNOW WHAT YOU ARE DOING, AND THEN
;BE SMART AND DON'T CHANGE THE ORDER ANYWAY.
;
;FOR NON-EXTENDED MONITOR:  MOVE HIGH SEGMENT AND THEN SYMBOL TABLE.
;
;FOR EXTENDED MONITOR:  MOVE SKY HIGH SEGMENT, EXTENDED SYMBOL TABLE,
;AND THEN HIGH SEGMENT.
IFN FTXMON,<
;ALLOCATE AND MAP NON-ZERO SECTION HIGH SEGMENT
	MOVE	T1,[SKYORG]	;WHERE SKY HIGH SEGMENT STARTS
	MOVE	T2,SKYEND##	;WHERE IT ENDS
	CAMLE	T1,T2		;IS THERE ANY CODE TO MOVE?
	JRST	ONCE4X		;NO, SKIP OVER SOME CODE
	PUSHJ	P,NZSCGC##	;ALLOCATE THE NON-ZERO SECTION CODE PAGES
	MOVE	T1,[SKYORG]	;FIRST ADDRESS IN THE SKY HIGH SEGMENT
	MOVE	P1,SKYEND##	;LAST ADDRESS IN THE SKY HIGH SEGMENT
	TRZE	P1,PG.BDY##	;ROUND UP
	ADDI	P1,PAGSIZ##	;...
	MOVE	T4,P1		;COPY IT AS DESTINATION OF XBLT
	SUB	P1,T1		;CALCULATE NUMBER OF PAGES TO MOVE
	LSH	P1,W2PLSH##	;...
	MOVE	T2,[SKYORG-1]	;BOOT READ IT IN PLACE
	LSH	T2,W2PLSH##	;CONVERT TO A PAGE NUMBER
	ADD	T2,P1		;COMPUTE LAST PAGE IN SKY HIGH SEGMENT
	MOVE	T1,.CPMAP##	;ADDRESS OF EXEC MAP
	HRLI	T2,(<PM.DCD>B2)	;ALLOW READING
	MOVEM	T2,.ECKSM/PAGSIZ##(T1) ;SET UP MAPPING
	XJRST	[MCSEC1+.+1]	;ENTER NON-ZERO SECTION TO DO XBLTS
ONCE4:	CLRPGT	(0,.ECKSM)	;LET THE PROCESSOR KNOW ABOUT THE CHANGE IN THE MAP
	MOVEI	T2,PAGSIZ##	;NUMBER OF WORDS TO MOVE
	XMOVEI	T3,.ECKSM	;VIRTUAL ADDRESS TO USE IN BLT
	SUBI	T4,PAGSIZ##	;DESTINATION
	PUSH	P,T4		;SAVE ACROSS BLT
	EXTEND	T2,[XBLT]	;MOVE A PAGE AT A TIME
	POP	P,T4		;RESTORE DESTINATION
	SOS	.ECKSM/PAGSIZ##(T1) ;MAP THE NEXT PAGE
	SOJG	P1,ONCE4	;LOOP FOR ALL PAGES
	JRST	@[0,,.+1]	;LEAVE SECTION ONE
ONCE4X:	SKIPGE	DEBUGF##	;DEBUGGING?
	PUSHJ	P,SYTBFX	;FIXUP SYSORG TO ACCOUNT FOR HIDDEN SYMBOL
				; TABLE, MOVE SYMBOL TABLE TO HIGH MEMORY
;NOW SETUP A 1:1 TO SECTION 0 MAP FOR THE REST OF THE SECTION EXCLUDING FUNNY SPACE
	MOVE	T3,.CPEPT##	;THIS CPU'S EPT
	MOVE	T1,<SECTAB+(MS.HGH)>(T3) ;SECTION POINTER FOR HIGH HIGH SEG MAP
	MOVE	T3,.CPMAP##	;THIS CPU'S MAP
	MOVEM	T1,.ECKSM/PAGSIZ##(T3) ;TO MAKE THE MAP ADDRESSABLE
	CLRPGT	(0,.ECKSM)	;SO MAPPING CAN BE SEEN
	MOVEI	T1,(<PM.ICD>B2+PM.WRT+PM.PUB+PM.CSH+PM.KPM+PM.SWB)
				; INDIRECT POINTERS TO SECTION 0 MAP
	HRLI	T1,SPTLOW##-SPTTAB## ;SPT SLOT USED FOR MAPPING SKY HIGH SEGMENT
	MOVS	T2,.CPCPN##	;OUR CPU NUMBER
	ADD 	T1,T2		;ADD THAT TO THE SPT INDEX
	MOVEI	T2,0		;STARTING AT PAGE 0
ONCE4A:	SKIPE	(T3)		;IF THE PAGE EXISTS IN THE SECTION 0 MAP,
	MOVSM	T1,.ECKSM(T2)	;POINT AT IT IN THE HIGH HIGH SEG MAP
	ADDI	T1,1		;NEXT PAGE
	ADDI	T3,1		; ..
	CAIGE	T2,MONORG/PAGSIZ##-1 ;UP TO MONITOR ORIGIN?
	AOJA	T2,ONCE4A	;NO, DO THE NEXT PAGE
	TRZ	T1,(PM.SWB)	;WRITE LOCKED FROM HERE ON OUT
	MOVEI	T2,MONORG/PAGSIZ## ; ..
ONCE4B:	MOVSM	T1,.ECKSM(T2)	;POINT AT IT IN THE HIGH HIGH SEG MAP
	ADDI	T1,1		;NEXT PAGE
	ADDI	T3,1		; ..
	CAIGE	T2,<SKYORG&777777>/PAGSIZ##-1 ;UP TO THE TOP OF THE LOW HIGH SEG?
	AOJA	T2,ONCE4B	;NO, DO THE NEXT PAGE
	MOVE	T1,.CPMAP##	;NOW SETUP SKIP CPU MAPPING
	DMOVE	T1,.ESKPC/PAGSIZ##(T1)
	TLO	T1,(PM.SWB)	;WRITE ENABLE
	TLO	T2,(PM.SWB)
	DMOVEM	T1,.ECKSM+.ESKPC/PAGSIZ##
;CLEAR MAPPING FOR UNUSED PAGES
	HRRZ	T1,SKYEND##	;GET LAST ADDRESS IN SKY HIGH SEGMENT
	TRZE	T1,PG.BDY##	;ROUND UP
	ADDI	T1,PAGSIZ##
	LSH	T1,W2PLSH##	;CONVERT TO PAGE NUMBER
	TRNN	T1,PG.BDY##	;ANY UNUSED PAGES IN THIS SECTION?
	JRST	ONCE4C		;NO
	MOVE	T2,.CPEPT##	;GET EPT ADDRESS
	HRRZ	T2,<SECTAB+(MS.HGH)>(T2) ;GET POINTER TO SKY HIGH SEGMENT
	LSH	T2,P2WLSH##	;CONVERT TO ADDRESS
	ADD	T1,T2		;ADD IN FIRST FREE PAGE NUMBER
	SETZM	(T1)		;ZERO MAPPING INFORMATION
	CAIGE	T1,PG.BDY##(T2)	;DONE ALL PAGES?
	AOJA	T1,.-2		;NO, LOOP
ONCE4C:
>; END IFN FTXMON
	MOVE	T1,SYSLEN##	;NUMBER OF WORDS IN CODE SEGMENT
	MOVSI	T2,(<PM.DCD>B2+PM.WRT+PM.PUB+PM.CSH)

	PUSHJ	P,ONCMAP##	;FILL IN MAP SLOTS

	MOVEI	T1,MONORG-1	;BOOT READ THIS IN PLACE
	ADD	T1,SYSLEN##	;HIGHEST ADDRESS - 1 IN THE MONITORS HI SEG
	LSH	T1,W2PLSH##	;CONVERT TO HIGHEST PAGE - 1
	MOVE	T2,.CPMAP##
	HRLI	T1,(<PM.DCD>B2)
	MOVEM	T1,.ECKSM/PAGSIZ##(T2)

	HRRI	T1,MONORG	;STARTING VIRTUAL ADDRESS OF THE MONITORS HI SEG
	ADD	T1,SYSLEN##	;HIGHEST VIRTUAL ADDRESS IN MONITORS HI SEG
	HRRZ	T2,T1		;COPY THAT
	MOVE	T3,SYSLEN##	;LENGTH OF THE MONITORS HI SEG
	LSH	T3,W2PLSH##	;NUMBER OF PAGES IN THE MONITORS HI SEG
	HRLI	T1,.ECKSM	;BLT HIGH SEG FROM THIS V.A.
ONCE5:	CLRPGT	(0,.ECKSM)	;LET THE PROCESSOR KNOW ABOUT THE CHANGE IN THE MAP
	SUBI	T1,PAGSIZ##	;DESTINATION
	PUSH	P,T1		;SAVE ACROSS THE BLT
	BLT	T1,-1(T2)	;BLT A PAGE OF THE HIGH SEG FROM WHERE IT
				; WAS READ TO WHERE IT IS TO LIVE
	MOVE	T1,.CPMAP##
	SOS	.ECKSM/PAGSIZ##(T1)

	POP	P,T1		;RESTORE THE BLT POINTER
	SUBI	T2,PAGSIZ##	;NEXT LOWEST PAGE BOUNDARY
	SOJG	T3,ONCE5	;LOOP UNTIL ALL HI SEG PAGES HAVE BEEN MOVED
	SKIPGE	DEBUGF##	;DEBUGGING?
IFE FTXMON,<
	PUSHJ	P,SYTBFX	;FIXUP SYSORG TO ACCOUNT FOR HIDDEN SYMBOL
				; TABLE, MOVE SYMBOL TABLE TO HIGH MEMORY
>; END IFE FTXMON
IFN FTXMON,<
	PUSHJ	P,FILEDV	;FILL IN .CPEDV FOR ALL CPUS
>; END IFN FTXMON
HITHRU:	MOVSI	T1,(JRST)	;PREVENT ANOTHER ATTEMPT TO SETUP THE
	HLLM	T1,HIDONE	; MAPPING FOR THE HIGH SEGMENT
IFE FTXMON,<PUSHJ P,BOOTMP>	;MAP BOOT INTO THE MONITOR'S ADDRESS SPACE
IFN FTXMON,<XJRST [MCSEC1+HIGHIN]> ;GET INTO SECTION 1 SO CAN LOOK AT THINGS
HIGHIN:
IFN FTXMON,<XJRST [MCSEC0+.+1]>	;RETURN TO SECTION 0
	PUSHJ	P,BSTRNG	;CONVERT ARGUMENTS TO BOOTS TO A STRING
				; FOR AUTO-RELOAD
	SETOM	DINITF##	;TELL AUTCON WHAT KIND OF CORE TO GET
IFN FTXMON,<
	MOVSI	T1,(MS.SAT)	;DATA SECTION FOR SATS, ETC.
	MOVEM	T1,RELMD1	;FIRST ALLOCATED WORD IN SECTION 2
	MOVEM	T1,FFMD1	;FIRST FREE WORD IN SECTION 2
	PUSHJ	P,ALCSMP	;ALLOCATE A MAP FOR THIS SECTION
	MOVSI	T1,(MS.MEM)	;DATA SECTION FOR PAGTAB/MEMTAB
	PUSHJ	P,ALCSMP	;ALLOCATE A SECTION MAP FOR SECTION 2
IFN FTSCA,<
	SKIPN	[SCASIZ##]	;ANY SCA FREE POOL?
	JRST	NOSCA		;NO, NO SECTION MAP OR BUFFERS NEEDED
	MOVSI	T1,(MS.SCA)	;DATA SECTION FOR SCA BUFFERS
	PUSHJ	P,ALCSMP	;ALLOCATE A SECTION MAP FOR SECTION 4
	MOVSI	T1,(MS.SCA)	;THEN ALLOCATE TONS OF MEMORY
	MOVEM	T1,SCALOC##	;SET STARTING ADDRESS OF SCA FREE POOL
	MOVEI	T2,SCASIZ##	;SIZE OF THE POOL
	ADD	T2,T1		;COMPUTE END ADDRESS
	MOVE	T3,T2		;GET A COPY
	ADDI	T3,PG.BDY##	;COMPUTE FIRST FREE PAGE ADDRESS FOLLOWING THE POOL
	TRZ	T3,PG.BDY##	;...
	MOVEM	T3,SCAFRE##	;SAVE FIRST FREE ADDRESS
	PUSHJ	P,NZSCGT##	;LET ONCMOD ALLOCATE IT FOR US
	PUSHJ	P,BHDINI##	;INITIALIZE BUFFER HEADERS AND DESCRIPTORS
	PUSHJ	P,SC.INI##	;INITIALIZE THE SCA PROTOCOL MODULE
NOSCA:
>; END IFN FTSCA
	MOVSI	T1,(MS.SCN)	;DATA SECTION FOR SCNSER DATA BASE
	PUSHJ	P,ALCSMP	;ALLOCATE A SECTION MAP FOR SECTION 3
	HRROI	T1,ALCSHM	;NOW ALLOCATE SKY HIGH SEGMENT SECTION MAPS
				; FOR OTHER CPUS
	PUSHJ	P,CPUAPP##	;DO IT
>
IFE FTXMON,<
;ALLOCATE DECNET BUFFER MAPS FOR OTHER CPUS
>
IFN FTKL10,<
;HERE TO INITIALIZE LOWTAB (CORE BLOCKS FOR IOWD'S)
SETLOW:	MOVE	T1,LOWPTR##	;ABOJN POINTER TO LOWTAB
	SETOM	(T1)		;SET IT TO ALL ONES
	AOBJN	T1,.-1		; ..
	MOVEI	P1,LTINIT##	;ADDRESS OF TABLE CONTAINING ADDRESSES OF
				;  LOWER CORE FOUR WORD BLOCKS
	HRRZ	P2,LTINIT##	;ADDRESS OF FIRST FOUR WORD BLOCK
	MOVEM	P2,LOWLOC##	;STORE THAT AS ORIGIN OF FOUR WORD IOWD SPACE
SETLO1:	SKIPN	T2,(P1)		;NEXT CHUNK OF FOUR WORD SPACE
	JRST	SETLO2		;ALL DONE
	HLRZ	T1,(P1)		;NUMBER OF FOUR WORD BLOCKS IN THIS CHUNK
	HRRZS	T2		;0,,STARTING ADDRESS OF THIS CHUNK
	SUBI	T2,(P2)		;RELATIVE ADDRESS WITHIN IOWD SPACE
	LSH	T2,-2		;FOUR WORDS PER BLOCK
	IDIVI	T2,^D36		;NUMBER OF BITS REPRESENTING FOUR WORD BLOCKS
	HRLS	T2		;WHERE THEY START IN THE TABLE
	ADD	T2,LOWPTR##	;MAKE AN AOBJN POINTER TO THE TABLE
	PUSHJ	P,SETZRS##	;INDICATE THAT THOSE BLOCKS ARE AVAILABLE
	AOJA	P1,SETLO1	;LOOP UNTIL ALL CHUNKS ARE MARKED IN BIT TABLE
SETLO2:
>
IFN FTAUTC,<
	MOVE	T1,MONVFF##	;WHERE TO START ALLOCATION
	MOVEM	T1,CORLOC##	;TELL AUTCON
	PUSHJ	P,AUTCON##	;SEE WHAT DISKS, TAPES WE HAVE
>
	PUSHJ	P,ONCINT	;START INTERVAL TIMER GIVING CLOCK TICKS
				; FOR ONCE, SET UP ONCKLT SO APRINT AND
				; OPRFIL CAN USE IT TO START UP TIMER AGAIN.
	SETTYO
	SKIPGE	DEBUGF##	;IF DEBUGGING DO NOT
	JRST	ONCE6		; DO SYSCHK
	HLRZ	T1,SYSCKI##
	CAIE	T1,(JSR)
	JRST	ONCE6
	MOVE	P,.CPNPD##	;SET UP A STACK
	MOVEI	T1,[ASCIZ /SYSCHK(N,Y):/]
	MOVEI	T2,[ASCIZ /NO	;Default answer/]
	PUSHJ	P,ASKDEF	;ASK THE QUESTION
	  JRST	ONCE6		;JUST CR-LF
	PUSHJ	P,ALTM##
	PUSHJ	P,COMTYI##
	CAIN	T3,"Y"
	XCT	SYSCKI##
ONCE6:	MOVE	P,.CPNPD##	;SET UP A STACK
	SKIPL	DEBUGF##
	JRST	ONCE7
	SETZM	TTFCOM##+TTFCXI##

ONCE7:	SETTYO
	PUSHJ	P,CRLF##
	PUSHJ	P,PATSIZ	;SET UP SYSSIZ, CHECK FOR B.P.'S AND NO EDDT
	MOVEI	T1,CONFIG##
	PUSHJ	P,CONMES##
	MOVEI	T1,[ASCIZ / /]
	PUSHJ	P,CONMES##
	MOVEI	T1,SYSDAT##
	PUSHJ	P,CONMES##
	PUSHJ	P,CRLF##	;ADD CRLF
	PUSHJ	P,OPOUT
;HERE TO DETERMINE IF THIS CPU IS A 166, KA10, OR
;  KI10 AND SETUP THE NUMBER OF CLOCK TICKS PER
;  SECOND ACCORDING TO POWER LINE FREQUENCY.


	MOVEI	F,CT.P6		;ASSUME A 166 (PDP-6) PROCESSOR
	MOVEI	T4,M.TPS##	;ASSUME LINE FREQUENCY UNKNOWN
				;EXCEPT FROM MONGEN
	JFCL	17,.+1		;CLEAR ALL FLAGS
	JRST	.+1		;SET PC CHANGE FLAG IF CPU IS A 166
	JFCL	1,CPU166	;BRANCH IF PDP-6
	SETZ	T1,		;THE TEST FOR A KL10 PROCESSOR
	BLT	T1,0		;IS A NO-OP BLKT LEAVING AC NON-ZERO
	JUMPE	T1,CPNTLS	;JUMP IF NOT KL OR KS
	MOVEI	P1,1
	SETZ	P2,		;BIG BINARY INTEGER
	MOVEI	P4,1		;ONE DIGIT BYTE
	EXTEND	P1,[CVTBDO]	;CONVERT WILL ABORT
	TLNN	P4,200000	;TEST EFFECT ON N
	JRST	CPKS10
	JRST	CPKL10
CPNTLS:	HRLOI	T1,020640	;WE HAVE A KA OR KI, FIND ITS TYPE
	IBP	T1		; ..
	TLNN	T1,1		;SKAP IF KA10
	JRST	CPKI10		;NO--MUST BE KI10
;HERE IF CPU IS A KA10.  DETERMINE LINE FREQUENCY BY
;TIMING ROTATES
;DEPENDS ON:
;MAX. POWER LINE FREQUENCY VARIATION OF PLUS OR MINUS 2 HERTZ.
;SHIFT TIME IN KA10 OF 150NS. PLUS OR MINUS 5%

	MOVEI	F,CT.KA		;REMEMBER THIS IS A KA10
;HERE IF KL10 OR KS10
CPKL10:	APRID	T1		;READ SERIAL NUMBER
	ANDI	T1,7777		;MASK OUT UCODE VER
	MOVEM	T1,.CPASN##	;SAVE AS REAL #
	MOVEI	F,CT.KL		;SET TYPE AS KL10
	JRST	CPU166		;NO CLOCK ON A KL
CPKS10:	APRID	T1		;READ SERIAL NUMBER
	ANDI	T1,77777	;MASK OUT CRUFT
	MOVEM	T1,.CPASN##	;SAVE IN CDB
	MOVEI	F,CT.KS		;SET TYPE AS KS
	JRST	CPU166		;NO LINE CLOCK ON KS
;HERE IF CPU IS A KI10.  CHECK APR STATUS BIT
CPKI10:	CONI	PAG,T1		;READ THE PROCESSORS SERIAL NUMBER
	LSH	T1,-^D26	;RIGHT ADJUST IT
	MOVEM	T1,.CPASN##	;STORE IT FOR PROPRIETARY PROGRAMS
	MOVEI	F,CT.KI		;REMEMBER THIS IS A KI10
	CONI	APR,T1		;GET APR STATUS
	TLNE	T1,(IP.50H)	;50 HERTZ POWER?
	SKIPA	T4,[EXP ^D50]	;50 HERTZ POWER LINE FREQUENCY
	MOVEI	T4,^D60		;60 HERTZ POWER LINE FREQUENCY
CPU166:	CAME	F,.CPTYP##	;DO WHAT THE MONITOR WAS BUILT FOR AND
				; THE CURRENT MACHINE AGREE?
	STOPCD	.,HALT,WCT	;++WRONG CPU TYPE
	MOVEM	T4,TICSEC##	;NUMBER OF CLOCK TICKS PER SECOND
	MOVSI	T1,(ST.CYC)	;SET BIT SIX OF STATES IF 50 HZ POWER
	CAIN	T4,^D50		;50 HERTZ POWER?
	IORM	T1,STATES##	;YES
	IMULI	T4,^D60		;NUMBER OF TICS PER MINUTE
	MOVEM	T4,TICMIN##	;SAVE THAT
	IMULI	T4,^D60*^D24	;NUMBER OF TICS PER DAY
	MOVEM	T4,MIDNIT##	;SAVE THAT FOR MIDNIGHT CHECKING
	JRST	WHYLOP		;GO ASK WHY RELOAD

;SETUP INTERNAL TIMER ON KL10 TO MIMIC CLOCKS OF EARLIER CPUS.

IFN FTKL10,<
ONCINT:	CONO	MTR,0		;MAKE SURE INT. TIME DOESNT INTERRUPT
	MOVEI	T2,^D1666+TO.SIT+TO.CTD	;WORD TO KEEP TIMER GOING
	MOVE	T1,STATES##	;GET STATES
	TLNE	T1,(ST.CYC)	;50 HZ?
	MOVEI	T2,^D2000+TO.SIT+TO.CTD	;50 HZ WORD TO KEEP TIMER GOING
	MOVEM	T2,ONCKLT	;CONO TIM,@ONCKLT STARTS TIMER GOING AGAIN
	CONO	TIM,TO.CIT(T2)	;CLEAR INTERNAL TIMER & START FIRST TIME
	POPJ	P,		;RETURN
>;END IFN FTKL10
IFN FTKS10,<
ONCINT:	WRAPR	SP.SSF!SP.ITI	;TURN ON INTERVAL TIMER
	MOVEI	T2,^D17*10000	;60HZ
	MOVE	T1,STATES	;GET STATES
	TLNE	T1,(ST.CYC)	;50HZ?
	MOVEI	T2,^D20*10000	;YES
	WRINT	T2		;SET UP INTERVAL REGISTER
	PUSHJ	P,UBAPIS##	;INIT AND SET UP UBA PI'S
	MOVEI	T1,VECTB1##	;GET UBA1'S INTERRUPT VECTOR TABLE
	MOVEM	T1,.EPVIT##	;INITIALIZE IN EPT
	MOVEI	T1,VECTB3##	;... DITTO FOR UBA3
	MOVEM	T1,.EPVIT##+2 ;...
	POPJ	P,
>;END IFN FTKS10
;ASK OPERATOR REASON FOR RELOAD
;ANSWER WILL BE PUT IN LOG FILE DAEMON
;ALONG WITH ARBITRARY OPERATOR COMMENT, IF ANY.
;ALLOW UNIQUE ABBREVIATION

WHYLOP:	SETZM	CRSHAC##	;CLEAR OUT CRASH AC AREA FOR OPERATOR COMMENT
	MOVE	T1,[XWD CRSHAC##,CRSHAC+1]
	BLT	T1,CRSHAC##+17
	SKIPL	DEBUGF##	;DEBUGGING STAND-ALONE?
	JRST	WHY0		;NO,
	MOVE	T1,SACOD	;YES, FLAG STAND-ALONE
	MOVEM	T1,WHYCOD##	;FOR DAEMON
	JRST	DATLOP		;GO ASK DATE
WHY0:	MOVE	T1,CRSWHY##	;GET STOPCD CHECKSUM FROM PREVIOUS LOAD
	JUMPE	T1,WHY01	;JUMP IF NONE
	PUSHJ	P,CHKDCS	;CHECK DATE/TIME CHECKSUM
	  JRST	WHY01		; IF PINK CRASH
	MOVEM	T1,WHYCOD##	;AND STORE AS REASON FOR RELOAD
	JRST	DATLOP		;SKIP QUESTION
WHY01:	MOVEI	T1,[ASCIZ /Why reload: /]
	MOVEI	T2,[ASCIZ /OTHER	;OPR did not answer/]
	PUSHJ	P,ASKDEF	;TYPE OUT AND WAIT FOR INPUT
	  JRST	WHYSHT		;JUST CR TYPED, GIVE SHORT HELP
	PUSHJ	P,CTEXT##	;GET FIRST WORD LEFT JUSTIFIED SIXBIT IN T2
	JUMPN	T2,WHY1		;ANYTHING BEFORE FIRST BREAK?
	CAIN	T3,"/"		;NO, IS BREAK A SLASH?
	JRST	WHYLNG		;YES, ASSUME /H AND GIVE LONG HELP
	JRST	WHYSHT		;NO, GIVE SHORT HELP

WHY1:	MOVE	P1,T3		;SAVE BREAK
	MOVE	T1,[-WHYLEN,,WHYTAB]	;POINT TO TABLE
	PUSHJ	P,FNDNAM##	;LOOKUP ABBREV.
	  JRST	WHYSHT		;GIVE HELP
	MOVE	T1,WHYTAB(T1)	;NO, GET UNABBREVIATED SIXBIT CODE
	MOVEM	T1,WHYCOD##	;AND STORE IN GETTAB FOR DAEMON
	JUMPE	P1,[CAME T1,OTHCOD ;IF END OF LINE AND RESPONSE WAS OTHER,
		    JRST DATLOP	; TELL HIM THAT OTHER REQUIRES
		    MOVEI T1,OTHMSG ; A COMMENT AND GO BACK TO WHYLOP
		    JRST WHYTYP] ; TO ASK AGAIN
;HERE TO GET OPERATOR COMMENT AND STORE IN CRASH ACS
	MOVEI	T1,20*5-1	;YES, NO. OF ASCIZ CHAR IN 20 WORDS
				;OF CRASH ACS. SAVE ROOM FOR NULL
	MOVEM	T1,WHYCNT	;STORE FOR LOOP COUNT
	MOVE	P1,[POINT 7,CRSHAC##]	;BYTE PTR FOR WHERE TO PUT
WHY4:	PUSHJ	P,COMTYI##	;GET NEXT CHARACTER (EVEN IF ;)
	JUMPE	T3,WHY5		;END OF STRING (GETLIN STORES NULL)
	CAIL	T3,12		;NO, END OF LINE CHAR?
	CAILE	T3,15		;"
	SKIPA			;NO
	JRST	WHY5		;YES, DO NOT STORE, JUST GO STORE NULL
	SOSG	WHYCNT		;ANY MORE ROOM IN CRSHAC BLOCK?
	JRST	WHY5		;NO, GO STORE NULL AND QUIT
	IDPB	T3,P1		;YES, STORE ASCIZ CHARACTER
	JRST	WHY4		;GO GET MORE

;HERE WHEN FINISHED COPYING OPERATOR COMMENT TO CRASH ACS
WHY5:	MOVEI	T3,0		;NULL
	IDPB	T3,P1		;STORE ON END SO ASCIZ
	JRST	DATLOP		;GO ASK FOR DATE

;HERE TO TYPE SHORT HELP MESSAGE ON ANY ERROR
WHYSHT:	MOVEI	T1,WHYMS1	;ADR OF SHORT HELP MESSAGE
	PUSHJ	P,ICONM		;INITIALIZE BUFFER AND MOVE CHAR
	PUSHJ	P,OPOUT		;START TYPING
	JRST	WHYLOP		;GO BACK TO ASK WHY RELOAD AGAIN

;HERE TO TYPE LONG HELP MESSAGE ON /H
WHYLNG:	MOVEI	T1,WHYMS2	;ADR OF LONG HELP MESSAGE
WHYTYP:	PUSHJ	P,ICONM		;INITIALIZE AND MOVE CHAR TO OUTPUT BUFFER
	PUSHJ	P,OPOUT		;START TYPING
	JRST	WHYLOP		;GO BACK AND ASK WHY RELOAD AGAIN

WHYCNT:	0			;COUNT FOR NO CHAR LEFT IN CRASH ACS
;LIST OF POSSIBLE WHY RELOAD ANSWERS (CAN BE ABBREVIATED)
; ORDER IS IMPORTANT. OPERATOR SHOULD ANSWER THE EARLIEST ONE
; IN TABLE WHICH APPLIES (WHEN MORE THAN ONE DOES)

WHYTAB:

;PREVIOUS SYSTEM PROBLEM:

	SIXBIT	/OPR/
	SIXBIT	/PARITY/
	SIXBIT	/POWER/
	SIXBIT	/STATIC/
	SIXBIT	/HARDWA/
	SIXBIT	/NXM/
	SIXBIT	/HALT/
	SIXBIT	/LOOP/
	SIXBIT	/HUNG/
;PREVIOUS NON-TIMESHARED USE OF SYSTEM:
	SIXBIT	/PM/
	SIXBIT	/CM/
SACOD:	SIXBIT	/SA/
;DIFFERENT MONITOR WANTED:
	SIXBIT	/NEW/
	SIXBIT	/SCHED/
;OPERATOR DOESNT KNOW OR NOT IN TABLE (YET):
OTHCOD:	SIXBIT	/OTHER/		;ALWAYS LAST OF TABLE
WHYLEN==.-WHYTAB		;LENGTH
;ADD ENTRIES IN MIDDLE ACCORDING TO PRECEDENCE, NOT AT END

;SHORT MESSAGE FOR JOGGING MEMORY
WHYMS1:	ASCIZ	"OPR,PARITY,POWER,STATIC,HARDWARE
NXM,HALT,LOOP,HUNG
PM,CM,SA
NEW,SCHED
OTHER
/H for help
"
;LONG MESSAGE FOR /H
WHYMS2:	ASCIZ	/Type first word which applies (abbreviations ok) followed by
any comment:
OPR operator error
PARITY memory parity stop
POWER power failure
NXM non-existent memory stop
STATIC static electric
HARDWARE hardware malfunction
HALT program stop

LOOP loop in exec mode
HUNG no response

PM preventative maint
CM corrective maint
SA stand alone

NEW new monitor
SCHED scheduled reload

OTHER you don't know why or not any of the above
/
BUFLEN==.-WHYMS2		;LENGTH OF ONCE TTY BUFFER
				; MAKE IT LONG ENOUGH FOR THIS BIG MESSAGE
OTHMSG:	ASCIZ	/%OTHER requires a comment
/
;ASK FOR TODAY'S DATE AND CONVERT
;DATE STORED AS ((Y-64)*12.+M-1)*31.+D-1

DATAGN:	ADJSP	P,-1		;FIX THE STACK (/DATE PROCESSING)
	AOSA	AGNFLG		;DOING IT AGAIN

DATLOP:	 SETZM	AGNFLG		;FIRST TIME
	MOVEI	T1,[ASCIZ /Date: /]
	SETZM	FETFLG		;ASSUME NO FE TIME
	PUSHJ	P,GFETIM##	;SEE IF FRONT END KNOWS TIME
	 JRST	DATLP1		;IT DOES NOT, TRY FOR LAST CRASH TIME
	JRST	DATL2A		;IT DOES, USE IT FOR A DEFAULT

DATHLP:	PUSHJ	P,RSTDEF	;SOMETHING WENT WRONG, GIVE OPR TIME TO PONDER
	SETZM	FETFLG		;FORGET WHATEVER THE FE MAY HAVE TOLD US
	MOVEI	T1,[ASCIZ /Please type today's date as MON-DD(-YY)
/]
DATLP1:	SETOM	LOCSEC##	;NO TIME KNOWN YET
	SETOM	CRSDAY		;FAR FAR DISTANT PAST
	PUSHJ	P,CHKDCS
	  JRST	GOASK
	MOVE	T2,T4		;COPY DATE
	ANDI	T2,17		;MASK OUT MONTH
	MOVEM	T2,LOCMON##	;STORE
	MOVE	T1,T4
	LSH	T1,-4		;SHIFT OFF MONTH
	MOVE	T2,T1		;COPY DATE
	ANDI	T2,37		;MASK OUT DAY
	MOVEM	T2,LOCDAY##	;STORE IN COMMON
	LSH	T1,-5		;SHIFT OFF DAY
	ADDI	T1,^D1970	;ADD IN BASE
	MOVEM	T1,LOCYER##	;STORE
	HRRZ	T1,CRSDTM##	;GET TIME
	IDIVI	T1,^D60*^D60	;GET HOURS
	IDIVI	T2,^D60		;GET MIN
	MOVEM	T1,LOCHOR##	;STORE HOURS
	MOVEM	T2,LOCMIN##	;STORE MIN
	MOVEM	T3,LOCSEC##	;STORE SECONDS
	PUSHJ	P,CHKMNT##	;SEE IF PASSED THROUGH MIDNIGHT WHILE RELOADING
	CAIA
DATL2A:	SETOM	FETFLG		;GOT TIME FROM FE
	PUSHJ	P,THSDA##
IFN FTDTCK,<
	PUSHJ	P,SUDATE##	;COMPUTE DATE TOO (TO PRINT DOW)
>;FTDTCK
DATLP2:	MOVE	T1,THSDAT##
	MOVEM	T1,CRSDAY
	MOVE	T1,DEFSP	;GET DEFAULT STRING POINTER
	MOVEM	T1,DEFPTR	;STORE AS POINTER
	MOVE	T1,LOCMON##	;GET MONTH
	PUSHJ	P,DECDEF	;DO THE DEFAULT STUFF
	MOVEI	T1,"-"		;ADD A DASH
	IDPB	T1,DEFPTR	; ..
	MOVE	T1,LOCDAY##	;GET THE DAY
	PUSHJ	P,DECDEF	;STORE AS PART OF DEFAULT
	MOVEI	T1,"-"		;ADD 1 MORE DASH
	IDPB	T1,DEFPTR	; ..
	MOVE	T1,LOCYER##	;GET THE YEAR
	PUSHJ	P,DECDEF	;ADD THAT ON
	SKIPN	FETFLG		;GOT TIME FROM FE?
	 JRST	DATL2B		;NO
	SETOM	CRSDAY		;YES, FORGET CRASH TIME
	SKIPA	T1,[[ASCIZ /	;From FE clock/]]
DATL2B:	 MOVEI	T1,[ASCIZ /	;From last crash/]
	PUSHJ	P,DEFSTR	;ADD TO DEFAULT
	IDPB	T2,DEFPTR	;STORE ZERO
	MOVEI	T1,[ASCIZ /Date: /]
	MOVEI	T2,DEFBUF
	SKIPN	FETFLG		;TIME FROM FE?
	 SKIPA	T3,OPRCNT	;NO, USE OPRCNT
	MOVEI	T3,^D5		;YES, REDUCE WAIT TO 5 SECS
	PUSHJ	P,ASKDFT	;ASK QUESTION
	  JRST	DATLO2
	JRST	GOASK1		;GO PARSE THE ANSWER
GOASK:	PUSHJ	P,ASKGET
	  JRST	DATHLP
GOASK1:	MOVEI	T1,LOCYER##
	PUSHJ	P,GTDATE##	;GET DATE
	  JRST	DATHLP		;ERROR
	MOVE	T2,LOCYER##
	SUBI	T2,^D1900
	CAMGE	T2,ONCYER
	JRST	DATHLP
	MOVE	T1,LOCMON##	;NOW CHECK DAY ARG.
	SOS	T1
	LDB	T2,PMONTB##
	AOS	T2
	SOJN	T1,DATLO1	;JUMP IF NOT FEB
	MOVE	T1,LOCYER##	;LEAP YEAR?
	TRNN	T1,3
	AOS	T2		;YES - 29 DAYS
DATLO1:	CAML	T2,LOCDAY##	;CHECK DAY ARG.
	JRST	DATLO2		;OK
	MOVEI	T1,[ASCIZ/?Illegal day
/]
	PUSHJ	P,ICONM
	PUSHJ	P,OPOUT
	JRST	DATHLP

DATLO2:	PUSHJ	P,THSDA##	;COMPUTE & STORE THSDAT
IFN FTDTCK,<
	PUSHJ	P,SUDATE##	;COMPUTE DATE TOO (FOR DOW PRINTING)
>;FTDTCK
	MOVE	T1,THSDAT##
	CAML	T1,CRSDAY
	JRST	VALID
	MOVEI	T1,[ASCIZ /
%Specified date is prior to last crash.
Last crash date:  /]
	PUSHJ	P,ICONM
	MOVEI	T1,DEFBUF
	JRST	VALID1

;ROUTINE TO CHECK DATE/TIME CHECKSUM
;RETURNS CRASH DATE IN T4
CHKDCS:	HLRZ	T4,CRSDTM##
	HRRZ	T2,CRSDTM##
	ADD	T2,T4		;ADD DATE AND TIME
	HLRZ	T3,CRSWHY##
	ADD	T2,T3		;PLUS STOPCD NAME
	HRRZ	T3,CRSSTS##	
	ADD	T2,T3
	ADDI	T2,507601	;PLUS MAGIC CONSTANT
	HRRZ	T3,CRSCHK##	;GET CHECKSUM COMPUTED BY COMMON
	CAIN	T3,(T2)		;MATCH?
	AOS	(P)
	POPJ	P,
;CODE TO VALIDATE THE DATE JUST TYPED IN

VALID:	MOVE	T1,ONCMON	;FORM 12 BIT DATE FOR COMPARISON
	IMULI	T1,^D31
	MOVEM	T1,CHKDAT
	MOVE	T1,ONCDAY
	SUBI	T1,1+^D31
	ADDM	T1,CHKDAT
	MOVE	T1,ONCYER
	SUBI	T1,^D64		;ADJUST TO T=0
	IMULI	T1,^D12*^D31
	ADD	T1,CHKDAT
	CAMG	T1,THSDAT##
IFN FTDTCK,<
	JRST	VALID2		;OK, BUT ASK OPR TO CONFIRM WHAT HE TYPED
>

IFE FTDTCK,<
	JRST	TIMLOP		;OK IF TODAY .GE. CREATION DAY
>;FTDTCK

	MOVEI	T1,[ASCIZ /
%Specified date is prior to monitor creation date.
Creation date:  /]
	PUSHJ	P,ICONM		;QUESTION EARLY DATE
	MOVEI	T1,SYSDAT##
VALID1:	PUSHJ	P,CONMES##
	PUSHJ	P,OPOUT

VALID2:	MOVEI	T1,[ASCIZ /
Specified date:   /]
	PUSHJ	P,ICONM
	PUSHJ	P,PRDAYD##	;TYPE DAY AND DATE
	PUSHJ	P,OPOUT
	SKIPE	FETFLG		;DID DATE/TIME COME FROM FE?
	 PUSHJ	P,RSTDEF	;YES, GIVE OPR TIME TO DISLIKE
	MOVEI	T1,[ASCIZ /

Is this correct? (Y or N)/]
	MOVEI	T2,[ASCIZ/YES	;default answer/]
	PUSHJ	P,YESNOD
	  JRST	DATHLP		;NO, TRY AGAIN
	JRST	TIMLOP		;HE LIKES IT ANYWAY

;CONSTANTS, MONTH,DAY,YEAR FROM MONGEN

ONCMON:	M.MON##
ONCDAY:	M.DAY##
ONCYER:	M.YEAR##
CHKDAT:	Z			;LOCAL STORAGE FOR DATE (12 BIT)
CRSDAY: Z
FETFLG:	Z			;-1 IF GOT DATE FROM A FE
AGNFLG:	Z			;0 IF FIRST TIME WE ARE GETTING THE DATE/TIME
;GET TIME OF DAY

TIMHLP:	SETZM	FETFLG		;FORGET ANY TIME FROM THE FE
	PUSHJ	P,RSTDEF	;GIVE OPR TIME TO PONDER
	SKIPA	T1,[[ASCIZ /Please type time as HHMMSS or HH:MM:SS
/]]
TIMLOP:	 MOVEI	T1,[ASCIZ /Time: /]
	SKIPGE	LOCSEC##	;DO WE KNOW TIME
	JRST	ASKTIM		;NO--GO ASK FOR IT
	MOVE	T1,DEFSP
	MOVEM	T1,DEFPTR
	MOVE	T1,LOCHOR##	;SETUP DEFAULT
	PUSHJ	P,DECDEF	; ..
	MOVEI	T1,":"
	IDPB	T1,DEFPTR
	MOVE	T1,LOCMIN##	; ..
	PUSHJ	P,DECDEF	; ..
	MOVEI	T1,":"
	IDPB	T1,DEFPTR
	MOVE	T1,LOCSEC##
	PUSHJ	P,DECDEF
	SKIPE	FETFLG		;GOT TIME FROM FE?
	 SKIPA	T1,[[ASCIZ /		;From FE clock/]]
	MOVEI	T1,[ASCIZ /		;From last crash or previous answer/]
	PUSHJ	P,DEFSTR	;ADD TO DEFAULT
	IDPB	T2,DEFPTR	;STORE ZERO
	MOVEI	T1,[ASCIZ /Time: /]
	MOVEI	T2,DEFBUF
	SKIPN	FETFLG		;TIME FROM FE?
	 SKIPA	T3,OPRCNT	;NO, USE OPRCNT
	MOVEI	T3,^D5		;YES, REDUCE WAIT TO 5 SECS
	PUSHJ 	P,ASKDFT	;GO ASK ABOUT TIME
	  JRST	HAVTIM		;JUST A CR
	JRST	ASKTM1

ASKTIM:	PUSHJ	P,ASKGET
	  JRST	TIMHLP		;JUST A CR
ASKTM1:	PUSHJ	P,RDTIM##	;GET TIME OF DAY
	  JRST	[PUSHJ	P,SVOSET## ;SETUP FOR OUTPUT
		 PUSHJ	P,ERRCRL## ;ISSUE CRLF AND ERROR MESSAGE
		 PUSHJ	P,OPOUT	;FORCE OUTPUT
		 JRST	TIMHLP]	;LOOP BACK AND TRY AGAIN
	IDIVI	T1,^D60*^D60	;T1:= HOURS
	IDIVI	T2,^D60		;T2:= MINUTES, T3:= SECONDS
	MOVEM	T1,LOCHOR##	;SAVE HOURS
	MOVEM	T2,LOCMIN##	;SAVE MINUTES
	MOVEM	T3,LOCSEC##	;SAVE SECONDS
;	PJRST	HAVTIM		;GO COMPARE AGAINST LAST CRASH TIME
HAVTIM:	MOVE	T1,LOCHOR##
	MOVE	T2,LOCMIN##
	IMULI	T1,^D60		;CONVERT TO MINUTES
	ADD	T1,T2		;MINUTES SINCE MIDNIGHT
	IMUL	T1,TICMIN##	;JIFFIES SINCE MIDNIGHT
	MOVEM	T1,TIME		;TIME=JIFFIES SINCE MIDNIGHT
	MOVE	T1,LOCSEC##	;SECONDS INTO THIS MINUTE
	IMUL	T1,TICSEC##	;JIFFIES INTO THIS MINUTE
	ADDB	T1,TIME##	;TIME=JIFFIES SINCE MIDNIGHT
	HRRZ	T2,CRSDTM##
	SUBI	T2,RLDTIM##
	IMUL	T2,TICSEC##
	MOVE	T3,THSDAT##
	CAMGE	T1,T2
	CAME	T3,CRSDAY
	JRST	HAVTI1
IFE FTDTCK,<
	MOVEI	T1,[ASCIZ /
%Specified time is prior to last crash.
Specified time:  /]
	PUSHJ	P,ICONM
	PUSHJ	P,PRDTIM##
	MOVEI	T1,[ASCIZ /Last crash time:  /]
	PUSHJ	P,CONMES##
>;FTDTCK

IFN FTDTCK,<
	MOVEI	T1,[ASCIZ /
%Specified time is prior to last crash time.
Crash time:  /]
	PUSHJ	P,ICONM
>;FTDTCK
	HRRZ	T1,CRSDTM##
	SUBI	T1,RLDTIM##
	IMUL	T1,TICSEC##
IFE FTDTCK,<
	PUSHJ	P,PRTIME##
>;FTDTCK

IFN FTDTCK,<
	PUSHJ	P,PRTIMS##	;PRINT IT
	PUSHJ	P,CRLF		;AND CRLF
>;FTDTCK
	PUSHJ	P,OPOUT

IFN FTDTCK,<
HAVTI1:	MOVEI	T1,[ASCIZ/Specified time:  /]
	PUSHJ	P,ICONM
	MOVE	T1,TIME##	;GET TIME
	PUSHJ	P,PRTIMS##	;PRINT IT
	MOVEI	T1,[ASCIZ/ (/]	;GET TEXT
	PUSHJ	P,CONMES##	;TYPE
	MOVE	T1,TIME##	;GET TIME AGAIN
	PUSHJ	P,PRAMPM##	;TYPE AS AM/PM
	MOVEI	T1,[ASCIZ/)/]	;
	PUSHJ	P,CONMES##	;
	PUSHJ	P,OPOUT		;
>;FTDTCK

	SKIPE	FETFLG		;DID DATE/TIME COME FROM FE?
	 PUSHJ	P,RSTDEF	;YES, GIVE OPR TIME TO DISLIKE
	MOVEI	T1,[ASCIZ /

Is this correct? (Y or N)/]
	MOVEI	T2,[ASCIZ/YES	;default answer/]
	PUSHJ	P,YESNOD
	  JRST	DATLP2

IFE FTDTCK,<
HAVTI1:				;IF NO VERIFICATION, CONTINUE HERE
>;FTDTCK
	SKIPE	FETFLG		;DID DATE/TIME COME FROM FE?
	 PUSHJ	P,RSTDEF	;YES, GIVE OPR TIME TO REPLY AGAIN
	SKIPE	AGNFLG		;DOING IT AGAIN?
	 JRST	SHORTD		;YES
	PUSH	P,J		;SAVE ALT-MODE TYPED FLAG

IFN FTKL10,<
	PUSHJ	P,SPRIPA##	;START THE IPA-20S ON ALL CPUS
>; END IFN FTKL10
;MOVE SYMBOL TABLE UP IN MEMORY
;FIRST FIND THE FIRST LOCATION OF NON-EXISTENT MEMORY


	TDZA	P2,P2
BYPSY0:	TLO	P2,400000	;FOR CALLS TO A SUBROUTINE IN SYSINI
	SETZB	U,P4
	MOVEI	P1,CORBLK##	;IN CASE MEMORY HAS NO NON-EXISTANT BANKS
BYPSY1:
IFN FTKL10,<
	CONO	APR,LP.CSF+LP.NXM ;CLEAR NXM FLAG ON A KL
>
IFN FTKS10,<
	WRAPR	SP.CSF+SP.NXM
>
BYPSY2:	ADDI	U,PAGSIZ##	;TRY NEXT 1K BLOCK
	SETZB	T2,P3
BYPS2A:	PUSH	P,U
	ADDI	U,(P3)
	PUSHJ	P,REFMEM##	;REFERENCE THIS LOCATION
	POP	P,U
	CONSO	APR,NXM##	;NON:EXISTANT?
	TLOA	T2,200000	;NO, REMEMBER EXISTANT MEMORY SEEN
	TLO	T2,400000	;YES, REMEMBER THAT
	CAIE	P3,MEMITL##-1	;LOOKED AT ENOUGH WORDS IN THIS PAGE
	AOJA	P3,BYPS2A	; TO DETECT INTERLEAVING ERROR?
	JUMPG	T2,BYPS2B	;JUMP IF NO NXM SEEN
	TLNN	T2,200000	;NXM, SOME EXISTANT ALSO?
	JRST	BYPS2C		;NO, NOT AN INTERLEAVING PROBLEM
	MOVEI	T1,[ASCIZ  /?Memory interleaving error
/]
	PUSHJ	P,ICONM		;TELL THE OPR ABOUT THE PROBLEM
	PUSHJ	P,OPOUT
	STOPCD	.,STOP,MIW,	;++MEMORY INTERLEAVING IS WRONG
BYPS2B:	SOJG	P1,BYPSY2	;NO, KEEP LOOKING AS LONG AS NOT TOP OF MEMORY
BYPS2C:	SKIPN	P4		;FIRST TIME THROUGH?
	MOVE	P4,U		;YES, REMEMBER LOCATION OF LOWEST NON-EX MEM
	SOJL	P1,BYPSY4	;ACCOUNT FOR MISSED SOJ AND SEE IF FINISHED
	MOVE	P3,U		;NOW SEE IF ANY MEMORY EXISTS HIGHER UP
BYPSY3:	;CLEAR THE NON-EX-MEM FLAG
IFN FTKL10,<
	CONO	APR,LP.CSF+LP.NXM
>
IFN FTKS10,<
	WRAPR	SP.CSF+SP.NXM
>
	ADDI	P3,PAGSIZ##	;TRY NEXT 1K BLOCK
	PUSH	P,U		;SAVE U
	MOVE	U,P3		;SET ARG FOR REFMEM
	PUSHJ	P,REFMEM##	;REFERENCE IT
	POP	P,U		;RESTORE U
	CONSZ	APR,NXM##	;IS IT THERE?
	SOJG	P1,BYPSY3	;NO, LOOP THROUGH ALL 256K
	SOJLE	P1,BYPSY4	;JUMP IF NO MORE EXISTANT MEMORY
	PUSHJ	P,MEMBAD	;TELL THE OPERATOR HE HAS HOLES IN MEMORY
	  JRST	BYPSY0		;HE SAID HE FIXED IT. GO SEE IF HE DID.
	  JFCL			;OFF-LINE

	  MOVE	U,P3		;HE SAID ITS BROKEN
	JRST	BYPSY1		;GO SEE IF THERE ARE ANY MORE HOLES
BYPSY4:	SKIPL	DEBUGF##	;SYS PROG DEBUGGING MONITOR?
				; NOTE - ALREADY TOLD HIM IF HOLE IN MIDDLE
;PATCH TO NO. OF WORDS OF CORE TO BE CHECKED FOR ALL-ON-LINE
PATNWC::CAML	U,NWCORE##	;NOW SEE IF THERE IS AT LEAST AS MUCH MEMORY AS THERE
				; WAS AT MONGEN TIME
	JRST	BYPSY5		;THERE IS SO NO REASON TO COMPLAIN
	MOVE	P3,NWCORE##	;REMIND HIM OF HOW MUCH MEMORY HE HAD AT MONGEN TIME
	PUSHJ	P,MEMBAD	;TELL THE OPERATOR THERE'S NOT THAT MUCH THERE
	  JRST	BYPSY0		;HE SAID HE FIXED IT. SEE IF HE REALLY DID.
	  MOVEM	U,NWCORE##	;HE SAID DOWN, DON'T ALLOCATE EXTRA CORE FOR
				; PAGTAB AND MEMTAB

;OK, HE'S WILLING TO BRING IT UP WITHOUT ALL THE MEMORY ON LINE (LET'S HOPE ITS DOWN)
BYPSY5:	CAMG	U,[XWD 1,0]	;MORE THAN 256K?
	SETZ	U,		;NO
	MOVEM	U,FLG256##	;SET GTR THAN 256K FLAG

	SKIPE	P2		;IF WE COMPLAINED,
	PUSHJ	P,SUNXMT
STO2:	JSR	JRSTI1		;SETUP LOCS 40 THRU 61 & TEST FOR 2 RELOC. HARDWARE
	MOVE	T1,[JRST LOADMS] ;ONLY MOVE SYMBOLS ONCE
	MOVEM	T1,BYPSY5
LOADMS:
	SETOM	PRESSL		;INIT PRESERVED SSL FLAG
	SETOM	PREASL		;INIT PRESERVED ASL FLAG
	SETOM	PRESDL		;INIT PRESERVED SDL FLAG
IFN FTMP,<PUSHJ P,ONCCPU##>	;SEE IF ALL CPU(S) ARE RUNNING
IFN FTCIDSK,<
	MOVE	T1,TIME##	;STORE TIME STAMP
	MOVEM	T1,BNDBEG##
	CONO	PI,PI.ON+DSKPIN## ;MAKE SURE DISK PI CHANNEL IS ON
>; END IFN FTCIDSK
	SKIPGE	(P)		;SKIP IF ALTMODE TERMINATED DATE
	JRST	LONGD		;DO THE LONG DIALOGUE IF THE LAST LINE
				; TYPED IN (NAMELY TIME OF DAY) WAS TERMINATED BY
				; AN "ALT MODE".  (PUSH-DOWN LIST IS SET UP
				; IN THE "GETLIN" SUBROUTINE CALLED ABOVE.)
;TYPING ESCAPE DURING ONCE WILL BRING YOU BACK HERE TO TRY AGAIN.

SHORTD::SETZB	P1,SHUTUP##	;CLEAR SHORT FLAG
	SETOM	FSTTIM		;FLAG NOT TO CREATE SABS, ETC.
	SETOM	OPTQIK##
	SETOM	OFFLOK##	;NO VERBOSITY
	SKIPL	DEBUGF##
	JRST	SHORT1		;NOT DEBUGGING
IFN FTCIDSK,<
	PUSHJ	P,ONCBND##	;BIND CI DISKS
>; END IFN FTCIDSK
	JRST	QUICK

SHORT1:	SETZM	ERROK##		;TYPE REAL ERRORS
	MOVEI	T1,[ASCIZ/
Startup option: /]
	MOVEI	T2,[ASCIZ /QUICK	;Default/]
	PUSHJ	P,ASKDEF	;ASK QUESTION
	  JRST	ONCHLP		;GIVE SOME HELP

	;DONE HERE BECAUSE WE COULD HAVE RUSHED THRU THE OTHER QUESTIONS
	HRRZ	T1,CRSSTS##	;STATES BEFORE THE RELOAD
	TRO	T1,ST.NOP	;ASSUME NO OPR IN ATTENDANCE
	SKIPGE	DEFALW		;DID THE OPR ANSWER?
	HRRM	T1,STATES##	;NO, STORE STATES AS PREVIOUSLY SET BY OPR

	PUSHJ	P,CTEXT##	;GET FIRST WORD
SWTEST:	CAIE	T3,"/"		;SWITCH COMING?
	JRST	LNG1		;NO, CHECK OPTION
	PUSH	P,T2		;SAVE OPTION
	PUSHJ	P,CTEXT##	;PICK UP SWITCH NAME
	MOVE	T1,[-SWTLEN,,SWTTAB]
	PUSHJ	P,FNDNAM##	;LOOKUP NAME
	  JRST	ONCHLS		;GIVE SOME HELP
	MOVSI	T2,(ST%ACV)	;LOAD SOME BITS TO TWIDDLE
	MOVEI	T3,ST.NRT
	MOVSI	T4,(ST%NPP)
	XCT	SWTXCT(T1)	;ACT ON THE SWITCH
	MOVE	T3,ONCTCH	;FETCH (POSSIBLY NEW) DELIMETER
	POP	P,T2		;RESTORE OPTION NAME
	JRST	SWTEST		;SEE IF ANOTHER SWITCH COMING
LNG1:	MOVE	T1,[-OPTLEN,,OPTTAB]
	PUSHJ	P,FNDNAM##	;LOOKUP NAME
	  JRST	ONCHLP		;GIVE SOME HELP
IFN FTCIDSK,<
	PUSHJ	P,ONCBND##	;BIND ALL UNATTACHED UNITS TO ALL CPUS
>
	XCT	OPTXCT(T1)	;DO YOUR THING

	JRST	SHORTD
;DONE BY XCT ABOVE

OPTXCT:	PUSHJ	P,SHRTPM##	;CHANGE
	PUSHJ	P,SHRTST##	;DESTROY
	JRST	QUICK		;GO
	PUSHJ	P,FILOPL##	;LONG
	JRST	PVQCK		;QUICK
	JRST	QUICKN		;NOINITIA
	PUSHJ	P,SHRTRF##	;REFRESH
	PUSHJ	P,SHRTID##	;UNITID

SWTXCT:	JRST	LNGHLP		;/HELP
	SETZM	OFFLOK##	;/OFFLINE
	SETOM	ERROK##		;/NOERROR
	IORM	T3,STATES##	;/STAND
	SETZM	OPTQIK		;/ASK
	ANDCAM	T2,CNFST2##	;/NOVALIDATE
IFN FTKL10,<
	IORM	T4,CNFST2##	;/NOPRIMARY
>
	PUSHJ	P,NOCOPY	;/NOCOPY
IFN FTKL10,<
	PUSHJ	P,NODXLD	;/NODXLD
>
	SETZM	PRESSL		;/NOSSL
	SETZM	PREASL		;/NOASL
	SETZM	PRESDL		;/NOSDL
IFN FTKL10&FTAUTC,<
	PUSHJ	P,NOCI		;/NOCI
>; END IFN FTKL10&FTAUTC
IFN FTSETS,<
	PUSHJ	P,SETS		;/SETS
>; END IFN FTSETS
	JRST	DATAGN		;/DATE
NOCOPY:	MOVSI	T1,(DF.DCC)	;DISABLE INVOCATION OF
	IORM	T1,DEBUGF##	; CRSCPY AT STARTUP
	POPJ	P,		;RETURN

IFN FTKL10,<
NODXLD:	MOVEI	T1,[SETOM .CPNLD##-.CPCDB##(P1) ;SUBROUTINE TO CALL
		    POPJ  P,]
	PJRST	CPUAPP##	;DISABLE LOADING ON ALL CPUS
>

IFN FTKL10&FTAUTC,<
NOCI:	MOVSI	T1,770000	;ASSUME NO ARGUMENT TO FOLLOW
	MOVE	T3,ONCTCH	;GET BREAK CHARACTER
	CAIE	T3,":"		;ARGUMENT? (CPU NUMBER)
	JRST	NOCI1		;NOPE, THEY WANTED ALL
	PUSHJ	P,DECIN##	;READ RESPONSE
	 JRST	NOCIE		;BAD RESPONSE
	  JRST	NOCIE		;BAD RESPONSE
	SKIPL	T2		;CHECK FOR VALIDITY
	CAIL	T2,CPUN##	;...
	  JRST	NOCIE		;ERROR
	MOVE	T1,BITTBL##(T2)	;GET BIT FOR THIS CPU
NOCI1:	IORM	T1,IPAMSK##	;REMEMBER FOR KLPSER/KNISER
	POPJ	P,		;RETURN

NOCIE:	MOVEI	T1,[ASCIZ /
?Invalid response
/]
	PUSHJ	P,ICONM		;START THE MESSAGE
	PUSHJ	P,OPOUT		;FORCE IT OUT
	ADJSP	P,-1		;TOSS RETURN TO SWTEST
	JRST	ONCHLS		;GET SOME HELP
>; END IFN FTKL10&FTAUTC
IFN FTSETS,<
SETS:	SETZ	P1,		;GET A ZERO INITIALLY (ALL SETS)
	MOVEI	T1,[ASCIZ /Type the desired disk set numbers to be mounted
(Extra <CR> when done)
/]
	PUSHJ	P,ICONM		;START THE MESSAGE
	PUSHJ	P,OPOUT		;FORCE IT OUT
SETS1:	PUSHJ	P,GETLIN	;GET OPERATOR'S RESPONSE
	  JRST	SETS2		;DONE
	PUSHJ	P,DECIN##	;READ RESPONSE
	 JRST	SETS3		;BAD RESPONSE
	  JRST	SETS3		;BAD RESPONSE
	CAIL	T2,^D1		;IN RANGE OF 1
	CAILE	T2,^D36		; TO 36?
	JRST	SETS3		;NO
	IOR	P1,BITTBL##-1(T2) ;INCLUDE BIT FOR THIS SET NUMBER
	JRST	SETS1		;ASK AGAIN

SETS2:	MOVEM	P1,DSKSET##	;STORE NEW VALUE
	POPJ	P,		;RETURN

SETS3:	MOVEI	T1,[ASCIZ /Bad response, try again
/]
	PUSHJ	P,ICONM		;START THE MESSAGE
	PUSHJ	P,OPOUT		;FORCE IT OUT
	JRST	SETS1		;ASK AGAIN
>; END IFN FTSETS
;SHORT HELP
ONCHLP:	ADJSP	P,1		;MATCH PUSH FROM OTHER PATHS
ONCHLS:	MOVEI	T1,[ASCIZ "
CHANGE,DESTROY,GO,LONG,QUICK,NOINITIA,REFRESH,UNITID
/H for help
"]
	JRST	ONCHL1		;TYPE THAT OUT
LNGMSG:	ASCIZ	"
CHANGE      - Change disk parameters.
DESTROY     - Rebuild all disks.  Deletes all files, sets all defaults.
GO          - Start the system if all is OK.
LONG        - Enters long dialogue.
QUICK       - Same as GO.
NOINITIA    - GO, but don't bring up OPSER, etc.
REFRESH     - Refresh selected structures.
UNITID      - Change unit IDs.

Switches typed after option are:
/HELP       - Type this text.
/OFFLINE    - Tell operator about off-line units.
/NOERROR    - Don't tell about non-serious errors.
/STAND      - Set SCHED 10.
/ASK        - Ask about off-line units.
/NOVALIDATE - Don't require project validation.
/NOPRIMARY  - Come up in secondary protocol.
/NOCOPY     - Don't start CRSCPY.
/NODXLD     - Don't auto reload DX20s.
/NOSSL      - Don't use preserved system search list.
/NOASL      - Don't use preserved active swapping list.
/NOSDL      - Don't use preserved system dump list.
/NOCI       - Don't start CI20s.
/SETS       - Ask which disk set numbers to mount.
"
;/DATE	    - Ask for date and time again.
IFNDEF	BUFLEN,<BUFLEN==.-LNGMSG>
IFL	BUFLEN-<.-LNGMSG>,<BUFLEN==.-LNGMSG>
LNGHLP:	MOVEI	T1,LNGMSG
ONCHL1:	ADJSP	P,-1		;FIX STACK
	PUSHJ	P,ICONM
	PUSHJ	P,OPOUT
	JRST	SHORTD
OPTTAB:	SIXBIT	/CHANGE/
	SIXBIT	/DESTRO/
	SIXBIT	/GO/
	SIXBIT	/LONG/
	SIXBIT	/QUICK/
	SIXBIT	/NOINIT/
	SIXBIT	/REFRES/
	SIXBIT	/UNITID/

OPTLEN==.-OPTTAB
SWTTAB:	SIXBIT	/HELP/
	SIXBIT	/OFF/
	SIXBIT	/NOERRO/
	SIXBIT	/STAND/
	SIXBIT	/ASK/
	SIXBIT	/NOVALI/
IFN FTKL10,<
	SIXBIT	/NOPRIM/
>
	SIXBIT	/NOCOPY/
IFN FTKL10,<
	SIXBIT	/NODXLD/
>
	SIXBIT	/NOSSL/
	SIXBIT	/NOASL/
	SIXBIT	/NOSDL/
IFN FTKL10&FTAUTC,<
	SIXBIT	/NOCI/
>; END IFN FTKL10&FTAUTC
IFN FTSETS,<
	SIXBIT	/SETS/
>; END IFN FTSETS
	SIXBIT	/DATE/
SWTLEN==.-SWTTAB
;THE LONG DIALOGUE BEGINNETH HERE.....

LONGD:	SETOM	(P)		;SET "ALTMOD"-TYPED FLAG
IFN FTCIDSK,<
	PUSHJ	P,ONCBND##	;BIND ALL UNATTACHED UNITS TO ALL CPUS
>
	PUSHJ	P,FILOPT##	;GO THROUGH THE REFRESH DIALOGUE(S) [LEVEL C]
				; TYPE STATE OF WHOLE DISK SYSTEM, THEN
				; ACCEPT CHANGES TO UNITS AND STR'S & REFRESH [LEVEL D]

;FIND CORE TO BE USED FOR MULTIPLE DEVICE DATA BLOCKS
; INCLUDING DISK


;GO, BUT NO INITIA
QUICKN:
	MOVEI	T1,TTFCXI##	;INDEX OF INITIA
	SETZM	TTFCOM##(T1)	;CLEAR ENTRY FROM FORCED COMMAND TABLE
				;AND FALL INTO QUICK

PVQCK::
QUICK:			;THIS IS THE SHORT-CUT EXIT TO BY-PASS MOST OF THE DIALOGUE.
	SKIPN	HICORE##	;HICORE BEEN UPDATED?
	PUSHJ	P,REDHOM##	;NO, DO SO NOW
	  JFCL

	PUSH	P,SYSSIZ##	;SAVE CURRENT SIZE
	JSP	T1,CNTDB##	;UPDATE SYSSIZ BY SPACE USED
				; FOR DEVICE DATA BLOCKS FOR DSK,DTA,MTA,TTY,PTY)

	POP	P,T1		;POP OFF CURRENT SYSTEM SIZE
	EXCH	T1,(P)		;EXCH WITH ALTMODE TYPED FLAG
	JUMPGE	T1,QUICK1	;JUMP IF QUICK DIALOGUE - DONT TYPE MONITOR SIZE

;PRINT OCTAL SIZE OF MONITOR

	MOVEI	T1,[ASCIZ /
Exec is /]
	PUSHJ	P,ICONM
	MOVE	T1,SYSSIZ##
	PUSHJ	P,OCTPNT##
	MOVEI	T1,[ASCIZ / octal locations long.
/]
	PUSHJ	P,CONMES##
	PUSHJ	P,CRLF##
	PUSHJ	P,OPOUT
QUICK1:			;THIS IS THE SHORT-CUT EXIT TO BY-PASS MOST OF THE DIALOGUE.
	POP	P,SYSSIZ##	;RESTORE SYSSIZ PRIOR TO ACTUAL CREATION
				; OF DEVICE DATA BLOCKS


	JRST	@ONCE		;***EXIT FROM THE "ONCE-ONLY CODE"***...........
JRSTI1:	0

;SET LOC TWOREG TO -1 IF MACHINE HAS TWO RELOC REG, TO 0 IF ONLY ONE RELOC REG


	MOVE	P3,.CPMAP##
	PUSH	P,.EUPMP/PAGSIZ##(P3)

IFN FTKL10,<
	SKIPE	[CPUN##-1]	;IF MORE THAN 1 CPU,
	SKIPA	T1,[JRST SYSTOP##] ;LET WARM RESTART=J407
	MOVE	T1,[JRST APRWRS##] ;WARM RESTART INSTRUCTION
	MOVEM	T1,WRSINS##	;STORE IN WARM RESTART LOCATION
>
IFN FTMP,<
	MOVE	T1,[JRST APRRES##] ;POWER FAIL-AUTO-RESTART INSTR.	
>
IFE FTMP,<
	MOVE	T1,[HALT APRRES##] ;HALT IF NOTHING SAVED
>
	MOVEM	T1,ARSLOC##	;STORE IN AUTO-RESTART LOCATION

	MOVE	T1,[XPCW @.CPKAF##]
	MOVEM	T1,KAFLOC##	;STORE IT IN RIGHT SPOT

	MOVSI	T1,(<PM.DCD>B2+PM.WRT)
	MOVEM	T1,.EUPMP/PAGSIZ##(P3)

	CLRPGT	(0)		;CLEAR PAGING MEMORY AFTER CHANGING THE MAP

	MOVEI	17,.EUPMP	;MOVE HARDWARE AC'S INTO SHADOW AC'S TO CLEAR PARITY
				;IF HARDWARE AC'S TURNED OFF, AC'S WILL BE PRESERVED
	BLT	17,.EUPMP+17	;STOP WITH SHADOW AC 17
	SETZ	T2,		;ZERO AC T2
	SETOM	.EUPMP+T2	;SET SHADOW AC T2
	CONO	PI,10000	;CLEAR PI SYSTEM
	MOVE	P3,.CPMAP##
	POP	P,.EUPMP/PAGSIZ##(P3)
	CLRPGT	(0)		;CLEAR PAGING MEMORY AFTER CHANGING THE MAP

IFE FTKL10,<
;SETUP LOCATIONS 40 THRU 61

	MOVE	T1,[XWD LOC40,.EPIL##]	;SETUP LOWER CORE PI LOCATIONS
	BLT	T1,.EPIL##+LOC40E-1
>
;LINK DEVICE SERVICE ROUTINES TOGETHER


	SKIPE	DEVLST##	;HAVE SERVICE ROUTINES BEEN CHAINED TOGETHER YET ?
	JRST	@JRSTI1		;YES, MUST HAVE BEEN LOADED WITH BUILD
	MOVSI	T1,INTNUM##	;NO, NEGATIVE NUMBER OF SERVICE ROUTINES*2
INTLOP:	LDB	U,PINTCH##	;GET NEXT PI NUMBER

	LDB	J,DDBNUM##	;NUMBER OF DDBS
	JUMPN	J,NTLVDD	;JUMP IF NOT LEVEL D DISK
	HRRZ	J,INTTB1##(T1)	;ADDRESS OF DDB
	JUMPE	J,NTLVDD	;JUMP IF REALLY NO DDBS
	HLRZ	J,(J)		;IS LEVEL D DISK, GET LH OF DEVICE NAME
	CAIE	J,(SIXBIT .DSK.) ;SKIP IF IS REALLY A DISK
	JRST	NTLVDD		;NO
	MOVNI	J,KONINT##	;YES, GET OFFSET FOR INTERRUP LOCS
	ADD	J,INTTAB##(T1)	;PLUS INTERRUPT LOC=KONT DB
	DPB	U,KOYPI##	;STORE PI CHANNEL
IFN FTAUTC,<
	JRST	NOPICH		;AUTCON WILL SET UP NEEDED INTERRUPT CHAINS
>

NTLVDD:	LSH	U,1		;SHIFT LEFT ONE SO MATCH PI LOCATIONS
	JUMPE	U,NOPICH	;DOES THIS DEVICE HAVE A PI CHANNEL (PTY) ?
	LDB	J,PINTCP##
	LSH	J,.CPSOF##
	MOVE	J,.C0EPT##(J)
	ADDI	J,(U)
	MOVE	J,.EPIL##-.EPMP##(J)
	ADDI	J,3

INTLP1:	MOVE	U,J		;SAVE IT IN U (EITHER A JRST DEV'INT OR
				; JEN @CH'N
	MOVE	J,1(U)		;PICK UP INSTR. FOLLOWING INTERRUPT CONSO
	TLNN	J,000740	;IS IT A JEN ?
	JRST	INTLP1		;NO, KEEP LOOKING
	HRRZ	T2,INTTAB(T1)	;YES, LAST DEVICE SO FAR, GET DEV'NT
IFN FTAUTC,<
	CAIE	T2,MT0INT##	;AUTCON WILL DO IT
>
	SKIPN	(T2)		;DEV'INT=0?
	JRST	NOPICH		;YES, MUST BE VECTORRED INTERRUPT DEVICE
	HRLI	T2,(JRST)	;MAKE JRST INSTR.
	MOVEM	T2,1(U)		;CHANGE JEN @CH'N TO JRST DEV'NT
	MOVEM	J,1(T2)		;MAKE DEV'NT+1 BE JEN @CH'N
NOPICH:	AOBJN	T1,.+1		;PICKUP EVERY OTHER WORD
	AOBJN	T1,INTLOP	;ANY MORE INTERRUPT SERVICE ROUTINES ?
	JRST	@JRSTI1		;NO, EXIT
IFE FTKL10,<
LOC40:	0			;UUO PC
UUOTRP::JSR	LUUOPC##	;TO UUO HANDLER
	XPCW	CH1##
	JSR	PIERR##
	XPCW	CH2##
	JSR	PIERR##
	XPCW	CH3##
	JSR	PIERR##
	XPCW	CH4##
	JSR	PIERR##
	XPCW	CH5##
	JSR	PIERR##
	XPCW	CH6##
	JSR	PIERR##
	XPCW	CH7##
	JSR	PIERR##

LOC40E==.-LOC40
>
;ROUTINE TO READ A LINE FROM OPERATORS CONSOLE
;CALL:	PUSHJ P,GETLIN
;	JUST A CR TYPED IN
;	NORMAL RETURN (NOT A BLANK LINE)


GETLIN::HRLOI	T1,377777	;DO NOT ALLOW A DEFAULT
	MOVEM	T1,DEFLAG	;STORE FLAG
GETLI0:	MOVE	T1,LINEP
	MOVEM	T1,ONCTIP	;INITIAL STORAGE POINTER
	MOVEI	T3,40		;PRIME COMMAND ROUTINES WITH A SPACE
	MOVEM	T3,ONCTCH	; ..
	MOVEI	J,0		;FLAG NO ALTMODE SEEN, ZERO CHARACTER COUNT (RH
				; OF J), CLEAR DELETE FLAG (LH OF J)
GET1:	PUSHJ	P,XTYI		;WAIT FOR A CHARACTER
	SKIPGE	DEFLAG		;NEED A DEFAULT?
	ILDB	T3,DEFPTR	;YES--GET BYTE
	SKIPL	DEFLAG		;NEED A DEFAULT?
	MOVE	T3,FROMFE	;GET CHAR FROM WHERE IT WAS SAVED
	ANDI	T3,177		;STRIP PARITY
	CAIE	T3,"H"-100	;BACKSPACE?
	CAIN	T3,177		;RUBOUT?
	JRST	DELETE		;YES
	TLZE	J,1
	PUSHJ	P,BKSLSH	;TERMINAL BACKSLASH IF WE HAD BEEN DELETING
	CAIN	T3,"R"-100	;CONTROL-R?
	JRST	RETYPE		;YES
	CAIN	T3,"U"-100	;CONTROL-U?
	JRST	CNTRLU		;YES
	CAIE	T3,"$"		;ACCEPT DOLLAR-SIGN AS AN ALT-MODE
	CAIN	T3,33		;ALTMODE/ESCAPE?
	JRST	GETLN1		;YES
	CAIE	T3,175		;OTHER ALTS?
	CAIN	T3,176		; ..
	JRST	GETLN1		;YES
GET2:	PUSHJ	P,XTYO		;ECHO
	CAIL	T3,140		;LOWER CASE?
	TRZ	T3,40		;YES. MAKE UPPER
	IDPB	T3,T1		;STORE IN INPUT BUFFER
	CAIE	T3,15		;CAR RET?
	AOJA	J,GET1		;NO. LOOP TILL BREAK
	MOVEI	T3,12		;YES. ADD LF
	PUSHJ	P,XTYO		;OUTPUT LF
	MOVEI	T3,0		;TERMINATE INPUT STRING IN BUFFER
	IDPB	T3,T1		; ..
	JUMPN	J,CPOPJ1	;IF NON-NULL LINE, SKIP RET
	POPJ	P,0		;NULL. NON-SKIP RET
DELETE:	TRNN	J,-1		;AT BEGINNING OF LINE ?
	JRST	DELET1		;YES
	TLON	J,1		;SET DELETE FLAG
	PUSHJ	P,BKSLSH	;TYPE BACKSLASH IF JUST STARTING TO DELETE
	LDB	T3,T1		;GET PREVIOUS CHARACTER
	PUSHJ	P,XTYO		;ECHO IT AS WE DELETE IT
	ADD	T1,[XWD 070000,0] ;BACK UP BYTE POINTER
	TLNE	T1,400000	;FINISHED THIS WORD YET ?
	ADD	T1,[XWD 347777,-1] ;YES, BACK UP ADDRESS
	SOJA	J,GET1

DELET1:	TLZE	J,1
	PUSHJ	P,BKSLSH	;TERMINAL BACKSLASH IF DELETED ANY CHARS
DELET2:	MOVEI	T3,15
	PUSHJ	P,XTYO
	MOVEI	T3,12
	PUSHJ	P,XTYO
	JRST	GETLIN

CNTRLU:	MOVEI	T3,"^"		;TYPE UP ARROW
	PUSHJ	P,XTYO
	MOVEI	T3,"U"		;TYPE U
	PUSHJ	P,XTYO
	JRST	DELET2		;FINISH UP

BKSLSH:	PUSH	P,T3
	MOVEI	T3,134		;TYPE BACKSLASH
	PUSHJ	P,XTYO
	POP	P,T3
	POPJ	P,0

GETLN1:	MOVEI	T3,"$"		;OUTPUT DOLLAR SIGN IF ALT-MODE TYPED
	PUSHJ	P,XTYO
	HRROS	J		;MECHANISM USED TO BY-PASS PART OF DIALOGUE
	MOVEI	T3,15		; WHEN ALTMODE IS TYPED (J NEGATIVE ON
	JRST	GET2		; RETURN FROM GETLIN).

RETYPE:	MOVEI	T3,15		;CARRIAGE RETURN
	PUSHJ	P,XTYO
	MOVEI	T3,12		;LINE FEED
	PUSHJ	P,XTYO
	PUSH	P,T1		;SAVE THE BYTE POINTER
	SETZ	T3,		;GET A ZERO
	IDPB	T3,T1		;MAKE ASCIZ
	MOVE	T1,LINEP	;GET VIRGIN BYTE POINTER TO INPUT LINE
RETYP1:	ILDB	T3,T1		;GET A CHARACTER
	JUMPE	T3,RETYP2	;DONE AT NULL
	PUSHJ	P,XTYO		;TYPE IT
	JRST	RETYP1		;LOOP
RETYP2:	POP	P,T1		;RESTORE BYTE POINTER
	JRST	GET1		;GET NEXT CHARACTER
;ROUTINE TO TYPE A LINE ON OPERATOR CONSOLE
;ECHO CHECK STOPS LINE AND RETURNS
;CALL:	ONCTOP SET TO END OF MESSAGE


;CALL OPOUTX FOR MESSAGE CONTINUATIONS TO BE SUPPRESSED IF
; THE PREVIOUS PART OF THE MESSAGE WAS ^O'D
OPOUTX::SKIPE	CNTRLO		;^O IN EFFECT ?
	PJRST	OTSET		;YES, JUST CLEAR BUFFER AND GO AWAY

OPOUT::	SETZM	CNTRLO		;CLEAR ^O FLAG
	MOVEI	T3,0		;MAKE SURE STRING ENDS
	IDPB	T3,ONCTOP	;WITH A NULL
	MOVE	T1,LINEP	;AND RESTART AT BEGINNING
	MOVEM	T1,ONCTOP	; ..
IFN FTKL10,<
OPOUT1:	PUSHJ	P,SPCGTI##	;WAIT FOR INPUT, SKIP WITH CHAR IN T3
	  JRST	.+2		;NOT READY YET
	JRST	OPOUT2		;YES
>
IFN FTKS10,<
OPOUT1:	SKIPN	T3,CTYIWD	;SKIP IF CHAR IS THERE
	  JRST	.+3		;NONE THERE
	SETZM	CTYIWD		;CLEAR CTYIWD
	JRST	OPOUT2		;GO DO CTRL-O
>
	ILDB	T3,ONCTOP	;GET CHAR TO TYPE
	JUMPE	T3,CPOPJ	;QUIT ON NULL
	PUSHJ	P,XTYO		;TYPE CHAR
	JRST	OPOUT1		;LOOP

;HERE WHEN KEY STRUCK DURING TYPEOUT
OPOUT2:	SETOM	CNTRLO		;SET ^O FLAG
	MOVEI	T3,"^"
	PUSHJ	P,XTYO
	MOVEI	T3,"O"
	PUSHJ	P,XTYO
	MOVEI	T3,15
	PUSHJ	P,XTYO		;TYPE OUT CRLF
	MOVEI	T3,12
	PUSHJ	P,XTYO
	JRST	OTSET		;RESET OUTPUT BUFFER, RETURN FROM OPOUT

CNTRLO:	0			;SUPPRESS TYPE-OUT WHEN -1
XTYO:	CAIL	T3," "		;CONTROL CHARACTER?
	JRST	XTYOCH		;NO
	CAIN	T3,15		;CARRIAGE RETURN?
	SETZM	ONCCOL		;YES, BACK AT BEGINNING OF LINE
	CAIE	T3,11		;TAB?
	JRST	XTYOCN		;NO, DON'T COUNT WIDTH OF CONTROL CHARACTERS
	PUSH	P,T3		;SAVE ORIGINAL CHARACTER
	MOVE	T3,ONCCOL	;GET COLUMN
	ADDI	T3,^D8		;GET TO NEXT TAB STOP
	TRZ	T3,7		;...
	SUB	T3,ONCCOL	;FIND NUMBER OF SPACES NEEDED
	PUSH	P,T3		;SAVE COUNT
	MOVEI	T3," "		;GET A SPACE
	PUSHJ	P,XTYOCH	;OUTPUT IT
	SOSLE	(P)		;NEED ANY MORE?
	JRST	.-2		;YES, DO ANOTHER
	ADJSP	P,-1		;TOSS THE COUNT
	POP	P,T3		;RESTORE ORIGINAL TAB
	POPJ	P,		;RETURN

XTYOCH:	AOS	ONCCOL		;INCREMENT COLUMN COUNT
XTYOCN:	PUSHJ	P,PEVEN8##	;GET GOOD PARITY FOR CHAR
IFN FTKL10,<
	PUSHJ	P,SPCTYO##	;TYPE OUT
	PUSHJ	P,OPRFIL##	;DO FILLERS
XTYO1:	PUSHJ	P,APRCHK	;UPDATE TIME
	PUSHJ	P,SPCWTO##	;WAIT FOR OUTPUT DONE
	  JRST	XTYO1		;NOT DONE, WAIT SOME MORE
>
IFN FTKS10,<
	PUSHJ	P,APRCHK	;UPDATE TIME
	SKIPE	CTYOWD		;CAN WE TYPE YET?
	JRST	.-2		;NO, WAIT
	TRO	T3,CTYOVL	;SET VALID FLAG
	MOVEM	T3,CTYOWD	;PUT IT IN 8080'S WORD
	WRAPR	SP.SSF+SP.IFE	;INTERRUPT THE 8080
	PUSHJ	P,APRCHK	;UPDATE TIME
	SKIPE	CTYOWD		;CHAR TAKEN YET?
	JRST	.-2		;NO, WAIT
>
	ANDI	T3,177		;ONLY CHAR FOR COMPARES IN GETLIN
	POPJ	P,		;RETURN

ONCCOL:	0			;COLUMN NUMBER FOR TAB SIMULATION
;WAIT TIL INPUT DONE ON BEFORE RETURNING WITH NEXT CHAR.

XTYI:	PUSH	P,T1		;SAVE AN AC
XTYI1:	PUSHJ	P,APRCHK
	SKIPGE	DEFLAG
	JRST	XTYI2
IFN FTKL10,<
	PUSHJ	P,SPCGTI##	;SKIP IF CHAR PRESENT, WITH IT IN T3
>
IFN FTKS10,<
	SKIPN	T3,CTYIWD	;SKIP IF CHAR PRESENT, WITH IT IN T3
>
	  JRST	XTYI1
IFN FTKS10,<
	SETZM	CTYIWD		;CLEAR FOR NEXT TIME
>; END IFN FTKS10
	MOVEM	T3,FROMFE	;SAVE CHARACTER FOR USE LATER
	HRLOI	T1,777		;RESET THE TIMER
	MOVEM	T1,DEFLAG	; SO WE DON'T START UP
	MOVEM	T1,OPRCNT
	SETZM	DEFALW
	JRST	TPOPJ##		;RETURN AND RESTORE T1

XTYI2:	SETOM	DEFALW
	JRST	TPOPJ##

ONCKLT::BLOCK	1		;PLACE TO KEEP BITS FOR KL10 INTERVAL TIMER
FROMFE:	BLOCK	1		;PLACE TO KEEP CHAR AFTER XTYO GETS IT
;CHECK APR FOR CLOCK FLAG SO TIME USER TYPES IN WILL BE ACCURATE

APRCHK::
IFN FTKL10,<
	CONSO	TIM,TI.ITD	;TIMER ON KL10 FINISHED WITH ITS TICK?
>
IFN FTKS10,<
	CONSO	APR,SP.ITI
>
	POPJ	P,		;NO
IFN FTMP,<
	PUSH	P,T1
	MOVEI	T1,.C0CDB##	;INCREMENT .CPOK FOR ALL CPUS
APRCH1:	AOS	.CPOK##-.CPCDB##(T1)
	HLRZ	T1,.CPCDB##-.CPCDB##(T1) ;STEP TO NEXT CPU
	JUMPN	T1,APRCH1
	POP	P,T1
>
IFN FTKL10,<
	CONO	TIM,@ONCKLT	;YES, CLEAR INTERNAL TIMER DONE AND START UP AGAIN
>
IFN FTKS10,<
	WRAPR	SP.CSF!SP.ITI
>
	AOS	TIME##		;INCREMENT TIME
	SOS	DEFLAG		;SEE IF TIME FOR DEFAULT
IFN FTSCA,<
	PUSHJ	P,SAVT##	;SAD BUT NEEDED
	PUSHJ	P,SC.TIC##	;DO ONCE/TICK SCA MEMORY ALLOCATION
	PUSHJ	P,PPDTIC##	;DITTO FOR THE KLIPA
>; END IFN FTSCA
	POPJ	P,
;ONCTIV	ONCE TTY INPUT VECTOR.

ONCTIV::PUSHJ	P,ONCTYI	;(0 = CTIGNC) GET NEXT CHAR
	MOVE	T3,ONCTCH	;(1 = CTIGLC) GET LAST CHAR
	MOVEM	T3,ONCTCH	;(2 = CTISLC) SET LAST CHAR
	MOVE	T1,ONCTIP	;(3 = CTIGBP) GET BYTE POINTER
	MOVEM	T1,ONCTIP	;(4 = CTISBP) SET BYTE POINTER

;HERE TO READ THE NEXT CHAR FOR COMCON.

ONCTYI:	ILDB	T3,ONCTIP	;GET INPUT CHARACTER
	MOVEM	T3,ONCTCH	;STORE FOR RE-READS
	POPJ	P,0		;AND RETURN TO CALLING ROUTINE


ONCTYO:	SOSLE	ONCCNT		;COUNT CHARACTERS
	IDPB	T3,ONCTOP	;PUT IN BUFFER
	POPJ	P,0		;AND RETURN
ICONM::	SETTYO			;INITIALIZE LINE BUFFER
	JRST	CONMES##	;OUTPUT MESSAGE


OTSET::	MOVEI	T3,ONCTSZ	;SIZE OF BUFFER
	MOVEM	T3,ONCCNT	;SO CANT OVERFLOW
	MOVEI	T3,ONCTIV	;ADDRESS FOR READ ROUTINES TO USE
	MOVEM	T3,.CPTIV##	; ..
	MOVEI	T3,ONCTYO	;ADDRESS FOR TYPEOUT ROUTINES TO GO TO
	MOVEM	T3,.CPTOA##	; ..
	MOVE	T3,LINEP	;INITIAL OUTPUT POINTER
	MOVEM	T3,ONCTOP
	POPJ	P,0

YESNOD:	PUSHJ	P,ASKDEF	;ASK THE QUESTION
	 POPJ	P,		;JUST <CR>
	JRST	YESN		;AND CHECK FOR 'YES'

YESNO::	PUSHJ	P,ASKGET	;ASK QUESTION, GET ANSWER
	  POPJ P,0		;JUST C-R
YESN:	PUSHJ	P,ALTM##
	NEXTC
	TRZ	T3,40		;FIRST CHAR OF RESPONSE (U.C.)
	CAIN	T3,"Y"		;WAS IT A Y ?
	AOS	0(P)		;YES. SKIP
	POPJ	P,		;NO, MAYBE IT WAS "N". SO DON'T SKIP

ASKGET:	PUSHJ	P,ICONM		;OUTPUT THE QUESTION
	PUSHJ	P,OPOUT
	PJRST	GETLIN		;GET ANSWER
PPNERR:	MOVEI	T1,[ASCIZ \Bad [P,PN] typed try again: \]
GTPPN::	PUSHJ	P,ASKGET	;ASK QUESTION, GET ANSWER
	  POPJ	P,
	PUSHJ	P,ALTM##	;DID HE TYPE ESC
GTPPN1:	NEXTC			;GET THE NEXT CHARACTER
	CAIN	T3," "		;SPACE
	  JRST	GTPPN1		;NO, TRY AGAIN
	CAIE	T3,"["		;BEGINNING OF PPN
	  JRST	PPNERR		;NO, TRY AGAIN
	PUSHJ	P,GETOCT	;GET THE FIRST OCTAL NUMBER
	JUMPE	T2,PPNERR	;NULL PROJECT NUMBER IS BAD
	TLNN	T2,777777	;TOO BIG?
	CAIE	T3,","		;OR A BAD P,PN SEPARATER
	  JRST	PPNERR		;YEP
	PUSH	P,T2		;SAVE IT
	PUSHJ	P,GETOCT	;GET THE PROGRAMMER NUMBER
	POP	P,T1		;GET PROJECT NUMBER BACK
	JUMPE	T2,PPNERR	;NULL PROGRAMMER NUMBER IS BAD
	CAIE	T3,"]"		;CHECK FOR LEGAL TERMINATER
	CAIN	T3,0		;CRLF IS OK TOO
	TLNE	T2,777777	;TOO BIG?
	  JRST	PPNERR		;YEP
	HRL	T1,T2		;GET PROGRAMMER NUMBER
	MOVSS	T1		;SET IT UP AS [PROJ,PROG]
	AOS	(P)		;GIVE A SKIP 
	POPJ	P,		;AND RETURN


GETOCT:	MOVEI	T2,777777	;ASSUME WILD
	NEXTC			;GET FIRST CHARACTER
	CAIE	T3,"*"		;WILD?
	TDZA	T2,T2		;NO - CLEAR RESULT
GETOC1:	NEXTC			;NEXT CHAR
	CAIL	T3,"0"		;IN RANGE?
	CAILE	T3,"7"
	POPJ	P,
	LSH	T2,3		;CLEAR NULL DIGIT
	SUBI	T3,"0"		;CONVERT TO BINARY
	ADDI	T2,(T3)		;ADD TO TOTAL
	JRST	GETOC1		;LOOP UNTIL DONE
IFN FTSETS,<
GETSE0:	MOVEI	T1,[ASCIZ |Bad response, try again
|]
GETSET::PUSHJ	P,ASKGET	;ASK QUESTION, GET RESPONSE
	  POPJ	P,		;<CR> TYPED
	PUSHJ	P,ALTM##	;ALLOW ALTMODE COP-OUT
	PUSHJ	P,CTIGBP##	;GET BYTE POINTER
	MOVE	P1,T1		;SAVE IT
	PUSHJ	P,DECIN##	;TRY TO READ A NUMBER
	 JRST	GETSE1		;BAD RESPONSE, MAYBE "ALL"
	  JRST	GETSE1		;DITTO
	CAIL	T2,^D1		;IN LEGAL RANGE?
	CAILE	T2,^D36		;...
	JRST	GETSE0		;NO, COMPLAIN AND ASK AGAIN
	MOVE	T1,T2		;GET RESPONSE IN T1
	JRST	CPOPJ1		;SKIP RETURN

GETSE1:	MOVE	T1,P1		;GET BYTE POINTER BACK
	PUSHJ	P,CTISBP##	;RESET IT
	PUSHJ	P,CTEXT##	;GET RESPONSE
	MOVSS	T2		;SWAP HALVES
	CAIE	T2,'ALL'	;VALID RESPONSE?
	JRST	GETSE0		;NO, COMPLAIN AND ASK AGAIN
	SETZ	T1,		;GET A ZERO
	JRST	CPOPJ1		;SKIP RETURN
>; END IFN FTSETS
;CONSTANTS

ONCTIP:	0			;TYPE-IN POINTER
ONCTCH:	0			;LAST CHAR TYPED IN.
ONCTOP:	0			;TYPE-OUT POINTER
ONCCNT:	0			;COUNTER FOR TYO
LINEP:	POINT	7,LINBUF	;INPUT AND OUTPUT LINE BUFFER
LINBUF:	BLOCK	BUFLEN		;LINE BUFFER (LONG ENOUGH FOR WHY RELOAD /H MESSAGE)
ONCTSZ=<BUFLEN*5>-1		;CHARACTERS WHICH FIT IN OUTPUT BUFFER

;ASK A QUESTION WITH A DEFAULT ANSWER
;CALL WITH:
;	MOVEI	T1,[ASCIZ /QUESTION/]
;	MOVEI	T2,[ASCIZ /ANSWER/]
;	PUSHJ	P,ASKDEF
;	  RETURN HERE ON CRLF
;	ELSE RETURN HERE
;
;    OR
;	MOVEI	T1,[ASCIZ/QUESTION/]
;	MOVEI	T2,[ASCIZ/ANSWER/]
;	MOVEI	T3,^DSECS TO WAIT
;	PUSHJ	P,ASKDFT
;	  CRLF
;	OTHERWISE

ASKDFT::PUSH	P,OPRCNT	;SAVE OLD OPRCNT
	EXCH	T3,OPRCNT	;FORCE CALLER'S
	TLNE	T3,-1		;UNLESS OLD WAS VERY LARGE - IN WHICH CASE
	 MOVEM	T3,OPRCNT	;OPR TYPED SOMETHING, DON'T INTERFERE
	PUSHJ	P,ASKDEF	;ASK THE QUESTION
	 CAIA			;PRESERVE SKIPNESS
	AOS	-1(P)		;...
	POP	P,OPRCNT	;RESTORE OLD TIMEOUT
	POPJ	P,

;ROUTINE TO MAKE SURE WE GIVE THE OPR TIME TO ANSWER, BECAUSE WE
;THINK WE MAY HAVE TIMED HIM OUT UNFAIRLY, AND THE NEXT QUESTION IS IMPORTANT
RSTDEF::SKIPL	DEFALW		;HAS OPR BEEN TIMED OUT?
	 POPJ	P,		;NO, NOTHING TO DO
	PUSH	P,T1		;YES, SAVE T1
	MOVEI	T1,^D60		;MAKE TIMEOUT AT LEAST A MINUTE AGAIN
	CAMLE	T1,OPRCNT	;SO OPR CAN INTERVENE
	 MOVEM	T1,OPRCNT	; (NEW IS LONGER, USE IT)
	SETZM	DEFALW		;AND FORGET HE ISN'T THERE
	JRST	TPOPJ##		;RETURN

ASKDEF::PUSH	P,T2		;SAVE T2
	PUSHJ	P,ICONM		;OUTPUT QUESTION
	PUSHJ	P,OPOUT		; ..
	POP	P,T1		;RESTORE ANSWER
	MOVE	T2,DEFSP	;GET BYTE POINTER
	HLL	T1,T2		; ..
ASKDF1:	ILDB	T3,T1		;COPY STRING
	IDPB	T3,T2		; ..
	JUMPN	T3,ASKDF1	; ..
	MOVEI	T3,15		;ADD ON A CR
	IDPB	T3,T2		; ..
	MOVE	T1,OPRCNT	;ALLOW 60 SEC.
	IMULI	T1,JIFSEC##	; ..
	SKIPGE	DEFALW		;IF THE OPR HAS BEEN TIMED OUT ALREADY,
	 MOVEI	T1,1		; HURRY ALONG
	MOVEM	T1,DEFLAG	;STORE TICKS TILL TIMOUT AS A FLAG
	MOVE	T1,DEFSP	;SETUP POINTER
	MOVEM	T1,DEFPTR	; ..
	JRST	GETLI0
DEFSP:	POINT	7,DEFBUF
DEFLAG:	-1
DEFPTR:	POINT	7,DEFBUF
DEFBUF:	BLOCK	24		;ENOUGH FOR 99 CHAR DEFAULT
OPRCNT:	EXP	^D60		;SECONDS TILL OPR ASSUMED NOT PRESENT

DEFALW:	0			;-1 TO TAKE DEFAULT ALWAYS
;SUBROUTINE TO PUT A DECIMAL STRING INTO THE DEFAULT BUFFER
DECDEF:	MOVEI	T2,"0"		;ALWAYS FORCE 2 DIGITS
	CAIGE	T1,^D10		;WILL WE GET MORE THAN ONE ANYWAY?
	IDPB	T2,DEFPTR	;NO--ADD IN LEADING DIGIT
DCDFLP:	IDIVI	T1,12
	HRLM	T2,(P)
	SKIPE	T1
	PUSHJ	P,DCDFLP
	HLRZ	T1,(P)
	ADDI	T1,"0"
	IDPB	T1,DEFPTR
	POPJ	P,0


;SUBROUTINE TO PUT AN ASCIZ STRING INTO THE DEFAULT BUFFER

DEFSTR:	HRLI	T1,(POINT 7,)	;MAKE A BYTE POINTER
DEFST0:	ILDB	T2,T1		;FETCH A CHAR
	JUMPE	T2,CPOPJ	;RETURN TO CALLER
	IDPB	T2,DEFPTR	;STORE THIS ONE
	JRST	DEFST0		;ONWARDS
REFLOG::SETTYO
	PUSHJ	P,INLMES##	;CALLED BY DSKWNZ ROUTINE IN COMMON WHEN
				; ONE OR MORE DISKS HAVE BEEN REFRESHED.
	ASCIZ	/To automatically log-in under [1,2] type "LOGIN"

/
	JRST	OPOUT
MEMBAD:	MOVEI	T1,[ASCIZ /%Memory from /]
	PUSHJ	P,ICONM
	MOVE	T1,U
	PUSHJ	P,PRT22A##
	MOVEI	T1,[ASCIZ / to /]
	PUSHJ	P,CONMES##
	MOVE	T1,P3
	SUBI	T1,1
	PUSHJ	P,PRT22A##
	MOVEI	T1,[ASCIZ / is OFF-LINE
/]
	PUSHJ	P,CONMES##
	PUSHJ	P,OPOUT
	MOVEI	T1,[ASCIZ/Do you want it to be 1) ON-LINE, 2) OFF-LINE, or 3) Down? (Type #)
/]

	MOVEI	T2,[ASCIZ /2	;Default/]
	PUSHJ	P,ASKDEF
	  JRST	MEMBAD
	PUSHJ	P,DECIN##
	  JRST	MEMBAD
	  JRST	MEMBAD
	SOJE	T2,CPOPJ
	SOJE	T2,CPOPJ2##

	SOSE	T2
	JRST	MEMBAD
CPOPJ1:	AOS	(P)
CPOPJ:	POPJ	P,
SUNXMT::PUSH	P,P1		;SAVE WORKING ACS
	PUSH	P,P2
	PUSH	P,P3
	SETZB	T4,NXMTAB##	;ZERO HIGHEST EXISTANT ADDRESS SEEN, AND NXMTAB
	MOVE	T1,[NXMTAB##,,NXMTAB##+1]
	MOVEI	T2,NXMTAB##	; ..
	BLT	T1,NXMTBL##-1(T2)
	MOVEI	P1,CORBLK##	;NUMBER OF PAGES OF CORE POSSIBLE
	MOVE	T2,[POINT 1,NXMTAB##]
	MOVEI	T3,1		;TO MARK A PAGE AS NON-EXISTANT
	SETZB	P2,U		;ZERO P2 TO CALL A ROUTINE IN SYSINI,
				; START LOOKING FOR NXM AT 0
SUNXM0:
IFN FTKL10,<
	CONO	APR,LP.CSF+LP.NXM	;CLEAR NXM FLAG
>
IFN FTKS10,<
	WRAPR	SP.CSF+SP.NXM
>
			
	IBP	T2		;NEXT BYTE IN NXMTAB
	MOVEI	P3,MEMITL##	;NUMBER OF WAYS THE MEMORY CAN BE INTERLEAVED
SUNXM1:	PUSH	P,U		;SAVE THE CURRENT ADDRESS
	ADDI	U,-1(P3)	;CHECK PAGE PLUS INTERLEAVE OFFSET
	PUSHJ	P,REFMEM##	;REFERENCE TIS ADDRESS
	POP	P,U		;RESTORE THE CURRENT ADDRESS
	SOJG	P3,SUNXM1	;LOOK AT NEXT ADDRESS WITHIN THIS PAGE
	CONSO	APR,NXM##	;NON-EXISTANT MEMORY SEEN?
	JRST	SUNXM2		;NO
	DPB	T3,T2		;YES, MARK THE PAGE AS NON-EXISTANT
	JUMPN	T4,SUNXM3	;JUMP IF THE LAST PAGE LOOKED AT WAS NXM
	SKIPA	T4,U		;NOT SO, SO REMEMBER THE ADDRESS OF HIGHEST
				; EXISTANT PAGE SEEN SO FAR
SUNXM2:	MOVEI	T4,0		;MEMORY EXISTS, HAVEN'T SEEN THE HIGHEST EXISTANT PAGE YET
SUNXM3:	ADDI	U,PAGSIZ##	;GO ON TO THE NEXT PAGE OF MEMORY
	SOJG	P1,SUNXM0	; PROVIDED ALL POSSIBLE MEMORY HASN'T BEEN CHECKED
SUNXM4:	IDPB	T3,T2		;ONES TO THE END OF THIS WORD IN NXMTAB
	TLNE	T2,770000	; ..
	JRST	SUNXM4		; ..
	SKIPN	T4		;SKIP IF THE HIGHEST POSSIBLE PAGE OF MEMORY DIDNT EXIST
	MOVE	T4,U		;IT DID, SO U CONTAINS THE ADDRESS OF THE HIGHEST PAGE
	POP	P,P3		;RESTORE ACS
	POP	P,P2
	POP	P,P1
	POPJ	P,
IFN FTXMON,<
;SUBROUTINE TO ALLOCATE A MAP FOR A NON-ZERO SECTION
;CALL WITH:
;	T1 = SECTION NUMBER,,0
;RETURNS WITH A MAP ALLOCATED AND ITS ADDRESS STORED IN THIS CPUS
; EXEC SECTION MAP

ALCSMP:	HLRZ	T2,T1		;GET DESIRED SECTION
	ADDI	T2,SECTAB	;OFFSET INTO SECTION MAP TABLE
	ADD	T2,.CPEPT##	;INDEX INTO THE EPT
	SKIPE	(T2)		;MAP ALREADY ALLOCATED?
	POPJ	P,		;YES--DONE
	PUSH	P,MONVFF##
	PUSH	P,T1
	MOVEI	T1,.EUPMP
	MOVEM	T1,MONVFF##
	MOVEI	T1,PAGSIZ##
	MOVSI	T2,(<PM.DCD>B2+PM.WRT+PM.CSH+PM.SWB)
	PUSHJ	P,ONCMAP##
	MOVE	T1,[.EUPMP,,.EUPMP+1]
	SETZM	.EUPMP
	BLT	T1,.EUPMP+PAGSIZ##-1
	POP	P,T1
	LSH	T1,-^D18
	MOVE	T2,.CPMAP##
	MOVE	T3,.EUPMP/PAGSIZ##(T2)
	TLZ	T3,(PM.KPM)	;TURN OFF "KEEP ME"
	IOR	T3,.CPKPM##	;LIGHT PM.KPM IF CPU HAS AN MCA25
	MOVE	T2,.CPEPT##
	ADDI	T2,(T1)
	MOVEM	T3,SECTAB(T2)
REPEAT 0,<
	CAIGE	T1,(MS.FMD)	;IS THIS AN EXTENDED SECTION?
	JRST	ALCSM2		;NO, DON'T BOTHER THE SPT
	CAIE	T1,(MS.HGH)	;YES, IS IT THE HIGH HIGH MAP?
	JRST	ALCSM1		;NO, HANDLE DIFFERENTLY
	MOVE	T2,.CPCPN##	;YES, GET OUR CPU NUMBER
	SKIPN	SPTHGH##(T2)	;IF FIRST TIME HERE,
	MOVEM	T3,SPTHGH##(T2)	;STORE MAP POINTER IN OUR SPT SLOT FOR MS.HGH
	JRST	ALCSM2		;DONE HERE
ALCSM1:	MOVEM	T3,SPTCOM##-<(MS.FMD)>(T1)	;STORE DATA MAP POINTER IN SPT
ALCSM2:>
	POP	P,MONVFF##
	POPJ	P,

FFMD1::	0
RELMD1::0
>
REPEAT 0,<
;SUBROUTINE TO ALLOCATE PHYSICAL PAGES (NOT IN ANY MAP)
;CALL WITH:
;	T1 = NUMBER OF PAGES TO ALLOCATE
;RETURNS CPOPJ IF NONE AVAILABLE, CPOPJ1 T1 = WHERE ALLOCATED
GETPPG:	PUSH	P,P1
	PUSH	P,P2
	MOVE	P1,T1
	MOVE	P2,MONPFF##
	LSH	P2,W2PLSH##
GETPP1:	MOVE	T2,P2
	IDIVI	T2,^D36
	MOVNS	T3
	MOVSI	T4,400000
	LSH	T4,(T3)
	IORM	T4,NXMTAB##(T2)
	AOS	P2
	SOJG	T1,GETPP1
	MOVE	T1,MONPFF##
	LSH	P1,P2WLSH##
	ADDM	P1,MONPFF##
	POP	P,P2
	POP	P,P1
	JRST	CPOPJ1
>; END REPEAT 0
IFN FTXMON,<
;SUBROUTINE TO ALLOCATE SKY HIGH SEGMENT SECTION MAPS FOR NON-BOOT CPUS

ALCSHM:	PUSHJ	P,SAVE3##	;SAVE AC'S
	MOVE	P2,.CPEPT##	;GET EPT ADDRESS
	MOVE	P3,.CPEPT##-.CPCDB##(P1) ;GET TARGET CPU'S EPT ADDRESS
REPEAT 0,<
	MOVE	P3,.CPCPN##-.CPCDB##(P1)
	MOVEM	T1,SPTHGH##(P3)
>
	POPJ	P,

>;END IFN FTXMON
DEVICE:	BLOCK	1		;MONITOR BOOTSTRAP DEVICE
FNAME:	BLOCK	1		;MONITOR BOOTSTRAP FILE NAME
FEXT:	BLOCK	1		;MONITOR BOOTSTRAP EXTENSION
PPN:	BLOCK	1		;MONITOR BOOTSTRAP PPN
SFDLST:	BLOCK	5		;MONITOR BOOTSTRAP SFDS

PRESSL::BLOCK	1		;NON-ZERO IF USING PRESERVED SSL
PREASL::BLOCK	1		;NON-ZERO IF USING PRESERVED ASL
PRESDL::BLOCK	1		;NON-ZERO IF USING PRESERVED SDL
PRECNT:	BLOCK	1		;COUNT OF ENTRIES FOUND
PREERR:	BLOCK	1		;NON-ZERO IF AN ERROR DETECTED
BLDTXT:	BLOCK	1		;ADDRESS OF IDENTIFYING TEXT
BLDTBL:	BLOCK	1		;ADDRESS OF TABLE IN BOOTSTRAP VECTOR
BLDPTR:	BLOCK	1		;AOBJN POINTER TO TABLE
SAVTBL:	BLOCK	1		;SAVED ADDRESS OF TABLE IN BOOTSTRAP VECTOR
SAVPTR:	BLOCK	1		;SAVED AOBJN POINTER TO TABLE

FSTTIM::BLOCK	1		;NON-ZERO FOR CALL TO REDHOM

RADIX 8

XLIST	;LITERALS

LIT


LIST

VAR
ONCEND::END