Re: [PATCH 2/3] Bluetooth: btrtl: add support for the RTL8723CS

2020-07-12 Thread Vasily Khoruzhick
On Tue, Jul 7, 2020 at 9:01 AM Marcel Holtmann  wrote:
>
> Hi Vasily,
>
> > The Realtek RTL8723CS is SDIO WiFi chip. It also contains a Bluetooth
> > module which is connected via UART to the host.
> >
> > It shares lmp subversion with 8703B, so Realtek's userspace
> > initialization tool (rtk_hciattach) differentiates varieties of RTL8723CS
> > (CG, VF, XX) with RTL8703B using vendor's command to read chip type.
> >
> > Also this chip declares support for some features it doesn't support
> > so add a quirk to indicate that these features are broken.
> >
> > Signed-off-by: Vasily Khoruzhick 
> > ---
> > drivers/bluetooth/btrtl.c  | 128 -
> > drivers/bluetooth/btrtl.h  |  12 
> > drivers/bluetooth/hci_h5.c |   6 ++
> > 3 files changed, 143 insertions(+), 3 deletions(-)
> >
> > diff --git a/drivers/bluetooth/btrtl.c b/drivers/bluetooth/btrtl.c
> > index 3a9afc905f24..8c7b35abe492 100644
> > --- a/drivers/bluetooth/btrtl.c
> > +++ b/drivers/bluetooth/btrtl.c
> > @@ -17,8 +17,12 @@
> >
> > #define VERSION "0.1"
> >
> > +#define RTL_CHIP_8723CS_CG   3
> > +#define RTL_CHIP_8723CS_VF   4
> > +#define RTL_CHIP_8723CS_XX   5
> > #define RTL_EPATCH_SIGNATURE  "Realtech"
> > #define RTL_ROM_LMP_3499  0x3499
> > +#define RTL_ROM_LMP_8703B0x8703
> > #define RTL_ROM_LMP_8723A 0x1200
> > #define RTL_ROM_LMP_8723B 0x8723
> > #define RTL_ROM_LMP_8723D 0x8873
> > @@ -31,6 +35,7 @@
> > #define IC_MATCH_FL_HCIREV(1 << 1)
> > #define IC_MATCH_FL_HCIVER(1 << 2)
> > #define IC_MATCH_FL_HCIBUS(1 << 3)
> > +#define IC_MATCH_FL_CHIP_TYPE(1 << 4)
> > #define IC_INFO(lmps, hcir) \
> >   .match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_HCIREV, \
> >   .lmp_subver = (lmps), \
> > @@ -42,6 +47,7 @@ struct id_table {
> >   __u16 hci_rev;
> >   __u8 hci_ver;
> >   __u8 hci_bus;
> > + __u8 chip_type;
> >   bool config_needed;
> >   bool has_rom_version;
> >   char *fw_name;
> > @@ -89,6 +95,39 @@ static const struct id_table ic_id_table[] = {
> > .fw_name  = "rtl_bt/rtl8723b_fw.bin",
> > .cfg_name = "rtl_bt/rtl8723b_config" },
> >
> > + /* 8723CS-CG */
> > + { .match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_CHIP_TYPE |
> > +  IC_MATCH_FL_HCIBUS,
> > +   .lmp_subver = RTL_ROM_LMP_8703B,
> > +   .chip_type = RTL_CHIP_8723CS_CG,
> > +   .hci_bus = HCI_UART,
> > +   .config_needed = true,
> > +   .has_rom_version = true,
> > +   .fw_name  = "rtl_bt/rtl8723cs_cg_fw.bin",
> > +   .cfg_name = "rtl_bt/rtl8723cs_cg_config" },
> > +
> > + /* 8723CS-VF */
> > + { .match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_CHIP_TYPE |
> > +  IC_MATCH_FL_HCIBUS,
> > +   .lmp_subver = RTL_ROM_LMP_8703B,
> > +   .chip_type = RTL_CHIP_8723CS_VF,
> > +   .hci_bus = HCI_UART,
> > +   .config_needed = true,
> > +   .has_rom_version = true,
> > +   .fw_name  = "rtl_bt/rtl8723cs_vf_fw.bin",
> > +   .cfg_name = "rtl_bt/rtl8723cs_vf_config" },
> > +
> > + /* 8723CS-XX */
> > + { .match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_CHIP_TYPE |
> > +  IC_MATCH_FL_HCIBUS,
> > +   .lmp_subver = RTL_ROM_LMP_8703B,
> > +   .chip_type = RTL_CHIP_8723CS_XX,
> > +   .hci_bus = HCI_UART,
> > +   .config_needed = true,
> > +   .has_rom_version = true,
> > +   .fw_name  = "rtl_bt/rtl8723cs_xx_fw.bin",
> > +   .cfg_name = "rtl_bt/rtl8723cs_xx_config" },
> > +
> >   /* 8723D */
> >   { IC_INFO(RTL_ROM_LMP_8723B, 0xd),
> > .config_needed = true,
> > @@ -171,7 +210,8 @@ static const struct id_table ic_id_table[] = {
> >   };
> >
> > static const struct id_table *btrtl_match_ic(u16 lmp_subver, u16 hci_rev,
> > -  u8 hci_ver, u8 hci_bus)
> > +  u8 hci_ver, u8 hci_bus,
> > +  u8 chip_type)
> > {
> >   int i;
> >
> > @@ -188,6 +228,9 @@ static const struct id_table *btrtl_match_ic(u16 
> > lmp_subver, u16 hci_rev,
> >   if ((ic_id_table[i].match_flags & IC_MATCH_FL_HCIBUS) &&
> >   (ic_id_table[i].hci_bus != hci_bus))
> >   continue;
> > + if ((ic_id_table[i].match_flags & IC_MATCH_FL_CHIP_TYPE) &&
> > + (ic_id_table[i].chip_type != chip_type))
> > + continue;
> >
> >   break;
> >   }
> > @@ -270,6 +313,7 @@ static int rtlbt_parse_firmware(struct hci_dev *hdev,
> >   { RTL_ROM_LMP_8723B, 1 },
> >   { RTL_ROM_LMP_8821A, 2 },
> >   { RTL_ROM_LMP_8761A, 3 },
> > + { RTL_ROM_LMP_8703B, 7 },
> >   { RTL_ROM_LMP_8822B, 8 },
> >   { RTL_ROM_LMP_8723B, 9 },   /* 8723D */
> >   { RTL_ROM_LMP_8821A, 10 },  /* 8821C */
> > @@ -545,6 +589,48 @@ static int 

Re: [PATCH 2/3] Bluetooth: btrtl: add support for the RTL8723CS

2020-07-07 Thread Marcel Holtmann
Hi Vasily,

> The Realtek RTL8723CS is SDIO WiFi chip. It also contains a Bluetooth
> module which is connected via UART to the host.
> 
> It shares lmp subversion with 8703B, so Realtek's userspace
> initialization tool (rtk_hciattach) differentiates varieties of RTL8723CS
> (CG, VF, XX) with RTL8703B using vendor's command to read chip type.
> 
> Also this chip declares support for some features it doesn't support
> so add a quirk to indicate that these features are broken.
> 
> Signed-off-by: Vasily Khoruzhick 
> ---
> drivers/bluetooth/btrtl.c  | 128 -
> drivers/bluetooth/btrtl.h  |  12 
> drivers/bluetooth/hci_h5.c |   6 ++
> 3 files changed, 143 insertions(+), 3 deletions(-)
> 
> diff --git a/drivers/bluetooth/btrtl.c b/drivers/bluetooth/btrtl.c
> index 3a9afc905f24..8c7b35abe492 100644
> --- a/drivers/bluetooth/btrtl.c
> +++ b/drivers/bluetooth/btrtl.c
> @@ -17,8 +17,12 @@
> 
> #define VERSION "0.1"
> 
> +#define RTL_CHIP_8723CS_CG   3
> +#define RTL_CHIP_8723CS_VF   4
> +#define RTL_CHIP_8723CS_XX   5
> #define RTL_EPATCH_SIGNATURE  "Realtech"
> #define RTL_ROM_LMP_3499  0x3499
> +#define RTL_ROM_LMP_8703B0x8703
> #define RTL_ROM_LMP_8723A 0x1200
> #define RTL_ROM_LMP_8723B 0x8723
> #define RTL_ROM_LMP_8723D 0x8873
> @@ -31,6 +35,7 @@
> #define IC_MATCH_FL_HCIREV(1 << 1)
> #define IC_MATCH_FL_HCIVER(1 << 2)
> #define IC_MATCH_FL_HCIBUS(1 << 3)
> +#define IC_MATCH_FL_CHIP_TYPE(1 << 4)
> #define IC_INFO(lmps, hcir) \
>   .match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_HCIREV, \
>   .lmp_subver = (lmps), \
> @@ -42,6 +47,7 @@ struct id_table {
>   __u16 hci_rev;
>   __u8 hci_ver;
>   __u8 hci_bus;
> + __u8 chip_type;
>   bool config_needed;
>   bool has_rom_version;
>   char *fw_name;
> @@ -89,6 +95,39 @@ static const struct id_table ic_id_table[] = {
> .fw_name  = "rtl_bt/rtl8723b_fw.bin",
> .cfg_name = "rtl_bt/rtl8723b_config" },
> 
> + /* 8723CS-CG */
> + { .match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_CHIP_TYPE |
> +  IC_MATCH_FL_HCIBUS,
> +   .lmp_subver = RTL_ROM_LMP_8703B,
> +   .chip_type = RTL_CHIP_8723CS_CG,
> +   .hci_bus = HCI_UART,
> +   .config_needed = true,
> +   .has_rom_version = true,
> +   .fw_name  = "rtl_bt/rtl8723cs_cg_fw.bin",
> +   .cfg_name = "rtl_bt/rtl8723cs_cg_config" },
> +
> + /* 8723CS-VF */
> + { .match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_CHIP_TYPE |
> +  IC_MATCH_FL_HCIBUS,
> +   .lmp_subver = RTL_ROM_LMP_8703B,
> +   .chip_type = RTL_CHIP_8723CS_VF,
> +   .hci_bus = HCI_UART,
> +   .config_needed = true,
> +   .has_rom_version = true,
> +   .fw_name  = "rtl_bt/rtl8723cs_vf_fw.bin",
> +   .cfg_name = "rtl_bt/rtl8723cs_vf_config" },
> +
> + /* 8723CS-XX */
> + { .match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_CHIP_TYPE |
> +  IC_MATCH_FL_HCIBUS,
> +   .lmp_subver = RTL_ROM_LMP_8703B,
> +   .chip_type = RTL_CHIP_8723CS_XX,
> +   .hci_bus = HCI_UART,
> +   .config_needed = true,
> +   .has_rom_version = true,
> +   .fw_name  = "rtl_bt/rtl8723cs_xx_fw.bin",
> +   .cfg_name = "rtl_bt/rtl8723cs_xx_config" },
> +
>   /* 8723D */
>   { IC_INFO(RTL_ROM_LMP_8723B, 0xd),
> .config_needed = true,
> @@ -171,7 +210,8 @@ static const struct id_table ic_id_table[] = {
>   };
> 
> static const struct id_table *btrtl_match_ic(u16 lmp_subver, u16 hci_rev,
> -  u8 hci_ver, u8 hci_bus)
> +  u8 hci_ver, u8 hci_bus,
> +  u8 chip_type)
> {
>   int i;
> 
> @@ -188,6 +228,9 @@ static const struct id_table *btrtl_match_ic(u16 
> lmp_subver, u16 hci_rev,
>   if ((ic_id_table[i].match_flags & IC_MATCH_FL_HCIBUS) &&
>   (ic_id_table[i].hci_bus != hci_bus))
>   continue;
> + if ((ic_id_table[i].match_flags & IC_MATCH_FL_CHIP_TYPE) &&
> + (ic_id_table[i].chip_type != chip_type))
> + continue;
> 
>   break;
>   }
> @@ -270,6 +313,7 @@ static int rtlbt_parse_firmware(struct hci_dev *hdev,
>   { RTL_ROM_LMP_8723B, 1 },
>   { RTL_ROM_LMP_8821A, 2 },
>   { RTL_ROM_LMP_8761A, 3 },
> + { RTL_ROM_LMP_8703B, 7 },
>   { RTL_ROM_LMP_8822B, 8 },
>   { RTL_ROM_LMP_8723B, 9 },   /* 8723D */
>   { RTL_ROM_LMP_8821A, 10 },  /* 8821C */
> @@ -545,6 +589,48 @@ static int btrtl_setup_rtl8723b(struct hci_dev *hdev,
>   return ret;
> }
> 
> +static bool rtl_has_chip_type(u16 lmp_subver)
> +{
> + switch (lmp_subver) {
> + case RTL_ROM_LMP_8703B:
> + return true;
> + default:
> + break;
> + }
> +
> + return  false;
> +}
> +
> 

[PATCH 2/3] Bluetooth: btrtl: add support for the RTL8723CS

2020-07-05 Thread Vasily Khoruzhick
The Realtek RTL8723CS is SDIO WiFi chip. It also contains a Bluetooth
module which is connected via UART to the host.

It shares lmp subversion with 8703B, so Realtek's userspace
initialization tool (rtk_hciattach) differentiates varieties of RTL8723CS
(CG, VF, XX) with RTL8703B using vendor's command to read chip type.

Also this chip declares support for some features it doesn't support
so add a quirk to indicate that these features are broken.

Signed-off-by: Vasily Khoruzhick 
---
 drivers/bluetooth/btrtl.c  | 128 -
 drivers/bluetooth/btrtl.h  |  12 
 drivers/bluetooth/hci_h5.c |   6 ++
 3 files changed, 143 insertions(+), 3 deletions(-)

diff --git a/drivers/bluetooth/btrtl.c b/drivers/bluetooth/btrtl.c
index 3a9afc905f24..8c7b35abe492 100644
--- a/drivers/bluetooth/btrtl.c
+++ b/drivers/bluetooth/btrtl.c
@@ -17,8 +17,12 @@
 
 #define VERSION "0.1"
 
+#define RTL_CHIP_8723CS_CG 3
+#define RTL_CHIP_8723CS_VF 4
+#define RTL_CHIP_8723CS_XX 5
 #define RTL_EPATCH_SIGNATURE   "Realtech"
 #define RTL_ROM_LMP_3499   0x3499
+#define RTL_ROM_LMP_8703B  0x8703
 #define RTL_ROM_LMP_8723A  0x1200
 #define RTL_ROM_LMP_8723B  0x8723
 #define RTL_ROM_LMP_8723D  0x8873
@@ -31,6 +35,7 @@
 #define IC_MATCH_FL_HCIREV (1 << 1)
 #define IC_MATCH_FL_HCIVER (1 << 2)
 #define IC_MATCH_FL_HCIBUS (1 << 3)
+#define IC_MATCH_FL_CHIP_TYPE  (1 << 4)
 #define IC_INFO(lmps, hcir) \
.match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_HCIREV, \
.lmp_subver = (lmps), \
@@ -42,6 +47,7 @@ struct id_table {
__u16 hci_rev;
__u8 hci_ver;
__u8 hci_bus;
+   __u8 chip_type;
bool config_needed;
bool has_rom_version;
char *fw_name;
@@ -89,6 +95,39 @@ static const struct id_table ic_id_table[] = {
  .fw_name  = "rtl_bt/rtl8723b_fw.bin",
  .cfg_name = "rtl_bt/rtl8723b_config" },
 
+   /* 8723CS-CG */
+   { .match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_CHIP_TYPE |
+IC_MATCH_FL_HCIBUS,
+ .lmp_subver = RTL_ROM_LMP_8703B,
+ .chip_type = RTL_CHIP_8723CS_CG,
+ .hci_bus = HCI_UART,
+ .config_needed = true,
+ .has_rom_version = true,
+ .fw_name  = "rtl_bt/rtl8723cs_cg_fw.bin",
+ .cfg_name = "rtl_bt/rtl8723cs_cg_config" },
+
+   /* 8723CS-VF */
+   { .match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_CHIP_TYPE |
+IC_MATCH_FL_HCIBUS,
+ .lmp_subver = RTL_ROM_LMP_8703B,
+ .chip_type = RTL_CHIP_8723CS_VF,
+ .hci_bus = HCI_UART,
+ .config_needed = true,
+ .has_rom_version = true,
+ .fw_name  = "rtl_bt/rtl8723cs_vf_fw.bin",
+ .cfg_name = "rtl_bt/rtl8723cs_vf_config" },
+
+   /* 8723CS-XX */
+   { .match_flags = IC_MATCH_FL_LMPSUBV | IC_MATCH_FL_CHIP_TYPE |
+IC_MATCH_FL_HCIBUS,
+ .lmp_subver = RTL_ROM_LMP_8703B,
+ .chip_type = RTL_CHIP_8723CS_XX,
+ .hci_bus = HCI_UART,
+ .config_needed = true,
+ .has_rom_version = true,
+ .fw_name  = "rtl_bt/rtl8723cs_xx_fw.bin",
+ .cfg_name = "rtl_bt/rtl8723cs_xx_config" },
+
/* 8723D */
{ IC_INFO(RTL_ROM_LMP_8723B, 0xd),
  .config_needed = true,
@@ -171,7 +210,8 @@ static const struct id_table ic_id_table[] = {
};
 
 static const struct id_table *btrtl_match_ic(u16 lmp_subver, u16 hci_rev,
-u8 hci_ver, u8 hci_bus)
+u8 hci_ver, u8 hci_bus,
+u8 chip_type)
 {
int i;
 
@@ -188,6 +228,9 @@ static const struct id_table *btrtl_match_ic(u16 
lmp_subver, u16 hci_rev,
if ((ic_id_table[i].match_flags & IC_MATCH_FL_HCIBUS) &&
(ic_id_table[i].hci_bus != hci_bus))
continue;
+   if ((ic_id_table[i].match_flags & IC_MATCH_FL_CHIP_TYPE) &&
+   (ic_id_table[i].chip_type != chip_type))
+   continue;
 
break;
}
@@ -270,6 +313,7 @@ static int rtlbt_parse_firmware(struct hci_dev *hdev,
{ RTL_ROM_LMP_8723B, 1 },
{ RTL_ROM_LMP_8821A, 2 },
{ RTL_ROM_LMP_8761A, 3 },
+   { RTL_ROM_LMP_8703B, 7 },
{ RTL_ROM_LMP_8822B, 8 },
{ RTL_ROM_LMP_8723B, 9 },   /* 8723D */
{ RTL_ROM_LMP_8821A, 10 },  /* 8821C */
@@ -545,6 +589,48 @@ static int btrtl_setup_rtl8723b(struct hci_dev *hdev,
return ret;
 }
 
+static bool rtl_has_chip_type(u16 lmp_subver)
+{
+   switch (lmp_subver) {
+   case RTL_ROM_LMP_8703B:
+   return true;
+   default:
+   break;
+   }
+
+   return  false;
+}
+
+static int rtl_read_chip_type(struct hci_dev *hdev, u8 *type)
+{
+   struct rtl_chip_type_evt