2018-01-15 11:47:23 +00:00
/*
This example code is in the Public Domain ( or CC0 licensed , at your option . )
2016-11-22 12:32:45 +00:00
2018-01-15 11:47:23 +00:00
Unless required by applicable law or agreed to in writing , this
software is distributed on an " AS IS " BASIS , WITHOUT WARRANTIES OR
CONDITIONS OF ANY KIND , either express or implied .
*/
2016-11-22 12:32:45 +00:00
/****************************************************************************
*
2018-10-24 03:24:07 +00:00
* This demo showcases BLE GATT client . It can scan BLE devices and connect to one device .
2017-07-21 03:03:20 +00:00
* Run the gatt_server demo , the client demo will automatically connect to the gatt_server demo .
2018-10-24 03:24:07 +00:00
* Client demo will enable gatt_server ' s notify after connection . The two devices will then exchange
2017-07-21 03:03:20 +00:00
* data .
2016-11-22 12:32:45 +00:00
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
# include <stdint.h>
# include <string.h>
# include <stdbool.h>
# include <stdio.h>
2017-07-13 15:46:19 +00:00
# include "nvs.h"
# include "nvs_flash.h"
2016-11-22 12:32:45 +00:00
2017-12-07 13:48:27 +00:00
# include "esp_bt.h"
2016-11-22 12:32:45 +00:00
# include "esp_gap_ble_api.h"
# include "esp_gattc_api.h"
# include "esp_gatt_defs.h"
# include "esp_bt_main.h"
2017-08-24 11:54:41 +00:00
# include "esp_gatt_common_api.h"
2018-04-08 04:10:50 +00:00
# include "esp_log.h"
# include "freertos/FreeRTOS.h"
2016-11-22 12:32:45 +00:00
2017-01-03 07:53:06 +00:00
# define GATTC_TAG "GATTC_DEMO"
2017-07-21 03:03:20 +00:00
# define REMOTE_SERVICE_UUID 0x00FF
# define REMOTE_NOTIFY_CHAR_UUID 0xFF01
2017-08-24 06:24:04 +00:00
# define PROFILE_NUM 1
# define PROFILE_A_APP_ID 0
# define INVALID_HANDLE 0
static const char remote_device_name [ ] = " ESP_GATTS_DEMO " ;
static bool connect = false ;
static bool get_server = false ;
static esp_gattc_char_elem_t * char_elem_result = NULL ;
static esp_gattc_descr_elem_t * descr_elem_result = NULL ;
2017-01-03 07:53:06 +00:00
2018-10-24 03:24:07 +00:00
/* Declare static functions */
2016-12-11 08:36:47 +00:00
static void esp_gap_cb ( esp_gap_ble_cb_event_t event , esp_ble_gap_cb_param_t * param ) ;
static void esp_gattc_cb ( esp_gattc_cb_event_t event , esp_gatt_if_t gattc_if , esp_ble_gattc_cb_param_t * param ) ;
2017-07-21 03:03:20 +00:00
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 ) ;
2016-12-11 08:36:47 +00:00
2016-11-22 12:32:45 +00:00
2017-07-21 03:03:20 +00:00
static esp_bt_uuid_t remote_filter_service_uuid = {
. len = ESP_UUID_LEN_16 ,
. uuid = { . uuid16 = REMOTE_SERVICE_UUID , } ,
} ;
2017-08-24 06:24:04 +00:00
static esp_bt_uuid_t remote_filter_char_uuid = {
. len = ESP_UUID_LEN_16 ,
. uuid = { . uuid16 = REMOTE_NOTIFY_CHAR_UUID , } ,
2016-12-19 09:12:43 +00:00
} ;
2016-11-22 12:32:45 +00:00
2017-08-24 06:24:04 +00:00
static esp_bt_uuid_t notify_descr_uuid = {
. len = ESP_UUID_LEN_16 ,
. uuid = { . uuid16 = ESP_GATT_UUID_CHAR_CLIENT_CONFIG , } ,
} ;
2016-11-22 12:32:45 +00:00
2016-11-24 18:10:15 +00:00
static esp_ble_scan_params_t ble_scan_params = {
. scan_type = BLE_SCAN_TYPE_ACTIVE ,
2017-05-05 08:46:08 +00:00
. own_addr_type = BLE_ADDR_TYPE_PUBLIC ,
2016-11-24 18:10:15 +00:00
. scan_filter_policy = BLE_SCAN_FILTER_ALLOW_ALL ,
. scan_interval = 0x50 ,
2018-05-03 12:22:08 +00:00
. scan_window = 0x30 ,
. scan_duplicate = BLE_SCAN_DUPLICATE_DISABLE
2016-11-22 12:32:45 +00:00
} ;
2016-12-11 08:36:47 +00:00
struct gattc_profile_inst {
esp_gattc_cb_t gattc_cb ;
uint16_t gattc_if ;
uint16_t app_id ;
uint16_t conn_id ;
2017-08-24 06:24:04 +00:00
uint16_t service_start_handle ;
uint16_t service_end_handle ;
uint16_t char_handle ;
2016-12-19 09:12:43 +00:00
esp_bd_addr_t remote_bda ;
2016-12-11 08:36:47 +00:00
} ;
/* One gatt-based profile one app_id and one gattc_if, this array will store the gattc_if returned by ESP_GATTS_REG_EVT */
static struct gattc_profile_inst gl_profile_tab [ PROFILE_NUM ] = {
[ PROFILE_A_APP_ID ] = {
2017-07-21 03:03:20 +00:00
. gattc_cb = gattc_profile_event_handler ,
2016-12-11 08:36:47 +00:00
. gattc_if = ESP_GATT_IF_NONE , /* Not get the gatt_if, so initial is ESP_GATT_IF_NONE */
} ,
} ;
2016-11-22 12:32:45 +00:00
2017-07-21 03:03:20 +00:00
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 )
2016-12-11 08:36:47 +00:00
{
esp_ble_gattc_cb_param_t * p_data = ( esp_ble_gattc_cb_param_t * ) param ;
switch ( event ) {
case ESP_GATTC_REG_EVT :
2017-03-29 08:51:21 +00:00
ESP_LOGI ( GATTC_TAG , " REG_EVT " ) ;
2017-07-21 03:03:20 +00:00
esp_err_t scan_ret = esp_ble_gap_set_scan_params ( & ble_scan_params ) ;
if ( scan_ret ) {
ESP_LOGE ( GATTC_TAG , " set scan params error, error code = %x " , scan_ret ) ;
}
2016-12-11 08:36:47 +00:00
break ;
2017-08-24 11:54:41 +00:00
case ESP_GATTC_CONNECT_EVT : {
2017-10-16 08:27:38 +00:00
ESP_LOGI ( GATTC_TAG , " ESP_GATTC_CONNECT_EVT conn_id %d, if %d " , p_data - > connect . conn_id , gattc_if ) ;
2017-07-21 03:03:20 +00:00
gl_profile_tab [ PROFILE_A_APP_ID ] . conn_id = p_data - > connect . conn_id ;
memcpy ( gl_profile_tab [ PROFILE_A_APP_ID ] . remote_bda , p_data - > connect . remote_bda , sizeof ( esp_bd_addr_t ) ) ;
2017-06-01 06:16:24 +00:00
ESP_LOGI ( GATTC_TAG , " REMOTE BDA: " ) ;
2017-06-11 13:59:49 +00:00
esp_log_buffer_hex ( GATTC_TAG , gl_profile_tab [ PROFILE_A_APP_ID ] . remote_bda , sizeof ( esp_bd_addr_t ) ) ;
2017-08-24 06:24:04 +00:00
esp_err_t mtu_ret = esp_ble_gattc_send_mtu_req ( gattc_if , p_data - > connect . conn_id ) ;
2017-07-21 03:03:20 +00:00
if ( mtu_ret ) {
ESP_LOGE ( GATTC_TAG , " config MTU error, error code = %x " , mtu_ret ) ;
}
break ;
2017-08-24 11:54:41 +00:00
}
2017-07-21 03:03:20 +00:00
case ESP_GATTC_OPEN_EVT :
if ( param - > open . status ! = ESP_GATT_OK ) {
ESP_LOGE ( GATTC_TAG , " open failed, status %d " , p_data - > open . status ) ;
break ;
}
ESP_LOGI ( GATTC_TAG , " open success " ) ;
break ;
case ESP_GATTC_CFG_MTU_EVT :
if ( param - > cfg_mtu . status ! = ESP_GATT_OK ) {
ESP_LOGE ( GATTC_TAG , " config mtu failed, error status = %x " , param - > cfg_mtu . status ) ;
}
ESP_LOGI ( GATTC_TAG , " ESP_GATTC_CFG_MTU_EVT, Status %d, MTU %d, conn_id %d " , param - > cfg_mtu . status , param - > cfg_mtu . mtu , param - > cfg_mtu . conn_id ) ;
esp_ble_gattc_search_service ( gattc_if , param - > cfg_mtu . conn_id , & remote_filter_service_uuid ) ;
2016-12-11 08:36:47 +00:00
break ;
case ESP_GATTC_SEARCH_RES_EVT : {
2018-03-20 11:27:50 +00:00
ESP_LOGI ( GATTC_TAG , " SEARCH RES: conn_id = %x is primary service %d " , p_data - > search_res . conn_id , p_data - > search_res . is_primary ) ;
2018-07-30 06:34:07 +00:00
ESP_LOGI ( GATTC_TAG , " start handle %d end handle %d current handle value %d " , p_data - > search_res . start_handle , p_data - > search_res . end_handle , p_data - > search_res . srvc_id . inst_id ) ;
2018-03-20 11:27:50 +00:00
if ( p_data - > search_res . srvc_id . uuid . len = = ESP_UUID_LEN_16 & & p_data - > search_res . srvc_id . uuid . uuid . uuid16 = = REMOTE_SERVICE_UUID ) {
2017-08-24 06:24:04 +00:00
ESP_LOGI ( GATTC_TAG , " service found " ) ;
2017-07-21 03:03:20 +00:00
get_server = true ;
2017-08-24 06:24:04 +00:00
gl_profile_tab [ PROFILE_A_APP_ID ] . service_start_handle = p_data - > search_res . start_handle ;
gl_profile_tab [ PROFILE_A_APP_ID ] . service_end_handle = p_data - > search_res . end_handle ;
2018-03-20 11:27:50 +00:00
ESP_LOGI ( GATTC_TAG , " UUID16: %x " , p_data - > search_res . srvc_id . uuid . uuid . uuid16 ) ;
2016-12-19 09:12:43 +00:00
}
break ;
}
case ESP_GATTC_SEARCH_CMPL_EVT :
2017-07-21 03:03:20 +00:00
if ( p_data - > search_cmpl . status ! = ESP_GATT_OK ) {
ESP_LOGE ( GATTC_TAG , " search service failed, error status = %x " , p_data - > search_cmpl . status ) ;
break ;
}
2018-09-28 06:12:32 +00:00
if ( p_data - > search_cmpl . searched_service_source = = ESP_GATT_SERVICE_FROM_REMOTE_DEVICE ) {
ESP_LOGI ( GATTC_TAG , " Get service information from remote device " ) ;
} else if ( p_data - > search_cmpl . searched_service_source = = ESP_GATT_SERVICE_FROM_NVS_FLASH ) {
ESP_LOGI ( GATTC_TAG , " Get service information from flash " ) ;
} else {
ESP_LOGI ( GATTC_TAG , " unknown service source " ) ;
}
2017-08-24 06:24:04 +00:00
ESP_LOGI ( GATTC_TAG , " ESP_GATTC_SEARCH_CMPL_EVT " ) ;
2017-07-21 03:03:20 +00:00
if ( get_server ) {
2017-08-24 06:24:04 +00:00
uint16_t count = 0 ;
esp_gatt_status_t status = esp_ble_gattc_get_attr_count ( gattc_if ,
p_data - > search_cmpl . conn_id ,
ESP_GATT_DB_CHARACTERISTIC ,
gl_profile_tab [ PROFILE_A_APP_ID ] . service_start_handle ,
gl_profile_tab [ PROFILE_A_APP_ID ] . service_end_handle ,
INVALID_HANDLE ,
& count ) ;
if ( status ! = ESP_GATT_OK ) {
ESP_LOGE ( GATTC_TAG , " esp_ble_gattc_get_attr_count error " ) ;
}
2016-12-19 09:12:43 +00:00
2017-08-24 06:24:04 +00:00
if ( count > 0 ) {
2017-10-23 03:07:03 +00:00
char_elem_result = ( esp_gattc_char_elem_t * ) malloc ( sizeof ( esp_gattc_char_elem_t ) * count ) ;
2017-08-24 06:24:04 +00:00
if ( ! char_elem_result ) {
ESP_LOGE ( GATTC_TAG , " gattc no mem " ) ;
} else {
status = esp_ble_gattc_get_char_by_uuid ( gattc_if ,
p_data - > search_cmpl . conn_id ,
gl_profile_tab [ PROFILE_A_APP_ID ] . service_start_handle ,
gl_profile_tab [ PROFILE_A_APP_ID ] . service_end_handle ,
remote_filter_char_uuid ,
char_elem_result ,
& count ) ;
if ( status ! = ESP_GATT_OK ) {
ESP_LOGE ( GATTC_TAG , " esp_ble_gattc_get_char_by_uuid error " ) ;
}
2016-12-19 09:12:43 +00:00
2017-08-24 06:24:04 +00:00
/* Every service have only one char in our 'ESP_GATTS_DEMO' demo, so we used first 'char_elem_result' */
if ( count > 0 & & ( char_elem_result [ 0 ] . properties & ESP_GATT_CHAR_PROP_BIT_NOTIFY ) ) {
gl_profile_tab [ PROFILE_A_APP_ID ] . char_handle = char_elem_result [ 0 ] . char_handle ;
esp_ble_gattc_register_for_notify ( gattc_if , gl_profile_tab [ PROFILE_A_APP_ID ] . remote_bda , char_elem_result [ 0 ] . char_handle ) ;
}
}
/* free char_elem_result */
free ( char_elem_result ) ;
} else {
ESP_LOGE ( GATTC_TAG , " no char found " ) ;
}
}
break ;
2016-12-19 09:12:43 +00:00
case ESP_GATTC_REG_FOR_NOTIFY_EVT : {
2017-08-24 06:24:04 +00:00
ESP_LOGI ( GATTC_TAG , " ESP_GATTC_REG_FOR_NOTIFY_EVT " ) ;
2017-07-21 03:03:20 +00:00
if ( p_data - > reg_for_notify . status ! = ESP_GATT_OK ) {
ESP_LOGE ( GATTC_TAG , " REG FOR NOTIFY failed: error status = %d " , p_data - > reg_for_notify . status ) ;
2017-08-24 06:24:04 +00:00
} else {
uint16_t count = 0 ;
uint16_t notify_en = 1 ;
esp_gatt_status_t ret_status = esp_ble_gattc_get_attr_count ( gattc_if ,
gl_profile_tab [ PROFILE_A_APP_ID ] . conn_id ,
ESP_GATT_DB_DESCRIPTOR ,
gl_profile_tab [ PROFILE_A_APP_ID ] . service_start_handle ,
gl_profile_tab [ PROFILE_A_APP_ID ] . service_end_handle ,
gl_profile_tab [ PROFILE_A_APP_ID ] . char_handle ,
& count ) ;
if ( ret_status ! = ESP_GATT_OK ) {
ESP_LOGE ( GATTC_TAG , " esp_ble_gattc_get_attr_count error " ) ;
}
if ( count > 0 ) {
2017-10-23 03:07:03 +00:00
descr_elem_result = malloc ( sizeof ( esp_gattc_descr_elem_t ) * count ) ;
2017-08-24 06:24:04 +00:00
if ( ! descr_elem_result ) {
ESP_LOGE ( GATTC_TAG , " malloc error, gattc no mem " ) ;
} else {
ret_status = esp_ble_gattc_get_descr_by_char_handle ( gattc_if ,
gl_profile_tab [ PROFILE_A_APP_ID ] . conn_id ,
p_data - > reg_for_notify . handle ,
notify_descr_uuid ,
descr_elem_result ,
& count ) ;
if ( ret_status ! = ESP_GATT_OK ) {
ESP_LOGE ( GATTC_TAG , " esp_ble_gattc_get_descr_by_char_handle error " ) ;
}
2018-02-13 06:55:18 +00:00
/* Every char has only one descriptor in our 'ESP_GATTS_DEMO' demo, so we used first 'descr_elem_result' */
2017-08-24 06:24:04 +00:00
if ( count > 0 & & descr_elem_result [ 0 ] . uuid . len = = ESP_UUID_LEN_16 & & descr_elem_result [ 0 ] . uuid . uuid . uuid16 = = ESP_GATT_UUID_CHAR_CLIENT_CONFIG ) {
ret_status = esp_ble_gattc_write_char_descr ( gattc_if ,
gl_profile_tab [ PROFILE_A_APP_ID ] . conn_id ,
descr_elem_result [ 0 ] . handle ,
sizeof ( notify_en ) ,
( uint8_t * ) & notify_en ,
ESP_GATT_WRITE_TYPE_RSP ,
ESP_GATT_AUTH_REQ_NONE ) ;
}
if ( ret_status ! = ESP_GATT_OK ) {
ESP_LOGE ( GATTC_TAG , " esp_ble_gattc_write_char_descr error " ) ;
}
/* free descr_elem_result */
free ( descr_elem_result ) ;
}
}
else {
ESP_LOGE ( GATTC_TAG , " decsr not found " ) ;
}
}
2016-12-19 09:12:43 +00:00
break ;
}
case ESP_GATTC_NOTIFY_EVT :
2017-10-26 06:39:49 +00:00
if ( p_data - > notify . is_notify ) {
ESP_LOGI ( GATTC_TAG , " ESP_GATTC_NOTIFY_EVT, receive notify value: " ) ;
} else {
ESP_LOGI ( GATTC_TAG , " ESP_GATTC_NOTIFY_EVT, receive indicate value: " ) ;
}
2017-07-21 03:03:20 +00:00
esp_log_buffer_hex ( GATTC_TAG , p_data - > notify . value , p_data - > notify . value_len ) ;
2016-12-19 09:12:43 +00:00
break ;
case ESP_GATTC_WRITE_DESCR_EVT :
2017-07-21 03:03:20 +00:00
if ( p_data - > write . status ! = ESP_GATT_OK ) {
ESP_LOGE ( GATTC_TAG , " write descr failed, error status = %x " , p_data - > write . status ) ;
break ;
}
ESP_LOGI ( GATTC_TAG , " write descr success " ) ;
2017-08-24 06:24:04 +00:00
uint8_t write_char_data [ 35 ] ;
for ( int i = 0 ; i < sizeof ( write_char_data ) ; + + i )
{
write_char_data [ i ] = i % 256 ;
}
esp_ble_gattc_write_char ( gattc_if ,
gl_profile_tab [ PROFILE_A_APP_ID ] . conn_id ,
gl_profile_tab [ PROFILE_A_APP_ID ] . char_handle ,
sizeof ( write_char_data ) ,
write_char_data ,
ESP_GATT_WRITE_TYPE_RSP ,
ESP_GATT_AUTH_REQ_NONE ) ;
2016-12-19 09:12:43 +00:00
break ;
2017-05-03 02:53:48 +00:00
case ESP_GATTC_SRVC_CHG_EVT : {
esp_bd_addr_t bda ;
memcpy ( bda , p_data - > srvc_chg . remote_bda , sizeof ( esp_bd_addr_t ) ) ;
2017-07-21 03:03:20 +00:00
ESP_LOGI ( GATTC_TAG , " ESP_GATTC_SRVC_CHG_EVT, bd_addr: " ) ;
esp_log_buffer_hex ( GATTC_TAG , bda , sizeof ( esp_bd_addr_t ) ) ;
2016-12-11 08:36:47 +00:00
break ;
}
2017-07-21 03:03:20 +00:00
case ESP_GATTC_WRITE_CHAR_EVT :
if ( p_data - > write . status ! = ESP_GATT_OK ) {
ESP_LOGE ( GATTC_TAG , " write char failed, error status = %x " , p_data - > write . status ) ;
2016-12-19 09:12:43 +00:00
break ;
}
2017-07-21 03:03:20 +00:00
ESP_LOGI ( GATTC_TAG , " write char success " ) ;
2016-12-19 09:12:43 +00:00
break ;
2017-07-21 03:03:20 +00:00
case ESP_GATTC_DISCONNECT_EVT :
connect = false ;
get_server = false ;
2017-10-16 08:27:38 +00:00
ESP_LOGI ( GATTC_TAG , " ESP_GATTC_DISCONNECT_EVT, reason = %d " , p_data - > disconnect . reason ) ;
2016-12-11 08:36:47 +00:00
break ;
default :
break ;
}
}
2016-11-22 12:32:45 +00:00
2016-12-11 08:36:47 +00:00
static void esp_gap_cb ( esp_gap_ble_cb_event_t event , esp_ble_gap_cb_param_t * param )
2016-11-22 12:32:45 +00:00
{
2016-11-24 18:10:15 +00:00
uint8_t * adv_name = NULL ;
uint8_t adv_name_len = 0 ;
switch ( event ) {
case ESP_GAP_BLE_SCAN_PARAM_SET_COMPLETE_EVT : {
//the unit of the duration is second
2017-04-19 12:06:38 +00:00
uint32_t duration = 30 ;
2016-11-24 18:10:15 +00:00
esp_ble_gap_start_scanning ( duration ) ;
break ;
}
2017-02-23 09:32:46 +00:00
case ESP_GAP_BLE_SCAN_START_COMPLETE_EVT :
//scan start complete event to indicate scan start successfully or failed
if ( param - > scan_start_cmpl . status ! = ESP_BT_STATUS_SUCCESS ) {
2017-07-21 03:03:20 +00:00
ESP_LOGE ( GATTC_TAG , " scan start failed, error status = %x " , param - > scan_start_cmpl . status ) ;
break ;
2017-02-23 09:32:46 +00:00
}
2017-07-21 03:03:20 +00:00
ESP_LOGI ( GATTC_TAG , " scan start success " ) ;
2017-02-23 09:32:46 +00:00
break ;
2016-11-24 18:10:15 +00:00
case ESP_GAP_BLE_SCAN_RESULT_EVT : {
esp_ble_gap_cb_param_t * scan_result = ( esp_ble_gap_cb_param_t * ) param ;
switch ( scan_result - > scan_rst . search_evt ) {
case ESP_GAP_SEARCH_INQ_RES_EVT :
2017-06-11 13:59:49 +00:00
esp_log_buffer_hex ( GATTC_TAG , scan_result - > scan_rst . bda , 6 ) ;
2017-07-21 03:03:20 +00:00
ESP_LOGI ( GATTC_TAG , " searched Adv Data Len %d, Scan Response Len %d " , scan_result - > scan_rst . adv_data_len , scan_result - > scan_rst . scan_rsp_len ) ;
2016-11-24 18:10:15 +00:00
adv_name = esp_ble_resolve_adv_data ( scan_result - > scan_rst . ble_adv ,
ESP_BLE_AD_TYPE_NAME_CMPL , & adv_name_len ) ;
2017-07-21 03:03:20 +00:00
ESP_LOGI ( GATTC_TAG , " searched Device Name Len %d " , adv_name_len ) ;
2017-06-11 13:59:49 +00:00
esp_log_buffer_char ( GATTC_TAG , adv_name , adv_name_len ) ;
2019-01-23 06:11:56 +00:00
# if CONFIG_EXAMPLE_DUMP_ADV_DATA_AND_SCAN_RESP
if ( scan_result - > scan_rst . adv_data_len > 0 ) {
ESP_LOGI ( GATTC_TAG , " adv data: " ) ;
esp_log_buffer_hex ( GATTC_TAG , & scan_result - > scan_rst . ble_adv [ 0 ] , scan_result - > scan_rst . adv_data_len ) ;
}
if ( scan_result - > scan_rst . scan_rsp_len > 0 ) {
ESP_LOGI ( GATTC_TAG , " scan resp: " ) ;
esp_log_buffer_hex ( GATTC_TAG , & scan_result - > scan_rst . ble_adv [ scan_result - > scan_rst . adv_data_len ] , scan_result - > scan_rst . scan_rsp_len ) ;
}
# endif
2017-06-01 06:16:24 +00:00
ESP_LOGI ( GATTC_TAG , " \n " ) ;
2019-01-23 06:11:56 +00:00
2016-11-24 18:10:15 +00:00
if ( adv_name ! = NULL ) {
2017-07-21 03:03:20 +00:00
if ( strlen ( remote_device_name ) = = adv_name_len & & strncmp ( ( char * ) adv_name , remote_device_name , adv_name_len ) = = 0 ) {
ESP_LOGI ( GATTC_TAG , " searched device %s \n " , remote_device_name ) ;
2016-12-11 08:36:47 +00:00
if ( connect = = false ) {
connect = true ;
2017-07-21 03:03:20 +00:00
ESP_LOGI ( GATTC_TAG , " connect to the remote device. " ) ;
2016-11-24 18:10:15 +00:00
esp_ble_gap_stop_scanning ( ) ;
2018-03-23 03:08:03 +00:00
esp_ble_gattc_open ( gl_profile_tab [ PROFILE_A_APP_ID ] . gattc_if , scan_result - > scan_rst . bda , scan_result - > scan_rst . ble_addr_type , true ) ;
2016-11-24 18:10:15 +00:00
}
}
}
break ;
case ESP_GAP_SEARCH_INQ_CMPL_EVT :
break ;
default :
break ;
}
break ;
}
2017-03-29 08:51:21 +00:00
case ESP_GAP_BLE_SCAN_STOP_COMPLETE_EVT :
if ( param - > scan_stop_cmpl . status ! = ESP_BT_STATUS_SUCCESS ) {
2017-07-21 03:03:20 +00:00
ESP_LOGE ( GATTC_TAG , " scan stop failed, error status = %x " , param - > scan_stop_cmpl . status ) ;
break ;
2017-03-29 08:51:21 +00:00
}
2017-07-21 03:03:20 +00:00
ESP_LOGI ( GATTC_TAG , " stop scan successfully " ) ;
2017-03-29 08:51:21 +00:00
break ;
case ESP_GAP_BLE_ADV_STOP_COMPLETE_EVT :
if ( param - > adv_stop_cmpl . status ! = ESP_BT_STATUS_SUCCESS ) {
2017-07-21 03:03:20 +00:00
ESP_LOGE ( GATTC_TAG , " adv stop failed, error status = %x " , param - > adv_stop_cmpl . status ) ;
break ;
2017-03-29 08:51:21 +00:00
}
2017-07-21 03:03:20 +00:00
ESP_LOGI ( GATTC_TAG , " stop adv successfully " ) ;
2017-03-29 08:51:21 +00:00
break ;
2017-08-24 12:46:03 +00:00
case ESP_GAP_BLE_UPDATE_CONN_PARAMS_EVT :
2018-02-13 06:55:18 +00:00
ESP_LOGI ( GATTC_TAG , " update connection params status = %d, min_int = %d, max_int = %d,conn_int = %d,latency = %d, timeout = %d " ,
2017-08-24 12:46:03 +00:00
param - > update_conn_params . status ,
param - > update_conn_params . min_int ,
param - > update_conn_params . max_int ,
param - > update_conn_params . conn_int ,
param - > update_conn_params . latency ,
param - > update_conn_params . timeout ) ;
break ;
2016-11-24 18:10:15 +00:00
default :
break ;
}
2016-11-22 12:32:45 +00:00
}
2016-12-11 08:36:47 +00:00
static void esp_gattc_cb ( esp_gattc_cb_event_t event , esp_gatt_if_t gattc_if , esp_ble_gattc_cb_param_t * param )
2016-11-22 12:32:45 +00:00
{
2016-12-11 08:36:47 +00:00
/* If event is register event, store the gattc_if for each profile */
if ( event = = ESP_GATTC_REG_EVT ) {
if ( param - > reg . status = = ESP_GATT_OK ) {
gl_profile_tab [ param - > reg . app_id ] . gattc_if = gattc_if ;
2016-11-24 18:10:15 +00:00
} else {
2017-07-21 03:03:20 +00:00
ESP_LOGI ( GATTC_TAG , " reg app failed, app_id %04x, status %d " ,
param - > reg . app_id ,
2016-12-11 08:36:47 +00:00
param - > reg . status ) ;
return ;
2016-11-24 18:10:15 +00:00
}
}
2016-12-11 08:36:47 +00:00
/* If the gattc_if equal to profile A, call profile A cb handler,
* so here call each profile ' s callback */
do {
int idx ;
for ( idx = 0 ; idx < PROFILE_NUM ; idx + + ) {
if ( gattc_if = = ESP_GATT_IF_NONE | | /* ESP_GATT_IF_NONE, not specify a certain gatt_if, need to call every profile cb function */
gattc_if = = gl_profile_tab [ idx ] . gattc_if ) {
if ( gl_profile_tab [ idx ] . gattc_cb ) {
gl_profile_tab [ idx ] . gattc_cb ( event , gattc_if , param ) ;
}
}
}
} while ( 0 ) ;
2016-11-22 12:32:45 +00:00
}
2017-07-21 03:03:20 +00:00
void app_main ( )
2016-11-22 12:32:45 +00:00
{
2017-07-21 03:03:20 +00:00
// Initialize NVS.
esp_err_t ret = nvs_flash_init ( ) ;
2018-07-25 15:11:09 +00:00
if ( ret = = ESP_ERR_NVS_NO_FREE_PAGES | | ret = = ESP_ERR_NVS_NEW_VERSION_FOUND ) {
2017-07-21 03:03:20 +00:00
ESP_ERROR_CHECK ( nvs_flash_erase ( ) ) ;
ret = nvs_flash_init ( ) ;
}
ESP_ERROR_CHECK ( ret ) ;
2016-12-11 08:36:47 +00:00
2017-12-12 07:24:43 +00:00
ESP_ERROR_CHECK ( esp_bt_controller_mem_release ( ESP_BT_MODE_CLASSIC_BT ) ) ;
2017-07-21 03:03:20 +00:00
esp_bt_controller_config_t bt_cfg = BT_CONTROLLER_INIT_CONFIG_DEFAULT ( ) ;
ret = esp_bt_controller_init ( & bt_cfg ) ;
if ( ret ) {
2018-02-22 13:48:53 +00:00
ESP_LOGE ( GATTC_TAG , " %s initialize controller failed: %s \n " , __func__ , esp_err_to_name ( ret ) ) ;
2017-07-21 03:03:20 +00:00
return ;
}
2016-11-24 18:10:15 +00:00
2017-12-12 07:24:43 +00:00
ret = esp_bt_controller_enable ( ESP_BT_MODE_BLE ) ;
2017-07-21 03:03:20 +00:00
if ( ret ) {
2018-02-22 13:48:53 +00:00
ESP_LOGE ( GATTC_TAG , " %s enable controller failed: %s \n " , __func__ , esp_err_to_name ( ret ) ) ;
2016-11-24 18:10:15 +00:00
return ;
}
2017-07-21 03:03:20 +00:00
ret = esp_bluedroid_init ( ) ;
if ( ret ) {
2018-02-22 13:48:53 +00:00
ESP_LOGE ( GATTC_TAG , " %s init bluetooth failed: %s \n " , __func__ , esp_err_to_name ( ret ) ) ;
2016-11-24 18:10:15 +00:00
return ;
}
2016-11-22 12:32:45 +00:00
2017-07-21 03:03:20 +00:00
ret = esp_bluedroid_enable ( ) ;
if ( ret ) {
2018-02-22 13:48:53 +00:00
ESP_LOGE ( GATTC_TAG , " %s enable bluetooth failed: %s \n " , __func__ , esp_err_to_name ( ret ) ) ;
2017-07-21 03:03:20 +00:00
return ;
}
2016-11-22 12:32:45 +00:00
2017-07-21 03:03:20 +00:00
//register the callback function to the gap module
ret = esp_ble_gap_register_callback ( esp_gap_cb ) ;
if ( ret ) {
ESP_LOGE ( GATTC_TAG , " %s gap register failed, error code = %x \n " , __func__ , ret ) ;
return ;
2017-07-13 15:46:19 +00:00
}
2017-07-21 03:03:20 +00:00
//register the callback function to the gattc module
ret = esp_ble_gattc_register_callback ( esp_gattc_cb ) ;
if ( ret ) {
ESP_LOGE ( GATTC_TAG , " %s gattc register failed, error code = %x \n " , __func__ , ret ) ;
return ;
}
ret = esp_ble_gattc_app_register ( PROFILE_A_APP_ID ) ;
if ( ret ) {
ESP_LOGE ( GATTC_TAG , " %s gattc app register failed, error code = %x \n " , __func__ , ret ) ;
}
2017-08-24 11:54:41 +00:00
esp_err_t local_mtu_ret = esp_ble_gatt_set_local_mtu ( 500 ) ;
if ( local_mtu_ret ) {
ESP_LOGE ( GATTC_TAG , " set local MTU failed, error code = %x " , local_mtu_ret ) ;
}
2017-02-17 11:24:58 +00:00
2016-11-22 12:32:45 +00:00
}