.TITLE LIB_BUGCHK_LOG Condition Handler to log fatal errors .IDENT /V03.02/ ;++BUGCHKLOG.MAR ; ; Facility: ; Fermilab Accelerator Control System - ACNET ; ; Abstract: ; The condition handler in this module serves as a generalized ; BUGCHECK routine usually used for detached processes. "Fatal" ; errors (such as returned by system services) are to be reported ; by the user's doing a LIB$STOP with the status code. This condition ; handler eventually gets control and uses the status code and the PC ; of the LIB$STOP call to generate a message sent to OPCOM to be routed ; to the system console and the Operator log file. ; ; Environment: ; User mode condition handler. In FERMILIB.OLB object library. ; ;-- ; ; Modification History: ; ; Author: F. Nagy Creation date: 11-Jan-82 ; ; V01.00 11-Jun-82 FJN Adapted from NETBUGCHK in ACNET ; V02.00 10-Jan-83 FJN Add process name to default string and expand ; comments ; V03.00 26-Jan-83 FJN Permit addition of "PSL=!XL" in text by adding ; the PSL as an argument to $FAO call ; V03.01 15-Apr-83 FJN Standardizing help comments ; V03.02 06-Aug-84 FJN Drop from HELP text, replaced by the newer ; routine, LIB_LOG_SIGNALS ; .PAGE .SUBTITLE Declarations ; ; Include Files: ; ; NONE ; ; Library Macros: ; .NOCROSS $SSDEF ;System completion codes $CHFDEF ;Condition Handling Facility defs. $JPIDEF ;Job/process information codes $OPCDEF ;Operator Communications Codes $SFDEF ;Stack Frame offsets .CROSS ; ; Local Macros: ; ; NONE ; ; Equated Symbols: ; ; NONE ; ; Argument list offsets ; nargs = 0 ;Number of arguments in list msgadr = 4 ;Address of string descriptor of the ; FAO input string onmadr = 8 ;Address of longword (only lower 24 ; bits used) of target operator mask nestab = 12 ;Flag to disable establishing condition ; handler namlen = 40 ;Length of buffer for signal name msglen = 128 ;Length of buffer for OPCOM message ; ; Offsets of buffers and string descriptors from FP on the stack. ; nambuf = -namlen ;Buffer for signal name namdsc = nambuf - 8 ;String descriptor for signal name msgbuf = namdsc - msglen ;Buffer for report and OPCOM messages msgdsc = msgbuf - 8 ;String descriptor for message buffer faodsc = msgdsc + 8 ;String descriptor for FAO output faobuf = faodsc + 8 ;Buffer for FAO string output .PAGE .SUBTITLE Local storage for string pointers ; ; Read/write (inpure) local data program section ; .PSECT _LIB_DATA,PIC,USR,CON,REL,LCL,NOSHR,NOEXE,WRT,RD .SHOW BINARY OPERATOR_MSG_FORMAT: ;Address of control string (FAO input) .ADDRESS DFT_OPMSG ; for report message TARGET_OPERATORS: ;Bit mask of target operators (24 bits) .LONG ^XFFFFFF00 ; default is to all operators DFT_TXT2: ;Default text (after process name) .ASCII / Bugcheck !AD. PC=!XL/ DFT_LEN2 = . - DFT_TXT2 DFT_OPMSG: ;Default Operator message descriptor .LONG DFT_LEN2+15 .ADDRESS DFT_TEXT DFT_TEXT: .BLKB DFT_LEN2+15 ;Text buffer ASSUME OPC$B_MS_TYPE EQ 0 ;Assume OPCOM message type is 1st byte ASSUME OPC$B_MS_TARGET EQ - ;Assume OPCOM message dest. flags are ; in the next 3 bytes. ASSUME OPC$L_MS_RQSTID EQ - ;Assume OPCOM message request id is in ; second longword of OPCOM message ASSUME OPC$L_MS_TEXT EQ - ;Assume OPCOM message text after above GET_NAME: $GETJPI itmlst=10$ 10$: .WORD 15 ;Length of buffer for process name .WORD JPI$_PRCNAM ;Process name code .ADDRESS DFT_TEXT ;Address of output buffer .ADDRESS DFT_OPMSG ;Address of return length word .LONG JPI$C_LISTEND ; ; Program section for code and read-only data ; .PSECT _LIB_CODE,PIC,USR,CON,REL,LCL,SHR,EXE,NOWRT,RD .PAGE .SUBTITLE Initialize logging condition handler ;+0LIB_BUGCHK_LOG ; Initialize and (by default) establish a condition handler to log ; signals to system operator(s) and the operator log file. ; ; CALL LIB_BUGCHK_LOG([ctlstr.rt.dx [,tgtops.rlu.r [,noestb.rlu.v]]]) ; ; ctlstr the control string ($FAO input) used to setup the report ; string. See the "Control_String" subtopic for more ; information. Passed by descriptor. ; ; tgtops longword in which the low order 24 bits are the bit mask ; describing to which system operators the report message ; is to be sent. Default is all operators. Passed by ; reference. ; ; noestb value of 0 (default) in this flag causes LIB_BUGCHECKER ; to be setup as the condition handler for the caller of ; this procedure (outer procedure). A value of 1 disables ; establishing the condition handler (must be done by the ; user explicitly). Passed by value. ; ; LIB_BUGCHK_LOG will not generate a message for OPCOM if the signal ; is SS$_OPRABORT. An alternate routine to provide signal logging ; is LIB_LOG_SIGNALS which is the recommended usage. ;2 Control_String ; The default $FAO control string used to format the report message ; is " Bugcheck !AD. PC=!XL" (text inside the quotation ; marks except that is replaced by the process name). A ; user-supplied control string must also include a "!AD" FAO directive ; to insert the signal name text (given by length and address) and ; a "!XL" directive (or equivalent) to insert the address where the ; signal was generated (usually the next byte after the CALL to ; LIB$STOP or LIB$SIGNAL). The control string may inlcude an additional ; "!XL" directive to insert the process status longword in the output. ; Thus an example of the full control string is: ; "ZORKO aborted with !AD at PC=!XL and PSL=!XL" ;- ;+0LIB_BUGCHK_LOG ; ; Functional Description: ; Establishes the condition handler (LIB_BUGCHECKER) for the outer ; procedure. Can redefine the report message text and the destination ; operator bit mask used in the condition handler. ; ; Calling Sequence: ; CALL LIB_BUGCHK_LOG( {msgadr {,onmadr {,nestab}}} ) ; ; Input Parameters: ; msgadr(AP) - address of a string descriptor for the $FAO control ; string used to assemble the report message. ; onmadr(AP) - address of a longword in which the low order 24 bits ; are the bit mask defining the target operators for the ; report message. ; nestab(AP) - value is a flag. If 1 then the condition handler will ; NOT be established for the outer procedure. ; ; Implicit Inputs: ; NONE ; ; Output Parameters: ; R0 - completion status code ; ; Implicit Outputs: ; OPERATOR_MSG_FORMAT - setup as the address of the $FAO control string ; TARGET_OPERATORS - operator names bit mask copied to here ; ; Condition Codes: ; NONE ; ; Side Effects: ; Unless nestab(AP) is 0, then the address of LIB_BUGCHECKER will be ; stored as the condition handler of the outer procedure. ; If no user-specified string is provided, the process name is gotten ; and used to form a default string. ;- .ENTRY LIB_BUGCHK_LOG,^M<> MOVL @SF$L_SAVE_FP(FP),R1 ;Save old "condition handler" setting MOVAB B^LIB_BUGCHECKER,- ;Establish error reporting @SF$L_SAVE_FP(FP) ; condition handler for the caller TSTB nargs(AP) ;Check argument count BNEQ ARGS ;If arguments, process them ; ; Setup default string using process name ; DEFAULT: MOVAQ DFT_OPMSG,OPERATOR_MSG_FORMAT $GETJPI_G GET_NAME ;Get process name PUSHR #^M MOVZWL DFT_OPMSG,R2 ;Get length of process name text ADDW2 #DFT_LEN2,DFT_OPMSG ;Add in length of fixed text ADDL3 R2,DFT_OPMSG+4,R3 ;Get pointer past process name text MOVC3 #DFT_LEN2,DFT_TXT2,(R3) ;Concatenate fixed text to process name POPR #^M RET ; ARGS: CASEB nargs(AP),S^#1,S^#2 ;Branch on number of arguments 2$: .SIGNED_WORD 10$-2$ ;Just 1 argument .SIGNED_WORD 20$-2$ ;Just 2 arguments .SIGNED_WORD 30$-2$ ;All 3 arguments ;Fall through if more than 3 arguments 30$: BLBC nestab(AP),20$ ;If disable bit is off, skip cleanup MOVL R1,@SF$L_SAVE_FP(FP) ;Setup disabled, restore old setting ; of caller's condition handler vector ; 20$: MOVL onmadr(AP),R0 ;Get address of operator names mask BEQL 10$ ;If defaulted, leave current setting EXTZV #0,#24,(R0),R0 ;Get 24 bits of operators' mask ASHL #8,R0,TARGET_OPERATORS ;Store shifted with 0 in low byte ; 10$: MOVL msgadr(AP),R0 ;Get address of control string descr. BEQL DEFAULT ;If none given, setup default string MOVL R0,OPERATOR_MSG_FORMAT ;Save control string descr. address 9$: RET .PAGE .SUBTITLE Condition Handler to report and log error ;+02LIB_BUGCHECKER ; The condition handler for reporting the signals to the system ; operators is called LIB_BUGCHECKER. It is called with the normal ; condition handler arguments (the signal array address and the ; mechanism array address). It uses the implicit arguments of ; the currently set target operator mask and the report message ; control string descriptor address. ; ;- ;+0LIB_BUGCHECKER ; ; Functional Description: ; This routine is a condition handler. It reports signals to the system ; operator(s) via OPCOM and the $SNDOPR system service. The reports ; include the signal name (gotten with $GETMSG) and the signal PC ; (usually the location after a CALL to LIB$STOP). ; ; Calling Sequence: ; status = LIB_BUGCHECKER( signal-array-address , mechanism-array-address ) ; ; Input Parameters: ; CHF$L_SIGARGLST(AP) - address of the signal array which includes (among ; other things) the signal name and the PC. ; CHF$L_MCHARGLST(AP) - address of the mechanism array ; ; Implicit Inputs: ; OPERATOR_MSG_FORMAT - address of descriptor for control string for FAO ; TARGET_OPERATORS - 24 bit mask of target operators ; ; Output Parameters: ; R0 - completion status code ; ; Implicit Outputs: ; NONE ; ; Condition Codes: ; SS$_RESIGNAL - resignal the condition ; ; Side Effects: ; The condition is re-signaled as this condition handler performs no ; corrective actions, serving only to provide notification to the ; operator(s) of a failure in a (usually) detached process. ; ;- ;!+ ; status = LIB_BUGCHECKER(signal_array_address,mechanism_array_address) ; ; Algorithm: ; ; sig <= signal_array_address ; IF sig_name(sig)=OPRABORT THEN RETURN(RESIGNAL) ENDIF ; Get the signal name (facility code, severity level and message ident) ; for the signal at chf$l_sig_name(sig). ; tmp <= chf$l_sig_args(sig) - 1 ; Construct the report message with the signal name and the PC value from ; (sig)[tmp] using the OPERATOR_MSG_FORMAT control string. ; Send the "request" to the target operator using the report message. ; RETURN(RESIGNAL) ;!- .ENTRY LIB_BUGCHECKER,^M MOVL CHF$L_SIGARGLST(AP),R2 ;Get the address of the signal array CMPW CHF$L_SIG_NAME(R2),- ;Check for operator requested abort #SS$_OPRABORT BNEQ 10$ ;If not operator abort, continue BRW 98$ ;Operator stopped process, do not log ; that signal to console ; 10$: SUBL2 #-msgdsc,SP ;Reserve stack space for buffers, etc. MOVAB nambuf(FP),namdsc+4(FP) ;Set pointer into buffer string descr. MOVZBL #namlen,namdsc(FP) ; and the buffer length $GETMSG_S - ;Get the signal name text msgid=CHF$L_SIG_NAME(R2),- ;Signal value msglen=namdsc(FP),- ;Returns length of string bufadr=namdsc(FP),- ;Buffer descriptor address flags=#^XE ;Return facility name, severity, ident. MOVAB faobuf(FP),faodsc+4(FP) ;Set pointer into string descriptor and MOVZBL #msglen-8,faodsc(FP) ; length for report message buffer SUBL3 #1,CHF$L_SIG_ARGS(R2),R1 ;Get index to PC in signal array $FAO_S - ;Make report string from ctrstr=@OPERATOR_MSG_FORMAT,- ; control string, name and PC outlen=faodsc(FP),- ;Return string length outbuf=faodsc(FP),- ;Returned string buffer (on stack) p1=namdsc(FP),- ;Length of signal name text parameter p2=namdsc+4(FP),- ;Address of signal name text p3=(R2)[R1],- ;PC of signal p4=4(R2)[R1] ;PSL of signal (follows PC) MOVAB msgbuf(FP),R1 ;Address of OPCOM message buffer MOVL R1,msgdsc+4(FP) ;Setup OPCOM message descriptor ADDW3 #8,faodsc(FP),msgdsc(FP);Length of OPCOM message (with text) BISL3 #OPC$_RQ_RQST,- ;Code is for OPCOM request and target TARGET_OPERATORS,- ; operators given by prestored mask OPC$B_MS_TYPE(R1) CLRL OPC$L_MS_RQSTID(R1) ;Clear request id field (no reply) $SNDOPR_S msgbuf=msgdsc(FP) ;Send message to the operator! 98$: MOVZWL #SS$_RESIGNAL,R0 ;Resignal the message RET .END