9#include <esp_bt_device.h>
10#include <esp_bt_main.h>
11#include <esp_gap_ble_api.h>
12#include <freertos/FreeRTOS.h>
13#include <freertos/FreeRTOSConfig.h>
14#include <freertos/task.h>
18#include <esp32-hal-bt.h>
24static const char *
const TAG =
"esp32_ble";
31 ESP_LOGCONFIG(TAG,
"Setting up BLE...");
34 ESP_LOGE(TAG,
"BLE could not be prepared for configuration");
98 esp_err_t err = nvs_flash_init();
100 ESP_LOGE(TAG,
"nvs_flash_init failed: %d", err);
120 ESP_LOGE(TAG,
"btStart failed: %d", esp_bt_controller_get_status());
124 if (esp_bt_controller_get_status() != ESP_BT_CONTROLLER_STATUS_ENABLED) {
126 if (esp_bt_controller_get_status() == ESP_BT_CONTROLLER_STATUS_IDLE) {
127 esp_bt_controller_config_t cfg = BT_CONTROLLER_INIT_CONFIG_DEFAULT();
128 err = esp_bt_controller_init(&cfg);
130 ESP_LOGE(TAG,
"esp_bt_controller_init failed: %s", esp_err_to_name(err));
133 while (esp_bt_controller_get_status() == ESP_BT_CONTROLLER_STATUS_IDLE)
136 if (esp_bt_controller_get_status() == ESP_BT_CONTROLLER_STATUS_INITED) {
137 err = esp_bt_controller_enable(ESP_BT_MODE_BLE);
139 ESP_LOGE(TAG,
"esp_bt_controller_enable failed: %s", esp_err_to_name(err));
143 if (esp_bt_controller_get_status() != ESP_BT_CONTROLLER_STATUS_ENABLED) {
144 ESP_LOGE(TAG,
"esp bt controller enable failed");
150 esp_bt_controller_mem_release(ESP_BT_MODE_CLASSIC_BT);
152 err = esp_bluedroid_init();
154 ESP_LOGE(TAG,
"esp_bluedroid_init failed: %d", err);
157 err = esp_bluedroid_enable();
159 ESP_LOGE(TAG,
"esp_bluedroid_enable failed: %d", err);
166 ESP_LOGE(TAG,
"esp_ble_gap_register_callback failed: %d", err);
174 ESP_LOGE(TAG,
"esp_ble_gatts_register_callback failed: %d", err);
182 ESP_LOGE(TAG,
"esp_ble_gattc_register_callback failed: %d", err);
195 if (name.length() > 20) {
197 name.erase(name.begin() + 13, name.end() - 7);
199 name = name.substr(0, 20);
204 err = esp_ble_gap_set_device_name(name.c_str());
206 ESP_LOGE(TAG,
"esp_ble_gap_set_device_name failed: %d", err);
210 err = esp_ble_gap_set_security_param(ESP_BLE_SM_IOCAP_MODE, &(this->
io_cap_),
sizeof(uint8_t));
212 ESP_LOGE(TAG,
"esp_ble_gap_set_security_param failed: %d", err);
223 esp_err_t err = esp_bluedroid_disable();
225 ESP_LOGE(TAG,
"esp_bluedroid_disable failed: %d", err);
228 err = esp_bluedroid_deinit();
230 ESP_LOGE(TAG,
"esp_bluedroid_deinit failed: %d", err);
236 ESP_LOGE(TAG,
"btStop failed: %d", esp_bt_controller_get_status());
240 if (esp_bt_controller_get_status() != ESP_BT_CONTROLLER_STATUS_IDLE) {
242 if (esp_bt_controller_get_status() == ESP_BT_CONTROLLER_STATUS_ENABLED) {
243 err = esp_bt_controller_disable();
245 ESP_LOGE(TAG,
"esp_bt_controller_disable failed: %s", esp_err_to_name(err));
248 while (esp_bt_controller_get_status() == ESP_BT_CONTROLLER_STATUS_ENABLED)
251 if (esp_bt_controller_get_status() == ESP_BT_CONTROLLER_STATUS_INITED) {
252 err = esp_bt_controller_deinit();
254 ESP_LOGE(TAG,
"esp_bt_controller_deinit failed: %s", esp_err_to_name(err));
258 if (esp_bt_controller_get_status() != ESP_BT_CONTROLLER_STATUS_IDLE) {
259 ESP_LOGE(TAG,
"esp bt controller disable failed");
273 ESP_LOGD(TAG,
"Disabling BLE...");
276 ble_event_handler->ble_before_disabled_event_handler();
280 ESP_LOGE(TAG,
"BLE could not be dismantled");
288 ESP_LOGD(TAG,
"Enabling BLE...");
292 ESP_LOGE(TAG,
"BLE could not be set up");
305 while (ble_event !=
nullptr) {
306 switch (ble_event->
type_) {
321 ble_event->~BLEEvent();
322 EVENT_ALLOCATOR.deallocate(ble_event, 1);
331 BLEEvent *new_event = EVENT_ALLOCATOR.allocate(1);
332 if (new_event ==
nullptr) {
336 new (new_event)
BLEEvent(event, param);
341 ESP_LOGV(TAG,
"(BLE) gap_event_handler - %d", event);
343 gap_handler->gap_event_handler(event, param);
348 esp_ble_gatts_cb_param_t *param) {
349 BLEEvent *new_event = EVENT_ALLOCATOR.allocate(1);
350 if (new_event ==
nullptr) {
354 new (new_event)
BLEEvent(event, gatts_if, param);
359 esp_ble_gatts_cb_param_t *param) {
360 ESP_LOGV(TAG,
"(BLE) gatts_event [esp_gatt_if: %d] - %d", gatts_if, event);
362 gatts_handler->gatts_event_handler(event, gatts_if, param);
367 esp_ble_gattc_cb_param_t *param) {
368 BLEEvent *new_event = EVENT_ALLOCATOR.allocate(1);
369 if (new_event ==
nullptr) {
373 new (new_event)
BLEEvent(event, gattc_if, param);
378 esp_ble_gattc_cb_param_t *param) {
379 ESP_LOGV(TAG,
"(BLE) gattc_event [esp_gatt_if: %d] - %d", gattc_if, event);
381 gattc_handler->gattc_event_handler(event, gattc_if, param);
388 const uint8_t *mac_address = esp_bt_dev_get_address();
390 const char *io_capability_s;
393 io_capability_s =
"display_only";
396 io_capability_s =
"display_yes_no";
399 io_capability_s =
"keyboard_only";
401 case ESP_IO_CAP_NONE:
402 io_capability_s =
"none";
404 case ESP_IO_CAP_KBDISP:
405 io_capability_s =
"keyboard_display";
408 io_capability_s =
"invalid";
411 ESP_LOGCONFIG(TAG,
"ESP32 BLE:");
412 ESP_LOGCONFIG(TAG,
" MAC address: %02X:%02X:%02X:%02X:%02X:%02X", mac_address[0], mac_address[1], mac_address[2],
413 mac_address[3], mac_address[4], mac_address[5]);
414 ESP_LOGCONFIG(TAG,
" IO Capability: %s", io_capability_s);
416 ESP_LOGCONFIG(TAG,
"ESP32 BLE: bluetooth stack is not enabled");
422 u |= uint64_t(
address[0] & 0xFF) << 40;
423 u |= uint64_t(
address[1] & 0xFF) << 32;
424 u |= uint64_t(
address[2] & 0xFF) << 24;
425 u |= uint64_t(
address[3] & 0xFF) << 16;
426 u |= uint64_t(
address[4] & 0xFF) << 8;
427 u |= uint64_t(
address[5] & 0xFF) << 0;
bool is_name_add_mac_suffix_enabled() const
const std::string & get_name() const
Get the name of this Application set by pre_setup().
virtual void mark_failed()
Mark this component as failed.
An STL allocator that uses SPI or internal RAM.
void set_manufacturer_data(const std::vector< uint8_t > &data)
void add_service_uuid(ESPBTUUID uuid)
void set_scan_response(bool scan_response)
void set_min_preferred_interval(uint16_t interval)
void set_service_data(const std::vector< uint8_t > &data)
void remove_service_uuid(ESPBTUUID uuid)
void register_raw_advertisement_callback(std::function< void(bool)> &&callback)
void set_appearance(uint16_t appearance)
struct esphome::esp32_ble::BLEEvent::@77::gattc_event gattc
struct esphome::esp32_ble::BLEEvent::@77::gap_event gap
struct esphome::esp32_ble::BLEEvent::@77::gatts_event gatts
union esphome::esp32_ble::BLEEvent::@77 event_
enum esphome::esp32_ble::BLEEvent::ble_event_t type_
std::vector< GATTsEventHandler * > gatts_event_handlers_
void advertising_set_manufacturer_data(const std::vector< uint8_t > &data)
static void gap_event_handler(esp_gap_ble_cb_event_t event, esp_ble_gap_cb_param_t *param)
optional< std::string > name_
BLEAdvertising * advertising_
static void gattc_event_handler(esp_gattc_cb_event_t event, esp_gatt_if_t gattc_if, esp_ble_gattc_cb_param_t *param)
void advertising_register_raw_advertisement_callback(std::function< void(bool)> &&callback)
std::vector< GAPEventHandler * > gap_event_handlers_
void real_gap_event_handler_(esp_gap_ble_cb_event_t event, esp_ble_gap_cb_param_t *param)
uint32_t advertising_cycle_time_
void advertising_add_service_uuid(ESPBTUUID uuid)
void dump_config() override
std::vector< BLEStatusEventHandler * > ble_status_event_handlers_
void real_gattc_event_handler_(esp_gattc_cb_event_t event, esp_gatt_if_t gattc_if, esp_ble_gattc_cb_param_t *param)
static void gatts_event_handler(esp_gatts_cb_event_t event, esp_gatt_if_t gatts_if, esp_ble_gatts_cb_param_t *param)
Queue< BLEEvent > ble_events_
void advertising_set_service_data(const std::vector< uint8_t > &data)
void real_gatts_event_handler_(esp_gatts_cb_event_t event, esp_gatt_if_t gatts_if, esp_ble_gatts_cb_param_t *param)
float get_setup_priority() const override
std::vector< GATTcEventHandler * > gattc_event_handlers_
void advertising_remove_service_uuid(ESPBTUUID uuid)
value_type const & value() const
uint64_t ble_addr_to_uint64(const esp_bd_addr_t address)
@ BLE_COMPONENT_STATE_DISABLE
BLE should be disabled on next loop.
@ BLE_COMPONENT_STATE_OFF
Nothing has been initialized yet.
@ BLE_COMPONENT_STATE_ENABLE
BLE should be enabled on next loop.
@ BLE_COMPONENT_STATE_DISABLED
BLE is disabled.
@ BLE_COMPONENT_STATE_ACTIVE
BLE is active.
Providing packet encoding functions for exchanging data with a remote host.
void IRAM_ATTR HOT delay(uint32_t ms)
std::string get_mac_address()
Get the device MAC address as a string, in lowercase hex notation.
Application App
Global storage of Application pointer - only one Application can exist.