@@ -205,6 +205,44 @@ static int qca_send_reset(struct hci_dev *hdev)
205
205
return 0 ;
206
206
}
207
207
208
+ static int qca_read_fw_board_id (struct hci_dev * hdev , u16 * bid )
209
+ {
210
+ u8 cmd ;
211
+ struct sk_buff * skb ;
212
+ struct edl_event_hdr * edl ;
213
+ int err = 0 ;
214
+
215
+ cmd = EDL_GET_BID_REQ_CMD ;
216
+ skb = __hci_cmd_sync_ev (hdev , EDL_PATCH_CMD_OPCODE , EDL_PATCH_CMD_LEN ,
217
+ & cmd , 0 , HCI_INIT_TIMEOUT );
218
+ if (IS_ERR (skb )) {
219
+ err = PTR_ERR (skb );
220
+ bt_dev_err (hdev , "Reading QCA board ID failed (%d)" , err );
221
+ return err ;
222
+ }
223
+
224
+ edl = skb_pull_data (skb , sizeof (* edl ));
225
+ if (!edl ) {
226
+ bt_dev_err (hdev , "QCA read board ID with no header" );
227
+ err = - EILSEQ ;
228
+ goto out ;
229
+ }
230
+
231
+ if (edl -> cresp != EDL_CMD_REQ_RES_EVT ||
232
+ edl -> rtype != EDL_GET_BID_REQ_CMD ) {
233
+ bt_dev_err (hdev , "QCA Wrong packet: %d %d" , edl -> cresp , edl -> rtype );
234
+ err = - EIO ;
235
+ goto out ;
236
+ }
237
+
238
+ * bid = (edl -> data [1 ] << 8 ) + edl -> data [2 ];
239
+ bt_dev_dbg (hdev , "%s: bid = %x" , __func__ , * bid );
240
+
241
+ out :
242
+ kfree_skb (skb );
243
+ return err ;
244
+ }
245
+
208
246
int qca_send_pre_shutdown_cmd (struct hci_dev * hdev )
209
247
{
210
248
struct sk_buff * skb ;
@@ -574,6 +612,23 @@ int qca_set_bdaddr_rome(struct hci_dev *hdev, const bdaddr_t *bdaddr)
574
612
}
575
613
EXPORT_SYMBOL_GPL (qca_set_bdaddr_rome );
576
614
615
+ static void qca_generate_hsp_nvm_name (char * fwname , size_t max_size ,
616
+ struct qca_btsoc_version ver , u8 rom_ver , u16 bid )
617
+ {
618
+ const char * variant ;
619
+
620
+ /* hsp gf chip */
621
+ if ((le32_to_cpu (ver .soc_id ) & QCA_HSP_GF_SOC_MASK ) == QCA_HSP_GF_SOC_ID )
622
+ variant = "g" ;
623
+ else
624
+ variant = "" ;
625
+
626
+ if (bid == 0x0 )
627
+ snprintf (fwname , max_size , "qca/hpnv%02x%s.bin" , rom_ver , variant );
628
+ else
629
+ snprintf (fwname , max_size , "qca/hpnv%02x%s.%x" , rom_ver , variant , bid );
630
+ }
631
+
577
632
int qca_uart_setup (struct hci_dev * hdev , uint8_t baudrate ,
578
633
enum qca_btsoc_type soc_type , struct qca_btsoc_version ver ,
579
634
const char * firmware_name )
@@ -582,6 +637,7 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
582
637
int err ;
583
638
u8 rom_ver = 0 ;
584
639
u32 soc_ver ;
640
+ u16 boardid = 0 ;
585
641
586
642
bt_dev_dbg (hdev , "QCA setup on UART" );
587
643
@@ -615,6 +671,10 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
615
671
snprintf (config .fwname , sizeof (config .fwname ),
616
672
"qca/apbtfw%02x.tlv" , rom_ver );
617
673
break ;
674
+ case QCA_QCA2066 :
675
+ snprintf (config .fwname , sizeof (config .fwname ),
676
+ "qca/hpbtfw%02x.tlv" , rom_ver );
677
+ break ;
618
678
case QCA_QCA6390 :
619
679
snprintf (config .fwname , sizeof (config .fwname ),
620
680
"qca/htbtfw%02x.tlv" , rom_ver );
@@ -649,6 +709,9 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
649
709
/* Give the controller some time to get ready to receive the NVM */
650
710
msleep (10 );
651
711
712
+ if (soc_type == QCA_QCA2066 )
713
+ qca_read_fw_board_id (hdev , & boardid );
714
+
652
715
/* Download NVM configuration */
653
716
config .type = TLV_TYPE_NVM ;
654
717
if (firmware_name ) {
@@ -671,6 +734,10 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
671
734
snprintf (config .fwname , sizeof (config .fwname ),
672
735
"qca/apnv%02x.bin" , rom_ver );
673
736
break ;
737
+ case QCA_QCA2066 :
738
+ qca_generate_hsp_nvm_name (config .fwname ,
739
+ sizeof (config .fwname ), ver , rom_ver , boardid );
740
+ break ;
674
741
case QCA_QCA6390 :
675
742
snprintf (config .fwname , sizeof (config .fwname ),
676
743
"qca/htnv%02x.bin" , rom_ver );
@@ -702,6 +769,7 @@ int qca_uart_setup(struct hci_dev *hdev, uint8_t baudrate,
702
769
703
770
switch (soc_type ) {
704
771
case QCA_WCN3991 :
772
+ case QCA_QCA2066 :
705
773
case QCA_QCA6390 :
706
774
case QCA_WCN6750 :
707
775
case QCA_WCN6855 :
0 commit comments