Merge tag 'usb-3.17-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/usb
Pull USB updates from Greg KH: "Here is the big USB driver update for 3.17-rc1. Loads of gadget driver changes in here, including some big file movements to make things easier to manage over time. There's also the usual xhci and uas driver updates, and a handful of other changes in here. The changelog has the full details. All of these have been in linux-next for a while" * tag 'usb-3.17-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/usb: (211 commits) USB: devio: fix issue with log flooding uas: Log a warning when we cannot use uas because the hcd lacks streams uas: Only complain about missing sg if all other checks succeed xhci: Add missing checks for xhci_alloc_command failure xhci: Rename Asrock P67 pci product-id to EJ168 xhci: Blacklist using streams on the Etron EJ168 controller uas: Limit qdepth to 32 when connected over usb-2 uwb/whci: use correct structure type name in sizeof usb-core bInterval quirk USB: serial: ftdi_sio: Add support for new Xsens devices USB: serial: ftdi_sio: Annotate the current Xsens PID assignments usb: chipidea: debug: fix sparse non static symbol warnings usb: ci_hdrc_imx doc: fsl,usbphy is required usb: ci_hdrc_imx: Return -EINVAL for missing USB PHY usb: core: allow zero packet flag for interrupt urbs usb: lvstest: Fix sparse warnings generated by kbuild test bot USB: core: hcd-pci: free IRQ before disabling PCI device when shutting down phy: miphy365x: Represent each PHY channel as a DT subnode phy: miphy365x: Provide support for the MiPHY356x Generic PHY phy: miphy365x: Add Device Tree bindings for the MiPHY365x ...
This commit is contained in:
@@ -199,6 +199,17 @@ static int usb_parse_endpoint(struct device *ddev, int cfgno, int inum,
|
||||
if (n == 0)
|
||||
n = 9; /* 32 ms = 2^(9-1) uframes */
|
||||
j = 16;
|
||||
|
||||
/*
|
||||
* Adjust bInterval for quirked devices.
|
||||
* This quirk fixes bIntervals reported in
|
||||
* linear microframes.
|
||||
*/
|
||||
if (to_usb_device(ddev)->quirks &
|
||||
USB_QUIRK_LINEAR_UFRAME_INTR_BINTERVAL) {
|
||||
n = clamp(fls(d->bInterval), i, j);
|
||||
i = j = n;
|
||||
}
|
||||
break;
|
||||
default: /* USB_SPEED_FULL or _LOW */
|
||||
/* For low-speed, 10 ms is the official minimum.
|
||||
|
@@ -1509,7 +1509,7 @@ static int proc_do_submiturb(struct usb_dev_state *ps, struct usbdevfs_urb *uurb
|
||||
u = (is_in ? URB_DIR_IN : URB_DIR_OUT);
|
||||
if (uurb->flags & USBDEVFS_URB_ISO_ASAP)
|
||||
u |= URB_ISO_ASAP;
|
||||
if (uurb->flags & USBDEVFS_URB_SHORT_NOT_OK)
|
||||
if (uurb->flags & USBDEVFS_URB_SHORT_NOT_OK && is_in)
|
||||
u |= URB_SHORT_NOT_OK;
|
||||
if (uurb->flags & USBDEVFS_URB_NO_FSBR)
|
||||
u |= URB_NO_FSBR;
|
||||
|
@@ -417,10 +417,11 @@ static int usb_unbind_interface(struct device *dev)
|
||||
*/
|
||||
lpm_disable_error = usb_unlocked_disable_lpm(udev);
|
||||
|
||||
/* Terminate all URBs for this interface unless the driver
|
||||
* supports "soft" unbinding.
|
||||
/*
|
||||
* Terminate all URBs for this interface unless the driver
|
||||
* supports "soft" unbinding and the device is still present.
|
||||
*/
|
||||
if (!driver->soft_unbind)
|
||||
if (!driver->soft_unbind || udev->state == USB_STATE_NOTATTACHED)
|
||||
usb_disable_interface(udev, intf, false);
|
||||
|
||||
driver->disconnect(intf);
|
||||
|
@@ -380,6 +380,8 @@ void usb_hcd_pci_shutdown(struct pci_dev *dev)
|
||||
if (test_bit(HCD_FLAG_HW_ACCESSIBLE, &hcd->flags) &&
|
||||
hcd->driver->shutdown) {
|
||||
hcd->driver->shutdown(hcd);
|
||||
if (usb_hcd_is_primary_hcd(hcd) && hcd->irq > 0)
|
||||
free_irq(hcd->irq, hcd);
|
||||
pci_disable_device(dev);
|
||||
}
|
||||
}
|
||||
|
@@ -855,8 +855,6 @@ static ssize_t authorized_default_show(struct device *dev,
|
||||
struct usb_bus *usb_bus = rh_usb_dev->bus;
|
||||
struct usb_hcd *usb_hcd;
|
||||
|
||||
if (usb_bus == NULL) /* FIXME: not sure if this case is possible */
|
||||
return -ENODEV;
|
||||
usb_hcd = bus_to_hcd(usb_bus);
|
||||
return snprintf(buf, PAGE_SIZE, "%u\n", usb_hcd->authorized_default);
|
||||
}
|
||||
@@ -871,8 +869,6 @@ static ssize_t authorized_default_store(struct device *dev,
|
||||
struct usb_bus *usb_bus = rh_usb_dev->bus;
|
||||
struct usb_hcd *usb_hcd;
|
||||
|
||||
if (usb_bus == NULL) /* FIXME: not sure if this case is possible */
|
||||
return -ENODEV;
|
||||
usb_hcd = bus_to_hcd(usb_bus);
|
||||
result = sscanf(buf, "%u\n", &val);
|
||||
if (result == 1) {
|
||||
|
@@ -2606,13 +2606,20 @@ static int hub_port_reset(struct usb_hub *hub, int port1,
|
||||
/* Is a USB 3.0 port in the Inactive or Compliance Mode state?
|
||||
* Port worm reset is required to recover
|
||||
*/
|
||||
static bool hub_port_warm_reset_required(struct usb_hub *hub, u16 portstatus)
|
||||
static bool hub_port_warm_reset_required(struct usb_hub *hub, int port1,
|
||||
u16 portstatus)
|
||||
{
|
||||
return hub_is_superspeed(hub->hdev) &&
|
||||
(((portstatus & USB_PORT_STAT_LINK_STATE) ==
|
||||
USB_SS_PORT_LS_SS_INACTIVE) ||
|
||||
((portstatus & USB_PORT_STAT_LINK_STATE) ==
|
||||
USB_SS_PORT_LS_COMP_MOD)) ;
|
||||
u16 link_state;
|
||||
|
||||
if (!hub_is_superspeed(hub->hdev))
|
||||
return false;
|
||||
|
||||
if (test_bit(port1, hub->warm_reset_bits))
|
||||
return true;
|
||||
|
||||
link_state = portstatus & USB_PORT_STAT_LINK_STATE;
|
||||
return link_state == USB_SS_PORT_LS_SS_INACTIVE
|
||||
|| link_state == USB_SS_PORT_LS_COMP_MOD;
|
||||
}
|
||||
|
||||
static int hub_port_wait_reset(struct usb_hub *hub, int port1,
|
||||
@@ -2649,7 +2656,7 @@ static int hub_port_wait_reset(struct usb_hub *hub, int port1,
|
||||
if ((portstatus & USB_PORT_STAT_RESET))
|
||||
return -EBUSY;
|
||||
|
||||
if (hub_port_warm_reset_required(hub, portstatus))
|
||||
if (hub_port_warm_reset_required(hub, port1, portstatus))
|
||||
return -ENOTCONN;
|
||||
|
||||
/* Device went away? */
|
||||
@@ -2749,9 +2756,10 @@ static int hub_port_reset(struct usb_hub *hub, int port1,
|
||||
if (status < 0)
|
||||
goto done;
|
||||
|
||||
if (hub_port_warm_reset_required(hub, portstatus))
|
||||
if (hub_port_warm_reset_required(hub, port1, portstatus))
|
||||
warm = true;
|
||||
}
|
||||
clear_bit(port1, hub->warm_reset_bits);
|
||||
|
||||
/* Reset the port */
|
||||
for (i = 0; i < PORT_RESET_TRIES; i++) {
|
||||
@@ -2788,7 +2796,8 @@ static int hub_port_reset(struct usb_hub *hub, int port1,
|
||||
&portstatus, &portchange) < 0)
|
||||
goto done;
|
||||
|
||||
if (!hub_port_warm_reset_required(hub, portstatus))
|
||||
if (!hub_port_warm_reset_required(hub, port1,
|
||||
portstatus))
|
||||
goto done;
|
||||
|
||||
/*
|
||||
@@ -2875,8 +2884,13 @@ static int check_port_resume_type(struct usb_device *udev,
|
||||
{
|
||||
struct usb_port *port_dev = hub->ports[port1 - 1];
|
||||
|
||||
/* Is a warm reset needed to recover the connection? */
|
||||
if (status == 0 && udev->reset_resume
|
||||
&& hub_port_warm_reset_required(hub, port1, portstatus)) {
|
||||
/* pass */;
|
||||
}
|
||||
/* Is the device still present? */
|
||||
if (status || port_is_suspended(hub, portstatus) ||
|
||||
else if (status || port_is_suspended(hub, portstatus) ||
|
||||
!port_is_power_on(hub, portstatus) ||
|
||||
!(portstatus & USB_PORT_STAT_CONNECTION)) {
|
||||
if (status >= 0)
|
||||
@@ -3263,6 +3277,43 @@ static int finish_port_resume(struct usb_device *udev)
|
||||
return status;
|
||||
}
|
||||
|
||||
/*
|
||||
* There are some SS USB devices which take longer time for link training.
|
||||
* XHCI specs 4.19.4 says that when Link training is successful, port
|
||||
* sets CSC bit to 1. So if SW reads port status before successful link
|
||||
* training, then it will not find device to be present.
|
||||
* USB Analyzer log with such buggy devices show that in some cases
|
||||
* device switch on the RX termination after long delay of host enabling
|
||||
* the VBUS. In few other cases it has been seen that device fails to
|
||||
* negotiate link training in first attempt. It has been
|
||||
* reported till now that few devices take as long as 2000 ms to train
|
||||
* the link after host enabling its VBUS and termination. Following
|
||||
* routine implements a 2000 ms timeout for link training. If in a case
|
||||
* link trains before timeout, loop will exit earlier.
|
||||
*
|
||||
* FIXME: If a device was connected before suspend, but was removed
|
||||
* while system was asleep, then the loop in the following routine will
|
||||
* only exit at timeout.
|
||||
*
|
||||
* This routine should only be called when persist is enabled for a SS
|
||||
* device.
|
||||
*/
|
||||
static int wait_for_ss_port_enable(struct usb_device *udev,
|
||||
struct usb_hub *hub, int *port1,
|
||||
u16 *portchange, u16 *portstatus)
|
||||
{
|
||||
int status = 0, delay_ms = 0;
|
||||
|
||||
while (delay_ms < 2000) {
|
||||
if (status || *portstatus & USB_PORT_STAT_CONNECTION)
|
||||
break;
|
||||
msleep(20);
|
||||
delay_ms += 20;
|
||||
status = hub_port_status(hub, *port1, portstatus, portchange);
|
||||
}
|
||||
return status;
|
||||
}
|
||||
|
||||
/*
|
||||
* usb_port_resume - re-activate a suspended usb device's upstream port
|
||||
* @udev: device to re-activate, not a root hub
|
||||
@@ -3359,6 +3410,10 @@ int usb_port_resume(struct usb_device *udev, pm_message_t msg)
|
||||
}
|
||||
}
|
||||
|
||||
if (udev->persist_enabled && hub_is_superspeed(hub->hdev))
|
||||
status = wait_for_ss_port_enable(udev, hub, &port1, &portchange,
|
||||
&portstatus);
|
||||
|
||||
status = check_port_resume_type(udev,
|
||||
hub, port1, status, portchange, portstatus);
|
||||
if (status == 0)
|
||||
@@ -3879,7 +3934,8 @@ int usb_disable_lpm(struct usb_device *udev)
|
||||
|
||||
if (!udev || !udev->parent ||
|
||||
udev->speed != USB_SPEED_SUPER ||
|
||||
!udev->lpm_capable)
|
||||
!udev->lpm_capable ||
|
||||
udev->state < USB_STATE_DEFAULT)
|
||||
return 0;
|
||||
|
||||
hcd = bus_to_hcd(udev->bus);
|
||||
@@ -3935,7 +3991,8 @@ void usb_enable_lpm(struct usb_device *udev)
|
||||
|
||||
if (!udev || !udev->parent ||
|
||||
udev->speed != USB_SPEED_SUPER ||
|
||||
!udev->lpm_capable)
|
||||
!udev->lpm_capable ||
|
||||
udev->state < USB_STATE_DEFAULT)
|
||||
return;
|
||||
|
||||
udev->lpm_disable_count--;
|
||||
@@ -4550,6 +4607,7 @@ static void hub_port_connect(struct usb_hub *hub, int port1, u16 portstatus,
|
||||
struct usb_hcd *hcd = bus_to_hcd(hdev->bus);
|
||||
struct usb_port *port_dev = hub->ports[port1 - 1];
|
||||
struct usb_device *udev = port_dev->child;
|
||||
static int unreliable_port = -1;
|
||||
|
||||
/* Disconnect any existing devices under this port */
|
||||
if (udev) {
|
||||
@@ -4570,10 +4628,14 @@ static void hub_port_connect(struct usb_hub *hub, int port1, u16 portstatus,
|
||||
USB_PORT_STAT_C_ENABLE)) {
|
||||
status = hub_port_debounce_be_stable(hub, port1);
|
||||
if (status < 0) {
|
||||
if (status != -ENODEV && printk_ratelimit())
|
||||
dev_err(&port_dev->dev,
|
||||
"connect-debounce failed\n");
|
||||
if (status != -ENODEV &&
|
||||
port1 != unreliable_port &&
|
||||
printk_ratelimit())
|
||||
dev_err(&udev->dev, "connect-debounce failed, port %d disabled\n",
|
||||
port1);
|
||||
|
||||
portstatus &= ~USB_PORT_STAT_CONNECTION;
|
||||
unreliable_port = port1;
|
||||
} else {
|
||||
portstatus = status;
|
||||
}
|
||||
@@ -4889,7 +4951,7 @@ static void port_event(struct usb_hub *hub, int port1)
|
||||
* Warm reset a USB3 protocol port if it's in
|
||||
* SS.Inactive state.
|
||||
*/
|
||||
if (hub_port_warm_reset_required(hub, portstatus)) {
|
||||
if (hub_port_warm_reset_required(hub, port1, portstatus)) {
|
||||
dev_dbg(&port_dev->dev, "do warm reset\n");
|
||||
if (!udev || !(portstatus & USB_PORT_STAT_CONNECTION)
|
||||
|| udev->state == USB_STATE_NOTATTACHED) {
|
||||
|
@@ -52,6 +52,8 @@ struct usb_hub {
|
||||
unsigned long power_bits[1]; /* ports that are powered */
|
||||
unsigned long child_usage_bits[1]; /* ports powered on for
|
||||
children */
|
||||
unsigned long warm_reset_bits[1]; /* ports requesting warm
|
||||
reset recovery */
|
||||
#if USB_MAXCHILDREN > 31 /* 8*sizeof(unsigned long) - 1 */
|
||||
#error event_bits[] is too short!
|
||||
#endif
|
||||
|
@@ -103,16 +103,19 @@ static int usb_port_runtime_resume(struct device *dev)
|
||||
msleep(hub_power_on_good_delay(hub));
|
||||
if (udev && !retval) {
|
||||
/*
|
||||
* Attempt to wait for usb hub port to be reconnected in order
|
||||
* to make the resume procedure successful. The device may have
|
||||
* disconnected while the port was powered off, so ignore the
|
||||
* return status.
|
||||
* Our preference is to simply wait for the port to reconnect,
|
||||
* as that is the lowest latency method to restart the port.
|
||||
* However, there are cases where toggling port power results in
|
||||
* the host port and the device port getting out of sync causing
|
||||
* a link training live lock. Upon timeout, flag the port as
|
||||
* needing warm reset recovery (to be performed later by
|
||||
* usb_port_resume() as requested via usb_wakeup_notification())
|
||||
*/
|
||||
retval = hub_port_debounce_be_connected(hub, port1);
|
||||
if (retval < 0)
|
||||
dev_dbg(&port_dev->dev, "can't get reconnection after setting port power on, status %d\n",
|
||||
retval);
|
||||
retval = 0;
|
||||
if (hub_port_debounce_be_connected(hub, port1) < 0) {
|
||||
dev_dbg(&port_dev->dev, "reconnect timeout\n");
|
||||
if (hub_is_superspeed(hdev))
|
||||
set_bit(port1, hub->warm_reset_bits);
|
||||
}
|
||||
|
||||
/* Force the child awake to revalidate after the power loss. */
|
||||
if (!test_and_set_bit(port1, hub->child_usage_bits)) {
|
||||
|
@@ -145,6 +145,10 @@ static const struct usb_device_id usb_quirk_list[] = {
|
||||
/* SKYMEDI USB_DRIVE */
|
||||
{ USB_DEVICE(0x1516, 0x8628), .driver_info = USB_QUIRK_RESET_RESUME },
|
||||
|
||||
/* Razer - Razer Blade Keyboard */
|
||||
{ USB_DEVICE(0x1532, 0x0116), .driver_info =
|
||||
USB_QUIRK_LINEAR_UFRAME_INTR_BINTERVAL },
|
||||
|
||||
/* BUILDWIN Photo Frame */
|
||||
{ USB_DEVICE(0x1908, 0x1315), .driver_info =
|
||||
USB_QUIRK_HONOR_BNUMINTERFACES },
|
||||
@@ -152,6 +156,9 @@ static const struct usb_device_id usb_quirk_list[] = {
|
||||
/* INTEL VALUE SSD */
|
||||
{ USB_DEVICE(0x8086, 0xf1a5), .driver_info = USB_QUIRK_RESET_RESUME },
|
||||
|
||||
/* USB3503 */
|
||||
{ USB_DEVICE(0x0424, 0x3503), .driver_info = USB_QUIRK_RESET_RESUME },
|
||||
|
||||
{ } /* terminating entry must be last */
|
||||
};
|
||||
|
||||
|
@@ -454,6 +454,7 @@ int usb_submit_urb(struct urb *urb, gfp_t mem_flags)
|
||||
URB_FREE_BUFFER);
|
||||
switch (xfertype) {
|
||||
case USB_ENDPOINT_XFER_BULK:
|
||||
case USB_ENDPOINT_XFER_INT:
|
||||
if (is_out)
|
||||
allowed |= URB_ZERO_PACKET;
|
||||
/* FALLTHROUGH */
|
||||
|
@@ -501,6 +501,7 @@ struct usb_device *usb_alloc_dev(struct usb_device *parent,
|
||||
}
|
||||
return dev;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(usb_alloc_dev);
|
||||
|
||||
/**
|
||||
* usb_get_dev - increments the reference count of the usb device structure
|
||||
|
Reference in New Issue
Block a user