diff --git a/components/bt/host/bluedroid/Kconfig.in b/components/bt/host/bluedroid/Kconfig.in index edf146769c..cb2b1dc4ba 100644 --- a/components/bt/host/bluedroid/Kconfig.in +++ b/components/bt/host/bluedroid/Kconfig.in @@ -1509,6 +1509,13 @@ config BT_BLE_FEAT_CONN_SUBRATING help Enable BLE connection subrating feature +config BT_BLE_FEAT_PAWR_EN + bool "Enable Periodic Advertisement with Response(PAwR)" + depends on (BT_BLE_50_FEATURES_SUPPORTED && ((BT_CONTROLLER_ENABLED && SOC_BLE_PAWR_SUPPORTED) || BT_CONTROLLER_DISABLED)) # NOERROR + default n + help + Enable BLE Periodic Advertisement with Response(PAwR) feature + config BT_BLE_VENDOR_HCI_EN bool "Enable BLE Vendor HCI command and event" depends on BT_BLE_ENABLED diff --git a/components/bt/host/bluedroid/api/esp_gap_ble_api.c b/components/bt/host/bluedroid/api/esp_gap_ble_api.c index d592b6b77f..d90d55cebe 100644 --- a/components/bt/host/bluedroid/api/esp_gap_ble_api.c +++ b/components/bt/host/bluedroid/api/esp_gap_ble_api.c @@ -2082,3 +2082,101 @@ esp_err_t esp_ble_gap_set_host_feature(uint16_t bit_num, uint8_t bit_val) == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); } #endif //#if (BLE_50_FEATURE_SUPPORT == TRUE) + +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +esp_err_t esp_ble_gap_set_periodic_adv_subevent_data(esp_ble_per_adv_subevent_data_params *subevent_data_params) +{ + btc_msg_t msg = {0}; + btc_ble_5_gap_args_t arg; + + if (esp_bluedroid_get_status() != ESP_BLUEDROID_STATUS_ENABLED) { + return ESP_ERR_INVALID_STATE; + } + + if ((!subevent_data_params) || (!subevent_data_params->subevent_params)) { + return ESP_ERR_NOT_ALLOWED; + } + + for (uint8_t i = 0; i < subevent_data_params->num_subevents_with_data; i++) + { + if (subevent_data_params->subevent_params[i].subevent_data_len && (subevent_data_params->subevent_params[i].subevent_data == NULL)) { + return ESP_ERR_NOT_ALLOWED; + } + } + + + msg.sig = BTC_SIG_API_CALL; + msg.pid = BTC_PID_GAP_BLE; + msg.act = BTC_GAP_BLE_SET_PA_SUBEVT_DATA; + + arg.per_adv_subevent_data_params.adv_handle = subevent_data_params->adv_handle; + arg.per_adv_subevent_data_params.num_subevents_with_data = subevent_data_params->num_subevents_with_data; + arg.per_adv_subevent_data_params.subevent_params = subevent_data_params->subevent_params; + + return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gap_args_t), btc_gap_ble_arg_deep_copy, btc_gap_ble_arg_deep_free) + == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); +} + +esp_err_t esp_ble_gap_set_periodic_adv_response_data(esp_ble_per_adv_response_data_params *rsp_data_params) +{ + btc_msg_t msg = {0}; + btc_ble_5_gap_args_t arg; + + if (esp_bluedroid_get_status() != ESP_BLUEDROID_STATUS_ENABLED) { + return ESP_ERR_INVALID_STATE; + } + + if (!rsp_data_params) { + return ESP_ERR_NOT_ALLOWED; + } + + if ((rsp_data_params->response_data == NULL) && rsp_data_params->response_data_len) { + return ESP_ERR_NOT_ALLOWED; + } + + msg.sig = BTC_SIG_API_CALL; + msg.pid = BTC_PID_GAP_BLE; + msg.act = BTC_GAP_BLE_SET_PA_RSP_DATA; + + arg.per_adv_response_data_params.sync_handle = rsp_data_params->sync_handle; + arg.per_adv_response_data_params.request_event = rsp_data_params->request_event; + arg.per_adv_response_data_params.request_subevent = rsp_data_params->request_subevent; + arg.per_adv_response_data_params.response_subevent = rsp_data_params->response_subevent; + arg.per_adv_response_data_params.response_slot = rsp_data_params->response_slot; + arg.per_adv_response_data_params.response_data_len = rsp_data_params->response_data_len; + arg.per_adv_response_data_params.response_data = rsp_data_params->response_data; + + return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gap_args_t), btc_gap_ble_arg_deep_copy, btc_gap_ble_arg_deep_free) + == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); +} + +esp_err_t esp_ble_gap_set_periodic_sync_subevent(esp_ble_per_sync_subevent_params *sync_subevent_params) +{ + btc_msg_t msg = {0}; + btc_ble_5_gap_args_t arg; + + if (esp_bluedroid_get_status() != ESP_BLUEDROID_STATUS_ENABLED) { + return ESP_ERR_INVALID_STATE; + } + + if (!sync_subevent_params) { + return ESP_ERR_NOT_ALLOWED; + } + + if ((sync_subevent_params->subevent == NULL) && sync_subevent_params->num_subevents_to_sync) { + return ESP_ERR_NOT_ALLOWED; + } + + msg.sig = BTC_SIG_API_CALL; + msg.pid = BTC_PID_GAP_BLE; + msg.act = BTC_GAP_BLE_SET_PA_SYNC_SUBEVT; + + arg.per_sync_subevent_params.sync_handle = sync_subevent_params->sync_handle; + arg.per_sync_subevent_params.periodic_adv_properties = sync_subevent_params->periodic_adv_properties; + arg.per_sync_subevent_params.num_subevents_to_sync = sync_subevent_params->num_subevents_to_sync; + arg.per_sync_subevent_params.subevent = sync_subevent_params->subevent; + + return (btc_transfer_context(&msg, &arg, sizeof(btc_ble_gap_args_t), btc_gap_ble_arg_deep_copy, btc_gap_ble_arg_deep_free) + == BT_STATUS_SUCCESS ? ESP_OK : ESP_FAIL); +} +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) diff --git a/components/bt/host/bluedroid/api/include/api/esp_gap_ble_api.h b/components/bt/host/bluedroid/api/include/api/esp_gap_ble_api.h index 89b14f7b75..c23c403d3b 100644 --- a/components/bt/host/bluedroid/api/include/api/esp_gap_ble_api.h +++ b/components/bt/host/bluedroid/api/include/api/esp_gap_ble_api.h @@ -249,6 +249,11 @@ typedef enum { ESP_GAP_BLE_SET_COMMON_FACTOR_CMPL_EVT, /*!< When set the common factor complete, the event comes */ ESP_GAP_BLE_SET_SCH_LEN_CMPL_EVT, /*!< When set the scheduling length complete, the event comes */ ESP_GAP_BLE_SET_SCAN_CHAN_MAP_CMPL_EVT, /*!< When set the channel map for scanning complete, the event comes */ + ESP_GAP_BLE_SET_PERIODIC_ADV_SUBEVT_DATA_EVT, /*!< When BLE update periodic adv subevent data complete, the event comes */ + ESP_GAP_BLE_SET_PERIODIC_ADV_RESPONSE_DATA_EVT, /*!< When BLE update periodic adv response data complete, the event comes */ + ESP_GAP_BLE_SET_PERIODIC_SYNC_SUBEVT_EVT, /*!< When BLE update periodic sync subevent complete, the event comes */ + ESP_GAP_BLE_PERIODIC_ADV_SUBEVT_DATA_REQUEST_EVT, /*!< When Controller is ready to transmit one or more subevents and is requesting the advertising data for these subevents, the event comes*/ + ESP_GAP_BLE_PERIODIC_ADV_RESPONSE_REPORT_EVT, /*!< When one or more devices have responded to a periodic advertising subevent during a PAwR train, the event comes */ ESP_GAP_BLE_EVT_MAX, /*!< when maximum advertising event complete, the event comes */ } esp_gap_ble_cb_event_t; @@ -975,7 +980,25 @@ typedef struct { typedef struct { uint16_t interval_min; /*!< periodic advertising minimum interval */ uint16_t interval_max; /*!< periodic advertising maximum interval */ - uint8_t properties; /*!< periodic advertising properties */ + uint16_t properties; /*!< periodic advertising properties */ +#if (CONFIG_BT_BLE_FEAT_PAWR_EN) + uint8_t num_subevents; /*!< Number of subevents in the PAwR. Range: 0x00 to 0x80 + 0x00: Periodic Advertising without responses */ + uint8_t subevent_interval; /*!< Interval between subevents. + Range: 0x06 to 0xFF. + Time = N × 1.25 ms. + Time Range: 7.5 ms to 318.75 ms. */ + uint8_t rsp_slot_delay; /*!< Time between the advertising packet in a subevent and the first response slot. + Range: 0x01 to 0xFE. + Time = N × 1.25 ms. + Time Range: 1.25 ms to 317.5 ms. */ + uint8_t rsp_slot_spacing; /*!< Time between response slots. + Range: 0x02 to 0xFF. + Time = N × 0.125 ms. + Time Range: 0.25 ms to 31.875 ms */ + uint8_t num_rsp_slots; /*!< Number of subevent response slots + Range: 0x01 to 0xFF. */ +#endif // (CONFIG_BT_BLE_FEAT_PAWR_EN) } esp_ble_gap_periodic_adv_params_t; /** @@ -1044,6 +1067,10 @@ typedef struct { 0x02: AoD Constant Tone Extension with 2 μs slots 0xFF: No Constant Tone Extension */ #endif // BT_BLE_FEAT_CTE_EN +#if (CONFIG_BT_BLE_FEAT_PAWR_EN) + uint16_t periodic_evt_counter; /*!< The value of paEventCounter for the reported periodic advertising packet */ + uint8_t subevt; /*!< The subevent number */ +#endif // (CONFIG_BT_BLE_FEAT_PAWR_EN) esp_ble_gap_ext_adv_data_status_t data_status; /*!< periodic advertising data type*/ uint8_t data_length; /*!< periodic advertising data length */ uint8_t data[251]; /*!< periodic advertising data */ @@ -1221,6 +1248,70 @@ typedef struct { The supervision_timeout, in milliseconds, shall be greater than 2 × current connection interval × subrate_max × (max_latency + 1) */ } esp_ble_subrate_req_param_t; +/** +* @brief Periodic adv subevent parameters +*/ +typedef struct { + uint8_t subevent; /*!< The subevent index of the data contained in this command. Range: 0x00 to 0x7F */ + uint8_t response_slot_start; /*!< The first response slots to be used in this subevent */ + uint8_t response_slot_count; /*!< The number of response slots to be used */ + uint8_t subevent_data_len; /*!< The number of octets in the Subevent_Data parameter. Range: 0 to 251 */ + uint8_t *subevent_data; /*!< The advertising data to be transmitted in the subevent of the advertising set */ +} esp_ble_subevent_params; + +/** +* @brief Periodic adv subevent data parameters +*/ +typedef struct { + uint8_t adv_handle; /*!< Used to identify a periodic advertising train */ + uint8_t num_subevents_with_data; /*!< Number of subevent data in the command. Range: 0x0001 to 0x0F */ + esp_ble_subevent_params *subevent_params; /*!< Periodic adv subevent parameters */ +} esp_ble_per_adv_subevent_data_params; + +/** +* @brief Periodic adv response data parameters +*/ +typedef struct { + uint16_t sync_handle; /*!< Sync_Handle identifying the PAwR train */ + uint16_t request_event; /*!< The value of eventCounter for the periodic advertising packet that the Host is responding to */ + uint8_t request_subevent; /*!< The subevent for the periodic advertising packet that the Host is responding to */ + uint8_t response_subevent; /*!< Used to identify the subevent of the PAwR train. Range: 0x00 to 0x7F */ + uint8_t response_slot; /*!< Used to identify the response slot of the PAwR train. Range: 0x00 to 0xFF */ + uint8_t response_data_len; /*!< The number of octets in the Response_Data parameter. Range: 0 to 251 */ + uint8_t *response_data; /*!< Response data */ +} esp_ble_per_adv_response_data_params; + +/** +* @brief Periodic sync subevent parameters +*/ +typedef struct { + uint16_t sync_handle; /*!< Sync_Handle identifying the PAwR train */ + uint16_t periodic_adv_properties; /*!< Include TxPower in the advertising PDU */ + uint8_t num_subevents_to_sync; /*!< Number of subevents. Range: 0x01 to 0x80 */ + uint8_t *subevent; /*!< The subevent to synchronize with. Range 0x00 to 0x7F */ +} esp_ble_per_sync_subevent_params; + +/** +* @brief Periodic response information +*/ +typedef struct { + int8_t tx_power; /*!< Range: -127 to +20, Units: dBm + 0x7F: Tx Power information not available*/ + int8_t rssi; /*!< Range: -127 to +20. Units: dBm + 0x7F: RSSI is not available */ + uint8_t cte_type; /*!< cte type + 0x00: AoA Constant Tone Extension + 0x01: AoD Constant Tone Extension with 1 µs slots + 0x02: AoD Constant Tone Extension with 2 µs slots + 0xFF: No Constant Tone Extension*/ + uint8_t rsp_slot; /*!< The response slot the data was received in. */ + uint8_t data_status; /*!< Data status + 0x00: Data complete + 0x01: Data incomplete, more data to come + 0xFF: Failed to receive or listen for an AUX_SYNC_SUBEVENT_RSP PDU*/ + uint8_t data_len; /*!< Length of the Data field */ + uint8_t *data; /*!< Periodic advertising response data formatted as defined in [Vol 3] Part C, Section 11*/ +} esp_ble_pa_rsp_info; /** * @brief Gap callback parameters union @@ -1634,6 +1725,12 @@ typedef union { esp_ble_gap_phy_t adv_phy; /*!< periodic advertising phy type */ uint16_t period_adv_interval; /*!< periodic advertising interval */ uint8_t adv_clk_accuracy; /*!< periodic advertising clock accuracy */ +#if (CONFIG_BT_BLE_FEAT_PAWR_EN) + uint8_t num_subevt; /*!< Number of subevents, Range: 0x00 to 0x80 */ + uint8_t subevt_interval; /*!< Subevent interval, Time = N × 1.25 ms */ + uint8_t rsp_slot_delay; /*!< Response slot delay, Time = N × 1.25 ms */ + uint8_t rsp_slot_spacing; /*!< Response slot spacing, Time = N × 0.125 ms */ +#endif // (CONFIG_BT_BLE_FEAT_PAWR_EN) } periodic_adv_sync_estab; /*!< Event parameter of ESP_GAP_BLE_PERIODIC_ADV_SYNC_ESTAB_EVT */ /** * @brief ESP_GAP_BLE_PHY_UPDATE_COMPLETE_EVT @@ -1879,6 +1976,49 @@ typedef union { esp_bt_status_t status; /*!< Indicate host feature update success status */ } host_feature; /*!< Event parameter of ESP_GAP_BLE_SET_HOST_FEATURE_CMPL_EVT */ #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + /** + * @brief ESP_GAP_BLE_SET_PERIODIC_ADV_SUBEVT_DATA_EVT + */ + struct ble_pa_subevt_data_evt { + esp_bt_status_t status; /*!< Indicate periodic adv subevent data update success status */ + uint8_t adv_handle; /*!< Used to identify a periodic advertising train */ + } pa_subevt_data_evt; /*!< Event parameter of ESP_GAP_BLE_SET_PERIODIC_ADV_SUBEVT_DATA_EVT */ + /** + * @brief ESP_GAP_BLE_SET_PERIODIC_ADV_RESPONSE_DATA_EVT + */ + struct ble_pa_rsp_data_evt { + esp_bt_status_t status; /*!< Indicate periodic adv response data update success status */ + uint16_t sync_handle; /*!< identifying the periodic advertising train */ + } pa_rsp_data_evt; /*!< Event parameter of ESP_GAP_BLE_SET_PERIODIC_ADV_RESPONSE_DATA_EVT */ + /** + * @brief ESP_GAP_BLE_SET_PERIODIC_SYNC_SUBEVT_EVT + */ + struct ble_pa_sync_subevt_evt { + esp_bt_status_t status; /*!< Indicate periodic sync subevent update success status */ + uint16_t sync_handle; /*!< identifying the periodic advertising train */ + } pa_sync_subevt_evt; /*!< Event parameter of ESP_GAP_BLE_SET_PERIODIC_SYNC_SUBEVT_EVT */ + /** + * @brief ESP_GAP_BLE_PERIODIC_ADV_SUBEVT_DATA_REQUEST_EVT + */ + struct ble_pa_subevt_data_req_evt { + uint8_t adv_handle; /*!< Used to identify a periodic advertising train */ + uint8_t subevt_start; /*!< The first subevent that data is requested for.*/ + uint8_t subevt_data_count; /*!< The number of subevents that data is requested for.*/ + } pa_subevt_data_req_evt; /*!< Event parameter of ESP_GAP_BLE_PERIODIC_ADV_SUBEVT_DATA_REQUEST_EVT */ + /** + * @brief ESP_GAP_BLE_PERIODIC_ADV_RESPONSE_REPORT_EVT + */ + struct ble_pa_rsp_rpt_evt { + uint8_t adv_handle; /*!< Used to identify a periodic advertising train */ + uint8_t subevt; /*!< The subevent number */ + uint8_t tx_status; /*!< + 0x00 AUX_SYNC_SUBEVENT_IND packet was transmitted. + 0x01 AUX_SYNC_SUBEVENT_IND packet was not transmitted.*/ + uint8_t num_rsp; /*!< Number of responses in event */ + esp_ble_pa_rsp_info *pa_rsp_info; /*!< response information */ + } pa_rsp_rpt_evt; /*!< Event parameter of ESP_GAP_BLE_PERIODIC_ADV_RESPONSE_REPORT_EVT */ +#endif // #if (CONFIG_BT_BLE_FEAT_PAWR_EN == TRUE) } esp_ble_gap_cb_param_t; /** @@ -3317,6 +3457,49 @@ esp_err_t esp_ble_gap_subrate_request(esp_ble_subrate_req_param_t *subrate_req_p */ esp_err_t esp_ble_gap_set_host_feature(uint16_t bit_num, uint8_t bit_val); +/** + * @brief This function is used to set the data for one or more subevents of PAwR in reply to a PA subevent data request event. + * The data for a subevent shall be transmitted only once. + * + * + * @param[in] subevent_data_params: Periodic adv subevent data parameters. + * + * + * @return + * - ESP_OK : success + * - other : failed + * + */ +esp_err_t esp_ble_gap_set_periodic_adv_subevent_data(esp_ble_per_adv_subevent_data_params *subevent_data_params); + +/** + * @brief This function is used to set the data for a response slot in a specific subevent of the PAwR identified. + * The data for a response slot shall be transmitted only once. + * + * + * @param[in] rsp_data_params: Periodic adv response data parameters. + * + * + * @return + * - ESP_OK : success + * - other : failed + */ +esp_err_t esp_ble_gap_set_periodic_adv_response_data(esp_ble_per_adv_response_data_params *rsp_data_params); + +/** + * @brief This function is used to instruct the Controller to synchronize with a subset of the subevents within a PAwR train, + * listen for packets sent by the peer device and pass any received data up to the Host. + * + * + * @param[in] sync_subevent_params: Periodic sync subevent parameters. + * + * + * @return + * - ESP_OK : success + * - other : failed + */ +esp_err_t esp_ble_gap_set_periodic_sync_subevent(esp_ble_per_sync_subevent_params *sync_subevent_params); + #ifdef __cplusplus } #endif diff --git a/components/bt/host/bluedroid/bta/dm/bta_dm_act.c b/components/bt/host/bluedroid/bta/dm/bta_dm_act.c index fd7d665acc..5082201278 100644 --- a/components/bt/host/bluedroid/bta/dm/bta_dm_act.c +++ b/components/bt/host/bluedroid/bta/dm/bta_dm_act.c @@ -6347,6 +6347,25 @@ void bta_dm_ble_set_host_feature(tBTA_DM_MSG *p_data) } #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +void bta_dm_api_set_periodic_adv_subevt_data(tBTA_DM_MSG *p_data) +{ + BTM_BleSetPaSubeventData(p_data->pa_subevt_data.adv_handle, p_data->pa_subevt_data.num_subevents_with_data, (uint8_t *)(p_data->pa_subevt_data.subevent_params)); +} + +void bta_dm_api_set_periodic_adv_response_data(tBTA_DM_MSG *p_data) +{ + BTM_BleSetPaResponseData(p_data->pa_rsp_data.sync_handle, p_data->pa_rsp_data.request_event, p_data->pa_rsp_data.request_subevent, + p_data->pa_rsp_data.rsp_subevent, p_data->pa_rsp_data.rsp_slot, p_data->pa_rsp_data.rsp_data_len, + p_data->pa_rsp_data.rsp_data); +} + +void bta_dm_api_set_periodic_sync_subevt(tBTA_DM_MSG *p_data) +{ + BTM_BleSetPaSyncSubevt(p_data->pa_sync_subevt.sync_handle, p_data->pa_sync_subevt.periodic_adv_properties, p_data->pa_sync_subevt.num_subevents_to_sync, p_data->pa_sync_subevt.subevent); +} +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) + #if (BLE_HOST_SETUP_STORAGE_EN == TRUE) /******************************************************************************* ** diff --git a/components/bt/host/bluedroid/bta/dm/bta_dm_api.c b/components/bt/host/bluedroid/bta/dm/bta_dm_api.c index 08510894e6..65f564ac08 100644 --- a/components/bt/host/bluedroid/bta/dm/bta_dm_api.c +++ b/components/bt/host/bluedroid/bta/dm/bta_dm_api.c @@ -3169,6 +3169,77 @@ void BTA_DmBleGapSetHostFeature(uint16_t bit_num, uint8_t bit_val) } #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +void BTA_DmBleGapSetPASubevtData(uint8_t adv_handle, uint8_t num_subevents_with_data, uint8_t *subevent_params) +{ + tBTA_DM_API_BLE_PA_SUBEVENT_DATA *p_msg; + tBTA_BLE_SUBEVENT_PARAMS *p_subevent_params = (tBTA_BLE_SUBEVENT_PARAMS*)subevent_params; + + if ((p_msg = (tBTA_DM_API_BLE_PA_SUBEVENT_DATA *)osi_malloc(sizeof(tBTA_DM_API_BLE_PA_SUBEVENT_DATA) + num_subevents_with_data * sizeof(tBTA_DM_API_BLE_SUBEVENT_PARAMS))) + != NULL) { + p_msg->hdr.event = BTA_DM_API_SET_PA_SUBEVT_DATA; + p_msg->adv_handle = adv_handle; + p_msg->num_subevents_with_data = num_subevents_with_data; + p_msg->subevent_params = (tBTA_DM_API_BLE_SUBEVENT_PARAMS *)(p_msg + 1); + for (uint8_t i = 0; i < num_subevents_with_data; i++) + { + p_msg->subevent_params[i].subevent = p_subevent_params[i].subevent; + p_msg->subevent_params[i].response_slot_start = p_subevent_params[i].response_slot_start; + p_msg->subevent_params[i].response_slot_count = p_subevent_params[i].response_slot_count; + p_msg->subevent_params[i].subevent_data_len = p_subevent_params[i].subevent_data_len; + memcpy(&(p_msg->subevent_params[i].subevent_data), p_subevent_params[i].subevent_data, p_subevent_params[i].subevent_data_len); + } + + bta_sys_sendmsg(p_msg); + } +} + +void BTA_DmBleGapSetPeriodicAdvRspData(uint16_t sync_handle, uint16_t request_event, uint8_t request_subevent, + uint8_t rsp_subevent, uint8_t rsp_slot, uint8_t rsp_data_len, uint8_t *rsp_data) +{ + tBTA_DM_API_BLE_PA_RSP_DATA *p_msg; + + if ((p_msg = (tBTA_DM_API_BLE_PA_RSP_DATA *)osi_malloc(sizeof(tBTA_DM_API_BLE_PA_RSP_DATA) + rsp_data_len)) + != NULL) { + p_msg->hdr.event = BTA_DM_API_SET_PA_RSP_DATA; + p_msg->sync_handle = sync_handle; + p_msg->request_event = request_event; + p_msg->request_subevent = request_subevent; + p_msg->rsp_subevent = rsp_subevent; + p_msg->rsp_slot = rsp_slot; + p_msg->rsp_data_len = rsp_data_len; + p_msg->rsp_data = (UINT8 *)(p_msg + 1); + if (rsp_data_len && rsp_data) { + memcpy(p_msg->rsp_data, rsp_data, rsp_data_len); + } else if (rsp_data_len) { + APPL_TRACE_ERROR("%s rsp_data is NULL", __func__); + } + bta_sys_sendmsg(p_msg); + } +} + +void BTA_DmBleGapSetPeriodicSyncSubevt(uint16_t sync_handle, uint16_t periodic_adv_properties, uint8_t num_subevents_to_sync, uint8_t *subevent) +{ + tBTA_DM_API_BLE_PA_SYNC_SUBEVT *p_msg; + + if ((p_msg = (tBTA_DM_API_BLE_PA_SYNC_SUBEVT *)osi_malloc(sizeof(tBTA_DM_API_BLE_PA_SYNC_SUBEVT) + num_subevents_to_sync)) + != NULL) { + p_msg->hdr.event = BTA_DM_API_SET_PA_SYNC_SUBEVT; + p_msg->sync_handle = sync_handle; + p_msg->periodic_adv_properties = periodic_adv_properties; + p_msg->num_subevents_to_sync = num_subevents_to_sync; + p_msg->subevent = (UINT8 *)(p_msg + 1); + if (num_subevents_to_sync && subevent) { + memcpy(p_msg->subevent, subevent, num_subevents_to_sync); + } else if (num_subevents_to_sync) { + APPL_TRACE_ERROR("%s subevent is NULL", __func__); + } + bta_sys_sendmsg(p_msg); + } +} + +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) + /******************************************************************************* ** ** Function BTA_VendorInit diff --git a/components/bt/host/bluedroid/bta/dm/bta_dm_main.c b/components/bt/host/bluedroid/bta/dm/bta_dm_main.c index 9fe5e7696e..362795cd32 100644 --- a/components/bt/host/bluedroid/bta/dm/bta_dm_main.c +++ b/components/bt/host/bluedroid/bta/dm/bta_dm_main.c @@ -344,6 +344,11 @@ const tBTA_DM_ACTION bta_dm_action[BTA_DM_MAX_EVT] = { #if (BLE_50_FEATURE_SUPPORT == TRUE) bta_dm_ble_set_host_feature, /* BTA_DM_API_SET_HOST_FEATURE_EVT */ #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + bta_dm_api_set_periodic_adv_subevt_data, /* BTA_DM_API_SET_PA_SUBEVT_DATA */ + bta_dm_api_set_periodic_adv_response_data, /* BTA_DM_API_SET_PA_RSP_DATA */ + bta_dm_api_set_periodic_sync_subevt, /* BTA_DM_API_SET_PA_SYNC_SUBEVT */ +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) }; diff --git a/components/bt/host/bluedroid/bta/dm/include/bta_dm_int.h b/components/bt/host/bluedroid/bta/dm/include/bta_dm_int.h index e724b37c3a..32b7e40a61 100644 --- a/components/bt/host/bluedroid/bta/dm/include/bta_dm_int.h +++ b/components/bt/host/bluedroid/bta/dm/include/bta_dm_int.h @@ -335,6 +335,11 @@ enum { #if (BLE_50_FEATURE_SUPPORT == TRUE) BTA_DM_API_SET_HOST_FEATURE_EVT, #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + BTA_DM_API_SET_PA_SUBEVT_DATA, + BTA_DM_API_SET_PA_RSP_DATA, + BTA_DM_API_SET_PA_SYNC_SUBEVT, +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) BTA_DM_MAX_EVT }; @@ -1156,6 +1161,51 @@ typedef struct { } tBTA_DM_API_SET_HOST_FEATURE; #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + +typedef struct { + UINT8 subevent; + UINT8 response_slot_start; + UINT8 response_slot_count; + UINT8 subevent_data_len; + UINT8 *subevent_data; +} tBTA_BLE_SUBEVENT_PARAMS; + +typedef struct { + UINT8 subevent; + UINT8 response_slot_start; + UINT8 response_slot_count; + UINT8 subevent_data_len; + UINT8 subevent_data[251]; +} tBTA_DM_API_BLE_SUBEVENT_PARAMS; + +typedef struct { + BT_HDR hdr; + UINT8 adv_handle; + UINT8 num_subevents_with_data; + tBTA_DM_API_BLE_SUBEVENT_PARAMS *subevent_params; +} tBTA_DM_API_BLE_PA_SUBEVENT_DATA; + +typedef struct { + BT_HDR hdr; + UINT16 sync_handle; + UINT16 request_event; + UINT8 request_subevent; + UINT8 rsp_subevent; + UINT8 rsp_slot; + UINT8 rsp_data_len; + UINT8 *rsp_data; +} tBTA_DM_API_BLE_PA_RSP_DATA; + +typedef struct { + BT_HDR hdr; + UINT16 sync_handle; + UINT16 periodic_adv_properties; + UINT8 num_subevents_to_sync; + UINT8 *subevent; +} tBTA_DM_API_BLE_PA_SYNC_SUBEVT; +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) + #endif /* BLE_INCLUDED */ #if (BLE_HOST_REMOVE_AN_ACL_EN == TRUE) @@ -1876,6 +1926,11 @@ typedef union { #if (BLE_50_FEATURE_SUPPORT == TRUE) tBTA_DM_API_SET_HOST_FEATURE set_host_feat; #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + tBTA_DM_API_BLE_PA_SUBEVENT_DATA pa_subevt_data; + tBTA_DM_API_BLE_PA_RSP_DATA pa_rsp_data; + tBTA_DM_API_BLE_PA_SYNC_SUBEVT pa_sync_subevt; +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) } tBTA_DM_MSG; @@ -2543,4 +2598,9 @@ void bta_dm_api_subrate_request(tBTA_DM_MSG *p_data); #if (BLE_50_FEATURE_SUPPORT == TRUE) extern void bta_dm_ble_set_host_feature(tBTA_DM_MSG *p_data); #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +void bta_dm_api_set_periodic_adv_subevt_data(tBTA_DM_MSG *p_data); +void bta_dm_api_set_periodic_adv_response_data(tBTA_DM_MSG *p_data); +void bta_dm_api_set_periodic_sync_subevt(tBTA_DM_MSG *p_data); +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) #endif /* BTA_DM_INT_H */ diff --git a/components/bt/host/bluedroid/bta/include/bta/bta_api.h b/components/bt/host/bluedroid/bta/include/bta/bta_api.h index aa1b632aad..b87d33acf3 100644 --- a/components/bt/host/bluedroid/bta/include/bta/bta_api.h +++ b/components/bt/host/bluedroid/bta/include/bta/bta_api.h @@ -1584,7 +1584,14 @@ typedef struct { typedef struct { UINT16 interval_min; UINT16 interval_max; - UINT8 properties; + UINT16 properties; +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + UINT8 num_subevents; + UINT8 subevent_interval; + UINT8 rsp_slot_delay; + UINT8 rsp_slot_spacing; + UINT8 num_rsp_slots; +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) } tBTA_DM_BLE_Periodic_Adv_Params; typedef struct { @@ -1701,6 +1708,14 @@ typedef struct { #define BTA_BLE_GAP_SET_HOST_FEATURE_EVT BTM_BLE_GAP_SET_HOST_FEATURE_EVT #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +#define BTA_BLE_GAP_SET_PERIODIC_ADV_SUBEVT_DATA_EVT BTM_BLE_GAP_SET_PERIODIC_ADV_SUBEVT_DATA_EVT +#define BTA_BLE_GAP_SET_PERIODIC_ADV_RESPONSE_DATA_EVT BTM_BLE_GAP_SET_PERIODIC_ADV_RESPONSE_DATA_EVT +#define BTA_BLE_GAP_SET_PERIODIC_SYNC_SUBEVT_EVT BTM_BLE_GAP_SET_PERIODIC_SYNC_SUBEVT_EVT +#define BTA_BLE_GAP_PERIODIC_ADV_SUBEVT_DATA_REQUEST_EVT BTM_BLE_GAP_PERIODIC_ADV_SUBEVT_DATA_REQUEST_EVT +#define BTA_BLE_GAP_PERIODIC_ADV_RESPONSE_REPORT_EVT BTM_BLE_GAP_PERIODIC_ADV_RESPONSE_REPORT_EVT +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) + #define BTA_DM_BLE_5_GAP_UNKNOWN_EVT BTM_BLE_5_GAP_UNKNOWN_EVT typedef tBTM_BLE_5_GAP_EVENT tBTA_DM_BLE_5_GAP_EVENT; @@ -3094,6 +3109,13 @@ void BTA_DmBleGapSubrateReqest(uint16_t conn_handle, uint16_t subrate_min, uint1 extern void BTA_DmBleGapSetHostFeature(uint16_t bit_num, uint8_t bit_val); #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +void BTA_DmBleGapSetPASubevtData(uint8_t adv_handle, uint8_t num_subevents_with_data, uint8_t *subevent_params); +void BTA_DmBleGapSetPeriodicAdvRspData(uint16_t sync_handle, uint16_t request_event, uint8_t request_subevent, + uint8_t rsp_subevent, uint8_t rsp_slot, uint8_t rsp_data_len, uint8_t *rsp_data); +void BTA_DmBleGapSetPeriodicSyncSubevt(uint16_t sync_handle, uint16_t periodic_adv_properties, uint8_t num_subevents_to_sync, uint8_t *subevent); +#endif// (BT_BLE_FEAT_PAWR_EN == TRUE) + /******************************************************************************* ** ** Function BTA_DmBleSetStorageParams diff --git a/components/bt/host/bluedroid/btc/profile/std/gap/btc_gap_ble.c b/components/bt/host/bluedroid/btc/profile/std/gap/btc_gap_ble.c index 67b54deea8..b517dea902 100644 --- a/components/bt/host/bluedroid/btc/profile/std/gap/btc_gap_ble.c +++ b/components/bt/host/bluedroid/btc/profile/std/gap/btc_gap_ble.c @@ -1155,6 +1155,10 @@ void btc_ble_5_gap_callback(tBTA_DM_BLE_5_GAP_EVENT event, #if (BLE_FEAT_CTE_EN == TRUE) param.period_adv_report.params.cte_type = params->period_adv_report.cte_type; #endif // #if (BLE_FEAT_CTE_EN == TRUE) + #if (BT_BLE_FEAT_PAWR_EN == TRUE) + param.period_adv_report.params.periodic_evt_counter = params->period_adv_report.periodic_evt_cnt; + param.period_adv_report.params.subevt = params->period_adv_report.subevt; + #endif // (BT_BLE_FEAT_PAWR_EN == TRUE) param.period_adv_report.params.data_status = params->period_adv_report.data_status; param.period_adv_report.params.data_length = params->period_adv_report.data_length; if (params->period_adv_report.data) { @@ -1179,6 +1183,12 @@ void btc_ble_5_gap_callback(tBTA_DM_BLE_5_GAP_EVENT event, param.periodic_adv_sync_estab.adv_phy = params->sync_estab.adv_phy; param.periodic_adv_sync_estab.period_adv_interval = params->sync_estab.period_adv_interval; param.periodic_adv_sync_estab.adv_clk_accuracy = params->sync_estab.adv_clk_accuracy; +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + param.periodic_adv_sync_estab.num_subevt = params->sync_estab.num_subevt; + param.periodic_adv_sync_estab.subevt_interval = params->sync_estab.subevt_interval; + param.periodic_adv_sync_estab.rsp_slot_delay = params->sync_estab.rsp_slot_delay; + param.periodic_adv_sync_estab.rsp_slot_spacing = params->sync_estab.rsp_slot_spacing; +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) break; } #endif // #if (BLE_50_EXTEND_SYNC_EN == TRUE) @@ -1287,12 +1297,43 @@ void btc_ble_5_gap_callback(tBTA_DM_BLE_5_GAP_EVENT event, param.host_feature.status = btc_btm_status_to_esp_status(params->status); break; #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + case BTA_BLE_GAP_SET_PERIODIC_ADV_SUBEVT_DATA_EVT: + msg.act = ESP_GAP_BLE_SET_PERIODIC_ADV_SUBEVT_DATA_EVT; + param.pa_subevt_data_evt.status = btc_btm_status_to_esp_status(params->pa_subevt_data_evt.status); + param.pa_subevt_data_evt.adv_handle = params->pa_subevt_data_evt.adv_handle; + break; + case BTA_BLE_GAP_SET_PERIODIC_ADV_RESPONSE_DATA_EVT: + msg.act = ESP_GAP_BLE_SET_PERIODIC_ADV_RESPONSE_DATA_EVT; + param.pa_rsp_data_evt.status = btc_btm_status_to_esp_status(params->pa_rsp_data_evt.status); + param.pa_rsp_data_evt.sync_handle = params->pa_rsp_data_evt.sync_handle; + break; + case BTA_BLE_GAP_SET_PERIODIC_SYNC_SUBEVT_EVT: + msg.act = ESP_GAP_BLE_SET_PERIODIC_SYNC_SUBEVT_EVT; + param.pa_sync_subevt_evt.status = btc_btm_status_to_esp_status(params->pa_sync_subevt_evt.status); + param.pa_sync_subevt_evt.sync_handle = params->pa_sync_subevt_evt.sync_handle; + break; + case BTA_BLE_GAP_PERIODIC_ADV_SUBEVT_DATA_REQUEST_EVT: + msg.act = ESP_GAP_BLE_PERIODIC_ADV_SUBEVT_DATA_REQUEST_EVT; + param.pa_subevt_data_req_evt.adv_handle = params->pa_subevent_data_req_evt.adv_handle; + param.pa_subevt_data_req_evt.subevt_start = params->pa_subevent_data_req_evt.subevt_start; + param.pa_subevt_data_req_evt.subevt_data_count = params->pa_subevent_data_req_evt.subevt_data_count; + break; + case BTA_BLE_GAP_PERIODIC_ADV_RESPONSE_REPORT_EVT: + msg.act = ESP_GAP_BLE_PERIODIC_ADV_RESPONSE_REPORT_EVT; + param.pa_rsp_rpt_evt.adv_handle = params->pa_rsp_rpt_evt.adv_handle; + param.pa_rsp_rpt_evt.subevt = params->pa_rsp_rpt_evt.subevt; + param.pa_rsp_rpt_evt.tx_status = params->pa_rsp_rpt_evt.tx_status; + param.pa_rsp_rpt_evt.num_rsp = params->pa_rsp_rpt_evt.num_rsp; + param.pa_rsp_rpt_evt.pa_rsp_info = (esp_ble_pa_rsp_info *)params->pa_rsp_rpt_evt.rsp_data_info; + break; +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) default: break; } ret = btc_transfer_context(&msg, ¶m, - sizeof(esp_ble_gap_cb_param_t), NULL, NULL); + sizeof(esp_ble_gap_cb_param_t), btc_gap_ble_cb_deep_copy, btc_gap_ble_cb_deep_free); if (ret != BT_STATUS_SUCCESS) { BTC_TRACE_ERROR("%s btc_transfer_context failed\n", __func__); @@ -1978,6 +2019,60 @@ void btc_gap_ble_arg_deep_copy(btc_msg_t *msg, void *p_dest, void *p_src) } break; } +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + case BTC_GAP_BLE_SET_PA_SUBEVT_DATA: { + btc_ble_5_gap_args_t *src = (btc_ble_5_gap_args_t *)p_src; + btc_ble_5_gap_args_t *dst = (btc_ble_5_gap_args_t *)p_dest; + if (src->per_adv_subevent_data_params.subevent_params) { + uint16_t params_len = src->per_adv_subevent_data_params.num_subevents_with_data * sizeof(esp_ble_subevent_params); + dst->per_adv_subevent_data_params.subevent_params = osi_malloc(params_len); + if (dst->per_adv_subevent_data_params.subevent_params) { + + for (uint8_t i = 0; i < src->per_adv_subevent_data_params.num_subevents_with_data; i++) + { + memcpy(&dst->per_adv_subevent_data_params.subevent_params[i], &src->per_adv_subevent_data_params.subevent_params[i], params_len); + // dst->per_adv_subevent_data_params.subevent_params[i].subevent = src->per_adv_subevent_data_params.subevent_params[i].subevent; + // dst->per_adv_subevent_data_params.subevent_params[i].response_slot_start = src->per_adv_subevent_data_params.subevent_params[i].response_slot_start; + // dst->per_adv_subevent_data_params.subevent_params[i].response_slot_count = src->per_adv_subevent_data_params.subevent_params[i].response_slot_count; + // dst->per_adv_subevent_data_params.subevent_params[i].subevent_data_len = src->per_adv_subevent_data_params.subevent_params[i].subevent_data_len; + dst->per_adv_subevent_data_params.subevent_params[i].subevent_data = osi_malloc(src->per_adv_subevent_data_params.subevent_params[i].subevent_data_len); + if (dst->per_adv_subevent_data_params.subevent_params[i].subevent_data) { + memcpy(dst->per_adv_subevent_data_params.subevent_params[i].subevent_data, src->per_adv_subevent_data_params.subevent_params[i].subevent_data, src->per_adv_subevent_data_params.subevent_params[i].subevent_data_len); + } else if (src->per_adv_subevent_data_params.subevent_params[i].subevent_data_len != 0) { + BTC_TRACE_ERROR("%s %d no mem\n",__func__, msg->act); + } + } + } + } + break; + } + case BTC_GAP_BLE_SET_PA_RSP_DATA: { + btc_ble_5_gap_args_t *src = (btc_ble_5_gap_args_t *)p_src; + btc_ble_5_gap_args_t *dst = (btc_ble_5_gap_args_t *)p_dest; + if (src->per_adv_response_data_params.response_data && src->per_adv_response_data_params.response_data_len) { + dst->per_adv_response_data_params.response_data = osi_malloc(src->per_adv_response_data_params.response_data_len); + if (dst->per_adv_response_data_params.response_data) { + memcpy(dst->per_adv_response_data_params.response_data, src->per_adv_response_data_params.response_data, src->per_adv_response_data_params.response_data_len); + } else { + BTC_TRACE_ERROR("%s %d no mem\n",__func__, msg->act); + } + } + break; + } + case BTC_GAP_BLE_SET_PA_SYNC_SUBEVT: { + btc_ble_5_gap_args_t *src = (btc_ble_5_gap_args_t *)p_src; + btc_ble_5_gap_args_t *dst = (btc_ble_5_gap_args_t *)p_dest; + if (src->per_sync_subevent_params.subevent && src->per_sync_subevent_params.num_subevents_to_sync) { + dst->per_sync_subevent_params.subevent = osi_malloc(src->per_sync_subevent_params.num_subevents_to_sync); + if (dst->per_sync_subevent_params.subevent) { + memcpy(dst->per_sync_subevent_params.subevent, src->per_sync_subevent_params.subevent, src->per_sync_subevent_params.num_subevents_to_sync); + } else { + BTC_TRACE_ERROR("%s %d no mem\n",__func__, msg->act); + } + } + break; + } +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) default: BTC_TRACE_ERROR("Unhandled deep copy %d\n", msg->act); break; @@ -2014,6 +2109,34 @@ void btc_gap_ble_cb_deep_copy(btc_msg_t *msg, void *p_dest, void *p_src) } break; } +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + case ESP_GAP_BLE_PERIODIC_ADV_RESPONSE_REPORT_EVT: + if (src->pa_rsp_rpt_evt.pa_rsp_info) { + dst->pa_rsp_rpt_evt.pa_rsp_info = osi_malloc(src->pa_rsp_rpt_evt.num_rsp * sizeof(esp_ble_pa_rsp_info)); + if (dst->pa_rsp_rpt_evt.pa_rsp_info) { + for (UINT8 i = 0; i < src->pa_rsp_rpt_evt.num_rsp; i++) + { + dst->pa_rsp_rpt_evt.pa_rsp_info[i].tx_power = src->pa_rsp_rpt_evt.pa_rsp_info[i].tx_power; + dst->pa_rsp_rpt_evt.pa_rsp_info[i].rssi = src->pa_rsp_rpt_evt.pa_rsp_info[i].rssi; + dst->pa_rsp_rpt_evt.pa_rsp_info[i].cte_type = src->pa_rsp_rpt_evt.pa_rsp_info[i].cte_type; + dst->pa_rsp_rpt_evt.pa_rsp_info[i].rsp_slot = src->pa_rsp_rpt_evt.pa_rsp_info[i].rsp_slot; + dst->pa_rsp_rpt_evt.pa_rsp_info[i].data_status = src->pa_rsp_rpt_evt.pa_rsp_info[i].data_status; + dst->pa_rsp_rpt_evt.pa_rsp_info[i].data_len = src->pa_rsp_rpt_evt.pa_rsp_info[i].data_len; + if (src->pa_rsp_rpt_evt.pa_rsp_info[i].data_len) { + dst->pa_rsp_rpt_evt.pa_rsp_info[i].data = osi_malloc(src->pa_rsp_rpt_evt.pa_rsp_info[i].data_len); + if (dst->pa_rsp_rpt_evt.pa_rsp_info[i].data) { + memcpy(dst->pa_rsp_rpt_evt.pa_rsp_info[i].data, src->pa_rsp_rpt_evt.pa_rsp_info[i].data, src->pa_rsp_rpt_evt.pa_rsp_info[i].data_len); + } else { + BTC_TRACE_ERROR("%s, data, no enough memory.", __func__); + } + } + } + } else { + BTC_TRACE_ERROR("%s, pa_rsp_info, no enough memory.", __func__); + } + } + break; +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) default: BTC_TRACE_ERROR("%s, Unhandled deep copy %d\n", __func__, msg->act); break; @@ -2136,6 +2259,35 @@ void btc_gap_ble_arg_deep_free(btc_msg_t *msg) break; } break; +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + case BTC_GAP_BLE_SET_PA_SUBEVT_DATA: { + struct per_adv_subevent_data_params_args *per_adv_subevent_data_params = &((btc_ble_5_gap_args_t *)msg->arg)->per_adv_subevent_data_params; + if (per_adv_subevent_data_params->subevent_params) { + for (uint8_t i = 0; i < per_adv_subevent_data_params->num_subevents_with_data; i++) + { + if (per_adv_subevent_data_params->subevent_params[i].subevent_data) { + osi_free(per_adv_subevent_data_params->subevent_params[i].subevent_data); + } + } + osi_free(per_adv_subevent_data_params->subevent_params); + } + break; + } + case BTC_GAP_BLE_SET_PA_RSP_DATA: { + uint8_t *response_data = ((btc_ble_5_gap_args_t *)msg->arg)->per_adv_response_data_params.response_data; + if (response_data) { + osi_free(response_data); + } + break; + } + case BTC_GAP_BLE_SET_PA_SYNC_SUBEVT: { + uint8_t *subevent = ((btc_ble_5_gap_args_t *)msg->arg)->per_sync_subevent_params.subevent; + if (subevent) { + osi_free(subevent); + } + break; + } +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) default: BTC_TRACE_DEBUG("Unhandled deep free %d\n", msg->act); break; @@ -2167,6 +2319,20 @@ void btc_gap_ble_cb_deep_free(btc_msg_t *msg) } break; } +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + case ESP_GAP_BLE_PERIODIC_ADV_RESPONSE_REPORT_EVT: + esp_ble_pa_rsp_info *pa_rsp_info = ((esp_ble_gap_cb_param_t *)msg->arg)->pa_rsp_rpt_evt.pa_rsp_info; + if (pa_rsp_info) { + uint8_t num_rsp = ((esp_ble_gap_cb_param_t *)msg->arg)->pa_rsp_rpt_evt.num_rsp; + for (UINT8 i = 0; i < num_rsp; i++) { + if (pa_rsp_info[i].data) { + osi_free(pa_rsp_info[i].data); + } + } + osi_free(pa_rsp_info); + } + break; +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) default: BTC_TRACE_DEBUG("Unhandled deep free %d", msg->act); break; @@ -2517,6 +2683,13 @@ void btc_gap_ble_call_handler(btc_msg_t *msg) params.interval_min = arg_5->peridic_adv_set_params.params.interval_min; params.interval_max = arg_5->peridic_adv_set_params.params.interval_max; params.properties = arg_5->peridic_adv_set_params.params.properties; +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + params.num_subevents = arg_5->peridic_adv_set_params.params.num_subevents; + params.subevent_interval = arg_5->peridic_adv_set_params.params.subevent_interval; + params.rsp_slot_delay = arg_5->peridic_adv_set_params.params.rsp_slot_delay; + params.rsp_slot_spacing = arg_5->peridic_adv_set_params.params.rsp_slot_spacing; + params.num_rsp_slots = arg_5->peridic_adv_set_params.params.num_rsp_slots; +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) BTC_TRACE_DEBUG("BTC_GAP_BLE_SET_PERIODIC_ADV_PARAMS"); BTA_DmBleGapPeriodicAdvSetParams(arg_5->peridic_adv_set_params.instance, ¶ms); @@ -2725,6 +2898,18 @@ void btc_gap_ble_call_handler(btc_msg_t *msg) BTA_DmBleGapSetHostFeature(arg_5->set_host_feature_params.bit_num, arg_5->set_host_feature_params.bit_val); break; #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + case BTC_GAP_BLE_SET_PA_SUBEVT_DATA: + BTA_DmBleGapSetPASubevtData(arg_5->per_adv_subevent_data_params.adv_handle, arg_5->per_adv_subevent_data_params.num_subevents_with_data, (uint8_t *)(arg_5->per_adv_subevent_data_params.subevent_params)); + break; + case BTC_GAP_BLE_SET_PA_RSP_DATA: + BTA_DmBleGapSetPeriodicAdvRspData(arg_5->per_adv_response_data_params.sync_handle, arg_5->per_adv_response_data_params.request_event, arg_5->per_adv_response_data_params.request_subevent, + arg_5->per_adv_response_data_params.response_subevent, arg_5->per_adv_response_data_params.response_slot, arg_5->per_adv_response_data_params.response_data_len, arg_5->per_adv_response_data_params.response_data); + break; + case BTC_GAP_BLE_SET_PA_SYNC_SUBEVT: + BTA_DmBleGapSetPeriodicSyncSubevt(arg_5->per_sync_subevent_params.sync_handle, arg_5->per_sync_subevent_params.periodic_adv_properties, arg_5->per_sync_subevent_params.num_subevents_to_sync, arg_5->per_sync_subevent_params.subevent); + break; +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) default: break; } diff --git a/components/bt/host/bluedroid/btc/profile/std/include/btc_gap_ble.h b/components/bt/host/bluedroid/btc/profile/std/include/btc_gap_ble.h index 03b1e0885d..ae1b974f66 100644 --- a/components/bt/host/bluedroid/btc/profile/std/include/btc_gap_ble.h +++ b/components/bt/host/bluedroid/btc/profile/std/include/btc_gap_ble.h @@ -141,6 +141,11 @@ typedef enum { BTC_GAP_ACT_SET_HOST_FEATURE, #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) BTC_GAP_BLE_READ_CHANNEL_MAP, +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + BTC_GAP_BLE_SET_PA_SUBEVT_DATA, + BTC_GAP_BLE_SET_PA_RSP_DATA, + BTC_GAP_BLE_SET_PA_SYNC_SUBEVT, +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) } btc_gap_ble_act_t; /* btc_ble_gap_args_t */ @@ -531,9 +536,34 @@ typedef union { } subrate_req_param; #endif // #if (BLE_FEAT_CONN_SUBRATING == TRUE) struct set_host_feature_arg { - uint16_t bit_num; - uint8_t bit_val; - } set_host_feature_params; + uint16_t bit_num; + uint8_t bit_val; + } set_host_feature_params; +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + // BTC_GAP_BLE_SET_PA_SUBEVT_DATA + struct per_adv_subevent_data_params_args { + uint8_t adv_handle; + uint8_t num_subevents_with_data; + esp_ble_subevent_params *subevent_params; + } per_adv_subevent_data_params; + // BTC_GAP_BLE_SET_PA_RSP_DATA + struct per_adv_response_data_params_args { + uint16_t sync_handle; + uint16_t request_event; + uint8_t request_subevent; + uint8_t response_subevent; + uint8_t response_slot; + uint8_t response_data_len; + uint8_t *response_data; + } per_adv_response_data_params; + // BTC_GAP_BLE_SET_PA_SYNC_SUBEVT + struct per_sync_subevent_params_args { + uint16_t sync_handle; + uint16_t periodic_adv_properties; + uint8_t num_subevents_to_sync; + uint8_t *subevent; + } per_sync_subevent_params; +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) } btc_ble_5_gap_args_t; #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) diff --git a/components/bt/host/bluedroid/common/include/common/bluedroid_user_config.h b/components/bt/host/bluedroid/common/include/common/bluedroid_user_config.h index 16a6320dbe..e784919b57 100644 --- a/components/bt/host/bluedroid/common/include/common/bluedroid_user_config.h +++ b/components/bt/host/bluedroid/common/include/common/bluedroid_user_config.h @@ -364,6 +364,12 @@ #define UC_BT_BLE_FEAT_CONN_SUBRATING FALSE #endif +#ifdef CONFIG_BT_BLE_FEAT_PAWR_EN +#define UC_BT_BLE_FEAT_PAWR_EN CONFIG_BT_BLE_FEAT_PAWR_EN +#else +#define UC_BT_BLE_FEAT_PAWR_EN FALSE +#endif + #ifdef CONFIG_BT_BLE_VENDOR_HCI_EN #define UC_BT_BLE_VENDOR_HCI_EN CONFIG_BT_BLE_VENDOR_HCI_EN #else diff --git a/components/bt/host/bluedroid/common/include/common/bt_target.h b/components/bt/host/bluedroid/common/include/common/bt_target.h index 6ec7ec52ba..eb2a6b92bb 100644 --- a/components/bt/host/bluedroid/common/include/common/bt_target.h +++ b/components/bt/host/bluedroid/common/include/common/bt_target.h @@ -415,6 +415,12 @@ #define BLE_FEAT_CONN_SUBRATING FALSE #endif +#if (UC_BT_BLE_FEAT_PAWR_EN == TRUE) +#define BT_BLE_FEAT_PAWR_EN TRUE +#else +#define BT_BLE_FEAT_PAWR_EN FALSE +#endif + #if (UC_BT_BLE_VENDOR_HCI_EN == TRUE) #define BLE_VENDOR_HCI_EN TRUE #else diff --git a/components/bt/host/bluedroid/device/controller.c b/components/bt/host/bluedroid/device/controller.c index 4b68eb93c8..0364ba2ca9 100644 --- a/components/bt/host/bluedroid/device/controller.c +++ b/components/bt/host/bluedroid/device/controller.c @@ -31,7 +31,7 @@ #include "osi/future.h" #include "config/stack_config.h" #if (BLE_50_FEATURE_SUPPORT == TRUE) -const bt_event_mask_t BLE_EVENT_MASK = { "\x00\x00\x00\x07\xff\xff\xff\xff" }; +const bt_event_mask_t BLE_EVENT_MASK = { "\x00\x00\x00\xff\xff\xff\xff\xff" }; #else const bt_event_mask_t BLE_EVENT_MASK = { "\x00\x00\x00\x00\x00\x00\x06\x7f" }; #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) diff --git a/components/bt/host/bluedroid/stack/btm/btm_ble_5_gap.c b/components/bt/host/bluedroid/stack/btm/btm_ble_5_gap.c index 4b3372504e..bda51c25de 100644 --- a/components/bt/host/bluedroid/stack/btm/btm_ble_5_gap.c +++ b/components/bt/host/bluedroid/stack/btm/btm_ble_5_gap.c @@ -710,11 +710,20 @@ tBTM_STATUS BTM_BlePeriodicAdvSetParams(UINT8 instance, tBTM_BLE_Periodic_Adv_Pa goto end; } - if ((err= btsnd_hcic_ble_set_periodic_adv_params(instance, params->interval_min, +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + if ((err = btsnd_hcic_ble_set_periodic_adv_params_v2(instance, params->interval_min, params->interval_max, + params->properties, params->num_subevents, params->subevent_interval, + params->rsp_slot_delay, params->rsp_slot_spacing, params->num_rsp_slots)) != HCI_SUCCESS) { + BTM_TRACE_ERROR("LE PA SetParams_V2: cmd err=0x%x", err); + status = BTM_HCI_ERROR | err; + } +#else + if ((err = btsnd_hcic_ble_set_periodic_adv_params(instance, params->interval_min, params->interval_max, params->properties)) != HCI_SUCCESS) { BTM_TRACE_ERROR("LE PA SetParams: cmd err=0x%x", err); status = BTM_HCI_ERROR | err; } +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) end: @@ -1740,3 +1749,67 @@ tBTM_STATUS BTM_BleSetHostFeature(uint16_t bit_num, uint8_t bit_val) return status; } #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) + +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +void BTM_BleSetPaSubeventData(UINT8 adv_handle, UINT8 num_subevents_with_data, uint8_t *subevent_params) +{ + tBTM_STATUS status = BTM_SUCCESS; + tHCI_STATUS err = HCI_SUCCESS; + tBTM_BLE_5_GAP_CB_PARAMS cb_params = {0}; + + if ((err = btsnd_hcic_ble_set_periodic_adv_subevt_data(adv_handle, num_subevents_with_data, (ble_subevent_params *)subevent_params)) != HCI_SUCCESS) { + BTM_TRACE_ERROR("%s cmd err = 0x%x", __func__, err); + status = BTM_HCI_ERROR | err; + } + + cb_params.pa_subevt_data_evt.status = status; + cb_params.pa_subevt_data_evt.adv_handle = adv_handle; + + BTM_ExtBleCallbackTrigger(BTM_BLE_GAP_SET_PERIODIC_ADV_SUBEVT_DATA_EVT, &cb_params); +} + +void BTM_BleSetPaResponseData(UINT16 sync_handle, UINT16 req_evt, UINT8 req_subevt, UINT8 rsp_subevt, UINT8 rsp_slot, UINT8 rsp_data_len, UINT8 *rsp_data) +{ + tBTM_STATUS status = BTM_SUCCESS; + tHCI_STATUS err = HCI_SUCCESS; + tBTM_BLE_5_GAP_CB_PARAMS cb_params = {0}; + + if ((err = btsnd_hcic_ble_set_periodic_adv_rsp_data(sync_handle, req_evt, req_subevt, rsp_subevt, rsp_slot, rsp_data_len, rsp_data)) != HCI_SUCCESS) { + BTM_TRACE_ERROR("%s cmd err = 0x%x", __func__, err); + status = BTM_HCI_ERROR | err; + } + + cb_params.pa_rsp_data_evt.status = status; + cb_params.pa_rsp_data_evt.sync_handle = sync_handle; + + BTM_ExtBleCallbackTrigger(BTM_BLE_GAP_SET_PERIODIC_ADV_RESPONSE_DATA_EVT, &cb_params); +} + +void BTM_BleSetPaSyncSubevt(UINT16 sync_handle, UINT16 periodic_adv_properties, UINT8 num_subevents_to_sync, UINT8 *subevt) +{ + tBTM_STATUS status = BTM_SUCCESS; + tHCI_STATUS err = HCI_SUCCESS; + tBTM_BLE_5_GAP_CB_PARAMS cb_params = {0}; + + if ((err = btsnd_hcic_ble_set_periodic_sync_subevt(sync_handle, periodic_adv_properties, num_subevents_to_sync, subevt)) != HCI_SUCCESS) { + BTM_TRACE_ERROR("%s cmd err = 0x%x", __func__, err); + status = BTM_HCI_ERROR | err; + } + + cb_params.pa_sync_subevt_evt.status = status; + cb_params.pa_sync_subevt_evt.sync_handle = sync_handle; + + BTM_ExtBleCallbackTrigger(BTM_BLE_GAP_SET_PERIODIC_SYNC_SUBEVT_EVT, &cb_params); +} + +void btm_ble_pa_subevt_data_req_evt(tBTM_BLE_PA_SUBEVT_DATA_REQ_EVT *params) +{ + BTM_ExtBleCallbackTrigger(BTM_BLE_GAP_PERIODIC_ADV_SUBEVT_DATA_REQUEST_EVT, (tBTM_BLE_5_GAP_CB_PARAMS *)params); +} + +void btm_ble_pa_rsp_rpt_evt(tBTM_BLE_PA_RSP_REPORT_EVT *params) +{ + BTM_ExtBleCallbackTrigger(BTM_BLE_GAP_PERIODIC_ADV_RESPONSE_REPORT_EVT, (tBTM_BLE_5_GAP_CB_PARAMS *)params); +} + +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) diff --git a/components/bt/host/bluedroid/stack/btm/include/btm_ble_int.h b/components/bt/host/bluedroid/stack/btm/include/btm_ble_int.h index de25c6fa3e..e7fe12925d 100644 --- a/components/bt/host/bluedroid/stack/btm/include/btm_ble_int.h +++ b/components/bt/host/bluedroid/stack/btm/include/btm_ble_int.h @@ -606,6 +606,10 @@ void btm_ble_transmit_power_report_evt(tBTM_BLE_TRANS_POWER_REPORT_EVT *params); #if (BLE_FEAT_CONN_SUBRATING == TRUE) void btm_ble_subrate_change_evt(tBTM_BLE_SUBRATE_CHANGE_EVT *params); #endif // #if (BLE_FEAT_CONN_SUBRATING == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +void btm_ble_pa_subevt_data_req_evt(tBTM_BLE_PA_SUBEVT_DATA_REQ_EVT *params); +void btm_ble_pa_rsp_rpt_evt(tBTM_BLE_PA_RSP_REPORT_EVT *params); +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) /* #ifdef __cplusplus diff --git a/components/bt/host/bluedroid/stack/btu/btu_hcif.c b/components/bt/host/bluedroid/stack/btu/btu_hcif.c index 2ff53852e0..fddfb02615 100644 --- a/components/bt/host/bluedroid/stack/btu/btu_hcif.c +++ b/components/bt/host/bluedroid/stack/btu/btu_hcif.c @@ -161,8 +161,8 @@ static void btu_ble_phy_update_complete_evt(UINT8 *p); static void btu_ble_ext_adv_report_evt(UINT8 *p, UINT16 evt_len); #endif // #if (BLE_50_EXTEND_SCAN_EN == TRUE) #if (BLE_50_EXTEND_SYNC_EN == TRUE) -static void btu_ble_periodic_adv_sync_establish_evt(UINT8 *p); -static void btu_ble_periodic_adv_report_evt(UINT8 *p, UINT8 evt_len); +static void btu_ble_periodic_adv_sync_establish_evt(UINT8 *p, bool v2_evt); +static void btu_ble_periodic_adv_report_evt(UINT8 *p, UINT8 evt_len, bool v2_evt); static void btu_ble_periodic_adv_sync_lost_evt(UINT8 *p); #endif // #if (BLE_50_EXTEND_SYNC_EN == TRUE) #if (BLE_50_EXTEND_SCAN_EN == TRUE) @@ -202,7 +202,7 @@ static void btu_ble_accept_cis_req_cmd_status(UINT8 status); static void btu_ble_cis_request_evt(UINT8 *p); #endif // #if (BLE_FEAT_ISO_CIG_PERIPHERAL_EN == TRUE) #if (BLE_FEAT_ISO_CIG_EN == TRUE) -static void btu_ble_cis_established_evt(UINT8 *p); +static void btu_ble_cis_established_evt(UINT8 *p, bool v2_evt); static void btu_ble_cis_disconnected(UINT16 handle, UINT8 reason); #endif // #if (BLE_FEAT_ISO_CIG_EN == TRUE) @@ -228,6 +228,11 @@ static void btu_ble_transmit_power_report_evt(UINT8 *p); static void btu_ble_subrate_change_evt(UINT8 *p); #endif // #if (BLE_FEAT_CONN_SUBRATING == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +static void btu_ble_pa_subevt_data_request_evt(UINT8 *p); +static void btu_ble_pa_response_report_evt(UINT8 *p); +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) + #if (BLE_42_ADV_EN == TRUE) extern osi_sem_t adv_enable_sem; extern osi_sem_t adv_data_sem; @@ -493,10 +498,16 @@ void btu_hcif_process_event (UNUSED_ATTR UINT8 controller_id, BT_HDR *p_msg) #endif // #if (BLE_50_EXTEND_SCAN_EN == TRUE) #if (BLE_50_EXTEND_SYNC_EN == TRUE) case HCI_BLE_PERIOD_ADV_SYNC_ESTAB_EVT: - btu_ble_periodic_adv_sync_establish_evt(p); + btu_ble_periodic_adv_sync_establish_evt(p, false); + break; + case HCI_BLE_PERIOD_ADV_SYNC_ESTAB_EVT_V2: + btu_ble_periodic_adv_sync_establish_evt(p, true); break; case HCI_BLE_PERIOD_ADV_REPORT_EVT: - btu_ble_periodic_adv_report_evt(p, hci_evt_len); + btu_ble_periodic_adv_report_evt(p, hci_evt_len, false); + break; + case HCI_BLE_PERIOD_ADV_REPORT_EVT_V2: + btu_ble_periodic_adv_report_evt(p, hci_evt_len, true); break; case HCI_BLE_PERIOD_ADV_SYNC_LOST_EVT: btu_ble_periodic_adv_sync_lost_evt(p); @@ -527,8 +538,10 @@ void btu_hcif_process_event (UNUSED_ATTR UINT8 controller_id, BT_HDR *p_msg) #if (BLE_FEAT_ISO_EN == TRUE) #if (BLE_FEAT_ISO_CIG_EN == TRUE) case HCI_BLE_CIS_ESTABLISHED_V1_EVT: + btu_ble_cis_established_evt(p, false); + break; case HCI_BLE_CIS_ESTABLISHED_V2_EVT: - btu_ble_cis_established_evt(p); + btu_ble_cis_established_evt(p, true); break; #endif // #if (BLE_FEAT_ISO_CIG_EN == TRUE) #if (BLE_FEAT_ISO_CIG_PERIPHERAL_EN == TRUE) @@ -586,6 +599,14 @@ void btu_hcif_process_event (UNUSED_ATTR UINT8 controller_id, BT_HDR *p_msg) btu_ble_subrate_change_evt(p); break; #endif // #if (BLE_FEAT_CONN_SUBRATING == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + case HCI_BLE_PA_SUBEVT_DATA_REQUEST_EVT: + btu_ble_pa_subevt_data_request_evt(p); + break; + case HCI_BLE_PA_RESPONSE_REPORT_EVT: + btu_ble_pa_response_report_evt(p); + break; +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) } break; #endif /* BLE_INCLUDED */ @@ -2540,7 +2561,7 @@ static void btu_ble_ext_adv_report_evt(UINT8 *p, UINT16 evt_len) #endif // #if (BLE_50_EXTEND_SCAN_EN == TRUE) #if (BLE_50_EXTEND_SYNC_EN == TRUE) -static void btu_ble_periodic_adv_sync_establish_evt(UINT8 *p) +static void btu_ble_periodic_adv_sync_establish_evt(UINT8 *p, bool v2_evt) { tBTM_BLE_PERIOD_ADV_SYNC_ESTAB sync_estab = {0}; @@ -2557,15 +2578,24 @@ static void btu_ble_periodic_adv_sync_establish_evt(UINT8 *p) STREAM_TO_UINT8(sync_estab.adv_phy, p); STREAM_TO_UINT16(sync_estab.period_adv_interval, p); STREAM_TO_UINT8(sync_estab.adv_clk_accuracy, p); +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + if (v2_evt) { + STREAM_TO_UINT8(sync_estab.num_subevt, p); + STREAM_TO_UINT8(sync_estab.subevt_interval, p); + STREAM_TO_UINT8(sync_estab.rsp_slot_delay, p); + STREAM_TO_UINT8(sync_estab.rsp_slot_spacing, p); + } +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) btm_ble_periodic_adv_sync_establish_evt(&sync_estab); } -static void btu_ble_periodic_adv_report_evt(UINT8 *p, UINT8 evt_len) +static void btu_ble_periodic_adv_report_evt(UINT8 *p, UINT8 evt_len, bool v2_evt) { tBTM_PERIOD_ADV_REPORT adv_report = {0}; /* This parameter is intended to be used in a future feature. */ UINT8 unused = 0; + UINT8 min_len = MIN_BLE_PERIODIC_ADV_REPORT_LEN; if (!p) { HCI_TRACE_ERROR("%s, Invalid params.", __func__); @@ -2581,10 +2611,17 @@ static void btu_ble_periodic_adv_report_evt(UINT8 *p, UINT8 evt_len) STREAM_TO_UINT8(adv_report.tx_power, p); STREAM_TO_UINT8(adv_report.rssi, p); STREAM_TO_UINT8(adv_report.cte_type, p); +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + if (v2_evt) { + STREAM_TO_UINT16(adv_report.periodic_evt_cnt, p); + STREAM_TO_UINT8(adv_report.subevt, p); + min_len += 3; + } +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) STREAM_TO_UINT8(adv_report.data_status, p); STREAM_TO_UINT8(adv_report.data_length, p); - if ((evt_len - MIN_BLE_PERIODIC_ADV_REPORT_LEN) != adv_report.data_length) { + if ((evt_len - min_len) != adv_report.data_length) { HCI_TRACE_ERROR("%s, Invalid ev_len = %d is less than adv len = %d", __func__, evt_len, adv_report.data_length); return; } @@ -2742,7 +2779,7 @@ static void btu_ble_cis_disconnected(UINT16 handle, UINT8 reason) btm_ble_cis_disconnected_evt(&cis_disconnected_evt); } -static void btu_ble_cis_established_evt(UINT8 *p) +static void btu_ble_cis_established_evt(UINT8 *p, bool v2_evt) { HCI_TRACE_DEBUG("%s", __func__); tBTM_BLE_CIS_ESTABLISHED_CMPL cis_estab_evt = {0}; @@ -2769,12 +2806,14 @@ static void btu_ble_cis_established_evt(UINT8 *p) STREAM_TO_UINT16(cis_estab_evt.max_pdu_p_to_c, p); STREAM_TO_UINT16(cis_estab_evt.iso_interval, p); #if (BLE_FEAT_ISO_60_EN == TRUE) - STREAM_TO_UINT24(cis_estab_evt.sub_interval, p); - STREAM_TO_UINT16(cis_estab_evt.max_sdu_c_to_p, p); - STREAM_TO_UINT16(cis_estab_evt.max_sdu_p_to_c, p); - STREAM_TO_UINT24(cis_estab_evt.sdu_int_c_to_p, p); - STREAM_TO_UINT24(cis_estab_evt.sdu_int_p_to_c, p); - STREAM_TO_UINT8(cis_estab_evt.framing, p); + if (v2_evt) { + STREAM_TO_UINT24(cis_estab_evt.sub_interval, p); + STREAM_TO_UINT16(cis_estab_evt.max_sdu_c_to_p, p); + STREAM_TO_UINT16(cis_estab_evt.max_sdu_p_to_c, p); + STREAM_TO_UINT24(cis_estab_evt.sdu_int_c_to_p, p); + STREAM_TO_UINT24(cis_estab_evt.sdu_int_p_to_c, p); + STREAM_TO_UINT8(cis_estab_evt.framing, p); + } #endif // #if (BLE_FEAT_ISO_60_EN == TRUE) btm_ble_cis_established_evt(&cis_estab_evt); @@ -3084,6 +3123,74 @@ static void btu_ble_subrate_change_evt(UINT8 *p) } #endif // #if (BLE_FEAT_CONN_SUBRATING == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +static void btu_ble_pa_subevt_data_request_evt(UINT8 *p) +{ + tBTM_BLE_PA_SUBEVT_DATA_REQ_EVT pa_subevt_req_evt = {0}; + if (!p) { + HCI_TRACE_ERROR("%s, Invalid params.", __func__); + return; + } + + STREAM_TO_UINT8(pa_subevt_req_evt.adv_handle, p); + STREAM_TO_UINT8(pa_subevt_req_evt.subevt_start, p); + STREAM_TO_UINT8(pa_subevt_req_evt.subevt_data_count, p); + + btm_ble_pa_subevt_data_req_evt(&pa_subevt_req_evt); +} + +static void btu_ble_pa_response_report_evt(UINT8 *p) +{ + tBTM_BLE_PA_RSP_REPORT_EVT pa_rsp_rpt_evt = {0}; + if (!p) { + HCI_TRACE_ERROR("%s, Invalid params.", __func__); + return; + } + + STREAM_TO_UINT8(pa_rsp_rpt_evt.adv_handle, p); + STREAM_TO_UINT8(pa_rsp_rpt_evt.subevt, p); + STREAM_TO_UINT8(pa_rsp_rpt_evt.tx_status, p); + STREAM_TO_UINT8(pa_rsp_rpt_evt.num_rsp, p); + + pa_rsp_rpt_evt.rsp_data_info = osi_malloc(pa_rsp_rpt_evt.num_rsp * sizeof(tBTM_BLE_PA_RSP_DATA_INFO)); + if (pa_rsp_rpt_evt.rsp_data_info) + { + for (UINT8 i = 0; i < pa_rsp_rpt_evt.num_rsp; i++) + { + STREAM_TO_UINT8(pa_rsp_rpt_evt.rsp_data_info[i].tx_power, p); + STREAM_TO_UINT8(pa_rsp_rpt_evt.rsp_data_info[i].rssi, p); + STREAM_TO_UINT8(pa_rsp_rpt_evt.rsp_data_info[i].cte_type, p); + STREAM_TO_UINT8(pa_rsp_rpt_evt.rsp_data_info[i].rsp_slot, p); + STREAM_TO_UINT8(pa_rsp_rpt_evt.rsp_data_info[i].data_status, p); + STREAM_TO_UINT8(pa_rsp_rpt_evt.rsp_data_info[i].data_len, p); + if (pa_rsp_rpt_evt.rsp_data_info[i].data_len) { + pa_rsp_rpt_evt.rsp_data_info[i].data = osi_malloc(pa_rsp_rpt_evt.rsp_data_info[i].data_len); + if (pa_rsp_rpt_evt.rsp_data_info[i].data) { + STREAM_TO_ARRAY(pa_rsp_rpt_evt.rsp_data_info[i].data, p, pa_rsp_rpt_evt.rsp_data_info[i].data_len); + } else { + HCI_TRACE_ERROR("%s, no enough memory.", __func__); + } + } + } + } else { + HCI_TRACE_ERROR("%s, no memory.", __func__); + } + + btm_ble_pa_rsp_rpt_evt(&pa_rsp_rpt_evt); + + if (pa_rsp_rpt_evt.rsp_data_info) + { + for (UINT8 i = 0; i < pa_rsp_rpt_evt.num_rsp; i++) + { + if (pa_rsp_rpt_evt.rsp_data_info[i].data) { + osi_free(pa_rsp_rpt_evt.rsp_data_info[i].data); + } + } + osi_free(pa_rsp_rpt_evt.rsp_data_info); + } +} +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) + /********************************************** ** End of BLE Events Handler ***********************************************/ diff --git a/components/bt/host/bluedroid/stack/hcic/hciblecmds.c b/components/bt/host/bluedroid/stack/hcic/hciblecmds.c index 5ad13216f7..7947ef557f 100644 --- a/components/bt/host/bluedroid/stack/hcic/hciblecmds.c +++ b/components/bt/host/bluedroid/stack/hcic/hciblecmds.c @@ -1421,10 +1421,40 @@ UINT8 btsnd_hcic_ble_clear_adv_set(void) #endif // #if (BLE_50_EXTEND_ADV_EN == TRUE) #if (BLE_50_PERIODIC_ADV_EN == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +UINT8 btsnd_hcic_ble_set_periodic_adv_params_v2(UINT8 adv_handle, UINT16 interval_min, UINT16 interval_max, + UINT16 propertics, UINT8 num_subevents, UINT8 subevent_interval, + UINT8 rsp_slot_delay, UINT8 rsp_slot_spacing, UINT8 num_rsp_slots) +{ + BT_HDR *p; + UINT8 *pp; + HCI_TRACE_EVENT("%s, adv_handle = %d, interval_min = %d, interval_max = %d, propertics = %d num_subevents = %d subevent_interval = %d rsp_slot_delay %d rsp_slot_spacing %d num_rsp_slots %d", + __func__, adv_handle, interval_min, interval_max, propertics, num_subevents, subevent_interval, rsp_slot_delay, rsp_slot_spacing, num_rsp_slots); + + HCIC_BLE_CMD_CREATED(p, pp, HCIC_PARAM_SIZE_SET_PERIODIC_ADV_PARAMS_V2); + + UINT16_TO_STREAM(pp, HCI_BLE_SET_PERIOD_ADV_PARAMS_V2); + UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_SET_PERIODIC_ADV_PARAMS_V2); + + UINT8_TO_STREAM(pp, adv_handle); + UINT16_TO_STREAM(pp, interval_min); + UINT16_TO_STREAM(pp, interval_max); + UINT16_TO_STREAM(pp, propertics); + UINT8_TO_STREAM(pp, num_subevents); + UINT8_TO_STREAM(pp, subevent_interval); + UINT8_TO_STREAM(pp, rsp_slot_delay); + UINT8_TO_STREAM(pp, rsp_slot_spacing); + UINT8_TO_STREAM(pp, num_rsp_slots); + + return btu_hcif_send_cmd_sync(LOCAL_BR_EDR_CONTROLLER_ID, p); + +} + +#else UINT8 btsnd_hcic_ble_set_periodic_adv_params(UINT8 adv_handle, UINT16 interval_min, UINT16 interval_max, - UINT8 propertics) + UINT16 propertics) { BT_HDR *p; UINT8 *pp; @@ -1445,6 +1475,9 @@ UINT8 btsnd_hcic_ble_set_periodic_adv_params(UINT8 adv_handle, } +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) + + UINT8 btsnd_hcic_ble_set_periodic_adv_data(UINT8 adv_handle, UINT8 operation, UINT8 len, @@ -2808,3 +2841,114 @@ UINT8 btsnd_hcic_ble_set_host_feature(uint16_t bit_num, uint8_t bit_val) return btu_hcif_send_cmd_sync(LOCAL_BR_EDR_CONTROLLER_ID, p); } #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) + +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +UINT8 btsnd_hcic_ble_set_periodic_adv_subevt_data(UINT8 adv_handle, UINT8 num_subevents_with_data, ble_subevent_params *subevent_params) +{ + BT_HDR *p; + UINT8 *pp; + uint8_t param_len = 0; + + HCI_TRACE_DEBUG("hci set PA subevent data, adv_handle %d num_subevents_with_data %d", adv_handle, num_subevents_with_data); + + if (!subevent_params) { + HCI_TRACE_ERROR("%s error\n", __func__); + return HCI_ERR_ILLEGAL_PARAMETER_FMT; + } + param_len += HCIC_PARAM_SIZE_SET_PA_SUBEVT_DATA_PARAMS_LEN; + + for (UINT8 i = 0; i < num_subevents_with_data; i++) + { + HCI_TRACE_DEBUG("subevent_params: subevent %d response_slot_start %d response_slot_count %d subevent_data_len %d", + subevent_params[i].subevent, subevent_params[i].response_slot_start, subevent_params[i].response_slot_count, + subevent_params[i].subevent_data_len); + + if (subevent_params[i].subevent_data_len) { + esp_log_buffer_hex_internal("data", subevent_params[i].data, subevent_params[i].subevent_data_len, ESP_LOG_DEBUG); + } + + param_len += (4 + subevent_params->subevent_data_len); + } + + HCIC_BLE_CMD_CREATED(p, pp, param_len); + + pp = (UINT8 *)(p + 1); + + UINT16_TO_STREAM(pp, HCI_BLE_SET_PERIOD_ADV_SUBEVT_DATA); + UINT8_TO_STREAM(pp, param_len); + + UINT8_TO_STREAM(pp, adv_handle); + UINT8_TO_STREAM(pp, num_subevents_with_data); + for (UINT8 i = 0; i < num_subevents_with_data; i++) + { + UINT8_TO_STREAM(pp, subevent_params[i].subevent); + UINT8_TO_STREAM(pp, subevent_params[i].response_slot_start); + UINT8_TO_STREAM(pp, subevent_params[i].response_slot_count); + UINT8_TO_STREAM(pp, subevent_params[i].subevent_data_len); + if (subevent_params[i].subevent_data_len) { + ARRAY_TO_STREAM(pp, subevent_params[i].data, subevent_params[i].subevent_data_len); + } + } + + return btu_hcif_send_cmd_sync(LOCAL_BR_EDR_CONTROLLER_ID, p); +} + +UINT8 btsnd_hcic_ble_set_periodic_adv_rsp_data(UINT16 sync_handle, UINT16 req_evt, UINT8 req_subevt, UINT8 rsp_subevt, UINT8 rsp_slot, UINT8 rsp_data_len, UINT8 *rsp_data) +{ + BT_HDR *p; + UINT8 *pp; + + HCI_TRACE_DEBUG("hci set PA rsp data, sync_handle %d req_evt %d req_subevt %d rsp_subevt %d rsp_slot %d rsp_data_len %d", + sync_handle, req_evt, req_subevt, rsp_subevt, rsp_slot, rsp_data_len); + + HCIC_BLE_CMD_CREATED(p, pp, HCIC_PARAM_SIZE_SET_PA_RESPONSE_DATA_PARAMS_LEN + rsp_data_len); + + pp = (UINT8 *)(p + 1); + + UINT16_TO_STREAM(pp, HCI_BLE_SET_PERIOD_ADV_RSP_DATA); + UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_SET_PA_RESPONSE_DATA_PARAMS_LEN + rsp_data_len); + + UINT16_TO_STREAM(pp, sync_handle); + UINT16_TO_STREAM(pp, req_evt); + UINT8_TO_STREAM(pp, req_subevt); + UINT8_TO_STREAM(pp, rsp_subevt); + UINT8_TO_STREAM(pp, rsp_slot); + UINT8_TO_STREAM(pp, rsp_data_len); + + if (rsp_data) { + ARRAY_TO_STREAM(pp, rsp_data, rsp_data_len); + } + + return btu_hcif_send_cmd_sync(LOCAL_BR_EDR_CONTROLLER_ID, p); +} + +UINT8 btsnd_hcic_ble_set_periodic_sync_subevt(UINT16 sync_handle, UINT16 periodic_adv_properties, UINT8 num_subevents_to_sync, UINT8 *subevt) +{ + BT_HDR *p; + UINT8 *pp; + + HCI_TRACE_DEBUG("hci set PA sync subevent, sync_handle %d periodic_adv_properties %d num_subevents_to_sync %d", + sync_handle, periodic_adv_properties, num_subevents_to_sync); + for (UINT8 i = 0; i < num_subevents_to_sync; i++) + { + HCI_TRACE_DEBUG("subevt[%d] = %d", i, subevt[i]); + } + + HCIC_BLE_CMD_CREATED(p, pp, HCIC_PARAM_SIZE_SET_PA_SYNC_SUBEVT_PARAMS_LEN + num_subevents_to_sync); + + pp = (UINT8 *)(p + 1); + + UINT16_TO_STREAM(pp, HCI_BLE_SET_PERIOD_SYNC_SUBEVT); + UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_SET_PA_SYNC_SUBEVT_PARAMS_LEN + num_subevents_to_sync); + + UINT16_TO_STREAM(pp, sync_handle); + UINT16_TO_STREAM(pp, periodic_adv_properties); + UINT8_TO_STREAM(pp, num_subevents_to_sync); + for (UINT8 i = 0; i < num_subevents_to_sync; i++) + { + UINT8_TO_STREAM(pp, subevt[i]); + } + + return btu_hcif_send_cmd_sync(LOCAL_BR_EDR_CONTROLLER_ID, p); +} +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) diff --git a/components/bt/host/bluedroid/stack/include/stack/btm_ble_api.h b/components/bt/host/bluedroid/stack/include/stack/btm_ble_api.h index e696fe65cf..5e1dcbceed 100644 --- a/components/bt/host/bluedroid/stack/include/stack/btm_ble_api.h +++ b/components/bt/host/bluedroid/stack/include/stack/btm_ble_api.h @@ -808,7 +808,14 @@ typedef struct { typedef struct { UINT16 interval_min; UINT16 interval_max; - UINT8 properties; + UINT16 properties; +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + UINT8 num_subevents; + UINT8 subevent_interval; + UINT8 rsp_slot_delay; + UINT8 rsp_slot_spacing; + UINT8 num_rsp_slots; +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) } tBTM_BLE_Periodic_Adv_Params; typedef struct { @@ -1090,7 +1097,14 @@ typedef void (tBTM_SET_VENDOR_EVT_MASK_CBACK) (tBTM_STATUS status); #if (BLE_50_FEATURE_SUPPORT == TRUE) #define BTM_BLE_GAP_SET_HOST_FEATURE_EVT 51 #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) -#define BTM_BLE_5_GAP_UNKNOWN_EVT 52 +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +#define BTM_BLE_GAP_SET_PERIODIC_ADV_SUBEVT_DATA_EVT 52 +#define BTM_BLE_GAP_SET_PERIODIC_ADV_RESPONSE_DATA_EVT 53 +#define BTM_BLE_GAP_SET_PERIODIC_SYNC_SUBEVT_EVT 54 +#define BTM_BLE_GAP_PERIODIC_ADV_SUBEVT_DATA_REQUEST_EVT 55 +#define BTM_BLE_GAP_PERIODIC_ADV_RESPONSE_REPORT_EVT 56 +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) +#define BTM_BLE_5_GAP_UNKNOWN_EVT 57 typedef UINT8 tBTM_BLE_5_GAP_EVENT; #if (BLE_FEAT_ISO_EN == TRUE) @@ -1332,6 +1346,10 @@ typedef struct { UINT8 tx_power; INT8 rssi; UINT8 cte_type; +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + UINT16 periodic_evt_cnt; + UINT8 subevt; +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) tBTM_BLE_EXT_ADV_DATA_STATUS data_status; UINT8 data_length; UINT8 *data; @@ -1350,6 +1368,12 @@ typedef struct { UINT8 adv_phy; UINT16 period_adv_interval; UINT8 adv_clk_accuracy; +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + UINT8 num_subevt; + UINT8 subevt_interval; + UINT8 rsp_slot_delay; + UINT8 rsp_slot_spacing; +#endif // (BT_BLE_FEAT_PAWR_EN == TRUE) } tBTM_BLE_PERIOD_ADV_SYNC_ESTAB; typedef struct { @@ -1453,6 +1477,44 @@ typedef struct { } __attribute__((packed)) tBTM_BLE_SUBRATE_CHANGE_EVT; #endif // #if (BLE_FEAT_CONN_SUBRATING == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +typedef struct { + UINT8 status; + UINT8 adv_handle; +} __attribute__((packed)) tBTM_BLE_PA_SUBEVT_DATA_EVT; +typedef struct { + UINT8 status; + UINT16 sync_handle; +} __attribute__((packed)) tBTM_BLE_PA_RSP_DATA_EVT; +typedef struct { + UINT8 status; + UINT16 sync_handle; +} __attribute__((packed)) tBTM_BLE_PA_SYNC_SUBEVT_DATA_EVT; +typedef struct { + UINT8 adv_handle; + UINT8 subevt_start; + UINT8 subevt_data_count; +} __attribute__((packed)) tBTM_BLE_PA_SUBEVT_DATA_REQ_EVT; + +typedef struct { + INT8 tx_power; + INT8 rssi; + UINT8 cte_type; + UINT8 rsp_slot; + UINT8 data_status; + UINT8 data_len; + UINT8 *data; +} __attribute__((packed)) tBTM_BLE_PA_RSP_DATA_INFO; + +typedef struct { + UINT8 adv_handle; + UINT8 subevt; + UINT8 tx_status; + UINT8 num_rsp; + tBTM_BLE_PA_RSP_DATA_INFO *rsp_data_info; +} __attribute__((packed)) tBTM_BLE_PA_RSP_REPORT_EVT; +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) + #if (BLE_FEAT_ISO_EN == TRUE) #if (BLE_FEAT_ISO_BIG_BROCASTER_EN == TRUE) typedef struct { @@ -1819,6 +1881,13 @@ typedef union { #if (BLE_FEAT_CONN_SUBRATING == TRUE) tBTM_BLE_SUBRATE_CHANGE_EVT subrate_change_evt; #endif // #if (BLE_FEAT_CONN_SUBRATING == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) + tBTM_BLE_PA_SUBEVT_DATA_EVT pa_subevt_data_evt; + tBTM_BLE_PA_RSP_DATA_EVT pa_rsp_data_evt; + tBTM_BLE_PA_SYNC_SUBEVT_DATA_EVT pa_sync_subevt_evt; + tBTM_BLE_PA_SUBEVT_DATA_REQ_EVT pa_subevent_data_req_evt; + tBTM_BLE_PA_RSP_REPORT_EVT pa_rsp_rpt_evt; +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) } tBTM_BLE_5_GAP_CB_PARAMS; typedef struct { @@ -3371,7 +3440,15 @@ void BTM_BleSetDefaultSubrate(UINT16 subrate_min, UINT16 subrate_max, UINT16 max void BTM_BleSubrateRequest(UINT16 conn_handle, UINT16 subrate_min, UINT16 subrate_max, UINT16 max_latency, UINT16 continuation_number, UINT16 supervision_timeout); #endif // #if (BLE_FEAT_CONN_SUBRATING == TRUE) + #if (BLE_50_FEATURE_SUPPORT == TRUE) tBTM_STATUS BTM_BleSetHostFeature(uint16_t bit_num, uint8_t bit_val); #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) + +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +void BTM_BleSetPaSubeventData(UINT8 adv_handle, UINT8 num_subevents_with_data, uint8_t *subevent_params); +void BTM_BleSetPaResponseData(UINT16 sync_handle, UINT16 req_evt, UINT8 req_subevt, UINT8 rsp_subevt, UINT8 rsp_slot, UINT8 rsp_data_len, UINT8 *rsp_data); +void BTM_BleSetPaSyncSubevt(UINT16 sync_handle, UINT16 periodic_adv_properties, UINT8 num_subevents_to_sync, UINT8 *subevt); +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) + #endif diff --git a/components/bt/host/bluedroid/stack/include/stack/hcidefs.h b/components/bt/host/bluedroid/stack/include/stack/hcidefs.h index 23f9b3e6b8..81bfbe0f43 100644 --- a/components/bt/host/bluedroid/stack/include/stack/hcidefs.h +++ b/components/bt/host/bluedroid/stack/include/stack/hcidefs.h @@ -443,6 +443,13 @@ #define HCI_BLE_SUBRATE_REQUEST (0x007E | HCI_GRP_BLE_CMDS) #endif // #if (BLE_FEAT_CONN_SUBRATING == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +#define HCI_BLE_SET_PERIOD_ADV_SUBEVT_DATA (0x0082 | HCI_GRP_BLE_CMDS) +#define HCI_BLE_SET_PERIOD_ADV_RSP_DATA (0x0083 | HCI_GRP_BLE_CMDS) +#define HCI_BLE_SET_PERIOD_SYNC_SUBEVT (0x0084 | HCI_GRP_BLE_CMDS) +#define HCI_BLE_SET_PERIOD_ADV_PARAMS_V2 (0x0086 | HCI_GRP_BLE_CMDS) +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) + // Vendor OGF define #define HCI_VENDOR_OGF 0x3F @@ -918,6 +925,14 @@ #define HCI_BLE_SUBRATE_CHANGE_EVT 0x23 #endif // #if (BLE_FEAT_CONN_SUBRATING == TRUE) +#define HCI_BLE_PERIOD_ADV_SYNC_ESTAB_EVT_V2 0x24 +#define HCI_BLE_PERIOD_ADV_REPORT_EVT_V2 0x25 + +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +#define HCI_BLE_PA_SUBEVT_DATA_REQUEST_EVT 0x27 +#define HCI_BLE_PA_RESPONSE_REPORT_EVT 0x28 +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) + /* Definitions for LE Channel Map */ #define HCI_BLE_CHNL_MAP_SIZE 5 diff --git a/components/bt/host/bluedroid/stack/include/stack/hcimsgs.h b/components/bt/host/bluedroid/stack/include/stack/hcimsgs.h index 4ee07b4d40..9ebbebdf92 100644 --- a/components/bt/host/bluedroid/stack/include/stack/hcimsgs.h +++ b/components/bt/host/bluedroid/stack/include/stack/hcimsgs.h @@ -1013,7 +1013,7 @@ UINT8 btsnd_hcic_ble_clear_adv_set(void); UINT8 btsnd_hcic_ble_set_periodic_adv_params(UINT8 adv_handle, UINT16 interval_min, UINT16 interval_max, - UINT8 propertics); + UINT16 propertics); UINT8 btsnd_hcic_ble_set_periodic_adv_data(UINT8 adv_handle, UINT8 operation, @@ -1243,4 +1243,26 @@ UINT8 btsnd_hcic_ble_subrate_request(UINT16 conn_handle, UINT16 subrate_min, UIN UINT8 btsnd_hcic_ble_set_host_feature(uint16_t bit_num, uint8_t bit_val); #endif // #if (BLE_50_FEATURE_SUPPORT == TRUE) +#if (BT_BLE_FEAT_PAWR_EN == TRUE) +typedef struct { + uint8_t subevent; + uint8_t response_slot_start; + uint8_t response_slot_count; + uint8_t subevent_data_len; + uint8_t data[251]; +} ble_subevent_params; + +#define HCIC_PARAM_SIZE_SET_PA_SUBEVT_DATA_PARAMS_LEN 2 +#define HCIC_PARAM_SIZE_SET_PA_RESPONSE_DATA_PARAMS_LEN 8 +#define HCIC_PARAM_SIZE_SET_PA_SYNC_SUBEVT_PARAMS_LEN 5 + +#define HCIC_PARAM_SIZE_SET_PERIODIC_ADV_PARAMS_V2 12 +UINT8 btsnd_hcic_ble_set_periodic_adv_params_v2(UINT8 adv_handle, UINT16 interval_min, UINT16 interval_max, + UINT16 propertics, UINT8 num_subevents, UINT8 subevent_interval, + UINT8 rsp_slot_delay, UINT8 rsp_slot_spacing, UINT8 num_rsp_slots); +UINT8 btsnd_hcic_ble_set_periodic_adv_subevt_data(UINT8 adv_handle, UINT8 num_subevents_with_data, ble_subevent_params *subevent_params); +UINT8 btsnd_hcic_ble_set_periodic_adv_rsp_data(UINT16 sync_handle, UINT16 req_evt, UINT8 req_subevt, UINT8 rsp_subevt, UINT8 rsp_slot, UINT8 rsp_data_len, UINT8 *rsp_data); +UINT8 btsnd_hcic_ble_set_periodic_sync_subevt(UINT16 sync_handle, UINT16 periodic_adv_properties, UINT8 num_subevents_to_sync, UINT8 *subevt); +#endif // #if (BT_BLE_FEAT_PAWR_EN == TRUE) + #endif