summaryrefslogtreecommitdiffstats
path: root/include/kunit
diff options
context:
space:
mode:
authorDavid Gow <davidgow@google.com>2022-11-25 16:43:05 +0800
committerShuah Khan <skhan@linuxfoundation.org>2022-12-12 14:13:47 -0700
commit91e93592219f74c4d5cd4f27006d726ac86ae15d (patch)
tree085447ad7679587245dfed13d28fd37da9b16d84 /include/kunit
parent908d0c177bbc7c34ab9129c6f2bcd87487115632 (diff)
downloadlinux-91e93592219f74c4d5cd4f27006d726ac86ae15d.tar.bz2
kunit: Use the static key when retrieving the current test
In order to detect if a KUnit test is running, and to access its context, the 'kunit_test' member of the current task_struct is used. Usually, this is accessed directly or via the kunit_fail_current_task() function. In order to speed up the case where no test is running, add a wrapper, kunit_get_current_test(), which uses the static key to fail early. Equally, Speed up kunit_fail_current_test() by using the static key. This should make it convenient for code to call this unconditionally in fakes or error paths, without worrying that this will slow the code down significantly. If CONFIG_KUNIT=n (or m), this compiles away to nothing. If CONFIG_KUNIT=y, it will compile down to a NOP (on most architectures) if no KUnit test is currently running. Note that kunit_get_current_test() does not work if KUnit is built as a module. This mirrors the existing restriction on kunit_fail_current_test(). Note that the definition of kunit_fail_current_test() still wraps an empty, inline function if KUnit is not built-in. This is to ensure that the printf format string __attribute__ will still work. Also update the documentation to suggest users use the new kunit_get_current_test() function, update the example, and to describe the behaviour when KUnit is disabled better. Cc: Jonathan Corbet <corbet@lwn.net> Cc: Sadiya Kazi <sadiyakazi@google.com> Signed-off-by: David Gow <davidgow@google.com> Reviewed-by: Daniel Latypov <dlatypov@google.com> Signed-off-by: Shuah Khan <skhan@linuxfoundation.org>
Diffstat (limited to 'include/kunit')
-rw-r--r--include/kunit/test-bug.h53
1 files changed, 50 insertions, 3 deletions
diff --git a/include/kunit/test-bug.h b/include/kunit/test-bug.h
index 5fc58081d511..c1b2e14eab64 100644
--- a/include/kunit/test-bug.h
+++ b/include/kunit/test-bug.h
@@ -9,16 +9,63 @@
#ifndef _KUNIT_TEST_BUG_H
#define _KUNIT_TEST_BUG_H
-#define kunit_fail_current_test(fmt, ...) \
- __kunit_fail_current_test(__FILE__, __LINE__, fmt, ##__VA_ARGS__)
-
#if IS_BUILTIN(CONFIG_KUNIT)
+#include <linux/jump_label.h> /* For static branch */
+#include <linux/sched.h>
+
+/* Static key if KUnit is running any tests. */
+DECLARE_STATIC_KEY_FALSE(kunit_running);
+
+/**
+ * kunit_get_current_test() - Return a pointer to the currently running
+ * KUnit test.
+ *
+ * If a KUnit test is running in the current task, returns a pointer to its
+ * associated struct kunit. This pointer can then be passed to any KUnit
+ * function or assertion. If no test is running (or a test is running in a
+ * different task), returns NULL.
+ *
+ * This function is safe to call even when KUnit is disabled. If CONFIG_KUNIT
+ * is not enabled, it will compile down to nothing and will return quickly no
+ * test is running.
+ */
+static inline struct kunit *kunit_get_current_test(void)
+{
+ if (!static_branch_unlikely(&kunit_running))
+ return NULL;
+
+ return current->kunit_test;
+}
+
+
+/**
+ * kunit_fail_current_test() - If a KUnit test is running, fail it.
+ *
+ * If a KUnit test is running in the current task, mark that test as failed.
+ *
+ * This macro will only work if KUnit is built-in (though the tests
+ * themselves can be modules). Otherwise, it compiles down to nothing.
+ */
+#define kunit_fail_current_test(fmt, ...) do { \
+ if (static_branch_unlikely(&kunit_running)) { \
+ __kunit_fail_current_test(__FILE__, __LINE__, \
+ fmt, ##__VA_ARGS__); \
+ } \
+ } while (0)
+
+
extern __printf(3, 4) void __kunit_fail_current_test(const char *file, int line,
const char *fmt, ...);
#else
+static inline struct kunit *kunit_get_current_test(void) { return NULL; }
+
+/* We define this with an empty helper function so format string warnings work */
+#define kunit_fail_current_test(fmt, ...) \
+ __kunit_fail_current_test(__FILE__, __LINE__, fmt, ##__VA_ARGS__)
+
static inline __printf(3, 4) void __kunit_fail_current_test(const char *file, int line,
const char *fmt, ...)
{