Next: restarts ignore-errors, Previous: restarts signal, Up: restarts [Index]
Evaluate body forms in a dynamic environment in which new exception
handlers are installed; it is capable of handling exceptions raised with
raise, raise-continuable and signal. Basically
behave like R6RS’s guard syntax.
The arguments ?clause must have one of the following syntaxes:
(?typespec ?condition-handler) (:no-error ?no-error-handler)
Every ?typespec is meant to be a logic predicate with the format:
?typespec = (?tag)
| (and ?inner-pred0 ?inner-pred ...)
| (or ?inner-pred0 ?inner-pred ...)
| (xor ?inner-pred0 ?inner-pred ...)
| (not ?inner-pred)
?inner-pred = ?tag
| (and ?inner-pred0 ?inner-pred ...)
| (or ?inner-pred0 ?inner-pred ...)
| (xor ?inner-pred0 ?inner-pred ...)
| (not ?inner-pred)
where: each ?tag is an identifier usable as second argument to
is-a?; and, or, xor, not
are the identifiers exported by (vicare).
Every ?condition-handler must be an expression evaluating to a procedure accepting a condition object as single argument; the condition object can be simple or compound.
In the no–error clause: :no-error must be the actual symbol;
?no-error-handler must be an expression evaluating to a procedure.
The optional :no-error clause can be present only if it is the
last one.
If the body performs a normal return:
:no-error clause is missing: the values returned by the
body become the values returned by handler-case.
:no-error clause is present: the procedure
?no-error-handler is applied to the returned values; the return
values of such application become the return values of
handler-case.
If an exception is raised (in Common Lisp jargon: a condition is signalled): a condition handler matching the raised object is searched in the sequence of clauses, left–to–right:
handler-case.
raise-continuable.
Usage examples:
(import (vicare)
(only (vicare checks)
with-result
add-result))
;;no condition
(with-result
(handler-case
((&error (lambda (E)
(add-result 'error-handler)
1))
(&warning (lambda (E)
(add-result 'warning-handler)
2)))
(add-result 'body)
1))
⇒ (1 (body))
;;no condition, :no-error clause
(with-result
(handler-case
((&error (lambda (E)
(add-result 'error-handler)
1))
(&warning (lambda (E)
(add-result 'warning-handler)
2))
(:no-error (lambda (X)
(add-result 'no-error)
(* 10 X))))
(add-result 'body)
1))
⇒ (10 (body no-error))
;;;
(internal-body ;signalled condition
(define (doit C)
(with-result
(handler-case
((&error (lambda (E)
(add-result 'error-handler)
1))
(&warning (lambda (E)
(add-result 'warning-handler)
2)))
(add-result 'body-begin)
(signal C)
(add-result 'body-normal-return))))
(doit (make-error))
⇒ (1 (body-begin error-handler))
(doit (make-warning))
⇒ (2 (body-begin warning-handler))
#| end of body |# )
;;Signalled condition, multiple types in single clause.
;;
(internal-body
(define (doit C)
(with-result
(handler-case
(((&error &warning) (lambda (E)
(add-result 'handler)
1)))
(add-result 'body-begin)
(signal C)
(add-result 'body-normal-return))))
(doit (make-error))
⇒ (1 (body-begin handler))
(doit (make-warning))
⇒ (1 (body-begin handler))
#| end of body |# )
;;Signalled condition, nested HANDLER-CASE uses.
;;
(internal-body
(define (doit C)
(with-result
(handler-case
((&error (lambda (E)
(add-result 'error-handler)
1)))
(handler-case
((&warning (lambda (E)
(add-result 'warning-handler)
2)))
(add-result 'body-begin)
(signal C)
(add-result 'body-normal-return)))))
(doit (make-error))
⇒ (1 (body-begin error-handler))
(doit (make-warning))
⇒ (2 (body-begin warning-handler))
#| end of body |# )
(internal-body ; unwind-protect
(define (doit C)
(with-result
(handler-case
((&error (lambda (E)
(add-result 'error-handler)
1)))
(with-unwind-handler
(lambda (why)
(add-result 'outer-unwind-handler))
(lambda ()
(handler-case
((&warning (lambda (E)
(add-result 'warning-handler)
2)))
(with-unwind-handler
(lambda (why)
(add-result 'inner-unwind-handler))
(lambda ()
(add-result 'body-begin)
(signal C)
(add-result 'body-normal-return)))))))))
(doit (make-error))
⇒ (1
(body-begin
inner-unwind-handler
outer-unwind-handler
error-handler))
(doit (make-warning))
⇒ (2
(body-begin
inner-unwind-handler
warning-handler
outer-unwind-handler))
#| end of body |# )
Next: restarts ignore-errors, Previous: restarts signal, Up: restarts [Index]