From c54211ede4fe52143640a469a0077de6c840bcd5 Mon Sep 17 00:00:00 2001 From: Greg Kroah-Hartman Date: Tue, 6 Mar 2018 10:17:55 -0800 Subject: [PATCH] 4.4-stable patches added patches: bluetooth-btusb-use-dmi-matching-for-qca-reset_resume-quirking.patch --- ...tching-for-qca-reset_resume-quirking.patch | 121 ++++++++++++++++++ 1 file changed, 121 insertions(+) create mode 100644 queue-4.4/bluetooth-btusb-use-dmi-matching-for-qca-reset_resume-quirking.patch diff --git a/queue-4.4/bluetooth-btusb-use-dmi-matching-for-qca-reset_resume-quirking.patch b/queue-4.4/bluetooth-btusb-use-dmi-matching-for-qca-reset_resume-quirking.patch new file mode 100644 index 00000000000..1d298f66e3b --- /dev/null +++ b/queue-4.4/bluetooth-btusb-use-dmi-matching-for-qca-reset_resume-quirking.patch @@ -0,0 +1,121 @@ +From 1fdb926974695d3dbc05a429bafa266fdd16510e Mon Sep 17 00:00:00 2001 +From: Hans de Goede +Date: Tue, 20 Feb 2018 09:06:18 +0100 +Subject: Bluetooth: btusb: Use DMI matching for QCA reset_resume quirking + +From: Hans de Goede + +commit 1fdb926974695d3dbc05a429bafa266fdd16510e upstream. + +Commit 61f5acea8737 ("Bluetooth: btusb: Restore QCA Rome suspend/resume fix +with a "rewritten" version") applied the USB_QUIRK_RESET_RESUME to all QCA +USB Bluetooth modules. But it turns out that the resume problems are not +caused by the QCA Rome chipset, on most platforms it resumes fine. The +resume problems are actually a platform problem (likely the platform +cutting all power when suspended). + +The USB_QUIRK_RESET_RESUME quirk also disables runtime suspend, so by +matching on usb-ids, we're causing all boards with these chips to use extra +power, to fix resume problems which only happen on some boards. + +This commit fixes this by applying the quirk based on DMI matching instead +of on usb-ids, so that we match the platform and not the chipset. + +Here is the /sys/kernel/debug/usb/devices for the Bluetooth module: + +T: Bus=01 Lev=01 Prnt=01 Port=07 Cnt=04 Dev#= 5 Spd=12 MxCh= 0 +D: Ver= 2.01 Cls=e0(wlcon) Sub=01 Prot=01 MxPS=64 #Cfgs= 1 +P: Vendor=0cf3 ProdID=e300 Rev= 0.01 +C:* #Ifs= 2 Cfg#= 1 Atr=e0 MxPwr=100mA +I:* If#= 0 Alt= 0 #EPs= 3 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=81(I) Atr=03(Int.) MxPS= 16 Ivl=1ms +E: Ad=82(I) Atr=02(Bulk) MxPS= 64 Ivl=0ms +E: Ad=02(O) Atr=02(Bulk) MxPS= 64 Ivl=0ms +I:* If#= 1 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 0 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 0 Ivl=1ms +I: If#= 1 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 9 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 9 Ivl=1ms +I: If#= 1 Alt= 2 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 17 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 17 Ivl=1ms +I: If#= 1 Alt= 3 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 25 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 25 Ivl=1ms +I: If#= 1 Alt= 4 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 33 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 33 Ivl=1ms +I: If#= 1 Alt= 5 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb +E: Ad=83(I) Atr=01(Isoc) MxPS= 49 Ivl=1ms +E: Ad=03(O) Atr=01(Isoc) MxPS= 49 Ivl=1ms + +BugLink: https://bugzilla.redhat.com/show_bug.cgi?id=1514836 +Fixes: 61f5acea8737 ("Bluetooth: btusb: Restore QCA Rome suspend/resume..") +Cc: stable@vger.kernel.org +Cc: Brian Norris +Cc: Kai-Heng Feng +Reported-and-tested-by: Kevin Fenzi +Signed-off-by: Hans de Goede +Signed-off-by: Marcel Holtmann +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/bluetooth/btusb.c | 25 +++++++++++++++++++------ + 1 file changed, 19 insertions(+), 6 deletions(-) + +--- a/drivers/bluetooth/btusb.c ++++ b/drivers/bluetooth/btusb.c +@@ -21,6 +21,7 @@ + * + */ + ++#include + #include + #include + #include +@@ -349,6 +350,21 @@ static const struct usb_device_id blackl + { } /* Terminating entry */ + }; + ++/* The Bluetooth USB module build into some devices needs to be reset on resume, ++ * this is a problem with the platform (likely shutting off all power) not with ++ * the module itself. So we use a DMI list to match known broken platforms. ++ */ ++static const struct dmi_system_id btusb_needs_reset_resume_table[] = { ++ { ++ /* Lenovo Yoga 920 (QCA Rome device 0cf3:e300) */ ++ .matches = { ++ DMI_MATCH(DMI_SYS_VENDOR, "LENOVO"), ++ DMI_MATCH(DMI_PRODUCT_VERSION, "Lenovo YOGA 920"), ++ }, ++ }, ++ {} ++}; ++ + #define BTUSB_MAX_ISOC_FRAMES 10 + + #define BTUSB_INTR_RUNNING 0 +@@ -2970,12 +2986,6 @@ static int btusb_probe(struct usb_interf + if (id->driver_info & BTUSB_QCA_ROME) { + data->setup_on_usb = btusb_setup_qca; + hdev->set_bdaddr = btusb_set_bdaddr_ath3012; +- +- /* QCA Rome devices lose their updated firmware over suspend, +- * but the USB hub doesn't notice any status change. +- * explicitly request a device reset on resume. +- */ +- interface_to_usbdev(intf)->quirks |= USB_QUIRK_RESET_RESUME; + } + + #ifdef CONFIG_BT_HCIBTUSB_RTL +@@ -3118,6 +3128,9 @@ static void btusb_disconnect(struct usb_ + hci_free_dev(hdev); + } + ++ if (dmi_check_system(btusb_needs_reset_resume_table)) ++ interface_to_usbdev(intf)->quirks |= USB_QUIRK_RESET_RESUME; ++ + #ifdef CONFIG_PM + static int btusb_suspend(struct usb_interface *intf, pm_message_t message) + { -- 2.47.3