Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge tag 'fixes-for-v4.4-rc2' of git://git.kernel.org/pub/scm/linux/kernel/git/balbi/usb into usb-linus

Felipe writes:

usb: fixes for v4.4-rc2

First round of fixes for this -rc cycle. We have the
usual set of miscellaneous fixes. The important
thing here is support for Intel Broxton SoC on dwc3,
some fixes for Rockchip SoCs on dwc2 and a fix on
dwc3 to let it report lower speeds than
USB_SPEED_SUPER.

+64 -23
+5 -4
drivers/usb/dwc2/hcd.c
··· 324 324 */ 325 325 static void dwc2_hcd_rem_wakeup(struct dwc2_hsotg *hsotg) 326 326 { 327 - if (hsotg->lx_state == DWC2_L2) { 327 + if (hsotg->bus_suspended) { 328 328 hsotg->flags.b.port_suspend_change = 1; 329 329 usb_hcd_resume_root_hub(hsotg->priv); 330 - } else { 331 - hsotg->flags.b.port_l1_change = 1; 332 330 } 331 + 332 + if (hsotg->lx_state == DWC2_L1) 333 + hsotg->flags.b.port_l1_change = 1; 333 334 } 334 335 335 336 /** ··· 1429 1428 dev_dbg(hsotg->dev, "Clear Resume: HPRT0=%0x\n", 1430 1429 dwc2_readl(hsotg->regs + HPRT0)); 1431 1430 1432 - hsotg->bus_suspended = 0; 1433 1431 dwc2_hcd_rem_wakeup(hsotg); 1432 + hsotg->bus_suspended = 0; 1434 1433 1435 1434 /* Change to L0 state */ 1436 1435 hsotg->lx_state = DWC2_L0;
+2 -1
drivers/usb/dwc2/platform.c
··· 108 108 .host_ls_low_power_phy_clk = -1, 109 109 .ts_dline = -1, 110 110 .reload_ctl = -1, 111 - .ahbcfg = 0x7, /* INCR16 */ 111 + .ahbcfg = GAHBCFG_HBSTLEN_INCR16 << 112 + GAHBCFG_HBSTLEN_SHIFT, 112 113 .uframe_sched = -1, 113 114 .external_id_pin_ctl = -1, 114 115 .hibernation = -1,
+4
drivers/usb/dwc3/dwc3-pci.c
··· 34 34 #define PCI_DEVICE_ID_INTEL_BSW 0x22b7 35 35 #define PCI_DEVICE_ID_INTEL_SPTLP 0x9d30 36 36 #define PCI_DEVICE_ID_INTEL_SPTH 0xa130 37 + #define PCI_DEVICE_ID_INTEL_BXT 0x0aaa 38 + #define PCI_DEVICE_ID_INTEL_APL 0x5aaa 37 39 38 40 static const struct acpi_gpio_params reset_gpios = { 0, 0, false }; 39 41 static const struct acpi_gpio_params cs_gpios = { 1, 0, false }; ··· 212 210 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_MRFLD), }, 213 211 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_SPTLP), }, 214 212 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_SPTH), }, 213 + { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_BXT), }, 214 + { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_APL), }, 215 215 { PCI_DEVICE(PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_NL_USB), }, 216 216 { } /* Terminating Entry */ 217 217 };
+23 -1
drivers/usb/dwc3/gadget.c
··· 2744 2744 } 2745 2745 2746 2746 dwc->gadget.ops = &dwc3_gadget_ops; 2747 - dwc->gadget.max_speed = USB_SPEED_SUPER; 2748 2747 dwc->gadget.speed = USB_SPEED_UNKNOWN; 2749 2748 dwc->gadget.sg_supported = true; 2750 2749 dwc->gadget.name = "dwc3-gadget"; 2750 + 2751 + /* 2752 + * FIXME We might be setting max_speed to <SUPER, however versions 2753 + * <2.20a of dwc3 have an issue with metastability (documented 2754 + * elsewhere in this driver) which tells us we can't set max speed to 2755 + * anything lower than SUPER. 2756 + * 2757 + * Because gadget.max_speed is only used by composite.c and function 2758 + * drivers (i.e. it won't go into dwc3's registers) we are allowing this 2759 + * to happen so we avoid sending SuperSpeed Capability descriptor 2760 + * together with our BOS descriptor as that could confuse host into 2761 + * thinking we can handle super speed. 2762 + * 2763 + * Note that, in fact, we won't even support GetBOS requests when speed 2764 + * is less than super speed because we don't have means, yet, to tell 2765 + * composite.c that we are USB 2.0 + LPM ECN. 2766 + */ 2767 + if (dwc->revision < DWC3_REVISION_220A) 2768 + dwc3_trace(trace_dwc3_gadget, 2769 + "Changing max_speed on rev %08x\n", 2770 + dwc->revision); 2771 + 2772 + dwc->gadget.max_speed = dwc->maximum_speed; 2751 2773 2752 2774 /* 2753 2775 * Per databook, DWC3 needs buffer size to be aligned to MaxPacketSize
+1 -1
drivers/usb/gadget/function/f_loopback.c
··· 329 329 for (i = 0; i < loop->qlen && result == 0; i++) { 330 330 result = -ENOMEM; 331 331 332 - in_req = usb_ep_alloc_request(loop->in_ep, GFP_KERNEL); 332 + in_req = usb_ep_alloc_request(loop->in_ep, GFP_ATOMIC); 333 333 if (!in_req) 334 334 goto fail; 335 335
+1 -1
drivers/usb/gadget/udc/atmel_usba_udc.c
··· 1633 1633 spin_lock(&udc->lock); 1634 1634 1635 1635 int_enb = usba_int_enb_get(udc); 1636 - status = usba_readl(udc, INT_STA) & int_enb; 1636 + status = usba_readl(udc, INT_STA) & (int_enb | USBA_HIGH_SPEED); 1637 1637 DBG(DBG_INT, "irq, status=%#08x\n", status); 1638 1638 1639 1639 if (status & USBA_DET_SUSPEND) {
+6 -6
drivers/usb/musb/musb_core.c
··· 132 132 /*-------------------------------------------------------------------------*/ 133 133 134 134 #ifndef CONFIG_BLACKFIN 135 - static int musb_ulpi_read(struct usb_phy *phy, u32 offset) 135 + static int musb_ulpi_read(struct usb_phy *phy, u32 reg) 136 136 { 137 137 void __iomem *addr = phy->io_priv; 138 138 int i = 0; ··· 151 151 * ULPICarKitControlDisableUTMI after clearing POWER_SUSPENDM. 152 152 */ 153 153 154 - musb_writeb(addr, MUSB_ULPI_REG_ADDR, (u8)offset); 154 + musb_writeb(addr, MUSB_ULPI_REG_ADDR, (u8)reg); 155 155 musb_writeb(addr, MUSB_ULPI_REG_CONTROL, 156 156 MUSB_ULPI_REG_REQ | MUSB_ULPI_RDN_WR); 157 157 ··· 176 176 return ret; 177 177 } 178 178 179 - static int musb_ulpi_write(struct usb_phy *phy, u32 offset, u32 data) 179 + static int musb_ulpi_write(struct usb_phy *phy, u32 val, u32 reg) 180 180 { 181 181 void __iomem *addr = phy->io_priv; 182 182 int i = 0; ··· 191 191 power &= ~MUSB_POWER_SUSPENDM; 192 192 musb_writeb(addr, MUSB_POWER, power); 193 193 194 - musb_writeb(addr, MUSB_ULPI_REG_ADDR, (u8)offset); 195 - musb_writeb(addr, MUSB_ULPI_REG_DATA, (u8)data); 194 + musb_writeb(addr, MUSB_ULPI_REG_ADDR, (u8)reg); 195 + musb_writeb(addr, MUSB_ULPI_REG_DATA, (u8)val); 196 196 musb_writeb(addr, MUSB_ULPI_REG_CONTROL, MUSB_ULPI_REG_REQ); 197 197 198 198 while (!(musb_readb(addr, MUSB_ULPI_REG_CONTROL) ··· 1668 1668 static bool use_dma = 1; 1669 1669 1670 1670 /* "modprobe ... use_dma=0" etc */ 1671 - module_param(use_dma, bool, 0); 1671 + module_param(use_dma, bool, 0644); 1672 1672 MODULE_PARM_DESC(use_dma, "enable/disable use of DMA"); 1673 1673 1674 1674 void musb_dma_completion(struct musb *musb, u8 epnum, u8 transmit)
+16 -6
drivers/usb/musb/musb_host.c
··· 112 112 struct musb *musb = ep->musb; 113 113 void __iomem *epio = ep->regs; 114 114 u16 csr; 115 - u16 lastcsr = 0; 116 115 int retries = 1000; 117 116 118 117 csr = musb_readw(epio, MUSB_TXCSR); 119 118 while (csr & MUSB_TXCSR_FIFONOTEMPTY) { 120 - if (csr != lastcsr) 121 - dev_dbg(musb->controller, "Host TX FIFONOTEMPTY csr: %02x\n", csr); 122 - lastcsr = csr; 123 119 csr |= MUSB_TXCSR_FLUSHFIFO | MUSB_TXCSR_TXPKTRDY; 124 120 musb_writew(epio, MUSB_TXCSR, csr); 125 121 csr = musb_readw(epio, MUSB_TXCSR); 126 - if (WARN(retries-- < 1, 122 + 123 + /* 124 + * FIXME: sometimes the tx fifo flush failed, it has been 125 + * observed during device disconnect on AM335x. 126 + * 127 + * To reproduce the issue, ensure tx urb(s) are queued when 128 + * unplug the usb device which is connected to AM335x usb 129 + * host port. 130 + * 131 + * I found using a usb-ethernet device and running iperf 132 + * (client on AM335x) has very high chance to trigger it. 133 + * 134 + * Better to turn on dev_dbg() in musb_cleanup_urb() with 135 + * CPPI enabled to see the issue when aborting the tx channel. 136 + */ 137 + if (dev_WARN_ONCE(musb->controller, retries-- < 1, 127 138 "Could not flush host TX%d fifo: csr: %04x\n", 128 139 ep->epnum, csr)) 129 140 return; 130 - mdelay(1); 131 141 } 132 142 } 133 143
+5 -2
drivers/usb/phy/phy-mxs-usb.c
··· 452 452 struct clk *clk; 453 453 struct mxs_phy *mxs_phy; 454 454 int ret; 455 - const struct of_device_id *of_id = 456 - of_match_device(mxs_phy_dt_ids, &pdev->dev); 455 + const struct of_device_id *of_id; 457 456 struct device_node *np = pdev->dev.of_node; 457 + 458 + of_id = of_match_device(mxs_phy_dt_ids, &pdev->dev); 459 + if (!of_id) 460 + return -ENODEV; 458 461 459 462 res = platform_get_resource(pdev, IORESOURCE_MEM, 0); 460 463 base = devm_ioremap_resource(&pdev->dev, res);
+1 -1
drivers/usb/phy/phy-omap-otg.c
··· 105 105 extcon = extcon_get_extcon_dev(config->extcon); 106 106 if (!extcon) 107 107 return -EPROBE_DEFER; 108 - otg_dev->extcon = extcon; 109 108 110 109 otg_dev = devm_kzalloc(&pdev->dev, sizeof(*otg_dev), GFP_KERNEL); 111 110 if (!otg_dev) ··· 114 115 if (IS_ERR(otg_dev->base)) 115 116 return PTR_ERR(otg_dev->base); 116 117 118 + otg_dev->extcon = extcon; 117 119 otg_dev->id_nb.notifier_call = omap_otg_id_notifier; 118 120 otg_dev->vbus_nb.notifier_call = omap_otg_vbus_notifier; 119 121