diff options
-rw-r--r-- | drivers/net/wireless/brcm80211/brcmfmac/usb.c | 2 | ||||
-rw-r--r-- | drivers/usb/core/hub.c | 4 | ||||
-rw-r--r-- | drivers/usb/host/xhci.c | 76 | ||||
-rw-r--r-- | include/linux/usb.h | 12 |
4 files changed, 57 insertions, 37 deletions
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/usb.c b/drivers/net/wireless/brcm80211/brcmfmac/usb.c index 8852d23ef82..f2bc48b745e 100644 --- a/drivers/net/wireless/brcm80211/brcmfmac/usb.c +++ b/drivers/net/wireless/brcm80211/brcmfmac/usb.c @@ -1604,7 +1604,7 @@ static struct usb_driver brcmf_usbdrvr = { .id_table = brcmf_usb_devid_table, .suspend = brcmf_usb_suspend, .resume = brcmf_usb_resume, - .supports_autosuspend = 1 + .supports_autosuspend = 1, .disable_hub_initiated_lpm = 1, }; diff --git a/drivers/usb/core/hub.c b/drivers/usb/core/hub.c index fcc244e9056..04fb834c3fa 100644 --- a/drivers/usb/core/hub.c +++ b/drivers/usb/core/hub.c @@ -3472,15 +3472,19 @@ int usb_disable_lpm(struct usb_device *udev) { return 0; } +EXPORT_SYMBOL_GPL(usb_disable_lpm); void usb_enable_lpm(struct usb_device *udev) { } +EXPORT_SYMBOL_GPL(usb_enable_lpm); int usb_unlocked_disable_lpm(struct usb_device *udev) { return 0; } +EXPORT_SYMBOL_GPL(usb_unlocked_disable_lpm); void usb_unlocked_enable_lpm(struct usb_device *udev) { } +EXPORT_SYMBOL_GPL(usb_unlocked_enable_lpm); #endif diff --git a/drivers/usb/host/xhci.c b/drivers/usb/host/xhci.c index 4ceba145fa8..afdc73ee84a 100644 --- a/drivers/usb/host/xhci.c +++ b/drivers/usb/host/xhci.c @@ -3837,8 +3837,43 @@ int xhci_set_usb2_hardware_lpm(struct usb_hcd *hcd, return 0; } +int xhci_update_device(struct usb_hcd *hcd, struct usb_device *udev) +{ + struct xhci_hcd *xhci = hcd_to_xhci(hcd); + int ret; + + ret = xhci_usb2_software_lpm_test(hcd, udev); + if (!ret) { + xhci_dbg(xhci, "software LPM test succeed\n"); + if (xhci->hw_lpm_support == 1) { + udev->usb2_hw_lpm_capable = 1; + ret = xhci_set_usb2_hardware_lpm(hcd, udev, 1); + if (!ret) + udev->usb2_hw_lpm_enabled = 1; + } + } + + return 0; +} + +#else + +int xhci_set_usb2_hardware_lpm(struct usb_hcd *hcd, + struct usb_device *udev, int enable) +{ + return 0; +} + +int xhci_update_device(struct usb_hcd *hcd, struct usb_device *udev) +{ + return 0; +} + +#endif /* CONFIG_USB_SUSPEND */ + /*---------------------- USB 3.0 Link PM functions ------------------------*/ +#ifdef CONFIG_PM /* Service interval in nanoseconds = 2^(bInterval - 1) * 125us * 1000ns / 1us */ static unsigned long long xhci_service_interval_to_ns( struct usb_endpoint_descriptor *desc) @@ -3921,7 +3956,7 @@ static u16 xhci_calculate_intel_u1_timeout(struct usb_device *udev, /* Otherwise the calculation is the same as isoc eps */ case USB_ENDPOINT_XFER_ISOC: timeout_ns = xhci_service_interval_to_ns(desc); - timeout_ns = DIV_ROUND_UP(timeout_ns * 105, 100); + timeout_ns = DIV_ROUND_UP_ULL(timeout_ns * 105, 100); if (timeout_ns < udev->u1_params.sel * 2) timeout_ns = udev->u1_params.sel * 2; break; @@ -3930,7 +3965,7 @@ static u16 xhci_calculate_intel_u1_timeout(struct usb_device *udev, } /* The U1 timeout is encoded in 1us intervals. */ - timeout_ns = DIV_ROUND_UP(timeout_ns, 1000); + timeout_ns = DIV_ROUND_UP_ULL(timeout_ns, 1000); /* Don't return a timeout of zero, because that's USB3_LPM_DISABLED. */ if (timeout_ns == USB3_LPM_DISABLED) timeout_ns++; @@ -3969,7 +4004,7 @@ static u16 xhci_calculate_intel_u2_timeout(struct usb_device *udev, timeout_ns = u2_del_ns; /* The U2 timeout is encoded in 256us intervals */ - timeout_ns = DIV_ROUND_UP(timeout_ns, 256 * 1000); + timeout_ns = DIV_ROUND_UP_ULL(timeout_ns, 256 * 1000); /* If the necessary timeout value is bigger than what we can set in the * USB 3.0 hub, we have to disable hub-initiated U2. */ @@ -4287,41 +4322,22 @@ int xhci_disable_usb3_lpm_timeout(struct usb_hcd *hcd, return ret; return 0; } -/*-------------------------------------------------------------------------*/ - -int xhci_update_device(struct usb_hcd *hcd, struct usb_device *udev) -{ - struct xhci_hcd *xhci = hcd_to_xhci(hcd); - int ret; - - ret = xhci_usb2_software_lpm_test(hcd, udev); - if (!ret) { - xhci_dbg(xhci, "software LPM test succeed\n"); - if (xhci->hw_lpm_support == 1) { - udev->usb2_hw_lpm_capable = 1; - ret = xhci_set_usb2_hardware_lpm(hcd, udev, 1); - if (!ret) - udev->usb2_hw_lpm_enabled = 1; - } - } +#else /* CONFIG_PM */ - return 0; -} - -#else - -int xhci_set_usb2_hardware_lpm(struct usb_hcd *hcd, - struct usb_device *udev, int enable) +int xhci_enable_usb3_lpm_timeout(struct usb_hcd *hcd, + struct usb_device *udev, enum usb3_link_state state) { - return 0; + return USB3_LPM_DISABLED; } -int xhci_update_device(struct usb_hcd *hcd, struct usb_device *udev) +int xhci_disable_usb3_lpm_timeout(struct usb_hcd *hcd, + struct usb_device *udev, enum usb3_link_state state) { return 0; } +#endif /* CONFIG_PM */ -#endif /* CONFIG_USB_SUSPEND */ +/*-------------------------------------------------------------------------*/ /* Once a hub descriptor is fetched for a device, we need to update the xHC's * internal data structures for the device. diff --git a/include/linux/usb.h b/include/linux/usb.h index c19297a8779..dea39dc551d 100644 --- a/include/linux/usb.h +++ b/include/linux/usb.h @@ -592,12 +592,6 @@ extern void usb_autopm_put_interface_async(struct usb_interface *intf); extern void usb_autopm_get_interface_no_resume(struct usb_interface *intf); extern void usb_autopm_put_interface_no_suspend(struct usb_interface *intf); -extern int usb_disable_lpm(struct usb_device *udev); -extern void usb_enable_lpm(struct usb_device *udev); -/* Same as above, but these functions lock/unlock the bandwidth_mutex. */ -extern int usb_unlocked_disable_lpm(struct usb_device *udev); -extern void usb_unlocked_enable_lpm(struct usb_device *udev); - static inline void usb_mark_last_busy(struct usb_device *udev) { pm_runtime_mark_last_busy(&udev->dev); @@ -629,6 +623,12 @@ static inline void usb_mark_last_busy(struct usb_device *udev) { } #endif +extern int usb_disable_lpm(struct usb_device *udev); +extern void usb_enable_lpm(struct usb_device *udev); +/* Same as above, but these functions lock/unlock the bandwidth_mutex. */ +extern int usb_unlocked_disable_lpm(struct usb_device *udev); +extern void usb_unlocked_enable_lpm(struct usb_device *udev); + /*-------------------------------------------------------------------------*/ /* for drivers using iso endpoints */ |