lvstest.c 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476
  1. // SPDX-License-Identifier: GPL-2.0
  2. /*
  3. * drivers/usb/misc/lvstest.c
  4. *
  5. * Test pattern generation for Link Layer Validation System Tests
  6. *
  7. * Copyright (C) 2014 ST Microelectronics
  8. * Pratyush Anand <pratyush.anand@gmail.com>
  9. */
  10. #include <linux/init.h>
  11. #include <linux/kernel.h>
  12. #include <linux/module.h>
  13. #include <linux/platform_device.h>
  14. #include <linux/slab.h>
  15. #include <linux/usb.h>
  16. #include <linux/usb/ch11.h>
  17. #include <linux/usb/hcd.h>
  18. #include <linux/usb/phy.h>
  19. struct lvs_rh {
  20. /* root hub interface */
  21. struct usb_interface *intf;
  22. /* if lvs device connected */
  23. bool present;
  24. /* port no at which lvs device is present */
  25. int portnum;
  26. /* urb buffer */
  27. u8 buffer[8];
  28. /* class descriptor */
  29. struct usb_hub_descriptor descriptor;
  30. /* urb for polling interrupt pipe */
  31. struct urb *urb;
  32. /* LVH RH work */
  33. struct work_struct rh_work;
  34. /* RH port status */
  35. struct usb_port_status port_status;
  36. };
  37. static struct usb_device *create_lvs_device(struct usb_interface *intf)
  38. {
  39. struct usb_device *udev, *hdev;
  40. struct usb_hcd *hcd;
  41. struct lvs_rh *lvs = usb_get_intfdata(intf);
  42. if (!lvs->present) {
  43. dev_err(&intf->dev, "No LVS device is present\n");
  44. return NULL;
  45. }
  46. hdev = interface_to_usbdev(intf);
  47. hcd = bus_to_hcd(hdev->bus);
  48. udev = usb_alloc_dev(hdev, hdev->bus, lvs->portnum);
  49. if (!udev) {
  50. dev_err(&intf->dev, "Could not allocate lvs udev\n");
  51. return NULL;
  52. }
  53. udev->speed = USB_SPEED_SUPER;
  54. udev->ep0.desc.wMaxPacketSize = cpu_to_le16(512);
  55. usb_set_device_state(udev, USB_STATE_DEFAULT);
  56. if (hcd->driver->enable_device) {
  57. if (hcd->driver->enable_device(hcd, udev) < 0) {
  58. dev_err(&intf->dev, "Failed to enable\n");
  59. usb_put_dev(udev);
  60. return NULL;
  61. }
  62. }
  63. return udev;
  64. }
  65. static void destroy_lvs_device(struct usb_device *udev)
  66. {
  67. struct usb_device *hdev = udev->parent;
  68. struct usb_hcd *hcd = bus_to_hcd(hdev->bus);
  69. if (hcd->driver->free_dev)
  70. hcd->driver->free_dev(hcd, udev);
  71. usb_put_dev(udev);
  72. }
  73. static int lvs_rh_clear_port_feature(struct usb_device *hdev,
  74. int port1, int feature)
  75. {
  76. return usb_control_msg(hdev, usb_sndctrlpipe(hdev, 0),
  77. USB_REQ_CLEAR_FEATURE, USB_RT_PORT, feature, port1,
  78. NULL, 0, 1000);
  79. }
  80. static int lvs_rh_set_port_feature(struct usb_device *hdev,
  81. int port1, int feature)
  82. {
  83. return usb_control_msg(hdev, usb_sndctrlpipe(hdev, 0),
  84. USB_REQ_SET_FEATURE, USB_RT_PORT, feature, port1,
  85. NULL, 0, 1000);
  86. }
  87. static ssize_t u3_entry_store(struct device *dev,
  88. struct device_attribute *attr, const char *buf, size_t count)
  89. {
  90. struct usb_interface *intf = to_usb_interface(dev);
  91. struct usb_device *hdev = interface_to_usbdev(intf);
  92. struct lvs_rh *lvs = usb_get_intfdata(intf);
  93. struct usb_device *udev;
  94. int ret;
  95. udev = create_lvs_device(intf);
  96. if (!udev) {
  97. dev_err(dev, "failed to create lvs device\n");
  98. return -ENOMEM;
  99. }
  100. ret = lvs_rh_set_port_feature(hdev, lvs->portnum,
  101. USB_PORT_FEAT_SUSPEND);
  102. if (ret < 0)
  103. dev_err(dev, "can't issue U3 entry %d\n", ret);
  104. destroy_lvs_device(udev);
  105. if (ret < 0)
  106. return ret;
  107. return count;
  108. }
  109. static DEVICE_ATTR_WO(u3_entry);
  110. static ssize_t u3_exit_store(struct device *dev,
  111. struct device_attribute *attr, const char *buf, size_t count)
  112. {
  113. struct usb_interface *intf = to_usb_interface(dev);
  114. struct usb_device *hdev = interface_to_usbdev(intf);
  115. struct lvs_rh *lvs = usb_get_intfdata(intf);
  116. struct usb_device *udev;
  117. int ret;
  118. udev = create_lvs_device(intf);
  119. if (!udev) {
  120. dev_err(dev, "failed to create lvs device\n");
  121. return -ENOMEM;
  122. }
  123. ret = lvs_rh_clear_port_feature(hdev, lvs->portnum,
  124. USB_PORT_FEAT_SUSPEND);
  125. if (ret < 0)
  126. dev_err(dev, "can't issue U3 exit %d\n", ret);
  127. destroy_lvs_device(udev);
  128. if (ret < 0)
  129. return ret;
  130. return count;
  131. }
  132. static DEVICE_ATTR_WO(u3_exit);
  133. static ssize_t hot_reset_store(struct device *dev,
  134. struct device_attribute *attr, const char *buf, size_t count)
  135. {
  136. struct usb_interface *intf = to_usb_interface(dev);
  137. struct usb_device *hdev = interface_to_usbdev(intf);
  138. struct lvs_rh *lvs = usb_get_intfdata(intf);
  139. int ret;
  140. ret = lvs_rh_set_port_feature(hdev, lvs->portnum,
  141. USB_PORT_FEAT_RESET);
  142. if (ret < 0) {
  143. dev_err(dev, "can't issue hot reset %d\n", ret);
  144. return ret;
  145. }
  146. return count;
  147. }
  148. static DEVICE_ATTR_WO(hot_reset);
  149. static ssize_t warm_reset_store(struct device *dev,
  150. struct device_attribute *attr, const char *buf, size_t count)
  151. {
  152. struct usb_interface *intf = to_usb_interface(dev);
  153. struct usb_device *hdev = interface_to_usbdev(intf);
  154. struct lvs_rh *lvs = usb_get_intfdata(intf);
  155. int ret;
  156. ret = lvs_rh_set_port_feature(hdev, lvs->portnum,
  157. USB_PORT_FEAT_BH_PORT_RESET);
  158. if (ret < 0) {
  159. dev_err(dev, "can't issue warm reset %d\n", ret);
  160. return ret;
  161. }
  162. return count;
  163. }
  164. static DEVICE_ATTR_WO(warm_reset);
  165. static ssize_t u2_timeout_store(struct device *dev,
  166. struct device_attribute *attr, const char *buf, size_t count)
  167. {
  168. struct usb_interface *intf = to_usb_interface(dev);
  169. struct usb_device *hdev = interface_to_usbdev(intf);
  170. struct lvs_rh *lvs = usb_get_intfdata(intf);
  171. unsigned long val;
  172. int ret;
  173. ret = kstrtoul(buf, 10, &val);
  174. if (ret < 0) {
  175. dev_err(dev, "couldn't parse string %d\n", ret);
  176. return ret;
  177. }
  178. if (val > 127)
  179. return -EINVAL;
  180. ret = lvs_rh_set_port_feature(hdev, lvs->portnum | (val << 8),
  181. USB_PORT_FEAT_U2_TIMEOUT);
  182. if (ret < 0) {
  183. dev_err(dev, "Error %d while setting U2 timeout %ld\n", ret, val);
  184. return ret;
  185. }
  186. return count;
  187. }
  188. static DEVICE_ATTR_WO(u2_timeout);
  189. static ssize_t u1_timeout_store(struct device *dev,
  190. struct device_attribute *attr, const char *buf, size_t count)
  191. {
  192. struct usb_interface *intf = to_usb_interface(dev);
  193. struct usb_device *hdev = interface_to_usbdev(intf);
  194. struct lvs_rh *lvs = usb_get_intfdata(intf);
  195. unsigned long val;
  196. int ret;
  197. ret = kstrtoul(buf, 10, &val);
  198. if (ret < 0) {
  199. dev_err(dev, "couldn't parse string %d\n", ret);
  200. return ret;
  201. }
  202. if (val > 127)
  203. return -EINVAL;
  204. ret = lvs_rh_set_port_feature(hdev, lvs->portnum | (val << 8),
  205. USB_PORT_FEAT_U1_TIMEOUT);
  206. if (ret < 0) {
  207. dev_err(dev, "Error %d while setting U1 timeout %ld\n", ret, val);
  208. return ret;
  209. }
  210. return count;
  211. }
  212. static DEVICE_ATTR_WO(u1_timeout);
  213. static ssize_t get_dev_desc_store(struct device *dev,
  214. struct device_attribute *attr, const char *buf, size_t count)
  215. {
  216. struct usb_interface *intf = to_usb_interface(dev);
  217. struct usb_device *udev;
  218. struct usb_device_descriptor *descriptor;
  219. int ret;
  220. descriptor = kmalloc(sizeof(*descriptor), GFP_KERNEL);
  221. if (!descriptor)
  222. return -ENOMEM;
  223. udev = create_lvs_device(intf);
  224. if (!udev) {
  225. dev_err(dev, "failed to create lvs device\n");
  226. ret = -ENOMEM;
  227. goto free_desc;
  228. }
  229. ret = usb_control_msg(udev, (PIPE_CONTROL << 30) | USB_DIR_IN,
  230. USB_REQ_GET_DESCRIPTOR, USB_DIR_IN, USB_DT_DEVICE << 8,
  231. 0, descriptor, sizeof(*descriptor),
  232. USB_CTRL_GET_TIMEOUT);
  233. if (ret < 0)
  234. dev_err(dev, "can't read device descriptor %d\n", ret);
  235. destroy_lvs_device(udev);
  236. free_desc:
  237. kfree(descriptor);
  238. if (ret < 0)
  239. return ret;
  240. return count;
  241. }
  242. static DEVICE_ATTR_WO(get_dev_desc);
  243. static ssize_t enable_compliance_store(struct device *dev,
  244. struct device_attribute *attr, const char *buf, size_t count)
  245. {
  246. struct usb_interface *intf = to_usb_interface(dev);
  247. struct usb_device *hdev = interface_to_usbdev(intf);
  248. struct lvs_rh *lvs = usb_get_intfdata(intf);
  249. int ret;
  250. ret = lvs_rh_set_port_feature(hdev,
  251. lvs->portnum | USB_SS_PORT_LS_COMP_MOD << 3,
  252. USB_PORT_FEAT_LINK_STATE);
  253. if (ret < 0) {
  254. dev_err(dev, "can't enable compliance mode %d\n", ret);
  255. return ret;
  256. }
  257. return count;
  258. }
  259. static DEVICE_ATTR_WO(enable_compliance);
  260. static struct attribute *lvs_attrs[] = {
  261. &dev_attr_get_dev_desc.attr,
  262. &dev_attr_u1_timeout.attr,
  263. &dev_attr_u2_timeout.attr,
  264. &dev_attr_hot_reset.attr,
  265. &dev_attr_warm_reset.attr,
  266. &dev_attr_u3_entry.attr,
  267. &dev_attr_u3_exit.attr,
  268. &dev_attr_enable_compliance.attr,
  269. NULL
  270. };
  271. ATTRIBUTE_GROUPS(lvs);
  272. static void lvs_rh_work(struct work_struct *work)
  273. {
  274. struct lvs_rh *lvs = container_of(work, struct lvs_rh, rh_work);
  275. struct usb_interface *intf = lvs->intf;
  276. struct usb_device *hdev = interface_to_usbdev(intf);
  277. struct usb_hcd *hcd = bus_to_hcd(hdev->bus);
  278. struct usb_hub_descriptor *descriptor = &lvs->descriptor;
  279. struct usb_port_status *port_status = &lvs->port_status;
  280. int i, ret = 0;
  281. u16 portchange;
  282. /* Examine each root port */
  283. for (i = 1; i <= descriptor->bNbrPorts; i++) {
  284. ret = usb_control_msg(hdev, usb_rcvctrlpipe(hdev, 0),
  285. USB_REQ_GET_STATUS, USB_DIR_IN | USB_RT_PORT, 0, i,
  286. port_status, sizeof(*port_status), 1000);
  287. if (ret < 4)
  288. continue;
  289. portchange = le16_to_cpu(port_status->wPortChange);
  290. if (portchange & USB_PORT_STAT_C_LINK_STATE)
  291. lvs_rh_clear_port_feature(hdev, i,
  292. USB_PORT_FEAT_C_PORT_LINK_STATE);
  293. if (portchange & USB_PORT_STAT_C_ENABLE)
  294. lvs_rh_clear_port_feature(hdev, i,
  295. USB_PORT_FEAT_C_ENABLE);
  296. if (portchange & USB_PORT_STAT_C_RESET)
  297. lvs_rh_clear_port_feature(hdev, i,
  298. USB_PORT_FEAT_C_RESET);
  299. if (portchange & USB_PORT_STAT_C_BH_RESET)
  300. lvs_rh_clear_port_feature(hdev, i,
  301. USB_PORT_FEAT_C_BH_PORT_RESET);
  302. if (portchange & USB_PORT_STAT_C_CONNECTION) {
  303. lvs_rh_clear_port_feature(hdev, i,
  304. USB_PORT_FEAT_C_CONNECTION);
  305. if (le16_to_cpu(port_status->wPortStatus) &
  306. USB_PORT_STAT_CONNECTION) {
  307. lvs->present = true;
  308. lvs->portnum = i;
  309. if (hcd->usb_phy)
  310. usb_phy_notify_connect(hcd->usb_phy,
  311. USB_SPEED_SUPER);
  312. } else {
  313. lvs->present = false;
  314. if (hcd->usb_phy)
  315. usb_phy_notify_disconnect(hcd->usb_phy,
  316. USB_SPEED_SUPER);
  317. }
  318. break;
  319. }
  320. }
  321. ret = usb_submit_urb(lvs->urb, GFP_KERNEL);
  322. if (ret != 0 && ret != -ENODEV && ret != -EPERM)
  323. dev_err(&intf->dev, "urb resubmit error %d\n", ret);
  324. }
  325. static void lvs_rh_irq(struct urb *urb)
  326. {
  327. struct lvs_rh *lvs = urb->context;
  328. schedule_work(&lvs->rh_work);
  329. }
  330. static int lvs_rh_probe(struct usb_interface *intf,
  331. const struct usb_device_id *id)
  332. {
  333. struct usb_device *hdev;
  334. struct usb_host_interface *desc;
  335. struct usb_endpoint_descriptor *endpoint;
  336. struct lvs_rh *lvs;
  337. unsigned int pipe;
  338. int ret, maxp;
  339. hdev = interface_to_usbdev(intf);
  340. desc = intf->cur_altsetting;
  341. ret = usb_find_int_in_endpoint(desc, &endpoint);
  342. if (ret)
  343. return ret;
  344. /* valid only for SS root hub */
  345. if (hdev->descriptor.bDeviceProtocol != USB_HUB_PR_SS || hdev->parent) {
  346. dev_err(&intf->dev, "Bind LVS driver with SS root Hub only\n");
  347. return -EINVAL;
  348. }
  349. lvs = devm_kzalloc(&intf->dev, sizeof(*lvs), GFP_KERNEL);
  350. if (!lvs)
  351. return -ENOMEM;
  352. lvs->intf = intf;
  353. usb_set_intfdata(intf, lvs);
  354. /* how many number of ports this root hub has */
  355. ret = usb_control_msg(hdev, usb_rcvctrlpipe(hdev, 0),
  356. USB_REQ_GET_DESCRIPTOR, USB_DIR_IN | USB_RT_HUB,
  357. USB_DT_SS_HUB << 8, 0, &lvs->descriptor,
  358. USB_DT_SS_HUB_SIZE, USB_CTRL_GET_TIMEOUT);
  359. if (ret < (USB_DT_HUB_NONVAR_SIZE + 2)) {
  360. dev_err(&hdev->dev, "wrong root hub descriptor read %d\n", ret);
  361. return ret < 0 ? ret : -EINVAL;
  362. }
  363. /* submit urb to poll interrupt endpoint */
  364. lvs->urb = usb_alloc_urb(0, GFP_KERNEL);
  365. if (!lvs->urb)
  366. return -ENOMEM;
  367. INIT_WORK(&lvs->rh_work, lvs_rh_work);
  368. pipe = usb_rcvintpipe(hdev, endpoint->bEndpointAddress);
  369. maxp = usb_maxpacket(hdev, pipe);
  370. usb_fill_int_urb(lvs->urb, hdev, pipe, &lvs->buffer[0], maxp,
  371. lvs_rh_irq, lvs, endpoint->bInterval);
  372. ret = usb_submit_urb(lvs->urb, GFP_KERNEL);
  373. if (ret < 0) {
  374. dev_err(&intf->dev, "couldn't submit lvs urb %d\n", ret);
  375. goto free_urb;
  376. }
  377. return ret;
  378. free_urb:
  379. usb_free_urb(lvs->urb);
  380. return ret;
  381. }
  382. static void lvs_rh_disconnect(struct usb_interface *intf)
  383. {
  384. struct lvs_rh *lvs = usb_get_intfdata(intf);
  385. usb_poison_urb(lvs->urb); /* used in scheduled work */
  386. flush_work(&lvs->rh_work);
  387. usb_free_urb(lvs->urb);
  388. }
  389. static struct usb_driver lvs_driver = {
  390. .name = "lvs",
  391. .probe = lvs_rh_probe,
  392. .disconnect = lvs_rh_disconnect,
  393. .dev_groups = lvs_groups,
  394. };
  395. module_usb_driver(lvs_driver);
  396. MODULE_DESCRIPTION("Link Layer Validation System Driver");
  397. MODULE_LICENSE("GPL");