[PATCH v2] kunit: mock: add support for function mocks with no parameters

From: Marcelo Schmitt
Date: Sat Sep 25 2021 - 15:42:13 EST


Function mocks defined with DEFINE_FUNCTION_MOCK(...) do not support
empty parameters list due to strict function prototypes enforcement
(-Werror=strict-prototypes). Add support for function mocks with no
parameters by adding checks to declare strict function prototypes when
an empty param list is provided.
Further, add an expectation to test that the generated code works.

Co-developed-by: Anderson Reis Rosa <andersonreisrosa@xxxxxxxxx>
Signed-off-by: Anderson Reis Rosa <andersonreisrosa@xxxxxxxxx>
Signed-off-by: Marcelo Schmitt <marcelo.schmitt1@xxxxxxxxx>
Reviewed-by: Daniel Latypov <dlatypov@xxxxxxxxxx>
---
Not sure if we are allowed to add a Reported-by tag to credit Andy Li, so we didn't.

include/test/mock.h | 2 +-
include/test/params.h | 12 +++++++++++-
test/mock-macro-test.c | 7 ++++++-
3 files changed, 18 insertions(+), 3 deletions(-)

diff --git a/include/test/mock.h b/include/test/mock.h
index 8b8031c13b2a..c46c90abc12a 100644
--- a/include/test/mock.h
+++ b/include/test/mock.h
@@ -640,7 +640,7 @@ int mock_in_sequence(struct KUNIT_T *test, struct mock_expectation *first, ...);
return_type, \
RETURN, \
param_types...) \
- return_type name(PARAM_LIST_FROM_TYPES(param_types)) \
+ return_type name(FUNC_PARAM_LIST_FROM_TYPES(param_types)) \
{ \
struct mock *mock = MOCK_SOURCE(mock_source_ctx, \
handle_index); \
diff --git a/include/test/params.h b/include/test/params.h
index 50d54035175d..ca4689dd0576 100644
--- a/include/test/params.h
+++ b/include/test/params.h
@@ -264,6 +264,11 @@
not_used, \
args)

+#define FUNC_PARAM_LIST_FROM_TYPES(args...) \
+ IF(IS_EQUAL(NUM_VA_ARGS(args), 0))(void) \
+ IF(IS_NOT_EQUAL(NUM_VA_ARGS(args), 0)) \
+ (PARAM_LIST_FROM_TYPES(args))
+
#define PRODUCE_TYPE_NAME(context, type, index) #type
#define TYPE_NAMES_FROM_TYPES(handle_index, args...) \
FOR_EACH_PARAM(PRODUCE_TYPE_NAME, \
@@ -282,12 +287,17 @@
IF(IS_EQUAL(index, ctrl_index))(struct mock *arg##ctrl_index) \
IF(IS_NOT_EQUAL(index, ctrl_index))( \
struct mock_param_matcher *arg##index)
-#define MATCHER_PARAM_LIST_FROM_TYPES(ctrl_index, args...) \
+#define MATCHER_PARAM_LIST_FROM_TYPES_INTERNAL(ctrl_index, args...) \
FOR_EACH_PARAM(PRODUCE_MATCHER_AND_ARG, \
FILTER_NONE, \
ctrl_index, \
args)

+#define MATCHER_PARAM_LIST_FROM_TYPES(ctrl_index, args...) \
+ IF(IS_EQUAL(NUM_VA_ARGS(args), 0))(void) \
+ IF(IS_NOT_EQUAL(NUM_VA_ARGS(args), 0)) \
+ (MATCHER_PARAM_LIST_FROM_TYPES_INTERNAL(ctrl_index, args))
+
#define PRODUCE_ARG(context, type, index) arg##index
#define ARG_NAMES_FROM_TYPES(ctrl_index, args...) \
FOR_EACH_PARAM(PRODUCE_ARG, \
diff --git a/test/mock-macro-test.c b/test/mock-macro-test.c
index 14da7ebe752d..d97cf3642bb3 100644
--- a/test/mock-macro-test.c
+++ b/test/mock-macro-test.c
@@ -59,6 +59,8 @@ DEFINE_VOID_CLASS_MOCK_HANDLE_INDEX(METHOD(test_void_ptr_func),

DEFINE_FUNCTION_MOCK(add, RETURNS(int), PARAMS(int, int));

+DEFINE_FUNCTION_MOCK(no_param, RETURNS(int), PARAMS());
+
struct mock_macro_context {
struct MOCK(test_struct) *mock_test_struct;
struct MOCK(void) *mock_void_ptr;
@@ -216,8 +218,11 @@ static void mock_macro_test_generated_function_code_works(struct KUNIT_T *test)

handle = EXPECT_CALL(add(int_eq(test, 4), int_eq(test, 3)));
handle->action = int_return(test, 7);
-
EXPECT_EQ(test, 7, add(4, 3));
+
+ handle = EXPECT_CALL(no_param());
+ handle->action = int_return(test, 9);
+ EXPECT_EQ(test, 9, no_param());
}

static int mock_macro_test_init(struct KUNIT_T *test)
--
2.33.0