diff options
Diffstat (limited to 'drivers/bluetooth/btusb.c')
-rw-r--r-- | drivers/bluetooth/btusb.c | 96 |
1 files changed, 70 insertions, 26 deletions
diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c index d31edad7a056..e384ef6ff050 100644 --- a/drivers/bluetooth/btusb.c +++ b/drivers/bluetooth/btusb.c @@ -477,6 +477,7 @@ static const struct usb_device_id quirks_table[] = { { USB_DEVICE(0x8087, 0x0033), .driver_info = BTUSB_INTEL_COMBINED }, { USB_DEVICE(0x8087, 0x0035), .driver_info = BTUSB_INTEL_COMBINED }, { USB_DEVICE(0x8087, 0x0036), .driver_info = BTUSB_INTEL_COMBINED }, + { USB_DEVICE(0x8087, 0x0037), .driver_info = BTUSB_INTEL_COMBINED }, { USB_DEVICE(0x8087, 0x0038), .driver_info = BTUSB_INTEL_COMBINED }, { USB_DEVICE(0x8087, 0x07da), .driver_info = BTUSB_CSR }, { USB_DEVICE(0x8087, 0x07dc), .driver_info = BTUSB_INTEL_COMBINED | @@ -542,6 +543,8 @@ static const struct usb_device_id quirks_table[] = { /* Realtek 8852BE Bluetooth devices */ { USB_DEVICE(0x0cb8, 0xc559), .driver_info = BTUSB_REALTEK | BTUSB_WIDEBAND_SPEECH }, + { USB_DEVICE(0x0bda, 0x4853), .driver_info = BTUSB_REALTEK | + BTUSB_WIDEBAND_SPEECH }, { USB_DEVICE(0x0bda, 0x887b), .driver_info = BTUSB_REALTEK | BTUSB_WIDEBAND_SPEECH }, { USB_DEVICE(0x0bda, 0xb85b), .driver_info = BTUSB_REALTEK | @@ -553,6 +556,9 @@ static const struct usb_device_id quirks_table[] = { { USB_DEVICE(0x13d3, 0x3572), .driver_info = BTUSB_REALTEK | BTUSB_WIDEBAND_SPEECH }, + /* Realtek 8852BT/8852BE-VT Bluetooth devices */ + { USB_DEVICE(0x0bda, 0x8520), .driver_info = BTUSB_REALTEK | + BTUSB_WIDEBAND_SPEECH }, /* Realtek Bluetooth devices */ { USB_VENDOR_AND_INTERFACE_INFO(0x0bda, 0xe0, 0x01, 0x01), .driver_info = BTUSB_REALTEK }, @@ -583,6 +589,9 @@ static const struct usb_device_id quirks_table[] = { { USB_DEVICE(0x0489, 0xe0c8), .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 }, { USB_DEVICE(0x0489, 0xe0e0), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, @@ -592,6 +601,9 @@ static const struct usb_device_id quirks_table[] = { { USB_DEVICE(0x04ca, 0x3802), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, + { USB_DEVICE(0x0e8d, 0x0608), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, { USB_DEVICE(0x13d3, 0x3563), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, @@ -607,10 +619,12 @@ static const struct usb_device_id quirks_table[] = { { USB_DEVICE(0x13d3, 0x3583), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, - { USB_DEVICE(0x0489, 0xe0cd), .driver_info = BTUSB_MEDIATEK | + { USB_DEVICE(0x13d3, 0x3606), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, - { USB_DEVICE(0x0e8d, 0x0608), .driver_info = BTUSB_MEDIATEK | + + /* MediaTek MT7922 Bluetooth devices */ + { USB_DEVICE(0x13d3, 0x3585), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, @@ -621,12 +635,6 @@ static const struct usb_device_id quirks_table[] = { { USB_DEVICE(0x0489, 0xe0d9), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, - { USB_DEVICE(0x0489, 0xe0f5), .driver_info = BTUSB_MEDIATEK | - BTUSB_WIDEBAND_SPEECH | - BTUSB_VALID_LE_STATES }, - { USB_DEVICE(0x13d3, 0x3568), .driver_info = BTUSB_MEDIATEK | - BTUSB_WIDEBAND_SPEECH | - BTUSB_VALID_LE_STATES }, { USB_DEVICE(0x0489, 0xe0e2), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, @@ -651,10 +659,39 @@ static const struct usb_device_id quirks_table[] = { { USB_DEVICE(0x04ca, 0x3804), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, + { USB_DEVICE(0x04ca, 0x38e4), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, + { USB_DEVICE(0x13d3, 0x3568), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, + { USB_DEVICE(0x13d3, 0x3605), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, + { USB_DEVICE(0x13d3, 0x3607), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, + { USB_DEVICE(0x13d3, 0x3614), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, + { USB_DEVICE(0x13d3, 0x3615), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, { USB_DEVICE(0x35f5, 0x7922), .driver_info = BTUSB_MEDIATEK | BTUSB_WIDEBAND_SPEECH | BTUSB_VALID_LE_STATES }, + /* Additional MediaTek MT7925 Bluetooth devices */ + { USB_DEVICE(0x0489, 0xe113), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, + { USB_DEVICE(0x13d3, 0x3602), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, + { USB_DEVICE(0x13d3, 0x3603), .driver_info = BTUSB_MEDIATEK | + BTUSB_WIDEBAND_SPEECH | + BTUSB_VALID_LE_STATES }, + /* Additional Realtek 8723AE Bluetooth devices */ { USB_DEVICE(0x0930, 0x021d), .driver_info = BTUSB_REALTEK }, { USB_DEVICE(0x13d3, 0x3394), .driver_info = BTUSB_REALTEK }, @@ -2941,7 +2978,7 @@ static int btusb_mtk_uhw_reg_read(struct btusb_data *data, u32 reg, u32 *val) err = usb_control_msg(data->udev, pipe, 0x01, 0xDE, reg >> 16, reg & 0xffff, - buf, 4, USB_CTRL_SET_TIMEOUT); + buf, 4, USB_CTRL_GET_TIMEOUT); if (err < 0) { bt_dev_err(hdev, "Failed to read uhw reg(%d)", err); goto err_free_buf; @@ -2969,7 +3006,7 @@ static int btusb_mtk_reg_read(struct btusb_data *data, u32 reg, u32 *val) err = usb_control_msg(data->udev, pipe, 0x63, USB_TYPE_VENDOR | USB_DIR_IN, reg >> 16, reg & 0xffff, - buf, size, USB_CTRL_SET_TIMEOUT); + buf, size, USB_CTRL_GET_TIMEOUT); if (err < 0) goto err_free_buf; @@ -3080,7 +3117,7 @@ static int btusb_mtk_setup(struct hci_dev *hdev) int err, status; u32 dev_id = 0; char fw_bin_name[64]; - u32 fw_version = 0; + u32 fw_version = 0, fw_flavor = 0; u8 param; struct btmediatek_data *mediatek; @@ -3103,6 +3140,12 @@ static int btusb_mtk_setup(struct hci_dev *hdev) bt_dev_err(hdev, "Failed to get fw version (%d)", err); return err; } + err = btusb_mtk_id_get(data, 0x70010020, &fw_flavor); + if (err < 0) { + bt_dev_err(hdev, "Failed to get fw flavor (%d)", err); + return err; + } + fw_flavor = (fw_flavor & 0x00000080) >> 7; } mediatek = hci_get_priv(hdev); @@ -3127,6 +3170,10 @@ static int btusb_mtk_setup(struct hci_dev *hdev) snprintf(fw_bin_name, sizeof(fw_bin_name), "mediatek/mt%04x/BT_RAM_CODE_MT%04x_1_%x_hdr.bin", dev_id & 0xffff, dev_id & 0xffff, (fw_version & 0xff) + 1); + else if (dev_id == 0x7961 && fw_flavor) + snprintf(fw_bin_name, sizeof(fw_bin_name), + "mediatek/BT_RAM_CODE_MT%04x_1a_%x_hdr.bin", + dev_id & 0xffff, (fw_version & 0xff) + 1); else snprintf(fw_bin_name, sizeof(fw_bin_name), "mediatek/BT_RAM_CODE_MT%04x_1_%x_hdr.bin", @@ -3273,7 +3320,6 @@ static int btusb_recv_acl_mtk(struct hci_dev *hdev, struct sk_buff *skb) { struct btusb_data *data = hci_get_drvdata(hdev); u16 handle = le16_to_cpu(hci_acl_hdr(skb)->handle); - struct sk_buff *skb_cd; switch (handle) { case 0xfc6f: /* Firmware dump from device */ @@ -3286,9 +3332,12 @@ static int btusb_recv_acl_mtk(struct hci_dev *hdev, struct sk_buff *skb) * for backward compatibility, so we have to clone the packet * extraly for the in-kernel coredump support. */ - skb_cd = skb_clone(skb, GFP_ATOMIC); - if (skb_cd) - btmtk_process_coredump(hdev, skb_cd); + if (IS_ENABLED(CONFIG_DEV_COREDUMP)) { + struct sk_buff *skb_cd = skb_clone(skb, GFP_ATOMIC); + + if (skb_cd) + btmtk_process_coredump(hdev, skb_cd); + } fallthrough; case 0x05ff: /* Firmware debug logging 1 */ @@ -3461,13 +3510,12 @@ static void btusb_dump_hdr_qca(struct hci_dev *hdev, struct sk_buff *skb) static void btusb_coredump_qca(struct hci_dev *hdev) { + int err; static const u8 param[] = { 0x26 }; - struct sk_buff *skb; - skb = __hci_cmd_sync(hdev, 0xfc0c, 1, param, HCI_CMD_TIMEOUT); - if (IS_ERR(skb)) - bt_dev_err(hdev, "%s: triggle crash failed (%ld)", __func__, PTR_ERR(skb)); - kfree_skb(skb); + err = __hci_cmd_send(hdev, 0xfc0c, 1, param); + if (err < 0) + bt_dev_err(hdev, "%s: triggle crash failed (%d)", __func__, err); } /* @@ -3673,7 +3721,7 @@ static int btusb_qca_send_vendor_req(struct usb_device *udev, u8 request, */ pipe = usb_rcvctrlpipe(udev, 0); err = usb_control_msg(udev, pipe, request, USB_TYPE_VENDOR | USB_DIR_IN, - 0, 0, buf, size, USB_CTRL_SET_TIMEOUT); + 0, 0, buf, size, USB_CTRL_GET_TIMEOUT); if (err < 0) { dev_err(&udev->dev, "Failed to access otp area (%d)", err); goto done; @@ -4311,11 +4359,6 @@ static int btusb_probe(struct usb_interface *intf, hdev->bus = HCI_USB; hci_set_drvdata(hdev, data); - if (id->driver_info & BTUSB_AMP) - hdev->dev_type = HCI_AMP; - else - hdev->dev_type = HCI_PRIMARY; - data->hdev = hdev; SET_HCIDEV_DEV(hdev, &intf->dev); @@ -4481,6 +4524,7 @@ static int btusb_probe(struct usb_interface *intf, set_bit(HCI_QUIRK_BROKEN_READ_TRANSMIT_POWER, &hdev->quirks); set_bit(HCI_QUIRK_BROKEN_SET_RPA_TIMEOUT, &hdev->quirks); set_bit(HCI_QUIRK_BROKEN_EXT_SCAN, &hdev->quirks); + set_bit(HCI_QUIRK_BROKEN_READ_ENC_KEY_SIZE, &hdev->quirks); } if (!reset) |