Merge tag 'dm-pull-12jun20' of git://git.denx.de/u-boot-dm into next
[platform/kernel/u-boot.git] / test / dm / usb.c
1 // SPDX-License-Identifier: GPL-2.0+
2 /*
3  * Copyright (C) 2015 Google, Inc
4  */
5
6 #include <common.h>
7 #include <console.h>
8 #include <dm.h>
9 #include <part.h>
10 #include <usb.h>
11 #include <asm/io.h>
12 #include <asm/state.h>
13 #include <asm/test.h>
14 #include <dm/device-internal.h>
15 #include <dm/test.h>
16 #include <dm/uclass-internal.h>
17 #include <test/ut.h>
18
19 struct keyboard_test_data {
20         const char modifiers;
21         const char scancode;
22         const char result[6];
23 };
24
25 /* Test that sandbox USB works correctly */
26 static int dm_test_usb_base(struct unit_test_state *uts)
27 {
28         struct udevice *bus;
29
30         ut_asserteq(-ENODEV, uclass_get_device_by_seq(UCLASS_USB, 0, &bus));
31         ut_assertok(uclass_get_device(UCLASS_USB, 0, &bus));
32         ut_asserteq(-ENODEV, uclass_get_device_by_seq(UCLASS_USB, 2, &bus));
33
34         return 0;
35 }
36 DM_TEST(dm_test_usb_base, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
37
38 /*
39  * Test that we can use the flash stick. This is more of a functional test. It
40  * covers scanning the bug, setting up a hub and a flash stick and reading
41  * data from the flash stick.
42  */
43 static int dm_test_usb_flash(struct unit_test_state *uts)
44 {
45         struct udevice *dev;
46         struct blk_desc *dev_desc;
47         char cmp[1024];
48
49         state_set_skip_delays(true);
50         ut_assertok(usb_init());
51         ut_assertok(uclass_get_device(UCLASS_MASS_STORAGE, 0, &dev));
52         ut_assertok(blk_get_device_by_str("usb", "0", &dev_desc));
53
54         /* Read a few blocks and look for the string we expect */
55         ut_asserteq(512, dev_desc->blksz);
56         memset(cmp, '\0', sizeof(cmp));
57         ut_asserteq(2, blk_dread(dev_desc, 0, 2, cmp));
58         ut_assertok(strcmp(cmp, "this is a test"));
59         ut_assertok(usb_stop());
60
61         return 0;
62 }
63 DM_TEST(dm_test_usb_flash, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
64
65 /* test that we can handle multiple storage devices */
66 static int dm_test_usb_multi(struct unit_test_state *uts)
67 {
68         struct udevice *dev;
69
70         state_set_skip_delays(true);
71         ut_assertok(usb_init());
72         ut_assertok(uclass_get_device(UCLASS_MASS_STORAGE, 0, &dev));
73         ut_assertok(uclass_get_device(UCLASS_MASS_STORAGE, 1, &dev));
74         ut_assertok(uclass_get_device(UCLASS_MASS_STORAGE, 2, &dev));
75         ut_assertok(usb_stop());
76
77         return 0;
78 }
79 DM_TEST(dm_test_usb_multi, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
80
81 /* test that we have an associated ofnode with the usb device */
82 static int dm_test_usb_fdt_node(struct unit_test_state *uts)
83 {
84         struct udevice *dev;
85         ofnode node;
86
87         state_set_skip_delays(true);
88         ut_assertok(usb_init());
89         ut_assertok(uclass_get_device(UCLASS_MASS_STORAGE, 0, &dev));
90         node = ofnode_path("/usb@1/hub/usbstor@1");
91         ut_asserteq(1, ofnode_equal(node, dev_ofnode(dev)));
92         ut_assertok(uclass_get_device(UCLASS_MASS_STORAGE, 1, &dev));
93         ut_asserteq(1, ofnode_equal(ofnode_null(), dev_ofnode(dev)));
94         ut_assertok(uclass_get_device(UCLASS_MASS_STORAGE, 2, &dev));
95         node = ofnode_path("/usb@1/hub/usbstor@3");
96         ut_asserteq(1, ofnode_equal(node, dev_ofnode(dev)));
97         ut_assertok(usb_stop());
98
99         return 0;
100 }
101 DM_TEST(dm_test_usb_fdt_node, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
102
103 static int count_usb_devices(void)
104 {
105         struct udevice *hub;
106         struct uclass *uc;
107         int count = 0;
108         int ret;
109
110         ret = uclass_get(UCLASS_USB_HUB, &uc);
111         if (ret)
112                 return ret;
113
114         uclass_foreach_dev(hub, uc) {
115                 struct udevice *dev;
116
117                 count++;
118                 for (device_find_first_child(hub, &dev);
119                      dev;
120                      device_find_next_child(&dev)) {
121                         count++;
122                 }
123         }
124
125         return count;
126 }
127
128 /* test that no USB devices are found after we stop the stack */
129 static int dm_test_usb_stop(struct unit_test_state *uts)
130 {
131         struct udevice *dev;
132
133         /* Scan and check that all devices are present */
134         state_set_skip_delays(true);
135         ut_assertok(usb_init());
136         ut_assertok(uclass_get_device(UCLASS_MASS_STORAGE, 0, &dev));
137         ut_assertok(uclass_get_device(UCLASS_MASS_STORAGE, 1, &dev));
138         ut_assertok(uclass_get_device(UCLASS_MASS_STORAGE, 2, &dev));
139         ut_asserteq(6, count_usb_devices());
140         ut_assertok(usb_stop());
141         ut_asserteq(0, count_usb_devices());
142
143         return 0;
144 }
145 DM_TEST(dm_test_usb_stop, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);
146
147 /**
148  * dm_test_usb_keyb() - test USB keyboard driver
149  *
150  * This test copies USB keyboard scan codes into the key buffer of the USB
151  * keyboard emulation driver. These are picked up during emulated interrupts
152  * by the USB keyboard driver and converted to characters and escape sequences.
153  * The test then reads and verifies these characters and escape sequences from
154  * the standard input.
155  *
156  * TODO: The following features are not yet tested:
157  *
158  * * LED status
159  * * caps-lock
160  * * num-lock
161  * * numerical pad keys
162  *
163  * TODO: The following features are not yet implemented by the USB keyboard
164  * driver and therefore not tested:
165  *
166  * * modifiers for non-alpha-numeric keys, e.g. <SHIFT><TAB> and <ALT><F4>
167  * * some special keys, e.g. <PRINT>
168  * * some modifiers, e.g. <ALT> and <META>
169  * * alternative keyboard layouts
170  *
171  * @uts:        unit test state
172  * Return:      0 on success
173  */
174 static int dm_test_usb_keyb(struct unit_test_state *uts)
175 {
176         struct udevice *dev;
177         const struct keyboard_test_data *pos;
178         const struct keyboard_test_data kbd_test_data[] = {
179                 /* <A> */
180                 {0x00, 0x04, "a"},
181                 /* <B> */
182                 {0x00, 0x05, "b"},
183                 /* <C> */
184                 {0x00, 0x06, "c"},
185                 /* <D> */
186                 {0x00, 0x07, "d"},
187                 /* <E> */
188                 {0x00, 0x08, "e"},
189                 /* <F> */
190                 {0x00, 0x09, "f"},
191                 /* <G> */
192                 {0x00, 0x0a, "g"},
193                 /* <H> */
194                 {0x00, 0x0b, "h"},
195                 /* <I> */
196                 {0x00, 0x0c, "i"},
197                 /* <J> */
198                 {0x00, 0x0d, "j"},
199                 /* <K> */
200                 {0x00, 0x0e, "k"},
201                 /* <L> */
202                 {0x00, 0x0f, "l"},
203                 /* <M> */
204                 {0x00, 0x10, "m"},
205                 /* <N> */
206                 {0x00, 0x11, "n"},
207                 /* <O> */
208                 {0x00, 0x12, "o"},
209                 /* <P> */
210                 {0x00, 0x13, "p"},
211                 /* <Q> */
212                 {0x00, 0x14, "q"},
213                 /* <R> */
214                 {0x00, 0x15, "r"},
215                 /* <S> */
216                 {0x00, 0x16, "s"},
217                 /* <T> */
218                 {0x00, 0x17, "t"},
219                 /* <U> */
220                 {0x00, 0x18, "u"},
221                 /* <V> */
222                 {0x00, 0x19, "v"},
223                 /* <W> */
224                 {0x00, 0x1a, "w"},
225                 /* <X> */
226                 {0x00, 0x1b, "x"},
227                 /* <Y> */
228                 {0x00, 0x1c, "y"},
229                 /* <Z> */
230                 {0x00, 0x1d, "z"},
231
232                 /* <LEFT-SHIFT><A> */
233                 {0x02, 0x04, "A"},
234                 /* <RIGHT-SHIFT><Z> */
235                 {0x20, 0x1d, "Z"},
236
237                 /* <LEFT-CONTROL><A> */
238                 {0x01, 0x04, "\x01"},
239                 /* <RIGHT-CONTROL><Z> */
240                 {0x10, 0x1d, "\x1a"},
241
242                 /* <1> */
243                 {0x00, 0x1e, "1"},
244                 /* <2> */
245                 {0x00, 0x1f, "2"},
246                 /* <3> */
247                 {0x00, 0x20, "3"},
248                 /* <4> */
249                 {0x00, 0x21, "4"},
250                 /* <5> */
251                 {0x00, 0x22, "5"},
252                 /* <6> */
253                 {0x00, 0x23, "6"},
254                 /* <7> */
255                 {0x00, 0x24, "7"},
256                 /* <8> */
257                 {0x00, 0x25, "8"},
258                 /* <9> */
259                 {0x00, 0x26, "9"},
260                 /* <0> */
261                 {0x00, 0x27, "0"},
262
263                 /* <LEFT-SHIFT><1> */
264                 {0x02, 0x1e, "!"},
265                 /* <RIGHT-SHIFT><2> */
266                 {0x20, 0x1f, "@"},
267                 /* <LEFT-SHIFT><3> */
268                 {0x02, 0x20, "#"},
269                 /* <RIGHT-SHIFT><4> */
270                 {0x20, 0x21, "$"},
271                 /* <LEFT-SHIFT><5> */
272                 {0x02, 0x22, "%"},
273                 /* <RIGHT-SHIFT><6> */
274                 {0x20, 0x23, "^"},
275                 /* <LEFT-SHIFT><7> */
276                 {0x02, 0x24, "&"},
277                 /* <RIGHT-SHIFT><8> */
278                 {0x20, 0x25, "*"},
279                 /* <LEFT-SHIFT><9> */
280                 {0x02, 0x26, "("},
281                 /* <RIGHT-SHIFT><0> */
282                 {0x20, 0x27, ")"},
283
284                 /* <ENTER> */
285                 {0x00, 0x28, "\r"},
286                 /* <ESCAPE> */
287                 {0x00, 0x29, "\x1b"},
288                 /* <BACKSPACE> */
289                 {0x00, 0x2a, "\x08"},
290                 /* <TAB> */
291                 {0x00, 0x2b, "\x09"},
292                 /* <SPACE> */
293                 {0x00, 0x2c, " "},
294                 /* <MINUS> */
295                 {0x00, 0x2d, "-"},
296                 /* <EQUAL> */
297                 {0x00, 0x2e, "="},
298                 /* <LEFT BRACE> */
299                 {0x00, 0x2f, "["},
300                 /* <RIGHT BRACE> */
301                 {0x00, 0x30, "]"},
302                 /* <BACKSLASH> */
303                 {0x00, 0x31, "\\"},
304                 /* <HASH-TILDE> */
305                 {0x00, 0x32, "#"},
306                 /* <SEMICOLON> */
307                 {0x00, 0x33, ";"},
308                 /* <APOSTROPHE> */
309                 {0x00, 0x34, "'"},
310                 /* <GRAVE> */
311                 {0x00, 0x35, "`"},
312                 /* <COMMA> */
313                 {0x00, 0x36, ","},
314                 /* <DOT> */
315                 {0x00, 0x37, "."},
316                 /* <SLASH> */
317                 {0x00, 0x38, "/"},
318
319                 /* <LEFT-SHIFT><ENTER> */
320                 {0x02, 0x28, "\r"},
321                 /* <RIGHT-SHIFT><ESCAPE> */
322                 {0x20, 0x29, "\x1b"},
323                 /* <LEFT-SHIFT><BACKSPACE> */
324                 {0x02, 0x2a, "\x08"},
325                 /* <RIGHT-SHIFT><TAB> */
326                 {0x20, 0x2b, "\x09"},
327                 /* <LEFT-SHIFT><SPACE> */
328                 {0x02, 0x2c, " "},
329                 /* <MINUS> */
330                 {0x20, 0x2d, "_"},
331                 /* <LEFT-SHIFT><EQUAL> */
332                 {0x02, 0x2e, "+"},
333                 /* <RIGHT-SHIFT><LEFT BRACE> */
334                 {0x20, 0x2f, "{"},
335                 /* <LEFT-SHIFT><RIGHT BRACE> */
336                 {0x02, 0x30, "}"},
337                 /* <RIGHT-SHIFT><BACKSLASH> */
338                 {0x20, 0x31, "|"},
339                 /* <LEFT-SHIFT><HASH-TILDE> */
340                 {0x02, 0x32, "~"},
341                 /* <RIGHT-SHIFT><SEMICOLON> */
342                 {0x20, 0x33, ":"},
343                 /* <LEFT-SHIFT><APOSTROPHE> */
344                 {0x02, 0x34, "\""},
345                 /* <RIGHT-SHIFT><GRAVE> */
346                 {0x20, 0x35, "~"},
347                 /* <LEFT-SHIFT><COMMA> */
348                 {0x02, 0x36, "<"},
349                 /* <RIGHT-SHIFT><DOT> */
350                 {0x20, 0x37, ">"},
351                 /* <LEFT-SHIFT><SLASH> */
352                 {0x02, 0x38, "?"},
353 #ifdef CONFIG_USB_KEYBOARD_FN_KEYS
354                 /* <F1> */
355                 {0x00, 0x3a, "\x1bOP"},
356                 /* <F2> */
357                 {0x00, 0x3b, "\x1bOQ"},
358                 /* <F3> */
359                 {0x00, 0x3c, "\x1bOR"},
360                 /* <F4> */
361                 {0x00, 0x3d, "\x1bOS"},
362                 /* <F5> */
363                 {0x00, 0x3e, "\x1b[15~"},
364                 /* <F6> */
365                 {0x00, 0x3f, "\x1b[17~"},
366                 /* <F7> */
367                 {0x00, 0x40, "\x1b[18~"},
368                 /* <F8> */
369                 {0x00, 0x41, "\x1b[19~"},
370                 /* <F9> */
371                 {0x00, 0x42, "\x1b[20~"},
372                 /* <F10> */
373                 {0x00, 0x43, "\x1b[21~"},
374                 /* <F11> */
375                 {0x00, 0x44, "\x1b[23~"},
376                 /* <F12> */
377                 {0x00, 0x45, "\x1b[24~"},
378                 /* <INSERT> */
379                 {0x00, 0x49, "\x1b[2~"},
380                 /* <HOME> */
381                 {0x00, 0x4a, "\x1b[H"},
382                 /* <PAGE UP> */
383                 {0x00, 0x4b, "\x1b[5~"},
384                 /* <DELETE> */
385                 {0x00, 0x4c, "\x1b[3~"},
386                 /* <END> */
387                 {0x00, 0x4d, "\x1b[F"},
388                 /* <PAGE DOWN> */
389                 {0x00, 0x4e, "\x1b[6~"},
390                 /* <RIGHT> */
391                 {0x00, 0x4f, "\x1b[C"},
392                 /* <LEFT> */
393                 {0x00, 0x50, "\x1b[D"},
394                 /* <DOWN> */
395                 {0x00, 0x51, "\x1b[B"},
396                 /* <UP> */
397                 {0x00, 0x52, "\x1b[A"},
398 #endif /* CONFIG_USB_KEYBOARD_FN_KEYS */
399
400                 /* End of list */
401                 {0x00, 0x00, "\0"}
402         };
403
404
405         state_set_skip_delays(true);
406         ut_assertok(usb_init());
407
408         /* Initially there should be no characters */
409         ut_asserteq(0, tstc());
410
411         ut_assertok(uclass_get_device_by_name(UCLASS_USB_EMUL, "keyb@3",
412                                               &dev));
413
414         /*
415          * Add scan codes to the USB keyboard buffer. They should appear as
416          * corresponding characters and escape sequences in stdin.
417          */
418         for (pos = kbd_test_data; pos->scancode; ++pos) {
419                 const char *c;
420                 char scancodes[USB_KBD_BOOT_REPORT_SIZE] = {0};
421
422                 scancodes[0] = pos->modifiers;
423                 scancodes[2] = pos->scancode;
424
425                 ut_assertok(sandbox_usb_keyb_add_string(dev, scancodes));
426
427                 for (c = pos->result; *c; ++c) {
428                         ut_asserteq(1, tstc());
429                         ut_asserteq(*c, getc());
430                 }
431                 ut_asserteq(0, tstc());
432         }
433         ut_assertok(usb_stop());
434
435         return 0;
436 }
437 DM_TEST(dm_test_usb_keyb, DM_TESTF_SCAN_PDATA | DM_TESTF_SCAN_FDT);