1 // SPDX-License-Identifier: GPL-2.0
2 /*
3  * Copyright (C) 2020 Texas Instruments Inc.
4  * Pratyush Yadav <p.yadav@ti.com>
5  */
6 #include <common.h>
7 #include <dm.h>
8 #include <mux.h>
9 #include <mux-internal.h>
10 #include <dt-bindings/mux/mux.h>
11 #include <asm/test.h>
12 #include <dm/test.h>
13 #include <test/ut.h>
14 #include <console.h>
15 #include <rand.h>
16 
17 #define BUF_SIZE		256
18 
19 /* Test 'mux list' */
dm_test_cmd_mux_list(struct unit_test_state * uts)20 static int dm_test_cmd_mux_list(struct unit_test_state *uts)
21 {
22 	char str[BUF_SIZE], *tok;
23 	struct udevice *dev;
24 	struct mux_chip *chip;
25 	struct mux_control *mux;
26 	int i;
27 	unsigned long val;
28 
29 	sandbox_set_enable_memio(true);
30 
31 	ut_assertok(uclass_get_device_by_name(UCLASS_MUX, "a-mux-controller",
32 					      &dev));
33 	chip = dev_get_uclass_priv(dev);
34 	ut_assertnonnull(chip);
35 
36 	run_command("mux list", 0);
37 	ut_assert_nextline("a-mux-controller:");
38 
39 	/*
40 	 * Check the table header to make sure we are not out of sync with the
41 	 * code in the command. If we are, catch it early.
42 	 */
43 	console_record_readline(str, BUF_SIZE);
44 	tok = strtok(str, " ");
45 	ut_asserteq_str("ID", tok);
46 
47 	tok = strtok(NULL, " ");
48 	ut_asserteq_str("Selected", tok);
49 
50 	tok = strtok(NULL, " ");
51 	ut_asserteq_str("Current", tok);
52 	tok = strtok(NULL, " ");
53 	ut_asserteq_str("State", tok);
54 
55 	tok = strtok(NULL, " ");
56 	ut_asserteq_str("Idle", tok);
57 	tok = strtok(NULL, " ");
58 	ut_asserteq_str("State", tok);
59 
60 	tok = strtok(NULL, " ");
61 	ut_asserteq_str("Num", tok);
62 	tok = strtok(NULL, " ");
63 	ut_asserteq_str("States", tok);
64 
65 	for (i = 0; i < chip->controllers; i++) {
66 		mux = &chip->mux[i];
67 
68 		console_record_readline(str, BUF_SIZE);
69 
70 		/*
71 		 * Check if the ID printed matches with the ID of the chip we
72 		 * have.
73 		 */
74 		tok = strtok(str, " ");
75 		ut_assertok(strict_strtoul(tok, 10, &val));
76 		ut_asserteq(i, val);
77 
78 		/* Check if mux selection state matches. */
79 		tok = strtok(NULL, " ");
80 		if (mux->in_use) {
81 			ut_asserteq_str("yes", tok);
82 		} else {
83 			ut_asserteq_str("no", tok);
84 		}
85 
86 		/* Check if the current state matches. */
87 		tok = strtok(NULL, " ");
88 		if (mux->cached_state == MUX_IDLE_AS_IS) {
89 			ut_asserteq_str("unknown", tok);
90 		} else {
91 			ut_assertok(strict_strtoul(tok, 16, &val));
92 			ut_asserteq(mux->cached_state, val);
93 		}
94 
95 		/* Check if the idle state matches */
96 		tok = strtok(NULL, " ");
97 		if (mux->idle_state == MUX_IDLE_AS_IS) {
98 			ut_asserteq_str("as-is", tok);
99 		} else {
100 			ut_assertok(strict_strtoul(tok, 16, &val));
101 			ut_asserteq(mux->idle_state, val);
102 		}
103 
104 		/* Check if the number of states matches */
105 		tok = strtok(NULL, " ");
106 		ut_assertok(strict_strtoul(tok, 16, &val));
107 		ut_asserteq(mux->states, val);
108 	}
109 
110 	return 0;
111 }
112 DM_TEST(dm_test_cmd_mux_list, UT_TESTF_SCAN_PDATA | UT_TESTF_SCAN_FDT);
113 
dm_test_cmd_mux_select(struct unit_test_state * uts)114 static int dm_test_cmd_mux_select(struct unit_test_state *uts)
115 {
116 	struct udevice *dev;
117 	struct mux_chip *chip;
118 	struct mux_control *mux;
119 	char cmd[BUF_SIZE];
120 	unsigned int i, state;
121 
122 	sandbox_set_enable_memio(true);
123 
124 	ut_assertok(uclass_get_device_by_name(UCLASS_MUX, "a-mux-controller",
125 					      &dev));
126 	chip = dev_get_uclass_priv(dev);
127 	ut_assertnonnull(chip);
128 
129 	srand(get_ticks() + rand());
130 	for (i = 0; i < chip->controllers; i++) {
131 		mux = &chip->mux[i];
132 
133 		state = rand() % mux->states;
134 
135 		snprintf(cmd, BUF_SIZE, "mux select a-mux-controller %x %x", i,
136 			 state);
137 		run_command(cmd, 0);
138 		ut_asserteq(!!mux->in_use, true);
139 		ut_asserteq(state, mux->cached_state);
140 
141 		ut_assertok(mux_control_deselect(mux));
142 	}
143 
144 	return 0;
145 }
146 DM_TEST(dm_test_cmd_mux_select, UT_TESTF_SCAN_PDATA | UT_TESTF_SCAN_FDT);
147 
dm_test_cmd_mux_deselect(struct unit_test_state * uts)148 static int dm_test_cmd_mux_deselect(struct unit_test_state *uts)
149 {
150 	struct udevice *dev;
151 	struct mux_chip *chip;
152 	struct mux_control *mux;
153 	char cmd[BUF_SIZE];
154 	unsigned int i, state;
155 
156 	sandbox_set_enable_memio(true);
157 
158 	ut_assertok(uclass_get_device_by_name(UCLASS_MUX, "a-mux-controller",
159 					      &dev));
160 	chip = dev_get_uclass_priv(dev);
161 	ut_assertnonnull(chip);
162 
163 	srand(get_ticks() + rand());
164 	for (i = 0; i < chip->controllers; i++) {
165 		mux = &chip->mux[i];
166 
167 		state = rand() % mux->states;
168 		ut_assertok(mux_control_select(mux, state));
169 
170 		snprintf(cmd, BUF_SIZE, "mux deselect a-mux-controller %d", i);
171 		run_command(cmd, 0);
172 		ut_asserteq(!!mux->in_use, false);
173 	}
174 
175 	return 0;
176 }
177 DM_TEST(dm_test_cmd_mux_deselect, UT_TESTF_SCAN_PDATA | UT_TESTF_SCAN_FDT);
178