summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSeung-Woo Kim <sw0312.kim@samsung.com>2024-07-22 12:58:56 +0900
committerSeung-Woo Kim <sw0312.kim@samsung.com>2024-07-22 16:05:19 +0900
commitffd01ec09d31d260c632160dbd0aa1d5841cd3e0 (patch)
tree5b9c423d43235c9fc59b51ddfead9dd15f05547e
parent17d98cf7b8a6cb92bf7bbc9dd4e4eb2db002d427 (diff)
downloadlinux-starfive-ffd01ec09d31d260c632160dbd0aa1d5841cd3e0.tar.gz
linux-starfive-ffd01ec09d31d260c632160dbd0aa1d5841cd3e0.tar.bz2
linux-starfive-ffd01ec09d31d260c632160dbd0aa1d5841cd3e0.zip
If the usb gadget of cdns3 drd device is used, set ep0 usb_req length with additional 2 bytes for zlp with exactly multiple of max packet length of the ep0 to resolve the cdns3 specific ep0 enumeration issue. The cdns3 has a known issue that zlp is missed when its usb_req size is exactly multiple of max packet length, 64 and it is not handled. In the visionfive2 board with cdns3 in its usb c port, board serial number is exactly 31 characters and including null character, utf-8 string length is 64, so the cdns3 zlp issue is occured during usb sdb enumeration for iSerial usb string descriptor. If it is fixed from cdns3 driver, this workaround can be reverted. Change-Id: I751c334d03bcf8fe94aa9f4b0367070bfc47c539 Ref: https://e2e.ti.com/support/processors-group/processors/f/processors-forum/1289171/am6411-no-usb-gadget-zlp-for-cdns3_ep0_run_transfer Suggested-by: Dongwoo Lee <dwoo08.lee@samsung.com> Signed-off-by: Seung-Woo Kim <sw0312.kim@samsung.com>
-rw-r--r--drivers/usb/gadget/composite.c9
1 files changed, 9 insertions, 0 deletions
diff --git a/drivers/usb/gadget/composite.c b/drivers/usb/gadget/composite.c
index 0ace45b66a31..8916ab46d4fb 100644
--- a/drivers/usb/gadget/composite.c
+++ b/drivers/usb/gadget/composite.c
@@ -2277,6 +2277,15 @@ check_value:
req->length = value;
req->context = cdev;
req->zero = value < w_length;
+
+#if defined(CONFIG_USB_CDNS3_GADGET)
+ /* workaround for visionfive2 cdns3 dual role device */
+ if (req->zero) {
+ if (value % cdev->gadget->ep0->maxpacket == 0)
+ req->length += 2;
+ }
+#endif
+
value = composite_ep0_queue(cdev, req, GFP_ATOMIC);
if (value < 0) {
DBG(cdev, "ep_queue --> %d\n", value);