From: Philippe Proulx Date: Wed, 26 Jun 2019 18:39:42 +0000 (-0400) Subject: Do not require logging support for BT_[CTF_]ASSERT_PRE() X-Git-Url: http://git.efficios.com/?p=babeltrace.git;a=commitdiff_plain;h=34ae0d6283e68bfecdcc80f56ff174bb2f49c7fa Do not require logging support for BT_[CTF_]ASSERT_PRE() This patch makes the BT_ASSERT_PRE(), BT_ASSERT_PRE_MSG(), BT_CTF_ASSERT_PRE(), and BT_CTF_ASSERT_PRE_MSG() not use BT_LIB_LOGF() and BT_LOGF() directly to not rely on the active log level to print the messages. This makes it possible to configure the build with `BABELTRACE_DEV_MODE=1` and `BABELTRACE_MINIMAL_LOG_LEVEL=NONE` and still get the precondition failure messages. This removes some code in `configure.ac` and `src/lib/logging.c` which ensured that the log level could not be NONE when developer mode is enabled. The macros now use _bt_log_write_d() (which does not check the active log level) and bt_lib_log() (which uses _bt_log_write_d() without checking the active log level) instead of BT_LOGF() and BT_LIB_LOGF(). The `assert-pre.h` header still require that you include `"lib/logging.h"` or `"logging/log.h"` before because this is where the logging tag and logging functions are found. Signed-off-by: Philippe Proulx Change-Id: If98a1c074d211cf257742d55960b379bbe9c6cf0 Reviewed-on: https://review.lttng.org/c/babeltrace/+/1546 Tested-by: jenkins --- diff --git a/configure.ac b/configure.ac index c265be67..b88bcbb7 100644 --- a/configure.ac +++ b/configure.ac @@ -402,9 +402,6 @@ AC_DEFINE_UNQUOTED([BT_LOG_LEVEL], [BT_LOG_$BABELTRACE_MINIMAL_LOG_LEVEL], [Mini # BABELTRACE_DEV_MODE: AC_ARG_VAR([BABELTRACE_DEV_MODE], [Set to 1 to enable the Babeltrace developer mode (enables run-time checks for plugin developers)]) AS_IF([test "x$BABELTRACE_DEV_MODE" = x1], [ - AS_IF([test "x$BABELTRACE_MINIMAL_LOG_LEVEL" = "xNONE"], [ - AC_MSG_ERROR([Babeltrace developer mode (\$BABELTRACE_DEV_MODE) needs \$BABELTRACE_MINIMAL_LOG_LEVEL to be at least FATAL.]) - ]) AC_DEFINE([BT_DEV_MODE], 1, [Babeltrace developer mode]) ], [BABELTRACE_DEV_MODE=0]) diff --git a/src/ctf-writer/assert-pre.h b/src/ctf-writer/assert-pre.h index 5444760d..c0a24614 100644 --- a/src/ctf-writer/assert-pre.h +++ b/src/ctf-writer/assert-pre.h @@ -44,6 +44,40 @@ #include "common/macros.h" #ifdef BT_DEV_MODE +/* + * Prints the details of an unsatisfied precondition without immediately + * aborting. You should use this within a function which checks + * preconditions, but which is called from a BT_CTF_ASSERT_PRE() + * context, so that the function can still return its result for + * BT_CTF_ASSERT_PRE() to evaluate it. + * + * Example: + * + * BT_CTF_ASSERT_PRE_FUNC + * static inline bool check_complex_precond(...) + * { + * ... + * + * if (...) { + * BT_CTF_ASSERT_PRE_MSG("Invalid object: ...", ...); + * return false; + * } + * + * ... + * } + * + * ... + * + * BT_CTF_ASSERT_PRE(check_complex_precond(...), + * "Precondition is not satisfied: ...", ...); + */ +# define BT_CTF_ASSERT_PRE_MSG(_fmt, ...) \ + do { \ + _bt_log_write_d(_BT_LOG_SRCLOC_FUNCTION, __FILE__, \ + __LINE__, BT_LOG_FATAL, BT_LOG_TAG, (_fmt), \ + ##__VA_ARGS__); \ + } while (0) + /* * Asserts that the library precondition _cond is satisfied. * @@ -56,9 +90,9 @@ # define BT_CTF_ASSERT_PRE(_cond, _fmt, ...) \ do { \ if (!(_cond)) { \ - BT_LOGF_STR("Library precondition not satisfied; error is:"); \ - BT_LOGF((_fmt), ##__VA_ARGS__); \ - BT_LOGF_STR("Aborting..."); \ + BT_CTF_ASSERT_PRE_MSG("CTF writer precondition not satisfied; error is:"); \ + BT_CTF_ASSERT_PRE_MSG((_fmt), ##__VA_ARGS__); \ + BT_CTF_ASSERT_PRE_MSG("Aborting..."); \ abort(); \ } \ } while (0) @@ -95,7 +129,6 @@ * BT_CTF_ASSERT_PRE(check_complex_precond(...), * "Precondition is not satisfied: ...", ...); */ -# define BT_CTF_ASSERT_PRE_MSG BT_LOGF #else # define BT_CTF_ASSERT_PRE(_cond, _fmt, ...) ((void) sizeof((void) (_cond), 0)) # define BT_CTF_ASSERT_PRE_FUNC __attribute__((unused)) diff --git a/src/lib/assert-pre.h b/src/lib/assert-pre.h index 1f4240eb..48fe9598 100644 --- a/src/lib/assert-pre.h +++ b/src/lib/assert-pre.h @@ -44,30 +44,6 @@ #include "common/macros.h" #ifdef BT_DEV_MODE -/* - * Asserts that the library precondition _cond is satisfied. - * - * If _cond is false, log a fatal statement using _fmt and the optional - * arguments using BT_LIB_LOGF(), and abort. - * - * To assert that a postcondition is satisfied or that some internal - * object/context/value is in the expected state, use BT_ASSERT(). - */ -# define BT_ASSERT_PRE(_cond, _fmt, ...) \ - do { \ - if (!(_cond)) { \ - BT_LOGF_STR("Library precondition not satisfied; error is:"); \ - BT_LIB_LOGF((_fmt), ##__VA_ARGS__); \ - BT_LOGF_STR("Aborting..."); \ - abort(); \ - } \ - } while (0) - -/* - * Marks a function as being only used within a BT_ASSERT_PRE() context. - */ -# define BT_ASSERT_PRE_FUNC - /* * Prints the details of an unsatisfied precondition without immediately * aborting. You should use this within a function which checks @@ -95,7 +71,36 @@ * BT_ASSERT_PRE(check_complex_precond(...), * "Precondition is not satisfied: ...", ...); */ -# define BT_ASSERT_PRE_MSG BT_LIB_LOGF +# define BT_ASSERT_PRE_MSG(_fmt, ...) \ + do { \ + bt_lib_log(_BT_LOG_SRCLOC_FUNCTION, __FILE__, \ + __LINE__, BT_LOG_FATAL, BT_LOG_TAG, \ + (_fmt), ##__VA_ARGS__); \ + } while (0) + +/* + * Asserts that the library precondition _cond is satisfied. + * + * If `_cond` is false, log a fatal statement using `_fmt` and the + * optional arguments (same usage as BT_LIB_LOGF()), and abort. + * + * To assert that a postcondition is satisfied or that some internal + * object/context/value is in the expected state, use BT_ASSERT(). + */ +# define BT_ASSERT_PRE(_cond, _fmt, ...) \ + do { \ + if (!(_cond)) { \ + BT_ASSERT_PRE_MSG("Babeltrace 2 library precondition not satisfied; error is:"); \ + BT_ASSERT_PRE_MSG((_fmt), ##__VA_ARGS__); \ + BT_ASSERT_PRE_MSG("Aborting..."); \ + abort(); \ + } \ + } while (0) + +/* + * Marks a function as being only used within a BT_ASSERT_PRE() context. + */ +# define BT_ASSERT_PRE_FUNC #else # define BT_ASSERT_PRE(_cond, _fmt, ...) ((void) sizeof((void) (_cond), 0)) # define BT_ASSERT_PRE_FUNC __attribute__((unused)) diff --git a/src/lib/logging.c b/src/lib/logging.c index 8f3160b5..64bd8ca9 100644 --- a/src/lib/logging.c +++ b/src/lib/logging.c @@ -27,30 +27,19 @@ #define BT_LOG_TAG "LIB/LOGGING" #include "lib/logging.h" -#ifdef BT_DEV_MODE -/* - * Default log level is FATAL in developer mode because fatal logging is - * our way to communicate an unsatisfied precondition and the details. - */ -# define DEFAULT_LOG_LEVEL BT_LOG_FATAL -#else -/* - * In non-developer mode, use NONE by default: we don't print logging - * statements for any executable which links with the library. The - * executable must call bt_logging_set_global_level() or the - * executable's user must set the `LIBBABELTRACE2_INIT_LOG_LEVEL` - * environment variable to enable logging. - */ -# define DEFAULT_LOG_LEVEL BT_LOG_NONE -#endif /* BT_DEV_MODE */ - /* * This is exported because even though the Python plugin provider is a * different shared object for packaging purposes, it's still considered * part of the library and therefore needs the library's run-time log * level. + * + * The default log level is NONE: we don't print logging statements for + * any executable which links with the library. The executable must call + * bt_logging_set_global_level() or the executable's user must set the + * `LIBBABELTRACE2_INIT_LOG_LEVEL` environment variable to enable + * logging. */ -int bt_lib_log_level = DEFAULT_LOG_LEVEL; +int bt_lib_log_level = BT_LOG_NONE; enum bt_logging_level bt_logging_get_minimal_level(void) { @@ -64,17 +53,6 @@ enum bt_logging_level bt_logging_get_global_level(void) void bt_logging_set_global_level(enum bt_logging_level log_level) { -#ifdef BT_DEV_MODE - /* - * Do not allow the library's log level to fall to NONE when in - * developer mode because fatal logging is our way to - * communicate an unsatisfied precondition and the details. - */ - if (log_level == BT_LOG_NONE) { - log_level = BT_LOG_FATAL; - } -#endif - bt_lib_log_level = log_level; }