diff --git a/cpp_utils/BLEAdvertisedDevice.cpp b/cpp_utils/BLEAdvertisedDevice.cpp index dbda9172..41d5faba 100644 --- a/cpp_utils/BLEAdvertisedDevice.cpp +++ b/cpp_utils/BLEAdvertisedDevice.cpp @@ -233,7 +233,8 @@ void BLEAdvertisedDevice::parseAdvertisement(uint8_t* payload, size_t total_len) uint8_t ad_type; uint8_t sizeConsumed = 0; bool finished = false; - setPayload(payload); + m_payload = payload; + m_payloadLength = total_len; while(!finished) { length = *payload; // Retrieve the length of the record. @@ -351,9 +352,9 @@ void BLEAdvertisedDevice::parseAdvertisement(uint8_t* payload, size_t total_len) } // Length <> 0 - if (sizeConsumed >= total_len || length == 0) { + if (sizeConsumed >= total_len) finished = true; - } + } // !finished } // parseAdvertisement @@ -510,10 +511,6 @@ uint8_t* BLEAdvertisedDevice::getPayload() { return m_payload; } -void BLEAdvertisedDevice::setPayload(uint8_t* payload) { - m_payload = payload; -} - esp_ble_addr_type_t BLEAdvertisedDevice::getAddressType() { return m_addressType; } @@ -522,6 +519,9 @@ void BLEAdvertisedDevice::setAddressType(esp_ble_addr_type_t type) { m_addressType = type; } +size_t BLEAdvertisedDevice::getPayloadLength() { + return m_payloadLength; +} #endif /* CONFIG_BT_ENABLED */ diff --git a/cpp_utils/BLEAdvertisedDevice.h b/cpp_utils/BLEAdvertisedDevice.h index aaa1417c..aec83746 100644 --- a/cpp_utils/BLEAdvertisedDevice.h +++ b/cpp_utils/BLEAdvertisedDevice.h @@ -40,6 +40,7 @@ class BLEAdvertisedDevice { BLEUUID getServiceUUID(); int8_t getTXPower(); uint8_t* getPayload(); + size_t getPayloadLength(); esp_ble_addr_type_t getAddressType(); void setAddressType(esp_ble_addr_type_t type); @@ -72,7 +73,6 @@ class BLEAdvertisedDevice { void setServiceUUID(const char* serviceUUID); void setServiceUUID(BLEUUID serviceUUID); void setTXPower(int8_t txPower); - void setPayload(uint8_t* payload); bool m_haveAppearance; bool m_haveManufacturerData; @@ -96,6 +96,7 @@ class BLEAdvertisedDevice { std::string m_serviceData; BLEUUID m_serviceDataUUID; uint8_t* m_payload; + size_t m_payloadLength = 0; esp_ble_addr_type_t m_addressType; }; diff --git a/cpp_utils/BLEAdvertising.cpp b/cpp_utils/BLEAdvertising.cpp index d4fd6332..41ad87a2 100644 --- a/cpp_utils/BLEAdvertising.cpp +++ b/cpp_utils/BLEAdvertising.cpp @@ -56,6 +56,7 @@ BLEAdvertising::BLEAdvertising() { m_advParams.own_addr_type = BLE_ADDR_TYPE_PUBLIC; m_advParams.channel_map = ADV_CHNL_ALL; m_advParams.adv_filter_policy = ADV_FILTER_ALLOW_SCAN_ANY_CON_ANY; + m_advParams.peer_addr_type = BLE_ADDR_TYPE_PUBLIC; m_customAdvData = false; // No custom advertising data m_customScanResponseData = false; // No custom scan response data @@ -92,15 +93,24 @@ void BLEAdvertising::setAppearance(uint16_t appearance) { } // setAppearance void BLEAdvertising::setMinInterval(uint16_t mininterval) { - m_advData.min_interval = mininterval; m_advParams.adv_int_min = mininterval; } // setMinInterval void BLEAdvertising::setMaxInterval(uint16_t maxinterval) { - m_advData.max_interval = maxinterval; m_advParams.adv_int_max = maxinterval; } // setMaxInterval +void BLEAdvertising::setMinPreferred(uint16_t mininterval) { + m_advData.min_interval = mininterval; +} // + +void BLEAdvertising::setMaxPreferred(uint16_t maxinterval) { + m_advData.max_interval = maxinterval; +} // + +void BLEAdvertising::setScanResponse(bool set) { + m_scanResp = set; +} /** * @brief Set the filtering for the scan filter. @@ -198,6 +208,8 @@ void BLEAdvertising::start() { if (!m_customAdvData) { // Set the configuration for advertising. m_advData.set_scan_rsp = false; + m_advData.include_name = !m_scanResp; + m_advData.include_txpower = !m_scanResp; errRc = ::esp_ble_gap_config_adv_data(&m_advData); if (errRc != ESP_OK) { ESP_LOGE(LOG_TAG, "<< esp_ble_gap_config_adv_data: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); @@ -205,8 +217,10 @@ void BLEAdvertising::start() { } } - if (!m_customScanResponseData) { + if (!m_customScanResponseData && m_scanResp) { m_advData.set_scan_rsp = true; + m_advData.include_name = m_scanResp; + m_advData.include_txpower = m_scanResp; errRc = ::esp_ble_gap_config_adv_data(&m_advData); if (errRc != ESP_OK) { ESP_LOGE(LOG_TAG, "<< esp_ble_gap_config_adv_data (Scan response): rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); @@ -456,5 +470,34 @@ std::string BLEAdvertisementData::getPayload() { return m_payload; } // getPayload +void BLEAdvertising::handleGAPEvent( + esp_gap_ble_cb_event_t event, + esp_ble_gap_cb_param_t* param) { + + ESP_LOGD(LOG_TAG, "handleGAPEvent [event no: %d]", (int)event); + + switch(event) { + case ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT: { + // m_semaphoreSetAdv.give(); + break; + } + case ESP_GAP_BLE_SCAN_RSP_DATA_SET_COMPLETE_EVT: { + // m_semaphoreSetAdv.give(); + break; + } + case ESP_GAP_BLE_ADV_START_COMPLETE_EVT: { + // m_semaphoreSetAdv.give(); + break; + } + case ESP_GAP_BLE_ADV_STOP_COMPLETE_EVT: { + ESP_LOGI(LOG_TAG, "STOP advertising"); + start(); + break; + } + default: + break; + } +} + #endif /* CONFIG_BT_ENABLED */ diff --git a/cpp_utils/BLEAdvertising.h b/cpp_utils/BLEAdvertising.h index f7cfc240..3128b50f 100644 --- a/cpp_utils/BLEAdvertising.h +++ b/cpp_utils/BLEAdvertising.h @@ -12,6 +12,7 @@ #include #include "BLEUUID.h" #include +#include "FreeRTOS.h" /** * @brief Advertisement data set by the programmer to be published by the %BLE server. @@ -19,6 +20,7 @@ class BLEAdvertisementData { // Only a subset of the possible BLE architected advertisement fields are currently exposed. Others will // be exposed on demand/request or as time permits. + // public: void setAppearance(uint16_t appearance); void setCompleteServices(BLEUUID uuid); @@ -55,13 +57,22 @@ class BLEAdvertising { void setAdvertisementData(BLEAdvertisementData& advertisementData); void setScanFilter(bool scanRequertWhitelistOnly, bool connectWhitelistOnly); void setScanResponseData(BLEAdvertisementData& advertisementData); + void setPrivateAddress(esp_ble_addr_type_t type = BLE_ADDR_TYPE_RANDOM); + + void handleGAPEvent(esp_gap_ble_cb_event_t event, esp_ble_gap_cb_param_t* param); + void setMinPreferred(uint16_t); + void setMaxPreferred(uint16_t); + void setScanResponse(bool); private: esp_ble_adv_data_t m_advData; esp_ble_adv_params_t m_advParams; std::vector m_serviceUUIDs; - bool m_customAdvData; // Are we using custom advertising data? - bool m_customScanResponseData; // Are we using custom scan response data? + bool m_customAdvData = false; // Are we using custom advertising data? + bool m_customScanResponseData = false; // Are we using custom scan response data? + FreeRTOS::Semaphore m_semaphoreSetAdv = FreeRTOS::Semaphore("startAdvert"); + bool m_scanResp = true; + }; #endif /* CONFIG_BT_ENABLED */ -#endif /* COMPONENTS_CPP_UTILS_BLEADVERTISING_H_ */ +#endif /* COMPONENTS_CPP_UTILS_BLEADVERTISING_H_ */ \ No newline at end of file diff --git a/cpp_utils/BLECharacteristic.cpp b/cpp_utils/BLECharacteristic.cpp index 6f696c7c..dee4454a 100644 --- a/cpp_utils/BLECharacteristic.cpp +++ b/cpp_utils/BLECharacteristic.cpp @@ -44,7 +44,7 @@ BLECharacteristic::BLECharacteristic(const char* uuid, uint32_t properties) : BL BLECharacteristic::BLECharacteristic(BLEUUID uuid, uint32_t properties) { m_bleUUID = uuid; m_handle = NULL_HANDLE; - m_properties = (esp_gatt_char_prop_t) 0; + m_properties = (esp_gatt_char_prop_t)0; m_pCallbacks = nullptr; setBroadcastProperty((properties & PROPERTY_BROADCAST) != 0); @@ -87,7 +87,7 @@ void BLECharacteristic::executeCreate(BLEService* pService) { return; } - m_pService = pService; // Save the service for to which this characteristic belongs. + m_pService = pService; // Save the service to which this characteristic belongs. ESP_LOGD(LOG_TAG, "Registering characteristic (esp_ble_gatts_add_char): uuid: %s, service: %s", getUUID().toString().c_str(), @@ -97,20 +97,11 @@ void BLECharacteristic::executeCreate(BLEService* pService) { control.auto_rsp = ESP_GATT_RSP_BY_APP; m_semaphoreCreateEvt.take("executeCreate"); - - /* - esp_attr_value_t value; - value.attr_len = m_value.getLength(); - value.attr_max_len = ESP_GATT_MAX_ATTR_LEN; - value.attr_value = m_value.getData(); - */ - esp_err_t errRc = ::esp_ble_gatts_add_char( m_pService->getHandle(), getUUID().getNative(), static_cast(m_permissions), getProperties(), - //&value, nullptr, &control); // Whether to auto respond or not. @@ -118,15 +109,9 @@ void BLECharacteristic::executeCreate(BLEService* pService) { ESP_LOGE(LOG_TAG, "<< esp_ble_gatts_add_char: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); return; } - m_semaphoreCreateEvt.wait("executeCreate"); - // Now that we have registered the characteristic, we must also register all the descriptors associated with this - // characteristic. We iterate through each of those and invoke the registration call to register them with the - // ESP environment. - BLEDescriptor* pDescriptor = m_descriptorMap.getFirst(); - while (pDescriptor != nullptr) { pDescriptor->executeCreate(this); pDescriptor = m_descriptorMap.getNext(); @@ -216,7 +201,7 @@ void BLECharacteristic::handleGATTServerEvent( esp_ble_gatts_cb_param_t* param) { ESP_LOGD(LOG_TAG, ">> handleGATTServerEvent: %s", BLEUtils::gattServerEventTypeToString(event).c_str()); - switch (event) { + switch(event) { // Events handled: // // ESP_GATTS_ADD_CHAR_EVT @@ -246,7 +231,7 @@ void BLECharacteristic::handleGATTServerEvent( } else { m_value.cancel(); } - +// ??? esp_err_t errRc = ::esp_ble_gatts_send_response( gatts_if, param->write.conn_id, @@ -265,9 +250,13 @@ void BLECharacteristic::handleGATTServerEvent( // - uint16_t service_handle // - esp_bt_uuid_t char_uuid case ESP_GATTS_ADD_CHAR_EVT: { - if (getUUID().equals(BLEUUID(param->add_char.char_uuid)) && - getHandle() == param->add_char.attr_handle && - getService()->getHandle() == param->add_char.service_handle) { + if (getHandle() == param->add_char.attr_handle) { + // we have created characteristic, now we can create descriptors + // BLEDescriptor* pDescriptor = m_descriptorMap.getFirst(); + // while (pDescriptor != nullptr) { + // pDescriptor->executeCreate(this); + // pDescriptor = m_descriptorMap.getNext(); + // } // End while m_semaphoreCreateEvt.give(); } break; @@ -357,7 +346,7 @@ void BLECharacteristic::handleGATTServerEvent( // // If the is_long flag is set then this is a follow on from an original read and we will already have sent at least 22 bytes. // If the is_long flag is not set then we need to check how much data we are going to send. If we are sending LESS than -// 22 bytes, then we "just" send it and that's the end of the story. +// 22 bytes, then we "just" send it and thats the end of the story. // If we are sending 22 bytes exactly, we just send it BUT we will get a follow on request. // If we are sending more than 22 bytes, we send the first 22 bytes and we will get a follow on request. // Because of follow on request processing, we need to maintain an offset of how much data we have already sent @@ -367,10 +356,11 @@ void BLECharacteristic::handleGATTServerEvent( // // The following code has deliberately not been factored to make it fewer statements because this would cloud the // the logic flow comprehension. +// - // TODO requires some more research to confirm that 512 is max PDU like in bluetooth specs - uint16_t maxOffset = BLEDevice::getMTU() - 1; - if (BLEDevice::getMTU() > 512) maxOffset = 512; + // get mtu for peer device that we are sending read request to + uint16_t maxOffset = getService()->getServer()->getPeerMTU(param->read.conn_id) - 1; + ESP_LOGD(LOG_TAG, "mtu value: %d", maxOffset); if (param->read.need_rsp) { ESP_LOGD(LOG_TAG, "Sending a response (esp_ble_gatts_send_response)"); esp_gatt_rsp_t rsp; @@ -393,10 +383,6 @@ void BLECharacteristic::handleGATTServerEvent( } } else { // read.is_long == false - if (m_pCallbacks != nullptr) { // If is.long is false then this is the first (or only) request to read data, so invoke the callback - m_pCallbacks->onRead(this); // Invoke the read callback. - } - std::string value = m_value.getValue(); if (value.length() + 1 > maxOffset) { @@ -411,6 +397,10 @@ void BLECharacteristic::handleGATTServerEvent( rsp.attr_value.offset = 0; memcpy(rsp.attr_value.value, value.data(), rsp.attr_value.len); } + + if (m_pCallbacks != nullptr) { // If is.long is false then this is the first (or only) request to read data, so invoke the callback + m_pCallbacks->onRead(this); // Invoke the read callback. + } } rsp.attr_value.handle = param->read.handle; rsp.attr_value.auth_req = ESP_GATT_AUTH_REQ_NONE; @@ -440,12 +430,13 @@ void BLECharacteristic::handleGATTServerEvent( // - uint16_t conn_id – The connection used. // case ESP_GATTS_CONF_EVT: { - m_semaphoreConfEvt.give(); + // ESP_LOGD(LOG_TAG, "m_handle = %d, conf->handle = %d", m_handle, param->conf.handle); + if(param->conf.conn_id == getService()->getServer()->getConnId()) // && param->conf.handle == m_handle) // bug in esp-idf and not implemented in arduino yet + m_semaphoreConfEvt.give(param->conf.status); break; } case ESP_GATTS_CONNECT_EVT: { - m_semaphoreConfEvt.give(); break; } @@ -475,46 +466,9 @@ void BLECharacteristic::handleGATTServerEvent( * @return N/A */ void BLECharacteristic::indicate() { - ESP_LOGD(LOG_TAG, ">> indicate: length: %d", m_value.getValue().length()); - - assert(getService() != nullptr); - assert(getService()->getServer() != nullptr); - - GeneralUtils::hexDump((uint8_t*)m_value.getValue().data(), m_value.getValue().length()); - - if (getService()->getServer()->getConnectedCount() == 0) { - ESP_LOGD(LOG_TAG, "<< indicate: No connected clients."); - return; - } - // Test to see if we have a 0x2902 descriptor. If we do, then check to see if indications are enabled - // and, if not, prevent the indication. - - BLE2902 *p2902 = (BLE2902*) getDescriptorByUUID((uint16_t) 0x2902); - if (p2902 != nullptr && !p2902->getIndications()) { - ESP_LOGD(LOG_TAG, "<< indications disabled; ignoring"); - return; - } - - if (m_value.getValue().length() > (BLEDevice::getMTU() - 3)) { - ESP_LOGI(LOG_TAG, "- Truncating to %d bytes (maximum indicate size)", BLEDevice::getMTU() - 3); - } - - size_t length = m_value.getValue().length(); - - m_semaphoreConfEvt.take("indicate"); - - esp_err_t errRc = ::esp_ble_gatts_send_indicate( - getService()->getServer()->getGattsIf(), - getService()->getServer()->getConnId(), - getHandle(), length, (uint8_t*)m_value.getValue().data(), true); // The need_confirm = true makes this an indication. - - if (errRc != ESP_OK) { - ESP_LOGE(LOG_TAG, "<< esp_ble_gatts_send_indicate: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); - return; - } - - m_semaphoreConfEvt.wait("indicate"); + ESP_LOGD(LOG_TAG, ">> indicate: length: %d", m_value.getValue().length()); + notify(false); ESP_LOGD(LOG_TAG, "<< indicate"); } // indicate @@ -525,7 +479,7 @@ void BLECharacteristic::indicate() { * will not block; it is a fire and forget. * @return N/A. */ -void BLECharacteristic::notify() { +void BLECharacteristic::notify(bool is_notification) { ESP_LOGD(LOG_TAG, ">> notify: length: %d", m_value.getValue().length()); assert(getService() != nullptr); @@ -541,31 +495,40 @@ void BLECharacteristic::notify() { // Test to see if we have a 0x2902 descriptor. If we do, then check to see if notification is enabled // and, if not, prevent the notification. - BLE2902 *p2902 = (BLE2902*) getDescriptorByUUID((uint16_t) 0x2902); - if (p2902 != nullptr && !p2902->getNotifications()) { - ESP_LOGD(LOG_TAG, "<< notifications disabled; ignoring"); - return; + BLE2902 *p2902 = (BLE2902*)getDescriptorByUUID((uint16_t)0x2902); + if(is_notification) { + if (p2902 != nullptr && !p2902->getNotifications()) { + ESP_LOGD(LOG_TAG, "<< notifications disabled; ignoring"); + return; + } } - - if (m_value.getValue().length() > (BLEDevice::getMTU() - 3)) { - ESP_LOGI(LOG_TAG, "- Truncating to %d bytes (maximum notify size)", BLEDevice::getMTU() - 3); + else{ + if (p2902 != nullptr && !p2902->getIndications()) { + ESP_LOGD(LOG_TAG, "<< indications disabled; ignoring"); + return; + } } + for (auto &myPair : getService()->getServer()->getPeerDevices(false)) { + uint16_t _mtu = (myPair.second.mtu); + if (m_value.getValue().length() > _mtu - 3) { + ESP_LOGW(LOG_TAG, "- Truncating to %d bytes (maximum notify size)", _mtu - 3); + } - size_t length = m_value.getValue().length(); - - m_semaphoreConfEvt.take("notify"); - - esp_err_t errRc = ::esp_ble_gatts_send_indicate( - getService()->getServer()->getGattsIf(), - getService()->getServer()->getConnId(), - getHandle(), length, (uint8_t*)m_value.getValue().data(), false); // The need_confirm = false makes this a notify. - if (errRc != ESP_OK) { - ESP_LOGE(LOG_TAG, "<< esp_ble_gatts_send_indicate: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); - return; + size_t length = m_value.getValue().length(); + if(!is_notification) + m_semaphoreConfEvt.take("indicate"); + esp_err_t errRc = ::esp_ble_gatts_send_indicate( + getService()->getServer()->getGattsIf(), + myPair.first, + getHandle(), length, (uint8_t*)m_value.getValue().data(), !is_notification); // The need_confirm = false makes this a notify. + if (errRc != ESP_OK) { + ESP_LOGE(LOG_TAG, "<< esp_ble_gatts_send_ %s: rc=%d %s",is_notification?"notify":"indicate", errRc, GeneralUtils::errorToString(errRc)); + m_semaphoreConfEvt.give(); + return; + } + if(!is_notification) + m_semaphoreConfEvt.wait("indicate"); } - - m_semaphoreConfEvt.wait("notify"); - ESP_LOGD(LOG_TAG, "<< notify"); } // Notify @@ -580,9 +543,9 @@ void BLECharacteristic::notify() { void BLECharacteristic::setBroadcastProperty(bool value) { //ESP_LOGD(LOG_TAG, "setBroadcastProperty(%d)", value); if (value) { - m_properties = (esp_gatt_char_prop_t) (m_properties | ESP_GATT_CHAR_PROP_BIT_BROADCAST); + m_properties = (esp_gatt_char_prop_t)(m_properties | ESP_GATT_CHAR_PROP_BIT_BROADCAST); } else { - m_properties = (esp_gatt_char_prop_t) (m_properties & ~ESP_GATT_CHAR_PROP_BIT_BROADCAST); + m_properties = (esp_gatt_char_prop_t)(m_properties & ~ESP_GATT_CHAR_PROP_BIT_BROADCAST); } } // setBroadcastProperty @@ -592,7 +555,7 @@ void BLECharacteristic::setBroadcastProperty(bool value) { * @param [in] pCallbacks An instance of a callbacks structure used to define any callbacks for the characteristic. */ void BLECharacteristic::setCallbacks(BLECharacteristicCallbacks* pCallbacks) { - ESP_LOGD(LOG_TAG, ">> setCallbacks: 0x%x", (uint32_t) pCallbacks); + ESP_LOGD(LOG_TAG, ">> setCallbacks: 0x%x", (uint32_t)pCallbacks); m_pCallbacks = pCallbacks; ESP_LOGD(LOG_TAG, "<< setCallbacks"); } // setCallbacks @@ -622,9 +585,9 @@ void BLECharacteristic::setHandle(uint16_t handle) { void BLECharacteristic::setIndicateProperty(bool value) { //ESP_LOGD(LOG_TAG, "setIndicateProperty(%d)", value); if (value) { - m_properties = (esp_gatt_char_prop_t) (m_properties | ESP_GATT_CHAR_PROP_BIT_INDICATE); + m_properties = (esp_gatt_char_prop_t)(m_properties | ESP_GATT_CHAR_PROP_BIT_INDICATE); } else { - m_properties = (esp_gatt_char_prop_t) (m_properties & ~ESP_GATT_CHAR_PROP_BIT_INDICATE); + m_properties = (esp_gatt_char_prop_t)(m_properties & ~ESP_GATT_CHAR_PROP_BIT_INDICATE); } } // setIndicateProperty @@ -636,9 +599,9 @@ void BLECharacteristic::setIndicateProperty(bool value) { void BLECharacteristic::setNotifyProperty(bool value) { //ESP_LOGD(LOG_TAG, "setNotifyProperty(%d)", value); if (value) { - m_properties = (esp_gatt_char_prop_t) (m_properties | ESP_GATT_CHAR_PROP_BIT_NOTIFY); + m_properties = (esp_gatt_char_prop_t)(m_properties | ESP_GATT_CHAR_PROP_BIT_NOTIFY); } else { - m_properties = (esp_gatt_char_prop_t) (m_properties & ~ESP_GATT_CHAR_PROP_BIT_NOTIFY); + m_properties = (esp_gatt_char_prop_t)(m_properties & ~ESP_GATT_CHAR_PROP_BIT_NOTIFY); } } // setNotifyProperty @@ -650,9 +613,9 @@ void BLECharacteristic::setNotifyProperty(bool value) { void BLECharacteristic::setReadProperty(bool value) { //ESP_LOGD(LOG_TAG, "setReadProperty(%d)", value); if (value) { - m_properties = (esp_gatt_char_prop_t) (m_properties | ESP_GATT_CHAR_PROP_BIT_READ); + m_properties = (esp_gatt_char_prop_t)(m_properties | ESP_GATT_CHAR_PROP_BIT_READ); } else { - m_properties = (esp_gatt_char_prop_t) (m_properties & ~ESP_GATT_CHAR_PROP_BIT_READ); + m_properties = (esp_gatt_char_prop_t)(m_properties & ~ESP_GATT_CHAR_PROP_BIT_READ); } } // setReadProperty @@ -683,7 +646,7 @@ void BLECharacteristic::setValue(uint8_t* data, size_t length) { * @return N/A. */ void BLECharacteristic::setValue(std::string value) { - setValue((uint8_t*) (value.data()), value.length()); + setValue((uint8_t*)(value.data()), value.length()); } // setValue void BLECharacteristic::setValue(uint16_t& data16) { @@ -713,13 +676,13 @@ void BLECharacteristic::setValue(int& data32) { void BLECharacteristic::setValue(float& data32) { uint8_t temp[4]; - *((float*) temp) = data32; + *((float*)temp) = data32; setValue(temp, 4); } // setValue void BLECharacteristic::setValue(double& data64) { uint8_t temp[8]; - *((double*) temp) = data64; + *((double*)temp) = data64; setValue(temp, 8); } // setValue @@ -731,9 +694,9 @@ void BLECharacteristic::setValue(double& data64) { void BLECharacteristic::setWriteNoResponseProperty(bool value) { //ESP_LOGD(LOG_TAG, "setWriteNoResponseProperty(%d)", value); if (value) { - m_properties = (esp_gatt_char_prop_t) (m_properties | ESP_GATT_CHAR_PROP_BIT_WRITE_NR); + m_properties = (esp_gatt_char_prop_t)(m_properties | ESP_GATT_CHAR_PROP_BIT_WRITE_NR); } else { - m_properties = (esp_gatt_char_prop_t) (m_properties & ~ESP_GATT_CHAR_PROP_BIT_WRITE_NR); + m_properties = (esp_gatt_char_prop_t)(m_properties & ~ESP_GATT_CHAR_PROP_BIT_WRITE_NR); } } // setWriteNoResponseProperty @@ -745,9 +708,9 @@ void BLECharacteristic::setWriteNoResponseProperty(bool value) { void BLECharacteristic::setWriteProperty(bool value) { //ESP_LOGD(LOG_TAG, "setWriteProperty(%d)", value); if (value) { - m_properties = (esp_gatt_char_prop_t) (m_properties | ESP_GATT_CHAR_PROP_BIT_WRITE); + m_properties = (esp_gatt_char_prop_t)(m_properties | ESP_GATT_CHAR_PROP_BIT_WRITE); } else { - m_properties = (esp_gatt_char_prop_t) (m_properties & ~ESP_GATT_CHAR_PROP_BIT_WRITE); + m_properties = (esp_gatt_char_prop_t)(m_properties & ~ESP_GATT_CHAR_PROP_BIT_WRITE); } } // setWriteProperty diff --git a/cpp_utils/BLECharacteristic.h b/cpp_utils/BLECharacteristic.h index bad5ba7a..5eb1e8d6 100644 --- a/cpp_utils/BLECharacteristic.h +++ b/cpp_utils/BLECharacteristic.h @@ -27,30 +27,27 @@ class BLECharacteristicCallbacks; */ class BLEDescriptorMap { public: - void setByUUID(const char* uuid, BLEDescriptor* pDescriptor); - void setByUUID(BLEUUID uuid, BLEDescriptor* pDescriptor); + void setByUUID(const char* uuid, BLEDescriptor* pDescriptor); + void setByUUID(BLEUUID uuid, BLEDescriptor* pDescriptor); void setByHandle(uint16_t handle, BLEDescriptor* pDescriptor); BLEDescriptor* getByUUID(const char* uuid); BLEDescriptor* getByUUID(BLEUUID uuid); BLEDescriptor* getByHandle(uint16_t handle); std::string toString(); - void handleGATTServerEvent( - esp_gatts_cb_event_t event, - esp_gatt_if_t gatts_if, - esp_ble_gatts_cb_param_t* param); + void handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t gatts_if, esp_ble_gatts_cb_param_t* param); BLEDescriptor* getFirst(); BLEDescriptor* getNext(); private: - std::map m_uuidMap; - std::map m_handleMap; - std::map::iterator m_iterator; + std::map m_uuidMap; + std::map m_handleMap; + std::map::iterator m_iterator; }; /** * @brief The model of a %BLE Characteristic. * - * A %BLE Characteristic is an identified value container that manages a value. It is exposed by a %BLE server and + * A BLE Characteristic is an identified value container that manages a value. It is exposed by a BLE server and * can be read and written to by a %BLE client. */ class BLECharacteristic { @@ -59,16 +56,15 @@ class BLECharacteristic { BLECharacteristic(BLEUUID uuid, uint32_t properties = 0); virtual ~BLECharacteristic(); - void addDescriptor(BLEDescriptor* pDescriptor); + void addDescriptor(BLEDescriptor* pDescriptor); BLEDescriptor* getDescriptorByUUID(const char* descriptorUUID); BLEDescriptor* getDescriptorByUUID(BLEUUID descriptorUUID); - //size_t getLength(); - BLEUUID getUUID(); - std::string getValue(); - uint8_t* getData(); + BLEUUID getUUID(); + std::string getValue(); + uint8_t* getData(); void indicate(); - void notify(); + void notify(bool is_notification = true); void setBroadcastProperty(bool value); void setCallbacks(BLECharacteristicCallbacks* pCallbacks); void setIndicateProperty(bool value); @@ -80,19 +76,19 @@ class BLECharacteristic { void setValue(uint32_t& data32); void setValue(int& data32); void setValue(float& data32); - void setValue(double& data64); + void setValue(double& data64); void setWriteProperty(bool value); void setWriteNoResponseProperty(bool value); std::string toString(); uint16_t getHandle(); void setAccessPermissions(esp_gatt_perm_t perm); - static const uint32_t PROPERTY_READ = 1 << 0; - static const uint32_t PROPERTY_WRITE = 1 << 1; - static const uint32_t PROPERTY_NOTIFY = 1 << 2; - static const uint32_t PROPERTY_BROADCAST = 1 << 3; - static const uint32_t PROPERTY_INDICATE = 1 << 4; - static const uint32_t PROPERTY_WRITE_NR = 1 << 5; + static const uint32_t PROPERTY_READ = 1<<0; + static const uint32_t PROPERTY_WRITE = 1<<1; + static const uint32_t PROPERTY_NOTIFY = 1<<2; + static const uint32_t PROPERTY_BROADCAST = 1<<3; + static const uint32_t PROPERTY_INDICATE = 1<<4; + static const uint32_t PROPERTY_WRITE_NR = 1<<5; private: @@ -101,24 +97,24 @@ class BLECharacteristic { friend class BLEDescriptor; friend class BLECharacteristicMap; - BLEUUID m_bleUUID; - BLEDescriptorMap m_descriptorMap; - uint16_t m_handle; - esp_gatt_char_prop_t m_properties; + BLEUUID m_bleUUID; + BLEDescriptorMap m_descriptorMap; + uint16_t m_handle; + esp_gatt_char_prop_t m_properties; BLECharacteristicCallbacks* m_pCallbacks; - BLEService* m_pService; - BLEValue m_value; - esp_gatt_perm_t m_permissions = ESP_GATT_PERM_READ | ESP_GATT_PERM_WRITE; + BLEService* m_pService; + BLEValue m_value; + esp_gatt_perm_t m_permissions = ESP_GATT_PERM_READ | ESP_GATT_PERM_WRITE; void handleGATTServerEvent( - esp_gatts_cb_event_t event, - esp_gatt_if_t gatts_if, + esp_gatts_cb_event_t event, + esp_gatt_if_t gatts_if, esp_ble_gatts_cb_param_t* param); - void executeCreate(BLEService* pService); + void executeCreate(BLEService* pService); esp_gatt_char_prop_t getProperties(); - BLEService* getService(); - void setHandle(uint16_t handle); + BLEService* getService(); + void setHandle(uint16_t handle); FreeRTOS::Semaphore m_semaphoreCreateEvt = FreeRTOS::Semaphore("CreateEvt"); FreeRTOS::Semaphore m_semaphoreConfEvt = FreeRTOS::Semaphore("ConfEvt"); }; // BLECharacteristic diff --git a/cpp_utils/BLEClient.cpp b/cpp_utils/BLEClient.cpp index 2a8d6f0c..8009f408 100644 --- a/cpp_utils/BLEClient.cpp +++ b/cpp_utils/BLEClient.cpp @@ -18,6 +18,7 @@ #include #include #include +#include "BLEDevice.h" #ifdef ARDUINO_ARCH_ESP32 #include "esp32-hal-log.h" #endif @@ -40,13 +41,14 @@ * We will assume that a BLERemoteService contains a map that maps BLEUUIDs to the set of owned characteristics * and that a BLECharacteristic contains a map that maps BLEUUIDs to the set of owned descriptors. * + * */ static const char* LOG_TAG = "BLEClient"; BLEClient::BLEClient() { m_pClientCallbacks = nullptr; - m_conn_id = 0; - m_gattc_if = 0; + m_conn_id = ESP_GATT_IF_NONE; + m_gattc_if = ESP_GATT_IF_NONE; m_haveServices = false; m_isConnected = false; // Initially, we are flagged as not connected. } // BLEClient @@ -80,22 +82,31 @@ void BLEClient::clearServices() { ESP_LOGD(LOG_TAG, "<< clearServices"); } // clearServices +/** + * Add overloaded function to ease connect to peer device with not public address + */ +bool BLEClient::connect(BLEAdvertisedDevice* device) { + BLEAddress address = device->getAddress(); + esp_ble_addr_type_t type = device->getAddressType(); + return connect(address, type); +} /** * @brief Connect to the partner (BLE Server). * @param [in] address The address of the partner. * @return True on success. */ -bool BLEClient::connect(BLEAddress address) { +bool BLEClient::connect(BLEAddress address, esp_ble_addr_type_t type) { ESP_LOGD(LOG_TAG, ">> connect(%s)", address.toString().c_str()); // We need the connection handle that we get from registering the application. We register the app // and then block on its completion. When the event has arrived, we will have the handle. + m_appId = BLEDevice::m_appId++; + BLEDevice::addPeerDevice(this, true, m_appId); m_semaphoreRegEvt.take("connect"); - clearServices(); // Delete any services that may exist. - - esp_err_t errRc = ::esp_ble_gattc_app_register(0); + // clearServices(); // we dont need to delete services since every client is unique? + esp_err_t errRc = ::esp_ble_gattc_app_register(m_appId); if (errRc != ESP_OK) { ESP_LOGE(LOG_TAG, "esp_ble_gattc_app_register: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); return false; @@ -108,10 +119,10 @@ bool BLEClient::connect(BLEAddress address) { // Perform the open connection request against the target BLE Server. m_semaphoreOpenEvt.take("connect"); errRc = ::esp_ble_gattc_open( - getGattcIf(), + m_gattc_if, *getPeerAddress().getNative(), // address - BLE_ADDR_TYPE_PUBLIC, // Note: This was added on 2018-04-03 when the latest ESP-IDF was detected to have changed the signature. - 1 // direct connection + type, // Note: This was added on 2018-04-03 when the latest ESP-IDF was detected to have changed the signature. + 1 // direct connection <-- maybe needs to be changed in case of direct indirect connection??? ); if (errRc != ESP_OK) { ESP_LOGE(LOG_TAG, "esp_ble_gattc_open: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); @@ -135,8 +146,6 @@ void BLEClient::disconnect() { ESP_LOGE(LOG_TAG, "esp_ble_gattc_close: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); return; } - esp_ble_gattc_app_unregister(getGattcIf()); - m_peerAddress = BLEAddress("00:00:00:00:00:00"); ESP_LOGD(LOG_TAG, "<< disconnect()"); } // disconnect @@ -149,8 +158,21 @@ void BLEClient::gattClientEventHandler( esp_gatt_if_t gattc_if, esp_ble_gattc_cb_param_t* evtParam) { + ESP_LOGD(LOG_TAG, "gattClientEventHandler [esp_gatt_if: %d] ... %s", + gattc_if, BLEUtils::gattClientEventTypeToString(event).c_str()); + // Execute handler code based on the type of event received. - switch (event) { + switch(event) { + + case ESP_GATTC_SRVC_CHG_EVT: + ESP_LOGI(LOG_TAG, "SERVICE CHANGED"); + break; + + case ESP_GATTC_CLOSE_EVT: { + // esp_ble_gattc_app_unregister(m_appId); + // BLEDevice::removePeerDevice(m_gattc_if, true); + break; + } // // ESP_GATTC_DISCONNECT_EVT @@ -162,10 +184,12 @@ void BLEClient::gattClientEventHandler( case ESP_GATTC_DISCONNECT_EVT: { // If we receive a disconnect event, set the class flag that indicates that we are // no longer connected. + m_isConnected = false; if (m_pClientCallbacks != nullptr) { m_pClientCallbacks->onDisconnect(this); } - m_isConnected = false; + BLEDevice::removePeerDevice(m_appId, true); + esp_ble_gattc_app_unregister(m_gattc_if); m_semaphoreRssiCmplEvt.give(); m_semaphoreSearchCmplEvt.give(1); break; @@ -178,7 +202,6 @@ void BLEClient::gattClientEventHandler( // - esp_gatt_status_t status // - uint16_t conn_id // - esp_bd_addr_t remote_bda - // - uint16_t mtu // case ESP_GATTC_OPEN_EVT: { m_conn_id = evtParam->open.conn_id; @@ -206,6 +229,26 @@ void BLEClient::gattClientEventHandler( break; } // ESP_GATTC_REG_EVT + case ESP_GATTC_CFG_MTU_EVT: + if(evtParam->cfg_mtu.status != ESP_GATT_OK) { + ESP_LOGE(LOG_TAG,"Config mtu failed"); + } + m_mtu = evtParam->cfg_mtu.mtu; + break; + + case ESP_GATTC_CONNECT_EVT: { + BLEDevice::updatePeerDevice(this, true, m_gattc_if); + esp_err_t errRc = esp_ble_gattc_send_mtu_req(gattc_if, evtParam->connect.conn_id); + if (errRc != ESP_OK) { + ESP_LOGE(LOG_TAG, "esp_ble_gattc_send_mtu_req: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); + } +#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig + if(BLEDevice::m_securityLevel){ + esp_ble_set_encryption(evtParam->connect.remote_bda, BLEDevice::m_securityLevel); + } +#endif // CONFIG_BLE_SMP_ENABLE + break; + } // ESP_GATTC_CONNECT_EVT // // ESP_GATTC_SEARCH_CMPL_EVT @@ -215,6 +258,21 @@ void BLEClient::gattClientEventHandler( // - uint16_t conn_id // case ESP_GATTC_SEARCH_CMPL_EVT: { + esp_ble_gattc_cb_param_t* p_data = (esp_ble_gattc_cb_param_t*)evtParam; + if (p_data->search_cmpl.status != ESP_GATT_OK){ + ESP_LOGE(LOG_TAG, "search service failed, error status = %x", p_data->search_cmpl.status); + break; + } +#ifndef ARDUINO_ARCH_ESP32 +// commented out just for now to keep backward compatibility + // if(p_data->search_cmpl.searched_service_source == ESP_GATT_SERVICE_FROM_REMOTE_DEVICE) { + // ESP_LOGI(LOG_TAG, "Get service information from remote device"); + // } else if (p_data->search_cmpl.searched_service_source == ESP_GATT_SERVICE_FROM_NVS_FLASH) { + // ESP_LOGI(LOG_TAG, "Get service information from flash"); + // } else { + // ESP_LOGI(LOG_TAG, "unknown service source"); + // } +#endif m_semaphoreSearchCmplEvt.give(0); break; } // ESP_GATTC_SEARCH_CMPL_EVT @@ -238,6 +296,7 @@ void BLEClient::gattClientEventHandler( evtParam->search_res.end_handle ); m_servicesMap.insert(std::pair(uuid.toString(), pRemoteService)); + m_servicesMapByInstID.insert(std::pair(pRemoteService, evtParam->search_res.srvc_id.inst_id)); break; } // ESP_GATTC_SEARCH_RES_EVT @@ -336,7 +395,7 @@ BLERemoteService* BLEClient::getService(BLEUUID uuid) { } } // End of each of the services. ESP_LOGD(LOG_TAG, "<< getService: not found"); - throw new BLEUuidNotFoundException; + return nullptr; } // getService @@ -355,20 +414,21 @@ std::map* BLEClient::getServices() { * and will culminate with an ESP_GATTC_SEARCH_CMPL_EVT when all have been received. */ ESP_LOGD(LOG_TAG, ">> getServices"); - +// TODO implement retrieving services from cache clearServices(); // Clear any services that may exist. esp_err_t errRc = esp_ble_gattc_search_service( getGattcIf(), getConnId(), - nullptr // Filter UUID + NULL // Filter UUID ); + m_semaphoreSearchCmplEvt.take("getServices"); if (errRc != ESP_OK) { ESP_LOGE(LOG_TAG, "esp_ble_gattc_search_service: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); return &m_servicesMap; } - // If successful, remember that we now have services. + // If sucessfull, remember that we now have services. m_haveServices = (m_semaphoreSearchCmplEvt.wait("getServices") == 0); ESP_LOGD(LOG_TAG, "<< getServices"); return &m_servicesMap; @@ -450,6 +510,9 @@ void BLEClient::setValue(BLEUUID serviceUUID, BLEUUID characteristicUUID, std::s ESP_LOGD(LOG_TAG, "<< setValue"); } // setValue +uint16_t BLEClient::getMTU() { + return m_mtu; +} /** * @brief Return a string representation of this client. diff --git a/cpp_utils/BLEClient.h b/cpp_utils/BLEClient.h index d66a8b4f..1b8144d5 100644 --- a/cpp_utils/BLEClient.h +++ b/cpp_utils/BLEClient.h @@ -19,9 +19,11 @@ #include "BLERemoteService.h" #include "BLEService.h" #include "BLEAddress.h" +#include "BLEAdvertisedDevice.h" class BLERemoteService; class BLEClientCallbacks; +class BLEAdvertisedDevice; /** * @brief A model of a %BLE client. @@ -31,7 +33,8 @@ class BLEClient { BLEClient(); ~BLEClient(); - bool connect(BLEAddress address); // Connect to the remote BLE Server + bool connect(BLEAdvertisedDevice* device); + bool connect(BLEAddress address, esp_ble_addr_type_t type = BLE_ADDR_TYPE_PUBLIC); // Connect to the remote BLE Server void disconnect(); // Disconnect from the remote BLE Server BLEAddress getPeerAddress(); // Get the address of the remote BLE Server int getRssi(); // Get the RSSI of the remote BLE Server @@ -47,12 +50,15 @@ class BLEClient { bool isConnected(); // Return true if we are connected. + void setClientCallbacks(BLEClientCallbacks *pClientCallbacks); void setValue(BLEUUID serviceUUID, BLEUUID characteristicUUID, std::string value); // Set the value of a given characteristic at a given service. - void setClientCallbacks(BLEClientCallbacks* pClientCallbacks); std::string toString(); // Return a string representation of this client. + uint16_t getConnId(); + esp_gatt_if_t getGattcIf(); + uint16_t getMTU(); - +uint16_t m_appId; private: friend class BLEDevice; friend class BLERemoteService; @@ -64,14 +70,12 @@ class BLEClient { esp_gatt_if_t gattc_if, esp_ble_gattc_cb_param_t* param); - uint16_t getConnId(); - esp_gatt_if_t getGattcIf(); + BLEAddress m_peerAddress = BLEAddress((uint8_t*)"\0\0\0\0\0\0"); // The BD address of the remote server. uint16_t m_conn_id; // int m_deviceType; - BLEAddress m_peerAddress = BLEAddress((uint8_t*) "\0\0\0\0\0\0"); // The BD address of the remote server. esp_gatt_if_t m_gattc_if; - bool m_haveServices; // Have we previously obtain the set of services from the remote server. - bool m_isConnected; // Are we currently connected. + bool m_haveServices = false; // Have we previously obtain the set of services from the remote server. + bool m_isConnected = false; // Are we currently connected. BLEClientCallbacks* m_pClientCallbacks; FreeRTOS::Semaphore m_semaphoreRegEvt = FreeRTOS::Semaphore("RegEvt"); @@ -79,7 +83,9 @@ class BLEClient { FreeRTOS::Semaphore m_semaphoreSearchCmplEvt = FreeRTOS::Semaphore("SearchCmplEvt"); FreeRTOS::Semaphore m_semaphoreRssiCmplEvt = FreeRTOS::Semaphore("RssiCmplEvt"); std::map m_servicesMap; + std::map m_servicesMapByInstID; void clearServices(); // Clear any existing services. + uint16_t m_mtu = 23; }; // class BLEDevice diff --git a/cpp_utils/BLEDescriptor.cpp b/cpp_utils/BLEDescriptor.cpp index 5f23026f..4d7b5efd 100644 --- a/cpp_utils/BLEDescriptor.cpp +++ b/cpp_utils/BLEDescriptor.cpp @@ -29,21 +29,21 @@ static const char* LOG_TAG = "BLEDescriptor"; /** * @brief BLEDescriptor constructor. */ -BLEDescriptor::BLEDescriptor(const char* uuid) : BLEDescriptor(BLEUUID(uuid)) { +BLEDescriptor::BLEDescriptor(const char* uuid, uint16_t len) : BLEDescriptor(BLEUUID(uuid), len) { } /** * @brief BLEDescriptor constructor. */ -BLEDescriptor::BLEDescriptor(BLEUUID uuid) { +BLEDescriptor::BLEDescriptor(BLEUUID uuid, uint16_t max_len) { m_bleUUID = uuid; m_value.attr_len = 0; // Initial length is 0. - m_value.attr_max_len = ESP_GATT_MAX_ATTR_LEN; // Maximum length of the data. + m_value.attr_max_len = max_len; // Maximum length of the data. m_handle = NULL_HANDLE; // Handle is initially unknown. m_pCharacteristic = nullptr; // No initial characteristic. m_pCallback = nullptr; // No initial callback. - m_value.attr_value = (uint8_t*) malloc(ESP_GATT_MAX_ATTR_LEN); // Allocate storage for the value. + m_value.attr_value = (uint8_t*) malloc(max_len); // Allocate storage for the value. } // BLEDescriptor @@ -70,12 +70,12 @@ void BLEDescriptor::executeCreate(BLECharacteristic* pCharacteristic) { m_pCharacteristic = pCharacteristic; // Save the characteristic associated with this service. esp_attr_control_t control; - control.auto_rsp = ESP_GATT_RSP_BY_APP; + control.auto_rsp = ESP_GATT_AUTO_RSP; m_semaphoreCreateEvt.take("executeCreate"); esp_err_t errRc = ::esp_ble_gatts_add_char_descr( pCharacteristic->getService()->getHandle(), getUUID().getNative(), - (esp_gatt_perm_t)(ESP_GATT_PERM_READ | ESP_GATT_PERM_WRITE), + (esp_gatt_perm_t)m_permissions, &m_value, &control); if (errRc != ESP_OK) { @@ -143,17 +143,6 @@ void BLEDescriptor::handleGATTServerEvent( // - uint16_t service_handle // - esp_bt_uuid_t char_uuid case ESP_GATTS_ADD_CHAR_DESCR_EVT: { - /* - ESP_LOGD(LOG_TAG, "DEBUG: m_pCharacteristic: %x", (uint32_t)m_pCharacteristic); - ESP_LOGD(LOG_TAG, "DEBUG: m_bleUUID: %s, add_char_descr.char_uuid: %s, equals: %d", - m_bleUUID.toString().c_str(), - BLEUUID(param->add_char_descr.char_uuid).toString().c_str(), - m_bleUUID.equals(BLEUUID(param->add_char_descr.char_uuid))); - ESP_LOGD(LOG_TAG, "DEBUG: service->getHandle: %x, add_char_descr.service_handle: %x", - m_pCharacteristic->getService()->getHandle(), param->add_char_descr.service_handle); - ESP_LOGD(LOG_TAG, "DEBUG: service->lastCharacteristic: %x", - (uint32_t)m_pCharacteristic->getService()->getLastCreatedCharacteristic()); - */ if (m_pCharacteristic != nullptr && m_bleUUID.equals(BLEUUID(param->add_char_descr.descr_uuid)) && m_pCharacteristic->getService()->getHandle() == param->add_char_descr.service_handle && @@ -180,23 +169,6 @@ void BLEDescriptor::handleGATTServerEvent( if (param->write.handle == m_handle) { setValue(param->write.value, param->write.len); // Set the value of the descriptor. - esp_gatt_rsp_t rsp; // Build a response. - rsp.attr_value.len = getLength(); - rsp.attr_value.handle = m_handle; - rsp.attr_value.offset = 0; - rsp.attr_value.auth_req = ESP_GATT_AUTH_REQ_NONE; - memcpy(rsp.attr_value.value, getValue(), rsp.attr_value.len); - esp_err_t errRc = ::esp_ble_gatts_send_response( - gatts_if, - param->write.conn_id, - param->write.trans_id, - ESP_GATT_OK, - &rsp); - - if (errRc != ESP_OK) { // Check the return code from the send of the response. - ESP_LOGE(LOG_TAG, "esp_ble_gatts_send_response: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); - } - if (m_pCallback != nullptr) { // We have completed the write, if there is a user supplied callback handler, invoke it now. m_pCallback->onWrite(this); // Invoke the onWrite callback handler. } @@ -223,26 +195,6 @@ void BLEDescriptor::handleGATTServerEvent( m_pCallback->onRead(this); // Invoke the onRead callback method in the callback handler. } - if (param->read.need_rsp) { // Do we need a response - ESP_LOGD(LOG_TAG, "Sending a response (esp_ble_gatts_send_response)"); - esp_gatt_rsp_t rsp; - rsp.attr_value.len = getLength(); - rsp.attr_value.handle = param->read.handle; - rsp.attr_value.offset = 0; - rsp.attr_value.auth_req = ESP_GATT_AUTH_REQ_NONE; - memcpy(rsp.attr_value.value, getValue(), rsp.attr_value.len); - - esp_err_t errRc = ::esp_ble_gatts_send_response( - gatts_if, - param->read.conn_id, - param->read.trans_id, - ESP_GATT_OK, - &rsp); - - if (errRc != ESP_OK) { // Check the return code from the send of the response. - ESP_LOGE(LOG_TAG, "esp_ble_gatts_send_response: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); - } - } // End of need a response. } // End of this is our handle break; } // ESP_GATTS_READ_EVT diff --git a/cpp_utils/BLEDescriptor.h b/cpp_utils/BLEDescriptor.h index d9e0aefb..03cc5791 100644 --- a/cpp_utils/BLEDescriptor.h +++ b/cpp_utils/BLEDescriptor.h @@ -24,8 +24,8 @@ class BLEDescriptorCallbacks; */ class BLEDescriptor { public: - BLEDescriptor(const char* uuid); - BLEDescriptor(BLEUUID uuid); + BLEDescriptor(const char* uuid, uint16_t max_len = 100); + BLEDescriptor(BLEUUID uuid, uint16_t max_len = 100); virtual ~BLEDescriptor(); uint16_t getHandle(); // Get the handle of the descriptor. diff --git a/cpp_utils/BLEDescriptorMap.cpp b/cpp_utils/BLEDescriptorMap.cpp index 075b3025..6b845833 100644 --- a/cpp_utils/BLEDescriptorMap.cpp +++ b/cpp_utils/BLEDescriptorMap.cpp @@ -32,8 +32,8 @@ BLEDescriptor* BLEDescriptorMap::getByUUID(const char* uuid) { */ BLEDescriptor* BLEDescriptorMap::getByUUID(BLEUUID uuid) { for (auto &myPair : m_uuidMap) { - if (myPair.second->getUUID().equals(uuid)) { - return myPair.second; + if (myPair.first->getUUID().equals(uuid)) { + return myPair.first; } } //return m_uuidMap.at(uuid.toString()); @@ -58,7 +58,7 @@ BLEDescriptor* BLEDescriptorMap::getByHandle(uint16_t handle) { * @return N/A. */ void BLEDescriptorMap::setByUUID(const char* uuid, BLEDescriptor* pDescriptor){ - m_uuidMap.insert(std::pair(uuid, pDescriptor)); + m_uuidMap.insert(std::pair(pDescriptor, uuid)); } // setByUUID @@ -70,7 +70,7 @@ void BLEDescriptorMap::setByUUID(const char* uuid, BLEDescriptor* pDescriptor){ * @return N/A. */ void BLEDescriptorMap::setByUUID(BLEUUID uuid, BLEDescriptor* pDescriptor) { - m_uuidMap.insert(std::pair(uuid.toString(), pDescriptor)); + m_uuidMap.insert(std::pair(pDescriptor, uuid.toString())); } // setByUUID @@ -98,7 +98,7 @@ std::string BLEDescriptorMap::toString() { stringStream << "\n"; } count++; - stringStream << "handle: 0x" << std::setw(2) << myPair.second->getHandle() << ", uuid: " + myPair.second->getUUID().toString(); + stringStream << "handle: 0x" << std::setw(2) << myPair.first->getHandle() << ", uuid: " + myPair.first->getUUID().toString(); } return stringStream.str(); } // toString @@ -116,7 +116,7 @@ void BLEDescriptorMap::handleGATTServerEvent( esp_ble_gatts_cb_param_t* param) { // Invoke the handler for every descriptor we have. for (auto &myPair : m_uuidMap) { - myPair.second->handleGATTServerEvent(event, gatts_if, param); + myPair.first->handleGATTServerEvent(event, gatts_if, param); } } // handleGATTServerEvent @@ -128,7 +128,7 @@ void BLEDescriptorMap::handleGATTServerEvent( BLEDescriptor* BLEDescriptorMap::getFirst() { m_iterator = m_uuidMap.begin(); if (m_iterator == m_uuidMap.end()) return nullptr; - BLEDescriptor* pRet = m_iterator->second; + BLEDescriptor* pRet = m_iterator->first; m_iterator++; return pRet; } // getFirst @@ -140,7 +140,7 @@ BLEDescriptor* BLEDescriptorMap::getFirst() { */ BLEDescriptor* BLEDescriptorMap::getNext() { if (m_iterator == m_uuidMap.end()) return nullptr; - BLEDescriptor* pRet = m_iterator->second; + BLEDescriptor* pRet = m_iterator->first; m_iterator++; return pRet; } // getNext diff --git a/cpp_utils/BLEDevice.cpp b/cpp_utils/BLEDevice.cpp index 77380d2b..33efabdb 100644 --- a/cpp_utils/BLEDevice.cpp +++ b/cpp_utils/BLEDevice.cpp @@ -41,11 +41,16 @@ static const char* LOG_TAG = "BLEDevice"; BLEServer* BLEDevice::m_pServer = nullptr; BLEScan* BLEDevice::m_pScan = nullptr; BLEClient* BLEDevice::m_pClient = nullptr; -bool initialized = false; // Have we been initialized? -esp_ble_sec_act_t BLEDevice::m_securityLevel = (esp_ble_sec_act_t) 0; +bool initialized = false; +esp_ble_sec_act_t BLEDevice::m_securityLevel = (esp_ble_sec_act_t)0; BLESecurityCallbacks* BLEDevice::m_securityCallbacks = nullptr; -uint16_t BLEDevice::m_localMTU = 23; +uint16_t BLEDevice::m_localMTU = 23; // not sure if this variable is useful BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; +uint16_t BLEDevice::m_appId = 0; +std::map BLEDevice::m_connectedClientsMap; +gap_event_handler BLEDevice::m_customGapHandler = nullptr; +gattc_event_handler BLEDevice::m_customGattcHandler = nullptr; +gatts_event_handler BLEDevice::m_customGattsHandler = nullptr; /** * @brief Create a new instance of a client. @@ -74,7 +79,7 @@ BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; abort(); #endif // CONFIG_GATTS_ENABLE m_pServer = new BLEServer(); - m_pServer->createApp(0); + m_pServer->createApp(m_appId++); ESP_LOGD(LOG_TAG, "<< createServer"); return m_pServer; } // createServer @@ -100,20 +105,14 @@ BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; switch (event) { case ESP_GATTS_CONNECT_EVT: { - BLEDevice::m_localMTU = 23; #ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig - if (BLEDevice::m_securityLevel) { + if(BLEDevice::m_securityLevel){ esp_ble_set_encryption(param->connect.remote_bda, BLEDevice::m_securityLevel); } #endif // CONFIG_BLE_SMP_ENABLE break; } // ESP_GATTS_CONNECT_EVT - case ESP_GATTS_MTU_EVT: { - BLEDevice::m_localMTU = param->mtu.mtu; - ESP_LOGI(LOG_TAG, "ESP_GATTS_MTU_EVT, MTU %d", BLEDevice::m_localMTU); - break; - } default: { break; } @@ -123,6 +122,11 @@ BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; if (BLEDevice::m_pServer != nullptr) { BLEDevice::m_pServer->handleGATTServerEvent(event, gatts_if, param); } + + if(m_customGattsHandler != nullptr) { + m_customGattsHandler(event, gatts_if, param); + } + } // gattServerEventHandler @@ -146,30 +150,29 @@ BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; switch(event) { case ESP_GATTC_CONNECT_EVT: { - if (BLEDevice::getMTU() != 23) { - esp_err_t errRc = esp_ble_gattc_send_mtu_req(gattc_if, param->connect.conn_id); - if (errRc != ESP_OK) { - ESP_LOGE(LOG_TAG, "esp_ble_gattc_send_mtu_req: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); - } - } #ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig - if (BLEDevice::m_securityLevel) { + if(BLEDevice::m_securityLevel){ esp_ble_set_encryption(param->connect.remote_bda, BLEDevice::m_securityLevel); } #endif // CONFIG_BLE_SMP_ENABLE break; - } // ESP_GATTC_CONNECT_EVT + } // ESP_GATTS_CONNECT_EVT default: break; } // switch + for(auto &myPair : BLEDevice::getPeerDevices(true)) { + conn_status_t conn_status = (conn_status_t)myPair.second; + if(((BLEClient*)conn_status.peer_device)->getGattcIf() == gattc_if || ((BLEClient*)conn_status.peer_device)->getGattcIf() == ESP_GATT_IF_NONE || gattc_if == ESP_GATT_IF_NONE){ + ((BLEClient*)conn_status.peer_device)->gattClientEventHandler(event, gattc_if, param); + } + } - - // If we have a client registered, call it. - if (BLEDevice::m_pClient != nullptr) { - BLEDevice::m_pClient->gattClientEventHandler(event, gattc_if, param); + if(m_customGattcHandler != nullptr) { + m_customGattcHandler(event, gattc_if, param); } + } // gattClientEventHandler @@ -178,33 +181,34 @@ BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; */ /* STATIC */ void BLEDevice::gapEventHandler( esp_gap_ble_cb_event_t event, - esp_ble_gap_cb_param_t* param) { + esp_ble_gap_cb_param_t *param) { BLEUtils::dumpGapEvent(event, param); - switch (event) { - case ESP_GAP_BLE_OOB_REQ_EVT: /* OOB request event */ - ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_OOB_REQ_EVT"); - break; - case ESP_GAP_BLE_LOCAL_IR_EVT: /* BLE local IR event */ - ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_LOCAL_IR_EVT"); - break; - case ESP_GAP_BLE_LOCAL_ER_EVT: /* BLE local ER event */ - ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_LOCAL_ER_EVT"); - break; - case ESP_GAP_BLE_NC_REQ_EVT: - ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_NC_REQ_EVT"); -#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig - if (BLEDevice::m_securityCallbacks != nullptr) { - esp_ble_confirm_reply(param->ble_security.ble_req.bd_addr, BLEDevice::m_securityCallbacks->onConfirmPIN(param->ble_security.key_notif.passkey)); + switch(event) { + + case ESP_GAP_BLE_OOB_REQ_EVT: /* OOB request event */ + ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_OOB_REQ_EVT"); + break; + case ESP_GAP_BLE_LOCAL_IR_EVT: /* BLE local IR event */ + ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_LOCAL_IR_EVT"); + break; + case ESP_GAP_BLE_LOCAL_ER_EVT: /* BLE local ER event */ + ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_LOCAL_ER_EVT"); + break; + case ESP_GAP_BLE_NC_REQ_EVT: /* NUMERIC CONFIRMATION */ + ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_NC_REQ_EVT"); +#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig + if(BLEDevice::m_securityCallbacks != nullptr){ + esp_ble_confirm_reply(param->ble_security.ble_req.bd_addr, BLEDevice::m_securityCallbacks->onConfirmPIN(param->ble_security.key_notif.passkey)); } #endif // CONFIG_BLE_SMP_ENABLE - break; - case ESP_GAP_BLE_PASSKEY_REQ_EVT: /* passkey request event */ + break; + case ESP_GAP_BLE_PASSKEY_REQ_EVT: /* passkey request event */ ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_PASSKEY_REQ_EVT: "); // esp_log_buffer_hex(LOG_TAG, m_remote_bda, sizeof(m_remote_bda)); -#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig - if (BLEDevice::m_securityCallbacks != nullptr) { +#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig + if(BLEDevice::m_securityCallbacks != nullptr){ esp_ble_passkey_reply(param->ble_security.ble_req.bd_addr, true, BLEDevice::m_securityCallbacks->onPassKeyRequest()); } #endif // CONFIG_BLE_SMP_ENABLE @@ -212,14 +216,15 @@ BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; /* * TODO should we add white/black list comparison? */ - case ESP_GAP_BLE_SEC_REQ_EVT: - /* send the positive(true) security response to the peer device to accept the security request. - If not accept the security request, should sent the security response with negative(false) accept value*/ - ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_SEC_REQ_EVT"); -#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig - if (BLEDevice::m_securityCallbacks != nullptr) { + case ESP_GAP_BLE_SEC_REQ_EVT: + /* send the positive(true) security response to the peer device to accept the security request. + If not accept the security request, should sent the security response with negative(false) accept value*/ + ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_SEC_REQ_EVT"); +#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig + if(BLEDevice::m_securityCallbacks!=nullptr){ esp_ble_gap_security_rsp(param->ble_security.ble_req.bd_addr, BLEDevice::m_securityCallbacks->onSecurityRequest()); - } else { + } + else{ esp_ble_gap_security_rsp(param->ble_security.ble_req.bd_addr, true); } #endif // CONFIG_BLE_SMP_ENABLE @@ -227,39 +232,36 @@ BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; /* * */ - case ESP_GAP_BLE_PASSKEY_NOTIF_EVT: // the app will receive this evt when the IO has Output capability and the peer device IO has Input capability. - // show the passkey number to the user to input it in the peer device. - ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_PASSKEY_NOTIF_EVT"); -#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig - if (BLEDevice::m_securityCallbacks != nullptr) { - ESP_LOGI(LOG_TAG, "passKey = %d", param->ble_security.key_notif.passkey); + case ESP_GAP_BLE_PASSKEY_NOTIF_EVT: //the app will receive this evt when the IO has Output capability and the peer device IO has Input capability. + //display the passkey number to the user to input it in the peer deivce within 30 seconds + ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_PASSKEY_NOTIF_EVT"); +#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig + ESP_LOGI(LOG_TAG, "passKey = %d", param->ble_security.key_notif.passkey); + if(BLEDevice::m_securityCallbacks!=nullptr){ BLEDevice::m_securityCallbacks->onPassKeyNotify(param->ble_security.key_notif.passkey); } #endif // CONFIG_BLE_SMP_ENABLE - break; - case ESP_GAP_BLE_KEY_EVT: - //shows the ble key type info share with peer device to the user. - ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_KEY_EVT"); -#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig - ESP_LOGI(LOG_TAG, "key type = %s", BLESecurity::esp_key_type_to_str(param->ble_security.ble_key.key_type)); + break; + case ESP_GAP_BLE_KEY_EVT: + //shows the ble key type info share with peer device to the user. + ESP_LOGD(LOG_TAG, "ESP_GAP_BLE_KEY_EVT"); +#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig + ESP_LOGI(LOG_TAG, "key type = %s", BLESecurity::esp_key_type_to_str(param->ble_security.ble_key.key_type)); #endif // CONFIG_BLE_SMP_ENABLE - break; - case ESP_GAP_BLE_AUTH_CMPL_EVT: - ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_AUTH_CMPL_EVT"); -#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig - if (BLEDevice::m_securityCallbacks != nullptr) { - BLEDevice::m_securityCallbacks->onAuthenticationComplete(param->ble_security.auth_cmpl); - } + break; + case ESP_GAP_BLE_AUTH_CMPL_EVT: + ESP_LOGI(LOG_TAG, "ESP_GAP_BLE_AUTH_CMPL_EVT"); +#ifdef CONFIG_BLE_SMP_ENABLE // Check that BLE SMP (security) is configured in make menuconfig + if(BLEDevice::m_securityCallbacks != nullptr){ + BLEDevice::m_securityCallbacks->onAuthenticationComplete(param->ble_security.auth_cmpl); + } #endif // CONFIG_BLE_SMP_ENABLE - break; - default: + break; + default: { break; + } } // switch - if (BLEDevice::m_pServer != nullptr) { - BLEDevice::m_pServer->handleGAPEvent(event, param); - } - if (BLEDevice::m_pClient != nullptr) { BLEDevice::m_pClient->handleGAPEvent(event, param); } @@ -268,10 +270,13 @@ BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; BLEDevice::getScan()->handleGAPEvent(event, param); } - /* - * Security events: - */ + if(m_bleAdvertising != nullptr) { + BLEDevice::getAdvertising()->handleGAPEvent(event, param); + } + if(m_customGapHandler != nullptr) { + BLEDevice::m_customGapHandler(event, param); + } } // gapEventHandler @@ -326,7 +331,7 @@ BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; * @param deviceName The device name of the device. */ /* STATIC */ void BLEDevice::init(std::string deviceName) { - if (!initialized) { + if(!initialized){ initialized = true; // Set the initialization flag to ensure we are only initialized once. esp_err_t errRc = ESP_OK; @@ -342,6 +347,9 @@ BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; return; } +#ifndef CLASSIC_BT_ENABLED + esp_bt_controller_mem_release(ESP_BT_MODE_CLASSIC_BT); +#endif esp_bt_controller_config_t bt_cfg = BT_CONTROLLER_INIT_CONFIG_DEFAULT(); errRc = esp_bt_controller_init(&bt_cfg); if (errRc != ESP_OK) { @@ -350,9 +358,7 @@ BLEAdvertising* BLEDevice::m_bleAdvertising = nullptr; } #ifndef CLASSIC_BT_ENABLED - // esp_bt_controller_mem_release(ESP_BT_MODE_CLASSIC_BT); //FIXME waiting for response from esp-idf issue errRc = esp_bt_controller_enable(ESP_BT_MODE_BLE); - //errRc = esp_bt_controller_enable(ESP_BT_MODE_BTDM); if (errRc != ESP_OK) { ESP_LOGE(LOG_TAG, "esp_bt_controller_enable: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); return; @@ -544,12 +550,12 @@ bool BLEDevice::getInitialized() { } BLEAdvertising* BLEDevice::getAdvertising() { - if (m_bleAdvertising == nullptr) { + if(m_bleAdvertising == nullptr) { m_bleAdvertising = new BLEAdvertising(); ESP_LOGI(LOG_TAG, "create advertising"); } ESP_LOGD(LOG_TAG, "get advertising"); - return m_bleAdvertising; + return m_bleAdvertising; } void BLEDevice::startAdvertising() { @@ -558,4 +564,81 @@ void BLEDevice::startAdvertising() { ESP_LOGD(LOG_TAG, "<< startAdvertising"); } // startAdvertising +/* multi connect support */ +/* requires a little more work */ +std::map BLEDevice::getPeerDevices(bool _client) { + return m_connectedClientsMap; +} + +BLEClient* BLEDevice::getClientByGattIf(uint16_t conn_id) { + return (BLEClient*)m_connectedClientsMap.find(conn_id)->second.peer_device; +} + +void BLEDevice::updatePeerDevice(void* peer, bool _client, uint16_t conn_id) { + ESP_LOGD(LOG_TAG, "update conn_id: %d, GATT role: %s", conn_id, _client? "client":"server"); + std::map::iterator it = m_connectedClientsMap.find(ESP_GATT_IF_NONE); + if (it != m_connectedClientsMap.end()) { + std::swap(m_connectedClientsMap[conn_id], it->second); + m_connectedClientsMap.erase(it); + }else{ + it = m_connectedClientsMap.find(conn_id); + if (it != m_connectedClientsMap.end()) { + conn_status_t _st = it->second; + _st.peer_device = peer; + std::swap(m_connectedClientsMap[conn_id], _st); + } + } +} + +void BLEDevice::addPeerDevice(void* peer, bool _client, uint16_t conn_id) { + ESP_LOGI(LOG_TAG, "add conn_id: %d, GATT role: %s", conn_id, _client? "client":"server"); + conn_status_t status = { + .peer_device = peer, + .connected = true, + .mtu = 23 + }; + + m_connectedClientsMap.insert(std::pair(conn_id, status)); +} + +void BLEDevice::removePeerDevice(uint16_t conn_id, bool _client) { + ESP_LOGI(LOG_TAG, "remove: %d, GATT role %s", conn_id, _client?"client":"server"); + if(m_connectedClientsMap.find(conn_id) != m_connectedClientsMap.end()) + m_connectedClientsMap.erase(conn_id); +} + +/* multi connect support */ + +/** + * @brief de-Initialize the %BLE environment. + * @param release_memory release the internal BT stack memory + */ +/* STATIC */ void BLEDevice::deinit(bool release_memory) { + if (!initialized) return; + + esp_bluedroid_disable(); + esp_bluedroid_deinit(); + esp_bt_controller_disable(); + esp_bt_controller_deinit(); +#ifndef ARDUINO_ARCH_ESP32 + if (release_memory) { + esp_bt_controller_mem_release(ESP_BT_MODE_BTDM); // <-- require tests because we released classic BT memory and this can cause crash (most likely not, esp-idf takes care of it) + } else { + initialized = false; + } +#endif +} + +void BLEDevice::setCustomGapHandler(gap_event_handler handler) { + m_customGapHandler = handler; +} + +void BLEDevice::setCustomGattcHandler(gattc_event_handler handler) { + m_customGattcHandler = handler; +} + +void BLEDevice::setCustomGattsHandler(gatts_event_handler handler) { + m_customGattsHandler = handler; +} + #endif // CONFIG_BT_ENABLED diff --git a/cpp_utils/BLEDevice.h b/cpp_utils/BLEDevice.h index 9fd53ebb..e9cd40a3 100644 --- a/cpp_utils/BLEDevice.h +++ b/cpp_utils/BLEDevice.h @@ -22,8 +22,12 @@ #include "BLEAddress.h" /** - * @brief %BLE functions. + * @brief BLE functions. */ +typedef void (*gap_event_handler)(esp_gap_ble_cb_event_t event, esp_ble_gap_cb_param_t* param); +typedef void (*gattc_event_handler)(esp_gattc_cb_event_t event, esp_gatt_if_t gattc_if, esp_ble_gattc_cb_param_t* param); +typedef void (*gatts_event_handler)(esp_gatts_cb_event_t event, esp_gatt_if_t gattc_if, esp_ble_gatts_cb_param_t* param); + class BLEDevice { public: @@ -43,19 +47,31 @@ class BLEDevice { static esp_err_t setMTU(uint16_t mtu); static uint16_t getMTU(); static bool getInitialized(); // Returns the state of the device, is it initialized or not? - static BLEAdvertising* getAdvertising(); - static void startAdvertising(); + /* move advertising to BLEDevice for saving ram and flash in beacons */ + static BLEAdvertising* getAdvertising(); + static void startAdvertising(); + static uint16_t m_appId; + /* multi connect */ + static std::map getPeerDevices(bool client); + static void addPeerDevice(void* peer, bool is_client, uint16_t conn_id); + static void updatePeerDevice(void* peer, bool _client, uint16_t conn_id); + static void removePeerDevice(uint16_t conn_id, bool client); + static BLEClient* getClientByGattIf(uint16_t conn_id); + static void setCustomGapHandler(gap_event_handler handler); + static void setCustomGattcHandler(gattc_event_handler handler); + static void setCustomGattsHandler(gatts_event_handler handler); + static void deinit(bool release_memory = false); + static uint16_t m_localMTU; + static esp_ble_sec_act_t m_securityLevel; private: - static BLEServer* m_pServer; - static BLEScan* m_pScan; - static BLEClient* m_pClient; - static esp_ble_sec_act_t m_securityLevel; + static BLEServer* m_pServer; + static BLEScan* m_pScan; + static BLEClient* m_pClient; static BLESecurityCallbacks* m_securityCallbacks; - static uint16_t m_localMTU; - static BLEAdvertising* m_bleAdvertising; - + static BLEAdvertising* m_bleAdvertising; static esp_gatt_if_t getGattcIF(); + static std::map m_connectedClientsMap; static void gattClientEventHandler( esp_gattc_cb_event_t event, @@ -71,6 +87,12 @@ class BLEDevice { esp_gap_ble_cb_event_t event, esp_ble_gap_cb_param_t* param); +public: +/* custom gap and gatt handlers for flexibility */ + static gap_event_handler m_customGapHandler; + static gattc_event_handler m_customGattcHandler; + static gatts_event_handler m_customGattsHandler; + }; // class BLE #endif // CONFIG_BT_ENABLED diff --git a/cpp_utils/BLERemoteCharacteristic.cpp b/cpp_utils/BLERemoteCharacteristic.cpp index 14177eac..21d91b47 100644 --- a/cpp_utils/BLERemoteCharacteristic.cpp +++ b/cpp_utils/BLERemoteCharacteristic.cpp @@ -147,7 +147,7 @@ static bool compareGattId(esp_gatt_id_t id1, esp_gatt_id_t id2) { * @returns N/A */ void BLERemoteCharacteristic::gattClientEventHandler(esp_gattc_cb_event_t event, esp_gatt_if_t gattc_if, esp_ble_gattc_cb_param_t* evtParam) { - switch (event) { + switch(event) { // ESP_GATTC_NOTIFY_EVT // // notify @@ -187,8 +187,7 @@ void BLERemoteCharacteristic::gattClientEventHandler(esp_gattc_cb_event_t event, // and unlock the semaphore to ensure that the requestor of the data can continue. if (evtParam->read.status == ESP_GATT_OK) { m_value = std::string((char*) evtParam->read.value, evtParam->read.value_len); - if (m_rawData != nullptr) free(m_rawData); - + if(m_rawData != nullptr) free(m_rawData); m_rawData = (uint8_t*) calloc(evtParam->read.value_len, sizeof(uint8_t)); memcpy(m_rawData, evtParam->read.value, evtParam->read.value_len); } else { @@ -260,8 +259,8 @@ void BLERemoteCharacteristic::retrieveDescriptors() { // For each descriptor we find, create a BLERemoteDescriptor instance. uint16_t offset = 0; esp_gattc_descr_elem_t result; - while (true) { - uint16_t count = 1; + while(true) { + uint16_t count = 10; esp_gatt_status_t status = ::esp_ble_gattc_get_all_descr( getRemoteService()->getClient()->getGattcIf(), getRemoteService()->getClient()->getConnId(), @@ -281,7 +280,7 @@ void BLERemoteCharacteristic::retrieveDescriptors() { } if (count == 0) break; - ESP_LOGE(LOG_TAG, ""); + ESP_LOGD(LOG_TAG, "Found a descriptor: Handle: %d, UUID: %s", result.handle, BLEUUID(result.uuid).toString().c_str()); // We now have a new characteristic ... let us add that to our set of known characteristics @@ -327,7 +326,7 @@ uint16_t BLERemoteCharacteristic::getHandle() { BLERemoteDescriptor* BLERemoteCharacteristic::getDescriptor(BLEUUID uuid) { ESP_LOGD(LOG_TAG, ">> getDescriptor: uuid: %s", uuid.toString().c_str()); std::string v = uuid.toString(); - for (auto& myPair : m_descriptorMap) { + for (auto &myPair : m_descriptorMap) { if (myPair.first == v) { ESP_LOGD(LOG_TAG, "<< getDescriptor: found"); return myPair.second; @@ -363,7 +362,7 @@ BLEUUID BLERemoteCharacteristic::getUUID() { uint16_t BLERemoteCharacteristic::readUInt16() { std::string value = readValue(); if (value.length() >= 2) { - return *(uint16_t*) value.data(); + return *(uint16_t*)(value.data()); } return 0; } // readUInt16 @@ -376,7 +375,7 @@ uint16_t BLERemoteCharacteristic::readUInt16() { uint32_t BLERemoteCharacteristic::readUInt32() { std::string value = readValue(); if (value.length() >= 4) { - return *(uint32_t*) value.data(); + return *(uint32_t*)(value.data()); } return 0; } // readUInt32 @@ -389,7 +388,7 @@ uint32_t BLERemoteCharacteristic::readUInt32() { uint8_t BLERemoteCharacteristic::readUInt8() { std::string value = readValue(); if (value.length() >= 1) { - return (uint8_t) value[0]; + return (uint8_t)value[0]; } return 0; } // readUInt8 @@ -439,12 +438,7 @@ std::string BLERemoteCharacteristic::readValue() { * unregistering a notification. * @return N/A. */ -void BLERemoteCharacteristic::registerForNotify( - void (*notifyCallback)( - BLERemoteCharacteristic* pBLERemoteCharacteristic, - uint8_t* pData, - size_t length, - bool isNotify), bool notifications) { +void BLERemoteCharacteristic::registerForNotify(notify_callback notifyCallback, bool notifications) { ESP_LOGD(LOG_TAG, ">> registerForNotify(): %s", toString().c_str()); m_notifyCallback = notifyCallback; // Save the notification callback. @@ -463,8 +457,8 @@ void BLERemoteCharacteristic::registerForNotify( } uint8_t val[] = {0x01, 0x00}; - if (!notifications) val[0] = 0x02; - BLERemoteDescriptor* desc = getDescriptor(BLEUUID("0x2902")); + if(!notifications) val[0] = 0x02; + BLERemoteDescriptor* desc = getDescriptor(BLEUUID((uint16_t)0x2902)); desc->writeValue(val, 2); } // End Register else { // If we weren't passed a callback function, then this is an unregistration. @@ -479,7 +473,7 @@ void BLERemoteCharacteristic::registerForNotify( } uint8_t val[] = {0x00, 0x00}; - BLERemoteDescriptor* desc = getDescriptor(BLEUUID("0x2902")); + BLERemoteDescriptor* desc = getDescriptor((uint16_t)0x2902); desc->writeValue(val, 2); } // End Unregister @@ -526,7 +520,32 @@ std::string BLERemoteCharacteristic::toString() { * @return N/A. */ void BLERemoteCharacteristic::writeValue(std::string newValue, bool response) { - ESP_LOGD(LOG_TAG, ">> writeValue(), length: %d", newValue.length()); + writeValue((uint8_t*)newValue.c_str(), strlen(newValue.c_str()), response); +} // writeValue + + +/** + * @brief Write the new value for the characteristic. + * + * This is a convenience function. Many BLE characteristics are a single byte of data. + * @param [in] newValue The new byte value to write. + * @param [in] response Whether we require a response from the write. + * @return N/A. + */ +void BLERemoteCharacteristic::writeValue(uint8_t newValue, bool response) { + writeValue(&newValue, 1, response); +} // writeValue + + +/** + * @brief Write the new value for the characteristic from a data buffer. + * @param [in] data A pointer to a data buffer. + * @param [in] length The length of the data in the data buffer. + * @param [in] response Whether we require a response from the write. + */ +void BLERemoteCharacteristic::writeValue(uint8_t* data, size_t length, bool response) { + // writeValue(std::string((char*)data, length), response); + ESP_LOGD(LOG_TAG, ">> writeValue(), length: %d", length); // Check to see that we are connected. if (!getRemoteService()->getClient()->isConnected()) { @@ -535,14 +554,13 @@ void BLERemoteCharacteristic::writeValue(std::string newValue, bool response) { } m_semaphoreWriteCharEvt.take("writeValue"); - // Invoke the ESP-IDF API to perform the write. esp_err_t errRc = ::esp_ble_gattc_write_char( m_pRemoteService->getClient()->getGattcIf(), m_pRemoteService->getClient()->getConnId(), getHandle(), - newValue.length(), - (uint8_t*)newValue.data(), + length, + data, response?ESP_GATT_WRITE_TYPE_RSP:ESP_GATT_WRITE_TYPE_NO_RSP, ESP_GATT_AUTH_REQ_NONE ); @@ -557,30 +575,6 @@ void BLERemoteCharacteristic::writeValue(std::string newValue, bool response) { ESP_LOGD(LOG_TAG, "<< writeValue"); } // writeValue - -/** - * @brief Write the new value for the characteristic. - * - * This is a convenience function. Many BLE characteristics are a single byte of data. - * @param [in] newValue The new byte value to write. - * @param [in] response Whether we require a response from the write. - * @return N/A. - */ -void BLERemoteCharacteristic::writeValue(uint8_t newValue, bool response) { - writeValue(std::string(reinterpret_cast(&newValue), 1), response); -} // writeValue - - -/** - * @brief Write the new value for the characteristic from a data buffer. - * @param [in] data A pointer to a data buffer. - * @param [in] length The length of the data in the data buffer. - * @param [in] response Whether we require a response from the write. - */ -void BLERemoteCharacteristic::writeValue(uint8_t* data, size_t length, bool response) { - writeValue(std::string((char*) data, length), response); -} // writeValue - /** * @brief Read raw data from remote characteristic as hex bytes * @return return pointer data read diff --git a/cpp_utils/BLERemoteCharacteristic.h b/cpp_utils/BLERemoteCharacteristic.h index 0750c1a9..fbcafe8d 100644 --- a/cpp_utils/BLERemoteCharacteristic.h +++ b/cpp_utils/BLERemoteCharacteristic.h @@ -21,6 +21,7 @@ class BLERemoteService; class BLERemoteDescriptor; +typedef void (*notify_callback)(BLERemoteCharacteristic* pBLERemoteCharacteristic, uint8_t* pData, size_t length, bool isNotify); /** * @brief A model of a remote %BLE characteristic. @@ -37,18 +38,18 @@ class BLERemoteCharacteristic { bool canWrite(); bool canWriteNoResponse(); BLERemoteDescriptor* getDescriptor(BLEUUID uuid); + std::map* getDescriptors(); uint16_t getHandle(); BLEUUID getUUID(); - std::map* getDescriptors(); - std::string readValue(void); - uint8_t readUInt8(void); - uint16_t readUInt16(void); - uint32_t readUInt32(void); - void registerForNotify(void (*notifyCallback)(BLERemoteCharacteristic* pBLERemoteCharacteristic, uint8_t* pData, size_t length, bool isNotify), bool notifications = true); + std::string readValue(); + uint8_t readUInt8(); + uint16_t readUInt16(); + uint32_t readUInt32(); + void registerForNotify(notify_callback _callback, bool notifications = true); void writeValue(uint8_t* data, size_t length, bool response = false); void writeValue(std::string newValue, bool response = false); void writeValue(uint8_t newValue, bool response = false); - std::string toString(void); + std::string toString(); uint8_t* readRawData(); private: @@ -58,26 +59,23 @@ class BLERemoteCharacteristic { friend class BLERemoteDescriptor; // Private member functions - void gattClientEventHandler( - esp_gattc_cb_event_t event, - esp_gatt_if_t gattc_if, - esp_ble_gattc_cb_param_t* evtParam); + void gattClientEventHandler(esp_gattc_cb_event_t event, esp_gatt_if_t gattc_if, esp_ble_gattc_cb_param_t* evtParam); BLERemoteService* getRemoteService(); - void removeDescriptors(); - void retrieveDescriptors(); + void removeDescriptors(); + void retrieveDescriptors(); // Private properties - BLEUUID m_uuid; + BLEUUID m_uuid; esp_gatt_char_prop_t m_charProp; - uint16_t m_handle; - BLERemoteService* m_pRemoteService; - FreeRTOS::Semaphore m_semaphoreReadCharEvt = FreeRTOS::Semaphore("ReadCharEvt"); + uint16_t m_handle; + BLERemoteService* m_pRemoteService; + FreeRTOS::Semaphore m_semaphoreReadCharEvt = FreeRTOS::Semaphore("ReadCharEvt"); FreeRTOS::Semaphore m_semaphoreRegForNotifyEvt = FreeRTOS::Semaphore("RegForNotifyEvt"); - FreeRTOS::Semaphore m_semaphoreWriteCharEvt = FreeRTOS::Semaphore("WriteCharEvt"); - std::string m_value; - uint8_t* m_rawData; - void (*m_notifyCallback)(BLERemoteCharacteristic* pBLERemoteCharacteristic, uint8_t* pData, size_t length, bool isNotify); + FreeRTOS::Semaphore m_semaphoreWriteCharEvt = FreeRTOS::Semaphore("WriteCharEvt"); + std::string m_value; + uint8_t *m_rawData; + notify_callback m_notifyCallback; // We maintain a map of descriptors owned by this characteristic keyed by a string representation of the UUID. std::map m_descriptorMap; diff --git a/cpp_utils/BLERemoteService.cpp b/cpp_utils/BLERemoteService.cpp index d632cff5..ef349986 100644 --- a/cpp_utils/BLERemoteService.cpp +++ b/cpp_utils/BLERemoteService.cpp @@ -126,10 +126,9 @@ void BLERemoteService::gattClientEventHandler( * @throws BLEUuidNotFoundException */ BLERemoteCharacteristic* BLERemoteService::getCharacteristic(const char* uuid) { - return getCharacteristic(BLEUUID(uuid)); + return getCharacteristic(BLEUUID(uuid)); } // getCharacteristic - - + /** * @brief Get the characteristic object for the UUID. * @param [in] uuid Characteristic uuid. @@ -152,7 +151,8 @@ BLERemoteCharacteristic* BLERemoteService::getCharacteristic(BLEUUID uuid) { return myPair.second; } } - throw new BLEUuidNotFoundException(); + // throw new BLEUuidNotFoundException(); // <-- we dont want exception here, which will cause app crash, we want to search if any characteristic can be found one after another + return nullptr; } // getCharacteristic @@ -169,7 +169,7 @@ void BLERemoteService::retrieveCharacteristics() { uint16_t offset = 0; esp_gattc_char_elem_t result; while (true) { - uint16_t count = 1; + uint16_t count = 10; // this value is used as in parameter that allows to search max 10 chars with the same uuid esp_gatt_status_t status = ::esp_ble_gattc_get_all_char( getClient()->getGattcIf(), getClient()->getConnId(), diff --git a/cpp_utils/BLERemoteService.h b/cpp_utils/BLERemoteService.h index 387afbdf..2ab86738 100644 --- a/cpp_utils/BLERemoteService.h +++ b/cpp_utils/BLERemoteService.h @@ -33,7 +33,8 @@ class BLERemoteService { BLERemoteCharacteristic* getCharacteristic(BLEUUID uuid); // Get the specified characteristic reference. BLERemoteCharacteristic* getCharacteristic(uint16_t uuid); // Get the specified characteristic reference. std::map* getCharacteristics(); - void getCharacteristics(std::map* pCharacteristicMap); // Get the characteristics map. + std::map* getCharacteristicsByHandle(); // Get the characteristics map. + void getCharacteristics(std::map* pCharacteristicMap); BLEClient* getClient(void); // Get a reference to the client associated with this service. uint16_t getHandle(); // Get the handle of this service. diff --git a/cpp_utils/BLEScan.cpp b/cpp_utils/BLEScan.cpp index 7164626b..e1778b84 100644 --- a/cpp_utils/BLEScan.cpp +++ b/cpp_utils/BLEScan.cpp @@ -101,7 +101,7 @@ void BLEScan::handleGAPEvent( if (found && !m_wantDuplicates) { // If we found a previous entry AND we don't want duplicates, then we are done. ESP_LOGD(LOG_TAG, "Ignoring %s, already seen it.", advertisedAddress.toString().c_str()); - vTaskDelay(1); // <--- allow to switch task in case we scan infinity and dont have new devices to report, or we will blocked here + vTaskDelay(1); // <--- allow to switch task in case we scan infinity and dont have new devices to report, or we are blocked here break; } @@ -314,5 +314,15 @@ BLEAdvertisedDevice BLEScanResults::getDevice(uint32_t i) { return dev; } +BLEScanResults BLEScan::getResults() { + return m_scanResults; +} + +void BLEScan::clearResults() { + for(auto _dev : m_scanResults.m_vectorAdvertisedDevices){ + delete _dev.second; + } + m_scanResults.m_vectorAdvertisedDevices.clear(); +} #endif /* CONFIG_BT_ENABLED */ diff --git a/cpp_utils/BLEServer.cpp b/cpp_utils/BLEServer.cpp index e5c675b8..9b52762d 100755 --- a/cpp_utils/BLEServer.cpp +++ b/cpp_utils/BLEServer.cpp @@ -10,8 +10,7 @@ #include #include #include -#include -//#include +#include "GeneralUtils.h" #include "BLEDevice.h" #include "BLEServer.h" #include "BLEService.h" @@ -33,18 +32,17 @@ static const char* LOG_TAG = "BLEServer"; * the BLEDevice class. */ BLEServer::BLEServer() { - m_appId = -1; - m_gatts_if = -1; + m_appId = ESP_GATT_IF_NONE; + m_gatts_if = ESP_GATT_IF_NONE; m_connectedCount = 0; - m_connId = -1; + m_connId = ESP_GATT_IF_NONE; m_pServerCallbacks = nullptr; - //createApp(0); } // BLEServer void BLEServer::createApp(uint16_t appId) { m_appId = appId; - registerApp(); + registerApp(appId); } // createApp @@ -79,12 +77,10 @@ BLEService* BLEServer::createService(BLEUUID uuid, uint32_t numHandles, uint8_t if (m_serviceMap.getByUUID(uuid) != nullptr) { ESP_LOGW(LOG_TAG, "<< Attempt to create a new service with uuid %s but a service with that UUID already exists.", uuid.toString().c_str()); - //m_semaphoreCreateEvt.give(); - //return nullptr; } BLEService* pService = new BLEService(uuid, numHandles); - pService->m_id = inst_id; + pService->m_instId = inst_id; m_serviceMap.setByUUID(uuid, pService); // Save a reference to this service being on this server. pService->executeCreate(this); // Perform the API calls to actually create the service. @@ -104,7 +100,6 @@ BLEService* BLEServer::getServiceByUUID(const char* uuid) { return m_serviceMap.getByUUID(uuid); } - /** * @brief Get a %BLE Service by its UUID * @param [in] uuid The UUID of the new service. @@ -114,20 +109,6 @@ BLEService* BLEServer::getServiceByUUID(BLEUUID uuid) { return m_serviceMap.getByUUID(uuid); } - -/** - * @brief Returns the amount of services registered to this server - * @param [in] includeDefaultServices Add the amount of default BluetoothLE services defined by the BLE standard - * @return The amount of registered services - */ -int BLEServer::getServiceCount(bool includeDefaultServices) { - if (includeDefaultServices) { - return m_serviceMap.getRegisteredServiceCount() + 2; - } - return m_serviceMap.getRegisteredServiceCount(); -} - - /** * @brief Retrieve the advertising object that can be used to advertise the existence of the server. * @@ -137,7 +118,6 @@ BLEAdvertising* BLEServer::getAdvertising() { return BLEDevice::getAdvertising(); } - uint16_t BLEServer::getConnId() { return m_connId; } @@ -156,41 +136,6 @@ uint16_t BLEServer::getGattsIf() { return m_gatts_if; } -/** - * @brief Handle a received GAP event. - * - * @param [in] event - * @param [in] param - */ -void BLEServer::handleGAPEvent( - esp_gap_ble_cb_event_t event, - esp_ble_gap_cb_param_t* param) { - ESP_LOGD(LOG_TAG, "BLEServer ... handling GAP event!"); - switch (event) { - case ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT: { - /* - esp_ble_adv_params_t adv_params; - adv_params.adv_int_min = 0x20; - adv_params.adv_int_max = 0x40; - adv_params.adv_type = ADV_TYPE_IND; - adv_params.own_addr_type = BLE_ADDR_TYPE_PUBLIC; - adv_params.channel_map = ADV_CHNL_ALL; - adv_params.adv_filter_policy = ADV_FILTER_ALLOW_SCAN_ANY_CON_ANY; - ESP_LOGD(tag, "Starting advertising"); - esp_err_t errRc = ::esp_ble_gap_start_advertising(&adv_params); - if (errRc != ESP_OK) { - ESP_LOGE(tag, "esp_ble_gap_start_advertising: rc=%d %s", errRc, espToString(errRc)); - return; - } - */ - break; - } - - default: - break; - } -} // handleGAPEvent - /** * @brief Handle a GATT Server Event. @@ -201,12 +146,10 @@ void BLEServer::handleGAPEvent( * */ void BLEServer::handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t gatts_if, esp_ble_gatts_cb_param_t* param) { - ESP_LOGD(LOG_TAG, ">> handleGATTServerEvent: %s", BLEUtils::gattServerEventTypeToString(event).c_str()); - - // Invoke the handler for every Service we have. - m_serviceMap.handleGATTServerEvent(event, gatts_if, param); + ESP_LOGD(LOG_TAG, ">> handleGATTServerEvent: %s", + BLEUtils::gattServerEventTypeToString(event).c_str()); - switch (event) { + switch(event) { // ESP_GATTS_ADD_CHAR_EVT - Indicate that a characteristic was added to the service. // add_char: // - esp_gatt_status_t status @@ -218,20 +161,23 @@ void BLEServer::handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t break; } // ESP_GATTS_ADD_CHAR_EVT + case ESP_GATTS_MTU_EVT: + updatePeerMTU(param->mtu.conn_id, param->mtu.mtu); + break; // ESP_GATTS_CONNECT_EVT // connect: // - uint16_t conn_id // - esp_bd_addr_t remote_bda - // - bool is_connected // case ESP_GATTS_CONNECT_EVT: { - m_connId = param->connect.conn_id; // Save the connection id. + m_connId = param->connect.conn_id; + addPeerDevice((void*)this, false, m_connId); if (m_pServerCallbacks != nullptr) { m_pServerCallbacks->onConnect(this); - m_pServerCallbacks->onConnect(this, param); + m_pServerCallbacks->onConnect(this, param); } - m_connectedCount++; // Increment the number of connected devices count. + m_connectedCount++; // Increment the number of connected devices count. break; } // ESP_GATTS_CONNECT_EVT @@ -245,7 +191,7 @@ void BLEServer::handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t // * esp_gatt_srvc_id_t service_id // case ESP_GATTS_CREATE_EVT: { - BLEService* pService = m_serviceMap.getByUUID(param->create.service_id.id.uuid); + BLEService* pService = m_serviceMap.getByUUID(param->create.service_id.id.uuid, param->create.service_id.id.inst_id); // <--- very big bug for multi services with the same uuid m_serviceMap.setByHandle(param->create.service_handle, pService); m_semaphoreCreateEvt.give(); break; @@ -255,9 +201,9 @@ void BLEServer::handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t // ESP_GATTS_DISCONNECT_EVT // // disconnect - // - uint16_t conn_id - // - esp_bd_addr_t remote_bda - // - bool is_connected + // - uint16_t conn_id + // - esp_bd_addr_t remote_bda + // - esp_gatt_conn_reason_t reason // // If we receive a disconnect event then invoke the callback for disconnects (if one is present). // we also want to start advertising again. @@ -267,6 +213,7 @@ void BLEServer::handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t m_pServerCallbacks->onDisconnect(this); } startAdvertising(); //- do this with some delay from the loop() + removePeerDevice(param->disconnect.conn_id, false); break; } // ESP_GATTS_DISCONNECT_EVT @@ -316,9 +263,17 @@ void BLEServer::handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t break; } + case ESP_GATTS_OPEN_EVT: + m_semaphoreOpenEvt.give(param->open.status); + break; + default: break; } + + // Invoke the handler for every Service we have. + m_serviceMap.handleGATTServerEvent(event, gatts_if, param); + ESP_LOGD(LOG_TAG, "<< handleGATTServerEvent"); } // handleGATTServerEvent @@ -328,7 +283,7 @@ void BLEServer::handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t * * @return N/A */ -void BLEServer::registerApp() { +void BLEServer::registerApp(uint16_t m_appId) { ESP_LOGD(LOG_TAG, ">> registerApp - %d", m_appId); m_semaphoreRegisterAppEvt.take("registerApp"); // Take the mutex, will be released by ESP_GATTS_REG_EVT event. ::esp_ble_gatts_app_register(m_appId); @@ -355,7 +310,7 @@ void BLEServer::setCallbacks(BLEServerCallbacks* pCallbacks) { */ void BLEServer::removeService(BLEService* service) { service->stop(); - service->executeDelete(); + service->executeDelete(); m_serviceMap.removeService(service); } @@ -371,6 +326,31 @@ void BLEServer::startAdvertising() { ESP_LOGD(LOG_TAG, "<< startAdvertising"); } // startAdvertising +/** + * Allow to connect GATT server to peer device + * Probably can be used in ANCS for iPhone + */ +bool BLEServer::connect(BLEAddress address) { + esp_bd_addr_t addr; + memcpy(&addr, address.getNative(), 6); + // Perform the open connection request against the target BLE Server. + m_semaphoreOpenEvt.take("connect"); + esp_err_t errRc = ::esp_ble_gatts_open( + getGattsIf(), + addr, // address + 1 // direct connection + ); + if (errRc != ESP_OK) { + ESP_LOGE(LOG_TAG, "esp_ble_gattc_open: rc=%d %s", errRc, GeneralUtils::errorToString(errRc)); + return false; + } + + uint32_t rc = m_semaphoreOpenEvt.wait("connect"); // Wait for the connection to complete. + ESP_LOGD(LOG_TAG, "<< connect(), rc=%d", rc==ESP_GATT_OK); + return rc == ESP_GATT_OK; +} // connect + + void BLEServerCallbacks::onConnect(BLEServer* pServer) { ESP_LOGD("BLEServerCallbacks", ">> onConnect(): Default"); @@ -391,4 +371,51 @@ void BLEServerCallbacks::onDisconnect(BLEServer* pServer) { ESP_LOGD("BLEServerCallbacks", "<< onDisconnect()"); } // onDisconnect +/* multi connect support */ +/* TODO do some more tweaks */ +void BLEServer::updatePeerMTU(uint16_t conn_id, uint16_t mtu) { + // set mtu in conn_status_t + const std::map::iterator it = m_connectedServersMap.find(conn_id); + if (it != m_connectedServersMap.end()) { + it->second.mtu = mtu; + std::swap(m_connectedServersMap[conn_id], it->second); + } +} + +std::map BLEServer::getPeerDevices(bool _client) { + return m_connectedServersMap; +} + + +uint16_t BLEServer::getPeerMTU(uint16_t conn_id) { + return m_connectedServersMap.find(conn_id)->second.mtu; +} + +void BLEServer::addPeerDevice(void* peer, bool _client, uint16_t conn_id) { + conn_status_t status = { + .peer_device = peer, + .connected = true, + .mtu = 23 + }; + + m_connectedServersMap.insert(std::pair(conn_id, status)); +} + +void BLEServer::removePeerDevice(uint16_t conn_id, bool _client) { + m_connectedServersMap.erase(conn_id); +} +/* multi connect support */ + +/** + * Update connection parameters can be called only after connection has been established + */ +void BLEServer::updateConnParams(esp_bd_addr_t remote_bda, uint16_t minInterval, uint16_t maxInterval, uint16_t latency, uint16_t timeout) { + esp_ble_conn_update_params_t conn_params; + memcpy(conn_params.bda, remote_bda, sizeof(esp_bd_addr_t)); + conn_params.latency = latency; + conn_params.max_int = maxInterval; // max_int = 0x20*1.25ms = 40ms + conn_params.min_int = minInterval; // min_int = 0x10*1.25ms = 20ms + conn_params.timeout = timeout; // timeout = 400*10ms = 4000ms + esp_ble_gap_update_conn_params(&conn_params); +} #endif // CONFIG_BT_ENABLED diff --git a/cpp_utils/BLEServer.h b/cpp_utils/BLEServer.h index 799eb25d..d39d8bfe 100755 --- a/cpp_utils/BLEServer.h +++ b/cpp_utils/BLEServer.h @@ -13,6 +13,7 @@ #include #include +// #include "BLEDevice.h" #include "BLEUUID.h" #include "BLEAdvertising.h" @@ -20,8 +21,15 @@ #include "BLEService.h" #include "BLESecurity.h" #include "FreeRTOS.h" +#include "BLEAddress.h" class BLEServerCallbacks; +/* TODO possibly refactor this struct */ +typedef struct { + void *peer_device; // peer device BLEClient or BLEServer - maybe its better to have 2 structures or union here + bool connected; // do we need it? + uint16_t mtu; // every peer device negotiate own mtu +} conn_status_t; /** @@ -31,26 +39,21 @@ class BLEServiceMap { public: BLEService* getByHandle(uint16_t handle); BLEService* getByUUID(const char* uuid); - BLEService* getByUUID(BLEUUID uuid); - void handleGATTServerEvent( - esp_gatts_cb_event_t event, - esp_gatt_if_t gatts_if, - esp_ble_gatts_cb_param_t* param); + BLEService* getByUUID(BLEUUID uuid, uint8_t inst_id = 0); + void handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t gatts_if, esp_ble_gatts_cb_param_t* param); void setByHandle(uint16_t handle, BLEService* service); void setByUUID(const char* uuid, BLEService* service); void setByUUID(BLEUUID uuid, BLEService* service); std::string toString(); BLEService* getFirst(); BLEService* getNext(); - void removeService(BLEService* service); + void removeService(BLEService *service); int getRegisteredServiceCount(); - private: std::map m_handleMap; std::map m_uuidMap; std::map::iterator m_iterator; - }; @@ -61,14 +64,26 @@ class BLEServer { public: uint32_t getConnectedCount(); BLEService* createService(const char* uuid); - BLEService* createService(BLEUUID uuid, uint32_t numHandles = 15, uint8_t inst_id = 0); + BLEService* createService(BLEUUID uuid, uint32_t numHandles=15, uint8_t inst_id=0); BLEAdvertising* getAdvertising(); void setCallbacks(BLEServerCallbacks* pCallbacks); void startAdvertising(); + void removeService(BLEService* service); BLEService* getServiceByUUID(const char* uuid); BLEService* getServiceByUUID(BLEUUID uuid); - void removeService(BLEService* service); - int getServiceCount(bool includeDefaultServices); + bool connect(BLEAddress address); + uint16_t m_appId; + void updateConnParams(esp_bd_addr_t remote_bda, uint16_t minInterval, uint16_t maxInterval, uint16_t latency, uint16_t timeout); + + /* multi connection support */ + std::map getPeerDevices(bool client); + void addPeerDevice(void* peer, bool is_client, uint16_t conn_id); + void removePeerDevice(uint16_t conn_id, bool client); + BLEServer* getServerByConnId(uint16_t conn_id); + void updatePeerMTU(uint16_t connId, uint16_t mtu); + uint16_t getPeerMTU(uint16_t conn_id); + uint16_t getConnId(); + private: BLEServer(); @@ -76,22 +91,22 @@ class BLEServer { friend class BLECharacteristic; friend class BLEDevice; esp_ble_adv_data_t m_adv_data; - uint16_t m_appId; // BLEAdvertising m_bleAdvertising; - uint16_t m_connId; - uint32_t m_connectedCount; - uint16_t m_gatts_if; - FreeRTOS::Semaphore m_semaphoreRegisterAppEvt = FreeRTOS::Semaphore("RegisterAppEvt"); - FreeRTOS::Semaphore m_semaphoreCreateEvt = FreeRTOS::Semaphore("CreateEvt"); + uint16_t m_connId; + uint32_t m_connectedCount; + uint16_t m_gatts_if; + std::map m_connectedServersMap; + + FreeRTOS::Semaphore m_semaphoreRegisterAppEvt = FreeRTOS::Semaphore("RegisterAppEvt"); + FreeRTOS::Semaphore m_semaphoreCreateEvt = FreeRTOS::Semaphore("CreateEvt"); + FreeRTOS::Semaphore m_semaphoreOpenEvt = FreeRTOS::Semaphore("OpenEvt"); BLEServiceMap m_serviceMap; - BLEServerCallbacks* m_pServerCallbacks; + BLEServerCallbacks* m_pServerCallbacks = nullptr; void createApp(uint16_t appId); - uint16_t getConnId(); uint16_t getGattsIf(); void handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t gatts_if, esp_ble_gatts_cb_param_t *param); - void registerApp(); - void handleGAPEvent(esp_gap_ble_cb_event_t event, esp_ble_gap_cb_param_t* param); + void registerApp(uint16_t); }; // BLEServer @@ -109,7 +124,7 @@ class BLEServerCallbacks { * @param [in] pServer A reference to the %BLE server that received the client connection. */ virtual void onConnect(BLEServer* pServer); - virtual void onConnect(BLEServer* pServer, esp_ble_gatts_cb_param_t* param); + virtual void onConnect(BLEServer* pServer, esp_ble_gatts_cb_param_t *param); /** * @brief Handle an existing client disconnection. * diff --git a/cpp_utils/BLEService.cpp b/cpp_utils/BLEService.cpp index 68019608..7e7d67ac 100644 --- a/cpp_utils/BLEService.cpp +++ b/cpp_utils/BLEService.cpp @@ -62,18 +62,13 @@ BLEService::BLEService(BLEUUID uuid, uint16_t numHandles) { */ void BLEService::executeCreate(BLEServer* pServer) { - //ESP_LOGD(LOG_TAG, ">> executeCreate() - Creating service (esp_ble_gatts_create_service) service uuid: %s", getUUID().toString().c_str()); - //getUUID(); // Needed for a weird bug fix - //char x[1000]; - //memcpy(x, &m_uuid, sizeof(m_uuid)); - //char x[10]; - //memcpy(x, &deleteMe, 10); + ESP_LOGD(LOG_TAG, ">> executeCreate() - Creating service (esp_ble_gatts_create_service) service uuid: %s", getUUID().toString().c_str()); m_pServer = pServer; m_semaphoreCreateEvt.take("executeCreate"); // Take the mutex and release at event ESP_GATTS_CREATE_EVT esp_gatt_srvc_id_t srvc_id; srvc_id.is_primary = true; - srvc_id.id.inst_id = m_id; + srvc_id.id.inst_id = m_instId; srvc_id.id.uuid = *m_uuid.getNative(); esp_err_t errRc = ::esp_ble_gatts_create_service(getServer()->getGattsIf(), &srvc_id, m_numHandles); // The maximum number of handles associated with the service. @@ -137,10 +132,10 @@ BLEUUID BLEService::getUUID() { * @return Start the service. */ void BLEService::start() { - // We ask the BLE runtime to start the service and then create each of the characteristics. - // We start the service through its local handle which was returned in the ESP_GATTS_CREATE_EVT event - // obtained as a result of calling esp_ble_gatts_create_service(). - // +// We ask the BLE runtime to start the service and then create each of the characteristics. +// We start the service through its local handle which was returned in the ESP_GATTS_CREATE_EVT event +// obtained as a result of calling esp_ble_gatts_create_service(). +// ESP_LOGD(LOG_TAG, ">> start(): Starting service (esp_ble_gatts_start_service): %s", toString().c_str()); if (m_handle == NULL_HANDLE) { ESP_LOGE(LOG_TAG, "<< !!! We attempted to start a service but don't know its handle!"); @@ -174,9 +169,9 @@ void BLEService::start() { * @brief Stop the service. */ void BLEService::stop() { - // We ask the BLE runtime to start the service and then create each of the characteristics. - // We start the service through its local handle which was returned in the ESP_GATTS_CREATE_EVT event - // obtained as a result of calling esp_ble_gatts_create_service(). +// We ask the BLE runtime to start the service and then create each of the characteristics. +// We start the service through its local handle which was returned in the ESP_GATTS_CREATE_EVT event +// obtained as a result of calling esp_ble_gatts_create_service(). ESP_LOGD(LOG_TAG, ">> stop(): Stopping service (esp_ble_gatts_stop_service): %s", toString().c_str()); if (m_handle == NULL_HANDLE) { ESP_LOGE(LOG_TAG, "<< !!! We attempted to stop a service but don't know its handle!"); @@ -228,6 +223,7 @@ void BLEService::addCharacteristic(BLECharacteristic* pCharacteristic) { // We maintain a mapping of characteristics owned by this service. These are managed by the // BLECharacteristicMap class instance found in m_characteristicMap. We add the characteristic // to the map and then ask the service to add the characteristic at the BLE level (ESP-IDF). + ESP_LOGD(LOG_TAG, ">> addCharacteristic()"); ESP_LOGD(LOG_TAG, "Adding characteristic: uuid=%s to service: %s", pCharacteristic->getUUID().toString().c_str(), @@ -256,7 +252,7 @@ void BLEService::addCharacteristic(BLECharacteristic* pCharacteristic) { BLECharacteristic* BLEService::createCharacteristic(const char* uuid, uint32_t properties) { return createCharacteristic(BLEUUID(uuid), properties); } - + /** * @brief Create a new BLE Characteristic associated with this service. @@ -296,7 +292,6 @@ void BLEService::handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t } pCharacteristic->setHandle(param->add_char.attr_handle); m_characteristicMap.setByHandle(param->add_char.attr_handle, pCharacteristic); - //ESP_LOGD(tag, "Characteristic map: %s", m_characteristicMap.toString().c_str()); break; } // Reached the correct service. break; @@ -342,7 +337,7 @@ void BLEService::handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t // * - bool is_primary // case ESP_GATTS_CREATE_EVT: { - if (getUUID().equals(BLEUUID(param->create.service_id.id.uuid)) && m_id == param->create.service_id.id.inst_id) { + if (getUUID().equals(BLEUUID(param->create.service_id.id.uuid)) && m_instId == param->create.service_id.id.inst_id) { setHandle(param->create.service_handle); m_semaphoreCreateEvt.give(); } diff --git a/cpp_utils/BLEService.h b/cpp_utils/BLEService.h index 711ac707..b42d57f2 100644 --- a/cpp_utils/BLEService.h +++ b/cpp_utils/BLEService.h @@ -27,7 +27,7 @@ class BLECharacteristicMap { void setByUUID(BLECharacteristic* pCharacteristic, const char* uuid); void setByUUID(BLECharacteristic* pCharacteristic, BLEUUID uuid); void setByHandle(uint16_t handle, BLECharacteristic* pCharacteristic); - BLECharacteristic* getByUUID(const char* uuid); + BLECharacteristic* getByUUID(const char* uuid); BLECharacteristic* getByUUID(BLEUUID uuid); BLECharacteristic* getByHandle(uint16_t handle); BLECharacteristic* getFirst(); @@ -53,16 +53,16 @@ class BLEService { BLECharacteristic* createCharacteristic(BLEUUID uuid, uint32_t properties); void dump(); void executeCreate(BLEServer* pServer); - void executeDelete(); + void executeDelete(); BLECharacteristic* getCharacteristic(const char* uuid); BLECharacteristic* getCharacteristic(BLEUUID uuid); BLEUUID getUUID(); BLEServer* getServer(); void start(); - void stop(); + void stop(); std::string toString(); uint16_t getHandle(); - uint8_t m_id = 0; + uint8_t m_instId = 0; private: BLEService(const char* uuid, uint16_t numHandles); @@ -75,8 +75,8 @@ class BLEService { BLECharacteristicMap m_characteristicMap; uint16_t m_handle; - BLECharacteristic* m_lastCreatedCharacteristic; - BLEServer* m_pServer; + BLECharacteristic* m_lastCreatedCharacteristic = nullptr; + BLEServer* m_pServer = nullptr; BLEUUID m_uuid; FreeRTOS::Semaphore m_semaphoreCreateEvt = FreeRTOS::Semaphore("CreateEvt"); @@ -87,10 +87,9 @@ class BLEService { uint16_t m_numHandles; BLECharacteristic* getLastCreatedCharacteristic(); - void handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t gatts_if, esp_ble_gatts_cb_param_t* param); + void handleGATTServerEvent(esp_gatts_cb_event_t event, esp_gatt_if_t gatts_if, esp_ble_gatts_cb_param_t* param); void setHandle(uint16_t handle); //void setService(esp_gatt_srvc_id_t srvc_id); - }; // BLEService diff --git a/cpp_utils/BLEServiceMap.cpp b/cpp_utils/BLEServiceMap.cpp index c749be16..cf4f75f4 100755 --- a/cpp_utils/BLEServiceMap.cpp +++ b/cpp_utils/BLEServiceMap.cpp @@ -25,7 +25,7 @@ BLEService* BLEServiceMap::getByUUID(const char* uuid) { * @param [in] UUID The UUID to look up the service. * @return The characteristic. */ -BLEService* BLEServiceMap::getByUUID(BLEUUID uuid) { +BLEService* BLEServiceMap::getByUUID(BLEUUID uuid, uint8_t inst_id) { for (auto &myPair : m_uuidMap) { if (myPair.first->getUUID().equals(uuid)) { return myPair.first; diff --git a/cpp_utils/BLEUUID.cpp b/cpp_utils/BLEUUID.cpp index ee8b6c9d..fd0f5ad5 100644 --- a/cpp_utils/BLEUUID.cpp +++ b/cpp_utils/BLEUUID.cpp @@ -95,8 +95,6 @@ BLEUUID::BLEUUID(std::string value) { m_uuid.uuid.uuid32 += (((MSB&0x0F) <<4) | (LSB & 0x0F))<<(6-i)*4; i+=2; } - } - } } else if (value.length() == 16) { // how we can have 16 byte length string reprezenting 128 bit uuid??? needs to be investigated (lack of time) m_uuid.len = ESP_UUID_LEN_128; diff --git a/cpp_utils/BLEUtils.cpp b/cpp_utils/BLEUtils.cpp index 0dd5f461..02cdf9ae 100644 --- a/cpp_utils/BLEUtils.cpp +++ b/cpp_utils/BLEUtils.cpp @@ -41,6 +41,7 @@ typedef struct { } member_t; static const member_t members_ids[] = { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 {0xFE08, "Microsoft"}, {0xFE09, "Pillsy, Inc."}, {0xFE0A, "ruwido austria gmbh"}, @@ -290,6 +291,7 @@ static const member_t members_ids[] = { {0xFEFE, "GN ReSound A/S"}, {0xFEFF, "GN Netcom"}, {0xFFFF, "Reserved"}, /*for testing purposes only*/ +#endif {0, "" } }; @@ -299,6 +301,7 @@ typedef struct { } gattdescriptor_t; static const gattdescriptor_t g_descriptor_ids[] = { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 {0x2905,"Characteristic Aggregate Format"}, {0x2900,"Characteristic Extended Properties"}, {0x2904,"Characteristic Presentation Format"}, @@ -314,6 +317,7 @@ static const gattdescriptor_t g_descriptor_ids[] = { {0x290E,"Time Trigger Setting"}, {0x2906,"Valid Range"}, {0x290A,"Value Trigger Setting"}, +#endif { 0, "" } }; @@ -323,6 +327,7 @@ typedef struct { } characteristicMap_t; static const characteristicMap_t g_characteristicsMappings[] = { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 {0x2A7E,"Aerobic Heart Rate Lower Limit"}, {0x2A84,"Aerobic Heart Rate Upper Limit"}, {0x2A7F,"Aerobic Threshold"}, @@ -539,6 +544,7 @@ static const characteristicMap_t g_characteristicsMappings[] = { {0x2A9D,"Weight Measurement"}, {0x2A9E,"Weight Scale Feature"}, {0x2A79,"Wind Chill"}, +#endif {0, ""} }; @@ -556,6 +562,7 @@ typedef struct { * Definition of the service ids to names that we know about. */ static const gattService_t g_gattServices[] = { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 {"Alert Notification Service", "org.bluetooth.service.alert_notification", 0x1811}, {"Automation IO", "org.bluetooth.service.automation_io", 0x1815 }, {"Battery Service","org.bluetooth.service.battery_service", 0x180F}, @@ -591,6 +598,7 @@ static const gattService_t g_gattServices[] = { {"Tx Power", "org.bluetooth.service.tx_power", 0x1804}, {"User Data", "org.bluetooth.service.user_data", 0x181C}, {"Weight Scale", "org.bluetooth.service.weight_scale", 0x181D}, +#endif {"", "", 0 } }; @@ -629,6 +637,7 @@ static std::string gattIdToString(esp_gatt_id_t gattId) { */ const char* BLEUtils::addressTypeToString(esp_ble_addr_type_t type) { switch (type) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case BLE_ADDR_TYPE_PUBLIC: return "BLE_ADDR_TYPE_PUBLIC"; case BLE_ADDR_TYPE_RANDOM: @@ -637,6 +646,7 @@ const char* BLEUtils::addressTypeToString(esp_ble_addr_type_t type) { return "BLE_ADDR_TYPE_RPA_PUBLIC"; case BLE_ADDR_TYPE_RPA_RANDOM: return "BLE_ADDR_TYPE_RPA_RANDOM"; +#endif default: return " esp_ble_addr_type_t"; } @@ -679,6 +689,7 @@ std::string BLEUtils::adFlagsToString(uint8_t adFlags) { */ const char* BLEUtils::advTypeToString(uint8_t advType) { switch (advType) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case ESP_BLE_AD_TYPE_FLAG: // 0x01 return "ESP_BLE_AD_TYPE_FLAG"; case ESP_BLE_AD_TYPE_16SRV_PART: // 0x02 @@ -729,8 +740,9 @@ const char* BLEUtils::advTypeToString(uint8_t advType) { return "ESP_BLE_AD_TYPE_128SERVICE_DATA"; case ESP_BLE_AD_MANUFACTURER_SPECIFIC_TYPE: // 0xff return "ESP_BLE_AD_MANUFACTURER_SPECIFIC_TYPE"; +#endif default: - ESP_LOGD(LOG_TAG, " adv data type: 0x%x", advType); + ESP_LOGV(LOG_TAG, " adv data type: 0x%x", advType); return ""; } // End switch } // advTypeToString @@ -812,42 +824,35 @@ std::string BLEUtils::buildPrintData(uint8_t* source, size_t length) { */ std::string BLEUtils::gattCloseReasonToString(esp_gatt_conn_reason_t reason) { switch (reason) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case ESP_GATT_CONN_UNKNOWN: { return "ESP_GATT_CONN_UNKNOWN"; } - case ESP_GATT_CONN_L2C_FAILURE: { return "ESP_GATT_CONN_L2C_FAILURE"; } - case ESP_GATT_CONN_TIMEOUT: { return "ESP_GATT_CONN_TIMEOUT"; } - case ESP_GATT_CONN_TERMINATE_PEER_USER: { return "ESP_GATT_CONN_TERMINATE_PEER_USER"; } - case ESP_GATT_CONN_TERMINATE_LOCAL_HOST: { return "ESP_GATT_CONN_TERMINATE_LOCAL_HOST"; } - case ESP_GATT_CONN_FAIL_ESTABLISH: { return "ESP_GATT_CONN_FAIL_ESTABLISH"; } - case ESP_GATT_CONN_LMP_TIMEOUT: { return "ESP_GATT_CONN_LMP_TIMEOUT"; } - case ESP_GATT_CONN_CONN_CANCEL: { return "ESP_GATT_CONN_CONN_CANCEL"; } - case ESP_GATT_CONN_NONE: { return "ESP_GATT_CONN_NONE"; } - +#endif default: { return "Unknown"; } @@ -857,6 +862,7 @@ std::string BLEUtils::gattCloseReasonToString(esp_gatt_conn_reason_t reason) { std::string BLEUtils::gattClientEventTypeToString(esp_gattc_cb_event_t eventType) { switch (eventType) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case ESP_GATTC_ACL_EVT: return "ESP_GATTC_ACL_EVT"; case ESP_GATTC_ADV_DATA_EVT: @@ -939,8 +945,9 @@ std::string BLEUtils::gattClientEventTypeToString(esp_gattc_cb_event_t eventType return "ESP_GATTC_WRITE_CHAR_EVT"; case ESP_GATTC_WRITE_DESCR_EVT: return "ESP_GATTC_WRITE_DESCR_EVT"; +#endif default: - ESP_LOGW(LOG_TAG, "Unknown GATT Client event type: %d", eventType); + ESP_LOGV(LOG_TAG, "Unknown GATT Client event type: %d", eventType); return "Unknown"; } } // gattClientEventTypeToString @@ -953,6 +960,7 @@ std::string BLEUtils::gattClientEventTypeToString(esp_gattc_cb_event_t eventType */ std::string BLEUtils::gattServerEventTypeToString(esp_gatts_cb_event_t eventType) { switch (eventType) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case ESP_GATTS_REG_EVT: return "ESP_GATTS_REG_EVT"; case ESP_GATTS_READ_EVT: @@ -1003,6 +1011,7 @@ std::string BLEUtils::gattServerEventTypeToString(esp_gatts_cb_event_t eventType return "ESP_GATTS_SET_ATTR_VAL_EVT"; case ESP_GATTS_SEND_SERVICE_CHANGE_EVT: return "ESP_GATTS_SEND_SERVICE_CHANGE_EVT"; +#endif default: return "Unknown"; } @@ -1016,12 +1025,14 @@ std::string BLEUtils::gattServerEventTypeToString(esp_gatts_cb_event_t eventType */ const char* BLEUtils::devTypeToString(esp_bt_dev_type_t type) { switch (type) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case ESP_BT_DEVICE_TYPE_BREDR: return "ESP_BT_DEVICE_TYPE_BREDR"; case ESP_BT_DEVICE_TYPE_BLE: return "ESP_BT_DEVICE_TYPE_BLE"; case ESP_BT_DEVICE_TYPE_DUMO: return "ESP_BT_DEVICE_TYPE_DUMO"; +#endif default: return "Unknown"; } @@ -1034,13 +1045,14 @@ const char* BLEUtils::devTypeToString(esp_bt_dev_type_t type) { void BLEUtils::dumpGapEvent( esp_gap_ble_cb_event_t event, esp_ble_gap_cb_param_t* param) { - ESP_LOGD(LOG_TAG, "Received a GAP event: %s", gapEventToString(event)); + ESP_LOGV(LOG_TAG, "Received a GAP event: %s", gapEventToString(event)); switch (event) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 // ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT // adv_data_cmpl // - esp_bt_status_t case ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d]", param->adv_data_cmpl.status); + ESP_LOGV(LOG_TAG, "[status: %d]", param->adv_data_cmpl.status); break; } // ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT @@ -1049,7 +1061,7 @@ void BLEUtils::dumpGapEvent( // adv_data_raw_cmpl // - esp_bt_status_t status case ESP_GAP_BLE_ADV_DATA_RAW_SET_COMPLETE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d]", param->adv_data_raw_cmpl.status); + ESP_LOGV(LOG_TAG, "[status: %d]", param->adv_data_raw_cmpl.status); break; } // ESP_GAP_BLE_ADV_DATA_RAW_SET_COMPLETE_EVT @@ -1058,7 +1070,7 @@ void BLEUtils::dumpGapEvent( // adv_start_cmpl // - esp_bt_status_t status case ESP_GAP_BLE_ADV_START_COMPLETE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d]", param->adv_start_cmpl.status); + ESP_LOGV(LOG_TAG, "[status: %d]", param->adv_start_cmpl.status); break; } // ESP_GAP_BLE_ADV_START_COMPLETE_EVT @@ -1067,7 +1079,7 @@ void BLEUtils::dumpGapEvent( // adv_stop_cmpl // - esp_bt_status_t status case ESP_GAP_BLE_ADV_STOP_COMPLETE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d]", param->adv_stop_cmpl.status); + ESP_LOGV(LOG_TAG, "[status: %d]", param->adv_stop_cmpl.status); break; } // ESP_GAP_BLE_ADV_STOP_COMPLETE_EVT @@ -1082,7 +1094,7 @@ void BLEUtils::dumpGapEvent( // - esp_bd_addr_type_t addr_type // - esp_bt_dev_type_t dev_type case ESP_GAP_BLE_AUTH_CMPL_EVT: { - ESP_LOGD(LOG_TAG, "[bd_addr: %s, key_present: %d, key: ***, key_type: %d, success: %d, fail_reason: %d, addr_type: ***, dev_type: %s]", + ESP_LOGV(LOG_TAG, "[bd_addr: %s, key_present: %d, key: ***, key_type: %d, success: %d, fail_reason: %d, addr_type: ***, dev_type: %s]", BLEAddress(param->ble_security.auth_cmpl.bd_addr).toString().c_str(), param->ble_security.auth_cmpl.key_present, param->ble_security.auth_cmpl.key_type, @@ -1098,7 +1110,7 @@ void BLEUtils::dumpGapEvent( // clear_bond_dev_cmpl // - esp_bt_status_t status case ESP_GAP_BLE_CLEAR_BOND_DEV_COMPLETE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d]", param->clear_bond_dev_cmpl.status); + ESP_LOGV(LOG_TAG, "[status: %d]", param->clear_bond_dev_cmpl.status); break; } // ESP_GAP_BLE_CLEAR_BOND_DEV_COMPLETE_EVT @@ -1114,7 +1126,7 @@ void BLEUtils::dumpGapEvent( // ESP_GAP_BLE_NC_REQ_EVT case ESP_GAP_BLE_NC_REQ_EVT: { - ESP_LOGD(LOG_TAG, "[bd_addr: %s, passkey: %d]", + ESP_LOGV(LOG_TAG, "[bd_addr: %s, passkey: %d]", BLEAddress(param->ble_security.key_notif.bd_addr).toString().c_str(), param->ble_security.key_notif.passkey); break; @@ -1127,7 +1139,7 @@ void BLEUtils::dumpGapEvent( // - int8_t rssi // - esp_bd_addr_t remote_addr case ESP_GAP_BLE_READ_RSSI_COMPLETE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d, rssi: %d, remote_addr: %s]", + ESP_LOGV(LOG_TAG, "[status: %d, rssi: %d, remote_addr: %s]", param->read_rssi_cmpl.status, param->read_rssi_cmpl.rssi, BLEAddress(param->read_rssi_cmpl.remote_addr).toString().c_str() @@ -1140,7 +1152,7 @@ void BLEUtils::dumpGapEvent( // scan_param_cmpl. // - esp_bt_status_t status case ESP_GAP_BLE_SCAN_PARAM_SET_COMPLETE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d]", param->scan_param_cmpl.status); + ESP_LOGV(LOG_TAG, "[status: %d]", param->scan_param_cmpl.status); break; } // ESP_GAP_BLE_SCAN_PARAM_SET_COMPLETE_EVT @@ -1161,7 +1173,7 @@ void BLEUtils::dumpGapEvent( case ESP_GAP_BLE_SCAN_RESULT_EVT: { switch (param->scan_rst.search_evt) { case ESP_GAP_SEARCH_INQ_RES_EVT: { - ESP_LOGD(LOG_TAG, "search_evt: %s, bda: %s, dev_type: %s, ble_addr_type: %s, ble_evt_type: %s, rssi: %d, ble_adv: ??, flag: %d (%s), num_resps: %d, adv_data_len: %d, scan_rsp_len: %d", + ESP_LOGV(LOG_TAG, "search_evt: %s, bda: %s, dev_type: %s, ble_addr_type: %s, ble_evt_type: %s, rssi: %d, ble_adv: ??, flag: %d (%s), num_resps: %d, adv_data_len: %d, scan_rsp_len: %d", searchEventTypeToString(param->scan_rst.search_evt), BLEAddress(param->scan_rst.bda).toString().c_str(), devTypeToString(param->scan_rst.dev_type), @@ -1178,7 +1190,7 @@ void BLEUtils::dumpGapEvent( } // ESP_GAP_SEARCH_INQ_RES_EVT default: { - ESP_LOGD(LOG_TAG, "search_evt: %s",searchEventTypeToString(param->scan_rst.search_evt)); + ESP_LOGV(LOG_TAG, "search_evt: %s",searchEventTypeToString(param->scan_rst.search_evt)); break; } } @@ -1190,13 +1202,13 @@ void BLEUtils::dumpGapEvent( // scan_rsp_data_cmpl // - esp_bt_status_t status case ESP_GAP_BLE_SCAN_RSP_DATA_SET_COMPLETE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d]", param->scan_rsp_data_cmpl.status); + ESP_LOGV(LOG_TAG, "[status: %d]", param->scan_rsp_data_cmpl.status); break; } // ESP_GAP_BLE_SCAN_RSP_DATA_SET_COMPLETE_EVT // ESP_GAP_BLE_SCAN_RSP_DATA_RAW_SET_COMPLETE_EVT case ESP_GAP_BLE_SCAN_RSP_DATA_RAW_SET_COMPLETE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d]", param->scan_rsp_data_raw_cmpl.status); + ESP_LOGV(LOG_TAG, "[status: %d]", param->scan_rsp_data_raw_cmpl.status); break; } // ESP_GAP_BLE_SCAN_RSP_DATA_RAW_SET_COMPLETE_EVT @@ -1205,7 +1217,7 @@ void BLEUtils::dumpGapEvent( // scan_start_cmpl // - esp_bt_status_t status case ESP_GAP_BLE_SCAN_START_COMPLETE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d]", param->scan_start_cmpl.status); + ESP_LOGV(LOG_TAG, "[status: %d]", param->scan_start_cmpl.status); break; } // ESP_GAP_BLE_SCAN_START_COMPLETE_EVT @@ -1214,7 +1226,7 @@ void BLEUtils::dumpGapEvent( // scan_stop_cmpl // - esp_bt_status_t status case ESP_GAP_BLE_SCAN_STOP_COMPLETE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d]", param->scan_stop_cmpl.status); + ESP_LOGV(LOG_TAG, "[status: %d]", param->scan_stop_cmpl.status); break; } // ESP_GAP_BLE_SCAN_STOP_COMPLETE_EVT @@ -1229,7 +1241,7 @@ void BLEUtils::dumpGapEvent( // - uint16_t conn_int // - uint16_t timeout case ESP_GAP_BLE_UPDATE_CONN_PARAMS_EVT: { - ESP_LOGD(LOG_TAG, "[status: %d, bd_addr: %s, min_int: %d, max_int: %d, latency: %d, conn_int: %d, timeout: %d]", + ESP_LOGV(LOG_TAG, "[status: %d, bd_addr: %s, min_int: %d, max_int: %d, latency: %d, conn_int: %d, timeout: %d]", param->update_conn_params.status, BLEAddress(param->update_conn_params.bda).toString().c_str(), param->update_conn_params.min_int, @@ -1243,12 +1255,12 @@ void BLEUtils::dumpGapEvent( // ESP_GAP_BLE_SEC_REQ_EVT case ESP_GAP_BLE_SEC_REQ_EVT: { - ESP_LOGD(LOG_TAG, "[bd_addr: %s]", BLEAddress(param->ble_security.ble_req.bd_addr).toString().c_str()); + ESP_LOGV(LOG_TAG, "[bd_addr: %s]", BLEAddress(param->ble_security.ble_req.bd_addr).toString().c_str()); break; } // ESP_GAP_BLE_SEC_REQ_EVT - +#endif default: { - ESP_LOGD(LOG_TAG, "*** dumpGapEvent: Logger not coded ***"); + ESP_LOGV(LOG_TAG, "*** dumpGapEvent: Logger not coded ***"); break; } // default } // switch @@ -1267,8 +1279,9 @@ void BLEUtils::dumpGattClientEvent( esp_ble_gattc_cb_param_t* evtParam) { //esp_ble_gattc_cb_param_t* evtParam = (esp_ble_gattc_cb_param_t*) param; - ESP_LOGD(LOG_TAG, "GATT Event: %s", BLEUtils::gattClientEventTypeToString(event).c_str()); + ESP_LOGV(LOG_TAG, "GATT Event: %s", BLEUtils::gattClientEventTypeToString(event).c_str()); switch (event) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 // ESP_GATTC_CLOSE_EVT // // close: @@ -1277,7 +1290,7 @@ void BLEUtils::dumpGattClientEvent( // - esp_bd_addr_t remote_bda // - esp_gatt_conn_reason_t reason case ESP_GATTC_CLOSE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, reason:%s, conn_id: %d]", + ESP_LOGV(LOG_TAG, "[status: %s, reason:%s, conn_id: %d]", BLEUtils::gattStatusToString(evtParam->close.status).c_str(), BLEUtils::gattCloseReasonToString(evtParam->close.reason).c_str(), evtParam->close.conn_id); @@ -1291,7 +1304,7 @@ void BLEUtils::dumpGattClientEvent( // - uint16_t conn_id // - esp_bd_addr_t remote_bda case ESP_GATTC_CONNECT_EVT: { - ESP_LOGD(LOG_TAG, "[conn_id: %d, remote_bda: %s]", + ESP_LOGV(LOG_TAG, "[conn_id: %d, remote_bda: %s]", evtParam->connect.conn_id, BLEAddress(evtParam->connect.remote_bda).toString().c_str() ); @@ -1305,7 +1318,7 @@ void BLEUtils::dumpGattClientEvent( // - uint16_t conn_id // - esp_bd_addr_t remote_bda case ESP_GATTC_DISCONNECT_EVT: { - ESP_LOGD(LOG_TAG, "[reason: %s, conn_id: %d, remote_bda: %s]", + ESP_LOGV(LOG_TAG, "[reason: %s, conn_id: %d, remote_bda: %s]", BLEUtils::gattCloseReasonToString(evtParam->disconnect.reason).c_str(), evtParam->disconnect.conn_id, BLEAddress(evtParam->disconnect.remote_bda).toString().c_str() @@ -1331,7 +1344,7 @@ void BLEUtils::dumpGattClientEvent( if (evtParam->get_char.char_id.uuid.len == ESP_UUID_LEN_16) { description = BLEUtils::gattCharacteristicUUIDToString(evtParam->get_char.char_id.uuid.uuid.uuid16); } - ESP_LOGD(LOG_TAG, "[status: %s, conn_id: %d, srvc_id: %s, char_id: %s [description: %s]\nchar_prop: %s]", + ESP_LOGV(LOG_TAG, "[status: %s, conn_id: %d, srvc_id: %s, char_id: %s [description: %s]\nchar_prop: %s]", BLEUtils::gattStatusToString(evtParam->get_char.status).c_str(), evtParam->get_char.conn_id, BLEUtils::gattServiceIdToString(evtParam->get_char.srvc_id).c_str(), @@ -1340,7 +1353,7 @@ void BLEUtils::dumpGattClientEvent( BLEUtils::characteristicPropertiesToString(evtParam->get_char.char_prop).c_str() ); } else { - ESP_LOGD(LOG_TAG, "[status: %s, conn_id: %d, srvc_id: %s]", + ESP_LOGV(LOG_TAG, "[status: %s, conn_id: %d, srvc_id: %s]", BLEUtils::gattStatusToString(evtParam->get_char.status).c_str(), evtParam->get_char.conn_id, BLEUtils::gattServiceIdToString(evtParam->get_char.srvc_id).c_str() @@ -1361,7 +1374,7 @@ void BLEUtils::dumpGattClientEvent( // bool is_notify // case ESP_GATTC_NOTIFY_EVT: { - ESP_LOGD(LOG_TAG, "[conn_id: %d, remote_bda: %s, handle: %d 0x%.2x, value_len: %d, is_notify: %d]", + ESP_LOGV(LOG_TAG, "[conn_id: %d, remote_bda: %s, handle: %d 0x%.2x, value_len: %d, is_notify: %d]", evtParam->notify.conn_id, BLEAddress(evtParam->notify.remote_bda).toString().c_str(), evtParam->notify.handle, @@ -1381,7 +1394,7 @@ void BLEUtils::dumpGattClientEvent( // - uint16_t mtu // case ESP_GATTC_OPEN_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, conn_id: %d, remote_bda: %s, mtu: %d]", + ESP_LOGV(LOG_TAG, "[status: %s, conn_id: %d, remote_bda: %s, mtu: %d]", BLEUtils::gattStatusToString(evtParam->open.status).c_str(), evtParam->open.conn_id, BLEAddress(evtParam->open.remote_bda).toString().c_str(), @@ -1401,7 +1414,7 @@ void BLEUtils::dumpGattClientEvent( // uint16_t value_type // uint16_t value_len case ESP_GATTC_READ_CHAR_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, conn_id: %d, handle: %d 0x%.2x, value_len: %d]", + ESP_LOGV(LOG_TAG, "[status: %s, conn_id: %d, handle: %d 0x%.2x, value_len: %d]", BLEUtils::gattStatusToString(evtParam->read.status).c_str(), evtParam->read.conn_id, evtParam->read.handle, @@ -1412,7 +1425,7 @@ void BLEUtils::dumpGattClientEvent( GeneralUtils::hexDump(evtParam->read.value, evtParam->read.value_len); /* char* pHexData = BLEUtils::buildHexData(nullptr, evtParam->read.value, evtParam->read.value_len); - ESP_LOGD(LOG_TAG, "value: %s \"%s\"", pHexData, BLEUtils::buildPrintData(evtParam->read.value, evtParam->read.value_len).c_str()); + ESP_LOGV(LOG_TAG, "value: %s \"%s\"", pHexData, BLEUtils::buildPrintData(evtParam->read.value, evtParam->read.value_len).c_str()); free(pHexData); */ } @@ -1425,7 +1438,7 @@ void BLEUtils::dumpGattClientEvent( // - esp_gatt_status_t status // - uint16_t app_id case ESP_GATTC_REG_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, app_id: 0x%x]", + ESP_LOGV(LOG_TAG, "[status: %s, app_id: 0x%x]", BLEUtils::gattStatusToString(evtParam->reg.status).c_str(), evtParam->reg.app_id); break; @@ -1437,7 +1450,7 @@ void BLEUtils::dumpGattClientEvent( // - esp_gatt_status_t status // - uint16_t handle case ESP_GATTC_REG_FOR_NOTIFY_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, handle: %d 0x%.2x]", + ESP_LOGV(LOG_TAG, "[status: %s, handle: %d 0x%.2x]", BLEUtils::gattStatusToString(evtParam->reg_for_notify.status).c_str(), evtParam->reg_for_notify.handle, evtParam->reg_for_notify.handle @@ -1451,7 +1464,7 @@ void BLEUtils::dumpGattClientEvent( // - esp_gatt_status_t status // - uint16_t conn_id case ESP_GATTC_SEARCH_CMPL_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, conn_id: %d]", + ESP_LOGV(LOG_TAG, "[status: %s, conn_id: %d]", BLEUtils::gattStatusToString(evtParam->search_cmpl.status).c_str(), evtParam->search_cmpl.conn_id); break; @@ -1465,7 +1478,7 @@ void BLEUtils::dumpGattClientEvent( // - uint16_t end_handle // - esp_gatt_id_t srvc_id case ESP_GATTC_SEARCH_RES_EVT: { - ESP_LOGD(LOG_TAG, "[conn_id: %d, start_handle: %d 0x%.2x, end_handle: %d 0x%.2x, srvc_id: %s", + ESP_LOGV(LOG_TAG, "[conn_id: %d, start_handle: %d 0x%.2x, end_handle: %d 0x%.2x, srvc_id: %s", evtParam->search_res.conn_id, evtParam->search_res.start_handle, evtParam->search_res.start_handle, @@ -1483,7 +1496,7 @@ void BLEUtils::dumpGattClientEvent( // - uint16_t handle // - uint16_t offset case ESP_GATTC_WRITE_CHAR_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, conn_id: %d, handle: %d 0x%.2x, offset: %d]", + ESP_LOGV(LOG_TAG, "[status: %s, conn_id: %d, handle: %d 0x%.2x, offset: %d]", BLEUtils::gattStatusToString(evtParam->write.status).c_str(), evtParam->write.conn_id, evtParam->write.handle, @@ -1492,7 +1505,7 @@ void BLEUtils::dumpGattClientEvent( ); break; } // ESP_GATTC_WRITE_CHAR_EVT - +#endif default: break; } @@ -1513,11 +1526,12 @@ void BLEUtils::dumpGattServerEvent( esp_gatts_cb_event_t event, esp_gatt_if_t gatts_if, esp_ble_gatts_cb_param_t* evtParam) { - ESP_LOGD(LOG_TAG, "GATT ServerEvent: %s", BLEUtils::gattServerEventTypeToString(event).c_str()); + ESP_LOGV(LOG_TAG, "GATT ServerEvent: %s", BLEUtils::gattServerEventTypeToString(event).c_str()); switch (event) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case ESP_GATTS_ADD_CHAR_DESCR_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, attr_handle: %d 0x%.2x, service_handle: %d 0x%.2x, char_uuid: %s]", + ESP_LOGV(LOG_TAG, "[status: %s, attr_handle: %d 0x%.2x, service_handle: %d 0x%.2x, char_uuid: %s]", gattStatusToString(evtParam->add_char_descr.status).c_str(), evtParam->add_char_descr.attr_handle, evtParam->add_char_descr.attr_handle, @@ -1529,7 +1543,7 @@ void BLEUtils::dumpGattServerEvent( case ESP_GATTS_ADD_CHAR_EVT: { if (evtParam->add_char.status == ESP_GATT_OK) { - ESP_LOGD(LOG_TAG, "[status: %s, attr_handle: %d 0x%.2x, service_handle: %d 0x%.2x, char_uuid: %s]", + ESP_LOGV(LOG_TAG, "[status: %s, attr_handle: %d 0x%.2x, service_handle: %d 0x%.2x, char_uuid: %s]", gattStatusToString(evtParam->add_char.status).c_str(), evtParam->add_char.attr_handle, evtParam->add_char.attr_handle, @@ -1555,7 +1569,7 @@ void BLEUtils::dumpGattServerEvent( // - esp_gatt_status_t status – The status code. // - uint16_t conn_id – The connection used. case ESP_GATTS_CONF_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, conn_id: 0x%.2x]", + ESP_LOGV(LOG_TAG, "[status: %s, conn_id: 0x%.2x]", gattStatusToString(evtParam->conf.status).c_str(), evtParam->conf.conn_id); break; @@ -1563,21 +1577,21 @@ void BLEUtils::dumpGattServerEvent( case ESP_GATTS_CONGEST_EVT: { - ESP_LOGD(LOG_TAG, "[conn_id: %d, congested: %d]", + ESP_LOGV(LOG_TAG, "[conn_id: %d, congested: %d]", evtParam->congest.conn_id, evtParam->congest.congested); break; } // ESP_GATTS_CONGEST_EVT case ESP_GATTS_CONNECT_EVT: { - ESP_LOGD(LOG_TAG, "[conn_id: %d, remote_bda: %s]", + ESP_LOGV(LOG_TAG, "[conn_id: %d, remote_bda: %s]", evtParam->connect.conn_id, BLEAddress(evtParam->connect.remote_bda).toString().c_str()); break; } // ESP_GATTS_CONNECT_EVT case ESP_GATTS_CREATE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, service_handle: %d 0x%.2x, service_id: [%s]]", + ESP_LOGV(LOG_TAG, "[status: %s, service_handle: %d 0x%.2x, service_id: [%s]]", gattStatusToString(evtParam->create.status).c_str(), evtParam->create.service_handle, evtParam->create.service_handle, @@ -1586,7 +1600,7 @@ void BLEUtils::dumpGattServerEvent( } // ESP_GATTS_CREATE_EVT case ESP_GATTS_DISCONNECT_EVT: { - ESP_LOGD(LOG_TAG, "[conn_id: %d, remote_bda: %s]", + ESP_LOGV(LOG_TAG, "[conn_id: %d, remote_bda: %s]", evtParam->connect.conn_id, BLEAddress(evtParam->connect.remote_bda).toString().c_str()); break; @@ -1617,7 +1631,7 @@ void BLEUtils::dumpGattServerEvent( break; } - ESP_LOGD(LOG_TAG, "[conn_id: %d, trans_id: %d, bda: %s, exec_write_flag: 0x%.2x=%s]", + ESP_LOGV(LOG_TAG, "[conn_id: %d, trans_id: %d, bda: %s, exec_write_flag: 0x%.2x=%s]", evtParam->exec_write.conn_id, evtParam->exec_write.trans_id, BLEAddress(evtParam->exec_write.bda).toString().c_str(), @@ -1628,14 +1642,14 @@ void BLEUtils::dumpGattServerEvent( case ESP_GATTS_MTU_EVT: { - ESP_LOGD(LOG_TAG, "[conn_id: %d, mtu: %d]", + ESP_LOGV(LOG_TAG, "[conn_id: %d, mtu: %d]", evtParam->mtu.conn_id, evtParam->mtu.mtu); break; } // ESP_GATTS_MTU_EVT case ESP_GATTS_READ_EVT: { - ESP_LOGD(LOG_TAG, "[conn_id: %d, trans_id: %d, bda: %s, handle: 0x%.2x, is_long: %d, need_rsp:%d]", + ESP_LOGV(LOG_TAG, "[conn_id: %d, trans_id: %d, bda: %s, handle: 0x%.2x, is_long: %d, need_rsp:%d]", evtParam->read.conn_id, evtParam->read.trans_id, BLEAddress(evtParam->read.bda).toString().c_str(), @@ -1646,14 +1660,14 @@ void BLEUtils::dumpGattServerEvent( } // ESP_GATTS_READ_EVT case ESP_GATTS_RESPONSE_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, handle: 0x%.2x]", + ESP_LOGV(LOG_TAG, "[status: %s, handle: 0x%.2x]", gattStatusToString(evtParam->rsp.status).c_str(), evtParam->rsp.handle); break; } // ESP_GATTS_RESPONSE_EVT case ESP_GATTS_REG_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, app_id: %d]", + ESP_LOGV(LOG_TAG, "[status: %s, app_id: %d]", gattStatusToString(evtParam->reg.status).c_str(), evtParam->reg.app_id); break; @@ -1666,7 +1680,7 @@ void BLEUtils::dumpGattServerEvent( // - esp_gatt_status_t status // - uint16_t service_handle case ESP_GATTS_START_EVT: { - ESP_LOGD(LOG_TAG, "[status: %s, service_handle: 0x%.2x]", + ESP_LOGV(LOG_TAG, "[status: %s, service_handle: 0x%.2x]", gattStatusToString(evtParam->start.status).c_str(), evtParam->start.service_handle); break; @@ -1686,7 +1700,7 @@ void BLEUtils::dumpGattServerEvent( // - uint16_t len – The length of the incoming value part. // - uint8_t* value – The data for this value part. case ESP_GATTS_WRITE_EVT: { - ESP_LOGD(LOG_TAG, "[conn_id: %d, trans_id: %d, bda: %s, handle: 0x%.2x, offset: %d, need_rsp: %d, is_prep: %d, len: %d]", + ESP_LOGV(LOG_TAG, "[conn_id: %d, trans_id: %d, bda: %s, handle: 0x%.2x, offset: %d, need_rsp: %d, is_prep: %d, len: %d]", evtParam->write.conn_id, evtParam->write.trans_id, BLEAddress(evtParam->write.bda).toString().c_str(), @@ -1696,13 +1710,13 @@ void BLEUtils::dumpGattServerEvent( evtParam->write.is_prep, evtParam->write.len); char* pHex = buildHexData(nullptr, evtParam->write.value, evtParam->write.len); - ESP_LOGD(LOG_TAG, "[Data: %s]", pHex); + ESP_LOGV(LOG_TAG, "[Data: %s]", pHex); free(pHex); break; } // ESP_GATTS_WRITE_EVT - +#endif default: - ESP_LOGD(LOG_TAG, "dumpGattServerEvent: *** NOT CODED ***"); + ESP_LOGV(LOG_TAG, "dumpGattServerEvent: *** NOT CODED ***"); break; } } // dumpGattServerEvent @@ -1715,6 +1729,7 @@ void BLEUtils::dumpGattServerEvent( */ const char* BLEUtils::eventTypeToString(esp_ble_evt_type_t eventType) { switch (eventType) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case ESP_BLE_EVT_CONN_ADV: return "ESP_BLE_EVT_CONN_ADV"; case ESP_BLE_EVT_CONN_DIR_ADV: @@ -1725,8 +1740,9 @@ const char* BLEUtils::eventTypeToString(esp_ble_evt_type_t eventType) { return "ESP_BLE_EVT_NON_CONN_ADV"; case ESP_BLE_EVT_SCAN_RSP: return "ESP_BLE_EVT_SCAN_RSP"; +#endif default: - ESP_LOGD(LOG_TAG, "Unknown esp_ble_evt_type_t: %d (0x%.2x)", eventType, eventType); + ESP_LOGV(LOG_TAG, "Unknown esp_ble_evt_type_t: %d (0x%.2x)", eventType, eventType); return "*** Unknown ***"; } } // eventTypeToString @@ -1740,6 +1756,7 @@ const char* BLEUtils::eventTypeToString(esp_ble_evt_type_t eventType) { */ const char* BLEUtils::gapEventToString(uint32_t eventType) { switch (eventType) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT: return "ESP_GAP_BLE_ADV_DATA_SET_COMPLETE_EVT"; case ESP_GAP_BLE_ADV_DATA_RAW_SET_COMPLETE_EVT: @@ -1794,8 +1811,9 @@ const char* BLEUtils::gapEventToString(uint32_t eventType) { return "ESP_GAP_BLE_SET_STATIC_RAND_ADDR_EVT"; case ESP_GAP_BLE_UPDATE_CONN_PARAMS_EVT: return "ESP_GAP_BLE_UPDATE_CONN_PARAMS_EVT"; +#endif default: - ESP_LOGD(LOG_TAG, "gapEventToString: Unknown event type %d 0x%.2x", eventType, eventType); + ESP_LOGV(LOG_TAG, "gapEventToString: Unknown event type %d 0x%.2x", eventType, eventType); return "Unknown event type"; } } // gapEventToString @@ -1874,6 +1892,7 @@ std::string BLEUtils::gattServiceToString(uint32_t serviceId) { */ std::string BLEUtils::gattStatusToString(esp_gatt_status_t status) { switch (status) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case ESP_GATT_OK: return "ESP_GATT_OK"; case ESP_GATT_INVALID_HANDLE: @@ -1960,6 +1979,7 @@ std::string BLEUtils::gattStatusToString(esp_gatt_status_t status) { return "ESP_GATT_PRC_IN_PROGRESS"; case ESP_GATT_OUT_OF_RANGE: return "ESP_GATT_OUT_OF_RANGE"; +#endif default: return "Unknown"; } @@ -1986,6 +2006,7 @@ std::string BLEUtils::getMember(uint32_t memberId) { */ const char* BLEUtils::searchEventTypeToString(esp_gap_search_evt_t searchEvt) { switch (searchEvt) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case ESP_GAP_SEARCH_INQ_RES_EVT: return "ESP_GAP_SEARCH_INQ_RES_EVT"; case ESP_GAP_SEARCH_INQ_CMPL_EVT: @@ -2000,8 +2021,9 @@ const char* BLEUtils::searchEventTypeToString(esp_gap_search_evt_t searchEvt) { return "ESP_GAP_SEARCH_DI_DISC_CMPL_EVT"; case ESP_GAP_SEARCH_SEARCH_CANCEL_CMPL_EVT: return "ESP_GAP_SEARCH_SEARCH_CANCEL_CMPL_EVT"; +#endif default: - ESP_LOGD(LOG_TAG, "Unknown event type: 0x%x", searchEvt); + ESP_LOGV(LOG_TAG, "Unknown event type: 0x%x", searchEvt); return "Unknown event type"; } } // searchEventTypeToString diff --git a/cpp_utils/GeneralUtils.cpp b/cpp_utils/GeneralUtils.cpp index 8d58d4eb..dbbc65be 100644 --- a/cpp_utils/GeneralUtils.cpp +++ b/cpp_utils/GeneralUtils.cpp @@ -365,6 +365,7 @@ std::vector GeneralUtils::split(std::string source, char delimiter) */ const char* GeneralUtils::errorToString(esp_err_t errCode) { switch (errCode) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case ESP_OK: return "ESP_OK"; case ESP_FAIL: @@ -431,6 +432,7 @@ const char* GeneralUtils::errorToString(esp_err_t errCode) { return "ESP_ERR_WIFI_TIMEOUT"; case ESP_ERR_WIFI_WAKE_FAIL: return "ESP_ERR_WIFI_WAKE_FAIL"; +#endif default: return "Unknown ESP_ERR error"; } @@ -448,6 +450,7 @@ const char* GeneralUtils::wifiErrorToString(uint8_t errCode) { if (errCode == UINT8_MAX) return "Not Connected (default value)"; switch ((wifi_err_reason_t) errCode) { +#if CONFIG_LOG_DEFAULT_LEVEL > 4 case WIFI_REASON_UNSPECIFIED: return "WIFI_REASON_UNSPECIFIED"; case WIFI_REASON_AUTH_EXPIRE: @@ -504,6 +507,7 @@ const char* GeneralUtils::wifiErrorToString(uint8_t errCode) { return "WIFI_REASON_ASSOC_FAIL"; case WIFI_REASON_HANDSHAKE_TIMEOUT: return "WIFI_REASON_HANDSHAKE_TIMEOUT"; +#endif default: return "Unknown ESP_ERR error"; }