[CATCH cx_class1 cx_class2 ... [INTO oref].
[CLEANUP [INTO oref].
The statement TRY introduces a control structure with
several statement blocks. The first statement block try_block is always run, whereas a branching off to exactly one of the remaining statement blocks only occurs if a
class-based exception occurs in the try_block.
A TRY control structure defines the following statement blocks:
a TRY-Block try_block directly after the TRY statement
The TRY block defines a guarded area whose class-based
exceptions can be caught in the subsequent CATCH blocks.
If no exception occurs in the TRY block and it reaches
its end, the system continues the processing after ENDTRY.
If a class-based exception occurs in the TRY block, the
system searches for an exception handler in the same or an external TRY control structure (see system response).
one or more optional CATCH blocks
catch_block each directly after a CATCH statement
A CATCH block is an exception handler, that is, the program
logic that is executed when the corresponding exceptions in TRY
block occur in the same TRY control structure.
CATCH block catches the exceptions of the exception classes
cx_class1 cx_class2 ..., which are specified after the
statement CATCH, as well as the exceptions of the subclasses
to these exception classes. In every CATCH statement of
a TRY control structure, you can execute a list of as
many exception classes cx_class1 cx_class2 ... as you
want, whereby the more special exception classes (subclasses) have to be executed before the more general
exception classes (superclasses). You have to observe this order within a
CATCH statement as well as across several CATCH statements of a TRY control structure.
If the INTO addition is specified, a reference to
the exception object is stored in oref, whereby
oref must be an object reference variable with a static type that is more general or the
same as the most general of the specified exception classes. You can access the attributes and methods of the exception object via oref.
If the system reaches the end of the CATCH block, it continues with the processing after ENDTRY.
an optional CLEANUP block
cleanup_block directly after the CLEANUP statement
A CLEANUP block is executed when a class-based exception
occurs in the TRY block of the same
TRY control structure, but is caught in a CATCH block of an internal TRY control structure (see
INTO addition is specified, a reference to the exception object is stored in
oref, whereby oref must be an object reference
variable of type CX_ROOT. You can access the exception object via oref.
You must execute the CLEANUP block fully and leave
it via ENDTRY, so that the exception can be propagated
to its handler. If you try to leave the context of a CLEANUP
block too early, a runtime error will occur. In a CLEANUP block, you cannot execute any
statements in which it is statically obvious that you cannot return to the CLEANUP block.
A TRY control structure precludes the simultaneous use of the CATCH SYSTEM-EXCEPTIONS statement to catch
catchable runtime errors in the current processing block.
All statement blocks of a TRY control structure can contain
any kind of control structures, in particular, further TRY control structures.
The rule that special exception classes have to be executed before general execution classes in
CATCH, ensures that an exception is not caught by a general exception handler (superclass) when a special handler (subclass) is intended.
In a CLEANUP block, you can execute a cleanup of the
TRY block. For example, you can bring objects to a consistent state, or release external resources to which an external handler would no longer have had access.
Since no exceptions (except those with category CX_NO_CHECK from event handlers) can be propagated from the
static constructors and event handlers, you must always catch these locally.
Catching class-based exceptions.
If the content of number is greater than 100, an exception
of class CX_DEMO_ABS_TOO_LARGE is triggered in the TRY block of the TRY control structure of the
framework program. This exception
is caught by the second CATCH block of the same
TRY control structure, since it is the subclass of the most general exception CX_ROOT.
If the content of number is 0, the runtime environment
triggers an exception of the predefined class CX_SY_ZERODIVIDE in the TRY
block of the TRY control structure of the called subprogram
calculation. This exception is caught in the
CATCH block of the same TRY control structure.
If the content of number is a negative number, the runtime
environment triggers an exception of the predefined class CX_SY_ARG_OUT_OF_DOMAIN in the
TRY block of the TRY control structure of the
called subprogram calculation. Since there is no handler
defined in the TRY control structure for this exception,
the exception is propagated from the subprogram, which is possible via the declaration of the subclass
CX_SY_ARITHMETIC_ERROR with RAISING in the subprogram
interface. Prior to this, the CLEANUP block of the internal TRY control structure is executed.
Further possible exceptions are caught in the last CATCH
block of the TRY control structure of the framework program
which, when you specify the most general exception class CX_ROOT, catches all possible exceptions. If,
for example, CX_SY_ARG_OUT_OF_DOMAIN or one of its superclasses were not declared in the interface of
the subprogram, then exceptions CX_SY_NO_HANDLER would result which would then be caught in the last CATCH block.
PARAMETERS number TYPE i.
DATA: result TYPE p LENGTH 8 DECIMALS 2,
oref TYPE REF TO cx_root,
text TYPE string.
IF ABS( number ) > 100.
RAISE EXCEPTION TYPE cx_demo_abs_too_large.
PERFORM calculation USING number
CATCH cx_sy_arithmetic_error INTO oref.
text = oref->get_text( ).
CATCH cx_root INTO oref.
text = oref->get_text( ).
IF NOT text IS INITIAL.
WRITE / text.
WRITE: / 'Final result:', result.
FORM calculation USING p_number LIKE number
CHANGING p_result LIKE result
p_text LIKE text
DATA l_oref TYPE REF TO cx_root.
p_result = 1 / p_number.
WRITE: / 'Result of division:', p_result.
p_result = SQRT( p_number ).
WRITE: / 'Result of square root:', p_result.
CATCH cx_sy_zerodivide INTO l_oref.
p_text = l_oref->get_text( ).