18c2ecf20Sopenharmony_ci// SPDX-License-Identifier: GPL-2.0-only
28c2ecf20Sopenharmony_ci/*
38c2ecf20Sopenharmony_ci * Test cases for printf facility.
48c2ecf20Sopenharmony_ci */
58c2ecf20Sopenharmony_ci
68c2ecf20Sopenharmony_ci#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
78c2ecf20Sopenharmony_ci
88c2ecf20Sopenharmony_ci#include <linux/init.h>
98c2ecf20Sopenharmony_ci#include <linux/kernel.h>
108c2ecf20Sopenharmony_ci#include <linux/module.h>
118c2ecf20Sopenharmony_ci#include <linux/printk.h>
128c2ecf20Sopenharmony_ci#include <linux/random.h>
138c2ecf20Sopenharmony_ci#include <linux/rtc.h>
148c2ecf20Sopenharmony_ci#include <linux/slab.h>
158c2ecf20Sopenharmony_ci#include <linux/string.h>
168c2ecf20Sopenharmony_ci
178c2ecf20Sopenharmony_ci#include <linux/bitmap.h>
188c2ecf20Sopenharmony_ci#include <linux/dcache.h>
198c2ecf20Sopenharmony_ci#include <linux/socket.h>
208c2ecf20Sopenharmony_ci#include <linux/in.h>
218c2ecf20Sopenharmony_ci
228c2ecf20Sopenharmony_ci#include <linux/gfp.h>
238c2ecf20Sopenharmony_ci#include <linux/mm.h>
248c2ecf20Sopenharmony_ci
258c2ecf20Sopenharmony_ci#include <linux/property.h>
268c2ecf20Sopenharmony_ci
278c2ecf20Sopenharmony_ci#include "../tools/testing/selftests/kselftest_module.h"
288c2ecf20Sopenharmony_ci
298c2ecf20Sopenharmony_ci#define BUF_SIZE 256
308c2ecf20Sopenharmony_ci#define PAD_SIZE 16
318c2ecf20Sopenharmony_ci#define FILL_CHAR '$'
328c2ecf20Sopenharmony_ci
338c2ecf20Sopenharmony_cistatic unsigned total_tests __initdata;
348c2ecf20Sopenharmony_cistatic unsigned failed_tests __initdata;
358c2ecf20Sopenharmony_cistatic char *test_buffer __initdata;
368c2ecf20Sopenharmony_cistatic char *alloced_buffer __initdata;
378c2ecf20Sopenharmony_ci
388c2ecf20Sopenharmony_cistatic int __printf(4, 0) __init
398c2ecf20Sopenharmony_cido_test(int bufsize, const char *expect, int elen,
408c2ecf20Sopenharmony_ci	const char *fmt, va_list ap)
418c2ecf20Sopenharmony_ci{
428c2ecf20Sopenharmony_ci	va_list aq;
438c2ecf20Sopenharmony_ci	int ret, written;
448c2ecf20Sopenharmony_ci
458c2ecf20Sopenharmony_ci	total_tests++;
468c2ecf20Sopenharmony_ci
478c2ecf20Sopenharmony_ci	memset(alloced_buffer, FILL_CHAR, BUF_SIZE + 2*PAD_SIZE);
488c2ecf20Sopenharmony_ci	va_copy(aq, ap);
498c2ecf20Sopenharmony_ci	ret = vsnprintf(test_buffer, bufsize, fmt, aq);
508c2ecf20Sopenharmony_ci	va_end(aq);
518c2ecf20Sopenharmony_ci
528c2ecf20Sopenharmony_ci	if (ret != elen) {
538c2ecf20Sopenharmony_ci		pr_warn("vsnprintf(buf, %d, \"%s\", ...) returned %d, expected %d\n",
548c2ecf20Sopenharmony_ci			bufsize, fmt, ret, elen);
558c2ecf20Sopenharmony_ci		return 1;
568c2ecf20Sopenharmony_ci	}
578c2ecf20Sopenharmony_ci
588c2ecf20Sopenharmony_ci	if (memchr_inv(alloced_buffer, FILL_CHAR, PAD_SIZE)) {
598c2ecf20Sopenharmony_ci		pr_warn("vsnprintf(buf, %d, \"%s\", ...) wrote before buffer\n", bufsize, fmt);
608c2ecf20Sopenharmony_ci		return 1;
618c2ecf20Sopenharmony_ci	}
628c2ecf20Sopenharmony_ci
638c2ecf20Sopenharmony_ci	if (!bufsize) {
648c2ecf20Sopenharmony_ci		if (memchr_inv(test_buffer, FILL_CHAR, BUF_SIZE + PAD_SIZE)) {
658c2ecf20Sopenharmony_ci			pr_warn("vsnprintf(buf, 0, \"%s\", ...) wrote to buffer\n",
668c2ecf20Sopenharmony_ci				fmt);
678c2ecf20Sopenharmony_ci			return 1;
688c2ecf20Sopenharmony_ci		}
698c2ecf20Sopenharmony_ci		return 0;
708c2ecf20Sopenharmony_ci	}
718c2ecf20Sopenharmony_ci
728c2ecf20Sopenharmony_ci	written = min(bufsize-1, elen);
738c2ecf20Sopenharmony_ci	if (test_buffer[written]) {
748c2ecf20Sopenharmony_ci		pr_warn("vsnprintf(buf, %d, \"%s\", ...) did not nul-terminate buffer\n",
758c2ecf20Sopenharmony_ci			bufsize, fmt);
768c2ecf20Sopenharmony_ci		return 1;
778c2ecf20Sopenharmony_ci	}
788c2ecf20Sopenharmony_ci
798c2ecf20Sopenharmony_ci	if (memchr_inv(test_buffer + written + 1, FILL_CHAR, BUF_SIZE + PAD_SIZE - (written + 1))) {
808c2ecf20Sopenharmony_ci		pr_warn("vsnprintf(buf, %d, \"%s\", ...) wrote beyond the nul-terminator\n",
818c2ecf20Sopenharmony_ci			bufsize, fmt);
828c2ecf20Sopenharmony_ci		return 1;
838c2ecf20Sopenharmony_ci	}
848c2ecf20Sopenharmony_ci
858c2ecf20Sopenharmony_ci	if (memcmp(test_buffer, expect, written)) {
868c2ecf20Sopenharmony_ci		pr_warn("vsnprintf(buf, %d, \"%s\", ...) wrote '%s', expected '%.*s'\n",
878c2ecf20Sopenharmony_ci			bufsize, fmt, test_buffer, written, expect);
888c2ecf20Sopenharmony_ci		return 1;
898c2ecf20Sopenharmony_ci	}
908c2ecf20Sopenharmony_ci	return 0;
918c2ecf20Sopenharmony_ci}
928c2ecf20Sopenharmony_ci
938c2ecf20Sopenharmony_cistatic void __printf(3, 4) __init
948c2ecf20Sopenharmony_ci__test(const char *expect, int elen, const char *fmt, ...)
958c2ecf20Sopenharmony_ci{
968c2ecf20Sopenharmony_ci	va_list ap;
978c2ecf20Sopenharmony_ci	int rand;
988c2ecf20Sopenharmony_ci	char *p;
998c2ecf20Sopenharmony_ci
1008c2ecf20Sopenharmony_ci	if (elen >= BUF_SIZE) {
1018c2ecf20Sopenharmony_ci		pr_err("error in test suite: expected output length %d too long. Format was '%s'.\n",
1028c2ecf20Sopenharmony_ci		       elen, fmt);
1038c2ecf20Sopenharmony_ci		failed_tests++;
1048c2ecf20Sopenharmony_ci		return;
1058c2ecf20Sopenharmony_ci	}
1068c2ecf20Sopenharmony_ci
1078c2ecf20Sopenharmony_ci	va_start(ap, fmt);
1088c2ecf20Sopenharmony_ci
1098c2ecf20Sopenharmony_ci	/*
1108c2ecf20Sopenharmony_ci	 * Every fmt+args is subjected to four tests: Three where we
1118c2ecf20Sopenharmony_ci	 * tell vsnprintf varying buffer sizes (plenty, not quite
1128c2ecf20Sopenharmony_ci	 * enough and 0), and then we also test that kvasprintf would
1138c2ecf20Sopenharmony_ci	 * be able to print it as expected.
1148c2ecf20Sopenharmony_ci	 */
1158c2ecf20Sopenharmony_ci	failed_tests += do_test(BUF_SIZE, expect, elen, fmt, ap);
1168c2ecf20Sopenharmony_ci	rand = 1 + prandom_u32_max(elen+1);
1178c2ecf20Sopenharmony_ci	/* Since elen < BUF_SIZE, we have 1 <= rand <= BUF_SIZE. */
1188c2ecf20Sopenharmony_ci	failed_tests += do_test(rand, expect, elen, fmt, ap);
1198c2ecf20Sopenharmony_ci	failed_tests += do_test(0, expect, elen, fmt, ap);
1208c2ecf20Sopenharmony_ci
1218c2ecf20Sopenharmony_ci	p = kvasprintf(GFP_KERNEL, fmt, ap);
1228c2ecf20Sopenharmony_ci	if (p) {
1238c2ecf20Sopenharmony_ci		total_tests++;
1248c2ecf20Sopenharmony_ci		if (memcmp(p, expect, elen+1)) {
1258c2ecf20Sopenharmony_ci			pr_warn("kvasprintf(..., \"%s\", ...) returned '%s', expected '%s'\n",
1268c2ecf20Sopenharmony_ci				fmt, p, expect);
1278c2ecf20Sopenharmony_ci			failed_tests++;
1288c2ecf20Sopenharmony_ci		}
1298c2ecf20Sopenharmony_ci		kfree(p);
1308c2ecf20Sopenharmony_ci	}
1318c2ecf20Sopenharmony_ci	va_end(ap);
1328c2ecf20Sopenharmony_ci}
1338c2ecf20Sopenharmony_ci
1348c2ecf20Sopenharmony_ci#define test(expect, fmt, ...)					\
1358c2ecf20Sopenharmony_ci	__test(expect, strlen(expect), fmt, ##__VA_ARGS__)
1368c2ecf20Sopenharmony_ci
1378c2ecf20Sopenharmony_cistatic void __init
1388c2ecf20Sopenharmony_citest_basic(void)
1398c2ecf20Sopenharmony_ci{
1408c2ecf20Sopenharmony_ci	/* Work around annoying "warning: zero-length gnu_printf format string". */
1418c2ecf20Sopenharmony_ci	char nul = '\0';
1428c2ecf20Sopenharmony_ci
1438c2ecf20Sopenharmony_ci	test("", &nul);
1448c2ecf20Sopenharmony_ci	test("100%", "100%%");
1458c2ecf20Sopenharmony_ci	test("xxx%yyy", "xxx%cyyy", '%');
1468c2ecf20Sopenharmony_ci	__test("xxx\0yyy", 7, "xxx%cyyy", '\0');
1478c2ecf20Sopenharmony_ci}
1488c2ecf20Sopenharmony_ci
1498c2ecf20Sopenharmony_cistatic void __init
1508c2ecf20Sopenharmony_citest_number(void)
1518c2ecf20Sopenharmony_ci{
1528c2ecf20Sopenharmony_ci	test("0x1234abcd  ", "%#-12x", 0x1234abcd);
1538c2ecf20Sopenharmony_ci	test("  0x1234abcd", "%#12x", 0x1234abcd);
1548c2ecf20Sopenharmony_ci	test("0|001| 12|+123| 1234|-123|-1234", "%d|%03d|%3d|%+d|% d|%+d|% d", 0, 1, 12, 123, 1234, -123, -1234);
1558c2ecf20Sopenharmony_ci	test("0|1|1|128|255", "%hhu|%hhu|%hhu|%hhu|%hhu", 0, 1, 257, 128, -1);
1568c2ecf20Sopenharmony_ci	test("0|1|1|-128|-1", "%hhd|%hhd|%hhd|%hhd|%hhd", 0, 1, 257, 128, -1);
1578c2ecf20Sopenharmony_ci	test("2015122420151225", "%ho%ho%#ho", 1037, 5282, -11627);
1588c2ecf20Sopenharmony_ci	/*
1598c2ecf20Sopenharmony_ci	 * POSIX/C99: »The result of converting zero with an explicit
1608c2ecf20Sopenharmony_ci	 * precision of zero shall be no characters.« Hence the output
1618c2ecf20Sopenharmony_ci	 * from the below test should really be "00|0||| ". However,
1628c2ecf20Sopenharmony_ci	 * the kernel's printf also produces a single 0 in that
1638c2ecf20Sopenharmony_ci	 * case. This test case simply documents the current
1648c2ecf20Sopenharmony_ci	 * behaviour.
1658c2ecf20Sopenharmony_ci	 */
1668c2ecf20Sopenharmony_ci	test("00|0|0|0|0", "%.2d|%.1d|%.0d|%.*d|%1.0d", 0, 0, 0, 0, 0, 0);
1678c2ecf20Sopenharmony_ci#ifndef __CHAR_UNSIGNED__
1688c2ecf20Sopenharmony_ci	{
1698c2ecf20Sopenharmony_ci		/*
1708c2ecf20Sopenharmony_ci		 * Passing a 'char' to a %02x specifier doesn't do
1718c2ecf20Sopenharmony_ci		 * what was presumably the intention when char is
1728c2ecf20Sopenharmony_ci		 * signed and the value is negative. One must either &
1738c2ecf20Sopenharmony_ci		 * with 0xff or cast to u8.
1748c2ecf20Sopenharmony_ci		 */
1758c2ecf20Sopenharmony_ci		char val = -16;
1768c2ecf20Sopenharmony_ci		test("0xfffffff0|0xf0|0xf0", "%#02x|%#02x|%#02x", val, val & 0xff, (u8)val);
1778c2ecf20Sopenharmony_ci	}
1788c2ecf20Sopenharmony_ci#endif
1798c2ecf20Sopenharmony_ci}
1808c2ecf20Sopenharmony_ci
1818c2ecf20Sopenharmony_cistatic void __init
1828c2ecf20Sopenharmony_citest_string(void)
1838c2ecf20Sopenharmony_ci{
1848c2ecf20Sopenharmony_ci	test("", "%s%.0s", "", "123");
1858c2ecf20Sopenharmony_ci	test("ABCD|abc|123", "%s|%.3s|%.*s", "ABCD", "abcdef", 3, "123456");
1868c2ecf20Sopenharmony_ci	test("1  |  2|3  |  4|5  ", "%-3s|%3s|%-*s|%*s|%*s", "1", "2", 3, "3", 3, "4", -3, "5");
1878c2ecf20Sopenharmony_ci	test("1234      ", "%-10.4s", "123456");
1888c2ecf20Sopenharmony_ci	test("      1234", "%10.4s", "123456");
1898c2ecf20Sopenharmony_ci	/*
1908c2ecf20Sopenharmony_ci	 * POSIX and C99 say that a negative precision (which is only
1918c2ecf20Sopenharmony_ci	 * possible to pass via a * argument) should be treated as if
1928c2ecf20Sopenharmony_ci	 * the precision wasn't present, and that if the precision is
1938c2ecf20Sopenharmony_ci	 * omitted (as in %.s), the precision should be taken to be
1948c2ecf20Sopenharmony_ci	 * 0. However, the kernel's printf behave exactly opposite,
1958c2ecf20Sopenharmony_ci	 * treating a negative precision as 0 and treating an omitted
1968c2ecf20Sopenharmony_ci	 * precision specifier as if no precision was given.
1978c2ecf20Sopenharmony_ci	 *
1988c2ecf20Sopenharmony_ci	 * These test cases document the current behaviour; should
1998c2ecf20Sopenharmony_ci	 * anyone ever feel the need to follow the standards more
2008c2ecf20Sopenharmony_ci	 * closely, this can be revisited.
2018c2ecf20Sopenharmony_ci	 */
2028c2ecf20Sopenharmony_ci	test("    ", "%4.*s", -5, "123456");
2038c2ecf20Sopenharmony_ci	test("123456", "%.s", "123456");
2048c2ecf20Sopenharmony_ci	test("a||", "%.s|%.0s|%.*s", "a", "b", 0, "c");
2058c2ecf20Sopenharmony_ci	test("a  |   |   ", "%-3.s|%-3.0s|%-3.*s", "a", "b", 0, "c");
2068c2ecf20Sopenharmony_ci}
2078c2ecf20Sopenharmony_ci
2088c2ecf20Sopenharmony_ci#define PLAIN_BUF_SIZE 64	/* leave some space so we don't oops */
2098c2ecf20Sopenharmony_ci
2108c2ecf20Sopenharmony_ci#if BITS_PER_LONG == 64
2118c2ecf20Sopenharmony_ci
2128c2ecf20Sopenharmony_ci#define PTR_WIDTH 16
2138c2ecf20Sopenharmony_ci#define PTR ((void *)0xffff0123456789abUL)
2148c2ecf20Sopenharmony_ci#define PTR_STR "ffff0123456789ab"
2158c2ecf20Sopenharmony_ci#define PTR_VAL_NO_CRNG "(____ptrval____)"
2168c2ecf20Sopenharmony_ci#define ZEROS "00000000"	/* hex 32 zero bits */
2178c2ecf20Sopenharmony_ci#define ONES "ffffffff"		/* hex 32 one bits */
2188c2ecf20Sopenharmony_ci
2198c2ecf20Sopenharmony_cistatic int __init
2208c2ecf20Sopenharmony_ciplain_format(void)
2218c2ecf20Sopenharmony_ci{
2228c2ecf20Sopenharmony_ci	char buf[PLAIN_BUF_SIZE];
2238c2ecf20Sopenharmony_ci	int nchars;
2248c2ecf20Sopenharmony_ci
2258c2ecf20Sopenharmony_ci	nchars = snprintf(buf, PLAIN_BUF_SIZE, "%p", PTR);
2268c2ecf20Sopenharmony_ci
2278c2ecf20Sopenharmony_ci	if (nchars != PTR_WIDTH)
2288c2ecf20Sopenharmony_ci		return -1;
2298c2ecf20Sopenharmony_ci
2308c2ecf20Sopenharmony_ci	if (strncmp(buf, PTR_VAL_NO_CRNG, PTR_WIDTH) == 0) {
2318c2ecf20Sopenharmony_ci		pr_warn("crng possibly not yet initialized. plain 'p' buffer contains \"%s\"",
2328c2ecf20Sopenharmony_ci			PTR_VAL_NO_CRNG);
2338c2ecf20Sopenharmony_ci		return 0;
2348c2ecf20Sopenharmony_ci	}
2358c2ecf20Sopenharmony_ci
2368c2ecf20Sopenharmony_ci	if (strncmp(buf, ZEROS, strlen(ZEROS)) != 0)
2378c2ecf20Sopenharmony_ci		return -1;
2388c2ecf20Sopenharmony_ci
2398c2ecf20Sopenharmony_ci	return 0;
2408c2ecf20Sopenharmony_ci}
2418c2ecf20Sopenharmony_ci
2428c2ecf20Sopenharmony_ci#else
2438c2ecf20Sopenharmony_ci
2448c2ecf20Sopenharmony_ci#define PTR_WIDTH 8
2458c2ecf20Sopenharmony_ci#define PTR ((void *)0x456789ab)
2468c2ecf20Sopenharmony_ci#define PTR_STR "456789ab"
2478c2ecf20Sopenharmony_ci#define PTR_VAL_NO_CRNG "(ptrval)"
2488c2ecf20Sopenharmony_ci#define ZEROS ""
2498c2ecf20Sopenharmony_ci#define ONES ""
2508c2ecf20Sopenharmony_ci
2518c2ecf20Sopenharmony_cistatic int __init
2528c2ecf20Sopenharmony_ciplain_format(void)
2538c2ecf20Sopenharmony_ci{
2548c2ecf20Sopenharmony_ci	/* Format is implicitly tested for 32 bit machines by plain_hash() */
2558c2ecf20Sopenharmony_ci	return 0;
2568c2ecf20Sopenharmony_ci}
2578c2ecf20Sopenharmony_ci
2588c2ecf20Sopenharmony_ci#endif	/* BITS_PER_LONG == 64 */
2598c2ecf20Sopenharmony_ci
2608c2ecf20Sopenharmony_cistatic int __init
2618c2ecf20Sopenharmony_ciplain_hash_to_buffer(const void *p, char *buf, size_t len)
2628c2ecf20Sopenharmony_ci{
2638c2ecf20Sopenharmony_ci	int nchars;
2648c2ecf20Sopenharmony_ci
2658c2ecf20Sopenharmony_ci	nchars = snprintf(buf, len, "%p", p);
2668c2ecf20Sopenharmony_ci
2678c2ecf20Sopenharmony_ci	if (nchars != PTR_WIDTH)
2688c2ecf20Sopenharmony_ci		return -1;
2698c2ecf20Sopenharmony_ci
2708c2ecf20Sopenharmony_ci	if (strncmp(buf, PTR_VAL_NO_CRNG, PTR_WIDTH) == 0) {
2718c2ecf20Sopenharmony_ci		pr_warn("crng possibly not yet initialized. plain 'p' buffer contains \"%s\"",
2728c2ecf20Sopenharmony_ci			PTR_VAL_NO_CRNG);
2738c2ecf20Sopenharmony_ci		return 0;
2748c2ecf20Sopenharmony_ci	}
2758c2ecf20Sopenharmony_ci
2768c2ecf20Sopenharmony_ci	return 0;
2778c2ecf20Sopenharmony_ci}
2788c2ecf20Sopenharmony_ci
2798c2ecf20Sopenharmony_cistatic int __init
2808c2ecf20Sopenharmony_ciplain_hash(void)
2818c2ecf20Sopenharmony_ci{
2828c2ecf20Sopenharmony_ci	char buf[PLAIN_BUF_SIZE];
2838c2ecf20Sopenharmony_ci	int ret;
2848c2ecf20Sopenharmony_ci
2858c2ecf20Sopenharmony_ci	ret = plain_hash_to_buffer(PTR, buf, PLAIN_BUF_SIZE);
2868c2ecf20Sopenharmony_ci	if (ret)
2878c2ecf20Sopenharmony_ci		return ret;
2888c2ecf20Sopenharmony_ci
2898c2ecf20Sopenharmony_ci	if (strncmp(buf, PTR_STR, PTR_WIDTH) == 0)
2908c2ecf20Sopenharmony_ci		return -1;
2918c2ecf20Sopenharmony_ci
2928c2ecf20Sopenharmony_ci	return 0;
2938c2ecf20Sopenharmony_ci}
2948c2ecf20Sopenharmony_ci
2958c2ecf20Sopenharmony_ci/*
2968c2ecf20Sopenharmony_ci * We can't use test() to test %p because we don't know what output to expect
2978c2ecf20Sopenharmony_ci * after an address is hashed.
2988c2ecf20Sopenharmony_ci */
2998c2ecf20Sopenharmony_cistatic void __init
3008c2ecf20Sopenharmony_ciplain(void)
3018c2ecf20Sopenharmony_ci{
3028c2ecf20Sopenharmony_ci	int err;
3038c2ecf20Sopenharmony_ci
3048c2ecf20Sopenharmony_ci	err = plain_hash();
3058c2ecf20Sopenharmony_ci	if (err) {
3068c2ecf20Sopenharmony_ci		pr_warn("plain 'p' does not appear to be hashed\n");
3078c2ecf20Sopenharmony_ci		failed_tests++;
3088c2ecf20Sopenharmony_ci		return;
3098c2ecf20Sopenharmony_ci	}
3108c2ecf20Sopenharmony_ci
3118c2ecf20Sopenharmony_ci	err = plain_format();
3128c2ecf20Sopenharmony_ci	if (err) {
3138c2ecf20Sopenharmony_ci		pr_warn("hashing plain 'p' has unexpected format\n");
3148c2ecf20Sopenharmony_ci		failed_tests++;
3158c2ecf20Sopenharmony_ci	}
3168c2ecf20Sopenharmony_ci}
3178c2ecf20Sopenharmony_ci
3188c2ecf20Sopenharmony_cistatic void __init
3198c2ecf20Sopenharmony_citest_hashed(const char *fmt, const void *p)
3208c2ecf20Sopenharmony_ci{
3218c2ecf20Sopenharmony_ci	char buf[PLAIN_BUF_SIZE];
3228c2ecf20Sopenharmony_ci	int ret;
3238c2ecf20Sopenharmony_ci
3248c2ecf20Sopenharmony_ci	/*
3258c2ecf20Sopenharmony_ci	 * No need to increase failed test counter since this is assumed
3268c2ecf20Sopenharmony_ci	 * to be called after plain().
3278c2ecf20Sopenharmony_ci	 */
3288c2ecf20Sopenharmony_ci	ret = plain_hash_to_buffer(p, buf, PLAIN_BUF_SIZE);
3298c2ecf20Sopenharmony_ci	if (ret)
3308c2ecf20Sopenharmony_ci		return;
3318c2ecf20Sopenharmony_ci
3328c2ecf20Sopenharmony_ci	test(buf, fmt, p);
3338c2ecf20Sopenharmony_ci}
3348c2ecf20Sopenharmony_ci
3358c2ecf20Sopenharmony_ci/*
3368c2ecf20Sopenharmony_ci * NULL pointers aren't hashed.
3378c2ecf20Sopenharmony_ci */
3388c2ecf20Sopenharmony_cistatic void __init
3398c2ecf20Sopenharmony_cinull_pointer(void)
3408c2ecf20Sopenharmony_ci{
3418c2ecf20Sopenharmony_ci	test(ZEROS "00000000", "%p", NULL);
3428c2ecf20Sopenharmony_ci	test(ZEROS "00000000", "%px", NULL);
3438c2ecf20Sopenharmony_ci	test("(null)", "%pE", NULL);
3448c2ecf20Sopenharmony_ci}
3458c2ecf20Sopenharmony_ci
3468c2ecf20Sopenharmony_ci/*
3478c2ecf20Sopenharmony_ci * Error pointers aren't hashed.
3488c2ecf20Sopenharmony_ci */
3498c2ecf20Sopenharmony_cistatic void __init
3508c2ecf20Sopenharmony_cierror_pointer(void)
3518c2ecf20Sopenharmony_ci{
3528c2ecf20Sopenharmony_ci	test(ONES "fffffff5", "%p", ERR_PTR(-11));
3538c2ecf20Sopenharmony_ci	test(ONES "fffffff5", "%px", ERR_PTR(-11));
3548c2ecf20Sopenharmony_ci	test("(efault)", "%pE", ERR_PTR(-11));
3558c2ecf20Sopenharmony_ci}
3568c2ecf20Sopenharmony_ci
3578c2ecf20Sopenharmony_ci#define PTR_INVALID ((void *)0x000000ab)
3588c2ecf20Sopenharmony_ci
3598c2ecf20Sopenharmony_cistatic void __init
3608c2ecf20Sopenharmony_ciinvalid_pointer(void)
3618c2ecf20Sopenharmony_ci{
3628c2ecf20Sopenharmony_ci	test_hashed("%p", PTR_INVALID);
3638c2ecf20Sopenharmony_ci	test(ZEROS "000000ab", "%px", PTR_INVALID);
3648c2ecf20Sopenharmony_ci	test("(efault)", "%pE", PTR_INVALID);
3658c2ecf20Sopenharmony_ci}
3668c2ecf20Sopenharmony_ci
3678c2ecf20Sopenharmony_cistatic void __init
3688c2ecf20Sopenharmony_cisymbol_ptr(void)
3698c2ecf20Sopenharmony_ci{
3708c2ecf20Sopenharmony_ci}
3718c2ecf20Sopenharmony_ci
3728c2ecf20Sopenharmony_cistatic void __init
3738c2ecf20Sopenharmony_cikernel_ptr(void)
3748c2ecf20Sopenharmony_ci{
3758c2ecf20Sopenharmony_ci	/* We can't test this without access to kptr_restrict. */
3768c2ecf20Sopenharmony_ci}
3778c2ecf20Sopenharmony_ci
3788c2ecf20Sopenharmony_cistatic void __init
3798c2ecf20Sopenharmony_cistruct_resource(void)
3808c2ecf20Sopenharmony_ci{
3818c2ecf20Sopenharmony_ci}
3828c2ecf20Sopenharmony_ci
3838c2ecf20Sopenharmony_cistatic void __init
3848c2ecf20Sopenharmony_ciaddr(void)
3858c2ecf20Sopenharmony_ci{
3868c2ecf20Sopenharmony_ci}
3878c2ecf20Sopenharmony_ci
3888c2ecf20Sopenharmony_cistatic void __init
3898c2ecf20Sopenharmony_ciescaped_str(void)
3908c2ecf20Sopenharmony_ci{
3918c2ecf20Sopenharmony_ci}
3928c2ecf20Sopenharmony_ci
3938c2ecf20Sopenharmony_cistatic void __init
3948c2ecf20Sopenharmony_cihex_string(void)
3958c2ecf20Sopenharmony_ci{
3968c2ecf20Sopenharmony_ci	const char buf[3] = {0xc0, 0xff, 0xee};
3978c2ecf20Sopenharmony_ci
3988c2ecf20Sopenharmony_ci	test("c0 ff ee|c0:ff:ee|c0-ff-ee|c0ffee",
3998c2ecf20Sopenharmony_ci	     "%3ph|%3phC|%3phD|%3phN", buf, buf, buf, buf);
4008c2ecf20Sopenharmony_ci	test("c0 ff ee|c0:ff:ee|c0-ff-ee|c0ffee",
4018c2ecf20Sopenharmony_ci	     "%*ph|%*phC|%*phD|%*phN", 3, buf, 3, buf, 3, buf, 3, buf);
4028c2ecf20Sopenharmony_ci}
4038c2ecf20Sopenharmony_ci
4048c2ecf20Sopenharmony_cistatic void __init
4058c2ecf20Sopenharmony_cimac(void)
4068c2ecf20Sopenharmony_ci{
4078c2ecf20Sopenharmony_ci	const u8 addr[6] = {0x2d, 0x48, 0xd6, 0xfc, 0x7a, 0x05};
4088c2ecf20Sopenharmony_ci
4098c2ecf20Sopenharmony_ci	test("2d:48:d6:fc:7a:05", "%pM", addr);
4108c2ecf20Sopenharmony_ci	test("05:7a:fc:d6:48:2d", "%pMR", addr);
4118c2ecf20Sopenharmony_ci	test("2d-48-d6-fc-7a-05", "%pMF", addr);
4128c2ecf20Sopenharmony_ci	test("2d48d6fc7a05", "%pm", addr);
4138c2ecf20Sopenharmony_ci	test("057afcd6482d", "%pmR", addr);
4148c2ecf20Sopenharmony_ci}
4158c2ecf20Sopenharmony_ci
4168c2ecf20Sopenharmony_cistatic void __init
4178c2ecf20Sopenharmony_ciip4(void)
4188c2ecf20Sopenharmony_ci{
4198c2ecf20Sopenharmony_ci	struct sockaddr_in sa;
4208c2ecf20Sopenharmony_ci
4218c2ecf20Sopenharmony_ci	sa.sin_family = AF_INET;
4228c2ecf20Sopenharmony_ci	sa.sin_port = cpu_to_be16(12345);
4238c2ecf20Sopenharmony_ci	sa.sin_addr.s_addr = cpu_to_be32(0x7f000001);
4248c2ecf20Sopenharmony_ci
4258c2ecf20Sopenharmony_ci	test("127.000.000.001|127.0.0.1", "%pi4|%pI4", &sa.sin_addr, &sa.sin_addr);
4268c2ecf20Sopenharmony_ci	test("127.000.000.001|127.0.0.1", "%piS|%pIS", &sa, &sa);
4278c2ecf20Sopenharmony_ci	sa.sin_addr.s_addr = cpu_to_be32(0x01020304);
4288c2ecf20Sopenharmony_ci	test("001.002.003.004:12345|1.2.3.4:12345", "%piSp|%pISp", &sa, &sa);
4298c2ecf20Sopenharmony_ci}
4308c2ecf20Sopenharmony_ci
4318c2ecf20Sopenharmony_cistatic void __init
4328c2ecf20Sopenharmony_ciip6(void)
4338c2ecf20Sopenharmony_ci{
4348c2ecf20Sopenharmony_ci}
4358c2ecf20Sopenharmony_ci
4368c2ecf20Sopenharmony_cistatic void __init
4378c2ecf20Sopenharmony_ciip(void)
4388c2ecf20Sopenharmony_ci{
4398c2ecf20Sopenharmony_ci	ip4();
4408c2ecf20Sopenharmony_ci	ip6();
4418c2ecf20Sopenharmony_ci}
4428c2ecf20Sopenharmony_ci
4438c2ecf20Sopenharmony_cistatic void __init
4448c2ecf20Sopenharmony_ciuuid(void)
4458c2ecf20Sopenharmony_ci{
4468c2ecf20Sopenharmony_ci	const char uuid[16] = {0x0, 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7,
4478c2ecf20Sopenharmony_ci			       0x8, 0x9, 0xa, 0xb, 0xc, 0xd, 0xe, 0xf};
4488c2ecf20Sopenharmony_ci
4498c2ecf20Sopenharmony_ci	test("00010203-0405-0607-0809-0a0b0c0d0e0f", "%pUb", uuid);
4508c2ecf20Sopenharmony_ci	test("00010203-0405-0607-0809-0A0B0C0D0E0F", "%pUB", uuid);
4518c2ecf20Sopenharmony_ci	test("03020100-0504-0706-0809-0a0b0c0d0e0f", "%pUl", uuid);
4528c2ecf20Sopenharmony_ci	test("03020100-0504-0706-0809-0A0B0C0D0E0F", "%pUL", uuid);
4538c2ecf20Sopenharmony_ci}
4548c2ecf20Sopenharmony_ci
4558c2ecf20Sopenharmony_cistatic struct dentry test_dentry[4] __initdata = {
4568c2ecf20Sopenharmony_ci	{ .d_parent = &test_dentry[0],
4578c2ecf20Sopenharmony_ci	  .d_name = QSTR_INIT(test_dentry[0].d_iname, 3),
4588c2ecf20Sopenharmony_ci	  .d_iname = "foo" },
4598c2ecf20Sopenharmony_ci	{ .d_parent = &test_dentry[0],
4608c2ecf20Sopenharmony_ci	  .d_name = QSTR_INIT(test_dentry[1].d_iname, 5),
4618c2ecf20Sopenharmony_ci	  .d_iname = "bravo" },
4628c2ecf20Sopenharmony_ci	{ .d_parent = &test_dentry[1],
4638c2ecf20Sopenharmony_ci	  .d_name = QSTR_INIT(test_dentry[2].d_iname, 4),
4648c2ecf20Sopenharmony_ci	  .d_iname = "alfa" },
4658c2ecf20Sopenharmony_ci	{ .d_parent = &test_dentry[2],
4668c2ecf20Sopenharmony_ci	  .d_name = QSTR_INIT(test_dentry[3].d_iname, 5),
4678c2ecf20Sopenharmony_ci	  .d_iname = "romeo" },
4688c2ecf20Sopenharmony_ci};
4698c2ecf20Sopenharmony_ci
4708c2ecf20Sopenharmony_cistatic void __init
4718c2ecf20Sopenharmony_cidentry(void)
4728c2ecf20Sopenharmony_ci{
4738c2ecf20Sopenharmony_ci	test("foo", "%pd", &test_dentry[0]);
4748c2ecf20Sopenharmony_ci	test("foo", "%pd2", &test_dentry[0]);
4758c2ecf20Sopenharmony_ci
4768c2ecf20Sopenharmony_ci	test("(null)", "%pd", NULL);
4778c2ecf20Sopenharmony_ci	test("(efault)", "%pd", PTR_INVALID);
4788c2ecf20Sopenharmony_ci	test("(null)", "%pD", NULL);
4798c2ecf20Sopenharmony_ci	test("(efault)", "%pD", PTR_INVALID);
4808c2ecf20Sopenharmony_ci
4818c2ecf20Sopenharmony_ci	test("romeo", "%pd", &test_dentry[3]);
4828c2ecf20Sopenharmony_ci	test("alfa/romeo", "%pd2", &test_dentry[3]);
4838c2ecf20Sopenharmony_ci	test("bravo/alfa/romeo", "%pd3", &test_dentry[3]);
4848c2ecf20Sopenharmony_ci	test("/bravo/alfa/romeo", "%pd4", &test_dentry[3]);
4858c2ecf20Sopenharmony_ci	test("/bravo/alfa", "%pd4", &test_dentry[2]);
4868c2ecf20Sopenharmony_ci
4878c2ecf20Sopenharmony_ci	test("bravo/alfa  |bravo/alfa  ", "%-12pd2|%*pd2", &test_dentry[2], -12, &test_dentry[2]);
4888c2ecf20Sopenharmony_ci	test("  bravo/alfa|  bravo/alfa", "%12pd2|%*pd2", &test_dentry[2], 12, &test_dentry[2]);
4898c2ecf20Sopenharmony_ci}
4908c2ecf20Sopenharmony_ci
4918c2ecf20Sopenharmony_cistatic void __init
4928c2ecf20Sopenharmony_cistruct_va_format(void)
4938c2ecf20Sopenharmony_ci{
4948c2ecf20Sopenharmony_ci}
4958c2ecf20Sopenharmony_ci
4968c2ecf20Sopenharmony_cistatic void __init
4978c2ecf20Sopenharmony_citime_and_date(void)
4988c2ecf20Sopenharmony_ci{
4998c2ecf20Sopenharmony_ci	/* 1543210543 */
5008c2ecf20Sopenharmony_ci	const struct rtc_time tm = {
5018c2ecf20Sopenharmony_ci		.tm_sec = 43,
5028c2ecf20Sopenharmony_ci		.tm_min = 35,
5038c2ecf20Sopenharmony_ci		.tm_hour = 5,
5048c2ecf20Sopenharmony_ci		.tm_mday = 26,
5058c2ecf20Sopenharmony_ci		.tm_mon = 10,
5068c2ecf20Sopenharmony_ci		.tm_year = 118,
5078c2ecf20Sopenharmony_ci	};
5088c2ecf20Sopenharmony_ci	/* 2019-01-04T15:32:23 */
5098c2ecf20Sopenharmony_ci	time64_t t = 1546615943;
5108c2ecf20Sopenharmony_ci
5118c2ecf20Sopenharmony_ci	test("(%pt?)", "%pt", &tm);
5128c2ecf20Sopenharmony_ci	test("2018-11-26T05:35:43", "%ptR", &tm);
5138c2ecf20Sopenharmony_ci	test("0118-10-26T05:35:43", "%ptRr", &tm);
5148c2ecf20Sopenharmony_ci	test("05:35:43|2018-11-26", "%ptRt|%ptRd", &tm, &tm);
5158c2ecf20Sopenharmony_ci	test("05:35:43|0118-10-26", "%ptRtr|%ptRdr", &tm, &tm);
5168c2ecf20Sopenharmony_ci	test("05:35:43|2018-11-26", "%ptRttr|%ptRdtr", &tm, &tm);
5178c2ecf20Sopenharmony_ci	test("05:35:43 tr|2018-11-26 tr", "%ptRt tr|%ptRd tr", &tm, &tm);
5188c2ecf20Sopenharmony_ci
5198c2ecf20Sopenharmony_ci	test("2019-01-04T15:32:23", "%ptT", &t);
5208c2ecf20Sopenharmony_ci	test("0119-00-04T15:32:23", "%ptTr", &t);
5218c2ecf20Sopenharmony_ci	test("15:32:23|2019-01-04", "%ptTt|%ptTd", &t, &t);
5228c2ecf20Sopenharmony_ci	test("15:32:23|0119-00-04", "%ptTtr|%ptTdr", &t, &t);
5238c2ecf20Sopenharmony_ci}
5248c2ecf20Sopenharmony_ci
5258c2ecf20Sopenharmony_cistatic void __init
5268c2ecf20Sopenharmony_cistruct_clk(void)
5278c2ecf20Sopenharmony_ci{
5288c2ecf20Sopenharmony_ci}
5298c2ecf20Sopenharmony_ci
5308c2ecf20Sopenharmony_cistatic void __init
5318c2ecf20Sopenharmony_cilarge_bitmap(void)
5328c2ecf20Sopenharmony_ci{
5338c2ecf20Sopenharmony_ci	const int nbits = 1 << 16;
5348c2ecf20Sopenharmony_ci	unsigned long *bits = bitmap_zalloc(nbits, GFP_KERNEL);
5358c2ecf20Sopenharmony_ci	if (!bits)
5368c2ecf20Sopenharmony_ci		return;
5378c2ecf20Sopenharmony_ci
5388c2ecf20Sopenharmony_ci	bitmap_set(bits, 1, 20);
5398c2ecf20Sopenharmony_ci	bitmap_set(bits, 60000, 15);
5408c2ecf20Sopenharmony_ci	test("1-20,60000-60014", "%*pbl", nbits, bits);
5418c2ecf20Sopenharmony_ci	bitmap_free(bits);
5428c2ecf20Sopenharmony_ci}
5438c2ecf20Sopenharmony_ci
5448c2ecf20Sopenharmony_cistatic void __init
5458c2ecf20Sopenharmony_cibitmap(void)
5468c2ecf20Sopenharmony_ci{
5478c2ecf20Sopenharmony_ci	DECLARE_BITMAP(bits, 20);
5488c2ecf20Sopenharmony_ci	const int primes[] = {2,3,5,7,11,13,17,19};
5498c2ecf20Sopenharmony_ci	int i;
5508c2ecf20Sopenharmony_ci
5518c2ecf20Sopenharmony_ci	bitmap_zero(bits, 20);
5528c2ecf20Sopenharmony_ci	test("00000|00000", "%20pb|%*pb", bits, 20, bits);
5538c2ecf20Sopenharmony_ci	test("|", "%20pbl|%*pbl", bits, 20, bits);
5548c2ecf20Sopenharmony_ci
5558c2ecf20Sopenharmony_ci	for (i = 0; i < ARRAY_SIZE(primes); ++i)
5568c2ecf20Sopenharmony_ci		set_bit(primes[i], bits);
5578c2ecf20Sopenharmony_ci	test("a28ac|a28ac", "%20pb|%*pb", bits, 20, bits);
5588c2ecf20Sopenharmony_ci	test("2-3,5,7,11,13,17,19|2-3,5,7,11,13,17,19", "%20pbl|%*pbl", bits, 20, bits);
5598c2ecf20Sopenharmony_ci
5608c2ecf20Sopenharmony_ci	bitmap_fill(bits, 20);
5618c2ecf20Sopenharmony_ci	test("fffff|fffff", "%20pb|%*pb", bits, 20, bits);
5628c2ecf20Sopenharmony_ci	test("0-19|0-19", "%20pbl|%*pbl", bits, 20, bits);
5638c2ecf20Sopenharmony_ci
5648c2ecf20Sopenharmony_ci	large_bitmap();
5658c2ecf20Sopenharmony_ci}
5668c2ecf20Sopenharmony_ci
5678c2ecf20Sopenharmony_cistatic void __init
5688c2ecf20Sopenharmony_cinetdev_features(void)
5698c2ecf20Sopenharmony_ci{
5708c2ecf20Sopenharmony_ci}
5718c2ecf20Sopenharmony_ci
5728c2ecf20Sopenharmony_cistatic void __init
5738c2ecf20Sopenharmony_ciflags(void)
5748c2ecf20Sopenharmony_ci{
5758c2ecf20Sopenharmony_ci	unsigned long flags;
5768c2ecf20Sopenharmony_ci	gfp_t gfp;
5778c2ecf20Sopenharmony_ci	char *cmp_buffer;
5788c2ecf20Sopenharmony_ci
5798c2ecf20Sopenharmony_ci	flags = 0;
5808c2ecf20Sopenharmony_ci	test("", "%pGp", &flags);
5818c2ecf20Sopenharmony_ci
5828c2ecf20Sopenharmony_ci	/* Page flags should filter the zone id */
5838c2ecf20Sopenharmony_ci	flags = 1UL << NR_PAGEFLAGS;
5848c2ecf20Sopenharmony_ci	test("", "%pGp", &flags);
5858c2ecf20Sopenharmony_ci
5868c2ecf20Sopenharmony_ci	flags |= 1UL << PG_uptodate | 1UL << PG_dirty | 1UL << PG_lru
5878c2ecf20Sopenharmony_ci		| 1UL << PG_active | 1UL << PG_swapbacked;
5888c2ecf20Sopenharmony_ci	test("uptodate|dirty|lru|active|swapbacked", "%pGp", &flags);
5898c2ecf20Sopenharmony_ci
5908c2ecf20Sopenharmony_ci
5918c2ecf20Sopenharmony_ci	flags = VM_READ | VM_EXEC | VM_MAYREAD | VM_MAYWRITE | VM_MAYEXEC
5928c2ecf20Sopenharmony_ci			| VM_DENYWRITE;
5938c2ecf20Sopenharmony_ci	test("read|exec|mayread|maywrite|mayexec|denywrite", "%pGv", &flags);
5948c2ecf20Sopenharmony_ci
5958c2ecf20Sopenharmony_ci	gfp = GFP_TRANSHUGE;
5968c2ecf20Sopenharmony_ci	test("GFP_TRANSHUGE", "%pGg", &gfp);
5978c2ecf20Sopenharmony_ci
5988c2ecf20Sopenharmony_ci	gfp = GFP_ATOMIC|__GFP_DMA;
5998c2ecf20Sopenharmony_ci	test("GFP_ATOMIC|GFP_DMA", "%pGg", &gfp);
6008c2ecf20Sopenharmony_ci
6018c2ecf20Sopenharmony_ci	gfp = __GFP_ATOMIC;
6028c2ecf20Sopenharmony_ci	test("__GFP_ATOMIC", "%pGg", &gfp);
6038c2ecf20Sopenharmony_ci
6048c2ecf20Sopenharmony_ci	cmp_buffer = kmalloc(BUF_SIZE, GFP_KERNEL);
6058c2ecf20Sopenharmony_ci	if (!cmp_buffer)
6068c2ecf20Sopenharmony_ci		return;
6078c2ecf20Sopenharmony_ci
6088c2ecf20Sopenharmony_ci	/* Any flags not translated by the table should remain numeric */
6098c2ecf20Sopenharmony_ci	gfp = ~__GFP_BITS_MASK;
6108c2ecf20Sopenharmony_ci	snprintf(cmp_buffer, BUF_SIZE, "%#lx", (unsigned long) gfp);
6118c2ecf20Sopenharmony_ci	test(cmp_buffer, "%pGg", &gfp);
6128c2ecf20Sopenharmony_ci
6138c2ecf20Sopenharmony_ci	snprintf(cmp_buffer, BUF_SIZE, "__GFP_ATOMIC|%#lx",
6148c2ecf20Sopenharmony_ci							(unsigned long) gfp);
6158c2ecf20Sopenharmony_ci	gfp |= __GFP_ATOMIC;
6168c2ecf20Sopenharmony_ci	test(cmp_buffer, "%pGg", &gfp);
6178c2ecf20Sopenharmony_ci
6188c2ecf20Sopenharmony_ci	kfree(cmp_buffer);
6198c2ecf20Sopenharmony_ci}
6208c2ecf20Sopenharmony_ci
6218c2ecf20Sopenharmony_cistatic void __init fwnode_pointer(void)
6228c2ecf20Sopenharmony_ci{
6238c2ecf20Sopenharmony_ci	const struct software_node softnodes[] = {
6248c2ecf20Sopenharmony_ci		{ .name = "first", },
6258c2ecf20Sopenharmony_ci		{ .name = "second", .parent = &softnodes[0], },
6268c2ecf20Sopenharmony_ci		{ .name = "third", .parent = &softnodes[1], },
6278c2ecf20Sopenharmony_ci		{ NULL /* Guardian */ }
6288c2ecf20Sopenharmony_ci	};
6298c2ecf20Sopenharmony_ci	const char * const full_name = "first/second/third";
6308c2ecf20Sopenharmony_ci	const char * const full_name_second = "first/second";
6318c2ecf20Sopenharmony_ci	const char * const second_name = "second";
6328c2ecf20Sopenharmony_ci	const char * const third_name = "third";
6338c2ecf20Sopenharmony_ci	int rval;
6348c2ecf20Sopenharmony_ci
6358c2ecf20Sopenharmony_ci	rval = software_node_register_nodes(softnodes);
6368c2ecf20Sopenharmony_ci	if (rval) {
6378c2ecf20Sopenharmony_ci		pr_warn("cannot register softnodes; rval %d\n", rval);
6388c2ecf20Sopenharmony_ci		return;
6398c2ecf20Sopenharmony_ci	}
6408c2ecf20Sopenharmony_ci
6418c2ecf20Sopenharmony_ci	test(full_name_second, "%pfw", software_node_fwnode(&softnodes[1]));
6428c2ecf20Sopenharmony_ci	test(full_name, "%pfw", software_node_fwnode(&softnodes[2]));
6438c2ecf20Sopenharmony_ci	test(full_name, "%pfwf", software_node_fwnode(&softnodes[2]));
6448c2ecf20Sopenharmony_ci	test(second_name, "%pfwP", software_node_fwnode(&softnodes[1]));
6458c2ecf20Sopenharmony_ci	test(third_name, "%pfwP", software_node_fwnode(&softnodes[2]));
6468c2ecf20Sopenharmony_ci
6478c2ecf20Sopenharmony_ci	software_node_unregister(&softnodes[2]);
6488c2ecf20Sopenharmony_ci	software_node_unregister(&softnodes[1]);
6498c2ecf20Sopenharmony_ci	software_node_unregister(&softnodes[0]);
6508c2ecf20Sopenharmony_ci}
6518c2ecf20Sopenharmony_ci
6528c2ecf20Sopenharmony_cistatic void __init
6538c2ecf20Sopenharmony_cierrptr(void)
6548c2ecf20Sopenharmony_ci{
6558c2ecf20Sopenharmony_ci	test("-1234", "%pe", ERR_PTR(-1234));
6568c2ecf20Sopenharmony_ci
6578c2ecf20Sopenharmony_ci	/* Check that %pe with a non-ERR_PTR gets treated as ordinary %p. */
6588c2ecf20Sopenharmony_ci	BUILD_BUG_ON(IS_ERR(PTR));
6598c2ecf20Sopenharmony_ci	test_hashed("%pe", PTR);
6608c2ecf20Sopenharmony_ci
6618c2ecf20Sopenharmony_ci#ifdef CONFIG_SYMBOLIC_ERRNAME
6628c2ecf20Sopenharmony_ci	test("(-ENOTSOCK)", "(%pe)", ERR_PTR(-ENOTSOCK));
6638c2ecf20Sopenharmony_ci	test("(-EAGAIN)", "(%pe)", ERR_PTR(-EAGAIN));
6648c2ecf20Sopenharmony_ci	BUILD_BUG_ON(EAGAIN != EWOULDBLOCK);
6658c2ecf20Sopenharmony_ci	test("(-EAGAIN)", "(%pe)", ERR_PTR(-EWOULDBLOCK));
6668c2ecf20Sopenharmony_ci	test("[-EIO    ]", "[%-8pe]", ERR_PTR(-EIO));
6678c2ecf20Sopenharmony_ci	test("[    -EIO]", "[%8pe]", ERR_PTR(-EIO));
6688c2ecf20Sopenharmony_ci	test("-EPROBE_DEFER", "%pe", ERR_PTR(-EPROBE_DEFER));
6698c2ecf20Sopenharmony_ci#endif
6708c2ecf20Sopenharmony_ci}
6718c2ecf20Sopenharmony_ci
6728c2ecf20Sopenharmony_cistatic void __init
6738c2ecf20Sopenharmony_citest_pointer(void)
6748c2ecf20Sopenharmony_ci{
6758c2ecf20Sopenharmony_ci	plain();
6768c2ecf20Sopenharmony_ci	null_pointer();
6778c2ecf20Sopenharmony_ci	error_pointer();
6788c2ecf20Sopenharmony_ci	invalid_pointer();
6798c2ecf20Sopenharmony_ci	symbol_ptr();
6808c2ecf20Sopenharmony_ci	kernel_ptr();
6818c2ecf20Sopenharmony_ci	struct_resource();
6828c2ecf20Sopenharmony_ci	addr();
6838c2ecf20Sopenharmony_ci	escaped_str();
6848c2ecf20Sopenharmony_ci	hex_string();
6858c2ecf20Sopenharmony_ci	mac();
6868c2ecf20Sopenharmony_ci	ip();
6878c2ecf20Sopenharmony_ci	uuid();
6888c2ecf20Sopenharmony_ci	dentry();
6898c2ecf20Sopenharmony_ci	struct_va_format();
6908c2ecf20Sopenharmony_ci	time_and_date();
6918c2ecf20Sopenharmony_ci	struct_clk();
6928c2ecf20Sopenharmony_ci	bitmap();
6938c2ecf20Sopenharmony_ci	netdev_features();
6948c2ecf20Sopenharmony_ci	flags();
6958c2ecf20Sopenharmony_ci	errptr();
6968c2ecf20Sopenharmony_ci	fwnode_pointer();
6978c2ecf20Sopenharmony_ci}
6988c2ecf20Sopenharmony_ci
6998c2ecf20Sopenharmony_cistatic void __init selftest(void)
7008c2ecf20Sopenharmony_ci{
7018c2ecf20Sopenharmony_ci	alloced_buffer = kmalloc(BUF_SIZE + 2*PAD_SIZE, GFP_KERNEL);
7028c2ecf20Sopenharmony_ci	if (!alloced_buffer)
7038c2ecf20Sopenharmony_ci		return;
7048c2ecf20Sopenharmony_ci	test_buffer = alloced_buffer + PAD_SIZE;
7058c2ecf20Sopenharmony_ci
7068c2ecf20Sopenharmony_ci	test_basic();
7078c2ecf20Sopenharmony_ci	test_number();
7088c2ecf20Sopenharmony_ci	test_string();
7098c2ecf20Sopenharmony_ci	test_pointer();
7108c2ecf20Sopenharmony_ci
7118c2ecf20Sopenharmony_ci	kfree(alloced_buffer);
7128c2ecf20Sopenharmony_ci}
7138c2ecf20Sopenharmony_ci
7148c2ecf20Sopenharmony_ciKSTM_MODULE_LOADERS(test_printf);
7158c2ecf20Sopenharmony_ciMODULE_AUTHOR("Rasmus Villemoes <linux@rasmusvillemoes.dk>");
7168c2ecf20Sopenharmony_ciMODULE_LICENSE("GPL");
717