The point of critical regions in your code is that sometimes you have data-base updates or other operations that, once started, must be completed in order to avoid an inconsistent state. In particular, such operations should not be interrupted by a ^C from the keyboard.
In releases of Quintus Prolog prior to release 3.0,
provided to allow critical regions to be specified using the predicates
end_critical/0. These predicates are still
provided, but they should be regarded as obsolete since they do not interact
well with exception handling. An exception occurring in between the
begin_critical and the
end_critical could cause two problems:
To avoid these problems, you should use the new predicates
critical(Goal) critical_on_exception(ErrorCode, Goal, Handler)
library(critical) now provides.
critical/1 runs the specified goal inside a critical region. It
solves (2) by catching any exceptions that are
raised and taking care to close the critical region before re-raising the
critical_on_exception/3 allows you to solve
(1) by specifying appropriate clean-up actions in
If an exception occurs during Goal, and the exception code unifies with
critical_on_exception/3 acts as if you had
instead. That is, the Handler will still be inside the critical region, and only the first solution it returns will be taken.
These forms also have the effect of committing to the first solution of Goal. Since the point of a critical region is to ensure that some operation with side-effects is completed, Goal should be determinate anyway, so this should be no problem.