From 3a0318140a6f8c3ab60f1f46c3f203923cb01882 Mon Sep 17 00:00:00 2001 From: Changcheng Deng Date: Fri, 21 Jan 2022 01:35:08 +0000 Subject: Bluetooth: mgmt: Replace zero-length array with flexible-array member There is a regular need in the kernel to provide a way to declare having a dynamically sized set of trailing elements in a structure. Kernel code should always use "flexible array members" for these cases. The older style of one-element or zero-length arrays should no longer be used. Reference: https://www.kernel.org/doc/html/latest/process/deprecated.html#zero-length-and-one-element-arrays Reported-by: Zeal Robot Signed-off-by: Changcheng Deng Signed-off-by: Luiz Augusto von Dentz --- include/net/bluetooth/mgmt.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/net/bluetooth/mgmt.h b/include/net/bluetooth/mgmt.h index 99266f7aebdc..3d26e6a3478b 100644 --- a/include/net/bluetooth/mgmt.h +++ b/include/net/bluetooth/mgmt.h @@ -1112,7 +1112,7 @@ struct mgmt_ev_adv_monitor_device_found { __s8 rssi; __le32 flags; __le16 eir_len; - __u8 eir[0]; + __u8 eir[]; } __packed; #define MGMT_EV_ADV_MONITOR_DEVICE_LOST 0x0030 -- cgit From 8cd3c55c629efd91e5f2b3e89d850575c5b90d47 Mon Sep 17 00:00:00 2001 From: Tom Rix Date: Tue, 1 Feb 2022 09:42:56 -0800 Subject: Bluetooth: hci_sync: fix undefined return of hci_disconnect_all_sync() clang static analysis reports this problem hci_sync.c:4428:2: warning: Undefined or garbage value returned to caller return err; ^~~~~~~~~~ If there are no connections this function is a noop but err is never set and a false error could be reported. Return 0 as other hci_* functions do. Fixes: 182ee45da083 ("Bluetooth: hci_sync: Rework hci_suspend_notifier") Signed-off-by: Tom Rix Signed-off-by: Luiz Augusto von Dentz --- net/bluetooth/hci_sync.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/net/bluetooth/hci_sync.c b/net/bluetooth/hci_sync.c index 8fa57ef0bbc9..e31d1150dc71 100644 --- a/net/bluetooth/hci_sync.c +++ b/net/bluetooth/hci_sync.c @@ -4428,7 +4428,7 @@ static int hci_disconnect_all_sync(struct hci_dev *hdev, u8 reason) return err; } - return err; + return 0; } /* This function perform power off HCI command sequence as follows: -- cgit From a6fbb2bf51adc117e7d4030e4fd55f0763ab890d Mon Sep 17 00:00:00 2001 From: Minghao Chi Date: Tue, 18 Jan 2022 07:50:33 +0000 Subject: Bluetooth: mgmt: Remove unneeded variable Return value from mgmt_cmd_complete() directly instead of taking this in another redundant variable. Reported-by: Zeal Robot Signed-off-by: Minghao Chi Signed-off-by: CGEL ZTE Signed-off-by: Luiz Augusto von Dentz --- net/bluetooth/mgmt.c | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c index 71aff6e65e7c..e0d36d1e4eed 100644 --- a/net/bluetooth/mgmt.c +++ b/net/bluetooth/mgmt.c @@ -8630,7 +8630,6 @@ static int get_adv_size_info(struct sock *sk, struct hci_dev *hdev, struct mgmt_cp_get_adv_size_info *cp = data; struct mgmt_rp_get_adv_size_info rp; u32 flags, supported_flags; - int err; bt_dev_dbg(hdev, "sock %p", sk); @@ -8657,10 +8656,8 @@ static int get_adv_size_info(struct sock *sk, struct hci_dev *hdev, rp.max_adv_data_len = tlv_data_max_len(hdev, flags, true); rp.max_scan_rsp_len = tlv_data_max_len(hdev, flags, false); - err = mgmt_cmd_complete(sk, hdev->id, MGMT_OP_GET_ADV_SIZE_INFO, - MGMT_STATUS_SUCCESS, &rp, sizeof(rp)); - - return err; + return mgmt_cmd_complete(sk, hdev->id, MGMT_OP_GET_ADV_SIZE_INFO, + MGMT_STATUS_SUCCESS, &rp, sizeof(rp)); } static const struct hci_mgmt_handler mgmt_handlers[] = { -- cgit From ba17bb62ce415950753c19d16bb43b2bd3701158 Mon Sep 17 00:00:00 2001 From: Radoslaw Biernacki Date: Tue, 1 Feb 2022 20:10:32 +0000 Subject: Bluetooth: Fix skb allocation in mgmt_remote_name() & mgmt_device_connected() This patch fixes skb allocation, as lack of space for ev might push skb tail beyond its end. Also introduce eir_precalc_len() that can be used instead of magic numbers for similar eir operations on skb. Fixes: cf1bce1de7eeb ("Bluetooth: mgmt: Make use of mgmt_send_event_skb in MGMT_EV_DEVICE_FOUND") Fixes: e96741437ef0a ("Bluetooth: mgmt: Make use of mgmt_send_event_skb in MGMT_EV_DEVICE_CONNECTED") Signed-off-by: Angela Czubak Signed-off-by: Marek Maslanka Signed-off-by: Radoslaw Biernacki Signed-off-by: Luiz Augusto von Dentz --- net/bluetooth/eir.h | 5 +++++ net/bluetooth/mgmt.c | 18 ++++++++---------- 2 files changed, 13 insertions(+), 10 deletions(-) diff --git a/net/bluetooth/eir.h b/net/bluetooth/eir.h index 05e2e917fc25..e5876751f07e 100644 --- a/net/bluetooth/eir.h +++ b/net/bluetooth/eir.h @@ -15,6 +15,11 @@ u8 eir_create_scan_rsp(struct hci_dev *hdev, u8 instance, u8 *ptr); u8 eir_append_local_name(struct hci_dev *hdev, u8 *eir, u8 ad_len); u8 eir_append_appearance(struct hci_dev *hdev, u8 *ptr, u8 ad_len); +static inline u16 eir_precalc_len(u8 data_len) +{ + return sizeof(u8) * 2 + data_len; +} + static inline u16 eir_append_data(u8 *eir, u16 eir_len, u8 type, u8 *data, u8 data_len) { diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c index e0d36d1e4eed..bfacf2ea692f 100644 --- a/net/bluetooth/mgmt.c +++ b/net/bluetooth/mgmt.c @@ -9085,12 +9085,14 @@ void mgmt_device_connected(struct hci_dev *hdev, struct hci_conn *conn, u16 eir_len = 0; u32 flags = 0; + /* allocate buff for LE or BR/EDR adv */ if (conn->le_adv_data_len > 0) skb = mgmt_alloc_skb(hdev, MGMT_EV_DEVICE_CONNECTED, - conn->le_adv_data_len); + sizeof(*ev) + conn->le_adv_data_len); else skb = mgmt_alloc_skb(hdev, MGMT_EV_DEVICE_CONNECTED, - 2 + name_len + 5); + sizeof(*ev) + (name ? eir_precalc_len(name_len) : 0) + + eir_precalc_len(sizeof(conn->dev_class))); ev = skb_put(skb, sizeof(*ev)); bacpy(&ev->addr.bdaddr, &conn->dst); @@ -9809,13 +9811,11 @@ void mgmt_remote_name(struct hci_dev *hdev, bdaddr_t *bdaddr, u8 link_type, { struct sk_buff *skb; struct mgmt_ev_device_found *ev; - u16 eir_len; - u32 flags; + u16 eir_len = 0; + u32 flags = 0; - if (name_len) - skb = mgmt_alloc_skb(hdev, MGMT_EV_DEVICE_FOUND, 2 + name_len); - else - skb = mgmt_alloc_skb(hdev, MGMT_EV_DEVICE_FOUND, 0); + skb = mgmt_alloc_skb(hdev, MGMT_EV_DEVICE_FOUND, + sizeof(*ev) + (name ? eir_precalc_len(name_len) : 0)); ev = skb_put(skb, sizeof(*ev)); bacpy(&ev->addr.bdaddr, bdaddr); @@ -9825,10 +9825,8 @@ void mgmt_remote_name(struct hci_dev *hdev, bdaddr_t *bdaddr, u8 link_type, if (name) { eir_len = eir_append_data(ev->eir, 0, EIR_NAME_COMPLETE, name, name_len); - flags = 0; skb_put(skb, eir_len); } else { - eir_len = 0; flags = MGMT_DEV_FOUND_NAME_REQUEST_FAILED; } -- cgit From c2b2a1a77f6b2694b7249073083ad6a0c918eef3 Mon Sep 17 00:00:00 2001 From: Radoslaw Biernacki Date: Tue, 1 Feb 2022 20:10:33 +0000 Subject: Bluetooth: Improve skb handling in mgmt_device_connected() This patch introduce eir_skb_put_data() that can be used to simplify operations on eir in goal of eliminating the necessity of intermediary buffers. eir_skb_put_data() is in pair to what eir_append_data() does with help of eir_len, but without awkwardness when passing return value to skb_put() (as it returns updated offset not size). Signed-off-by: Radoslaw Biernacki Signed-off-by: Luiz Augusto von Dentz --- net/bluetooth/eir.h | 15 +++++++++++++++ net/bluetooth/mgmt.c | 25 ++++++++----------------- 2 files changed, 23 insertions(+), 17 deletions(-) diff --git a/net/bluetooth/eir.h b/net/bluetooth/eir.h index e5876751f07e..43f1945bffc5 100644 --- a/net/bluetooth/eir.h +++ b/net/bluetooth/eir.h @@ -41,6 +41,21 @@ static inline u16 eir_append_le16(u8 *eir, u16 eir_len, u8 type, u16 data) return eir_len; } +static inline u16 eir_skb_put_data(struct sk_buff *skb, u8 type, u8 *data, u8 data_len) +{ + u8 *eir; + u16 eir_len; + + eir_len = eir_precalc_len(data_len); + eir = skb_put(skb, eir_len); + WARN_ON(sizeof(type) + data_len > U8_MAX); + eir[0] = sizeof(type) + data_len; + eir[1] = type; + memcpy(&eir[2], data, data_len); + + return eir_len; +} + static inline void *eir_get_data(u8 *eir, size_t eir_len, u8 type, size_t *data_len) { diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c index bfacf2ea692f..40f1f5dae9f9 100644 --- a/net/bluetooth/mgmt.c +++ b/net/bluetooth/mgmt.c @@ -9111,18 +9111,12 @@ void mgmt_device_connected(struct hci_dev *hdev, struct hci_conn *conn, skb_put_data(skb, conn->le_adv_data, conn->le_adv_data_len); eir_len = conn->le_adv_data_len; } else { - if (name_len > 0) { - eir_len = eir_append_data(ev->eir, 0, EIR_NAME_COMPLETE, - name, name_len); - skb_put(skb, eir_len); - } + if (name) + eir_len += eir_skb_put_data(skb, EIR_NAME_COMPLETE, name, name_len); - if (memcmp(conn->dev_class, "\0\0\0", 3) != 0) { - eir_len = eir_append_data(ev->eir, eir_len, - EIR_CLASS_OF_DEV, - conn->dev_class, 3); - skb_put(skb, 5); - } + if (memcmp(conn->dev_class, "\0\0\0", sizeof(conn->dev_class))) + eir_len += eir_skb_put_data(skb, EIR_CLASS_OF_DEV, + conn->dev_class, sizeof(conn->dev_class)); } ev->eir_len = cpu_to_le16(eir_len); @@ -9822,13 +9816,10 @@ void mgmt_remote_name(struct hci_dev *hdev, bdaddr_t *bdaddr, u8 link_type, ev->addr.type = link_to_bdaddr(link_type, addr_type); ev->rssi = rssi; - if (name) { - eir_len = eir_append_data(ev->eir, 0, EIR_NAME_COMPLETE, name, - name_len); - skb_put(skb, eir_len); - } else { + if (name) + eir_len += eir_skb_put_data(skb, EIR_NAME_COMPLETE, name, name_len); + else flags = MGMT_DEV_FOUND_NAME_REQUEST_FAILED; - } ev->eir_len = cpu_to_le16(eir_len); ev->flags = cpu_to_le32(flags); -- cgit From 2ca57c8099268001f41aa158cac92838daed323e Mon Sep 17 00:00:00 2001 From: Kiran K Date: Mon, 31 Jan 2022 22:02:35 +0530 Subject: Bluetooth: btusb: Add support for Intel Madison Peak (MsP2) device $ lsusb Bus 003 Device 003: ID 8087:0035 Intel Corp. $ cat /sys/kernel/debug/usb/devices T: Bus=03 Lev=01 Prnt=01 Port=09 Cnt=02 Dev#= 3 Spd=12 MxCh= 0 D: Ver= 2.01 Cls=e0(wlcon) Sub=01 Prot=01 MxPS=64 #Cfgs= 1 P: Vendor=8087 ProdID=0035 Rev= 0.00 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= 64 Ivl=1ms E: Ad=02(O) Atr=02(Bulk) MxPS= 64 Ivl=0ms E: Ad=82(I) 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=03(O) Atr=01(Isoc) MxPS= 0 Ivl=1ms E: Ad=83(I) 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=03(O) Atr=01(Isoc) MxPS= 9 Ivl=1ms E: Ad=83(I) 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=03(O) Atr=01(Isoc) MxPS= 17 Ivl=1ms E: Ad=83(I) 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=03(O) Atr=01(Isoc) MxPS= 25 Ivl=1ms E: Ad=83(I) 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=03(O) Atr=01(Isoc) MxPS= 33 Ivl=1ms E: Ad=83(I) 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=03(O) Atr=01(Isoc) MxPS= 49 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 49 Ivl=1ms I: If#= 1 Alt= 6 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=03(O) Atr=01(Isoc) MxPS= 63 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 63 Ivl=1ms Signed-off-by: Kiran K Signed-off-by: Marcel Holtmann --- drivers/bluetooth/btusb.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c index aefa0ee293f3..e03dfbd92fcc 100644 --- a/drivers/bluetooth/btusb.c +++ b/drivers/bluetooth/btusb.c @@ -384,6 +384,7 @@ static const struct usb_device_id blacklist_table[] = { { USB_DEVICE(0x8087, 0x0029), .driver_info = BTUSB_INTEL_COMBINED }, { USB_DEVICE(0x8087, 0x0032), .driver_info = BTUSB_INTEL_COMBINED }, { USB_DEVICE(0x8087, 0x0033), .driver_info = BTUSB_INTEL_COMBINED }, + { USB_DEVICE(0x8087, 0x0035), .driver_info = BTUSB_INTEL_COMBINED }, { USB_DEVICE(0x8087, 0x07da), .driver_info = BTUSB_CSR }, { USB_DEVICE(0x8087, 0x07dc), .driver_info = BTUSB_INTEL_COMBINED | BTUSB_INTEL_NO_WBS_SUPPORT | -- cgit From 467e98cda80fd2fd966bc21652335643b30dac8f Mon Sep 17 00:00:00 2001 From: Piotr Dymacz Date: Fri, 11 Feb 2022 10:31:03 +0100 Subject: Bluetooth: btusb: add support for LG LGSBWAC02 (MT7663BUN) The LG LGSBWAC02 (FCC ID: BEJLGSBWAC02) is a combo Wi-Fi/BT module which can be found in several different LG TV models. This module is based on already supported MediaTek MT7663U series. Device from /sys/kernel/debug/usb/devices: T: Bus=01 Lev=02 Prnt=02 Port=03 Cnt=02 Dev#= 4 Spd=480 MxCh= 0 D: Ver= 2.10 Cls=ef(misc ) Sub=02 Prot=01 MxPS=64 #Cfgs= 1 P: Vendor=043e ProdID=310c Rev= 1.00 S: Manufacturer=MediaTek Inc. S: Product=Wireless_Device S: SerialNumber=000000000 C:* #Ifs= 3 Cfg#= 1 Atr=a0 MxPwr=100mA A: FirstIf#= 0 IfCount= 2 Cls=e0(wlcon) Sub=01 Prot=01 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=125us E: Ad=82(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms E: Ad=02(O) Atr=02(Bulk) MxPS= 512 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 I: If#= 1 Alt= 6 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=83(I) Atr=01(Isoc) MxPS= 63 Ivl=1ms E: Ad=03(O) Atr=01(Isoc) MxPS= 63 Ivl=1ms I:* If#= 2 Alt= 0 #EPs= 8 Cls=ff(vend.) Sub=ff Prot=ff Driver=mt7663u E: Ad=84(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms E: Ad=85(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms E: Ad=08(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms E: Ad=04(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms E: Ad=05(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms E: Ad=06(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms E: Ad=07(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms E: Ad=09(O) Atr=02(Bulk) MxPS= 512 Ivl=0ms Signed-off-by: Piotr Dymacz Signed-off-by: Marcel Holtmann --- drivers/bluetooth/btusb.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c index e03dfbd92fcc..ef5d52f0e123 100644 --- a/drivers/bluetooth/btusb.c +++ b/drivers/bluetooth/btusb.c @@ -435,6 +435,11 @@ static const struct usb_device_id blacklist_table[] = { /* Additional MediaTek MT7615E Bluetooth devices */ { USB_DEVICE(0x13d3, 0x3560), .driver_info = BTUSB_MEDIATEK}, + /* Additional MediaTek MT7663 Bluetooth devices */ + { USB_DEVICE(0x043e, 0x310c), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, + /* Additional MediaTek MT7668 Bluetooth devices */ { USB_DEVICE(0x043e, 0x3109), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | -- cgit From 599ece4f8f073097904d411ee70280a2ec890ad3 Mon Sep 17 00:00:00 2001 From: Zijun Hu Date: Mon, 14 Feb 2022 18:43:39 +0800 Subject: Bluetooth: btusb: Improve stability for QCA devices WCN6855 2.1 will reset to apply firmware downloaded, so wait a moment for reset done then go ahead to improve stability. Signed-off-by: Zijun Hu Signed-off-by: Marcel Holtmann --- drivers/bluetooth/btusb.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c index ef5d52f0e123..9e0d59d4382a 100644 --- a/drivers/bluetooth/btusb.c +++ b/drivers/bluetooth/btusb.c @@ -2999,6 +2999,7 @@ static int btusb_set_bdaddr_wcn6855(struct hci_dev *hdev, #define QCA_PATCH_UPDATED 0x80 #define QCA_DFU_TIMEOUT 3000 #define QCA_FLAG_MULTI_NVM 0x80 +#define QCA_BT_RESET_WAIT_MS 100 #define WCN6855_2_0_RAM_VERSION_GF 0x400c1200 #define WCN6855_2_1_RAM_VERSION_GF 0x400c1211 @@ -3325,6 +3326,13 @@ static int btusb_setup_qca(struct hci_dev *hdev) err = btusb_setup_qca_load_nvm(hdev, &ver, info); if (err < 0) return err; + + /* WCN6855 2.1 will reset to apply firmware downloaded here, so + * wait ~100ms for reset Done then go ahead, otherwise, it maybe + * cause potential enable failure. + */ + if (info->rom_version == 0x00130201) + msleep(QCA_BT_RESET_WAIT_MS); } return 0; -- cgit From f1b8eea0fa662709fd8f3e32511bafeee99b10b3 Mon Sep 17 00:00:00 2001 From: Christophe JAILLET Date: Sun, 13 Feb 2022 22:30:47 +0100 Subject: Bluetooth: 6lowpan: No need to clear memory twice 'peer_addr' is a structure embedded in 'struct lowpan_peer'. So there is no need to explicitly call memset(0) on it. It is already zeroed by kzalloc() when 'peer' is allocated. Signed-off-by: Christophe JAILLET Signed-off-by: Marcel Holtmann --- net/bluetooth/6lowpan.c | 1 - 1 file changed, 1 deletion(-) diff --git a/net/bluetooth/6lowpan.c b/net/bluetooth/6lowpan.c index 133d7ea063fb..8e8c07541153 100644 --- a/net/bluetooth/6lowpan.c +++ b/net/bluetooth/6lowpan.c @@ -641,7 +641,6 @@ static struct l2cap_chan *add_peer_chan(struct l2cap_chan *chan, return NULL; peer->chan = chan; - memset(&peer->peer_addr, 0, sizeof(struct in6_addr)); baswap((void *)peer->lladdr, &chan->dst); -- cgit From e616fec63f517449e153051b785b1769775562ce Mon Sep 17 00:00:00 2001 From: Colin Ian King Date: Mon, 14 Feb 2022 21:51:30 +0000 Subject: Bluetooth: make array bt_uuid_any static const Don't populate the read-only array bt_uuid_any on the stack but instead make it static const. Also makes the object code a little smaller. Signed-off-by: Colin Ian King Signed-off-by: Marcel Holtmann --- net/bluetooth/mgmt.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c index 40f1f5dae9f9..89b1c0488527 100644 --- a/net/bluetooth/mgmt.c +++ b/net/bluetooth/mgmt.c @@ -2298,7 +2298,9 @@ static int remove_uuid(struct sock *sk, struct hci_dev *hdev, void *data, struct mgmt_cp_remove_uuid *cp = data; struct mgmt_pending_cmd *cmd; struct bt_uuid *match, *tmp; - u8 bt_uuid_any[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; + static const u8 bt_uuid_any[] = { + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 + }; int err, found; bt_dev_dbg(hdev, "sock %p", sk); -- cgit From 8fafe702253d50bf90daf324ae86b5ad5ac8a5e1 Mon Sep 17 00:00:00 2001 From: Chih-Ying Chiang Date: Wed, 9 Feb 2022 02:17:40 +0800 Subject: Bluetooth: mt7921s: support bluetooth reset mechanism Implement .cmd_timeout to reset the MT7921s device via a dedicated GPIO pin when the firmware hang or the command has no response. Co-developed-by: Mark Chen Signed-off-by: Mark Chen Co-developed-by: Sean Wang Signed-off-by: Sean Wang Signed-off-by: Chih-Ying Chiang Signed-off-by: Marcel Holtmann --- drivers/bluetooth/btmtk.h | 6 +++ drivers/bluetooth/btmtksdio.c | 113 +++++++++++++++++++++++++++++++++++++++++- 2 files changed, 118 insertions(+), 1 deletion(-) diff --git a/drivers/bluetooth/btmtk.h b/drivers/bluetooth/btmtk.h index fb76d9765ce0..8960a5f89d48 100644 --- a/drivers/bluetooth/btmtk.h +++ b/drivers/bluetooth/btmtk.h @@ -10,9 +10,15 @@ #define BTMTK_WMT_REG_WRITE 0x1 #define BTMTK_WMT_REG_READ 0x2 +#define MT7921_BTSYS_RST 0x70002610 +#define MT7921_BTSYS_RST_WITH_GPIO BIT(7) + #define MT7921_PINMUX_0 0x70005050 #define MT7921_PINMUX_1 0x70005054 +#define MT7921_DLSTATUS 0x7c053c10 +#define BT_DL_STATE BIT(1) + enum { BTMTK_WMT_PATCH_DWNLD = 0x1, BTMTK_WMT_TEST = 0x2, diff --git a/drivers/bluetooth/btmtksdio.c b/drivers/bluetooth/btmtksdio.c index 8be763ab3bf4..8e200e80d2f6 100644 --- a/drivers/bluetooth/btmtksdio.c +++ b/drivers/bluetooth/btmtksdio.c @@ -12,10 +12,12 @@ #include #include +#include #include #include #include #include +#include #include #include @@ -83,6 +85,7 @@ MODULE_DEVICE_TABLE(sdio, btmtksdio_table); #define MTK_REG_CHCR 0xc #define C_INT_CLR_CTRL BIT(1) +#define BT_RST_DONE BIT(8) /* CHISR have the same bits field definition with CHIER */ #define MTK_REG_CHISR 0x10 @@ -114,6 +117,7 @@ MODULE_DEVICE_TABLE(sdio, btmtksdio_table); #define BTMTKSDIO_HW_TX_READY 2 #define BTMTKSDIO_FUNC_ENABLED 3 #define BTMTKSDIO_PATCH_ENABLED 4 +#define BTMTKSDIO_HW_RESET_ACTIVE 5 struct mtkbtsdio_hdr { __le16 len; @@ -133,6 +137,8 @@ struct btmtksdio_dev { struct sk_buff *evt_skb; const struct btmtksdio_data *data; + + struct gpio_desc *reset; }; static int mtk_hci_wmt_sync(struct hci_dev *hdev, @@ -297,6 +303,11 @@ static u32 btmtksdio_drv_own_query_79xx(struct btmtksdio_dev *bdev) return sdio_readl(bdev->func, MTK_REG_PD2HRM0R, NULL); } +static u32 btmtksdio_chcr_query(struct btmtksdio_dev *bdev) +{ + return sdio_readl(bdev->func, MTK_REG_CHCR, NULL); +} + static int btmtksdio_fw_pmctrl(struct btmtksdio_dev *bdev) { u32 status; @@ -967,6 +978,28 @@ static int btmtksdio_sco_setting(struct hci_dev *hdev) return btmtksdio_mtk_reg_write(hdev, MT7921_PINMUX_1, val, ~0); } +static int btmtksdio_reset_setting(struct hci_dev *hdev) +{ + int err; + u32 val; + + err = btmtksdio_mtk_reg_read(hdev, MT7921_PINMUX_1, &val); + if (err < 0) + return err; + + val |= 0x20; /* set the pin (bit field 11:8) work as GPIO mode */ + err = btmtksdio_mtk_reg_write(hdev, MT7921_PINMUX_1, val, ~0); + if (err < 0) + return err; + + err = btmtksdio_mtk_reg_read(hdev, MT7921_BTSYS_RST, &val); + if (err < 0) + return err; + + val |= MT7921_BTSYS_RST_WITH_GPIO; + return btmtksdio_mtk_reg_write(hdev, MT7921_BTSYS_RST, val, ~0); +} + static int btmtksdio_setup(struct hci_dev *hdev) { struct btmtksdio_dev *bdev = hci_get_drvdata(hdev); @@ -974,13 +1007,32 @@ static int btmtksdio_setup(struct hci_dev *hdev) unsigned long long duration; char fwname[64]; int err, dev_id; - u32 fw_version = 0; + u32 fw_version = 0, val; calltime = ktime_get(); set_bit(BTMTKSDIO_HW_TX_READY, &bdev->tx_state); switch (bdev->data->chipid) { case 0x7921: + if (test_bit(BTMTKSDIO_HW_RESET_ACTIVE, &bdev->tx_state)) { + err = btmtksdio_mtk_reg_read(hdev, MT7921_DLSTATUS, + &val); + if (err < 0) + return err; + + val &= ~BT_DL_STATE; + err = btmtksdio_mtk_reg_write(hdev, MT7921_DLSTATUS, + val, ~0); + if (err < 0) + return err; + + btmtksdio_fw_pmctrl(bdev); + msleep(20); + btmtksdio_drv_pmctrl(bdev); + + clear_bit(BTMTKSDIO_HW_RESET_ACTIVE, &bdev->tx_state); + } + err = btmtksdio_mtk_reg_read(hdev, 0x70010200, &dev_id); if (err < 0) { bt_dev_err(hdev, "Failed to get device id (%d)", err); @@ -1015,6 +1067,16 @@ static int btmtksdio_setup(struct hci_dev *hdev) return err; } + /* Enable GPIO reset mechanism */ + if (bdev->reset) { + err = btmtksdio_reset_setting(hdev); + if (err < 0) { + bt_dev_err(hdev, "Failed to enable Reset setting (%d)", err); + devm_gpiod_put(bdev->dev, bdev->reset); + bdev->reset = NULL; + } + } + break; case 0x7663: case 0x7668: @@ -1111,6 +1173,47 @@ static int btmtksdio_send_frame(struct hci_dev *hdev, struct sk_buff *skb) return 0; } +static void btmtksdio_cmd_timeout(struct hci_dev *hdev) +{ + struct btmtksdio_dev *bdev = hci_get_drvdata(hdev); + u32 status; + int err; + + if (!bdev->reset || bdev->data->chipid != 0x7921) + return; + + pm_runtime_get_sync(bdev->dev); + + if (test_and_set_bit(BTMTKSDIO_HW_RESET_ACTIVE, &bdev->tx_state)) + return; + + sdio_claim_host(bdev->func); + + sdio_writel(bdev->func, C_INT_EN_CLR, MTK_REG_CHLPCR, NULL); + skb_queue_purge(&bdev->txq); + cancel_work_sync(&bdev->txrx_work); + + gpiod_set_value_cansleep(bdev->reset, 1); + msleep(100); + gpiod_set_value_cansleep(bdev->reset, 0); + + err = readx_poll_timeout(btmtksdio_chcr_query, bdev, status, + status & BT_RST_DONE, 100000, 2000000); + if (err < 0) { + bt_dev_err(hdev, "Failed to reset (%d)", err); + goto err; + } + + clear_bit(BTMTKSDIO_PATCH_ENABLED, &bdev->tx_state); +err: + sdio_release_host(bdev->func); + + pm_runtime_put_noidle(bdev->dev); + pm_runtime_disable(bdev->dev); + + hci_reset_dev(hdev); +} + static bool btmtksdio_sdio_wakeup(struct hci_dev *hdev) { struct btmtksdio_dev *bdev = hci_get_drvdata(hdev); @@ -1172,6 +1275,7 @@ static int btmtksdio_probe(struct sdio_func *func, hdev->open = btmtksdio_open; hdev->close = btmtksdio_close; + hdev->cmd_timeout = btmtksdio_cmd_timeout; hdev->flush = btmtksdio_flush; hdev->setup = btmtksdio_setup; hdev->shutdown = btmtksdio_shutdown; @@ -1216,6 +1320,13 @@ static int btmtksdio_probe(struct sdio_func *func, if (err) bt_dev_err(hdev, "failed to initialize device wakeup"); + bdev->dev->of_node = of_find_compatible_node(NULL, NULL, + "mediatek,mt7921s-bluetooth"); + bdev->reset = devm_gpiod_get_optional(bdev->dev, "reset", + GPIOD_OUT_LOW); + if (IS_ERR(bdev->reset)) + err = PTR_ERR(bdev->reset); + return err; } -- cgit From e4412654e260842e1a94ffe0d4026e8a6fd34246 Mon Sep 17 00:00:00 2001 From: Sean Wang Date: Wed, 9 Feb 2022 02:17:41 +0800 Subject: Bluetooth: mediatek: fix the conflict between mtk and msft vendor event There is a conflict between MediaTek wmt event and msft vendor extension logic in the core layer since 145373cb1b1f ("Bluetooth: Add framework for Microsoft vendor extension") was introduced because we changed the type of mediatek wmt event to the type of msft vendor event in the driver. But the purpose we reported mediatek event to the core layer is for the diagnostic purpose with that we are able to see the full packet trace via monitoring socket with btmon. Thus, it is harmless we keep the original type of mediatek vendor event here to avoid breaking the msft extension function especially they can be supported by Mediatek chipset like MT7921 , MT7922 devices and future devices. Signed-off-by: Sean Wang Signed-off-by: Marcel Holtmann --- drivers/bluetooth/btmtk.h | 1 + drivers/bluetooth/btmtksdio.c | 9 +-------- drivers/bluetooth/btusb.c | 8 -------- 3 files changed, 2 insertions(+), 16 deletions(-) diff --git a/drivers/bluetooth/btmtk.h b/drivers/bluetooth/btmtk.h index 8960a5f89d48..013850fd2055 100644 --- a/drivers/bluetooth/btmtk.h +++ b/drivers/bluetooth/btmtk.h @@ -5,6 +5,7 @@ #define FIRMWARE_MT7668 "mediatek/mt7668pr2h.bin" #define FIRMWARE_MT7961 "mediatek/BT_RAM_CODE_MT7961_1_2_hdr.bin" +#define HCI_EV_WMT 0xe4 #define HCI_WMT_MAX_EVENT_SIZE 64 #define BTMTK_WMT_REG_WRITE 0x1 diff --git a/drivers/bluetooth/btmtksdio.c b/drivers/bluetooth/btmtksdio.c index 8e200e80d2f6..cbb09e1b823d 100644 --- a/drivers/bluetooth/btmtksdio.c +++ b/drivers/bluetooth/btmtksdio.c @@ -381,13 +381,6 @@ static int btmtksdio_recv_event(struct hci_dev *hdev, struct sk_buff *skb) struct hci_event_hdr *hdr = (void *)skb->data; int err; - /* Fix up the vendor event id with 0xff for vendor specific instead - * of 0xe4 so that event send via monitoring socket can be parsed - * properly. - */ - if (hdr->evt == 0xe4) - hdr->evt = HCI_EV_VENDOR; - /* When someone waits for the WMT event, the skb is being cloned * and being processed the events from there then. */ @@ -403,7 +396,7 @@ static int btmtksdio_recv_event(struct hci_dev *hdev, struct sk_buff *skb) if (err < 0) goto err_free_skb; - if (hdr->evt == HCI_EV_VENDOR) { + if (hdr->evt == HCI_EV_WMT) { if (test_and_clear_bit(BTMTKSDIO_TX_WAIT_VND_EVT, &bdev->tx_state)) { /* Barrier to sync with other CPUs */ diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c index 9e0d59d4382a..558151f2f150 100644 --- a/drivers/bluetooth/btusb.c +++ b/drivers/bluetooth/btusb.c @@ -2256,7 +2256,6 @@ static void btusb_mtk_wmt_recv(struct urb *urb) { struct hci_dev *hdev = urb->context; struct btusb_data *data = hci_get_drvdata(hdev); - struct hci_event_hdr *hdr; struct sk_buff *skb; int err; @@ -2276,13 +2275,6 @@ static void btusb_mtk_wmt_recv(struct urb *urb) hci_skb_pkt_type(skb) = HCI_EVENT_PKT; skb_put_data(skb, urb->transfer_buffer, urb->actual_length); - hdr = (void *)skb->data; - /* Fix up the vendor event id with 0xff for vendor specific - * instead of 0xe4 so that event send via monitoring socket can - * be parsed properly. - */ - hdr->evt = 0xff; - /* When someone waits for the WMT event, the skb is being cloned * and being processed the events from there then. */ -- cgit From 9b392e0e0b6d026da5a62bb79a08f32e27af858e Mon Sep 17 00:00:00 2001 From: Luiz Augusto von Dentz Date: Thu, 3 Mar 2022 13:11:57 -0800 Subject: Bluetooth: Fix not checking for valid hdev on bt_dev_{info,warn,err,dbg} This fixes attemting to print hdev->name directly which causes them to print an error: kernel: read_version:367: (efault): sock 000000006a3008f2 Signed-off-by: Luiz Augusto von Dentz Signed-off-by: Marcel Holtmann --- include/net/bluetooth/bluetooth.h | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/include/net/bluetooth/bluetooth.h b/include/net/bluetooth/bluetooth.h index a647e5fabdbd..2aa5e95808a5 100644 --- a/include/net/bluetooth/bluetooth.h +++ b/include/net/bluetooth/bluetooth.h @@ -204,19 +204,21 @@ void bt_err_ratelimited(const char *fmt, ...); #define BT_DBG(fmt, ...) pr_debug(fmt "\n", ##__VA_ARGS__) #endif +#define bt_dev_name(hdev) ((hdev) ? (hdev)->name : "null") + #define bt_dev_info(hdev, fmt, ...) \ - BT_INFO("%s: " fmt, (hdev)->name, ##__VA_ARGS__) + BT_INFO("%s: " fmt, bt_dev_name(hdev), ##__VA_ARGS__) #define bt_dev_warn(hdev, fmt, ...) \ - BT_WARN("%s: " fmt, (hdev)->name, ##__VA_ARGS__) + BT_WARN("%s: " fmt, bt_dev_name(hdev), ##__VA_ARGS__) #define bt_dev_err(hdev, fmt, ...) \ - BT_ERR("%s: " fmt, (hdev)->name, ##__VA_ARGS__) + BT_ERR("%s: " fmt, bt_dev_name(hdev), ##__VA_ARGS__) #define bt_dev_dbg(hdev, fmt, ...) \ - BT_DBG("%s: " fmt, (hdev)->name, ##__VA_ARGS__) + BT_DBG("%s: " fmt, bt_dev_name(hdev), ##__VA_ARGS__) #define bt_dev_warn_ratelimited(hdev, fmt, ...) \ - bt_warn_ratelimited("%s: " fmt, (hdev)->name, ##__VA_ARGS__) + bt_warn_ratelimited("%s: " fmt, bt_dev_name(hdev), ##__VA_ARGS__) #define bt_dev_err_ratelimited(hdev, fmt, ...) \ - bt_err_ratelimited("%s: " fmt, (hdev)->name, ##__VA_ARGS__) + bt_err_ratelimited("%s: " fmt, bt_dev_name(hdev), ##__VA_ARGS__) /* Connection and socket states */ enum { -- cgit From f95fd5f364839ec48b18b80312ed86bf51908e56 Mon Sep 17 00:00:00 2001 From: Luiz Augusto von Dentz Date: Thu, 3 Mar 2022 14:17:07 -0800 Subject: Bluetooth: btusb: Make use of of BIT macro to declare flags This makes use of BIT macro when declaring BTUSB flags which makes it understand how many bits are in use and many are left. Signed-off-by: Luiz Augusto von Dentz Signed-off-by: Marcel Holtmann --- drivers/bluetooth/btusb.c | 54 +++++++++++++++++++++++------------------------ 1 file changed, 27 insertions(+), 27 deletions(-) diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c index 558151f2f150..34d008380fdb 100644 --- a/drivers/bluetooth/btusb.c +++ b/drivers/bluetooth/btusb.c @@ -36,33 +36,33 @@ static bool reset = true; static struct usb_driver btusb_driver; -#define BTUSB_IGNORE 0x01 -#define BTUSB_DIGIANSWER 0x02 -#define BTUSB_CSR 0x04 -#define BTUSB_SNIFFER 0x08 -#define BTUSB_BCM92035 0x10 -#define BTUSB_BROKEN_ISOC 0x20 -#define BTUSB_WRONG_SCO_MTU 0x40 -#define BTUSB_ATH3012 0x80 -#define BTUSB_INTEL_COMBINED 0x100 -#define BTUSB_INTEL_BOOT 0x200 -#define BTUSB_BCM_PATCHRAM 0x400 -#define BTUSB_MARVELL 0x800 -#define BTUSB_SWAVE 0x1000 -#define BTUSB_AMP 0x4000 -#define BTUSB_QCA_ROME 0x8000 -#define BTUSB_BCM_APPLE 0x10000 -#define BTUSB_REALTEK 0x20000 -#define BTUSB_BCM2045 0x40000 -#define BTUSB_IFNUM_2 0x80000 -#define BTUSB_CW6622 0x100000 -#define BTUSB_MEDIATEK 0x200000 -#define BTUSB_WIDEBAND_SPEECH 0x400000 -#define BTUSB_VALID_LE_STATES 0x800000 -#define BTUSB_QCA_WCN6855 0x1000000 -#define BTUSB_INTEL_BROKEN_SHUTDOWN_LED 0x2000000 -#define BTUSB_INTEL_BROKEN_INITIAL_NCMD 0x4000000 -#define BTUSB_INTEL_NO_WBS_SUPPORT 0x8000000 +#define BTUSB_IGNORE BIT(0) +#define BTUSB_DIGIANSWER BIT(1) +#define BTUSB_CSR BIT(2) +#define BTUSB_SNIFFER BIT(3) +#define BTUSB_BCM92035 BIT(4) +#define BTUSB_BROKEN_ISOC BIT(5) +#define BTUSB_WRONG_SCO_MTU BIT(6) +#define BTUSB_ATH3012 BIT(7) +#define BTUSB_INTEL_COMBINED BIT(8) +#define BTUSB_INTEL_BOOT BIT(9) +#define BTUSB_BCM_PATCHRAM BIT(10) +#define BTUSB_MARVELL BIT(11) +#define BTUSB_SWAVE BIT(12) +#define BTUSB_AMP BIT(13) +#define BTUSB_QCA_ROME BIT(14) +#define BTUSB_BCM_APPLE BIT(15) +#define BTUSB_REALTEK BIT(16) +#define BTUSB_BCM2045 BIT(17) +#define BTUSB_IFNUM_2 BIT(18) +#define BTUSB_CW6622 BIT(19) +#define BTUSB_MEDIATEK BIT(20) +#define BTUSB_WIDEBAND_SPEECH BIT(21) +#define BTUSB_VALID_LE_STATES BIT(22) +#define BTUSB_QCA_WCN6855 BIT(23) +#define BTUSB_INTEL_BROKEN_SHUTDOWN_LED BIT(24) +#define BTUSB_INTEL_BROKEN_INITIAL_NCMD BIT(25) +#define BTUSB_INTEL_NO_WBS_SUPPORT BIT(26) static const struct usb_device_id btusb_table[] = { /* Generic Bluetooth USB device */ -- cgit From 728abc0151b06b3cb1d084ca2ee7418c3fad89e2 Mon Sep 17 00:00:00 2001 From: Niels Dossche Date: Wed, 9 Feb 2022 15:08:51 +0100 Subject: Bluetooth: hci_event: Add missing locking on hdev in hci_le_ext_adv_term_evt Both hci_find_adv_instance and hci_remove_adv_instance have a comment above their function definition saying that these two functions require the caller to hold the hdev->lock lock. However, hci_le_ext_adv_term_evt does not acquire that lock and neither does its caller hci_le_meta_evt (hci_le_meta_evt calls hci_le_ext_adv_term_evt via an indirect function call because of the lookup in hci_le_ev_table). The other event handlers all acquire and release the hdev->lock and they follow the rule that hci_find_adv_instance and hci_remove_adv_instance must be called while holding the hdev->lock lock. The solution is to make sure hci_le_ext_adv_term_evt also acquires and releases the hdev->lock lock. The check on ev->status which logs a warning and does an early return is not covered by the lock because other functions also access ev->status without holding the lock. Signed-off-by: Niels Dossche Signed-off-by: Marcel Holtmann --- net/bluetooth/hci_event.c | 19 ++++++++++++------- 1 file changed, 12 insertions(+), 7 deletions(-) diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c index 63b925921c87..4888c1f8a9b7 100644 --- a/net/bluetooth/hci_event.c +++ b/net/bluetooth/hci_event.c @@ -5716,8 +5716,6 @@ static void hci_le_ext_adv_term_evt(struct hci_dev *hdev, void *data, bt_dev_dbg(hdev, "status 0x%2.2x", ev->status); - adv = hci_find_adv_instance(hdev, ev->handle); - /* The Bluetooth Core 5.3 specification clearly states that this event * shall not be sent when the Host disables the advertising set. So in * case of HCI_ERROR_CANCELLED_BY_HOST, just ignore the event. @@ -5730,9 +5728,13 @@ static void hci_le_ext_adv_term_evt(struct hci_dev *hdev, void *data, return; } + hci_dev_lock(hdev); + + adv = hci_find_adv_instance(hdev, ev->handle); + if (ev->status) { if (!adv) - return; + goto unlock; /* Remove advertising as it has been terminated */ hci_remove_adv_instance(hdev, ev->handle); @@ -5740,12 +5742,12 @@ static void hci_le_ext_adv_term_evt(struct hci_dev *hdev, void *data, list_for_each_entry_safe(adv, n, &hdev->adv_instances, list) { if (adv->enabled) - return; + goto unlock; } /* We are no longer advertising, clear HCI_LE_ADV */ hci_dev_clear_flag(hdev, HCI_LE_ADV); - return; + goto unlock; } if (adv) @@ -5760,16 +5762,19 @@ static void hci_le_ext_adv_term_evt(struct hci_dev *hdev, void *data, if (hdev->adv_addr_type != ADDR_LE_DEV_RANDOM || bacmp(&conn->resp_addr, BDADDR_ANY)) - return; + goto unlock; if (!ev->handle) { bacpy(&conn->resp_addr, &hdev->random_addr); - return; + goto unlock; } if (adv) bacpy(&conn->resp_addr, &adv->random_addr); } + +unlock: + hci_dev_unlock(hdev); } static void hci_le_conn_update_complete_evt(struct hci_dev *hdev, void *data, -- cgit From 4bd80d7a4039ac605a1e9ae767d2b01dbfc9b61e Mon Sep 17 00:00:00 2001 From: Niels Dossche Date: Sun, 13 Feb 2022 00:14:30 +0100 Subject: Bluetooth: move adv_instance_cnt read within the device lock The field adv_instance_cnt is always accessed within a device lock, except in the function add_advertising. A concurrent remove of an advertisement with adding another one could result in the if check "if a new instance was actually added" to not trigger, resulting in not triggering the "advertising added event". Signed-off-by: Niels Dossche Signed-off-by: Marcel Holtmann --- net/bluetooth/mgmt.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c index 89b1c0488527..68ce7dcff0e3 100644 --- a/net/bluetooth/mgmt.c +++ b/net/bluetooth/mgmt.c @@ -8079,7 +8079,7 @@ static int add_advertising(struct sock *sk, struct hci_dev *hdev, u32 flags; u8 status; u16 timeout, duration; - unsigned int prev_instance_cnt = hdev->adv_instance_cnt; + unsigned int prev_instance_cnt; u8 schedule_instance = 0; struct adv_info *next_instance; int err; @@ -8130,6 +8130,8 @@ static int add_advertising(struct sock *sk, struct hci_dev *hdev, goto unlock; } + prev_instance_cnt = hdev->adv_instance_cnt; + err = hci_add_adv_instance(hdev, cp->instance, flags, cp->adv_data_len, cp->data, cp->scan_rsp_len, -- cgit From c5e25bb585cea7458b173e017309ef6ca22b44ed Mon Sep 17 00:00:00 2001 From: Yake Yang Date: Wed, 23 Feb 2022 07:55:59 +0800 Subject: Bluetooth: btusb: Add a new PID/VID 13d3/3567 for MT7921 Add VID 13D3 & PID 3567 for MediaTek MT7921 USB Bluetooth chip. The information in /sys/kernel/debug/usb/devices about the Bluetooth device is listed as the below. T: Bus=05 Lev=01 Prnt=01 Port=00 Cnt=01 Dev#= 2 Spd=480 MxCh= 0 D: Ver= 2.10 Cls=ef(misc ) Sub=02 Prot=01 MxPS=64 #Cfgs= 1 P: Vendor=13d3 ProdID=3567 Rev= 1.00 S: Manufacturer=MediaTek Inc. S: Product=Wireless_Device S: SerialNumber=000000000 C:* #Ifs= 3 Cfg#= 1 Atr=e0 MxPwr=100mA A: FirstIf#= 0 IfCount= 3 Cls=e0(wlcon) Sub=01 Prot=01 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=125us E: Ad=82(I) Atr=02(Bulk) MxPS= 512 Ivl=0ms E: Ad=02(O) Atr=02(Bulk) MxPS= 512 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 I: If#= 1 Alt= 6 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=btusb E: Ad=83(I) Atr=01(Isoc) MxPS= 63 Ivl=1ms E: Ad=03(O) Atr=01(Isoc) MxPS= 63 Ivl=1ms I:* If#= 2 Alt= 0 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) E: Ad=8a(I) Atr=03(Int.) MxPS= 64 Ivl=125us E: Ad=0a(O) Atr=03(Int.) MxPS= 64 Ivl=125us I: If#= 2 Alt= 1 #EPs= 2 Cls=e0(wlcon) Sub=01 Prot=01 Driver=(none) E: Ad=8a(I) Atr=03(Int.) MxPS= 64 Ivl=125us E: Ad=0a(O) Atr=03(Int.) MxPS= 64 Ivl=125us Co-developed-by: Sean Wang Signed-off-by: Sean Wang Signed-off-by: Yake Yang Signed-off-by: Marcel Holtmann --- drivers/bluetooth/btusb.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c index 34d008380fdb..141de9d7c2a3 100644 --- a/drivers/bluetooth/btusb.c +++ b/drivers/bluetooth/btusb.c @@ -455,6 +455,9 @@ static const struct usb_device_id blacklist_table[] = { { USB_DEVICE(0x13d3, 0x3564), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, + { USB_DEVICE(0x13d3, 0x3567), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, { USB_DEVICE(0x0489, 0xe0cd), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, -- cgit From eb3f05179a27b98f99e590bf2164582113f23f7e Mon Sep 17 00:00:00 2001 From: Yake Yang Date: Wed, 23 Feb 2022 07:56:00 +0800 Subject: Bluetooth: btmtksdio: Fix kernel oops when sdio suspend. Do not kfree the skb when the skb failed to send with __hci_cmd_sync 2435.241210] Call trace: [ 2435.241224] kfree_skb+0x20/0x140 [ 2435.241240] btmtksdio_sdio_wakeup+0x8c/0xcc [ 2435.241360] hci_suspend_notifier+0x108/0x184 [ 2435.241377] notifier_call_chain_robust+0x58/0xd8 [ 2435.241390] blocking_notifier_call_chain_robust+0x54/0x84 [ 2435.241402] pm_notifier_call_chain_robust+0x2c/0x4c [ 2435.241414] suspend_prepare+0x40/0x238 [ 2435.241425] enter_state+0xec/0x3a8 [ 2435.241436] pm_suspend+0x60/0xcc [ 2435.241446] state_store+0xb8/0x114 [ 2435.241460] kobj_attr_store+0x18/0x2c [ 2435.241473] sysfs_kf_write+0x44/0x58 [ 2435.241486] kernfs_fop_write_iter+0xf4/0x190 [ 2435.241500] vfs_write+0x2b0/0x2e4 [ 2435.241511] ksys_write+0x80/0xec [ 2435.241523] __arm64_sys_write+0x24/0x30 [ 2435.241538] el0_svc_common+0xf0/0x1d8 [ 2435.241550] do_el0_svc_compat+0x28/0x54 [ 2435.241564] el0_svc_compat+0x10/0x1c [ 2435.241574] el0_sync_compat_handler+0xa8/0xcc [ 2435.241586] el0_sync_compat+0x188/0x1c0 [ 2435.241606] Code: a9014ff4 910003fd b40002c0 aa0003f3 (b84d4c08) [ 2435.241619] ---[ end trace d496539b850baf14 ]--- Fixes: ce64b3e94919 ("Bluetooth: mt7921s: Support wake on bluetooth") Co-developed-by: Sean Wang Signed-off-by: Sean Wang Signed-off-by: Yake Yang Signed-off-by: Marcel Holtmann --- drivers/bluetooth/btmtksdio.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/bluetooth/btmtksdio.c b/drivers/bluetooth/btmtksdio.c index cbb09e1b823d..df3f9d090529 100644 --- a/drivers/bluetooth/btmtksdio.c +++ b/drivers/bluetooth/btmtksdio.c @@ -1226,8 +1226,8 @@ static bool btmtksdio_sdio_wakeup(struct hci_dev *hdev) &bt_awake, HCI_CMD_TIMEOUT); if (IS_ERR(skb)) may_wakeup = false; - - kfree_skb(skb); + else + kfree_skb(skb); } return may_wakeup; -- cgit From d3715b2333e9a21692ba16ef8645eda584a9515d Mon Sep 17 00:00:00 2001 From: "Minghao Chi (CGEL ZTE)" Date: Fri, 25 Feb 2022 07:41:52 +0000 Subject: Bluetooth: use memset avoid memory leaks Use memset to initialize structs to prevent memory leaks in l2cap_ecred_connect Reported-by: Zeal Robot Signed-off-by: Minghao Chi (CGEL ZTE) Signed-off-by: Marcel Holtmann --- net/bluetooth/l2cap_core.c | 1 + 1 file changed, 1 insertion(+) diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c index e817ff0607a0..8df99c07f272 100644 --- a/net/bluetooth/l2cap_core.c +++ b/net/bluetooth/l2cap_core.c @@ -1436,6 +1436,7 @@ static void l2cap_ecred_connect(struct l2cap_chan *chan) l2cap_ecred_init(chan, 0); + memset(&data, 0, sizeof(data)); data.pdu.req.psm = chan->psm; data.pdu.req.mtu = cpu_to_le16(chan->imtu); data.pdu.req.mps = cpu_to_le16(chan->mps); -- cgit From 01da346c1802f046496845cccd7c871ca35f24a7 Mon Sep 17 00:00:00 2001 From: Luca Weiss Date: Fri, 25 Feb 2022 21:41:38 +0100 Subject: Bluetooth: hci_bcm: add BCM43430A0 & BCM43430A1 Add the compatible for BCM43430A0 bluetooth used in lg-lenok and BCM43430A1 used in asus-sparrow. Signed-off-by: Luca Weiss Signed-off-by: Marcel Holtmann --- drivers/bluetooth/hci_bcm.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/drivers/bluetooth/hci_bcm.c b/drivers/bluetooth/hci_bcm.c index d634a27bc850..bd090d92a548 100644 --- a/drivers/bluetooth/hci_bcm.c +++ b/drivers/bluetooth/hci_bcm.c @@ -1513,6 +1513,8 @@ static const struct of_device_id bcm_bluetooth_of_match[] = { { .compatible = "brcm,bcm4330-bt" }, { .compatible = "brcm,bcm4334-bt" }, { .compatible = "brcm,bcm4345c5" }, + { .compatible = "brcm,bcm43430a0-bt" }, + { .compatible = "brcm,bcm43430a1-bt" }, { .compatible = "brcm,bcm43438-bt", .data = &bcm43438_device_data }, { .compatible = "brcm,bcm43540-bt", .data = &bcm4354_device_data }, { .compatible = "brcm,bcm4335a0" }, -- cgit From 6dfbe29f45fb0bde29213dbd754a79e8bfc6ecef Mon Sep 17 00:00:00 2001 From: Helmut Grohne Date: Sat, 26 Feb 2022 16:22:56 +0100 Subject: Bluetooth: btusb: Add another Realtek 8761BU This device is sometimes wrapped with a label "EDUP". T: Bus=01 Lev=02 Prnt=02 Port=02 Cnt=03 Dev#=107 Spd=12 MxCh= 0 D: Ver= 1.10 Cls=e0(wlcon) Sub=01 Prot=01 MxPS=64 #Cfgs= 1 P: Vendor=2550 ProdID=8761 Rev= 2.00 S: Manufacturer=Realtek S: Product=Bluetooth Radio S: SerialNumber=00E04C239987 C:* #Ifs= 2 Cfg#= 1 Atr=e0 MxPwr=500mA 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=02(O) Atr=02(Bulk) MxPS= 64 Ivl=0ms E: Ad=82(I) 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=03(O) Atr=01(Isoc) MxPS= 0 Ivl=1ms E: Ad=83(I) 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=03(O) Atr=01(Isoc) MxPS= 9 Ivl=1ms E: Ad=83(I) 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=03(O) Atr=01(Isoc) MxPS= 17 Ivl=1ms E: Ad=83(I) 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=03(O) Atr=01(Isoc) MxPS= 25 Ivl=1ms E: Ad=83(I) 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=03(O) Atr=01(Isoc) MxPS= 33 Ivl=1ms E: Ad=83(I) 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=03(O) Atr=01(Isoc) MxPS= 49 Ivl=1ms E: Ad=83(I) Atr=01(Isoc) MxPS= 49 Ivl=1ms Signed-off-by: Helmut Grohne Link: https://bugs.launchpad.net/ubuntu/+source/linux/+bug/1955351 Signed-off-by: Marcel Holtmann --- drivers/bluetooth/btusb.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c index 141de9d7c2a3..1bb00b7547fb 100644 --- a/drivers/bluetooth/btusb.c +++ b/drivers/bluetooth/btusb.c @@ -496,6 +496,8 @@ static const struct usb_device_id blacklist_table[] = { /* Additional Realtek 8761BU Bluetooth devices */ { USB_DEVICE(0x0b05, 0x190e), .driver_info = BTUSB_REALTEK | BTUSB_WIDEBAND_SPEECH }, + { USB_DEVICE(0x2550, 0x8761), .driver_info = BTUSB_REALTEK | + BTUSB_WIDEBAND_SPEECH }, /* Additional Realtek 8821AE Bluetooth devices */ { USB_DEVICE(0x0b05, 0x17dc), .driver_info = BTUSB_REALTEK }, -- cgit