Starting with SWI-Prolog 9.3.13, SWI-Prolog introduces a new class of
reserved exceptions. An exception of the shape unwind(Term)
is handled special by catch/3
and friends. Rather than simply calling the
Recover goal (third argument), catch/3
acts as if called as
catch(Goal, Ball, call_cleanup(once(Recover), throw(Ball)))
The above implies that cleanup that may be required on exceptions should use call_cleanup/2 (or one of its variations) or should perform the cleanup in the Recover goal. For example, the following does not properly cleanup after an exception:
( catch(Goal, Error, true) -> ( var(Error) -> <no exception> ; <cleanup> % NOT called on throw(unwind(...)) ...
This implies that, unless the user ensures Recover does not terminate, the exception will unwind the entire Prolog stack. While foreign code that catches these exceptions should propagate them to the parent environment, we cannot enforce this behaviour.
Currently, this mechanism defines these values for Term:
'$aborted'
using the same
unwind semantics.unwind(halt(Status)
)
is raised in the main
thread, this system halts with exit
code
Status