	.TITLE	CNTRPRC_DISP
	.IDENT	/V1-001/
;++
;1 CNTRPRC_DISP	
; Programme to disp monitor data on screen.
; Records can be selected by:
;	Node
;	Facility 
;		Each facility provides further specific selection criteria.
;2 Facilities
; Currently there are 2 facilities embedded in this suite:
; RMI. Performance management using the $GETRMI facility (VMS7.3-2 and higher)
; Quomon. Monitors quota usage on a per process basis.
;3 RMI
;  Some 260 system-wide performance oriented counters per node. A future 
; implementation will allow grouping of items together in sub-groups to 
; facilitate easier reading of displays.
;3 Quomon
;  Each process detected in the system is monitored for quota remaining on 
;  20 items. Each result is expressed as percentage remaining so all results
; will be in range 0-100. 
; Records can be selected by node, image and process. All avaialable are 
; displayed in a dynamically created menu.  
;2 Modifications:
; 001	Feb-2004	PB	Creation
;	
;--
	.library        /CNTPRC.MLB/
        $IODEF                          ;Define I/O functions and modifiers
	$SSDEF
	$SMGDEF
	$TRMDEF
	$RMIDEF
	CNTRPRCDEF			; Counter processing
	

	.PSECT	CNTRPRC_DISP_D,WRT,NOEXE,PIC,SHR,QUAD

File:
CNTRPRCFAB:	$FAB  FAC = <DEL,UPD,GET,PUT>,- ; Access
		SHR = <DEL,UPD,GET,PUT>,- 	; Share with anyone
		FOP = CIF,-
		ORG = IDX,-			; Keyed file (Finally)
		FNM = <CNTRPRC>,-      		; Filename 
		DNM = <CNTRPRC.DAT.>,-      	; Filename 
		MRS = CTPRECSIZE,-
		XAB = CNTRPRCXAB
CNTRPRCRAB:	
		$RAB  FAB = CNTRPRCFAB,-        ; Record 
		ROP = <NLK>-			; Do not lock
 		RBF = CNTRPRCREC,-
		UBF = CNTRPRCREC,-
		USZ = CTPRECSIZE,-
		RSZ = CTPRECSIZE,-
		RAC = KEY,-		 	; KEY access
		KBF = KEY_BUF,-
		KSZ = 112
CNTRPRCXAB:
	  	$XABKEY	REF = 0,-  		; Primary key
		DTP = STG,-            		; Key = 12 Bytes
		POS = 0,-               	; Key position
		SIZ = 112,-              	; Key len
                NXT = CNTRPRCXAB1
CNTRPRCXAB1:
	  	$XABKEY	REF = 1,-  	; Second key
		DTP = STG,-            	; Key = 8 Bytes(node name space padded)
		POS = 0,-               ; Key position
		SIZ = 8,-               ; Key len
                FLG = <DUP>,-           ; Duplicates, changes allowed
                NXT = CNTRPRCXAB2
CNTRPRCXAB2:
	  	$XABKEY	REF = 2,-  	; 
		DTP = BN4,-             ; FACILITY
		POS = 8,-               ; Key position
		SIZ = 4,-               ; Key len
                FLG = <DUP>,-           ; Duplicates, changes allowed
                NXT = CNTRPRCXAB3
CNTRPRCXAB3:
	  	$XABKEY	REF = 3,-  	; 
		DTP = BN4,-             ; Code
		POS = 12,-              ; Key position
		SIZ = 4,-               ; Key len
                FLG = <DUP>,-           ; Duplicates, changes allowed
                NXT = CNTRPRCXAB4
CNTRPRCXAB4:
	  	$XABKEY	REF = 4,-  	 ; 
		DTP = STG,-              ; Facility specific
		POS = 16,-               ; Key position
		SIZ = 96,-               ; Key len
                FLG = <DUP>              ; Duplicates, changes allowed

;
	.ALIGN	QUAD
KEY_BUF:		
CNTRPRCREC:             .BLKB	CTPRECSIZE
KEY_ARRAY:		.BLKB	CTP_C_KEYSIZ*450
;

; FAO
FAOLST:		.BLKB	512
FAOBUF:		.BLKB	480
FAODESC:
FAOLEN:		.LONG	.-FAOBUF
		.ADDRESS  FAOBUF
TITLE1BUF:	.BLKB	132
TITLE1DESC:
TITLE1LEN:	.LONG	.-TITLE1BUF
		.ADDRESS  TITLE1BUF
RMII32HDRI:	.ASCID	/!40<!AC!> (I) !10<!UL!>!15<!UL!>!15<!UL!>!15<!UL!>!15<!UL!>!15<!AS!>/ 
RMII32HDRG:	.ASCID	/!40<!AC!> (G) !10<!UL!>!15<!UL!>!15<!UL!>!15<!UL!>!15<!UL!>!15<!AS!>/ 
RMIFLTHDR:	.ASCID	/!40<!AC!> !15<!AD!>!15<!AD!>!15<!AD!>!15<!AD!>!15<!AD!>!15<!AD!>!15<!AD!>/
RMITIT3:	.ASCID	/     !40<Counter!>!10<Count!>!15<Long Range!>!15<ShortRange!>!15<Maximum!>!18<Minimum!>!13<Slope!>/ 

SAMSTRI:	.ASCID	/ !24<!UL!> !7(15UL)/
SAMSTRF:	.ASCID	/ !24<!AD!> !7(15AD)/
CNTSMUPMT:	.ASCID	/ Press return for detail or ^Z for Station Menu /
TIMESTR:	.ASCID	/ !24<!%D!> !7(15AD)/
INTFMT: 	.ASCID	/!UL/
HINT1:		.ASCID	/Count is the number of sample cycles completed. Rises to 1728 and latches./
HINT2:		.ASCID	/Long and Short Range are the ranges this counter normally moves in./
HINT3:		.ASCID	/The number is a percentage (+ or -) of the mean (average) the series moves in. E.G. a series/
HINT4:		.ASCID	/who's average is calculated at 100 and the range expressed as 15 means this counter normally/
HINT5:		.ASCID	/is between 85 and 115. It is outside this range that alerts are generated./
HINT6:		.ASCID	/Maximum and Minimum are exatly that - the largest and smallest values observed./
HINT7:		.ASCID	/Slope is the calculated slope of the best fit line when this data is graphed. 0 is a flat line/
HINT8:		.ASCID	/(no change over time). A negative number is trending lower and a positive number is trending higher./
HINT9:		.ASCID	/The magnitude of the number indicates the strength of the trend./
	
CNT_MENU:	.ASCII	/Next    /
		.ASCII	/Counters/
SAM_MENU:	.ASCII	/Forward         /
		.ASCII	/Backward        /
		.ASCII	/Exit            /
SAM_MENU_LEN = .-SAM_MENU	
	.ALIGN	LONG
;
; Virtual Display Parameters
;
VD_DISP:	.LONG		; Virtual Display ID
VD_ROWS: 	.LONG 	3
VD_COLS: 	.LONG 	132
VD_DISP2:	.LONG		; Display 2
VD_ROW2:	.LONG 	15
VD_COL2:	.LONG	132      ;
VD_DISP3:	.LONG		; Display 3
VD_ROW3:	.LONG 	10
VD_COL3:	.LONG	132      ;
VD_DISP4:	.LONG		; Display 3
VD_ROW4:	.LONG 	2
VD_COL4:	.LONG	132      ;
;
; Optional Display Characteristics
;
;
; Pasteboard Paramenters
;
PB_BOARD:	.LONG 		; Pasteboard ID
PB_BOARD2:	.LONG 		; Pasteboard ID
PB_BOARD3:	.LONG 		; Pasteboard ID
PB_BOARD4:	.LONG 		; Pasteboard ID
PB_COL:		.LONG	1      
PB_ROW:		.LONG 	1
PB_COL2:	.LONG	1      ; Position for DISP2
PB_ROW2:	.LONG 	4
PB_COL3:	.LONG	1      ; Position for DISP3
PB_ROW3:	.LONG 	23
PB_COL4:	.LONG	1      ; Position for DISP4
PB_ROW4:	.LONG 	20
;
; Virtual Keyboard Parameters
;
KB_BOARD:	.LONG           	; Virtual Keyboard ID
KB_BUF:		.BLKB	80		; Input buffer
KB_DES:		.LONG	.-KB_BUF
		.ADDRESS KB_BUF
; 
; Menu parameters
;
; Menu Items
; Main Menu
M_LIST:	
		.ASCII	/Performance Monitor /
		.ASCII	/Quota Monitor       /
M_LIST_SIZE	=.-M_LIST
	.ALIGN	LONG
RMI_LIST:	
		.ASCII	/All                 /
		.ASCII	/Categories          /
RMI_LIST_SIZE	=.-RMI_LIST
	.ALIGN	LONG

M_DCS:		.WORD	20                  ; size of element
		.BYTE	DSC$K_DTYPE_T
		.BYTE	DSC$K_CLASS_A
M_ADDR:		.LONG		            ; Pointer to menu top
		.WORD	0		    ; DIGITS, SCALE
		.BYTE	DSC$K_DTYPE_T	    ; AFLAGS
		.BYTE	DSC$K_CLASS_S	    ; DIMCT
;		.LONG	^X01E00000          ; DIMCT,AFLAGS,DIGITS,SCALE
M_LEN:		.LONG   		    ; Size of array
		.LONG	20
		.LONG 	1		    ; 
		.LONG	20
		.LONG 	1		    ; 
BORDER:		.LONG	SMG$M_BORDER
REVERSE:	.LONG	SMG$M_REVERSE
HORIZONTAL:	.LONG	SMG$K_HORIZONTAL
VERTICAL:	.LONG	SMG$K_VERTICAL
BLOCK:		.LONG	SMG$K_BLOCK
W2:		.LONG 	2
W3:    		.LONG 	3
BOLD:		.LONG	SMG$M_BOLD
SPACING:	.LONG	SMG$M_DOUBLE_SPACE
FORMAT:		.LONG	SMG$M_FIXED_FORMAT
ERASE:		.LONG	SMG$M_ERASE_MENU
CURSOR_FLAGS:	.LONG	<SMG$M_CURSOR_OFF!SMG$M_SCROLL_JUMP>
UPCASE:		.LONG	TRM$M_TM_CVTLOW 	;Convert lower to upper case
CURCOL:		.LONG   1
CURROW:		.LONG   1
CHOICE:		.WORD
BYTCNT:		.WORD
CHOICE2:	.WORD
CHOIDE3:	.WORD

;
;Dynamic Menu
TEMPBUF:	.BLKB	24
TEMPDESC:	.LONG	.-TEMPBUF
		.ADDRESS  TEMPBUF
TEMPBUF2:	.BLKB	24
TEMPDESC2:	.LONG	.-TEMPBUF2
		.ADDRESS  TEMPBUF2
TEMPDESC3:	.QUAD
TIMBUF:		.BLKB	24
TIMDESC:	.LONG	.-TIMBUF
		.ADDRESS  TIMBUF
DM_LIST:        .BLKB	132*450		   ; Allow up to 450 items
DM_SIZ = .-DM_LIST
DMENU_END:	.LONG
CDXLT:		.LONG
	.ALIGN	LONG

DM_DCS:		.WORD	17                  ; size of element
		.BYTE	DSC$K_DTYPE_T
		.BYTE	DSC$K_CLASS_A
		.ADDRESS DM_LIST             ; Pointer
		.WORD	0		    ; DIGITS, SCALE
		.BYTE	DSC$K_DTYPE_T	    ; AFLAGS
		.BYTE	DSC$K_CLASS_S	    ; DIMCT
;		.LONG	^X01E00000          ; DIMCT,AFLAGS,DIGITS,SCALE
DM_SIZE:	.LONG   DMENU_END-DM_LIST	    ; Size of array
		.LONG	20
		.LONG 	1		    ; 
		.LONG	20
		.LONG 	1		    ; 

	.ALIGN quad

; Misc
OUTP:           .BLKB   512		; Strings here
OUTP_SIZ = .-OUTP
SAVE_DISP:	.LONG	0		; Saved char
SCR_WID:	.LONG	132
SCR_HEIGHT:	.LONG	48
CNTR:		.LONG	0
LASTSEEN:	.LONG	0
FLTLEN:		.LONG	0
RECCNT:		.LONG	0
       
	.PSECT CNTRPRC_DISP_C,EXE,NOWRT,LONG

	.CALL_ENTRY	MAX_ARGS=12, HOME_ARGS=TRUE, -
			INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			PRESERVE=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			LABEL=CNTRPRC_DISP
; 
	$OPEN	FAB=CNTRPRCFAB
	BSBW	ERROR_CHK		; Any error fatal
	$CONNECT RAB=CNTRPRCRAB
	BSBW	ERROR_CHK
	BSBW	CREATE_ENVIRONMENT
START:
; Opening menu
	PUSHAL	VD_DISP2
	CALLS	#1,G^SMG$ERASE_DISPLAY
	PUSHAL	CURSOR_FLAGS                    ; Turn cursor off
	PUSHAL	PB_BOARD
	CALLS	#2, G^SMG$SET_CURSOR_MODE
	BSBW	ERROR_CHK
	MOVW	#20,M_DCS			; Size of elements
	MOVAL	M_LIST,M_ADDR			; Address of text
	MOVL	#M_LIST_SIZE,M_LEN		; Size of text
 	PUSHAL	REVERSE                 	; Create menu
	PUSHAL	W3                              ; Menu options ...
	CLRL	-(SP)
	PUSHAL	SPACING
	PUSHAL	VERTICAL
	PUSHAL	M_DCS
	PUSHAL	VD_DISP2
	CALLS	#7,G^SMG$CREATE_MENU            ; 
	BSBW	ERROR_CHK
	PUSHAL	CHOICE
	PUSHAL	VD_DISP2
	PUSHAL	KB_BOARD
	CALLS	#3,G^SMG$SELECT_FROM_MENU
	BLBS	R0,20$
	CMPL	R0,#SMG$_EOF
	BEQLU	10$
	BSBW	ERROR_CHK
10$:
	PUSHAL	SAVE_DISP	
	PUSHAL  PB_BOARD
	CALLS	#1,G^SMG$RESTORE_PHYSICAL_SCREEN	; No error check
	PUSHAL	VD_DISP         	; Delete Environment
	CALLS	#1,G^SMG$DELETE_VIRTUAL_DISPLAY
	PUSHAL	VD_DISP2
       	CALLS	#1,G^SMG$DELETE_VIRTUAL_DISPLAY
	PUSHAL	VD_DISP3
       	CALLS	#1,G^SMG$DELETE_VIRTUAL_DISPLAY
	MOVL	#SS$_NORMAL,R0			; Signal Success
	$EXIT_S
20$:
	CASEW	CHOICE,#1,#1		; Select routine
100$:
	.WORD	101$-100$
	.WORD	102$-100$
101$:		   	     
	BSBW	SEL_RMI    
	BRW	START	     
102$:		   	     
	BSBW	SEL_QUOMON    
	BRW	START	     
     
; For each selection routine scan CNTRPOLL index adding each unique entry to
; a menu. Display that menu.
SEL_RMI:
	.JSB_ENTRY	INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			OUTPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>
	PUSHAL	VD_DISP2
	CALLS	#1,G^SMG$ERASE_DISPLAY
	PUSHAL	CURSOR_FLAGS                    ; Turn cursor off
	PUSHAL	PB_BOARD
	CALLS	#2, G^SMG$SET_CURSOR_MODE
	BSBW	ERROR_CHK
	MOVW	#20,M_DCS			; Size of elements
	MOVAL	RMI_LIST,M_ADDR			; Address of text
	MOVL	#RMI_LIST_SIZE,M_LEN  		; Size of text
 	PUSHAL	REVERSE                 	; Create menu
	PUSHAL	W3                              ; Menu options ...
	CLRL	-(SP)
	PUSHAL	SPACING
	PUSHAL	VERTICAL
	PUSHAL	M_DCS
	PUSHAL	VD_DISP2
	CALLS	#7,G^SMG$CREATE_MENU            ; 
	BSBW	ERROR_CHK
	PUSHAL	CHOICE
	PUSHAL	VD_DISP2
	PUSHAL	KB_BOARD
	CALLS	#3,G^SMG$SELECT_FROM_MENU
	BLBS	R0,20$
	CMPL	R0,#SMG$_EOF
	BEQLU	10$
	BSBW	ERROR_CHK
10$:
	RSB
20$:
	CASEW	CHOICE,#1,#1		; Select routine
100$:
	.WORD	101$-100$
	.WORD	102$-100$
101$:		   	     
102$:		   	     

; Scan all records in the file extracting each unique instance of the 
; specified component into a mem section fo display as menu.
	MOVC5	#0,#0,#0,#DM_SIZ,DM_LIST	; Clear
        MOVL	#450,R8                	;Maximum entries
	$REWIND	RAB=CNTRPRCRAB             ; from start of file
       	BSBW	ERROR_CHK
 	BISL    #RAB$M_EQNXT,CNTRPRCRAB+RAB$L_ROP
	MOVC5	#0,#0,#0,#CTP_C_KEYSIZ,CNTRPRCREC
	MOVB	#4,CNTRPRCRAB+RAB$B_KSZ
        MOVB	#3,CNTRPRCRAB+RAB$B_KRF
; Write titles
	MOVL	#132,FAODESC
	PUSHL	R0			; DUMMY
	PUSHAL	FAODESC
	PUSHAL	FAODESC
	PUSHAL	RMITIT3
	CALLS	#4,G^SYS$FAO

; Create table to pass to menu
	MOVAL	FAODESC,R1
	BSBW	PRINTH

	MOVAL	DM_LIST,R9               	;Location MENU items
	MOVAL	KEY_ARRAY,R10			; Location rec keys
	CLRL	R11				; Rec cnt
110$:   		
	MOVW	#CTPRECSIZE,CNTRPRCRAB+RAB$W_USZ
	MOVW	#CTPRECSIZE,CNTRPRCRAB+RAB$W_RSZ

	$GET	RAB=CNTRPRCRAB
       	BLBS	R0,120$
       	CMPL	R0,#RMS$_EOF
       	BEQLU	130$
       	BSBW	ERROR_CHK
; If RMI rec then add.
120$:
	TSTL	R11
	BNEQ	125$
 	MOVB    #RAB$C_SEQ,CNTRPRCRAB+RAB$B_RAC
125$:
	MOVAL	CNTRPRCREC,R6			; rec here
	CMPL	#CTP_FAC_RMI,CTP_L_FAC(R6)      ; RMI?
	BNEQU	110$				; Br not
	MOVL	#132,TEMPDESC3
	MOVL	R9,TEMPDESC3+4
	PUSHAL	TEMPDESC3				; Write here
	PUSHL	R6				; REC
	CALLS	#2,G^FORMAT_HEADER
	BLBC	R0,110$				; Ignore on error
; Save this rec key in array for later retrieval
	MOVC3	#CTP_C_KEYSIZ,(R6),(R10)
	ADDL	#CTP_C_KEYSIZ,R10
	ADDL	#132,R9
; Ensure no overflow - on overflow ignore rest.
	AOBLSS	R8,R11,110$

; Calc menu size and disp
130$:
; Print hints in DISP3
	MOVAL	HINT1,R1
	BSBW	PRINT_HINT
	MOVAL	HINT2,R1
	BSBW	PRINT_HINT
	MOVAL	HINT3,R1
	BSBW	PRINT_HINT
	MOVAL	HINT4,R1
	BSBW	PRINT_HINT
	MOVAL	HINT5,R1
	BSBW	PRINT_HINT
	MOVAL	HINT6,R1
	BSBW	PRINT_HINT
	MOVAL	HINT7,R1
	BSBW	PRINT_HINT
	MOVAL	HINT8,R1
	BSBW	PRINT_HINT
	MOVAL	HINT9,R1
	BSBW	PRINT_HINT

	MULL3	R11,#132,DM_SIZE
	MOVW	#132,DM_DCS
	PUSHAL	CURSOR_FLAGS                    ; Turn cursor off
       	PUSHAL	PB_BOARD
       	CALLS	#2, G^SMG$SET_CURSOR_MODE
       	BSBW	ERROR_CHK
132$:
       	PUSHAL	REVERSE                 	; Create menu
       	PUSHAL	W3                              ; Menu options ...
       	CLRL	-(SP)
       	PUSHAL	FORMAT
       	PUSHAL	BLOCK
	PUSHAL	DM_DCS
	PUSHAL	VD_DISP2
       	CALLS  	#7,G^SMG$CREATE_MENU            ; 
       	BSBW	ERROR_CHK
       	PUSHAL	CHOICE2
       	PUSHAL	CHOICE2
       	PUSHAL	VD_DISP2
       	PUSHAL	KB_BOARD
       	CALLS	#4,G^SMG$SELECT_FROM_MENU
	BLBS	R0,140$
	CMPL	R0,#SMG$_EOF
	BEQLU	135$
       	BSBW	ERROR_CHK
135$:	
	RSB
140$:    	
;  Calc offset to record
	MOVAL	KEY_ARRAY,R10			; Location rec keys
	MOVZWL	CHOICE2,R1 
	DECL	R1
	MULL	#CTP_C_KEYSIZ,R1
	ADDL	R1,R10
 	MOVB    #RAB$C_KEY,CNTRPRCRAB+RAB$B_RAC
	MOVB	#CTP_C_KEYSIZ,CNTRPRCRAB+RAB$B_KSZ
        MOVB	#0,CNTRPRCRAB+RAB$B_KRF
	MOVC3	#CTP_C_KEYSIZ,(R10),KEY_BUF
 	CLRL    CNTRPRCRAB+RAB$L_ROP

150$:   		
	MOVW	#CTPRECSIZE,CNTRPRCRAB+RAB$W_USZ
	MOVW	#CTPRECSIZE,CNTRPRCRAB+RAB$W_RSZ
	$GET	RAB=CNTRPRCRAB
       	BLBS	R0,160$
	RET
160$:
	PUSHAL	CNTRPRCREC
	CALLS	#1,G^DISPLAY_COUNTERS
	BRW	132$



SEL_QUOMON:
	.JSB_ENTRY	INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			OUTPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>
	RSB

; Subroutines
;
ERROR_CHK:
	.JSB_ENTRY	INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			OUTPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>

	BLBC	R0,10$
	RSB
10$:
	MOVL	R0,R6
	PUSHAL	SAVE_DISP	
	PUSHAL  PB_BOARD
	CALLS	#1,G^SMG$RESTORE_PHYSICAL_SCREEN	; No error check
	PUSHAL	VD_DISP         	; Delete Environment
	CALLS	#1,G^SMG$DELETE_VIRTUAL_DISPLAY
	PUSHAL	VD_DISP2
       	CALLS	#1,G^SMG$DELETE_VIRTUAL_DISPLAY
	MOVL	R6,R0
	$EXIT_S	R0				; Die
READ_PROMPT:
	.JSB_ENTRY	INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			OUTPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>

; Address of .ascid is in R1
		PUSHAL	VD_DISP                 ; Output display
		CLRL	-(SP)                   ; Blank 
		PUSHAL	BYTCNT                  ; Bytes to display
		CLRL	-(SP)                   ; Blank 
		CLRL	-(SP)                   ; Blank 
		PUSHAL	UPCASE                  ; Make input UPCASE 
		CLRL	-(SP)                   ; Blank 
		PUSHL	R1                      ; Output DSC
		PUSHAL	KB_DES                  ; Input buf
		PUSHAL	KB_BOARD                ; Input ID
		CALLS	#10,G^SMG$READ_STRING
		BLBS	R0,10$
		CMPL	#SMG$_EOF,R0            ; Trap and return ^Z
		BEQLU	10$
		BSBW	ERROR_CHK
10$:
		RSB
;
; Print subroutines
;
PRINT:
	.JSB_ENTRY	INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			OUTPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>
		PUSHAL	FAODESC
		PUSHAL	VD_DISP2
		CALLS	#2,G^SMG$PUT_LINE
		BSBW	ERROR_CHK
		RSB
PRINTH:
	.JSB_ENTRY	INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			OUTPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>
		
		PUSHL	R1			; Addr of .ascid in R1
		PUSHAL	VD_DISP
		CALLS	#2,G^SMG$PUT_LINE
		BSBW	ERROR_CHK
		RSB
PRINT2:
	.JSB_ENTRY	INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			OUTPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>

		PUSHL	R1			; Addr of .ascid in R1
		PUSHAL	VD_DISP2
		CALLS	#2,G^SMG$PUT_LINE
		BSBW	ERROR_CHK
		RSB

PRINT3:
	.JSB_ENTRY	INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			OUTPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>

		PUSHAL	FAODESC			
		PUSHAL	VD_DISP3
		CALLS	#2,G^SMG$PUT_LINE
		BSBW	ERROR_CHK
		RSB
PRINT_HINT:
	.JSB_ENTRY	INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			OUTPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>
; .addr of desc in R1
		PUSHL	R1		
		PUSHAL	VD_DISP3
		CALLS	#2,G^SMG$PUT_LINE
		BSBW	ERROR_CHK
		RSB

	.CALL_ENTRY	MAX_ARGS=12, HOME_ARGS=TRUE, -
			INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			PRESERVE=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			LABEL=DISPLAY_COUNTERS
; Routine to display tables within CNTRPRC rec and allow scrolling through them
;
; Input = .address of CNRREC_BUF to display


	PUSHAL	VD_DISP3
	CALLS	#1,G^SMG$ERASE_DISPLAY


; Detailed sample display.
; Print 2 line table with time(s) across top and samples on line 2.
; Print 1st 8 samples  and display  menu for FWD, BACK, Stations (menu).
; FWD is next 8 samples (limited to 48) Back is Prev 8 
;
	MOVL	4(AP),R6
	MOVW	#1,CHOICE
340$:
; TBLPNT is pointing to oldest sample. Display previous 8.
	SUBL3	#8,CTP_L_TBLPNT(R6),CNTR		; Set pointer
	BGEQ	350$                     		; If before begin ...
	ADDL	#CTP_C_MAXTBL,CNTR	                ; ... Wrap
	INCL	CNTR				; Account for 0 crossing
350$:
; Re-enter here
	MOVL	CNTR,R3
	MOVL	#8,R4					; Sample count

; 
360$:	
; Display times
	ADDL3	#CTP_TQ_TIMTBL,R6,R7		; Time origin
	MOVAL	OUTP,R9	     			; Strings
	MOVAL	FAOLST,R8      			; Descriptors (512)
	MOVL    #512,R10   			; Str len

370$:
	MOVAQ	(R7)[R3],(R8)			; Addr of 1st date/time
	ADDL	#4,R8                           ; Next list item
	INCL	R3				; Next index
	CMPL	#CTP_C_MAXTBL,R3	        ; If past end ...
	BGEQ	380$                     	; 
	CLRL	R3	                        ; ... Wrap to begin 
380$:
	DECL	R4   
385$:
; Extract time from each date string for remainder of display
; Set up out desc
	MOVL	R10,TEMPDESC3		; Make desc
	MOVL	R9,TEMPDESC3+4
	PUSHL	#2			; TIME
	PUSHAL	TEMPDESC3			; 
	PUSHAQ	(R7)[R3]
	CALLS	#3,G^EXTRACT_DATE

	INCL	R3				; Next index
	CMPL	#CTP_C_MAXTBL,R3	        ; If past end ...
	BGEQ	386$                     	; 
	CLRL	R3	                        ; ... Wrap to begin 
386$:
	ADDL	TEMPDESC3,R9 			; Adjust pointers
	SUBL	TEMPDESC3,R10
	MOVQ	TEMPDESC3,(R8)                  ; Add desc to list
	ADDL	#8,R8                           ; Next desc
	SOBGTR	R4,385$

	MOVL	#132,FAODESC
	PUSHAL	FAOLST
	PUSHAL	FAODESC
	PUSHAL	FAODESC
	PUSHAL	TIMESTR
	CALLS	#4,G^SYS$FAOL
	BLBS	R0,390$
	RET
390$:
	BSBW	PRINT3
 ; Display Corresponding 8 samples
	BBS	#CTP_V_FLT,CTP_L_DTYP(R6),1000$	; Br if Floating data
	MOVL	CNTR,R3
	MOVL	#8,R4					; Sample count

	ADDL3	#CTP_TF_SAMTBL,R6,R7		; Time origin
	MOVAL	OUTP,R9	     			; Strings
	MOVAL	FAOLST,R8      			; Descriptors (512)
	MOVL    #512,R10   			; Str len

400$:
; Extract time from each date string for remainder of display
; Set up out desc
	MOVL	R10,TEMPDESC3		; Make desc
	MOVL	R9,TEMPDESC3+4
	PUSHL	(R7)[R3]                ; Value
	PUSHAL	TEMPDESC3			; Len
	PUSHAL	TEMPDESC3		; 
	PUSHAL	INTFMT
	CALLS	#4,G^SYS$FAO
        BLBS	R0,410$
	RET
410$:
	INCL	R3				; Next index
	CMPL	#CTP_C_MAXTBL,R3	        ; If past end ...
	BGEQ	415$                     	; 
	CLRL	R3	                        ; ... Wrap to begin 
415$:
	MOVL	TEMPDESC3,(R8)+                  ; Add desc to list
	MOVL	R9,(R8)+
	ADDL	FLTLEN,R9 			; Adjust pointers
	SUBL	FLTLEN,R10
	SOBGTR	R4,400$

	MOVL	#132,FAODESC
	PUSHAL	FAOLST
	PUSHAL	FAODESC
	PUSHAL	FAODESC
	PUSHAL	SAMSTRF
	CALLS	#4,G^SYS$FAOL
	BLBS	R0,420$
	RET
420$:
	BSBW	PRINT3
; MENU
	MOVW	#16,M_DCS                	; Size of 1 ele
	MOVAL	SAM_MENU,M_ADDR
	MOVL	#SAM_MENU_LEN,M_LEN
 	PUSHAL	REVERSE                 	; Create menu
	PUSHAL	W3                              ; Menu options ...
	CLRL	-(SP)
	PUSHAL	SPACING
	PUSHAL	BLOCK
	PUSHAL	M_DCS
	PUSHAL	VD_DISP4
	CALLS	#7,G^SMG$CREATE_MENU            ; 
	BSBW	ERROR_CHK
	PUSHAL	CHOICE
	PUSHAL	CHOICE
	PUSHAL	VD_DISP4
	PUSHAL	KB_BOARD
	CALLS	#4,G^SMG$SELECT_FROM_MENU
	BLBC	R0,470$
        CMPW	#1,CHOICE
        BNEQU	450$
	ADDL	#8,CNTR				; Move forward 8 samples
	CMPL	CNTR,#CTP_C_MAXTBL			; Past end?
	BLEQ	440$                            ; No
	SUBL	#CTP_C_MAXTBL,CNTR
	DECL	CNTR				; Account for 0 crossing
440$:
	BRW	350$
450$:
        CMPW	#2,CHOICE
        BNEQU	470$
	SUBL	#8,CNTR				; Move BACK 8 samples
	BGEQ	460$				; Br if > 0
	ADDL	#CTP_C_MAXTBL,CNTR                        ; Wrap to top
	INCL	CNTR				; Account for 0 crossing
460$:
	BRW	350$
470$:
	PUSHAL	VD_DISP4
	CALLS	#1,G^SMG$ERASE_DISPLAY
	PUSHAL	VD_DISP3
	CALLS	#1,G^SMG$ERASE_DISPLAY
	RET
1000$:
; Display floating data                                              \
	PUSHAL	VD_DISP
	CALLS	#1,G^SMG$ERASE_DISPLAY
	MOVL	CNTR,R3
	MOVL	#8,R4					; Sample count

	ADDL3	#CTP_TF_SAMTBL,R6,R7		; Time origin
	MOVAL	OUTP,R9	     			; Strings
	MOVAL	FAOLST,R8      			; Descriptors (512)
	MOVL    #512,R10   			; Str len

1010$:
; Extract time from each date string for remainder of display
; Set up out desc
	MOVL	R10,TEMPDESC3		; Make desc
	MOVL	R9,TEMPDESC3+4
	PUSHAL	FLTLEN			; Len
	PUSHAL	TEMPDESC3		; 
	PUSHL	(R7)[R3]                ; Value
	CALLS	#3,G^FAO_FFLOAT
        BLBS	R0,1020$
	RET
1020$:
	INCL	R3				; Next index
	CMPL	#CTP_C_MAXTBL,R3	        ; If past end ...
	BGEQ	1030$                     	; 
	CLRL	R3	                        ; ... Wrap to begin 
1030$:
	MOVL	FLTLEN,(R8)+                  ; Add desc to list
	MOVL	R9,(R8)+
	ADDL	FLTLEN,R9 			; Adjust pointers
	SUBL	FLTLEN,R10
	SOBGTR	R4,1010$

	MOVL	#132,FAODESC
	PUSHAL	FAOLST
	PUSHAL	FAODESC
	PUSHAL	FAODESC
	PUSHAL	SAMSTRF
	CALLS	#4,G^SYS$FAOL
	BLBS	R0,420$
	RET

        
	.CALL_ENTRY	MAX_ARGS=12, HOME_ARGS=TRUE, -
			INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			PRESERVE=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			LABEL=FORMAT_HEADER
;++
;2 FORMAT_HEADER
; Routine to format the summary line for input CNTRPRC rec.

;3 Inputs
; .address of CNTRPRC record
; .address of desc pointing to output array. 
;3 Output
; The output array is written with the resulting fixed len string.
;3 Returns
;   SS$_NORMAL		OK
;   SS$_BADPARAM        Unrecognised data type
;   Any from $FAO
;--
	MOVL	4(AP),R6	; Record
	
; Select processor for datatype
; Determine record type and branch
	
	BBS	#CTP_V_INT,CTP_L_DTYP(R6),1$
	BBS	#CTP_V_QAD,CTP_L_DTYP(R6),1$
	BBS	#CTP_V_FLT,CTP_L_DTYP(R6),2$
	MOVL	#SS$_BADPARAM,R0
	RET                             ; Return

1$:
; Integer (32)
	PUSHAL	CDXLT			; Addr here
	PUSHL	CTP_L_CODE(R6)		; (TEMP)
	CALLS	#2,G^XLATE_RMI
; Slope
	MOVL	#24,TEMPDESC
	MOVAL	TEMPBUF,TEMPDESC+4
	PUSHAL	FLTLEN
	PUSHAL	TEMPDESC
	PUSHL	CTP_F_SLOPE(R6)
	CALLS	#3,G^FAO_FFLOAT
	BLBS	R0,15$
	RET
15$:
	MOVL	#24,TEMPDESC2
	MOVAL	TEMPBUF2,TEMPDESC2+4
	PUSHL	#1			; Date only
	PUSHAL	TEMPDESC2
	ADDL3	R6,#CTP_Q_LASTSN,-(SP)
	CALLS	#3,G^EXTRACT_DATE
; Select format string based on counter type
	MOVAL	RMII32HDRI,R2			; Assume INCR
	BBS	#CTP_V_INCR,CTP_L_DTYP(R6),17$  ; Br if so
	MOVAL	RMII32HDRG,R2			; Make GUAGE
17$: 

;	PUSHAL	TEMPDESC2		; Last seen
	PUSHAL	TEMPDESC		; Slope
	PUSHL	CTP_X_MIN(R6)		; Minimum
	PUSHL	CTP_X_MAX(R6)		; Maximum
	PUSHL	CTP_X_STRNG(R6)		; Short Term Range
	PUSHL	CTP_X_LTRNG(R6)		; Long Term Range
	PUSHL	CTP_X_LTCNT(R6)		; Long Term Count
	PUSHL	CDXLT			; (TEMP)
	PUSHL	8(AP)
	PUSHL	8(AP)
	PUSHL	R2
	CALLS	#10,G^SYS$FAO
	RET
2$:
	MOVAL	OUTP,R7		; Strings
	MOVAL	FAOLST,R8	; Descriptors (512)
	MOVL    #512,R10	; Str len

; Name
; Set up out desc
	MOVL	R10,TEMPDESC
	MOVL	R7,TEMPDESC+4

	PUSHAL	TEMPBUF			; .ascic addr here 
	PUSHL	CTP_L_CODE(R6)          ; code
	CALLS	#2,G^XLATE_RMI          ; Returns address of desc
	BLBS	R0,10$
	RET
10$:
	MOVL	TEMPBUF,(R8)
	MOVZBL	@TEMPBUF,R1
	ADDL	R1,R7       		; Next str
	SUBL	R1,R10      		; Deduct from len
	ADDL	#4,R8           	; Next desc
; LT TOTAL
	MOVL	R10,TEMPDESC
	MOVL	R7,TEMPDESC+4
	PUSHAL	FLTLEN
	PUSHAL	TEMPDESC
	PUSHL	CTP_X_LTTOT(R6)
	CALLS	#3,G^FAO_FFLOAT
	BLBS	R0,20$
	RET
20$:
	MOVL	FLTLEN,(R8)	; Store desc
	MOVL	R7,4(R8)
	ADDL	#8,R8           ; Next desc
	ADDL	FLTLEN,R7       ; Next str
	SUBL	FLTLEN,R10      ; Deduct from len
; LTRNG
	MOVL	R10,TEMPDESC
	MOVL	R7,TEMPDESC+4
	PUSHAL	FLTLEN
	PUSHAL	TEMPDESC
	PUSHL	CTP_X_LTRNG(R6)
	CALLS	#3,G^FAO_FFLOAT
	BLBS	R0,30$
	RET
30$:
	MOVL	FLTLEN,(R8)	; Store desc
	MOVL	R7,4(R8)
	ADDL	#8,R8           ; Next desc
	ADDL	FLTLEN,R7       ; Next str
	SUBL	FLTLEN,R10      ; Deduct from len
; STRNG
	MOVL	R10,TEMPDESC
	MOVL	R7,TEMPDESC+4
	PUSHAL	FLTLEN
	PUSHAL	TEMPDESC
	PUSHL	CTP_X_STRNG(R6)
	CALLS	#3,G^FAO_FFLOAT
	BLBS	R0,40$
	RET
40$:
	MOVL	FLTLEN,(R8)	; Store desc
	MOVL	R7,4(R8)
	ADDL	#8,R8           ; Next desc
	ADDL	FLTLEN,R7       ; Next str
	SUBL	FLTLEN,R10      ; Deduct from len
; STCNT
	MOVL	R10,TEMPDESC
	MOVL	R7,TEMPDESC+4
	PUSHAL	FLTLEN
	PUSHAL	TEMPDESC
	PUSHL	CTP_X_STCNT(R6)
	CALLS	#3,G^FAO_FFLOAT
	BLBS	R0,50$
	RET
50$:
	MOVL	FLTLEN,(R8)	; Store desc
	MOVL	R7,4(R8)
	ADDL	#8,R8           ; Next desc
	ADDL	FLTLEN,R7       ; Next str
	SUBL	FLTLEN,R10      ; Deduct from len
; MAX
	MOVL	R10,TEMPDESC
	MOVL	R7,TEMPDESC+4
	PUSHAL	FLTLEN
	PUSHAL	TEMPDESC
	PUSHL	CTP_X_MAX(R6)
	CALLS	#3,G^FAO_FFLOAT
	BLBS	R0,60$
	RET
60$:
	MOVL	FLTLEN,(R8)	; Store desc
	MOVL	R7,4(R8)
	ADDL	#8,R8           ; Next desc
	ADDL	FLTLEN,R7       ; Next str
	SUBL	FLTLEN,R10      ; Deduct from len
; MIN
	MOVL	R10,TEMPDESC
	MOVL	R7,TEMPDESC+4
	PUSHAL	FLTLEN
	PUSHAL	TEMPDESC
	PUSHL	CTP_X_MIN(R6)
	CALLS	#3,G^FAO_FFLOAT
	BLBS	R0,70$
	RET
70$:
	MOVL	FLTLEN,(R8)	; Store desc
	MOVL	R7,4(R8)
	ADDL	#8,R8           ; Next desc
	ADDL	FLTLEN,R7       ; Next str
	SUBL	FLTLEN,R10      ; Deduct from len

; Slope
	MOVL	R10,TEMPDESC
	MOVL	R7,TEMPDESC+4
	PUSHAL	FLTLEN
	PUSHAL	TEMPDESC
	PUSHL	CTP_F_SLOPE(R6)
	CALLS	#3,G^FAO_FFLOAT
	BLBS	R0,80$
	RET
80$:
	MOVL	FLTLEN,(R8)	; Store desc
	MOVL	R7,4(R8)
	ADDL	#8,R8           ; Next desc
	ADDL	FLTLEN,R7       ; Next str
	SUBL	FLTLEN,R10      ; Deduct from len

; Last seen
	MOVL	R10,TEMPDESC
	MOVL	R7,TEMPDESC+4
	PUSHL	#1			; Date only
	PUSHAL	TEMPDESC
	ADDL3	R6,#CTP_Q_LASTSN,-(SP)
	CALLS	#3,G^EXTRACT_DATE
	BLBS	R0,90$
	RET
90$:
	MOVQ	TEMPDESC,(R8)


	PUSHAL	FAOLST
	PUSHL	8(AP)
	PUSHL	8(AP)
	PUSHAL	RMIFLTHDR   
	CALLS	#4,G^SYS$FAOL
	RET

	.CALL_ENTRY	MAX_ARGS=12, HOME_ARGS=TRUE, -
			INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			PRESERVE=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			LABEL=EXTRACT_DATE
;++
;2 EXTRACT_DATE
; Routine to take binary time, convert it to ascii and return the date
; or time portion. The routine writes the entire date string to the outp desc
; then adjusts the len to include the selected field only. Thus the outp desc 
; must be at least 23 bytes though the len returned is always 11(date) or 
; 8 (time).
;3 Inputs
; .address of .quad VMS binary time to convert
; .address of desc pointing to outp area. Must be at least 23 bytes long
; .long flag - 2 = time. any other param defaults to date. 
;3 Outputs
;  The entire date string is produced in the outp area and then 
; manipulated to return the desired field.
;3 Returns
;	SS$_NORMAL	OK
; any from $ASCTIM
;--

	CLRL	-(SP)			; cvtflg
	PUSHL	4(AP)
	PUSHL	8(AP)
	PUSHL	8(AP)
	CALLS	#4,G^SYS$ASCTIM
        BLBS	R0,10$
	RET
10$:
	CMPL	12(AP),#2
	BEQL	20$
; Date
	MOVL	#11,@8(AP)
	MOVL	#SS$_NORMAL,R0
	RET
; Time
20$:
	MOVQ	@8(AP),R6
	MOVL	#8,R6
	ADDL3	#12,R7,R8
	MOVC3	R6,(R8),(R7)
	MOVQ	R6,@8(AP)
	MOVL	#SS$_NORMAL,R0
	RET

	


;
CREATE_ENVIRONMENT:
	.JSB_ENTRY	INPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>, -
			OUTPUT=<R2,R3,R4,R5,R6,R7,R8,R9,R10,R11>

;
; Create Pasteboards
;
	PUSHAL	PB_BOARD
	CALLS	#1,G^SMG$CREATE_PASTEBOARD
	BSBW	ERROR_CHK
	PUSHAL	PB_BOARD2
	CALLS	#1,G^SMG$CREATE_PASTEBOARD
	BSBW	ERROR_CHK
	PUSHAL	PB_BOARD3
	CALLS	#1,G^SMG$CREATE_PASTEBOARD
	BSBW	ERROR_CHK
	PUSHAL	PB_BOARD4
	CALLS	#1,G^SMG$CREATE_PASTEBOARD
	BSBW	ERROR_CHK
; Save the current screen set up. Attempt to set it to 48x132. Restore
; on exit
	CLRL	-(SP)                         ; 1st row
	CLRL	-(SP)                         ; Last row
	PUSHAL	SAVE_DISP		      ; Saved screen ID
	PUSHAL 	PB_BOARD		      ; Our id
	CALLS	#4,G^SMG$SAVE_PHYSICAL_SCREEN
	BSBW	ERROR_CHK
; 
	CLRL	-(SP)                         ; No colour change
	CLRL	-(SP)                         ;      "
	PUSHAL	VD_ROWS			      ; Actual height set
	PUSHAL	SCR_HEIGHT		      ; Try for 48
	PUSHAL	VD_COLS			      ; Actual wid
	PUSHAL  SCR_WID			      ; Try 132
	PUSHAL	PB_BOARD
	CALLS	#7,G^SMG$CHANGE_PBD_CHARACTERISTICS
	BSBW	ERROR_CHK
	MOVL	#11,VD_ROWS			; Set our page len
;
	PUSHAL	BORDER
	PUSHAL	VD_DISP
	PUSHAL	VD_COLS
        PUSHAL	VD_ROWS
	CALLS	#4,G^SMG$CREATE_VIRTUAL_DISPLAY
	BSBW	ERROR_CHK

	PUSHAL	BORDER
	PUSHAL	VD_DISP2
	PUSHAL	VD_COL2
        PUSHAL	VD_ROW2
	CALLS	#4,G^SMG$CREATE_VIRTUAL_DISPLAY
	BSBW	ERROR_CHK

	PUSHAL	BORDER
	PUSHAL	VD_DISP3
	PUSHAL	VD_COL3
        PUSHAL	VD_ROW3
	CALLS	#4,G^SMG$CREATE_VIRTUAL_DISPLAY
	BSBW	ERROR_CHK

	PUSHAL	BORDER
	PUSHAL	VD_DISP4
	PUSHAL	VD_COL4
        PUSHAL	VD_ROW4
	CALLS	#4,G^SMG$CREATE_VIRTUAL_DISPLAY
	BSBW	ERROR_CHK


;
; Create Virtual Keyboard
;
	PUSHAL	KB_BOARD
	CALLS	#1,G^SMG$CREATE_VIRTUAL_KEYBOARD
	BSBW	ERROR_CHK
;
; Associate the pasteboards and Virtual Displays
;
	PUSHAL	PB_COL		;Column
	PUSHAL	PB_ROW		;Row
	PUSHAL	PB_BOARD
	PUSHAL	VD_DISP
	CALLS	#4,G^SMG$PASTE_VIRTUAL_DISPLAY
	BSBW	ERROR_CHK
	PUSHAL	PB_COL2		;Column
	PUSHAL	PB_ROW2		;Row
	PUSHAL	PB_BOARD2
	PUSHAL	VD_DISP2
	CALLS	#4,G^SMG$PASTE_VIRTUAL_DISPLAY
	BSBW	ERROR_CHK

	PUSHAL	PB_COL3		;Column
	PUSHAL	PB_ROW3		;Row
	PUSHAL	PB_BOARD3
	PUSHAL	VD_DISP3
	CALLS	#4,G^SMG$PASTE_VIRTUAL_DISPLAY
	BSBW	ERROR_CHK

	PUSHAL	PB_COL4		;Column
	PUSHAL	PB_ROW4		;Row
	PUSHAL	PB_BOARD4
	PUSHAL	VD_DISP4
	CALLS	#4,G^SMG$PASTE_VIRTUAL_DISPLAY
	BSBW	ERROR_CHK


	pushal	cursor_flags                    ; Turn cursor off
	pushal	PB_BOARD
	calls	#2, g^smg$set_cursor_mode
	RSB

	.END	CNTRPRC_DISP
