X-Git-Url: http://repo.macrolet.net/gitweb/?a=blobdiff_plain;f=src%2Fruntime%2Finterr.c;h=2187fd838ea477e503756b962572fa668102f30d;hb=0285aa5ff8416027932daa001b84429be2ca559b;hp=64eacea46ad58edf51c67feb12d240aa1795d685;hpb=92c8db80e039f60623e53a0b9355cf0a9ec49f3d;p=sbcl.git diff --git a/src/runtime/interr.c b/src/runtime/interr.c index 64eacea..2187fd8 100644 --- a/src/runtime/interr.c +++ b/src/runtime/interr.c @@ -28,6 +28,7 @@ #include "genesis/static-symbols.h" #include "genesis/vector.h" #include "thread.h" +#include "monitor.h" /* the way that we shut down the system on a fatal error */ @@ -37,33 +38,86 @@ default_lossage_handler(void) exit(1); } static void (*lossage_handler)(void) = default_lossage_handler; -void -set_lossage_handler(void handler(void)) + +void enable_lossage_handler(void) +{ + lossage_handler = monitor_or_something; +} +void disable_lossage_handler(void) { - lossage_handler = handler; + lossage_handler = default_lossage_handler; } -never_returns -lose(char *fmt, ...) +static +void print_message(char *fmt, va_list ap) { - va_list ap; - fprintf(stderr, "fatal error encountered in SBCL pid %d",getpid()); + fprintf(stderr, " in SBCL pid %d",getpid()); #if defined(LISP_FEATURE_SB_THREAD) - fprintf(stderr, "(tid %lu)",thread_self()); + fprintf(stderr, "(tid %lu)", (unsigned long) thread_self()); #endif if (fmt) { fprintf(stderr, ":\n"); - va_start(ap, fmt); vfprintf(stderr, fmt, ap); - va_end(ap); } fprintf(stderr, "\n"); - fflush(stderr); +} + +static inline void +call_lossage_handler() never_returns; + +static inline void +call_lossage_handler() +{ lossage_handler(); fprintf(stderr, "Argh! lossage_handler() returned, total confusion..\n"); exit(1); } + +void +lose(char *fmt, ...) +{ + va_list ap; + /* Block signals to prevent other threads, timers and such from + * interfering. If only all threads could be stopped somehow. */ + block_blockable_signals(0, 0); + fprintf(stderr, "fatal error encountered"); + va_start(ap, fmt); + print_message(fmt, ap); + va_end(ap); + fprintf(stderr, "\n"); + fflush(stderr); + call_lossage_handler(); +} + +boolean lose_on_corruption_p = 0; + +void +corruption_warning_and_maybe_lose(char *fmt, ...) +{ + va_list ap; +#ifndef LISP_FEATURE_WIN32 + sigset_t oldset; + block_blockable_signals(0, &oldset); +#endif + fprintf(stderr, "CORRUPTION WARNING"); + va_start(ap, fmt); + print_message(fmt, ap); + va_end(ap); + fprintf(stderr, "The integrity of this image is possibly compromised.\n"); + if (lose_on_corruption_p) + fprintf(stderr, "Exiting.\n"); + else + fprintf(stderr, "Continuing with fingers crossed.\n"); + fflush(stderr); + if (lose_on_corruption_p) + call_lossage_handler(); +#ifndef LISP_FEATURE_WIN32 + else + thread_sigmask(SIG_SETMASK,&oldset,0); +#endif +} +char *internal_error_descriptions[] = {INTERNAL_ERROR_NAMES}; /* internal error handler for when the Lisp error system doesn't exist * * FIXME: Shouldn't error output go to stderr instead of stdout? (Alas, @@ -76,7 +130,9 @@ describe_internal_error(os_context_t *context) int len, scoffset, sc, offset, ch; len = *ptr++; - printf("internal error #%d\n", *ptr++); + printf("internal error #%d (%s)\n", *ptr, + internal_error_descriptions[*ptr]); + ptr++; len--; while (len > 0) { scoffset = *ptr++; @@ -172,6 +228,6 @@ lispobj debug_print(lispobj string) fprintf(stderr, "%s\n", (char *)(((struct vector *)native_pointer(string))->data)); /* shut GCC up about not using this, because that's the point.. */ - if (untouched); + (void)untouched; return NIL; }