#define ESP_LE_AUTH_REQ_SC_MITM_BOND (ESP_LE_AUTH_REQ_MITM | ESP_LE_AUTH_REQ_SC_ONLY | ESP_LE_AUTH_BOND) /*!< 1101 */ /* relate to BTM_LE_AUTH_REQ_SC_MITM_BOND in stack/btm_api.h */
typedef uint8_t esp_ble_auth_req_t; /*!< combination of the above bit pattern */
+#define ESP_BLE_ONLY_ACCEPT_SPECIFIED_AUTH_DISABLE 0
+#define ESP_BLE_ONLY_ACCEPT_SPECIFIED_AUTH_ENABLE 1
+
/* relate to BTM_IO_CAP_xxx in stack/btm_api.h */
#define ESP_IO_CAP_OUT 0 /*!< DisplayOnly */ /* relate to BTM_IO_CAP_OUT in stack/btm_api.h */
#define ESP_IO_CAP_IO 1 /*!< DisplayYesNo */ /* relate to BTM_IO_CAP_IO in stack/btm_api.h */
ESP_BLE_SM_MAX_KEY_SIZE,
ESP_BLE_SM_SET_STATIC_PASSKEY,
ESP_BLE_SM_CLEAR_STATIC_PASSKEY,
+ ESP_BLE_SM_ONLY_ACCEPT_SPECIFIED_SEC_AUTH,
ESP_BLE_SM_MAX_PARAM,
} esp_ble_sm_param_t;
uint8_t fail_reason; /*!< The HCI reason/error code for when success=FALSE */
esp_ble_addr_type_t addr_type; /*!< Peer device address type */
esp_bt_dev_type_t dev_type; /*!< Device type */
-} esp_ble_auth_cmpl_t; /*!< The ble authentication complite cb type */
+ esp_ble_auth_req_t auth_mode; /*!< authentication mode */
+} esp_ble_auth_cmpl_t; /*!< The ble authentication complete cb type */
/**
* @brief union associated with ble security
memset(&sec_event, 0, sizeof(tBTA_DM_SEC));
switch (event) {
- case BTM_LE_IO_REQ_EVT:
- // #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
-
+ case BTM_LE_IO_REQ_EVT: {
+ // #if (BT_SSP_INCLUDED == TRUE)
+ UINT8 enable = bta_dm_co_ble_get_accept_auth_enable();
+ UINT8 origin_auth = bta_dm_co_ble_get_auth_req();
+ BTM_BleSetAcceptAuthMode(enable, origin_auth);
bta_dm_co_ble_io_req(bda,
&p_data->io_req.io_cap,
&p_data->io_req.oob_data,
APPL_TRACE_EVENT("io mitm: %d oob_data:%d\n", p_data->io_req.auth_req, p_data->io_req.oob_data);
break;
+ }
case BTM_LE_SEC_REQUEST_EVT:
bdcpy(sec_event.ble_req.bd_addr, bda);
}
}
-
+ sec_event.auth_cmpl.auth_mode = p_data->complt.auth_mode;
if (bta_dm_cb.p_sec_cback) {
//bta_dm_cb.p_sec_cback(BTA_DM_AUTH_CMPL_EVT, &sec_event);
bta_dm_cb.p_sec_cback(BTA_DM_BLE_AUTH_CMPL_EVT, &sec_event);
#endif /* #if (defined(BTIF_INCLUDED) && BTIF_INCLUDED == TRUE) */
#if (defined BLE_INCLUDED && BLE_INCLUDED == TRUE && SMP_INCLUDED == TRUE)
#include "common/bte_appl.h"
+
+#define BTM_BLE_ONLY_ACCEPT_SPECIFIED_SEC_AUTH_DISABLE 0
+#define BTM_BLE_ONLY_ACCEPT_SPECIFIED_SEC_AUTH_ENABLE 1
+
tBTE_APPL_CFG bte_appl_cfg = {
#if SMP_INCLUDED == TRUE
BTA_LE_AUTH_REQ_SC_MITM_BOND, // Authentication requirements
BTM_LOCAL_IO_CAPS_BLE,
BTM_BLE_INITIATOR_KEY_SIZE,
BTM_BLE_RESPONDER_KEY_SIZE,
- BTM_BLE_MAX_KEY_SIZE
+ BTM_BLE_MAX_KEY_SIZE,
+ BTM_BLE_ONLY_ACCEPT_SPECIFIED_SEC_AUTH_DISABLE
};
#endif
#endif ///SMP_INCLUDED == TRUE
}
-void bta_dm_co_ble_set_io_cap(UINT8 ble_io_cap)
+void bta_dm_co_ble_set_io_cap(UINT8 ble_io_cap)
{
#if (SMP_INCLUDED == TRUE)
if(ble_io_cap < BTM_IO_CAP_MAX ) {
#endif ///SMP_INCLUDED == TRUE
}
-void bta_dm_co_ble_set_auth_req(UINT8 ble_auth_req)
+void bta_dm_co_ble_set_auth_req(UINT8 ble_auth_req)
{
#if (SMP_INCLUDED == TRUE)
bte_appl_cfg.ble_auth_req = ble_auth_req;
}
#endif ///SMP_INCLUDED == TRUE
}
+
+void bta_dm_co_ble_set_accept_auth_enable(UINT8 enable)
+{
+#if (SMP_INCLUDED == TRUE)
+ if (enable) {
+ enable = BTM_BLE_ONLY_ACCEPT_SPECIFIED_SEC_AUTH_ENABLE;
+ }
+ bte_appl_cfg.ble_accept_auth_enable = enable;
+#endif ///SMP_INCLUDED == TRUE
+}
+
+UINT8 bta_dm_co_ble_get_accept_auth_enable(void)
+{
+#if (SMP_INCLUDED == TRUE)
+ return bte_appl_cfg.ble_accept_auth_enable;
+#endif ///SMP_INCLUDED == TRUE
+ return 0;
+}
+
+UINT8 bta_dm_co_ble_get_auth_req(void)
+{
+#if (SMP_INCLUDED == TRUE)
+ return bte_appl_cfg.ble_auth_req;
+#endif ///SMP_INCLUDED == TRUE
+ return 0;
+}
+
#endif
UINT8 fail_reason; /* The HCI reason/error code for when success=FALSE */
tBLE_ADDR_TYPE addr_type; /* Peer device address type */
tBT_DEVICE_TYPE dev_type;
+ UINT8 auth_mode;
} tBTA_DM_AUTH_CMPL;
extern void bta_dm_co_ble_set_rsp_key_req(UINT8 rsp_key);
extern void bta_dm_co_ble_set_max_key_size(UINT8 ble_key_size);
+
+extern void bta_dm_co_ble_set_accept_auth_enable(UINT8 enable);
+
+extern UINT8 bta_dm_co_ble_get_accept_auth_enable(void);
+
+extern UINT8 bta_dm_co_ble_get_auth_req(void);
#endif
param.ble_security.auth_cmpl.key_present = p_data->auth_cmpl.key_present;
memcpy(param.ble_security.auth_cmpl.bd_addr, p_data->auth_cmpl.bd_addr, sizeof(BD_ADDR));
memcpy(param.ble_security.auth_cmpl.key, p_data->auth_cmpl.key, sizeof(LINK_KEY));
+ param.ble_security.auth_cmpl.auth_mode = p_data->auth_cmpl.auth_mode;
btc_dm_ble_auth_cmpl_evt(&p_data->auth_cmpl);
break;
}
BTA_DmBleSetStaticPasskey(false, 0);
break;
}
+ case ESP_BLE_SM_ONLY_ACCEPT_SPECIFIED_SEC_AUTH: {
+ uint8_t enable = 0;
+ STREAM_TO_UINT8(enable, value);
+ bta_dm_co_ble_set_accept_auth_enable(enable);
+ break;
+ }
default:
break;
}
UINT8 ble_init_key;
UINT8 ble_resp_key;
UINT8 ble_max_key_size;
+ UINT8 ble_accept_auth_enable;
#endif
} tBTE_APPL_CFG;
#endif
}
+/*******************************************************************************
+**
+** Function BTM_BleSetStaticPasskey
+**
+** Description This function is called to set static passkey
+**
+**
+** Parameters: add - set static passkey when add is TRUE
+** clear static passkey when add is FALSE
+** passkey - static passkey
+**
+**
+*******************************************************************************/
void BTM_BleSetStaticPasskey(BOOLEAN add, UINT32 passkey)
{
#if SMP_INCLUDED == TRUE
SMP_SetStaticPasskey(add, passkey);
#endif
}
+
+/*******************************************************************************
+**
+** Function BTM_BleSetAcceptAuthMode
+**
+** Description This function is called to set only accept specified Authentication
+**
+**
+** Parameters: enable - Whether to enable this function
+**
+** auth_mode - Authentication mode
+**
+**
+*******************************************************************************/
+void BTM_BleSetAcceptAuthMode(UINT8 enable, UINT8 auth_mode)
+{
+#if SMP_INCLUDED == TRUE
+ SMP_SetAcceptAuthMode(enable, auth_mode);
+#endif
+}
/*******************************************************************************
**
** Function BTM_BleConfirmReply
UINT8 sec_level;
BOOLEAN is_pair_cancel;
BOOLEAN smp_over_br;
+ tSMP_AUTH_REQ auth_mode;
} tBTM_LE_COMPLT;
#endif
*******************************************************************************/
void BTM_BleSetStaticPasskey(BOOLEAN add, UINT32 passkey);
+/*******************************************************************************
+**
+** Function BTM_BleSetAcceptAuthMode
+**
+** Description This function is called to set only accept specified Authentication
+**
+**
+** Parameters: enable - Whether to enable this function
+**
+** auth_mode - Authentication mode
+**
+**
+*******************************************************************************/
+void BTM_BleSetAcceptAuthMode(UINT8 enable, UINT8 auth_mode);
+
/*******************************************************************************
**
** Function BTM_BleConfirmReply
tSMP_SEC_LEVEL sec_level;
BOOLEAN is_pair_cancel;
BOOLEAN smp_over_br;
+ tSMP_AUTH_REQ auth_mode;
} tSMP_CMPL;
typedef struct {
*******************************************************************************/
extern void SMP_SetStaticPasskey (BOOLEAN add, UINT32 passkey);
+extern void SMP_SetAcceptAuthMode (UINT8 enable, UINT8 auth_mode);
+
/*******************************************************************************
**
** Function SMP_ConfirmReply
BOOLEAN wait_for_authorization_complete;
BOOLEAN use_static_passkey;
UINT32 static_passkey;
+ BOOLEAN accept_specified_sec_auth;
+ tSMP_AUTH_REQ origin_loc_auth_req;
} tSMP_CB;
/* Server Action functions are of this type */
smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &reason);
return;
}
+ if(p_cb->accept_specified_sec_auth) {
+ if((p_cb->origin_loc_auth_req & p_cb->peer_auth_req & p_cb->loc_auth_req) != p_cb->origin_loc_auth_req ) {
+ SMP_TRACE_ERROR("%s pairing failed - slave requires 0x%x auth but peer auth req 0x%x local auth req 0x%x",
+ __func__, p_cb->origin_loc_auth_req, p_cb->peer_auth_req, p_cb->loc_auth_req);
+ reason = SMP_PAIR_AUTH_FAIL;
+ smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &reason);
+ }
+ }
if (p_cb->selected_association_model == SMP_MODEL_SEC_CONN_OOB) {
if (smp_request_oob_data(p_cb)) {
return;
}
+ if (p_cb->accept_specified_sec_auth) {
+ if ((p_cb->origin_loc_auth_req & p_cb->peer_auth_req & p_cb->loc_auth_req) != p_cb->origin_loc_auth_req ) {
+ SMP_TRACE_ERROR("%s pairing failed - master requires 0x%x auth but peer auth req 0x%x local auth req 0x%x",
+ __func__, p_cb->origin_loc_auth_req, p_cb->peer_auth_req, p_cb->loc_auth_req);
+ reason = SMP_PAIR_AUTH_FAIL;
+ smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &reason);
+ }
+ }
+
if (p_cb->selected_association_model == SMP_MODEL_SEC_CONN_OOB) {
if (smp_request_oob_data(p_cb)) {
return;
return;
}
+/*******************************************************************************
+**
+** Function SMP_SetStaticPasskey
+**
+** Description This function is called to set static passkey
+**
+**
+** Parameters: add - set static passkey when add is TRUE
+** clear static passkey when add is FALSE
+** passkey - static passkey
+**
+**
+*******************************************************************************/
void SMP_SetStaticPasskey (BOOLEAN add, UINT32 passkey)
{
SMP_TRACE_DEBUG("static passkey %6d", passkey);
p_cb->use_static_passkey = false;
}
}
+
+/*******************************************************************************
+**
+** Function SMP_SetAcceptAuthMode
+**
+** Description This function is called to set only accept specified Authentication
+**
+**
+** Parameters: enable - Whether to enable this function
+**
+** auth_mode - Authentication mode
+**
+**
+*******************************************************************************/
+void SMP_SetAcceptAuthMode (UINT8 enable, UINT8 auth_mode)
+{
+ tSMP_CB *p_cb = & smp_cb;
+
+ p_cb->accept_specified_sec_auth = enable;
+ p_cb->origin_loc_auth_req = auth_mode;
+
+}
/*******************************************************************************
**
** Function SMP_ConfirmReply
evt_data.cmplt.reason = p_cb->status;
evt_data.cmplt.smp_over_br = p_cb->smp_over_br;
-
+ evt_data.cmplt.auth_mode = 0;
if (p_cb->status == SMP_SUCCESS) {
evt_data.cmplt.sec_level = p_cb->sec_level;
+ evt_data.cmplt.auth_mode = (p_cb->peer_auth_req & p_cb->loc_auth_req);
}
evt_data.cmplt.is_pair_cancel = FALSE;
return key_str;
}
+static char *esp_auth_req_to_str(esp_ble_auth_req_t auth_req)
+{
+ char *auth_str = NULL;
+ switch(auth_req) {
+ case ESP_LE_AUTH_NO_BOND:
+ auth_str = "ESP_LE_AUTH_NO_BOND";
+ break;
+ case ESP_LE_AUTH_BOND:
+ auth_str = "ESP_LE_AUTH_BOND";
+ break;
+ case ESP_LE_AUTH_REQ_MITM:
+ auth_str = "ESP_LE_AUTH_REQ_MITM";
+ break;
+ case ESP_LE_AUTH_REQ_SC_ONLY:
+ auth_str = "ESP_LE_AUTH_REQ_SC_ONLY";
+ break;
+ case ESP_LE_AUTH_REQ_SC_BOND:
+ auth_str = "ESP_LE_AUTH_REQ_SC_BOND";
+ break;
+ case ESP_LE_AUTH_REQ_SC_MITM:
+ auth_str = "ESP_LE_AUTH_REQ_SC_MITM";
+ break;
+ case ESP_LE_AUTH_REQ_SC_MITM_BOND:
+ auth_str = "ESP_LE_AUTH_REQ_SC_MITM_BOND";
+ break;
+ default:
+ auth_str = "INVALID BLE AUTH REQ";
+ break;
+ }
+
+ return auth_str;
+}
+
static void gattc_profile_event_handler(esp_gattc_cb_event_t event, esp_gatt_if_t gattc_if, esp_ble_gattc_cb_param_t *param)
{
esp_ble_gattc_cb_param_t *p_data = (esp_ble_gattc_cb_param_t *)param;
ESP_LOGI(GATTC_TAG, "Write char success ");
break;
case ESP_GATTC_DISCONNECT_EVT:
- ESP_LOGI(GATTC_TAG, "ESP_GATTC_DISCONNECT_EVT, reason = %d", p_data->disconnect.reason);
+ ESP_LOGI(GATTC_TAG, "ESP_GATTC_DISCONNECT_EVT, reason = 0x%x", p_data->disconnect.reason);
connect = false;
get_service = false;
break;
(bd_addr[4] << 8) + bd_addr[5]);
ESP_LOGI(GATTC_TAG, "address type = %d", param->ble_security.auth_cmpl.addr_type);
ESP_LOGI(GATTC_TAG, "pair status = %s",param->ble_security.auth_cmpl.success ? "success" : "fail");
+ if (!param->ble_security.auth_cmpl.success) {
+ ESP_LOGI(GATTC_TAG, "fail reason = 0x%x",param->ble_security.auth_cmpl.fail_reason);
+ } else {
+ ESP_LOGI(GATTC_TAG, "auth mode = %s",esp_auth_req_to_str(param->ble_security.auth_cmpl.auth_mode));
+ }
break;
}
case ESP_GAP_BLE_SCAN_RESULT_EVT: {
return key_str;
}
+static char *esp_auth_req_to_str(esp_ble_auth_req_t auth_req)
+{
+ char *auth_str = NULL;
+ switch(auth_req) {
+ case ESP_LE_AUTH_NO_BOND:
+ auth_str = "ESP_LE_AUTH_NO_BOND";
+ break;
+ case ESP_LE_AUTH_BOND:
+ auth_str = "ESP_LE_AUTH_BOND";
+ break;
+ case ESP_LE_AUTH_REQ_MITM:
+ auth_str = "ESP_LE_AUTH_REQ_MITM";
+ break;
+ case ESP_LE_AUTH_REQ_SC_ONLY:
+ auth_str = "ESP_LE_AUTH_REQ_SC_ONLY";
+ break;
+ case ESP_LE_AUTH_REQ_SC_BOND:
+ auth_str = "ESP_LE_AUTH_REQ_SC_BOND";
+ break;
+ case ESP_LE_AUTH_REQ_SC_MITM:
+ auth_str = "ESP_LE_AUTH_REQ_SC_MITM";
+ break;
+ case ESP_LE_AUTH_REQ_SC_MITM_BOND:
+ auth_str = "ESP_LE_AUTH_REQ_SC_MITM_BOND";
+ break;
+ default:
+ auth_str = "INVALID BLE AUTH REQ";
+ break;
+ }
+
+ return auth_str;
+}
+
static void show_bonded_devices(void)
{
int dev_num = esp_ble_get_bond_device_num();
ESP_LOGI(GATTS_TABLE_TAG, "pair status = %s",param->ble_security.auth_cmpl.success ? "success" : "fail");
if(!param->ble_security.auth_cmpl.success) {
ESP_LOGI(GATTS_TABLE_TAG, "fail reason = 0x%x",param->ble_security.auth_cmpl.fail_reason);
+ } else {
+ ESP_LOGI(GATTS_TABLE_TAG, "auth mode = %s",esp_auth_req_to_str(param->ble_security.auth_cmpl.auth_mode));
}
show_bonded_devices();
break;
esp_ble_set_encryption(param->connect.remote_bda, ESP_BLE_SEC_ENCRYPT_MITM);
break;
case ESP_GATTS_DISCONNECT_EVT:
- ESP_LOGI(GATTS_TABLE_TAG, "ESP_GATTS_DISCONNECT_EVT");
+ ESP_LOGI(GATTS_TABLE_TAG, "ESP_GATTS_DISCONNECT_EVT, disconnect reason 0x%x", param->disconnect.reason);
/* start advertising again when missing the connect */
esp_ble_gap_start_advertising(&heart_rate_adv_params);
break;
uint8_t rsp_key = ESP_BLE_ENC_KEY_MASK | ESP_BLE_ID_KEY_MASK;
//set static passkey
uint32_t passkey = 123456;
+ uint8_t auth_option = ESP_BLE_ONLY_ACCEPT_SPECIFIED_AUTH_DISABLE;
esp_ble_gap_set_security_param(ESP_BLE_SM_SET_STATIC_PASSKEY, &passkey, sizeof(uint32_t));
esp_ble_gap_set_security_param(ESP_BLE_SM_AUTHEN_REQ_MODE, &auth_req, sizeof(uint8_t));
esp_ble_gap_set_security_param(ESP_BLE_SM_IOCAP_MODE, &iocap, sizeof(uint8_t));
esp_ble_gap_set_security_param(ESP_BLE_SM_MAX_KEY_SIZE, &key_size, sizeof(uint8_t));
+ esp_ble_gap_set_security_param(ESP_BLE_SM_ONLY_ACCEPT_SPECIFIED_SEC_AUTH, &auth_option, sizeof(uint8_t));
/* If your BLE device act as a Slave, the init_key means you hope which types of key of the master should distribut to you,
and the response key means which key you can distribut to the Master;
If your BLE device act as a master, the response key means you hope which types of key of the slave should distribut to you,
break;
}
case ESP_GATTS_DISCONNECT_EVT:
- ESP_LOGI(GATTS_TAG, "ESP_GATTS_DISCONNECT_EVT");
+ ESP_LOGI(GATTS_TAG, "ESP_GATTS_DISCONNECT_EVT, disconnect reason 0x%x", param->disconnect.reason);
esp_ble_gap_start_advertising(&adv_params);
break;
case ESP_GATTS_CONF_EVT:
esp_ble_gap_update_conn_params(&conn_params);
break;
case ESP_GATTS_DISCONNECT_EVT:
- ESP_LOGI(GATTS_TABLE_TAG, "ESP_GATTS_DISCONNECT_EVT, reason = %d", param->disconnect.reason);
+ ESP_LOGI(GATTS_TABLE_TAG, "ESP_GATTS_DISCONNECT_EVT, reason = 0x%x", param->disconnect.reason);
esp_ble_gap_start_advertising(&adv_params);
break;
case ESP_GATTS_CREAT_ATTR_TAB_EVT:{