xref: /linux/drivers/platform/wmi/tests/marshalling_kunit.c (revision f50822fd8675c68d294e89bd102f7b487ca3acd3)
1*29dfba69SArmin Wolf // SPDX-License-Identifier: GPL-2.0-or-later
2*29dfba69SArmin Wolf /*
3*29dfba69SArmin Wolf  * KUnit test for the ACPI-WMI marshalling code.
4*29dfba69SArmin Wolf  *
5*29dfba69SArmin Wolf  * Copyright (C) 2025 Armin Wolf <W_Armin@gmx.de>
6*29dfba69SArmin Wolf  */
7*29dfba69SArmin Wolf 
8*29dfba69SArmin Wolf #include <linux/acpi.h>
9*29dfba69SArmin Wolf #include <linux/align.h>
10*29dfba69SArmin Wolf #include <linux/module.h>
11*29dfba69SArmin Wolf #include <linux/slab.h>
12*29dfba69SArmin Wolf #include <linux/string.h>
13*29dfba69SArmin Wolf #include <linux/types.h>
14*29dfba69SArmin Wolf #include <linux/wmi.h>
15*29dfba69SArmin Wolf 
16*29dfba69SArmin Wolf #include <kunit/resource.h>
17*29dfba69SArmin Wolf #include <kunit/test.h>
18*29dfba69SArmin Wolf 
19*29dfba69SArmin Wolf #include "../internal.h"
20*29dfba69SArmin Wolf 
21*29dfba69SArmin Wolf struct wmi_acpi_param {
22*29dfba69SArmin Wolf 	const char *name;
23*29dfba69SArmin Wolf 	const union acpi_object obj;
24*29dfba69SArmin Wolf 	const struct wmi_buffer buffer;
25*29dfba69SArmin Wolf };
26*29dfba69SArmin Wolf 
27*29dfba69SArmin Wolf struct wmi_string_param {
28*29dfba69SArmin Wolf 	const char *name;
29*29dfba69SArmin Wolf 	const char *string;
30*29dfba69SArmin Wolf 	const struct wmi_buffer buffer;
31*29dfba69SArmin Wolf };
32*29dfba69SArmin Wolf 
33*29dfba69SArmin Wolf struct wmi_invalid_acpi_param {
34*29dfba69SArmin Wolf 	const char *name;
35*29dfba69SArmin Wolf 	const union acpi_object obj;
36*29dfba69SArmin Wolf };
37*29dfba69SArmin Wolf 
38*29dfba69SArmin Wolf struct wmi_invalid_string_param {
39*29dfba69SArmin Wolf 	const char *name;
40*29dfba69SArmin Wolf 	const struct wmi_buffer buffer;
41*29dfba69SArmin Wolf };
42*29dfba69SArmin Wolf 
43*29dfba69SArmin Wolf /* 0xdeadbeef */
44*29dfba69SArmin Wolf static u8 expected_single_integer[] = {
45*29dfba69SArmin Wolf 	0xef, 0xbe, 0xad, 0xde,
46*29dfba69SArmin Wolf };
47*29dfba69SArmin Wolf 
48*29dfba69SArmin Wolf /* "TEST" */
49*29dfba69SArmin Wolf static u8 expected_single_string[] = {
50*29dfba69SArmin Wolf 	0x0a, 0x00, 0x54, 0x00, 0x45, 0x00, 0x53, 0x00, 0x54, 0x00, 0x00, 0x00,
51*29dfba69SArmin Wolf };
52*29dfba69SArmin Wolf 
53*29dfba69SArmin Wolf static u8 test_buffer[] = {
54*29dfba69SArmin Wolf 	0xab, 0xcd,
55*29dfba69SArmin Wolf };
56*29dfba69SArmin Wolf 
57*29dfba69SArmin Wolf static u8 expected_single_buffer[] = {
58*29dfba69SArmin Wolf 	0xab, 0xcd,
59*29dfba69SArmin Wolf };
60*29dfba69SArmin Wolf 
61*29dfba69SArmin Wolf static union acpi_object simple_package_elements[] = {
62*29dfba69SArmin Wolf 	{
63*29dfba69SArmin Wolf 		.buffer = {
64*29dfba69SArmin Wolf 			.type = ACPI_TYPE_BUFFER,
65*29dfba69SArmin Wolf 			.length = sizeof(test_buffer),
66*29dfba69SArmin Wolf 			.pointer = test_buffer,
67*29dfba69SArmin Wolf 		},
68*29dfba69SArmin Wolf 	},
69*29dfba69SArmin Wolf 	{
70*29dfba69SArmin Wolf 		.integer = {
71*29dfba69SArmin Wolf 			.type = ACPI_TYPE_INTEGER,
72*29dfba69SArmin Wolf 			.value = 0x01020304,
73*29dfba69SArmin Wolf 		},
74*29dfba69SArmin Wolf 	},
75*29dfba69SArmin Wolf };
76*29dfba69SArmin Wolf 
77*29dfba69SArmin Wolf static u8 expected_simple_package[] = {
78*29dfba69SArmin Wolf 	0xab, 0xcd,
79*29dfba69SArmin Wolf 	0x00, 0x00,
80*29dfba69SArmin Wolf 	0x04, 0x03, 0x02, 0x01,
81*29dfba69SArmin Wolf };
82*29dfba69SArmin Wolf 
83*29dfba69SArmin Wolf static u8 test_small_buffer[] = {
84*29dfba69SArmin Wolf 	0xde,
85*29dfba69SArmin Wolf };
86*29dfba69SArmin Wolf 
87*29dfba69SArmin Wolf static union acpi_object complex_package_elements[] = {
88*29dfba69SArmin Wolf 	{
89*29dfba69SArmin Wolf 		.integer = {
90*29dfba69SArmin Wolf 			.type = ACPI_TYPE_INTEGER,
91*29dfba69SArmin Wolf 			.value = 0xdeadbeef,
92*29dfba69SArmin Wolf 		},
93*29dfba69SArmin Wolf 	},
94*29dfba69SArmin Wolf 	{
95*29dfba69SArmin Wolf 		.buffer = {
96*29dfba69SArmin Wolf 			.type = ACPI_TYPE_BUFFER,
97*29dfba69SArmin Wolf 			.length = sizeof(test_small_buffer),
98*29dfba69SArmin Wolf 			.pointer = test_small_buffer,
99*29dfba69SArmin Wolf 		},
100*29dfba69SArmin Wolf 	},
101*29dfba69SArmin Wolf 	{
102*29dfba69SArmin Wolf 		.string = {
103*29dfba69SArmin Wolf 			.type = ACPI_TYPE_STRING,
104*29dfba69SArmin Wolf 			.length = sizeof("TEST") - 1,
105*29dfba69SArmin Wolf 			.pointer = "TEST",
106*29dfba69SArmin Wolf 		},
107*29dfba69SArmin Wolf 	},
108*29dfba69SArmin Wolf 	{
109*29dfba69SArmin Wolf 		.buffer = {
110*29dfba69SArmin Wolf 			.type = ACPI_TYPE_BUFFER,
111*29dfba69SArmin Wolf 			.length = sizeof(test_small_buffer),
112*29dfba69SArmin Wolf 			.pointer = test_small_buffer,
113*29dfba69SArmin Wolf 		},
114*29dfba69SArmin Wolf 	},
115*29dfba69SArmin Wolf 	{
116*29dfba69SArmin Wolf 		.integer = {
117*29dfba69SArmin Wolf 			.type = ACPI_TYPE_INTEGER,
118*29dfba69SArmin Wolf 			.value = 0x01020304,
119*29dfba69SArmin Wolf 		},
120*29dfba69SArmin Wolf 	}
121*29dfba69SArmin Wolf };
122*29dfba69SArmin Wolf 
123*29dfba69SArmin Wolf static u8 expected_complex_package[] = {
124*29dfba69SArmin Wolf 	0xef, 0xbe, 0xad, 0xde,
125*29dfba69SArmin Wolf 	0xde,
126*29dfba69SArmin Wolf 	0x00,
127*29dfba69SArmin Wolf 	0x0a, 0x00, 0x54, 0x00, 0x45, 0x00, 0x53, 0x00, 0x54, 0x00, 0x00, 0x00,
128*29dfba69SArmin Wolf 	0xde,
129*29dfba69SArmin Wolf 	0x00,
130*29dfba69SArmin Wolf 	0x04, 0x03, 0x02, 0x01,
131*29dfba69SArmin Wolf };
132*29dfba69SArmin Wolf 
133*29dfba69SArmin Wolf static const struct wmi_acpi_param wmi_acpi_params_array[] = {
134*29dfba69SArmin Wolf 	{
135*29dfba69SArmin Wolf 		.name = "single_integer",
136*29dfba69SArmin Wolf 		.obj = {
137*29dfba69SArmin Wolf 			.integer = {
138*29dfba69SArmin Wolf 				.type = ACPI_TYPE_INTEGER,
139*29dfba69SArmin Wolf 				.value = 0xdeadbeef,
140*29dfba69SArmin Wolf 			},
141*29dfba69SArmin Wolf 		},
142*29dfba69SArmin Wolf 		.buffer = {
143*29dfba69SArmin Wolf 			.data = expected_single_integer,
144*29dfba69SArmin Wolf 			.length = sizeof(expected_single_integer),
145*29dfba69SArmin Wolf 		},
146*29dfba69SArmin Wolf 	},
147*29dfba69SArmin Wolf 	{
148*29dfba69SArmin Wolf 		.name = "single_string",
149*29dfba69SArmin Wolf 		.obj = {
150*29dfba69SArmin Wolf 			.string = {
151*29dfba69SArmin Wolf 				.type = ACPI_TYPE_STRING,
152*29dfba69SArmin Wolf 				.length = sizeof("TEST") - 1,
153*29dfba69SArmin Wolf 				.pointer = "TEST",
154*29dfba69SArmin Wolf 			},
155*29dfba69SArmin Wolf 		},
156*29dfba69SArmin Wolf 		.buffer = {
157*29dfba69SArmin Wolf 			.data = expected_single_string,
158*29dfba69SArmin Wolf 			.length = sizeof(expected_single_string),
159*29dfba69SArmin Wolf 		},
160*29dfba69SArmin Wolf 	},
161*29dfba69SArmin Wolf 	{
162*29dfba69SArmin Wolf 		.name = "single_buffer",
163*29dfba69SArmin Wolf 		.obj = {
164*29dfba69SArmin Wolf 			.buffer = {
165*29dfba69SArmin Wolf 				.type = ACPI_TYPE_BUFFER,
166*29dfba69SArmin Wolf 				.length = sizeof(test_buffer),
167*29dfba69SArmin Wolf 				.pointer = test_buffer,
168*29dfba69SArmin Wolf 			},
169*29dfba69SArmin Wolf 		},
170*29dfba69SArmin Wolf 		.buffer = {
171*29dfba69SArmin Wolf 			.data = expected_single_buffer,
172*29dfba69SArmin Wolf 			.length = sizeof(expected_single_buffer),
173*29dfba69SArmin Wolf 		},
174*29dfba69SArmin Wolf 	},
175*29dfba69SArmin Wolf 	{
176*29dfba69SArmin Wolf 		.name = "simple_package",
177*29dfba69SArmin Wolf 		.obj = {
178*29dfba69SArmin Wolf 			.package = {
179*29dfba69SArmin Wolf 				.type = ACPI_TYPE_PACKAGE,
180*29dfba69SArmin Wolf 				.count = ARRAY_SIZE(simple_package_elements),
181*29dfba69SArmin Wolf 				.elements = simple_package_elements,
182*29dfba69SArmin Wolf 			},
183*29dfba69SArmin Wolf 		},
184*29dfba69SArmin Wolf 		.buffer = {
185*29dfba69SArmin Wolf 			.data = expected_simple_package,
186*29dfba69SArmin Wolf 			.length = sizeof(expected_simple_package),
187*29dfba69SArmin Wolf 		},
188*29dfba69SArmin Wolf 	},
189*29dfba69SArmin Wolf 	{
190*29dfba69SArmin Wolf 		.name = "complex_package",
191*29dfba69SArmin Wolf 		.obj = {
192*29dfba69SArmin Wolf 			.package = {
193*29dfba69SArmin Wolf 				.type = ACPI_TYPE_PACKAGE,
194*29dfba69SArmin Wolf 				.count = ARRAY_SIZE(complex_package_elements),
195*29dfba69SArmin Wolf 				.elements = complex_package_elements,
196*29dfba69SArmin Wolf 			},
197*29dfba69SArmin Wolf 		},
198*29dfba69SArmin Wolf 		.buffer = {
199*29dfba69SArmin Wolf 			.data = expected_complex_package,
200*29dfba69SArmin Wolf 			.length = sizeof(expected_complex_package),
201*29dfba69SArmin Wolf 		},
202*29dfba69SArmin Wolf 	},
203*29dfba69SArmin Wolf };
204*29dfba69SArmin Wolf 
205*29dfba69SArmin Wolf static void wmi_acpi_param_get_desc(const struct wmi_acpi_param *param, char *desc)
206*29dfba69SArmin Wolf {
207*29dfba69SArmin Wolf 	strscpy(desc, param->name, KUNIT_PARAM_DESC_SIZE);
208*29dfba69SArmin Wolf }
209*29dfba69SArmin Wolf 
210*29dfba69SArmin Wolf KUNIT_ARRAY_PARAM(wmi_unmarshal_acpi_object, wmi_acpi_params_array, wmi_acpi_param_get_desc);
211*29dfba69SArmin Wolf 
212*29dfba69SArmin Wolf /* "WMI\0" */
213*29dfba69SArmin Wolf static u8 padded_wmi_string[] = {
214*29dfba69SArmin Wolf 	0x0a, 0x00,
215*29dfba69SArmin Wolf 	0x57, 0x00,
216*29dfba69SArmin Wolf 	0x4D, 0x00,
217*29dfba69SArmin Wolf 	0x49, 0x00,
218*29dfba69SArmin Wolf 	0x00, 0x00,
219*29dfba69SArmin Wolf 	0x00, 0x00,
220*29dfba69SArmin Wolf };
221*29dfba69SArmin Wolf 
222*29dfba69SArmin Wolf static const struct wmi_string_param wmi_string_params_array[] = {
223*29dfba69SArmin Wolf 	{
224*29dfba69SArmin Wolf 		.name = "test",
225*29dfba69SArmin Wolf 		.string = "TEST",
226*29dfba69SArmin Wolf 		.buffer = {
227*29dfba69SArmin Wolf 			.length = sizeof(expected_single_string),
228*29dfba69SArmin Wolf 			.data = expected_single_string,
229*29dfba69SArmin Wolf 		},
230*29dfba69SArmin Wolf 	},
231*29dfba69SArmin Wolf 	{
232*29dfba69SArmin Wolf 		.name = "padded",
233*29dfba69SArmin Wolf 		.string = "WMI",
234*29dfba69SArmin Wolf 		.buffer = {
235*29dfba69SArmin Wolf 			.length = sizeof(padded_wmi_string),
236*29dfba69SArmin Wolf 			.data = padded_wmi_string,
237*29dfba69SArmin Wolf 		},
238*29dfba69SArmin Wolf 	},
239*29dfba69SArmin Wolf };
240*29dfba69SArmin Wolf 
241*29dfba69SArmin Wolf static void wmi_string_param_get_desc(const struct wmi_string_param *param, char *desc)
242*29dfba69SArmin Wolf {
243*29dfba69SArmin Wolf 	strscpy(desc, param->name, KUNIT_PARAM_DESC_SIZE);
244*29dfba69SArmin Wolf }
245*29dfba69SArmin Wolf 
246*29dfba69SArmin Wolf KUNIT_ARRAY_PARAM(wmi_marshal_string, wmi_string_params_array, wmi_string_param_get_desc);
247*29dfba69SArmin Wolf 
248*29dfba69SArmin Wolf static union acpi_object nested_package_elements[] = {
249*29dfba69SArmin Wolf 	{
250*29dfba69SArmin Wolf 		.package = {
251*29dfba69SArmin Wolf 			.type = ACPI_TYPE_PACKAGE,
252*29dfba69SArmin Wolf 			.count = ARRAY_SIZE(simple_package_elements),
253*29dfba69SArmin Wolf 			.elements = simple_package_elements,
254*29dfba69SArmin Wolf 		},
255*29dfba69SArmin Wolf 	}
256*29dfba69SArmin Wolf };
257*29dfba69SArmin Wolf 
258*29dfba69SArmin Wolf static const struct wmi_invalid_acpi_param wmi_invalid_acpi_params_array[] = {
259*29dfba69SArmin Wolf 	{
260*29dfba69SArmin Wolf 		.name = "nested_package",
261*29dfba69SArmin Wolf 		.obj = {
262*29dfba69SArmin Wolf 			.package = {
263*29dfba69SArmin Wolf 				.type = ACPI_TYPE_PACKAGE,
264*29dfba69SArmin Wolf 				.count = ARRAY_SIZE(nested_package_elements),
265*29dfba69SArmin Wolf 				.elements = nested_package_elements,
266*29dfba69SArmin Wolf 			},
267*29dfba69SArmin Wolf 		},
268*29dfba69SArmin Wolf 	},
269*29dfba69SArmin Wolf 	{
270*29dfba69SArmin Wolf 		.name = "reference",
271*29dfba69SArmin Wolf 		.obj = {
272*29dfba69SArmin Wolf 			.reference = {
273*29dfba69SArmin Wolf 				.type = ACPI_TYPE_LOCAL_REFERENCE,
274*29dfba69SArmin Wolf 				.actual_type = ACPI_TYPE_ANY,
275*29dfba69SArmin Wolf 				.handle = NULL,
276*29dfba69SArmin Wolf 			},
277*29dfba69SArmin Wolf 		},
278*29dfba69SArmin Wolf 	},
279*29dfba69SArmin Wolf 	{
280*29dfba69SArmin Wolf 		.name = "processor",
281*29dfba69SArmin Wolf 		.obj = {
282*29dfba69SArmin Wolf 			.processor = {
283*29dfba69SArmin Wolf 				.type = ACPI_TYPE_PROCESSOR,
284*29dfba69SArmin Wolf 				.proc_id = 0,
285*29dfba69SArmin Wolf 				.pblk_address = 0,
286*29dfba69SArmin Wolf 				.pblk_length = 0,
287*29dfba69SArmin Wolf 			},
288*29dfba69SArmin Wolf 		},
289*29dfba69SArmin Wolf 	},
290*29dfba69SArmin Wolf 	{
291*29dfba69SArmin Wolf 		.name = "power_resource",
292*29dfba69SArmin Wolf 		.obj = {
293*29dfba69SArmin Wolf 			.power_resource = {
294*29dfba69SArmin Wolf 				.type = ACPI_TYPE_POWER,
295*29dfba69SArmin Wolf 				.system_level = 0,
296*29dfba69SArmin Wolf 				.resource_order = 0,
297*29dfba69SArmin Wolf 			},
298*29dfba69SArmin Wolf 		},
299*29dfba69SArmin Wolf 	},
300*29dfba69SArmin Wolf };
301*29dfba69SArmin Wolf 
302*29dfba69SArmin Wolf static void wmi_invalid_acpi_param_get_desc(const struct wmi_invalid_acpi_param *param, char *desc)
303*29dfba69SArmin Wolf {
304*29dfba69SArmin Wolf 	strscpy(desc, param->name, KUNIT_PARAM_DESC_SIZE);
305*29dfba69SArmin Wolf }
306*29dfba69SArmin Wolf 
307*29dfba69SArmin Wolf KUNIT_ARRAY_PARAM(wmi_unmarshal_acpi_object_failure, wmi_invalid_acpi_params_array,
308*29dfba69SArmin Wolf 		  wmi_invalid_acpi_param_get_desc);
309*29dfba69SArmin Wolf 
310*29dfba69SArmin Wolf static u8 oversized_wmi_string[] = {
311*29dfba69SArmin Wolf 	0x04, 0x00, 0x00, 0x00,
312*29dfba69SArmin Wolf };
313*29dfba69SArmin Wolf 
314*29dfba69SArmin Wolf /*
315*29dfba69SArmin Wolf  * The error is that 3 bytes can not hold UTF-16 characters
316*29dfba69SArmin Wolf  * without cutting of the last one.
317*29dfba69SArmin Wolf  */
318*29dfba69SArmin Wolf static u8 undersized_wmi_string[] = {
319*29dfba69SArmin Wolf 	0x03, 0x00, 0x00, 0x00, 0x00,
320*29dfba69SArmin Wolf };
321*29dfba69SArmin Wolf 
322*29dfba69SArmin Wolf static u8 non_ascii_wmi_string[] = {
323*29dfba69SArmin Wolf 	0x04, 0x00, 0xC4, 0x00, 0x00, 0x00,
324*29dfba69SArmin Wolf };
325*29dfba69SArmin Wolf 
326*29dfba69SArmin Wolf static const struct wmi_invalid_string_param wmi_invalid_string_params_array[] = {
327*29dfba69SArmin Wolf 	{
328*29dfba69SArmin Wolf 		.name = "empty_buffer",
329*29dfba69SArmin Wolf 		.buffer = {
330*29dfba69SArmin Wolf 			.length = 0,
331*29dfba69SArmin Wolf 			.data = ZERO_SIZE_PTR,
332*29dfba69SArmin Wolf 		},
333*29dfba69SArmin Wolf 
334*29dfba69SArmin Wolf 	},
335*29dfba69SArmin Wolf 	{
336*29dfba69SArmin Wolf 		.name = "oversized",
337*29dfba69SArmin Wolf 		.buffer = {
338*29dfba69SArmin Wolf 			.length = sizeof(oversized_wmi_string),
339*29dfba69SArmin Wolf 			.data = oversized_wmi_string,
340*29dfba69SArmin Wolf 		},
341*29dfba69SArmin Wolf 	},
342*29dfba69SArmin Wolf 	{
343*29dfba69SArmin Wolf 		.name = "undersized",
344*29dfba69SArmin Wolf 		.buffer = {
345*29dfba69SArmin Wolf 			.length = sizeof(undersized_wmi_string),
346*29dfba69SArmin Wolf 			.data = undersized_wmi_string,
347*29dfba69SArmin Wolf 		},
348*29dfba69SArmin Wolf 	},
349*29dfba69SArmin Wolf 	{
350*29dfba69SArmin Wolf 		.name = "non_ascii",
351*29dfba69SArmin Wolf 		.buffer = {
352*29dfba69SArmin Wolf 			.length = sizeof(non_ascii_wmi_string),
353*29dfba69SArmin Wolf 			.data = non_ascii_wmi_string,
354*29dfba69SArmin Wolf 		},
355*29dfba69SArmin Wolf 	},
356*29dfba69SArmin Wolf };
357*29dfba69SArmin Wolf 
358*29dfba69SArmin Wolf static void wmi_invalid_string_param_get_desc(const struct wmi_invalid_string_param *param,
359*29dfba69SArmin Wolf 					      char *desc)
360*29dfba69SArmin Wolf {
361*29dfba69SArmin Wolf 	strscpy(desc, param->name, KUNIT_PARAM_DESC_SIZE);
362*29dfba69SArmin Wolf }
363*29dfba69SArmin Wolf 
364*29dfba69SArmin Wolf KUNIT_ARRAY_PARAM(wmi_marshal_string_failure, wmi_invalid_string_params_array,
365*29dfba69SArmin Wolf 		  wmi_invalid_string_param_get_desc);
366*29dfba69SArmin Wolf 
367*29dfba69SArmin Wolf KUNIT_DEFINE_ACTION_WRAPPER(kfree_wrapper, kfree, const void *);
368*29dfba69SArmin Wolf 
369*29dfba69SArmin Wolf static void wmi_unmarshal_acpi_object_test(struct kunit *test)
370*29dfba69SArmin Wolf {
371*29dfba69SArmin Wolf 	const struct wmi_acpi_param *param = test->param_value;
372*29dfba69SArmin Wolf 	struct wmi_buffer result;
373*29dfba69SArmin Wolf 	int ret;
374*29dfba69SArmin Wolf 
375*29dfba69SArmin Wolf 	ret = wmi_unmarshal_acpi_object(&param->obj, &result);
376*29dfba69SArmin Wolf 	if (ret < 0)
377*29dfba69SArmin Wolf 		KUNIT_FAIL_AND_ABORT(test, "Unmarshalling of ACPI object failed\n");
378*29dfba69SArmin Wolf 
379*29dfba69SArmin Wolf 	kunit_add_action(test, kfree_wrapper, result.data);
380*29dfba69SArmin Wolf 
381*29dfba69SArmin Wolf 	KUNIT_EXPECT_TRUE(test, IS_ALIGNED((uintptr_t)result.data, 8));
382*29dfba69SArmin Wolf 	KUNIT_EXPECT_EQ(test, result.length, param->buffer.length);
383*29dfba69SArmin Wolf 	KUNIT_EXPECT_MEMEQ(test, result.data, param->buffer.data, result.length);
384*29dfba69SArmin Wolf }
385*29dfba69SArmin Wolf 
386*29dfba69SArmin Wolf static void wmi_unmarshal_acpi_object_failure_test(struct kunit *test)
387*29dfba69SArmin Wolf {
388*29dfba69SArmin Wolf 	const struct wmi_invalid_acpi_param *param = test->param_value;
389*29dfba69SArmin Wolf 	struct wmi_buffer result;
390*29dfba69SArmin Wolf 	int ret;
391*29dfba69SArmin Wolf 
392*29dfba69SArmin Wolf 	ret = wmi_unmarshal_acpi_object(&param->obj, &result);
393*29dfba69SArmin Wolf 	if (ret < 0)
394*29dfba69SArmin Wolf 		return;
395*29dfba69SArmin Wolf 
396*29dfba69SArmin Wolf 	kfree(result.data);
397*29dfba69SArmin Wolf 	KUNIT_FAIL(test, "Invalid ACPI object was not rejected\n");
398*29dfba69SArmin Wolf }
399*29dfba69SArmin Wolf 
400*29dfba69SArmin Wolf static void wmi_marshal_string_test(struct kunit *test)
401*29dfba69SArmin Wolf {
402*29dfba69SArmin Wolf 	const struct wmi_string_param *param = test->param_value;
403*29dfba69SArmin Wolf 	struct acpi_buffer result;
404*29dfba69SArmin Wolf 	int ret;
405*29dfba69SArmin Wolf 
406*29dfba69SArmin Wolf 	ret = wmi_marshal_string(&param->buffer, &result);
407*29dfba69SArmin Wolf 	if (ret < 0)
408*29dfba69SArmin Wolf 		KUNIT_FAIL_AND_ABORT(test, "Marshalling of WMI string failed\n");
409*29dfba69SArmin Wolf 
410*29dfba69SArmin Wolf 	kunit_add_action(test, kfree_wrapper, result.pointer);
411*29dfba69SArmin Wolf 
412*29dfba69SArmin Wolf 	KUNIT_EXPECT_EQ(test, result.length, strlen(param->string));
413*29dfba69SArmin Wolf 	KUNIT_EXPECT_STREQ(test, result.pointer, param->string);
414*29dfba69SArmin Wolf }
415*29dfba69SArmin Wolf 
416*29dfba69SArmin Wolf static void wmi_marshal_string_failure_test(struct kunit *test)
417*29dfba69SArmin Wolf {
418*29dfba69SArmin Wolf 	const struct wmi_invalid_string_param *param = test->param_value;
419*29dfba69SArmin Wolf 	struct acpi_buffer result;
420*29dfba69SArmin Wolf 	int ret;
421*29dfba69SArmin Wolf 
422*29dfba69SArmin Wolf 	ret = wmi_marshal_string(&param->buffer, &result);
423*29dfba69SArmin Wolf 	if (ret < 0)
424*29dfba69SArmin Wolf 		return;
425*29dfba69SArmin Wolf 
426*29dfba69SArmin Wolf 	kfree(result.pointer);
427*29dfba69SArmin Wolf 	KUNIT_FAIL(test, "Invalid string was not rejected\n");
428*29dfba69SArmin Wolf }
429*29dfba69SArmin Wolf 
430*29dfba69SArmin Wolf static struct kunit_case wmi_marshalling_test_cases[] = {
431*29dfba69SArmin Wolf 	KUNIT_CASE_PARAM(wmi_unmarshal_acpi_object_test,
432*29dfba69SArmin Wolf 			 wmi_unmarshal_acpi_object_gen_params),
433*29dfba69SArmin Wolf 	KUNIT_CASE_PARAM(wmi_marshal_string_test,
434*29dfba69SArmin Wolf 			 wmi_marshal_string_gen_params),
435*29dfba69SArmin Wolf 	KUNIT_CASE_PARAM(wmi_unmarshal_acpi_object_failure_test,
436*29dfba69SArmin Wolf 			 wmi_unmarshal_acpi_object_failure_gen_params),
437*29dfba69SArmin Wolf 	KUNIT_CASE_PARAM(wmi_marshal_string_failure_test,
438*29dfba69SArmin Wolf 			 wmi_marshal_string_failure_gen_params),
439*29dfba69SArmin Wolf 	{}
440*29dfba69SArmin Wolf };
441*29dfba69SArmin Wolf 
442*29dfba69SArmin Wolf static struct kunit_suite wmi_marshalling_test_suite = {
443*29dfba69SArmin Wolf 	.name = "wmi_marshalling",
444*29dfba69SArmin Wolf 	.test_cases = wmi_marshalling_test_cases,
445*29dfba69SArmin Wolf };
446*29dfba69SArmin Wolf 
447*29dfba69SArmin Wolf kunit_test_suite(wmi_marshalling_test_suite);
448*29dfba69SArmin Wolf 
449*29dfba69SArmin Wolf MODULE_AUTHOR("Armin Wolf <W_Armin@gmx.de>");
450*29dfba69SArmin Wolf MODULE_DESCRIPTION("KUnit test for the ACPI-WMI marshalling code");
451*29dfba69SArmin Wolf MODULE_IMPORT_NS("EXPORTED_FOR_KUNIT_TESTING");
452*29dfba69SArmin Wolf MODULE_LICENSE("GPL");
453