From 295e7c80e88e7fabad278cf7eacabf5a50d329b3 Mon Sep 17 00:00:00 2001 From: Tony Finch Date: Fri, 3 Mar 2023 12:01:03 +0000 Subject: [PATCH] Ad-hoc backtrace logging with isc_backtrace_log() It's sometimes helpful to get a quick idea of the call stack when debugging. This change factors out the backtrace logging from named's fatal error handler so that it's easy to use in other places too. --- bin/named/main.c | 30 ++++-------------------------- lib/isc/assertions.c | 4 ++-- lib/isc/backtrace.c | 30 ++++++++++++++++++++++++++++++ lib/isc/include/isc/backtrace.h | 14 ++++++++++++++ 4 files changed, 50 insertions(+), 28 deletions(-) diff --git a/bin/named/main.c b/bin/named/main.c index 752745d7fe..9ae8832a40 100644 --- a/bin/named/main.c +++ b/bin/named/main.c @@ -101,13 +101,6 @@ */ /* #include "xxdb.h" */ -/* - * The maximum number of stack frames to dump on assertion failure. - */ -#ifndef BACKTRACE_MAXFRAME -#define BACKTRACE_MAXFRAME 128 -#endif /* ifndef BACKTRACE_MAXFRAME */ - extern unsigned int dns_zone_mkey_hour; extern unsigned int dns_zone_mkey_day; extern unsigned int dns_zone_mkey_month; @@ -189,9 +182,6 @@ assertion_failed(const char *file, int line, isc_assertiontype_t type, static void assertion_failed(const char *file, int line, isc_assertiontype_t type, const char *cond) { - void *tracebuf[BACKTRACE_MAXFRAME]; - int nframes; - /* * Handle assertion failures. */ @@ -203,24 +193,12 @@ assertion_failed(const char *file, int line, isc_assertiontype_t type, */ isc_assertion_setcallback(NULL); - nframes = isc_backtrace(tracebuf, BACKTRACE_MAXFRAME); isc_log_write(named_g_lctx, NAMED_LOGCATEGORY_GENERAL, NAMED_LOGMODULE_MAIN, ISC_LOG_CRITICAL, - "%s:%d: %s(%s) failed%s", file, line, - isc_assertion_typetotext(type), cond, - (nframes > 0) ? ", back trace" : ""); - if (nframes > 0) { - char **strs = isc_backtrace_symbols(tracebuf, nframes); - if (strs != NULL) { - for (int i = 0; i < nframes; i++) { - isc_log_write(named_g_lctx, - NAMED_LOGCATEGORY_GENERAL, - NAMED_LOGMODULE_MAIN, - ISC_LOG_CRITICAL, "%s", - strs[i]); - } - } - } + "%s:%d: %s(%s) failed", file, line, + isc_assertion_typetotext(type), cond); + isc_backtrace_log(named_g_lctx, NAMED_LOGCATEGORY_GENERAL, + NAMED_LOGMODULE_MAIN, ISC_LOG_CRITICAL); isc_log_write(named_g_lctx, NAMED_LOGCATEGORY_GENERAL, NAMED_LOGMODULE_MAIN, ISC_LOG_CRITICAL, "exiting (due to assertion failure)"); diff --git a/lib/isc/assertions.c b/lib/isc/assertions.c index a5cc0a2ac8..3dfccdcb07 100644 --- a/lib/isc/assertions.c +++ b/lib/isc/assertions.c @@ -95,8 +95,8 @@ isc_assertion_typetotext(isc_assertiontype_t type) { static void default_callback(const char *file, int line, isc_assertiontype_t type, const char *cond) { - void *tracebuf[BACKTRACE_MAXFRAME]; - int nframes = isc_backtrace(tracebuf, BACKTRACE_MAXFRAME); + void *tracebuf[ISC_BACKTRACE_MAXFRAME]; + int nframes = isc_backtrace(tracebuf, ISC_BACKTRACE_MAXFRAME); fprintf(stderr, "%s:%d: %s(%s) failed%s\n", file, line, isc_assertion_typetotext(type), cond, diff --git a/lib/isc/backtrace.c b/lib/isc/backtrace.c index fc15acf3eb..23369417fc 100644 --- a/lib/isc/backtrace.c +++ b/lib/isc/backtrace.c @@ -20,6 +20,7 @@ #endif /* HAVE_BACKTRACE_SYMBOLS */ #include +#include #include #include @@ -60,6 +61,26 @@ isc_backtrace_symbols_fd(void *const *buffer, int size, int fd) { backtrace_symbols_fd(buffer, size, fd); } +void +isc_backtrace_log(isc_log_t *lctx, isc_logcategory_t *category, + isc_logmodule_t *module, int level) { + void *tracebuf[ISC_BACKTRACE_MAXFRAME]; + int nframes; + char **strs; + + nframes = isc_backtrace(tracebuf, ISC_BACKTRACE_MAXFRAME); + if (nframes <= 0) { + return; + } + strs = isc_backtrace_symbols(tracebuf, nframes); + if (strs == NULL) { + return; + } + for (int i = 0; i < nframes; i++) { + isc_log_write(lctx, category, module, level, "%s", strs[i]); + } +} + #else /* HAVE_BACKTRACE_SYMBOLS */ int @@ -85,4 +106,13 @@ isc_backtrace_symbols_fd(void *const *buffer, int size, int fd) { UNUSED(fd); } +void +isc_backtrace_log(isc_log_t *lctx, isc_logcategory_t *category, + isc_logmodule_t *module, int level) { + UNUSED(lctx); + UNUSED(category); + UNUSED(module); + UNUSED(level); +} + #endif /* HAVE_BACKTRACE_SYMBOLS */ diff --git a/lib/isc/include/isc/backtrace.h b/lib/isc/include/isc/backtrace.h index f818c3b54a..c8fa3242b0 100644 --- a/lib/isc/include/isc/backtrace.h +++ b/lib/isc/include/isc/backtrace.h @@ -34,6 +34,13 @@ ***/ #include +/* + * The maximum number of stack frames to dump on assertion failure. + */ +#ifndef ISC_BACKTRACE_MAXFRAME +#define ISC_BACKTRACE_MAXFRAME 128 +#endif /* ifndef ISC_BACKTRACE_MAXFRAME */ + /*** *** Functions ***/ @@ -98,4 +105,11 @@ isc_backtrace_symbols_fd(void *const *buffer, int size, int fd); *\li See platform NOTES for backtrace_symbols_fd for caveats */ +void +isc_backtrace_log(isc_log_t *lctx, isc_logcategory_t *category, + isc_logmodule_t *module, int level); +/* + * Write a backtrace to the log. + */ + ISC_LANG_ENDDECLS