diff options
Diffstat (limited to 'test/cmd_ut.c')
| -rw-r--r-- | test/cmd_ut.c | 243 | 
1 files changed, 129 insertions, 114 deletions
| diff --git a/test/cmd_ut.c b/test/cmd_ut.c index fbfdaaae0b5..44e5fdfdaa6 100644 --- a/test/cmd_ut.c +++ b/test/cmd_ut.c @@ -7,7 +7,6 @@  #include <command.h>  #include <console.h>  #include <vsprintf.h> -#include <test/suites.h>  #include <test/test.h>  #include <test/ut.h> @@ -20,77 +19,31 @@   * @name: Name of suite   * @start: First test in suite   * @end: End test in suite (points to the first test in the next suite) - * @cmd: Command to use to run the suite   * @help: Help-string to show for this suite   */  struct suite {  	const char *name;  	struct unit_test *start;  	struct unit_test *end; -	ut_cmd_func cmd;  	const char *help;  }; -static int do_ut_all(struct unit_test_state *uts, struct cmd_tbl *cmdtp, -		     int flag, int argc, char *const argv[]); +static int do_ut_all(struct unit_test_state *uts, const char *select_name, +		     int runs_per_test, bool force_run, +		     const char *test_insert); -static int do_ut_info(struct cmd_tbl *cmdtp, int flag, int argc, -		      char *const argv[]); - -int cmd_ut_category(struct unit_test_state *uts, const char *name, -		    const char *prefix, struct unit_test *tests, int n_ents, -		    int argc, char *const argv[]) -{ -	const char *test_insert = NULL; -	int runs_per_text = 1; -	bool force_run = false; -	int ret; - -	while (argc > 1 && *argv[1] == '-') { -		const char *str = argv[1]; - -		switch (str[1]) { -		case 'r': -			runs_per_text = dectoul(str + 2, NULL); -			break; -		case 'f': -			force_run = true; -			break; -		case 'I': -			test_insert = str + 2; -			break; -		} -		argv++; -		argc--; -	} - -	ret = ut_run_list(uts, name, prefix, tests, n_ents, -			  cmd_arg1(argc, argv), runs_per_text, force_run, -			  test_insert); - -	return ret ? CMD_RET_FAILURE : 0; -} +static int do_ut_info(bool show_suites);  /* declare linker-list symbols for the start and end of a suite */  #define SUITE_DECL(_name) \  	ll_start_decl(suite_start_ ## _name, struct unit_test, ut_ ## _name); \  	ll_end_decl(suite_end_ ## _name, struct unit_test, ut_ ## _name) -/* declare a test suite which uses a subcommand to run */ -#define SUITE_CMD(_name, _cmd_func, _help) { \ -	#_name, \ -	suite_start_ ## _name, \ -	suite_end_ ## _name, \ -	_cmd_func, \ -	_help, \ -	} -  /* declare a test suite which can be run directly without a subcommand */  #define SUITE(_name, _help) { \  	#_name, \  	suite_start_ ## _name, \  	suite_end_ ## _name, \ -	NULL, \  	_help, \  	} @@ -105,6 +58,7 @@ SUITE_DECL(dm);  SUITE_DECL(env);  SUITE_DECL(exit);  SUITE_DECL(fdt); +SUITE_DECL(fdt_overlay);  SUITE_DECL(font);  SUITE_DECL(hush);  SUITE_DECL(lib); @@ -114,7 +68,6 @@ SUITE_DECL(mbr);  SUITE_DECL(measurement);  SUITE_DECL(mem);  SUITE_DECL(optee); -SUITE_DECL(overlay);  SUITE_DECL(pci_mps);  SUITE_DECL(seama);  SUITE_DECL(setexpr); @@ -125,15 +78,14 @@ static struct suite suites[] = {  	SUITE(bdinfo, "bdinfo (board info) command"),  	SUITE(bloblist, "bloblist implementation"),  	SUITE(bootm, "bootm command"), -#ifdef CONFIG_UT_BOOTSTD -	SUITE_CMD(bootstd, do_ut_bootstd, "standard boot implementation"), -#endif +	SUITE(bootstd, "standard boot implementation"),  	SUITE(cmd, "various commands"),  	SUITE(common, "tests for common/ directory"),  	SUITE(dm, "driver model"),  	SUITE(env, "environment"),  	SUITE(exit, "shell exit and variables"),  	SUITE(fdt, "fdt command"), +	SUITE(fdt_overlay, "device tree overlays"),  	SUITE(font, "font command"),  	SUITE(hush, "hush behaviour"),  	SUITE(lib, "library functions"), @@ -142,12 +94,7 @@ static struct suite suites[] = {  	SUITE(mbr, "mbr command"),  	SUITE(measurement, "TPM-based measured boot"),  	SUITE(mem, "memory-related commands"), -#ifdef CONFIG_UT_OPTEE -	SUITE_CMD(optee, do_ut_optee, "OP-TEE"), -#endif -#ifdef CONFIG_UT_OVERLAY -	SUITE_CMD(overlay, do_ut_overlay, "device tree overlays"), -#endif +	SUITE(optee, "OP-TEE"),  	SUITE(pci_mps, "PCI Express Maximum Payload Size"),  	SUITE(seama, "seama command parameters loading and decoding"),  	SUITE(setexpr, "setexpr command"), @@ -167,33 +114,59 @@ static bool has_tests(struct suite *ste)  {  	int n_ents = ste->end - ste->start; -	return n_ents || ste->cmd; +	return n_ents;  }  /** run_suite() - Run a suite of tests */  static int run_suite(struct unit_test_state *uts, struct suite *ste, -		     struct cmd_tbl *cmdtp, int flag, int argc, -		     char *const argv[]) +		     const char *select_name, int runs_per_test, bool force_run, +		     const char *test_insert)  { +	int n_ents = ste->end - ste->start; +	char prefix[30];  	int ret; -	if (ste->cmd) { -		ret = ste->cmd(uts, cmdtp, flag, argc, argv); -	} else { -		int n_ents = ste->end - ste->start; -		char prefix[30]; +	/* use a standard prefix */ +	snprintf(prefix, sizeof(prefix), "%s_test_", ste->name); -		/* use a standard prefix */ -		snprintf(prefix, sizeof(prefix), "%s_test", ste->name); -		ret = cmd_ut_category(uts, ste->name, prefix, ste->start, -				      n_ents, argc, argv); -	} +	ret = ut_run_list(uts, ste->name, prefix, ste->start, n_ents, +			  select_name, runs_per_test, force_run, test_insert);  	return ret;  } -static int do_ut_all(struct unit_test_state *uts, struct cmd_tbl *cmdtp, -		     int flag, int argc, char *const argv[]) +static void show_stats(struct unit_test_state *uts) +{ +	if (uts->run_count < 2) +		return; + +	ut_report(&uts->total, uts->run_count); +	if (CONFIG_IS_ENABLED(UNIT_TEST_DURATION) && +	    uts->total.test_count && uts->worst) { +		ulong avg = uts->total.duration_ms / uts->total.test_count; + +		printf("Average test time: %ld ms, worst case '%s' took %d ms\n", +		       avg, uts->worst->name, uts->worst_ms); +	} +} + +static void update_stats(struct unit_test_state *uts, const struct suite *ste) +{ +	if (CONFIG_IS_ENABLED(UNIT_TEST_DURATION) && uts->cur.test_count) { +		ulong avg; + +		avg = uts->cur.duration_ms ? +			uts->cur.duration_ms / +			uts->cur.test_count : 0; +		if (avg > uts->worst_ms) { +			uts->worst_ms = avg; +			uts->worst = ste; +		} +	} +} + +static int do_ut_all(struct unit_test_state *uts, const char *select_name, +		     int runs_per_test, bool force_run, const char *test_insert)  {  	int i;  	int retval; @@ -201,25 +174,23 @@ static int do_ut_all(struct unit_test_state *uts, struct cmd_tbl *cmdtp,  	for (i = 0; i < ARRAY_SIZE(suites); i++) {  		struct suite *ste = &suites[i]; -		char *const argv[] = {(char *)ste->name, NULL};  		if (has_tests(ste)) {  			printf("----Running %s tests----\n", ste->name); -			retval = run_suite(uts, ste, cmdtp, flag, 1, argv); +			retval = run_suite(uts, ste, select_name, runs_per_test, +					   force_run, test_insert);  			if (!any_fail)  				any_fail = retval; +			update_stats(uts, ste);  		}  	} -	ut_report(&uts->total, uts->run_count);  	return any_fail;  } -static int do_ut_info(struct cmd_tbl *cmdtp, int flag, int argc, -		      char *const argv[]) +static int do_ut_info(bool show_suites)  {  	int suite_count, i; -	const char *flags;  	for (suite_count = 0, i = 0; i < ARRAY_SIZE(suites); i++) {  		struct suite *ste = &suites[i]; @@ -231,24 +202,26 @@ static int do_ut_info(struct cmd_tbl *cmdtp, int flag, int argc,  	printf("Test suites: %d\n", suite_count);  	printf("Total tests: %d\n", (int)UNIT_TEST_ALL_COUNT()); -	flags = cmd_arg1(argc, argv); -	if (flags && !strcmp("-s", flags)) { -		int i; +	if (show_suites) { +		int i, total;  		puts("\nTests  Suite         Purpose");  		puts("\n-----  ------------  -------------------------\n"); -		for (i = 0; i < ARRAY_SIZE(suites); i++) { +		for (i = 0, total = 0; i < ARRAY_SIZE(suites); i++) {  			struct suite *ste = &suites[i];  			long n_ent = ste->end - ste->start; -			if (n_ent) -				printf("%5ld", n_ent); -			else if (ste->cmd) -				printf("%5s", "?"); -			else  /* suite is not present */ -				continue; -			printf("  %-13.13s %s\n", ste->name, ste->help); +			if (n_ent) { +				printf("%5ld  %-13.13s %s\n", n_ent, ste->name, +				       ste->help); +				total += n_ent; +			}  		} +		puts("-----  ------------  -------------------------\n"); +		printf("%5d  %-13.13s\n", total, "Total"); + +		if (UNIT_TEST_ALL_COUNT() != total) +			puts("Error: Suite test-count does not match total\n");  	}  	return 0; @@ -269,37 +242,77 @@ static struct suite *find_suite(const char *name)  static int do_ut(struct cmd_tbl *cmdtp, int flag, int argc, char *const argv[])  { +	const char *test_insert = NULL, *select_name;  	struct unit_test_state uts; +	bool show_suites = false; +	bool force_run = false; +	int runs_per_text = 1;  	struct suite *ste; -	const char *name; +	char *name;  	int ret; -	if (argc < 2) -		return CMD_RET_USAGE; -  	/* drop initial "ut" arg */  	argc--;  	argv++; +	while (argc > 0 && *argv[0] == '-') { +		const char *str = argv[0]; + +		switch (str[1]) { +		case 'r': +			runs_per_text = dectoul(str + 2, NULL); +			break; +		case 'f': +			force_run = true; +			break; +		case 'I': +			test_insert = str + 2; +			if (!strchr(test_insert, ':')) +				return CMD_RET_USAGE; +			break; +		case 's': +			show_suites = true; +			break; +		} +		argv++; +		argc--; +	} + +	if (argc < 1) +		return CMD_RET_USAGE; +  	ut_init_state(&uts);  	name = argv[0]; +	select_name = cmd_arg1(argc, argv);  	if (!strcmp(name, "all")) { -		ret = do_ut_all(&uts, cmdtp, flag, argc, argv); +		ret = do_ut_all(&uts, select_name, runs_per_text, force_run, +				test_insert);  	} else if (!strcmp(name, "info")) { -		ret = do_ut_info(cmdtp, flag, argc, argv); +		ret = do_ut_info(show_suites);  	} else { -		ste = find_suite(argv[0]); -		if (!ste) { -			printf("Suite '%s' not found\n", argv[0]); -			return CMD_RET_FAILURE; -		} else if (!has_tests(ste)) { -			/* perhaps a Kconfig option needs to be set? */ -			printf("Suite '%s' is not enabled\n", argv[0]); -			return CMD_RET_FAILURE; +		int any_fail = 0; +		const char *p; + +		for (; p = strsep(&name, ","), p; name = NULL) { +			ste = find_suite(p); +			if (!ste) { +				printf("Suite '%s' not found\n", p); +				return CMD_RET_FAILURE; +			} else if (!has_tests(ste)) { +				/* perhaps a Kconfig option needs to be set? */ +				printf("Suite '%s' is not enabled\n", p); +				return CMD_RET_FAILURE; +			} + +			ret = run_suite(&uts, ste, select_name, runs_per_text, +					force_run, test_insert); +			if (!any_fail) +				any_fail = ret; +			update_stats(&uts, ste);  		} - -		ret = run_suite(&uts, ste, cmdtp, flag, argc, argv); +		ret = any_fail;  	} +	show_stats(&uts);  	if (ret)  		return ret;  	ut_uninit_state(&uts); @@ -308,14 +321,16 @@ static int do_ut(struct cmd_tbl *cmdtp, int flag, int argc, char *const argv[])  }  U_BOOT_LONGHELP(ut, -	"[-r] [-f] [<suite>] - run unit tests\n" +	"[-rs] [-f] [-I<n>:<one_test>][<suites>] - run unit tests\n"  	"   -r<runs>   Number of times to run each test\n"  	"   -f         Force 'manual' tests to run as well\n" -	"   <suite>    Test suite to run, or all\n" +	"   -I         Test to run after <n> other tests have run\n" +	"   -s         Show all suites with ut info\n" +	"   <suites>   Comma-separated list of suites to run\n"  	"\n" -	"\nOptions for <suite>:" -	"\nall - execute all enabled tests" -	"\ninfo [-s] - show info about tests [and suites]" +	"Options for <suite>:\n" +	"all       - execute all enabled tests\n" +	"info      - show info about tests [and suites]"  	);  U_BOOT_CMD( | 
