usb.c 10 KB

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