Operating System - OpenVMS
1753883 Members
7676 Online
108809 Solutions
New Discussion юеВ

Re: Which $STATUS would be returned ?

 
SOLVED
Go to solution
The Brit
Honored Contributor

Which $STATUS would be returned ?

I had a fatal error occur during a batch backup job,

%BACKUP-E-FATALERR, fatal error on $2$MGA1:[]ND10.BCK;
-SYSTEM-F-PARITY, parity error

I want to trap this and similar errors using the "ON SEVERE_ERR0R" condition.

My question is: Will this situation be caught by SEVERE_ERROR condition ($severity = 4), or will the returned status be for the ERROR ($severity = 2)?

Thanks

Dave.
10 REPLIES 10
Willem Grooters
Honored Contributor

Re: Which $STATUS would be returned ?

Yes. ON ERROR ($severity = 2) will trap any error condition on, or above value 2, provided bit 0 is clear (causing informationals ($severity = 3) to pass)

From HELP ON:

If you specified an error condition as the condition parameter,
the action is taken when errors equal to or greater than the
specified level of error occur.

Willem
Willem Grooters
OpenVMS Developer & System Manager
The Brit
Honored Contributor

Re: Which $STATUS would be returned ?

Note:

I don't necessarily want to be notified just because an ERROR condition occurred.
I am only interested in whether a SEVERE_ERROR occurred.

Dave
Willem Grooters
Honored Contributor

Re: Which $STATUS would be returned ?

Too fast...
$STATUS will be "%BACKUP-E-FATALERR", $severity will be 2 and therefore, you wont be able to trap this one with ON SEVERE_ERROR.

On the other hand: Trapping it with ON ERROR, save $STATUS (because it will change with every statement), and check whether bit 3 is set: $ IF(STATUS .AND. 4) THEN...
would do the trick.
Willem Grooters
OpenVMS Developer & System Manager
Hein van den Heuvel
Honored Contributor

Re: Which $STATUS would be returned ?

Dave,

You are asking about what threshold level to pick right? You are not under the impression that you can do "on error this; on severe that" no?

There recently was an interesting spinoff discussion in a comp.os.vms thread about: "file locked by another user" mystery

Check it out...

http://groups.google.com/group/comp.os.vms/search?group=comp.os.vms&q=%22on+error%22+mystery&qt_g=Search+this+group

fyi... It brought up the old chestnut:
$ RESET := ON ERROR THEN RESET

Cheers,
Hein.
The Brit
Honored Contributor

Re: Which $STATUS would be returned ?

Hein,
you are correct, I am trying to figure out what level of error I need to trap this problem so I can deal with it appropriately.

Willem,
I cant quite figure out what you are describing with the (STATUS .AND. 4) check.

Here is something I am playing with,

Consider;

$ TYPE ASDF:[ASDF]ASDF
%TYPE-W-SEARCHFAIL, error searching for ASDF:[ASDF]ASDF.LIS;
-RMS-F-DEV, error in device name or inappropriate device type for operation
$ show symb $severity
$SEVERITY == "0"

and

$ edit ASDF:[ASDF]ASDF
%EDT-F-OPENIN, error opening ASDF:[ASDF]ASDF.; as input
-RMS-F-DEV, error in device name or inappropriate device type for operation
$ show symb $severity
$SEVERITY == "4"

I was playing with this scripting idea, vis.

$ Set Verify
$ On WARNING then Gosub ERROR_CHECK
$ TYPE ASDF:[ASDF]ASDF
$ Edit ASDF:[ASDF]ASDF
$ Set NoVerify
$ Exit
$!
$ ERROR_CHECK: ! Sub-routine
$ Stat = $Status
$ Write sys$output Stat
$ write sys$output f$message(Stat)
$ On ERROR then Gosub ERROR_CHECK
$ Return

When this runs,

@gosub_test
$ On WARNING then Gosub ERROR_CHECK
$ TYPE ASDF:[ASDF]ASDF
%TYPE-W-SEARCHFAIL, error searching for ASDF:[ASDF]ASDF.LIS;
-RMS-F-DEV, error in device name or inappropriate device type for operation
$ ERROR_CHECK: ! Sub-routine
$ Stat = $Status
$ Write sys$output Stat
%X10951238
$ write sys$output f$message(Stat)
%TYPE-W-SEARCHFAIL, error searching for !AS
$ On ERROR then Gosub ERROR_CHECK
$ Return
$ Edit ASDF:[ASDF]ASDF
%EDT-F-OPENIN, error opening ASDF:[ASDF]ASDF.; as input
-RMS-F-DEV, error in device name or inappropriate device type for operation
$ ERROR_CHECK: ! Sub-routine
$ Stat = $Status
$ Write sys$output Stat
%X1085109C
$ write sys$output f$message(Stat)
%EDT-F-OPENIN, error opening !AS as input
$ On ERROR then Gosub ERROR_CHECK
$ Return
$ Set NoVerify

The only danger that I see is if an warning or higher occurs actually in the subroutine. However the problem is that it only reports the first (lesser) warning/error.

Is there any way to get to the accompanying message, i.e.

-RMS-F-DEV, error in device name or inappropriate device type for operation

Dave.

Richard W Hunt
Valued Contributor
Solution

Re: Which $STATUS would be returned ?

Part of your problem is a confusing error name for which I blame someone who laid out the BACKUP messages. The "FATALERR" as reported by BACKUP isn't really FATAL (SEVERE_ERROR), it is merely (ordinary) ERROR. There was, indeed, a FATAL error at the device driver level, but BACKUP intercepted that and down-graded it from F to E. But then it re-signalled it as -E-.

What you see (two lines of error message) is what is issued by the DCL Last-Chance error handler. There was nothing between the BACKUP verb and the Last-Chance handler. That facility traverses the stacks to find out who did what to whom. In this case, the actions are:

1. Device issues fatal parity error
2. Backup reports this as error with an IDENTIFICATION field that includes the word FATAL but as a less-than-fatal severity.

DCL scripts, running at yet another layer (and in a different access-mode as well), would only see the BACKUP-E-... errors, not the underlying -F- errors.

So to see this in a script, you MUST use syntax

$ ON ERROR THEN ...

What you do in that case is define an error handler at the DCL level but between the BACKUP command and the Last-Chance handler. So you can intercept the error before you get to Last-Chance and blow up on the untrapped -E- condition.

If you actually took the trap, it would be either -E- or -F- and you would have to trap $STATUS to a local symbol for further analysis.
Sr. Systems Janitor
John Gillings
Honored Contributor

Re: Which $STATUS would be returned ?

Dave,
Stepping back a bit...

Error messages are generated from a structure called a "signal array". The structure can contain multiple condition codes, each with its own set if parameters (file names, PC values etc...). A signal array is generated when an error condition is encountered. It's then "signalled", which means it propagates up the call chain looking for a condition handler.

Any layer of software can declare its own condition handler, which will "catch" the signal array on its way up the stack. The handler can choose one of 3 options:

1) correct the condition and CONTINUE from the point it was signalled from

2) convert the signal to a return status and unwind the stack to a point of its choosing (usually the caller of the routine which declared the handler)

3) resignal the condition, possibly after tacking its own condition entry into the signal array.

Thus the signal array can accumulate additional information working its way up the call chain, so you'll sometimes see multiple condition codes from different facilities.

If the condition isn't handled somewhere up the call chain, it will be caught by the last chance exception handler, which typically will generate an error message, and possibly a traceback.

Your problem stems from the fact that the FINAL condition code, returned as $STATUS to DCL is just a longword. So we have to reduce a complex structure which can potentially contain a lot of fine detail, down to a single 32 bit entity. By convention, the $STATUS is simply the condition code from the first entry in the signal array.

Even worse, for an application which generates multiple conditions (perhaps because it's continuing after W severity conditions), it needs to choose a final status from all the signal arrays it's generated along the way.

The severity of that entry isn't necessarily related to that of any other entries. For example, if you attempt to TYPE a non-existent file, the RMS error is -E-FNF, but TYPE considers SEARCHFAIL to be W. Since the TYPE condition is the primary, that's what will end up in $STATUS.

So, answering your question... for your particular example the signal array is

-E-FATALERR
-F-PARITY

Since the primary condition is -E- that's what you'll get in $STATUS. Short of parsing the SYS$ERROR output, there's no way you can detect secondary, teritiary or deeper conditions from DCL. It was BACKUPs choice how to report the condition and it chose -E-.

If you want to get to that level of control, you may be able to catch the signal array by writing your own program to perform the BACKUP. See the OpenVMS Utility Routines Manual. This is not necessarily as difficult as it sounds, assuming you've got some fairly consisitent BACKUP operations.
A crucible of informative mistakes
Hoff
Honored Contributor

Re: Which $STATUS would be returned ?

There's the theory, and then there's the ugly. Error levels are a form of a polite fiction. They're surprisingly slippery. The more you dig into this area, the more you'll find murk. I've been in more than a few debates on the severity, and there are guidelines, but there are inevitably various oddities and borderline cases.

Fatal errors are not necessarily fatal, and severe errors aren't necessary severe.

The best you can state is that errors are errors. No more. No less.

If you have a specific error you're interested in, test for it.

If you encounter an unrecognized error during the execution of some code, the OpenVMS norm is to report it to somebody (else) to deal with.

By and large, an error and severe error are effectively the same (and particularly here, by the time you get back to the $ prompt), unless you're the one that's writing the code that's originally fielding the error itself.

There are cases where more severe errors further up the signal frames are downgraded. For example:

$ delete nosuchfile.txt;*
%DELETE-W-SEARCHFAIL, error searching for NOSUCHFILE.TXT;*
-RMS-E-FNF, file not found
$

There are many other cases.

One of the typical approaches in your current predicament is to capture the various error stacks with a regular expression (and having access to a decent regex makes this much easier), and use DIFFERENCES or analogous to spot new errors. This allows you to ride over the errors that are expected.

All that written, a fatal error message named FATALERR that isn't itself fatal looks odd.

Stephen Hoffman
HoffmanLabs LLC

Willem Grooters
Honored Contributor

Re: Which $STATUS would be returned ?

Dave,

(STATUS .AND. 4) = bit 3 is set. Any FATAL error would have this. If this bit is set, the outcome would be 4:

$ a=12
$ b=(a.and.4)
$ sho symb b
B = 4 Hex = 00000004 Octal = 00000000004
$ a=11
$ b=(a.and.4)
$ sho symb b
B = 0 Hex = 00000000 Octal = 00000000000

Check against 4 reveals the code is FATAL:

$ FATAL = 4
...
$ IF ($STATUS .AND. 4) .EQ. FATAL THEN ...

That's behind it :)

The real problem here is you need access to the real reason. Where BACKUP finished in ERROR, it was caused by a SEVERE_ERROR.

It would be nice if BACKUP would set a follow-up, the way MMS keeps the highest severity encountered. AFAIK, this data is lost once DCL regains control from BACKUP. So you will not be able to track the real problem unless scanning SYS$ERROR - like others already mentioned.



Willem Grooters
OpenVMS Developer & System Manager