@@ -29,13 +29,25 @@ LOG_MODULE_REGISTER(bt_nxp_ctlr);
2929
3030#define DT_DRV_COMPAT nxp_bt_hci_uart
3131
32- #define FW_UPLOAD_CHANGE_TIMEOUT_RETRY_COUNT 6
32+ #define FW_UPLOAD_CHANGE_TIMEOUT_RETRY_COUNT 6
33+ #define HCI_CMD_STORE_BT_CAL_DATA_ANNEX100_OCF 0xFF
34+ #define HCI_CMD_STORE_BT_CAL_DATA_PARAM_ANNEX100_LENGTH 16
35+ #define HCI_CMD_STORE_BT_CAL_DATA_OCF 0x61
36+ #define HCI_CMD_STORE_BT_CAL_DATA_PARAM_LENGTH 32
3337
3438extern const unsigned char * bt_fw_bin ;
3539extern const unsigned int bt_fw_bin_len ;
3640
3741static const struct device * uart_dev = DEVICE_DT_GET (DT_INST_GPARENT (0 ));
3842
43+ #if !defined(CONFIG_HCI_NXP_SET_CAL_DATA )
44+ #define bt_nxp_set_calibration_data_annex55 () 0
45+ #endif
46+
47+ #if !defined(CONFIG_HCI_NXP_SET_CAL_DATA_ANNEX100 )
48+ #define bt_nxp_set_calibration_data_annex100 () 0
49+ #endif
50+
3951#if DT_NODE_HAS_PROP (DT_DRV_INST (0 ), sdio_reset_gpios )
4052struct gpio_dt_spec sdio_reset = GPIO_DT_SPEC_GET (DT_DRV_INST (0 ), sdio_reset_gpios );
4153#endif /* DT_NODE_HAS_PROP(DT_DRV_INST(0), sdio_reset_gpios) */
@@ -1171,6 +1183,189 @@ static int bt_nxp_ctlr_init(void)
11711183 return 0 ;
11721184}
11731185
1186+ #if defined(CONFIG_HCI_NXP_SET_CAL_DATA )
1187+
1188+ static int bt_nxp_set_calibration_data_annex55 (void )
1189+ {
1190+ int ret = 0 ;
1191+ uint16_t opcode = BT_OP (BT_OGF_VS , HCI_CMD_STORE_BT_CAL_DATA_OCF );
1192+
1193+ const uint8_t hci_cal_data_annex55 [HCI_CMD_STORE_BT_CAL_DATA_PARAM_LENGTH ] = {
1194+ #if defined(CONFIG_BT_NXP_NW612 )
1195+ 0x00 , /* Sequence Number : 0x00 */
1196+ 0x01 , /* Action : 0x01 */
1197+ 0x01 , /* Type : Not use CheckSum */
1198+ 0x1C , /* File Length : 0x1C */
1199+ 0x37 , /* BT Annex Type : BT CFG */
1200+ 0x33 , /* Checksum : 0x71 */
1201+ 0x1C , /* Annex Length LSB: 0x001C */
1202+ 0x00 , /* Annex Length MSB: 0x001C */
1203+ 0x00 , /* Pointer For Next Annex[0] : 0x00000000 */
1204+ 0x00 , /* Pointer For Next Annex[1] : 0x00000000 */
1205+ 0x00 , /* Pointer For Next Annex[2] : 0x00000000 */
1206+ 0x00 , /* Pointer For Next Annex[3] : 0x00000000 */
1207+ 0x01 , /* Annex Version : 0x01 */
1208+ 0x81 , /* External Xtal Calibration Value : 0x7d */
1209+ 0x0D , /* Initial TX Power : 13 */
1210+ 0x07 , /* Front End Loss : 0x07 */
1211+ 0x28 , /* BT Options : */
1212+ /* BIT[0] Force Class 2 operation = 0 */
1213+ /* BIT[1] Disable Pwr-ctrl for class 2=0 */
1214+ /* BIT[2] MiscFlg(to indicate ext.XTAL)=0 */
1215+ /* BIT[3] Used Internal Sleep Clock = 1 */
1216+ /* BIT[4] BT AOA location support = 0 */
1217+ /* BIT[5] Force Class 1 mode = 1 */
1218+ /* BIT[7:6] Reserved */
1219+ 0x00 , /* AOANumberOfAntennas: 0x00 */
1220+ 0x00 , /* RSSI Golden Low : 0 */
1221+ 0x00 , /* RSSI Golden High : 0 */
1222+ 0xC0 , /* UART Baud Rate[0] : 0x002DC6C0(3000000) */
1223+ 0xC6 , /* UART Baud Rate[1] : 0x002DC6C0(3000000) */
1224+ 0x2D , /* UART Baud Rate[2] : 0x002DC6C0(3000000) */
1225+ 0x00 , /* UART Baud Rate[3] : 0x002DC6C0(3000000) */
1226+ 0x00 , /* BdAddress[0] : 0x000000000000 */
1227+ 0x00 , /* BdAddress[1] : 0x000000000000 */
1228+ 0x00 , /* BdAddress[2] : 0x000000000000 */
1229+ 0x00 , /* BdAddress[3] : 0x000000000000 */
1230+ 0x00 , /* BdAddress[4] : 0x000000000000 */
1231+ 0x00 , /* BdAddress[5] : 0x000000000000 */
1232+ 0xF0 , /* Encr_Key_Len[3:0]: MinEncrKeyLen = 0x0 */
1233+ /* ExEncrKeyLen = 0xF */
1234+ 0x00 , /* RegionCode : 0x00 */
1235+ #elif defined(CONFIG_BT_NXP_IW416 )
1236+ 0x00 , /* Sequence Number : 0x00 */
1237+ 0x01 , /* Action : 0x01 */
1238+ 0x01 , /* Type : Not use CheckSum */
1239+ 0x1C , /* File Length : 0x1C */
1240+ 0x37 , /* BT Annex Type : BT CFG */
1241+ 0x33 , /* Checksum : 0x71 */
1242+ 0x1C , /* Annex Length LSB: 0x001C */
1243+ 0x00 , /* Annex Length MSB: 0x001C */
1244+ 0x00 , /* Pointer For Next Annex[0] : 0x00000000 */
1245+ 0x00 , /* Pointer For Next Annex[1] : 0x00000000 */
1246+ 0x00 , /* Pointer For Next Annex[2] : 0x00000000 */
1247+ 0x00 , /* Pointer For Next Annex[3] : 0x00000000 */
1248+ 0x01 , /* Annex Version : 0x01 */
1249+ 0x00 , /* External Xtal Calibration Value */
1250+ 0x03 , /* Initial TX Power : 0x03 */
1251+ 0x03 , /* Front End Loss : 0x03 */
1252+ 0x00 , /* BT Options : */
1253+ /* BIT[0] Force Class 2 operation = 0 */
1254+ /* BIT[1] Disable Pwr Ctrl for class 2=0 */
1255+ /* BIT[2] MiscFlg(to indicate ext.XTAL)=0 */
1256+ /* BIT[3] Used Internal Sleep Clock = 0 */
1257+ /* BIT[4] BT AOA localtion support = 0 */
1258+ /* BIT[5] Force Class 1 mode = 0 */
1259+ /* BIT[7:6] Reserved */
1260+ 0x00 , /* AOANumberOfAntennas: 0x00 */
1261+ 0xBA , /* RSSI Golden Low : 0 */
1262+ 0xCE , /* RSSI Golden High : 0 */
1263+ 0xC0 , /* UART Baud Rate[0] : 0x002DC6C0(3000000) */
1264+ 0xC6 , /* UART Baud Rate[1] : 0x002DC6C0(3000000) */
1265+ 0x2D , /* UART Baud Rate[2] : 0x002DC6C0(3000000) */
1266+ 0x00 , /* UART Baud Rate[3] : 0x002DC6C0(3000000) */
1267+ 0x00 , /* BdAddress[0] : 0x000000000000 */
1268+ 0x00 , /* BdAddress[1] : 0x000000000000 */
1269+ 0x00 , /* BdAddress[2] : 0x000000000000 */
1270+ 0x00 , /* BdAddress[3] : 0x000000000000 */
1271+ 0x00 , /* BdAddress[4] : 0x000000000000 */
1272+ 0x00 , /* BdAddress[5] : 0x000000000000 */
1273+ 0xF0 , /* Encr_Key_Len[3:0]: MinEncrKeyLen = 0x0 */
1274+ /* ExEncrKeyLen = 0xF */
1275+ 0x00 , /* RegionCode : 0x00 */
1276+ #else
1277+ #error "BT Calibration data (annex-55) is not given for selected chipset"
1278+ #endif
1279+ };
1280+
1281+ if (IS_ENABLED (CONFIG_BT_HCI_HOST )) {
1282+ struct net_buf * buf ;
1283+
1284+ buf = bt_hci_cmd_create (opcode , HCI_CMD_STORE_BT_CAL_DATA_PARAM_LENGTH );
1285+ if (buf == NULL ) {
1286+ LOG_ERR ("Unable to allocate command buffer" );
1287+ return - ENOMEM ;
1288+ }
1289+
1290+ net_buf_add_mem (buf , hci_cal_data_annex55 , HCI_CMD_STORE_BT_CAL_DATA_PARAM_LENGTH );
1291+
1292+ ret = bt_hci_cmd_send_sync (opcode , buf , NULL );
1293+ if (ret ) {
1294+ LOG_ERR ("Failed to send set-calibration cmd (err %d)" , ret );
1295+ return ret ;
1296+ }
1297+
1298+ (void )k_msleep (CONFIG_BT_H4_NXP_CTLR_WAIT_TIME_AFTER_BAUDRATE_UPDATE );
1299+ }
1300+
1301+ return ret ;
1302+ }
1303+ #endif /*CONFIG_HCI_NXP_SET_CAL_DATA*/
1304+
1305+ #if defined(CONFIG_HCI_NXP_SET_CAL_DATA_ANNEX100 )
1306+
1307+ static int bt_nxp_set_calibration_data_annex100 (void )
1308+ {
1309+ int ret = 0 ;
1310+ const uint8_t hci_cal_data_annex100 [HCI_CMD_STORE_BT_CAL_DATA_PARAM_ANNEX100_LENGTH ] = {
1311+ #if defined(CONFIG_BT_NXP_NW612 )
1312+ 0x64 , /* Annex Type : 0x64 */
1313+ 0x83 , /* Checksum */
1314+ 0x10 , 0x00 , /* Length */
1315+ 0x00 , 0x00 , 0x00 , 0x00 , /* Pointer for next Annex-Structure */
1316+ 0x01 , /* Ext PA Present (1 bit) + */
1317+ /* Ext. PA Gain (7 bits) */
1318+ 0x00 , /* Ext Antenna Gain(1 bit) + */
1319+ /* Ext. Antenna Gain Val(4 bits) */
1320+ 0x04 , 0x00 , /* BT / LE Ext PA FEM CTRL Bitmask */
1321+ 0x01 , /* Ext LNA Present (1 bit) + */
1322+ /* Ext LNA Gain (7 bits) */
1323+ 0x00 , /* Reserved */
1324+ 0x04 , 0x00 /* BT / LE Ext LNA FEM CTRL Bitmask */
1325+ #elif defined(CONFIG_BT_NXP_IW416 )
1326+ 0x64 , /* Annex Type : 0x64 */
1327+ 0x83 , /* Checksum */
1328+ 0x10 , 0x00 , /* Length */
1329+ 0x00 , 0x00 , 0x00 , 0x00 , /* Pointer for next Annex-Structure */
1330+ 0x01 , /* Ext PA Present (1 bit) + */
1331+ /* Ext. PA Gain (7 bits) */
1332+ 0x00 , /* Ext Antenna Gain(1 bit) + */
1333+ /* Ext. Antenna Gain Val (4 bits) */
1334+ 0x0C , 0x00 , /* BT / LE Ext PA FEM CTRL Bitmask */
1335+ 0x01 , /* Ext LNA Present (1 bit) + */
1336+ /* Ext LNA Gain (7 bits) */
1337+ 0x00 , /* Reserved */
1338+ 0x0C , 0x00 /* BT/LE Ext LNA FEM CTRL Bitmask */
1339+ #else
1340+ #error "BT Calibration data (annex-100) is not given for selected chipset"
1341+ #endif
1342+ };
1343+
1344+ uint16_t opcode = BT_OP (BT_OGF_VS , HCI_CMD_STORE_BT_CAL_DATA_ANNEX100_OCF );
1345+
1346+ if (IS_ENABLED (CONFIG_BT_HCI_HOST )) {
1347+ struct net_buf * buf ;
1348+
1349+ buf = bt_hci_cmd_create (opcode , HCI_CMD_STORE_BT_CAL_DATA_PARAM_ANNEX100_LENGTH );
1350+ if (buf == NULL ) {
1351+ LOG_ERR ("Unable to allocate command buffer" );
1352+ return - ENOMEM ;
1353+ }
1354+
1355+ net_buf_add_mem (buf , hci_cal_data_annex100 ,
1356+ HCI_CMD_STORE_BT_CAL_DATA_PARAM_ANNEX100_LENGTH );
1357+
1358+ ret = bt_hci_cmd_send_sync (opcode , buf , NULL );
1359+ if (ret ) {
1360+ LOG_ERR ("Failed to send set-calibration cmd (err %d)" , ret );
1361+ return ret ;
1362+ }
1363+ }
1364+
1365+ return ret ;
1366+ }
1367+ #endif /* defined(CONFIG_HCI_NXP_SET_CAL_DATA_ANNEX100) */
1368+
11741369int bt_hci_transport_setup (const struct device * dev )
11751370{
11761371 int ret = 0 ;
@@ -1231,6 +1426,7 @@ int bt_h4_vnd_setup(const struct device *dev)
12311426 flowcontrol_of_hci = (bool )DT_PROP_OR (DT_DRV_INST (0 ), hw_flow_control , false);
12321427
12331428 if (operation_speed == default_speed ) {
1429+ fw_upload .is_setup_done = true;
12341430 return 0 ;
12351431 }
12361432
@@ -1240,7 +1436,7 @@ int bt_h4_vnd_setup(const struct device *dev)
12401436 return err ;
12411437 }
12421438
1243- /* BT waiting time after controller bandrate updated */
1439+ /* BT waiting time after controller bandrate updated */
12441440 (void )k_msleep (CONFIG_BT_H4_NXP_CTLR_WAIT_TIME_AFTER_BAUDRATE_UPDATE );
12451441 }
12461442
@@ -1250,7 +1446,21 @@ int bt_h4_vnd_setup(const struct device *dev)
12501446 return err ;
12511447 }
12521448
1253- fw_upload .is_setup_done = true;
1449+ if (!fw_upload .is_setup_done ) {
1450+ err = bt_nxp_set_calibration_data_annex55 ();
1451+ if (err ) {
1452+ LOG_ERR ("Fail to load annex-55 calibration data" );
1453+ return err ;
1454+ }
1455+
1456+ err = bt_nxp_set_calibration_data_annex100 ();
1457+ if (err ) {
1458+ LOG_ERR ("Fail to load annex-100 calibration data" );
1459+ return err ;
1460+ }
1461+
1462+ fw_upload .is_setup_done = true;
1463+ }
12541464
12551465 return 0 ;
12561466}
0 commit comments