NAME
error, nexterror, poperror, waserror – error handling functions |
SYNOPSIS
void error(char*) void nexterror(void) void poperror(void)
int waserror(void) |
DESCRIPTION
The kernel handles error conditions using non–local gotos, similar
to setjmp(2), but using a stack of error labels to implement nested
exception handling. This simplifies many of the internal interfaces
by eliminating the need for returning and checking error codes
at every level of the call stack, at the cost of requiring
kernel routines to adhere to a strict discipline.
Each process has in its defining kernel Proc structure a stack
of labels, NERR (currently 64) elements deep. A kernel function
that must perform a clean up or recovery action on an error makes
a stylised call to waserror, nexterror and poperror:
Within the recovery block, after handling an error condition, there must normally be a call to nexterror to transfer control to any error recovery lower down in the stack. The main exception is in the outermost function in a process, which must not call nexterror (there being nothing further on the stack), but calls pexit (see kproc(9)) instead, to terminate the process. When the need to recover a particular resource has passed, a function that has called waserror must remove the corresponding label from the stack by calling poperror. This must be done before returning from the function; otherwise, a subsequent call to error will return to an obsolete activation record, with unpredictable but unpleasant consequences. Error copies the given error message, which is limited to ERRMAX bytes, into the Proc.error of the current process, enables interrupts by calling spllo (native only), and finally calls nexterror to start invoking the recovery procedures currently stacked by waserror. The file /sys/src/9/port/error.h offer a wide selection of predefined error messages, suitable for almost any occasion. The message set by the most recent call to error can be obtained within the kernel by examining up–>error and in an application, by using the %r directive of print(2).
A complex function can have nested error handlers. A waserror
block will follow the acquisition of a resource, releasing it
on error before calling nexterror, and a poperror will precede
its release in the normal case. For example:
|
SOURCE
/sys/src/9/port/proc.c |
CAVEATS
The description above has many instances of should, will, must
and must not. |
SEE ALSO
panic(9) |