Museum

Home

Lab Overview

Retrotechnology Articles

Online Manuals

⇒ __exc_last_chance(3) — Tru64 UNIX 5.1b

Media Vault

Software Library

Restoration Projects

Artifacts Sought

Related Articles

exception_intro(3)

exc_lookup_function_entry(3)

signal(2)

sigaction(2)

setjmp(3)

exc_unwind(3)

exception_dispatcher(3)

ieee(3)

excpt(4)

c_excpt(4)

signal(4)

pdsc(4)

set_unhandled_exception(3)  —  Subroutines

NAME

set_unhandled_exception, __exc_last_chance, exc_set_last_chance_handler − support routines for unhandled exceptions

SYNOPSIS

#include <excpt.h>
void set_unhandled_exception(
        exception_handler_type handler ); static void __exc_last_chance(
        system_exrec_type ∗exceptionRecord,
        void ∗EstablisherFrame,
        CONTEXT ∗contextRecord,
        DISPATCHER_CONTEXT ∗dispatcherContext ); void exc_set_last_chance_handler(
        exception_handler_type last_chance );

LIBRARY

Exception Handling Library (libexc.a)

PARAMETERS

handler
Address of last chance handler.

exceptionRecord
Address of primary exception record.

EstablisherFrame
Virtual frame pointer of handler’s establisher.

contextRecord
Pointer to a struct sigcontext (see signal(2)) used to represent a procedure’s context. 

dispatcherContext
Address of exception dispatcher’s control record.

last_chance
Address of last chance handler.

DESCRIPTION

When called as the result of an exception, exc_dispatch_exception(3) attempts to find a handler to process the exception by searching the stack frames of procedures in the call chain. It does this by virtually unwinding the stack (see unwind(3)). The exc_dispatch_exception() routine invokes a handler, if one exists, for each procedure in the call chain until it finds one that handles the exception. If no handler handles the exception, the dispatcher returns to its caller (for instance, exc_raise_exception(3)).  The caller typically calls exc_unwind() to perform an exit unwind. 

During an exit unwind, existing handlers for procedures in the call chain are invoked with notification that unwinding is in progress, thus allowing handlers to perform scope cleanup. Once the stack has been unwound and all frames for procedures in the call chain have been removed from the stack, __exc_last_chance() is called. It calls a user specified handler, if present, or prints a message using stdio and calls exit(2) with an argument of 1. 

You can establish a last chance handler by calling either set_unhandled_exception() or exc_set_last_chance_handler() specifying a nonzero value as a handler. There is only one last chance handler per process and it is inherited over forks. 

The type exception_handler_type is defined in excpt.h and matches the prototype for __exc_last_chance. 

EXAMPLES

In the following example, exc_set_unhandled_exception() installs my_lastchance as the last chance handler. Because the exception_dispatcher is installed as the signal handler for SIGSEGV signals, the dispatcher begins searching for a frame-based handler, when the segmentation violation occurs, by virtually unwinding the context of the current and previous procedure call frames. When it determines that no frame-based handler exists for this exception, the dispatcher performs an exit unwind of the procedure call stack (see exc_resume(3)). Eventually the last-chance handler, my_last_chance, executes. 

/∗
 ∗ cc -call_shared -o lastchance lastchance.c -lexc
 ∗/
#include <stdio.h>
#include <signal.h>
#include <excpt.h>
int     ∗x = 0;
EXCEPTION_DISPOSITION
my_lastchance (
        system_exrec_type ∗exceptionRecord,
        void ∗establisherFrame,
        CONTEXT ∗contextRecord,
        DISPATCHER_CONTEXT ∗dispatcherContext)
    {
    printf ("Handler: executing...\n");
    printf ("The signal code is 0x%0lx\n", exceptionRecord->ExceptionCode);
    printf ("The exception PC is 0x%0lx\n", contextRecord->sc_pc);
    printf ("Exception Masks: ");
    /∗ Print option mask values ∗/
    if (exceptionRecord->ExceptionFlags & EXCEPTION_NONCONTINUABLE)
        printf ("NONCONTINUABLE ");
    if (exceptionRecord->ExceptionFlags & EXCEPTION_UNWINDING)
        printf ("UNWINDING ");
    if (exceptionRecord->ExceptionFlags & EXCEPTION_EXIT_UNWIND)
        printf ("EXIT_UNWIND ");
    if (exceptionRecord->ExceptionFlags & EXCEPTION_STACK_INVALID)
        printf ("STACK_INVALID ");
    if (exceptionRecord->ExceptionFlags & EXCEPTION_NESTED_CALL)
        printf ("NESTED_CALL ");
    if (exceptionRecord->ExceptionFlags & EXCEPTION_TARGET_UNWIND)
        printf ("TARGET_UNWIND ");
    if (exceptionRecord->ExceptionFlags & EXCEPTION_COLLIDED_UNWIND)
        printf ("COLLIDED_UNWIND ");
        printf ("\n");
    exit (0);
    }
/∗
 ∗
 ∗/
int
main ()
    {
    struct sigaction action;
    action.sa_handler = exception_dispatcher;
    action.sa_mask = 0;
    action.sa_options = 0;
    /∗
     ∗ Request frame based exception dispatcher
     ∗ to be invoked on a signal.
     ∗/
    if (sigaction (SIGSEGV, &action, NULL) == -1) {
        perror ("sigaction");
        exit (1);
        }
    /∗ establish last-chance handler ∗/
    set_unhandled_exception (my_lastchance);
    ∗x = 55;    /∗ Let’s SEGV now! ∗/
    return 0;
    }

FILES

/usr/ccs/lib/cmplrs/cc/libexc.a −− exception handling library
/usr/include/excpt.h −− include file
/usr/include/pdsc.h −− include file
/usr/include/signal.h −− include file
/usr/include/machine/fpu.h −− include file

SEE ALSO

Functions: exception_intro(3), exc_lookup_function_entry(3), signal(2), sigaction(2), setjmp(3), exc_unwind(3), exception_dispatcher(3), ieee(3)

Files: excpt(4), c_excpt(4), signal(4), pdsc(4)

Assembly Language Programmer’s Guide

Calling Standard for Alpha Systems

Typewritten Software • bear@typewritten.org • Edmonds, WA 98026