[PATCH] kunit: debugfs: Handle errors from alloc_string_stream()

2023-09-27 Thread Richard Fitzgerald
In kunit_debugfs_create_suite() give up and skip creating the debugfs
file if any of the alloc_string_stream() calls return an error or NULL.
Only put a value in the log pointer of kunit_suite and kunit_test if it
is a valid pointer to a log.

This prevents the potential invalid dereference reported by smatch:

 lib/kunit/debugfs.c:115 kunit_debugfs_create_suite() error: 'suite->log'
dereferencing possible ERR_PTR()
 lib/kunit/debugfs.c:119 kunit_debugfs_create_suite() error: 'test_case->log'
dereferencing possible ERR_PTR()

Signed-off-by: Richard Fitzgerald 
Reported-by: Dan Carpenter 
Fixes: 05e2006ce493 ("kunit: Use string_stream for test log")
---
 lib/kunit/debugfs.c | 29 -
 1 file changed, 24 insertions(+), 5 deletions(-)

diff --git a/lib/kunit/debugfs.c b/lib/kunit/debugfs.c
index 270d185737e6..73075ca6e88c 100644
--- a/lib/kunit/debugfs.c
+++ b/lib/kunit/debugfs.c
@@ -109,14 +109,27 @@ static const struct file_operations debugfs_results_fops 
= {
 void kunit_debugfs_create_suite(struct kunit_suite *suite)
 {
struct kunit_case *test_case;
+   struct string_stream *stream;
 
-   /* Allocate logs before creating debugfs representation. */
-   suite->log = alloc_string_stream(GFP_KERNEL);
-   string_stream_set_append_newlines(suite->log, true);
+   /*
+* Allocate logs before creating debugfs representation.
+* The log pointer must be NULL if there isn't a log so only
+* set it if the log stream was created successfully.
+*/
+   stream = alloc_string_stream(GFP_KERNEL);
+   if (IS_ERR_OR_NULL(stream))
+   goto err;
+
+   string_stream_set_append_newlines(stream, true);
+   suite->log = stream;
 
kunit_suite_for_each_test_case(suite, test_case) {
-   test_case->log = alloc_string_stream(GFP_KERNEL);
-   string_stream_set_append_newlines(test_case->log, true);
+   stream = alloc_string_stream(GFP_KERNEL);
+   if (IS_ERR_OR_NULL(stream))
+   goto err;
+
+   string_stream_set_append_newlines(stream, true);
+   test_case->log = stream;
}
 
suite->debugfs = debugfs_create_dir(suite->name, debugfs_rootdir);
@@ -124,6 +137,12 @@ void kunit_debugfs_create_suite(struct kunit_suite *suite)
debugfs_create_file(KUNIT_DEBUGFS_RESULTS, S_IFREG | 0444,
suite->debugfs,
suite, &debugfs_results_fops);
+   return;
+
+err:
+   string_stream_destroy(suite->log);
+   kunit_suite_for_each_test_case(suite, test_case)
+   string_stream_destroy(test_case->log);
 }
 
 void kunit_debugfs_destroy_suite(struct kunit_suite *suite)
-- 
2.30.2



Re: [PATCH] kunit: debugfs: Handle errors from alloc_string_stream()

2023-09-28 Thread Richard Fitzgerald

On 27/09/2023 17:50, Richard Fitzgerald wrote:

In kunit_debugfs_create_suite() give up and skip creating the debugfs
file if any of the alloc_string_stream() calls return an error or NULL.
Only put a value in the log pointer of kunit_suite and kunit_test if it
is a valid pointer to a log.

This prevents the potential invalid dereference reported by smatch:

  lib/kunit/debugfs.c:115 kunit_debugfs_create_suite() error: 'suite->log'
dereferencing possible ERR_PTR()
  lib/kunit/debugfs.c:119 kunit_debugfs_create_suite() error: 'test_case->log'
dereferencing possible ERR_PTR()

Signed-off-by: Richard Fitzgerald 
Reported-by: Dan Carpenter 
Fixes: 05e2006ce493 ("kunit: Use string_stream for test log")
---
  lib/kunit/debugfs.c | 29 -
  1 file changed, 24 insertions(+), 5 deletions(-)

diff --git a/lib/kunit/debugfs.c b/lib/kunit/debugfs.c
index 270d185737e6..73075ca6e88c 100644
--- a/lib/kunit/debugfs.c
+++ b/lib/kunit/debugfs.c
@@ -109,14 +109,27 @@ static const struct file_operations debugfs_results_fops 
= {
  void kunit_debugfs_create_suite(struct kunit_suite *suite)
  {
struct kunit_case *test_case;
+   struct string_stream *stream;
  
-	/* Allocate logs before creating debugfs representation. */

-   suite->log = alloc_string_stream(GFP_KERNEL);
-   string_stream_set_append_newlines(suite->log, true);
+   /*
+* Allocate logs before creating debugfs representation.
+* The log pointer must be NULL if there isn't a log so only
+* set it if the log stream was created successfully.
+*/
+   stream = alloc_string_stream(GFP_KERNEL);
+   if (IS_ERR_OR_NULL(stream))
+   goto err;


This can be a return. Nothing has been created at this point so
there is nothing to clean up.
I'll send a V2.


+
+   string_stream_set_append_newlines(stream, true);
+   suite->log = stream;
  
  	kunit_suite_for_each_test_case(suite, test_case) {

-   test_case->log = alloc_string_stream(GFP_KERNEL);
-   string_stream_set_append_newlines(test_case->log, true);
+   stream = alloc_string_stream(GFP_KERNEL);
+   if (IS_ERR_OR_NULL(stream))
+   goto err;
+
+   string_stream_set_append_newlines(stream, true);
+   test_case->log = stream;
}
  
  	suite->debugfs = debugfs_create_dir(suite->name, debugfs_rootdir);

@@ -124,6 +137,12 @@ void kunit_debugfs_create_suite(struct kunit_suite *suite)
debugfs_create_file(KUNIT_DEBUGFS_RESULTS, S_IFREG | 0444,
suite->debugfs,
suite, &debugfs_results_fops);
+   return;
+
+err:
+   string_stream_destroy(suite->log);
+   kunit_suite_for_each_test_case(suite, test_case)
+   string_stream_destroy(test_case->log);
  }
  
  void kunit_debugfs_destroy_suite(struct kunit_suite *suite)


[PATCH v2] kunit: debugfs: Handle errors from alloc_string_stream()

2023-09-28 Thread Richard Fitzgerald
In kunit_debugfs_create_suite() give up and skip creating the debugfs
file if any of the alloc_string_stream() calls return an error or NULL.
Only put a value in the log pointer of kunit_suite and kunit_test if it
is a valid pointer to a log.

This prevents the potential invalid dereference reported by smatch:

 lib/kunit/debugfs.c:115 kunit_debugfs_create_suite() error: 'suite->log'
dereferencing possible ERR_PTR()
 lib/kunit/debugfs.c:119 kunit_debugfs_create_suite() error: 'test_case->log'
dereferencing possible ERR_PTR()

Signed-off-by: Richard Fitzgerald 
Reported-by: Dan Carpenter 
Fixes: 05e2006ce493 ("kunit: Use string_stream for test log")
Reviewed-by: Rae Moar 
---
Changes from V1:
- If the alloc_string_stream() for the suite->log fails
  just return. Nothing has been created at this point so
  there's nothing to clean up.
- Re-word the explanation of why the log pointers are only
  set if they point to a valid log.

As these changes are trivial I've carried Rae Moar's
Reviewed-by from V1.
---
 lib/kunit/debugfs.c | 30 +-
 1 file changed, 25 insertions(+), 5 deletions(-)

diff --git a/lib/kunit/debugfs.c b/lib/kunit/debugfs.c
index 270d185737e6..9d167adfa746 100644
--- a/lib/kunit/debugfs.c
+++ b/lib/kunit/debugfs.c
@@ -109,14 +109,28 @@ static const struct file_operations debugfs_results_fops 
= {
 void kunit_debugfs_create_suite(struct kunit_suite *suite)
 {
struct kunit_case *test_case;
+   struct string_stream *stream;
 
-   /* Allocate logs before creating debugfs representation. */
-   suite->log = alloc_string_stream(GFP_KERNEL);
-   string_stream_set_append_newlines(suite->log, true);
+   /*
+* Allocate logs before creating debugfs representation.
+* The suite->log and test_case->log pointer are expected to be NULL
+* if there isn't a log, so only set it if the log stream was created
+* successfully.
+*/
+   stream = alloc_string_stream(GFP_KERNEL);
+   if (IS_ERR_OR_NULL(stream))
+   return;
+
+   string_stream_set_append_newlines(stream, true);
+   suite->log = stream;
 
kunit_suite_for_each_test_case(suite, test_case) {
-   test_case->log = alloc_string_stream(GFP_KERNEL);
-   string_stream_set_append_newlines(test_case->log, true);
+   stream = alloc_string_stream(GFP_KERNEL);
+   if (IS_ERR_OR_NULL(stream))
+   goto err;
+
+   string_stream_set_append_newlines(stream, true);
+   test_case->log = stream;
}
 
suite->debugfs = debugfs_create_dir(suite->name, debugfs_rootdir);
@@ -124,6 +138,12 @@ void kunit_debugfs_create_suite(struct kunit_suite *suite)
debugfs_create_file(KUNIT_DEBUGFS_RESULTS, S_IFREG | 0444,
suite->debugfs,
suite, &debugfs_results_fops);
+   return;
+
+err:
+   string_stream_destroy(suite->log);
+   kunit_suite_for_each_test_case(suite, test_case)
+   string_stream_destroy(test_case->log);
 }
 
 void kunit_debugfs_destroy_suite(struct kunit_suite *suite)
-- 
2.30.2



[PATCH] kunit: string-stream: Allow ERR_PTR to be passed to string_stream_destroy()

2023-09-28 Thread Richard Fitzgerald
Check the stream pointer passed to string_stream_destroy() for
IS_ERR_OR_NULL() instead of only NULL.

Whatever alloc_string_stream() returns should be safe to pass
to string_stream_destroy(), and that will be an ERR_PTR.

It's obviously good practise and generally helpful to also check
for NULL pointers so that client cleanup code can call
string_stream_destroy() unconditionally - which could include
pointers that have never been set to anything and so are NULL.

Signed-off-by: Richard Fitzgerald 
---
 lib/kunit/string-stream.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/lib/kunit/string-stream.c b/lib/kunit/string-stream.c
index a6f3616c2048..54f4fdcbfac8 100644
--- a/lib/kunit/string-stream.c
+++ b/lib/kunit/string-stream.c
@@ -173,7 +173,7 @@ void string_stream_destroy(struct string_stream *stream)
 {
KUNIT_STATIC_STUB_REDIRECT(string_stream_destroy, stream);
 
-   if (!stream)
+   if (IS_ERR_OR_NULL(stream))
return;
 
string_stream_clear(stream);
-- 
2.30.2



[PATCH] kunit: debugfs: Fix unchecked dereference in debugfs_print_results()

2023-09-28 Thread Richard Fitzgerald
Move the call to kunit_suite_has_succeeded() after the check that
the kunit_suite pointer is valid.

This was found by smatch:

 lib/kunit/debugfs.c:66 debugfs_print_results() warn: variable
 dereferenced before check 'suite' (see line 63)

Signed-off-by: Richard Fitzgerald 
Reported-by: Dan Carpenter 
Fixes: 38289a26e1b8 ("kunit: fix debugfs code to use enum kunit_status, not 
bool")
---
 lib/kunit/debugfs.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/lib/kunit/debugfs.c b/lib/kunit/debugfs.c
index 9d167adfa746..382706dfb47d 100644
--- a/lib/kunit/debugfs.c
+++ b/lib/kunit/debugfs.c
@@ -60,12 +60,14 @@ static void debugfs_print_result(struct seq_file *seq, 
struct string_stream *log
 static int debugfs_print_results(struct seq_file *seq, void *v)
 {
struct kunit_suite *suite = (struct kunit_suite *)seq->private;
-   enum kunit_status success = kunit_suite_has_succeeded(suite);
+   enum kunit_status success;
struct kunit_case *test_case;
 
if (!suite)
return 0;
 
+   success = kunit_suite_has_succeeded(suite);
+
/* Print KTAP header so the debugfs log can be parsed as valid KTAP. */
seq_puts(seq, "KTAP version 1\n");
seq_puts(seq, "1..1\n");
-- 
2.30.2



[PATCH v2 RESEND] kunit: debugfs: Handle errors from alloc_string_stream()

2023-10-30 Thread Richard Fitzgerald
In kunit_debugfs_create_suite() give up and skip creating the debugfs
file if any of the alloc_string_stream() calls return an error or NULL.
Only put a value in the log pointer of kunit_suite and kunit_test if it
is a valid pointer to a log.

This prevents the potential invalid dereference reported by smatch:

 lib/kunit/debugfs.c:115 kunit_debugfs_create_suite() error: 'suite->log'
dereferencing possible ERR_PTR()
 lib/kunit/debugfs.c:119 kunit_debugfs_create_suite() error: 'test_case->log'
dereferencing possible ERR_PTR()

Signed-off-by: Richard Fitzgerald 
Reported-by: Dan Carpenter 
Fixes: 05e2006ce493 ("kunit: Use string_stream for test log")
---
 lib/kunit/debugfs.c | 30 +-
 1 file changed, 25 insertions(+), 5 deletions(-)

diff --git a/lib/kunit/debugfs.c b/lib/kunit/debugfs.c
index 270d185737e6..9d167adfa746 100644
--- a/lib/kunit/debugfs.c
+++ b/lib/kunit/debugfs.c
@@ -109,14 +109,28 @@ static const struct file_operations debugfs_results_fops 
= {
 void kunit_debugfs_create_suite(struct kunit_suite *suite)
 {
struct kunit_case *test_case;
+   struct string_stream *stream;
 
-   /* Allocate logs before creating debugfs representation. */
-   suite->log = alloc_string_stream(GFP_KERNEL);
-   string_stream_set_append_newlines(suite->log, true);
+   /*
+* Allocate logs before creating debugfs representation.
+* The suite->log and test_case->log pointer are expected to be NULL
+* if there isn't a log, so only set it if the log stream was created
+* successfully.
+*/
+   stream = alloc_string_stream(GFP_KERNEL);
+   if (IS_ERR_OR_NULL(stream))
+   return;
+
+   string_stream_set_append_newlines(stream, true);
+   suite->log = stream;
 
kunit_suite_for_each_test_case(suite, test_case) {
-   test_case->log = alloc_string_stream(GFP_KERNEL);
-   string_stream_set_append_newlines(test_case->log, true);
+   stream = alloc_string_stream(GFP_KERNEL);
+   if (IS_ERR_OR_NULL(stream))
+   goto err;
+
+   string_stream_set_append_newlines(stream, true);
+   test_case->log = stream;
}
 
suite->debugfs = debugfs_create_dir(suite->name, debugfs_rootdir);
@@ -124,6 +138,12 @@ void kunit_debugfs_create_suite(struct kunit_suite *suite)
debugfs_create_file(KUNIT_DEBUGFS_RESULTS, S_IFREG | 0444,
suite->debugfs,
suite, &debugfs_results_fops);
+   return;
+
+err:
+   string_stream_destroy(suite->log);
+   kunit_suite_for_each_test_case(suite, test_case)
+   string_stream_destroy(test_case->log);
 }
 
 void kunit_debugfs_destroy_suite(struct kunit_suite *suite)
-- 
2.30.2



[PATCH RESEND] kunit: string-stream: Allow ERR_PTR to be passed to string_stream_destroy()

2023-10-30 Thread Richard Fitzgerald
Check the stream pointer passed to string_stream_destroy() for
IS_ERR_OR_NULL() instead of only NULL.

Whatever alloc_string_stream() returns should be safe to pass
to string_stream_destroy(), and that will be an ERR_PTR.

It's obviously good practise and generally helpful to also check
for NULL pointers so that client cleanup code can call
string_stream_destroy() unconditionally - which could include
pointers that have never been set to anything and so are NULL.

Signed-off-by: Richard Fitzgerald 
---
 lib/kunit/string-stream.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/lib/kunit/string-stream.c b/lib/kunit/string-stream.c
index a6f3616c2048..54f4fdcbfac8 100644
--- a/lib/kunit/string-stream.c
+++ b/lib/kunit/string-stream.c
@@ -173,7 +173,7 @@ void string_stream_destroy(struct string_stream *stream)
 {
KUNIT_STATIC_STUB_REDIRECT(string_stream_destroy, stream);
 
-   if (!stream)
+   if (IS_ERR_OR_NULL(stream))
return;
 
string_stream_clear(stream);
-- 
2.30.2



[PATCH RESEND] kunit: debugfs: Fix unchecked dereference in debugfs_print_results()

2023-10-30 Thread Richard Fitzgerald
Move the call to kunit_suite_has_succeeded() after the check that
the kunit_suite pointer is valid.

This was found by smatch:

 lib/kunit/debugfs.c:66 debugfs_print_results() warn: variable
 dereferenced before check 'suite' (see line 63)

Signed-off-by: Richard Fitzgerald 
Reported-by: Dan Carpenter 
Fixes: 38289a26e1b8 ("kunit: fix debugfs code to use enum kunit_status, not 
bool")
---
 lib/kunit/debugfs.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/lib/kunit/debugfs.c b/lib/kunit/debugfs.c
index 9d167adfa746..382706dfb47d 100644
--- a/lib/kunit/debugfs.c
+++ b/lib/kunit/debugfs.c
@@ -60,12 +60,14 @@ static void debugfs_print_result(struct seq_file *seq, 
struct string_stream *log
 static int debugfs_print_results(struct seq_file *seq, void *v)
 {
struct kunit_suite *suite = (struct kunit_suite *)seq->private;
-   enum kunit_status success = kunit_suite_has_succeeded(suite);
+   enum kunit_status success;
struct kunit_case *test_case;
 
if (!suite)
return 0;
 
+   success = kunit_suite_has_succeeded(suite);
+
/* Print KTAP header so the debugfs log can be parsed as valid KTAP. */
seq_puts(seq, "KTAP version 1\n");
seq_puts(seq, "1..1\n");
-- 
2.30.2



[PATCH] kunit: test: Avoid cast warning in when adding kfree() as an action

2023-11-06 Thread Richard Fitzgerald
In kunit_log_test() pass the kfree_wrapper() function to kunit_add_action()
instead of directly passing kfree().

This prevents a cast warning:

lib/kunit/kunit-test.c:565:25: warning: cast from 'void (*)(const void *)'
to 'kunit_action_t *' (aka 'void (*)(void *)') converts to incompatible
function type [-Wcast-function-type-strict]

   564  full_log = string_stream_get_string(test->log);
 > 565  kunit_add_action(test, (kunit_action_t *)kfree, full_log);

Signed-off-by: Richard Fitzgerald 
Reported-by: kernel test robot 
Closes: 
https://lore.kernel.org/oe-kbuild-all/202311070041.kwvyx7yp-...@intel.com/
Fixes: 05e2006ce493 ("kunit: Use string_stream for test log")
---
 lib/kunit/kunit-test.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/lib/kunit/kunit-test.c b/lib/kunit/kunit-test.c
index 99d2a3a528e1..de2113a58fa0 100644
--- a/lib/kunit/kunit-test.c
+++ b/lib/kunit/kunit-test.c
@@ -562,7 +562,7 @@ static void kunit_log_test(struct kunit *test)
KUNIT_EXPECT_TRUE(test, test->log->append_newlines);
 
full_log = string_stream_get_string(test->log);
-   kunit_add_action(test, (kunit_action_t *)kfree, full_log);
+   kunit_add_action(test, kfree_wrapper, full_log);
KUNIT_EXPECT_NOT_ERR_OR_NULL(test,
 strstr(full_log, "put this in log."));
KUNIT_EXPECT_NOT_ERR_OR_NULL(test,
-- 
2.30.2



Re: [PATCH] kunit: test: Avoid cast warning in when adding kfree() as an action

2023-11-06 Thread Richard Fitzgerald

On 6/11/23 17:23, Richard Fitzgerald wrote:

In kunit_log_test() pass the kfree_wrapper() function to kunit_add_action()
instead of directly passing kfree().


Aargh! Sorry, noticed spurious word in commit title. Will send a V2.


[PATCH v2] kunit: test: Avoid cast warning when adding kfree() as an action

2023-11-06 Thread Richard Fitzgerald
In kunit_log_test() pass the kfree_wrapper() function to kunit_add_action()
instead of directly passing kfree().

This prevents a cast warning:

lib/kunit/kunit-test.c:565:25: warning: cast from 'void (*)(const void *)'
to 'kunit_action_t *' (aka 'void (*)(void *)') converts to incompatible
function type [-Wcast-function-type-strict]

   564  full_log = string_stream_get_string(test->log);
 > 565  kunit_add_action(test, (kunit_action_t *)kfree, full_log);

Signed-off-by: Richard Fitzgerald 
Reported-by: kernel test robot 
Closes: 
https://lore.kernel.org/oe-kbuild-all/202311070041.kwvyx7yp-...@intel.com/
Fixes: 05e2006ce493 ("kunit: Use string_stream for test log")
---
 lib/kunit/kunit-test.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/lib/kunit/kunit-test.c b/lib/kunit/kunit-test.c
index 99d2a3a528e1..de2113a58fa0 100644
--- a/lib/kunit/kunit-test.c
+++ b/lib/kunit/kunit-test.c
@@ -562,7 +562,7 @@ static void kunit_log_test(struct kunit *test)
KUNIT_EXPECT_TRUE(test, test->log->append_newlines);
 
full_log = string_stream_get_string(test->log);
-   kunit_add_action(test, (kunit_action_t *)kfree, full_log);
+   kunit_add_action(test, kfree_wrapper, full_log);
KUNIT_EXPECT_NOT_ERR_OR_NULL(test,
 strstr(full_log, "put this in log."));
KUNIT_EXPECT_NOT_ERR_OR_NULL(test,
-- 
2.30.2



[PATCH] kunit: string-stream-test: Avoid cast warning when testing gfp_t flags

2023-11-21 Thread Richard Fitzgerald
Passing a gfp_t to KUNIT_EXPECT_EQ() causes a cast warning:

  lib/kunit/string-stream-test.c:73:9: sparse: sparse: incorrect type in
  initializer (different base types) expected long long right_value
  got restricted gfp_t const __right

Avoid this by testing stream->gfp for the expected value and passing the
boolean result of this comparison to KUNIT_EXPECT_TRUE(), as was already
done a few lines above in string_stream_managed_init_test().

Signed-off-by: Richard Fitzgerald 
Fixes: d1a0d699bfc0 ("kunit: string-stream: Add tests for freeing 
resource-managed string_stream")
Reported-by: kernel test robot 
Closes: 
https://lore.kernel.org/oe-kbuild-all/202311181918.0mpcu2xh-...@intel.com/
---
 lib/kunit/string-stream-test.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/lib/kunit/string-stream-test.c b/lib/kunit/string-stream-test.c
index 06822766f29a..03fb511826f7 100644
--- a/lib/kunit/string-stream-test.c
+++ b/lib/kunit/string-stream-test.c
@@ -72,7 +72,7 @@ static void string_stream_unmanaged_init_test(struct kunit 
*test)
 
KUNIT_EXPECT_EQ(test, stream->length, 0);
KUNIT_EXPECT_TRUE(test, list_empty(&stream->fragments));
-   KUNIT_EXPECT_EQ(test, stream->gfp, GFP_KERNEL);
+   KUNIT_EXPECT_TRUE(test, (stream->gfp == GFP_KERNEL));
KUNIT_EXPECT_FALSE(test, stream->append_newlines);
 
KUNIT_EXPECT_TRUE(test, string_stream_is_empty(stream));
-- 
2.30.2




Re: [PATCH v2] kunit: run test suites only after module initialization completes

2023-12-06 Thread Richard Fitzgerald

On 28/11/2023 10:16, Marco Pagani wrote:

Commit 2810c1e99867 ("kunit: Fix wild-memory-access bug in
kunit_free_suite_set()") fixed a wild-memory-access bug that could have
happened during the loading phase of test suites built and executed as
loadable modules. However, it also introduced a problematic side effect
that causes test suites modules to crash when they attempt to register
fake devices.

When a module is loaded, it traverses the MODULE_STATE_UNFORMED and
MODULE_STATE_COMING states before reaching the normal operating state
MODULE_STATE_LIVE. Finally, when the module is removed, it moves to
MODULE_STATE_GOING before being released. However, if the loading
function load_module() fails between complete_formation() and
do_init_module(), the module goes directly from MODULE_STATE_COMING to
MODULE_STATE_GOING without passing through MODULE_STATE_LIVE.

This behavior was causing kunit_module_exit() to be called without
having first executed kunit_module_init(). Since kunit_module_exit() is
responsible for freeing the memory allocated by kunit_module_init()
through kunit_filter_suites(), this behavior was resulting in a
wild-memory-access bug.

Commit 2810c1e99867 ("kunit: Fix wild-memory-access bug in
kunit_free_suite_set()") fixed this issue by running the tests when the
module is still in MODULE_STATE_COMING. However, modules in that state
are not fully initialized, lacking sysfs kobjects. Therefore, if a test
module attempts to register a fake device, it will inevitably crash.

This patch proposes a different approach to fix the original
wild-memory-access bug while restoring the normal module execution flow
by making kunit_module_exit() able to detect if kunit_module_init() has
previously initialized the tests suite set. In this way, test modules
can once again register fake devices without crashing.

This behavior is achieved by checking whether mod->kunit_suites is a
virtual or direct mapping address. If it is a virtual address, then
kunit_module_init() has allocated the suite_set in kunit_filter_suites()
using kmalloc_array(). On the contrary, if mod->kunit_suites is still
pointing to the original address that was set when looking up the
.kunit_test_suites section of the module, then the loading phase has
failed and there's no memory to be freed.

v2:
- add include 

Fixes: 2810c1e99867 ("kunit: Fix wild-memory-access bug in 
kunit_free_suite_set()")
Signed-off-by: Marco Pagani 


Tested-by: Richard Fitzgerald 

Fixed this crash:
https://lore.kernel.org/all/e239b94b-462a-41e5-9a4c-cd1ffd530...@opensource.cirrus.com/

Also tested with sound/pci/hda/cirrus_scodec_test.c



[PATCH] kunit: Fix NULL-dereference in kunit_init_suite() if suite->log is NULL

2023-12-18 Thread Richard Fitzgerald
suite->log must be checked for NULL before passing it to
string_stream_clear(). This was done in kunit_init_test() but was missing
from kunit_init_suite().

Signed-off-by: Richard Fitzgerald 
Fixes: 6d696c4695c5 ("kunit: add ability to run tests after boot using debugfs")
---
 lib/kunit/test.c | 4 +++-
 1 file changed, 3 insertions(+), 1 deletion(-)

diff --git a/lib/kunit/test.c b/lib/kunit/test.c
index e803d998e855..ea7f0913e55a 100644
--- a/lib/kunit/test.c
+++ b/lib/kunit/test.c
@@ -658,7 +658,9 @@ static void kunit_init_suite(struct kunit_suite *suite)
kunit_debugfs_create_suite(suite);
suite->status_comment[0] = '\0';
suite->suite_init_err = 0;
-   string_stream_clear(suite->log);
+
+   if (suite->log)
+   string_stream_clear(suite->log);
 }
 
 bool kunit_enabled(void)
-- 
2.30.2




[PATCH 1/2] kunit: Allow passing function pointer to kunit_activate_static_stub()

2023-12-18 Thread Richard Fitzgerald
Swap the arguments to typecheck_fn() in kunit_activate_static_stub()
so that real_fn_addr can be either the function itself or a pointer
to that function.

This is useful to simplify redirecting static functions in a module.
Having to pass the actual function meant that it must be exported
from the module. Either making the 'static' and EXPORT_SYMBOL*()
conditional (which makes the code messy), or change it to always
exported (which increases the export namespace and prevents the
compiler inlining a trivial stub function in non-test builds).

With the original definition of kunit_activate_static_stub() the
address of real_fn_addr was passed to typecheck_fn() as the type to
be passed. This meant that if real_fn_addr was a pointer-to-function
it would resolve to a ** instead of a *, giving an error like this:

   error: initialization of ‘int (**)(int)’ from incompatible pointer
   type ‘int (*)(int)’ [-Werror=incompatible-pointer-types]
   kunit_activate_static_stub(test, add_one_fn_ptr, subtract_one);
  | ^~~~
   ./include/linux/typecheck.h:21:25: note: in definition of macro
   ‘typecheck_fn’
   21 | ({ typeof(type) __tmp = function; \

Swapping the arguments to typecheck_fn makes it take the type of a
pointer to the replacement function. Either a function or a pointer
to function can be assigned to that. For example:

static int some_function(int x)
{
/* whatever */
}

int (* some_function_ptr)(int) = some_function;

static int replacement(int x)
{
/* whatever */
}

Then:
  kunit_activate_static_stub(test, some_function, replacement);
yields:
  typecheck_fn(typeof(&replacement), some_function);

and:
  kunit_activate_static_stub(test, some_function_ptr, replacement);
yields:
  typecheck_fn(typeof(&replacement), some_function_ptr);

The two typecheck_fn() then resolve to:

  int (*__tmp)(int) = some_function;
and
  int (*__tmp)(int) = some_function_ptr;

Both of these are valid. In the first case the compiler inserts
an implicit '&' to take the address of the supplied function, and
in the second case the RHS is already a pointer to the same type.

Signed-off-by: Richard Fitzgerald 
---
 include/kunit/static_stub.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/include/kunit/static_stub.h b/include/kunit/static_stub.h
index 85315c80b303..bf940322dfc0 100644
--- a/include/kunit/static_stub.h
+++ b/include/kunit/static_stub.h
@@ -93,7 +93,7 @@ void __kunit_activate_static_stub(struct kunit *test,
  * The redirection can be disabled again with kunit_deactivate_static_stub().
  */
 #define kunit_activate_static_stub(test, real_fn_addr, replacement_addr) do {  
\
-   typecheck_fn(typeof(&real_fn_addr), replacement_addr);  
\
+   typecheck_fn(typeof(&replacement_addr), real_fn_addr);  
\
__kunit_activate_static_stub(test, real_fn_addr, replacement_addr); 
\
 } while (0)
 
-- 
2.30.2




[PATCH 2/2] kunit: Add example of kunit_activate_static_stub() with pointer-to-function

2023-12-18 Thread Richard Fitzgerald
Adds a variant of example_static_stub_test() that shows use of a
pointer-to-function with kunit_activate_static_stub().

A const pointer to the add_one() function is declared. This
pointer-to-function is passed to kunit_activate_static_stub() and
kunit_deactivate_static_stub() instead of passing add_one directly.

Signed-off-by: Richard Fitzgerald 
---
 lib/kunit/kunit-example-test.c | 27 +++
 1 file changed, 27 insertions(+)

diff --git a/lib/kunit/kunit-example-test.c b/lib/kunit/kunit-example-test.c
index d2f7a3c62c18..9e57f341dc37 100644
--- a/lib/kunit/kunit-example-test.c
+++ b/lib/kunit/kunit-example-test.c
@@ -168,6 +168,8 @@ static int subtract_one(int i)
return i - 1;
 }
 
+static int (* const add_one_fn_ptr)(int i) = add_one;
+
 /*
  * This test shows the use of static stubs.
  */
@@ -187,6 +189,30 @@ static void example_static_stub_test(struct kunit *test)
KUNIT_EXPECT_EQ(test, add_one(1), 2);
 }
 
+/*
+ * This test shows the use of static stubs when the function being
+ * replaced is provided as a pointer-to-function instead of the
+ * actual function. This is useful for providing access to static
+ * functions in a module by exporting a pointer to that function
+ * instead of having to change the static function to a non-static
+ * exported function.
+ */
+static void example_static_stub_using_fn_ptr_test(struct kunit *test)
+{
+   /* By default, function is not stubbed. */
+   KUNIT_EXPECT_EQ(test, add_one(1), 2);
+
+   /* Replace add_one() with subtract_one(). */
+   kunit_activate_static_stub(test, add_one_fn_ptr, subtract_one);
+
+   /* add_one() is now replaced. */
+   KUNIT_EXPECT_EQ(test, add_one(1), 0);
+
+   /* Return add_one() to normal. */
+   kunit_deactivate_static_stub(test, add_one_fn_ptr);
+   KUNIT_EXPECT_EQ(test, add_one(1), 2);
+}
+
 static const struct example_param {
int value;
 } example_params_array[] = {
@@ -245,6 +271,7 @@ static struct kunit_case example_test_cases[] = {
KUNIT_CASE(example_mark_skipped_test),
KUNIT_CASE(example_all_expect_macros_test),
KUNIT_CASE(example_static_stub_test),
+   KUNIT_CASE(example_static_stub_using_fn_ptr_test),
KUNIT_CASE_PARAM(example_params_test, example_gen_params),
KUNIT_CASE_SLOW(example_slow_test),
{}
-- 
2.30.2




Re: [PATCH v3] kunit: run test suites only after module initialization completes

2023-12-20 Thread Richard Fitzgerald

On 06/12/2023 15:07, Marco Pagani wrote:

Commit 2810c1e99867 ("kunit: Fix wild-memory-access bug in
kunit_free_suite_set()") fixed a wild-memory-access bug that could have
happened during the loading phase of test suites built and executed as
loadable modules. However, it also introduced a problematic side effect
that causes test suites modules to crash when they attempt to register
fake devices.

When a module is loaded, it traverses the MODULE_STATE_UNFORMED and
MODULE_STATE_COMING states before reaching the normal operating state
MODULE_STATE_LIVE. Finally, when the module is removed, it moves to
MODULE_STATE_GOING before being released. However, if the loading
function load_module() fails between complete_formation() and
do_init_module(), the module goes directly from MODULE_STATE_COMING to
MODULE_STATE_GOING without passing through MODULE_STATE_LIVE.

This behavior was causing kunit_module_exit() to be called without
having first executed kunit_module_init(). Since kunit_module_exit() is
responsible for freeing the memory allocated by kunit_module_init()
through kunit_filter_suites(), this behavior was resulting in a
wild-memory-access bug.

Commit 2810c1e99867 ("kunit: Fix wild-memory-access bug in
kunit_free_suite_set()") fixed this issue by running the tests when the
module is still in MODULE_STATE_COMING. However, modules in that state
are not fully initialized, lacking sysfs kobjects. Therefore, if a test
module attempts to register a fake device, it will inevitably crash.

This patch proposes a different approach to fix the original
wild-memory-access bug while restoring the normal module execution flow
by making kunit_module_exit() able to detect if kunit_module_init() has
previously initialized the tests suite set. In this way, test modules
can once again register fake devices without crashing.

This behavior is achieved by checking whether mod->kunit_suites is a
virtual or direct mapping address. If it is a virtual address, then
kunit_module_init() has allocated the suite_set in kunit_filter_suites()
using kmalloc_array(). On the contrary, if mod->kunit_suites is still
pointing to the original address that was set when looking up the
.kunit_test_suites section of the module, then the loading phase has
failed and there's no memory to be freed.

v3:
- add a comment to clarify why the start address is checked
v2:
- add include 

Fixes: 2810c1e99867 ("kunit: Fix wild-memory-access bug in 
kunit_free_suite_set()")
Tested-by: Richard Fitzgerald 
Reviewed-by: Javier Martinez Canillas 
Signed-off-by: Marco Pagani 
---


For V3:

Tested-by: Richard Fitzgerald 

Fixes this crash:
https://lore.kernel.org/all/e239b94b-462a-41e5-9a4c-cd1ffd530...@opensource.cirrus.com/

Also tested with sound/pci/hda/cirrus_scodec_test.c



[PATCH] kunit: Protect string comparisons against NULL

2023-12-20 Thread Richard Fitzgerald
Add NULL checks to KUNIT_BINARY_STR_ASSERTION() so that it will fail
cleanly if either pointer is NULL, instead of causing a NULL pointer
dereference in the strcmp().

A test failure could be that a string is unexpectedly NULL. This could
be trapped by KUNIT_ASSERT_NOT_NULL() but that would terminate the test
at that point. It's preferable that the KUNIT_EXPECT_STR*() macros can
handle NULL pointers as a failure.

Signed-off-by: Richard Fitzgerald 
---
 include/kunit/test.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/include/kunit/test.h b/include/kunit/test.h
index b163b9984b33..c2ce379c329b 100644
--- a/include/kunit/test.h
+++ b/include/kunit/test.h
@@ -758,7 +758,7 @@ do {
   \
.right_text = #right,  \
}; \
   \
-   if (likely(strcmp(__left, __right) op 0))  \
+   if (likely((__left) && (__right) && (strcmp(__left, __right) op 0)))   \
break; \
   \
   \
-- 
2.30.2




[PATCH v2 2/2] kunit: Add example of kunit_activate_static_stub() with pointer-to-function

2023-12-21 Thread Richard Fitzgerald
Adds a variant of example_static_stub_test() that shows use of a
pointer-to-function with kunit_activate_static_stub().

A const pointer to the add_one() function is declared. This
pointer-to-function is passed to kunit_activate_static_stub() and
kunit_deactivate_static_stub() instead of passing add_one directly.

Signed-off-by: Richard Fitzgerald 
---
V2: Added comment for add_one_fn_ptr.
---
 lib/kunit/kunit-example-test.c | 35 ++
 1 file changed, 35 insertions(+)

diff --git a/lib/kunit/kunit-example-test.c b/lib/kunit/kunit-example-test.c
index 359dbee10201..798924f7cc86 100644
--- a/lib/kunit/kunit-example-test.c
+++ b/lib/kunit/kunit-example-test.c
@@ -168,6 +168,16 @@ static int subtract_one(int i)
return i - 1;
 }
 
+/*
+ * If the function to be replaced is static within a module it is
+ * useful to export a pointer to that function instead of having
+ * to change the static function to a non-static exported function.
+ *
+ * This pointer simulates a module exporting a pointer to a static
+ * function.
+ */
+static int (* const add_one_fn_ptr)(int i) = add_one;
+
 /*
  * This test shows the use of static stubs.
  */
@@ -187,6 +197,30 @@ static void example_static_stub_test(struct kunit *test)
KUNIT_EXPECT_EQ(test, add_one(1), 2);
 }
 
+/*
+ * This test shows the use of static stubs when the function being
+ * replaced is provided as a pointer-to-function instead of the
+ * actual function. This is useful for providing access to static
+ * functions in a module by exporting a pointer to that function
+ * instead of having to change the static function to a non-static
+ * exported function.
+ */
+static void example_static_stub_using_fn_ptr_test(struct kunit *test)
+{
+   /* By default, function is not stubbed. */
+   KUNIT_EXPECT_EQ(test, add_one(1), 2);
+
+   /* Replace add_one() with subtract_one(). */
+   kunit_activate_static_stub(test, add_one_fn_ptr, subtract_one);
+
+   /* add_one() is now replaced. */
+   KUNIT_EXPECT_EQ(test, add_one(1), 0);
+
+   /* Return add_one() to normal. */
+   kunit_deactivate_static_stub(test, add_one_fn_ptr);
+   KUNIT_EXPECT_EQ(test, add_one(1), 2);
+}
+
 static const struct example_param {
int value;
 } example_params_array[] = {
@@ -259,6 +293,7 @@ static struct kunit_case example_test_cases[] = {
KUNIT_CASE(example_mark_skipped_test),
KUNIT_CASE(example_all_expect_macros_test),
KUNIT_CASE(example_static_stub_test),
+   KUNIT_CASE(example_static_stub_using_fn_ptr_test),
KUNIT_CASE(example_priv_test),
KUNIT_CASE_PARAM(example_params_test, example_gen_params),
KUNIT_CASE_SLOW(example_slow_test),
-- 
2.30.2




[PATCH v2 1/2] kunit: Allow passing function pointer to kunit_activate_static_stub()

2023-12-21 Thread Richard Fitzgerald
Swap the arguments to typecheck_fn() in kunit_activate_static_stub()
so that real_fn_addr can be either the function itself or a pointer
to that function.

This is useful to simplify redirecting static functions in a module.
Having to pass the actual function meant that it must be exported
from the module. Either making the 'static' and EXPORT_SYMBOL*()
conditional (which makes the code messy), or change it to always
exported (which increases the export namespace and prevents the
compiler inlining a trivial stub function in non-test builds).

With the original definition of kunit_activate_static_stub() the
address of real_fn_addr was passed to typecheck_fn() as the type to
be passed. This meant that if real_fn_addr was a pointer-to-function
it would resolve to a ** instead of a *, giving an error like this:

   error: initialization of ‘int (**)(int)’ from incompatible pointer
   type ‘int (*)(int)’ [-Werror=incompatible-pointer-types]
   kunit_activate_static_stub(test, add_one_fn_ptr, subtract_one);
  | ^~~~
   ./include/linux/typecheck.h:21:25: note: in definition of macro
   ‘typecheck_fn’
   21 | ({ typeof(type) __tmp = function; \

Swapping the arguments to typecheck_fn makes it take the type of a
pointer to the replacement function. Either a function or a pointer
to function can be assigned to that. For example:

static int some_function(int x)
{
/* whatever */
}

int (* some_function_ptr)(int) = some_function;

static int replacement(int x)
{
/* whatever */
}

Then:
  kunit_activate_static_stub(test, some_function, replacement);
yields:
  typecheck_fn(typeof(&replacement), some_function);

and:
  kunit_activate_static_stub(test, some_function_ptr, replacement);
yields:
  typecheck_fn(typeof(&replacement), some_function_ptr);

The two typecheck_fn() then resolve to:

  int (*__tmp)(int) = some_function;
and
  int (*__tmp)(int) = some_function_ptr;

Both of these are valid. In the first case the compiler inserts
an implicit '&' to take the address of the supplied function, and
in the second case the RHS is already a pointer to the same type.

Signed-off-by: Richard Fitzgerald 
Reviewed-by: Rae Moar 
---
No changes since V1.
---
 include/kunit/static_stub.h | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/include/kunit/static_stub.h b/include/kunit/static_stub.h
index 85315c80b303..bf940322dfc0 100644
--- a/include/kunit/static_stub.h
+++ b/include/kunit/static_stub.h
@@ -93,7 +93,7 @@ void __kunit_activate_static_stub(struct kunit *test,
  * The redirection can be disabled again with kunit_deactivate_static_stub().
  */
 #define kunit_activate_static_stub(test, real_fn_addr, replacement_addr) do {  
\
-   typecheck_fn(typeof(&real_fn_addr), replacement_addr);  
\
+   typecheck_fn(typeof(&replacement_addr), real_fn_addr);  
\
__kunit_activate_static_stub(test, real_fn_addr, replacement_addr); 
\
 } while (0)
 
-- 
2.30.2




Re: [PATCH] kunit: Protect string comparisons against NULL

2024-01-04 Thread Richard Fitzgerald

On 22/12/23 08:39, David Gow wrote:

On Wed, 20 Dec 2023 at 23:52, Richard Fitzgerald
 wrote:


Add NULL checks to KUNIT_BINARY_STR_ASSERTION() so that it will fail
cleanly if either pointer is NULL, instead of causing a NULL pointer
dereference in the strcmp().

A test failure could be that a string is unexpectedly NULL. This could
be trapped by KUNIT_ASSERT_NOT_NULL() but that would terminate the test
at that point. It's preferable that the KUNIT_EXPECT_STR*() macros can
handle NULL pointers as a failure.

Signed-off-by: Richard Fitzgerald 
---


I think this is the right thing to do. There's possibly an argument
that this should succeed if both are NULL, but I prefer it this way.



Maybe an _OR_NULL() variant of the string test macros would be better to
be explicit that NULL is acceptable.


Reviewed-by: David Gow 

Cheers,
-- David





Re: Regression on drm-tip

2024-01-31 Thread Richard Fitzgerald

On 31/1/24 05:34, Borah, Chaitanya Kumar wrote:

Hello Richard,

Hope you are doing well. I am Chaitanya from the Linux graphics team in Intel.

This mail is regarding a regression we are seeing in our CI runs[1] on 
drm-tip[2] repository.
These are captured by gitlab issues[3].

We bisected the issue and have found the following commit to be the first bad 
commit.
`
commit a0b84213f947176ddcd0e96e0751a109f28cde21
Author: Richard Fitzgerald r...@opensource.cirrus.com
Date:   Mon Dec 18 15:17:29 2023 +

 kunit: Fix NULL-dereference in kunit_init_suite() if suite->log is NULL

 suite->log must be checked for NULL before passing it to
 string_stream_clear(). This was done in kunit_init_test() but was missing
 from kunit_init_suite().

 Signed-off-by: Richard Fitzgerald r...@opensource.cirrus.com
 Fixes: 6d696c4695c5 ("kunit: add ability to run tests after boot using 
debugfs")
 Reviewed-by: Rae Moar rm...@google.com
 Acked-by: David Gow david...@google.com
 Reviewed-by: Muhammad Usama Anjum usama.an...@collabora.com
 Signed-off-by: Shuah Khan sk...@linuxfoundation.org

lib/kunit/test.c | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
`
We tried reverting the patch and the original issue is not seen but it results 
in NULL pointer deference[4] which I am guessing is expected.

Could you please check why the patch causes this regression and provide a fix 
if necessary?
  
[1] https://intel-gfx-ci.01.org/tree/drm-tip/index.html?testfilter=drm

[2] https://cgit.freedesktop.org/drm-tip/
[3] https://gitlab.freedesktop.org/drm/intel/-/issues/10140
   https://gitlab.freedesktop.org/drm/intel/-/issues/10143
[4]
[  179.849411] [IGT] drm_buddy: executing
[  179.856385] [IGT] drm_buddy: starting subtest drm_buddy
[  179.862594] KTAP version 1
[  179.862600] 1..1
[  179.863375] BUG: kernel NULL pointer dereference, address: 
0030
[  179.863381] #PF: supervisor read access in kernel mode
[  179.863384] #PF: error_code(0x) - not-present page
[  179.863387] PGD 0 P4D 0
[  179.863391] Oops:  [#1] PREEMPT SMP NOPTI
[  179.863395] CPU: 1 PID: 1319 Comm: drm_buddy Not tainted 
6.8.0-rc1-bisecttrail015 #16
[  179.863398] Hardware name: Intel Corporation Meteor Lake Client 
Platform/MTL-P DDR5 SODIMM SBS RVP, BIOS MTLPFWI1.R00.3471.D81.2311291340 
11/29/2023
[  179.863400] RIP: 0010:__lock_acquire+0x71f/0x2300
[  179.863408] Code: 84 03 06 00 00 44 8b 15 27 f6 72 01 45 85 d2 0f 84 9c 00 
00 00 f6 45 22 10 0f 84 63 03 00 00 41 bf 01 00 00 00 e9 8a 00 00 00 <48> 81 3f 
40 d7 fa 82 41 b9 00 00 00 00 45 0f 45 c8 83 fe 01 0f 87
...
[  179.863445] PKRU: 5554
[  179.863448] Call Trace:
[  179.863450]  
[  179.863453]  ? __die_body+0x1a/0x60
[  179.863459]  ? page_fault_oops+0x156/0x450
[  179.863465]  ? do_user_addr_fault+0x65/0x9e0
[  179.863472]  ? exc_page_fault+0x68/0x1a0
[  179.863479]  ? asm_exc_page_fault+0x26/0x30
[  179.863487]  ? __lock_acquire+0x71f/0x2300
[  179.863493]  ? __pfx_do_sync_core+0x10/0x10
[  179.863500]  lock_acquire+0xd8/0x2d0
[  179.863505]  ? string_stream_clear+0x29/0xb0 [kunit]
[  179.863523]  _raw_spin_lock+0x2e/0x40
[  179.863528]  ? string_stream_clear+0x29/0xb0 [kunit]
[  179.863540]  string_stream_clear+0x29/0xb0 [kunit]
[  179.863554]  __kunit_test_suites_init+0x7e/0xe0 [kunit]
[  179.863568]  kunit_module_notify+0x20f/0x220 [kunit]
[  179.863583]  notifier_call_chain+0x46/0x130
[  179.863591]  notifier_call_chain_robust+0x3e/0x90
[  179.863598]  blocking_notifier_call_chain_robust+0x42/0x60
[  179.863605]  load_module+0x1bcd/0x1f80
[  179.863617]  ? init_module_from_file+0x86/0xd0
[  179.863621]  init_module_from_file+0x86/0xd0
[  179.863629]  idempotent_init_module+0x17c/0x230
[  179.863637]  __x64_sys_finit_module+0x56/0xb0
[  179.863642]  do_syscall_64+0x6f/0x140
[  179.863649]  entry_SYSCALL_64_after_hwframe+0x6e/0x76
[  179.863654] RIP: 0033:0x7f0e6676195d


Looking at the gitlab bug reports compared to the crash log above:

[3] You have hit a failure on the 3rd test case:

<6> [59.039608] [IGT] drm_buddy: starting dynamic subtest
drm_test_buddy_alloc_limit
<6> [59.077701] KTAP version 1
<6> [59.077705] 1..1
<6> [59.078487] KTAP version 1
<6> [59.078494] # Subtest: drm_buddy
<6> [59.078496] # module: drm_buddy_test
<6> [59.078498] 1..4
<6> [59.07