netdev.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v3 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property
       [not found] <1554368908-22017-1-git-send-email-rjliao@codeaurora.org>
@ 2019-04-10  9:27 ` Rocky Liao
  2019-05-12  3:19   ` [PATCH v4 " Rocky Liao
  0 siblings, 1 reply; 10+ messages in thread
From: Rocky Liao @ 2019-04-10  9:27 UTC (permalink / raw)
  To: robh+dt, mark.rutland, marcel, johan.hedberg, thierry.escande
  Cc: netdev, devicetree, linux-kernel, linux-bluetooth, linux-arm-msm,
	bgodavar, Rocky Liao

QCA BTSOC NVM is a customized firmware file and different vendors may
want to have different BTSOC configuration (e.g. Configure SCO over PCM
or I2S, Setting Tx power, etc.) via this file. This patch will allow
vendors to download different NVM firmware file by reading a device
property "firmware-name".

Signed-off-by: Rocky Liao <rjliao@codeaurora.org>
---
Changes in v3:
  * added firmware-name instead of nvm-postfix to specify full firmware name
---
 drivers/bluetooth/btqca.c   | 14 ++++++++++----
 drivers/bluetooth/btqca.h   |  6 ++++--
 drivers/bluetooth/hci_qca.c | 19 ++++++++++++++++++-
 3 files changed, 32 insertions(+), 7 deletions(-)

diff --git a/drivers/bluetooth/btqca.c b/drivers/bluetooth/btqca.c
index 6122685..645a893 100644
--- a/drivers/bluetooth/btqca.c
+++ b/drivers/bluetooth/btqca.c
@@ -332,7 +332,8 @@ int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr)
 EXPORT_SYMBOL_GPL(qca_set_bdaddr_rome);
 
 int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-		   enum qca_btsoc_type soc_type, u32 soc_ver)
+		   enum qca_btsoc_type soc_type, u32 soc_ver,
+		   const char *firmware_name)
 {
 	struct rome_config config;
 	int err;
@@ -368,9 +369,14 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
 	if (soc_type == QCA_WCN3990)
 		snprintf(config.fwname, sizeof(config.fwname),
 			 "qca/crnv%02x.bin", rom_ver);
-	else
-		snprintf(config.fwname, sizeof(config.fwname),
-			 "qca/nvm_%08x.bin", soc_ver);
+	else {
+		if (firmware_name)
+			snprintf(config.fwname, sizeof(config.fwname),
+				 "qca/%s", firmware_name);
+		else
+			snprintf(config.fwname, sizeof(config.fwname),
+				 "qca/nvm_%08x.bin", soc_ver);
+	}
 
 	err = qca_download_firmware(hdev, &config);
 	if (err < 0) {
diff --git a/drivers/bluetooth/btqca.h b/drivers/bluetooth/btqca.h
index 6fdc25d..41dc806 100644
--- a/drivers/bluetooth/btqca.h
+++ b/drivers/bluetooth/btqca.h
@@ -139,7 +139,8 @@ enum qca_btsoc_type {
 
 int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr);
 int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-		   enum qca_btsoc_type soc_type, u32 soc_ver);
+		   enum qca_btsoc_type soc_type, u32 soc_ver,
+		   const char *firmware_name);
 int qca_read_soc_version(struct hci_dev *hdev, u32 *soc_version);
 int qca_set_bdaddr(struct hci_dev *hdev, const bdaddr_t *bdaddr);
 #else
@@ -150,7 +151,8 @@ static inline int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdad
 }
 
 static inline int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-				 enum qca_btsoc_type soc_type, u32 soc_ver)
+				 enum qca_btsoc_type soc_type, u32 soc_ver,
+				 const char *firmware_name)
 {
 	return -EOPNOTSUPP;
 }
diff --git a/drivers/bluetooth/hci_qca.c b/drivers/bluetooth/hci_qca.c
index 4ea995d..9b8d4d7 100644
--- a/drivers/bluetooth/hci_qca.c
+++ b/drivers/bluetooth/hci_qca.c
@@ -168,6 +168,7 @@ struct qca_serdev {
 	struct qca_power *bt_power;
 	u32 init_speed;
 	u32 oper_speed;
+	const char *firmware_name;
 };
 
 static int qca_power_setup(struct hci_uart *hu, bool on);
@@ -189,6 +190,17 @@ static enum qca_btsoc_type qca_soc_type(struct hci_uart *hu)
 	return soc_type;
 }
 
+static const char *qca_get_firmware_name(struct hci_uart *hu)
+{
+	if (hu->serdev) {
+		struct qca_serdev *qsd = serdev_device_get_drvdata(hu->serdev);
+
+		return qsd->firmware_name;
+	} else {
+		return NULL;
+	}
+}
+
 static void __serial_clock_on(struct tty_struct *tty)
 {
 	/* TODO: Some chipset requires to enable UART clock on client
@@ -1191,6 +1203,7 @@ static int qca_setup(struct hci_uart *hu)
 	struct qca_data *qca = hu->priv;
 	unsigned int speed, qca_baudrate = QCA_BAUDRATE_115200;
 	enum qca_btsoc_type soc_type = qca_soc_type(hu);
+	const char *firmware_name = qca_get_firmware_name(hu);
 	int ret;
 	int soc_ver = 0;
 
@@ -1241,7 +1254,8 @@ static int qca_setup(struct hci_uart *hu)
 
 	bt_dev_info(hdev, "QCA controller version 0x%08x", soc_ver);
 	/* Setup patch / NVM configurations */
-	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver);
+	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver,
+			firmware_name);
 	if (!ret) {
 		set_bit(STATE_IN_BAND_SLEEP_ENABLED, &qca->flags);
 		qca_debugfs_init(hdev);
@@ -1462,6 +1476,9 @@ static int qca_serdev_probe(struct serdev_device *serdev)
 			return PTR_ERR(qcadev->bt_en);
 		}
 
+		device_property_read_string(&serdev->dev, "firmware-name",
+					 &qcadev->firmware_name);
+
 		qcadev->susclk = devm_clk_get(&serdev->dev, NULL);
 		if (IS_ERR(qcadev->susclk)) {
 			dev_err(&serdev->dev, "failed to acquire clk\n");
-- 
The Qualcomm Innovation Center, Inc. is a member of the Code Aurora Forum, a Linux Foundation Collaborative Project


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [PATCH v4 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property
  2019-04-10  9:27 ` [PATCH v3 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property Rocky Liao
@ 2019-05-12  3:19   ` Rocky Liao
  2019-05-15  5:32     ` Balakrishna Godavarthi
  2019-05-15 11:19     ` [PATCH v5 " Rocky Liao
  0 siblings, 2 replies; 10+ messages in thread
From: Rocky Liao @ 2019-05-12  3:19 UTC (permalink / raw)
  To: robh+dt, mark.rutland, marcel, johan.hedberg, thierry.escande
  Cc: netdev, devicetree, linux-kernel, linux-bluetooth, linux-arm-msm,
	bgodavar, Rocky Liao

QCA BTSOC NVM is a customized firmware file and different vendors may
want to have different BTSOC configuration (e.g. Configure SCO over PCM
or I2S, Setting Tx power, etc.) via this file. This patch will allow
vendors to download different NVM firmware file by reading a device
property "firmware-name".

Signed-off-by: Rocky Liao <rjliao@codeaurora.org>
---
Changes in v4:
  * rebased the code base and merge with latest code
---
 drivers/bluetooth/btqca.c   | 14 ++++++++++----
 drivers/bluetooth/btqca.h   |  6 ++++--
 drivers/bluetooth/hci_qca.c | 19 ++++++++++++++++++-
 3 files changed, 32 insertions(+), 7 deletions(-)

diff --git a/drivers/bluetooth/btqca.c b/drivers/bluetooth/btqca.c
index cc12eec..0ea690a 100644
--- a/drivers/bluetooth/btqca.c
+++ b/drivers/bluetooth/btqca.c
@@ -332,7 +332,8 @@ int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr)
 EXPORT_SYMBOL_GPL(qca_set_bdaddr_rome);
 
 int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-		   enum qca_btsoc_type soc_type, u32 soc_ver)
+		   enum qca_btsoc_type soc_type, u32 soc_ver,
+		   const char *firmware_name)
 {
 	struct rome_config config;
 	int err;
@@ -368,9 +369,14 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
 	if (qca_is_wcn399x(soc_type))
 		snprintf(config.fwname, sizeof(config.fwname),
 			 "qca/crnv%02x.bin", rom_ver);
-	else
-		snprintf(config.fwname, sizeof(config.fwname),
-			 "qca/nvm_%08x.bin", soc_ver);
+	else {
+		if (firmware_name)
+			snprintf(config.fwname, sizeof(config.fwname),
+				 "qca/%s", firmware_name);
+		else
+			snprintf(config.fwname, sizeof(config.fwname),
+				 "qca/nvm_%08x.bin", soc_ver);
+	}
 
 	err = qca_download_firmware(hdev, &config);
 	if (err < 0) {
diff --git a/drivers/bluetooth/btqca.h b/drivers/bluetooth/btqca.h
index 4c4fe2b..8c037bb 100644
--- a/drivers/bluetooth/btqca.h
+++ b/drivers/bluetooth/btqca.h
@@ -140,7 +140,8 @@ enum qca_btsoc_type {
 
 int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr);
 int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-		   enum qca_btsoc_type soc_type, u32 soc_ver);
+		   enum qca_btsoc_type soc_type, u32 soc_ver,
+		   const char *firmware_name);
 int qca_read_soc_version(struct hci_dev *hdev, u32 *soc_version);
 int qca_set_bdaddr(struct hci_dev *hdev, const bdaddr_t *bdaddr);
 static inline bool qca_is_wcn399x(enum qca_btsoc_type soc_type)
@@ -155,7 +156,8 @@ static inline int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdad
 }
 
 static inline int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-				 enum qca_btsoc_type soc_type, u32 soc_ver)
+				 enum qca_btsoc_type soc_type, u32 soc_ver,
+				 const char *firmware_name)
 {
 	return -EOPNOTSUPP;
 }
diff --git a/drivers/bluetooth/hci_qca.c b/drivers/bluetooth/hci_qca.c
index 57322c4..9590602 100644
--- a/drivers/bluetooth/hci_qca.c
+++ b/drivers/bluetooth/hci_qca.c
@@ -169,6 +169,7 @@ struct qca_serdev {
 	struct qca_power *bt_power;
 	u32 init_speed;
 	u32 oper_speed;
+	const char *firmware_name;
 };
 
 static int qca_power_setup(struct hci_uart *hu, bool on);
@@ -190,6 +191,17 @@ static enum qca_btsoc_type qca_soc_type(struct hci_uart *hu)
 	return soc_type;
 }
 
+static const char *qca_get_firmware_name(struct hci_uart *hu)
+{
+	if (hu->serdev) {
+		struct qca_serdev *qsd = serdev_device_get_drvdata(hu->serdev);
+
+		return qsd->firmware_name;
+	} else {
+		return NULL;
+	}
+}
+
 static void __serial_clock_on(struct tty_struct *tty)
 {
 	/* TODO: Some chipset requires to enable UART clock on client
@@ -1195,6 +1207,7 @@ static int qca_setup(struct hci_uart *hu)
 	struct qca_data *qca = hu->priv;
 	unsigned int speed, qca_baudrate = QCA_BAUDRATE_115200;
 	enum qca_btsoc_type soc_type = qca_soc_type(hu);
+	const char *firmware_name = qca_get_firmware_name(hu);
 	int ret;
 	int soc_ver = 0;
 
@@ -1245,7 +1258,8 @@ static int qca_setup(struct hci_uart *hu)
 
 	bt_dev_info(hdev, "QCA controller version 0x%08x", soc_ver);
 	/* Setup patch / NVM configurations */
-	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver);
+	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver,
+			firmware_name);
 	if (!ret) {
 		set_bit(QCA_IBS_ENABLED, &qca->flags);
 		qca_debugfs_init(hdev);
@@ -1477,6 +1491,9 @@ static int qca_serdev_probe(struct serdev_device *serdev)
 			return PTR_ERR(qcadev->bt_en);
 		}
 
+		device_property_read_string(&serdev->dev, "firmware-name",
+					 &qcadev->firmware_name);
+
 		qcadev->susclk = devm_clk_get(&serdev->dev, NULL);
 		if (IS_ERR(qcadev->susclk)) {
 			dev_err(&serdev->dev, "failed to acquire clk\n");
-- 
The Qualcomm Innovation Center, Inc. is a member of the Code Aurora Forum, a Linux Foundation Collaborative Project


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* Re: [PATCH v4 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property
  2019-05-12  3:19   ` [PATCH v4 " Rocky Liao
@ 2019-05-15  5:32     ` Balakrishna Godavarthi
  2019-05-15  8:30       ` Rocky Liao
  2019-05-15 11:19     ` [PATCH v5 " Rocky Liao
  1 sibling, 1 reply; 10+ messages in thread
From: Balakrishna Godavarthi @ 2019-05-15  5:32 UTC (permalink / raw)
  To: Rocky Liao
  Cc: robh+dt, mark.rutland, marcel, johan.hedberg, thierry.escande,
	netdev, devicetree, linux-kernel, linux-bluetooth, linux-arm-msm,
	hemtang

Hi Rocky,

On 2019-05-12 08:49, Rocky Liao wrote:
> QCA BTSOC NVM is a customized firmware file and different vendors may
> want to have different BTSOC configuration (e.g. Configure SCO over PCM
> or I2S, Setting Tx power, etc.) via this file. This patch will allow
> vendors to download different NVM firmware file by reading a device
> property "firmware-name".
> 
> Signed-off-by: Rocky Liao <rjliao@codeaurora.org>
> ---
> Changes in v4:
>   * rebased the code base and merge with latest code
> ---
>  drivers/bluetooth/btqca.c   | 14 ++++++++++----
>  drivers/bluetooth/btqca.h   |  6 ++++--
>  drivers/bluetooth/hci_qca.c | 19 ++++++++++++++++++-
>  3 files changed, 32 insertions(+), 7 deletions(-)
> 
> diff --git a/drivers/bluetooth/btqca.c b/drivers/bluetooth/btqca.c
> index cc12eec..0ea690a 100644
> --- a/drivers/bluetooth/btqca.c
> +++ b/drivers/bluetooth/btqca.c
> @@ -332,7 +332,8 @@ int qca_set_bdaddr_rome(struct hci_dev *hdev,
> const bdaddr_t *bdaddr)
>  EXPORT_SYMBOL_GPL(qca_set_bdaddr_rome);
> 
>  int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
> -		   enum qca_btsoc_type soc_type, u32 soc_ver)
> +		   enum qca_btsoc_type soc_type, u32 soc_ver,
> +		   const char *firmware_name)
>  {
>  	struct rome_config config;
>  	int err;
> @@ -368,9 +369,14 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t 
> baudrate,
>  	if (qca_is_wcn399x(soc_type))
>  		snprintf(config.fwname, sizeof(config.fwname),
>  			 "qca/crnv%02x.bin", rom_ver);
> -	else
> -		snprintf(config.fwname, sizeof(config.fwname),
> -			 "qca/nvm_%08x.bin", soc_ver);
> +	else {
> +		if (firmware_name)
> +			snprintf(config.fwname, sizeof(config.fwname),
> +				 "qca/%s", firmware_name);
> +		else
> +			snprintf(config.fwname, sizeof(config.fwname),
> +				 "qca/nvm_%08x.bin", soc_ver);
> +	}
> 
[Bala]: Can you make this change  applicable to the wcn399x series chip 
sets too.

        something like this

        if (qca_is_wcn399x(soc_type) && !firmware_name)
          snprintf(config.fwname, sizeof(config.fwname),
               "qca/crnv%02x.bin", rom_ver);
       elseif (firmware_name)
          snprintf(config.fwname, sizeof(config.fwname),
             "qca/%s", firmware_name);
       else
         snprintf(config.fwname, sizeof(config.fwname),
               "qca/nvm_%08x.bin", soc_ver);


>  	err = qca_download_firmware(hdev, &config);
>  	if (err < 0) {
> diff --git a/drivers/bluetooth/btqca.h b/drivers/bluetooth/btqca.h
> index 4c4fe2b..8c037bb 100644
> --- a/drivers/bluetooth/btqca.h
> +++ b/drivers/bluetooth/btqca.h
> @@ -140,7 +140,8 @@ enum qca_btsoc_type {
> 
>  int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr);
>  int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
> -		   enum qca_btsoc_type soc_type, u32 soc_ver);
> +		   enum qca_btsoc_type soc_type, u32 soc_ver,
> +		   const char *firmware_name);
>  int qca_read_soc_version(struct hci_dev *hdev, u32 *soc_version);
>  int qca_set_bdaddr(struct hci_dev *hdev, const bdaddr_t *bdaddr);
>  static inline bool qca_is_wcn399x(enum qca_btsoc_type soc_type)
> @@ -155,7 +156,8 @@ static inline int qca_set_bdaddr_rome(struct
> hci_dev *hdev, const bdaddr_t *bdad
>  }
> 
>  static inline int qca_uart_setup(struct hci_dev *hdev, uint8_t 
> baudrate,
> -				 enum qca_btsoc_type soc_type, u32 soc_ver)
> +				 enum qca_btsoc_type soc_type, u32 soc_ver,
> +				 const char *firmware_name)
>  {
>  	return -EOPNOTSUPP;
>  }
> diff --git a/drivers/bluetooth/hci_qca.c b/drivers/bluetooth/hci_qca.c
> index 57322c4..9590602 100644
> --- a/drivers/bluetooth/hci_qca.c
> +++ b/drivers/bluetooth/hci_qca.c
> @@ -169,6 +169,7 @@ struct qca_serdev {
>  	struct qca_power *bt_power;
>  	u32 init_speed;
>  	u32 oper_speed;
> +	const char *firmware_name;
>  };
> 
>  static int qca_power_setup(struct hci_uart *hu, bool on);
> @@ -190,6 +191,17 @@ static enum qca_btsoc_type qca_soc_type(struct
> hci_uart *hu)
>  	return soc_type;
>  }
> 
> +static const char *qca_get_firmware_name(struct hci_uart *hu)
> +{
> +	if (hu->serdev) {
> +		struct qca_serdev *qsd = serdev_device_get_drvdata(hu->serdev);
> +
> +		return qsd->firmware_name;
> +	} else {
> +		return NULL;
> +	}
> +}
> +
>  static void __serial_clock_on(struct tty_struct *tty)
>  {
>  	/* TODO: Some chipset requires to enable UART clock on client
> @@ -1195,6 +1207,7 @@ static int qca_setup(struct hci_uart *hu)
>  	struct qca_data *qca = hu->priv;
>  	unsigned int speed, qca_baudrate = QCA_BAUDRATE_115200;
>  	enum qca_btsoc_type soc_type = qca_soc_type(hu);
> +	const char *firmware_name = qca_get_firmware_name(hu);
>  	int ret;
>  	int soc_ver = 0;
> 
> @@ -1245,7 +1258,8 @@ static int qca_setup(struct hci_uart *hu)
> 
>  	bt_dev_info(hdev, "QCA controller version 0x%08x", soc_ver);
>  	/* Setup patch / NVM configurations */
> -	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver);
> +	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver,
> +			firmware_name);
>  	if (!ret) {
>  		set_bit(QCA_IBS_ENABLED, &qca->flags);
>  		qca_debugfs_init(hdev);
> @@ -1477,6 +1491,9 @@ static int qca_serdev_probe(struct serdev_device 
> *serdev)
>  			return PTR_ERR(qcadev->bt_en);
>  		}
> 
> +		device_property_read_string(&serdev->dev, "firmware-name",
> +					 &qcadev->firmware_name);
> +
>  		qcadev->susclk = devm_clk_get(&serdev->dev, NULL);
>  		if (IS_ERR(qcadev->susclk)) {
>  			dev_err(&serdev->dev, "failed to acquire clk\n");

-- 
Regards
Balakrishna.

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH v4 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property
  2019-05-15  5:32     ` Balakrishna Godavarthi
@ 2019-05-15  8:30       ` Rocky Liao
  0 siblings, 0 replies; 10+ messages in thread
From: Rocky Liao @ 2019-05-15  8:30 UTC (permalink / raw)
  To: Balakrishna Godavarthi
  Cc: robh+dt, mark.rutland, marcel, johan.hedberg, thierry.escande,
	netdev, devicetree, linux-kernel, linux-bluetooth, linux-arm-msm,
	hemtang, linux-bluetooth-owner

Hi Bala,

On 2019-05-15 13:32, Balakrishna Godavarthi wrote:
> Hi Rocky,
> 
> On 2019-05-12 08:49, Rocky Liao wrote:
>> QCA BTSOC NVM is a customized firmware file and different vendors may
>> want to have different BTSOC configuration (e.g. Configure SCO over 
>> PCM
>> or I2S, Setting Tx power, etc.) via this file. This patch will allow
>> vendors to download different NVM firmware file by reading a device
>> property "firmware-name".
>> 
>> Signed-off-by: Rocky Liao <rjliao@codeaurora.org>
>> ---
>> Changes in v4:
>>   * rebased the code base and merge with latest code
>> ---
>>  drivers/bluetooth/btqca.c   | 14 ++++++++++----
>>  drivers/bluetooth/btqca.h   |  6 ++++--
>>  drivers/bluetooth/hci_qca.c | 19 ++++++++++++++++++-
>>  3 files changed, 32 insertions(+), 7 deletions(-)
>> 
>> diff --git a/drivers/bluetooth/btqca.c b/drivers/bluetooth/btqca.c
>> index cc12eec..0ea690a 100644
>> --- a/drivers/bluetooth/btqca.c
>> +++ b/drivers/bluetooth/btqca.c
>> @@ -332,7 +332,8 @@ int qca_set_bdaddr_rome(struct hci_dev *hdev,
>> const bdaddr_t *bdaddr)
>>  EXPORT_SYMBOL_GPL(qca_set_bdaddr_rome);
>> 
>>  int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
>> -		   enum qca_btsoc_type soc_type, u32 soc_ver)
>> +		   enum qca_btsoc_type soc_type, u32 soc_ver,
>> +		   const char *firmware_name)
>>  {
>>  	struct rome_config config;
>>  	int err;
>> @@ -368,9 +369,14 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t 
>> baudrate,
>>  	if (qca_is_wcn399x(soc_type))
>>  		snprintf(config.fwname, sizeof(config.fwname),
>>  			 "qca/crnv%02x.bin", rom_ver);
>> -	else
>> -		snprintf(config.fwname, sizeof(config.fwname),
>> -			 "qca/nvm_%08x.bin", soc_ver);
>> +	else {
>> +		if (firmware_name)
>> +			snprintf(config.fwname, sizeof(config.fwname),
>> +				 "qca/%s", firmware_name);
>> +		else
>> +			snprintf(config.fwname, sizeof(config.fwname),
>> +				 "qca/nvm_%08x.bin", soc_ver);
>> +	}
>> 
> [Bala]: Can you make this change  applicable to the wcn399x series
> chip sets too.
> 
>        something like this
> 
>        if (qca_is_wcn399x(soc_type) && !firmware_name)
>          snprintf(config.fwname, sizeof(config.fwname),
>               "qca/crnv%02x.bin", rom_ver);
>       elseif (firmware_name)
>          snprintf(config.fwname, sizeof(config.fwname),
>             "qca/%s", firmware_name);
>       else
>         snprintf(config.fwname, sizeof(config.fwname),
>               "qca/nvm_%08x.bin", soc_ver);
> 
> 
>>  	err = qca_download_firmware(hdev, &config);
>>  	if (err < 0) {
>> diff --git a/drivers/bluetooth/btqca.h b/drivers/bluetooth/btqca.h
>> index 4c4fe2b..8c037bb 100644
>> --- a/drivers/bluetooth/btqca.h
>> +++ b/drivers/bluetooth/btqca.h
>> @@ -140,7 +140,8 @@ enum qca_btsoc_type {
>> 
>>  int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t 
>> *bdaddr);
>>  int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
>> -		   enum qca_btsoc_type soc_type, u32 soc_ver);
>> +		   enum qca_btsoc_type soc_type, u32 soc_ver,
>> +		   const char *firmware_name);
>>  int qca_read_soc_version(struct hci_dev *hdev, u32 *soc_version);
>>  int qca_set_bdaddr(struct hci_dev *hdev, const bdaddr_t *bdaddr);
>>  static inline bool qca_is_wcn399x(enum qca_btsoc_type soc_type)
>> @@ -155,7 +156,8 @@ static inline int qca_set_bdaddr_rome(struct
>> hci_dev *hdev, const bdaddr_t *bdad
>>  }
>> 
>>  static inline int qca_uart_setup(struct hci_dev *hdev, uint8_t 
>> baudrate,
>> -				 enum qca_btsoc_type soc_type, u32 soc_ver)
>> +				 enum qca_btsoc_type soc_type, u32 soc_ver,
>> +				 const char *firmware_name)
>>  {
>>  	return -EOPNOTSUPP;
>>  }
>> diff --git a/drivers/bluetooth/hci_qca.c b/drivers/bluetooth/hci_qca.c
>> index 57322c4..9590602 100644
>> --- a/drivers/bluetooth/hci_qca.c
>> +++ b/drivers/bluetooth/hci_qca.c
>> @@ -169,6 +169,7 @@ struct qca_serdev {
>>  	struct qca_power *bt_power;
>>  	u32 init_speed;
>>  	u32 oper_speed;
>> +	const char *firmware_name;
>>  };
>> 
>>  static int qca_power_setup(struct hci_uart *hu, bool on);
>> @@ -190,6 +191,17 @@ static enum qca_btsoc_type qca_soc_type(struct
>> hci_uart *hu)
>>  	return soc_type;
>>  }
>> 
>> +static const char *qca_get_firmware_name(struct hci_uart *hu)
>> +{
>> +	if (hu->serdev) {
>> +		struct qca_serdev *qsd = serdev_device_get_drvdata(hu->serdev);
>> +
>> +		return qsd->firmware_name;
>> +	} else {
>> +		return NULL;
>> +	}
>> +}
>> +
>>  static void __serial_clock_on(struct tty_struct *tty)
>>  {
>>  	/* TODO: Some chipset requires to enable UART clock on client
>> @@ -1195,6 +1207,7 @@ static int qca_setup(struct hci_uart *hu)
>>  	struct qca_data *qca = hu->priv;
>>  	unsigned int speed, qca_baudrate = QCA_BAUDRATE_115200;
>>  	enum qca_btsoc_type soc_type = qca_soc_type(hu);
>> +	const char *firmware_name = qca_get_firmware_name(hu);
>>  	int ret;
>>  	int soc_ver = 0;
>> 
>> @@ -1245,7 +1258,8 @@ static int qca_setup(struct hci_uart *hu)
>> 
>>  	bt_dev_info(hdev, "QCA controller version 0x%08x", soc_ver);
>>  	/* Setup patch / NVM configurations */
>> -	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver);
>> +	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver,
>> +			firmware_name);
>>  	if (!ret) {
>>  		set_bit(QCA_IBS_ENABLED, &qca->flags);
>>  		qca_debugfs_init(hdev);
>> @@ -1477,6 +1491,9 @@ static int qca_serdev_probe(struct serdev_device 
>> *serdev)
>>  			return PTR_ERR(qcadev->bt_en);
>>  		}
>> 
>> +		device_property_read_string(&serdev->dev, "firmware-name",
>> +					 &qcadev->firmware_name);
>> +
>>  		qcadev->susclk = devm_clk_get(&serdev->dev, NULL);
>>  		if (IS_ERR(qcadev->susclk)) {
>>  			dev_err(&serdev->dev, "failed to acquire clk\n");

OK, will make the change and send out the updated version soon.

-- 
The Qualcomm Innovation Center, Inc. is a member of the Code Aurora 
Forum,
a Linux Foundation Collaborative Project

^ permalink raw reply	[flat|nested] 10+ messages in thread

* [PATCH v5 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property
  2019-05-12  3:19   ` [PATCH v4 " Rocky Liao
  2019-05-15  5:32     ` Balakrishna Godavarthi
@ 2019-05-15 11:19     ` Rocky Liao
  2019-05-17  2:43       ` Balakrishna Godavarthi
  2019-06-06  9:40       ` [PATCH v6 " Rocky Liao
  1 sibling, 2 replies; 10+ messages in thread
From: Rocky Liao @ 2019-05-15 11:19 UTC (permalink / raw)
  To: robh+dt, mark.rutland, marcel, johan.hedberg, thierry.escande
  Cc: netdev, devicetree, linux-kernel, linux-bluetooth, linux-arm-msm,
	bgodavar, c-hbandi, Rocky Liao

QCA BTSOC NVM is a customized firmware file and different vendors may
want to have different BTSOC configuration (e.g. Configure SCO over PCM
or I2S, Setting Tx power, etc.) via this file. This patch will allow
vendors to download different NVM firmware file by reading a device
property "firmware-name".

Signed-off-by: Rocky Liao <rjliao@codeaurora.org>
---
Changes in v5:
  * Made the change applicable to the wcn399x series chip sets
---
 drivers/bluetooth/btqca.c   |  8 ++++++--
 drivers/bluetooth/btqca.h   |  6 ++++--
 drivers/bluetooth/hci_qca.c | 19 ++++++++++++++++++-
 3 files changed, 28 insertions(+), 5 deletions(-)

diff --git a/drivers/bluetooth/btqca.c b/drivers/bluetooth/btqca.c
index cc12eec..a78b80e 100644
--- a/drivers/bluetooth/btqca.c
+++ b/drivers/bluetooth/btqca.c
@@ -332,7 +332,8 @@ int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr)
 EXPORT_SYMBOL_GPL(qca_set_bdaddr_rome);
 
 int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-		   enum qca_btsoc_type soc_type, u32 soc_ver)
+		   enum qca_btsoc_type soc_type, u32 soc_ver,
+		   const char *firmware_name)
 {
 	struct rome_config config;
 	int err;
@@ -365,7 +366,10 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
 
 	/* Download NVM configuration */
 	config.type = TLV_TYPE_NVM;
-	if (qca_is_wcn399x(soc_type))
+	if (firmware_name)
+		snprintf(config.fwname, sizeof(config.fwname),
+			 "qca/%s", firmware_name);
+	else if (qca_is_wcn399x(soc_type))
 		snprintf(config.fwname, sizeof(config.fwname),
 			 "qca/crnv%02x.bin", rom_ver);
 	else
diff --git a/drivers/bluetooth/btqca.h b/drivers/bluetooth/btqca.h
index 4c4fe2b..8c037bb 100644
--- a/drivers/bluetooth/btqca.h
+++ b/drivers/bluetooth/btqca.h
@@ -140,7 +140,8 @@ enum qca_btsoc_type {
 
 int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr);
 int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-		   enum qca_btsoc_type soc_type, u32 soc_ver);
+		   enum qca_btsoc_type soc_type, u32 soc_ver,
+		   const char *firmware_name);
 int qca_read_soc_version(struct hci_dev *hdev, u32 *soc_version);
 int qca_set_bdaddr(struct hci_dev *hdev, const bdaddr_t *bdaddr);
 static inline bool qca_is_wcn399x(enum qca_btsoc_type soc_type)
@@ -155,7 +156,8 @@ static inline int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdad
 }
 
 static inline int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-				 enum qca_btsoc_type soc_type, u32 soc_ver)
+				 enum qca_btsoc_type soc_type, u32 soc_ver,
+				 const char *firmware_name)
 {
 	return -EOPNOTSUPP;
 }
diff --git a/drivers/bluetooth/hci_qca.c b/drivers/bluetooth/hci_qca.c
index 57322c4..9590602 100644
--- a/drivers/bluetooth/hci_qca.c
+++ b/drivers/bluetooth/hci_qca.c
@@ -169,6 +169,7 @@ struct qca_serdev {
 	struct qca_power *bt_power;
 	u32 init_speed;
 	u32 oper_speed;
+	const char *firmware_name;
 };
 
 static int qca_power_setup(struct hci_uart *hu, bool on);
@@ -190,6 +191,17 @@ static enum qca_btsoc_type qca_soc_type(struct hci_uart *hu)
 	return soc_type;
 }
 
+static const char *qca_get_firmware_name(struct hci_uart *hu)
+{
+	if (hu->serdev) {
+		struct qca_serdev *qsd = serdev_device_get_drvdata(hu->serdev);
+
+		return qsd->firmware_name;
+	} else {
+		return NULL;
+	}
+}
+
 static void __serial_clock_on(struct tty_struct *tty)
 {
 	/* TODO: Some chipset requires to enable UART clock on client
@@ -1195,6 +1207,7 @@ static int qca_setup(struct hci_uart *hu)
 	struct qca_data *qca = hu->priv;
 	unsigned int speed, qca_baudrate = QCA_BAUDRATE_115200;
 	enum qca_btsoc_type soc_type = qca_soc_type(hu);
+	const char *firmware_name = qca_get_firmware_name(hu);
 	int ret;
 	int soc_ver = 0;
 
@@ -1245,7 +1258,8 @@ static int qca_setup(struct hci_uart *hu)
 
 	bt_dev_info(hdev, "QCA controller version 0x%08x", soc_ver);
 	/* Setup patch / NVM configurations */
-	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver);
+	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver,
+			firmware_name);
 	if (!ret) {
 		set_bit(QCA_IBS_ENABLED, &qca->flags);
 		qca_debugfs_init(hdev);
@@ -1477,6 +1491,9 @@ static int qca_serdev_probe(struct serdev_device *serdev)
 			return PTR_ERR(qcadev->bt_en);
 		}
 
+		device_property_read_string(&serdev->dev, "firmware-name",
+					 &qcadev->firmware_name);
+
 		qcadev->susclk = devm_clk_get(&serdev->dev, NULL);
 		if (IS_ERR(qcadev->susclk)) {
 			dev_err(&serdev->dev, "failed to acquire clk\n");
-- 
The Qualcomm Innovation Center, Inc. is a member of the Code Aurora Forum, a Linux Foundation Collaborative Project


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* Re: [PATCH v5 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property
  2019-05-15 11:19     ` [PATCH v5 " Rocky Liao
@ 2019-05-17  2:43       ` Balakrishna Godavarthi
  2019-05-17  4:26         ` Harish Bandi
  2019-06-06  9:40       ` [PATCH v6 " Rocky Liao
  1 sibling, 1 reply; 10+ messages in thread
From: Balakrishna Godavarthi @ 2019-05-17  2:43 UTC (permalink / raw)
  To: Rocky Liao
  Cc: robh+dt, mark.rutland, marcel, johan.hedberg, thierry.escande,
	netdev, devicetree, linux-kernel, linux-bluetooth, linux-arm-msm,
	c-hbandi, Hemantg

Hi Rocky,

On 2019-05-15 16:49, Rocky Liao wrote:
> QCA BTSOC NVM is a customized firmware file and different vendors may
> want to have different BTSOC configuration (e.g. Configure SCO over PCM
> or I2S, Setting Tx power, etc.) via this file. This patch will allow
> vendors to download different NVM firmware file by reading a device
> property "firmware-name".
> 
> Signed-off-by: Rocky Liao <rjliao@codeaurora.org>
> ---
> Changes in v5:
>   * Made the change applicable to the wcn399x series chip sets
> ---
>  drivers/bluetooth/btqca.c   |  8 ++++++--
>  drivers/bluetooth/btqca.h   |  6 ++++--
>  drivers/bluetooth/hci_qca.c | 19 ++++++++++++++++++-
>  3 files changed, 28 insertions(+), 5 deletions(-)
> 
> diff --git a/drivers/bluetooth/btqca.c b/drivers/bluetooth/btqca.c
> index cc12eec..a78b80e 100644
> --- a/drivers/bluetooth/btqca.c
> +++ b/drivers/bluetooth/btqca.c
> @@ -332,7 +332,8 @@ int qca_set_bdaddr_rome(struct hci_dev *hdev,
> const bdaddr_t *bdaddr)
>  EXPORT_SYMBOL_GPL(qca_set_bdaddr_rome);
> 
>  int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
> -		   enum qca_btsoc_type soc_type, u32 soc_ver)
> +		   enum qca_btsoc_type soc_type, u32 soc_ver,
> +		   const char *firmware_name)
>  {
>  	struct rome_config config;
>  	int err;
> @@ -365,7 +366,10 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t 
> baudrate,
> 
>  	/* Download NVM configuration */
>  	config.type = TLV_TYPE_NVM;
> -	if (qca_is_wcn399x(soc_type))
> +	if (firmware_name)
> +		snprintf(config.fwname, sizeof(config.fwname),
> +			 "qca/%s", firmware_name);
> +	else if (qca_is_wcn399x(soc_type))
>  		snprintf(config.fwname, sizeof(config.fwname),
>  			 "qca/crnv%02x.bin", rom_ver);
>  	else
> diff --git a/drivers/bluetooth/btqca.h b/drivers/bluetooth/btqca.h
> index 4c4fe2b..8c037bb 100644
> --- a/drivers/bluetooth/btqca.h
> +++ b/drivers/bluetooth/btqca.h
> @@ -140,7 +140,8 @@ enum qca_btsoc_type {
> 
>  int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr);
>  int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
> -		   enum qca_btsoc_type soc_type, u32 soc_ver);
> +		   enum qca_btsoc_type soc_type, u32 soc_ver,
> +		   const char *firmware_name);
>  int qca_read_soc_version(struct hci_dev *hdev, u32 *soc_version);
>  int qca_set_bdaddr(struct hci_dev *hdev, const bdaddr_t *bdaddr);
>  static inline bool qca_is_wcn399x(enum qca_btsoc_type soc_type)
> @@ -155,7 +156,8 @@ static inline int qca_set_bdaddr_rome(struct
> hci_dev *hdev, const bdaddr_t *bdad
>  }
> 
>  static inline int qca_uart_setup(struct hci_dev *hdev, uint8_t 
> baudrate,
> -				 enum qca_btsoc_type soc_type, u32 soc_ver)
> +				 enum qca_btsoc_type soc_type, u32 soc_ver,
> +				 const char *firmware_name)
>  {
>  	return -EOPNOTSUPP;
>  }
> diff --git a/drivers/bluetooth/hci_qca.c b/drivers/bluetooth/hci_qca.c
> index 57322c4..9590602 100644
> --- a/drivers/bluetooth/hci_qca.c
> +++ b/drivers/bluetooth/hci_qca.c
> @@ -169,6 +169,7 @@ struct qca_serdev {
>  	struct qca_power *bt_power;
>  	u32 init_speed;
>  	u32 oper_speed;
> +	const char *firmware_name;
>  };
> 
>  static int qca_power_setup(struct hci_uart *hu, bool on);
> @@ -190,6 +191,17 @@ static enum qca_btsoc_type qca_soc_type(struct
> hci_uart *hu)
>  	return soc_type;
>  }
> 
> +static const char *qca_get_firmware_name(struct hci_uart *hu)
> +{
> +	if (hu->serdev) {
> +		struct qca_serdev *qsd = serdev_device_get_drvdata(hu->serdev);
> +
> +		return qsd->firmware_name;
> +	} else {
> +		return NULL;
> +	}
> +}
> +
>  static void __serial_clock_on(struct tty_struct *tty)
>  {
>  	/* TODO: Some chipset requires to enable UART clock on client
> @@ -1195,6 +1207,7 @@ static int qca_setup(struct hci_uart *hu)
>  	struct qca_data *qca = hu->priv;
>  	unsigned int speed, qca_baudrate = QCA_BAUDRATE_115200;
>  	enum qca_btsoc_type soc_type = qca_soc_type(hu);
> +	const char *firmware_name = qca_get_firmware_name(hu);
>  	int ret;
>  	int soc_ver = 0;
> 
> @@ -1245,7 +1258,8 @@ static int qca_setup(struct hci_uart *hu)
> 
>  	bt_dev_info(hdev, "QCA controller version 0x%08x", soc_ver);
>  	/* Setup patch / NVM configurations */
> -	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver);
> +	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver,
> +			firmware_name);
>  	if (!ret) {
>  		set_bit(QCA_IBS_ENABLED, &qca->flags);
>  		qca_debugfs_init(hdev);
> @@ -1477,6 +1491,9 @@ static int qca_serdev_probe(struct serdev_device 
> *serdev)
>  			return PTR_ERR(qcadev->bt_en);
>  		}
> 
> +		device_property_read_string(&serdev->dev, "firmware-name",
> +					 &qcadev->firmware_name);
> +
>  		qcadev->susclk = devm_clk_get(&serdev->dev, NULL);
>  		if (IS_ERR(qcadev->susclk)) {
>  			dev_err(&serdev->dev, "failed to acquire clk\n");

Thanks for doing it for wcn399x series too.

Change look fine to me.

Reviewed-by: Balakrishna Godavarthi <bgodavar@codeaurora.org>
-- 
Regards
Balakrishna.

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH v5 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property
  2019-05-17  2:43       ` Balakrishna Godavarthi
@ 2019-05-17  4:26         ` Harish Bandi
  0 siblings, 0 replies; 10+ messages in thread
From: Harish Bandi @ 2019-05-17  4:26 UTC (permalink / raw)
  To: Balakrishna Godavarthi
  Cc: Rocky Liao, robh+dt, mark.rutland, marcel, johan.hedberg,
	thierry.escande, netdev, devicetree, linux-kernel,
	linux-bluetooth, linux-arm-msm, Hemantg, linux-bluetooth-owner

On 2019-05-17 08:13, Balakrishna Godavarthi wrote:
> Hi Rocky,
> 
> On 2019-05-15 16:49, Rocky Liao wrote:
>> QCA BTSOC NVM is a customized firmware file and different vendors may
>> want to have different BTSOC configuration (e.g. Configure SCO over 
>> PCM
>> or I2S, Setting Tx power, etc.) via this file. This patch will allow
>> vendors to download different NVM firmware file by reading a device
>> property "firmware-name".
>> 
>> Signed-off-by: Rocky Liao <rjliao@codeaurora.org>
>> ---
>> Changes in v5:
>>   * Made the change applicable to the wcn399x series chip sets
>> ---
>>  drivers/bluetooth/btqca.c   |  8 ++++++--
>>  drivers/bluetooth/btqca.h   |  6 ++++--
>>  drivers/bluetooth/hci_qca.c | 19 ++++++++++++++++++-
>>  3 files changed, 28 insertions(+), 5 deletions(-)
>> 
>> diff --git a/drivers/bluetooth/btqca.c b/drivers/bluetooth/btqca.c
>> index cc12eec..a78b80e 100644
>> --- a/drivers/bluetooth/btqca.c
>> +++ b/drivers/bluetooth/btqca.c
>> @@ -332,7 +332,8 @@ int qca_set_bdaddr_rome(struct hci_dev *hdev,
>> const bdaddr_t *bdaddr)
>>  EXPORT_SYMBOL_GPL(qca_set_bdaddr_rome);
>> 
>>  int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
>> -		   enum qca_btsoc_type soc_type, u32 soc_ver)
>> +		   enum qca_btsoc_type soc_type, u32 soc_ver,
>> +		   const char *firmware_name)
>>  {
>>  	struct rome_config config;
>>  	int err;
>> @@ -365,7 +366,10 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t 
>> baudrate,
>> 
>>  	/* Download NVM configuration */
>>  	config.type = TLV_TYPE_NVM;
>> -	if (qca_is_wcn399x(soc_type))
>> +	if (firmware_name)
>> +		snprintf(config.fwname, sizeof(config.fwname),
>> +			 "qca/%s", firmware_name);
>> +	else if (qca_is_wcn399x(soc_type))
>>  		snprintf(config.fwname, sizeof(config.fwname),
>>  			 "qca/crnv%02x.bin", rom_ver);
>>  	else
>> diff --git a/drivers/bluetooth/btqca.h b/drivers/bluetooth/btqca.h
>> index 4c4fe2b..8c037bb 100644
>> --- a/drivers/bluetooth/btqca.h
>> +++ b/drivers/bluetooth/btqca.h
>> @@ -140,7 +140,8 @@ enum qca_btsoc_type {
>> 
>>  int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t 
>> *bdaddr);
>>  int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
>> -		   enum qca_btsoc_type soc_type, u32 soc_ver);
>> +		   enum qca_btsoc_type soc_type, u32 soc_ver,
>> +		   const char *firmware_name);
>>  int qca_read_soc_version(struct hci_dev *hdev, u32 *soc_version);
>>  int qca_set_bdaddr(struct hci_dev *hdev, const bdaddr_t *bdaddr);
>>  static inline bool qca_is_wcn399x(enum qca_btsoc_type soc_type)
>> @@ -155,7 +156,8 @@ static inline int qca_set_bdaddr_rome(struct
>> hci_dev *hdev, const bdaddr_t *bdad
>>  }
>> 
>>  static inline int qca_uart_setup(struct hci_dev *hdev, uint8_t 
>> baudrate,
>> -				 enum qca_btsoc_type soc_type, u32 soc_ver)
>> +				 enum qca_btsoc_type soc_type, u32 soc_ver,
>> +				 const char *firmware_name)
>>  {
>>  	return -EOPNOTSUPP;
>>  }
>> diff --git a/drivers/bluetooth/hci_qca.c b/drivers/bluetooth/hci_qca.c
>> index 57322c4..9590602 100644
>> --- a/drivers/bluetooth/hci_qca.c
>> +++ b/drivers/bluetooth/hci_qca.c
>> @@ -169,6 +169,7 @@ struct qca_serdev {
>>  	struct qca_power *bt_power;
>>  	u32 init_speed;
>>  	u32 oper_speed;
>> +	const char *firmware_name;
>>  };
>> 
>>  static int qca_power_setup(struct hci_uart *hu, bool on);
>> @@ -190,6 +191,17 @@ static enum qca_btsoc_type qca_soc_type(struct
>> hci_uart *hu)
>>  	return soc_type;
>>  }
>> 
>> +static const char *qca_get_firmware_name(struct hci_uart *hu)
>> +{
>> +	if (hu->serdev) {
>> +		struct qca_serdev *qsd = serdev_device_get_drvdata(hu->serdev);
>> +
>> +		return qsd->firmware_name;
>> +	} else {
>> +		return NULL;
>> +	}
>> +}
>> +
>>  static void __serial_clock_on(struct tty_struct *tty)
>>  {
>>  	/* TODO: Some chipset requires to enable UART clock on client
>> @@ -1195,6 +1207,7 @@ static int qca_setup(struct hci_uart *hu)
>>  	struct qca_data *qca = hu->priv;
>>  	unsigned int speed, qca_baudrate = QCA_BAUDRATE_115200;
>>  	enum qca_btsoc_type soc_type = qca_soc_type(hu);
>> +	const char *firmware_name = qca_get_firmware_name(hu);
>>  	int ret;
>>  	int soc_ver = 0;
>> 
>> @@ -1245,7 +1258,8 @@ static int qca_setup(struct hci_uart *hu)
>> 
>>  	bt_dev_info(hdev, "QCA controller version 0x%08x", soc_ver);
>>  	/* Setup patch / NVM configurations */
>> -	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver);
>> +	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver,
>> +			firmware_name);
>>  	if (!ret) {
>>  		set_bit(QCA_IBS_ENABLED, &qca->flags);
>>  		qca_debugfs_init(hdev);
>> @@ -1477,6 +1491,9 @@ static int qca_serdev_probe(struct serdev_device 
>> *serdev)
>>  			return PTR_ERR(qcadev->bt_en);
>>  		}
>> 
>> +		device_property_read_string(&serdev->dev, "firmware-name",
>> +					 &qcadev->firmware_name);
>> +
>>  		qcadev->susclk = devm_clk_get(&serdev->dev, NULL);
>>  		if (IS_ERR(qcadev->susclk)) {
>>  			dev_err(&serdev->dev, "failed to acquire clk\n");
> 
> Thanks for doing it for wcn399x series too.
> 
> Change look fine to me.
> 
> Reviewed-by: Balakrishna Godavarthi <bgodavar@codeaurora.org>

Tested for WCN3998.

Tested-by: Harish Bandi <c-hbandi@codeaurora.org>

Thanks,
Harish

^ permalink raw reply	[flat|nested] 10+ messages in thread

* [PATCH v6 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property
  2019-05-15 11:19     ` [PATCH v5 " Rocky Liao
  2019-05-17  2:43       ` Balakrishna Godavarthi
@ 2019-06-06  9:40       ` Rocky Liao
  2019-06-06 12:02         ` Harish Bandi
  2019-07-06 10:51         ` Marcel Holtmann
  1 sibling, 2 replies; 10+ messages in thread
From: Rocky Liao @ 2019-06-06  9:40 UTC (permalink / raw)
  To: robh+dt, mark.rutland, marcel, johan.hedberg, thierry.escande
  Cc: netdev, devicetree, linux-kernel, linux-bluetooth, linux-arm-msm,
	bgodavar, c-hbandi, Rocky Liao

QCA BTSOC NVM is a customized firmware file and different vendors may
want to have different BTSOC configuration (e.g. Configure SCO over PCM
or I2S, Setting Tx power, etc.) via this file. This patch will allow
vendors to download different NVM firmware file by reading a device
property "firmware-name".

Signed-off-by: Rocky Liao <rjliao@codeaurora.org>
---
Changes in v6:
  * Added read firmware-name property for both QCA6174 and WCN399X
---
 drivers/bluetooth/btqca.c   |  8 ++++++--
 drivers/bluetooth/btqca.h   |  6 ++++--
 drivers/bluetooth/hci_qca.c | 18 +++++++++++++++++-
 3 files changed, 27 insertions(+), 5 deletions(-)

diff --git a/drivers/bluetooth/btqca.c b/drivers/bluetooth/btqca.c
index cc12eec..a78b80e 100644
--- a/drivers/bluetooth/btqca.c
+++ b/drivers/bluetooth/btqca.c
@@ -332,7 +332,8 @@ int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr)
 EXPORT_SYMBOL_GPL(qca_set_bdaddr_rome);
 
 int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-		   enum qca_btsoc_type soc_type, u32 soc_ver)
+		   enum qca_btsoc_type soc_type, u32 soc_ver,
+		   const char *firmware_name)
 {
 	struct rome_config config;
 	int err;
@@ -365,7 +366,10 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
 
 	/* Download NVM configuration */
 	config.type = TLV_TYPE_NVM;
-	if (qca_is_wcn399x(soc_type))
+	if (firmware_name)
+		snprintf(config.fwname, sizeof(config.fwname),
+			 "qca/%s", firmware_name);
+	else if (qca_is_wcn399x(soc_type))
 		snprintf(config.fwname, sizeof(config.fwname),
 			 "qca/crnv%02x.bin", rom_ver);
 	else
diff --git a/drivers/bluetooth/btqca.h b/drivers/bluetooth/btqca.h
index 4c4fe2b..8c037bb 100644
--- a/drivers/bluetooth/btqca.h
+++ b/drivers/bluetooth/btqca.h
@@ -140,7 +140,8 @@ enum qca_btsoc_type {
 
 int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr);
 int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-		   enum qca_btsoc_type soc_type, u32 soc_ver);
+		   enum qca_btsoc_type soc_type, u32 soc_ver,
+		   const char *firmware_name);
 int qca_read_soc_version(struct hci_dev *hdev, u32 *soc_version);
 int qca_set_bdaddr(struct hci_dev *hdev, const bdaddr_t *bdaddr);
 static inline bool qca_is_wcn399x(enum qca_btsoc_type soc_type)
@@ -155,7 +156,8 @@ static inline int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdad
 }
 
 static inline int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
-				 enum qca_btsoc_type soc_type, u32 soc_ver)
+				 enum qca_btsoc_type soc_type, u32 soc_ver,
+				 const char *firmware_name)
 {
 	return -EOPNOTSUPP;
 }
diff --git a/drivers/bluetooth/hci_qca.c b/drivers/bluetooth/hci_qca.c
index 57322c4..05ee0a1 100644
--- a/drivers/bluetooth/hci_qca.c
+++ b/drivers/bluetooth/hci_qca.c
@@ -169,6 +169,7 @@ struct qca_serdev {
 	struct qca_power *bt_power;
 	u32 init_speed;
 	u32 oper_speed;
+	const char *firmware_name;
 };
 
 static int qca_power_setup(struct hci_uart *hu, bool on);
@@ -190,6 +191,17 @@ static enum qca_btsoc_type qca_soc_type(struct hci_uart *hu)
 	return soc_type;
 }
 
+static const char *qca_get_firmware_name(struct hci_uart *hu)
+{
+	if (hu->serdev) {
+		struct qca_serdev *qsd = serdev_device_get_drvdata(hu->serdev);
+
+		return qsd->firmware_name;
+	} else {
+		return NULL;
+	}
+}
+
 static void __serial_clock_on(struct tty_struct *tty)
 {
 	/* TODO: Some chipset requires to enable UART clock on client
@@ -1195,6 +1207,7 @@ static int qca_setup(struct hci_uart *hu)
 	struct qca_data *qca = hu->priv;
 	unsigned int speed, qca_baudrate = QCA_BAUDRATE_115200;
 	enum qca_btsoc_type soc_type = qca_soc_type(hu);
+	const char *firmware_name = qca_get_firmware_name(hu);
 	int ret;
 	int soc_ver = 0;
 
@@ -1245,7 +1258,8 @@ static int qca_setup(struct hci_uart *hu)
 
 	bt_dev_info(hdev, "QCA controller version 0x%08x", soc_ver);
 	/* Setup patch / NVM configurations */
-	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver);
+	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver,
+			firmware_name);
 	if (!ret) {
 		set_bit(QCA_IBS_ENABLED, &qca->flags);
 		qca_debugfs_init(hdev);
@@ -1439,6 +1453,8 @@ static int qca_serdev_probe(struct serdev_device *serdev)
 	qcadev->serdev_hu.serdev = serdev;
 	data = of_device_get_match_data(&serdev->dev);
 	serdev_device_set_drvdata(serdev, qcadev);
+	device_property_read_string(&serdev->dev, "firmware-name",
+					 &qcadev->firmware_name);
 	if (data && qca_is_wcn399x(data->soc_type)) {
 		qcadev->btsoc_type = data->soc_type;
 		qcadev->bt_power = devm_kzalloc(&serdev->dev,
-- 
The Qualcomm Innovation Center, Inc. is a member of the Code Aurora Forum, a Linux Foundation Collaborative Project


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* Re: [PATCH v6 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property
  2019-06-06  9:40       ` [PATCH v6 " Rocky Liao
@ 2019-06-06 12:02         ` Harish Bandi
  2019-07-06 10:51         ` Marcel Holtmann
  1 sibling, 0 replies; 10+ messages in thread
From: Harish Bandi @ 2019-06-06 12:02 UTC (permalink / raw)
  To: Rocky Liao
  Cc: robh+dt, mark.rutland, marcel, johan.hedberg, thierry.escande,
	netdev, devicetree, linux-kernel, linux-bluetooth, linux-arm-msm,
	bgodavar, linux-bluetooth-owner

On 2019-06-06 15:10, Rocky Liao wrote:
> QCA BTSOC NVM is a customized firmware file and different vendors may
> want to have different BTSOC configuration (e.g. Configure SCO over PCM
> or I2S, Setting Tx power, etc.) via this file. This patch will allow
> vendors to download different NVM firmware file by reading a device
> property "firmware-name".
> 
> Signed-off-by: Rocky Liao <rjliao@codeaurora.org>
> ---
> Changes in v6:
>   * Added read firmware-name property for both QCA6174 and WCN399X
> ---
>  drivers/bluetooth/btqca.c   |  8 ++++++--
>  drivers/bluetooth/btqca.h   |  6 ++++--
>  drivers/bluetooth/hci_qca.c | 18 +++++++++++++++++-
>  3 files changed, 27 insertions(+), 5 deletions(-)
> 
> diff --git a/drivers/bluetooth/btqca.c b/drivers/bluetooth/btqca.c
> index cc12eec..a78b80e 100644
> --- a/drivers/bluetooth/btqca.c
> +++ b/drivers/bluetooth/btqca.c
> @@ -332,7 +332,8 @@ int qca_set_bdaddr_rome(struct hci_dev *hdev,
> const bdaddr_t *bdaddr)
>  EXPORT_SYMBOL_GPL(qca_set_bdaddr_rome);
> 
>  int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
> -		   enum qca_btsoc_type soc_type, u32 soc_ver)
> +		   enum qca_btsoc_type soc_type, u32 soc_ver,
> +		   const char *firmware_name)
>  {
>  	struct rome_config config;
>  	int err;
> @@ -365,7 +366,10 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t 
> baudrate,
> 
>  	/* Download NVM configuration */
>  	config.type = TLV_TYPE_NVM;
> -	if (qca_is_wcn399x(soc_type))
> +	if (firmware_name)
> +		snprintf(config.fwname, sizeof(config.fwname),
> +			 "qca/%s", firmware_name);
> +	else if (qca_is_wcn399x(soc_type))
>  		snprintf(config.fwname, sizeof(config.fwname),
>  			 "qca/crnv%02x.bin", rom_ver);
>  	else
> diff --git a/drivers/bluetooth/btqca.h b/drivers/bluetooth/btqca.h
> index 4c4fe2b..8c037bb 100644
> --- a/drivers/bluetooth/btqca.h
> +++ b/drivers/bluetooth/btqca.h
> @@ -140,7 +140,8 @@ enum qca_btsoc_type {
> 
>  int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr);
>  int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
> -		   enum qca_btsoc_type soc_type, u32 soc_ver);
> +		   enum qca_btsoc_type soc_type, u32 soc_ver,
> +		   const char *firmware_name);
>  int qca_read_soc_version(struct hci_dev *hdev, u32 *soc_version);
>  int qca_set_bdaddr(struct hci_dev *hdev, const bdaddr_t *bdaddr);
>  static inline bool qca_is_wcn399x(enum qca_btsoc_type soc_type)
> @@ -155,7 +156,8 @@ static inline int qca_set_bdaddr_rome(struct
> hci_dev *hdev, const bdaddr_t *bdad
>  }
> 
>  static inline int qca_uart_setup(struct hci_dev *hdev, uint8_t 
> baudrate,
> -				 enum qca_btsoc_type soc_type, u32 soc_ver)
> +				 enum qca_btsoc_type soc_type, u32 soc_ver,
> +				 const char *firmware_name)
>  {
>  	return -EOPNOTSUPP;
>  }
> diff --git a/drivers/bluetooth/hci_qca.c b/drivers/bluetooth/hci_qca.c
> index 57322c4..05ee0a1 100644
> --- a/drivers/bluetooth/hci_qca.c
> +++ b/drivers/bluetooth/hci_qca.c
> @@ -169,6 +169,7 @@ struct qca_serdev {
>  	struct qca_power *bt_power;
>  	u32 init_speed;
>  	u32 oper_speed;
> +	const char *firmware_name;
>  };
> 
>  static int qca_power_setup(struct hci_uart *hu, bool on);
> @@ -190,6 +191,17 @@ static enum qca_btsoc_type qca_soc_type(struct
> hci_uart *hu)
>  	return soc_type;
>  }
> 
> +static const char *qca_get_firmware_name(struct hci_uart *hu)
> +{
> +	if (hu->serdev) {
> +		struct qca_serdev *qsd = serdev_device_get_drvdata(hu->serdev);
> +
> +		return qsd->firmware_name;
> +	} else {
> +		return NULL;
> +	}
> +}
> +
>  static void __serial_clock_on(struct tty_struct *tty)
>  {
>  	/* TODO: Some chipset requires to enable UART clock on client
> @@ -1195,6 +1207,7 @@ static int qca_setup(struct hci_uart *hu)
>  	struct qca_data *qca = hu->priv;
>  	unsigned int speed, qca_baudrate = QCA_BAUDRATE_115200;
>  	enum qca_btsoc_type soc_type = qca_soc_type(hu);
> +	const char *firmware_name = qca_get_firmware_name(hu);
>  	int ret;
>  	int soc_ver = 0;
> 
> @@ -1245,7 +1258,8 @@ static int qca_setup(struct hci_uart *hu)
> 
>  	bt_dev_info(hdev, "QCA controller version 0x%08x", soc_ver);
>  	/* Setup patch / NVM configurations */
> -	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver);
> +	ret = qca_uart_setup(hdev, qca_baudrate, soc_type, soc_ver,
> +			firmware_name);
>  	if (!ret) {
>  		set_bit(QCA_IBS_ENABLED, &qca->flags);
>  		qca_debugfs_init(hdev);
> @@ -1439,6 +1453,8 @@ static int qca_serdev_probe(struct serdev_device 
> *serdev)
>  	qcadev->serdev_hu.serdev = serdev;
>  	data = of_device_get_match_data(&serdev->dev);
>  	serdev_device_set_drvdata(serdev, qcadev);
> +	device_property_read_string(&serdev->dev, "firmware-name",
> +					 &qcadev->firmware_name);
>  	if (data && qca_is_wcn399x(data->soc_type)) {
>  		qcadev->btsoc_type = data->soc_type;
>  		qcadev->bt_power = devm_kzalloc(&serdev->dev,
Tested for WCN3998.

Tested-by: Harish Bandi <c-hbandi@codeaurora.org>

Thanks,
Harish

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH v6 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property
  2019-06-06  9:40       ` [PATCH v6 " Rocky Liao
  2019-06-06 12:02         ` Harish Bandi
@ 2019-07-06 10:51         ` Marcel Holtmann
  1 sibling, 0 replies; 10+ messages in thread
From: Marcel Holtmann @ 2019-07-06 10:51 UTC (permalink / raw)
  To: Rocky Liao
  Cc: robh+dt, mark.rutland, Johan Hedberg, thierry.escande, netdev,
	devicetree, linux-kernel, linux-bluetooth, linux-arm-msm,
	bgodavar, c-hbandi

Hi Rocky,

> QCA BTSOC NVM is a customized firmware file and different vendors may
> want to have different BTSOC configuration (e.g. Configure SCO over PCM
> or I2S, Setting Tx power, etc.) via this file. This patch will allow
> vendors to download different NVM firmware file by reading a device
> property "firmware-name".
> 
> Signed-off-by: Rocky Liao <rjliao@codeaurora.org>
> ---
> Changes in v6:
>  * Added read firmware-name property for both QCA6174 and WCN399X
> ---
> drivers/bluetooth/btqca.c   |  8 ++++++--
> drivers/bluetooth/btqca.h   |  6 ++++--
> drivers/bluetooth/hci_qca.c | 18 +++++++++++++++++-
> 3 files changed, 27 insertions(+), 5 deletions(-)

patch has been applied to bluetooth-next tree.

Regards

Marcel


^ permalink raw reply	[flat|nested] 10+ messages in thread

end of thread, other threads:[~2019-07-06 10:51 UTC | newest]

Thread overview: 10+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
     [not found] <1554368908-22017-1-git-send-email-rjliao@codeaurora.org>
2019-04-10  9:27 ` [PATCH v3 1/2] Bluetooth: hci_qca: Load customized NVM based on the device property Rocky Liao
2019-05-12  3:19   ` [PATCH v4 " Rocky Liao
2019-05-15  5:32     ` Balakrishna Godavarthi
2019-05-15  8:30       ` Rocky Liao
2019-05-15 11:19     ` [PATCH v5 " Rocky Liao
2019-05-17  2:43       ` Balakrishna Godavarthi
2019-05-17  4:26         ` Harish Bandi
2019-06-06  9:40       ` [PATCH v6 " Rocky Liao
2019-06-06 12:02         ` Harish Bandi
2019-07-06 10:51         ` Marcel Holtmann

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).