I have 2 ESP32s, a server and a client in the Arduino platform. The notifyCallback works fine when a sensor message is sent from the server code in the loop(). However, I plan to use the server (sensor) ESP32 in a battery operated scenario. I'd like to send the sensor value, then put the ESP32 into deep sleep mode. When I moved the code out of the loop(), to be in the setup() with deep sleep functionality, I don't get a notification back from the client. Following is my code:
Server Code:
- #include <BLEDevice.h>
- #include <BLEServer.h>
- #include <BLEUtils.h>
- #include <BLE2902.h>
- #include "DHT.h"
- #define DHTPIN 4
- #define DHTTYPE DHT22
- #define uS_TO_S_FACTOR 1000000 //Conversion factor for micro seconds to seconds
- #define TIME_TO_SLEEP 15 //Time ESP32 will go to sleep (in seconds)
- RTC_DATA_ATTR int bootCount = 0;
- DHT dht(DHTPIN, DHTTYPE);
- BLECharacteristic *pCharacteristic;
- bool deviceConnected = false;
- uint8_t txValue = 50;
- #define SERVICE_UUID "4fafc201-1fb5-459e-8fcc-c5c9c331914b" // UART service UUID
- #define CHARACTERISTIC_UUID_TX "beb5483e-36e1-4688-b7f5-ea07361b26a8"
- class MyServerCallbacks: public BLEServerCallbacks {
- void onConnect(BLEServer* pServer) {
- deviceConnected = true;
- };
- void onDisconnect(BLEServer* pServer) {
- deviceConnected = false;
- }
- };
- //Function that prints the reason by which ESP32 has been awaken from sleep
- void print_wakeup_reason(){
- esp_sleep_wakeup_cause_t wakeup_reason;
- wakeup_reason = esp_sleep_get_wakeup_cause();
- switch(wakeup_reason)
- {
- case 1 : Serial.println("Wakeup caused by external signal using RTC_IO"); break;
- case 2 : Serial.println("Wakeup caused by external signal using RTC_CNTL"); break;
- case 3 : Serial.println("Wakeup caused by timer"); break;
- case 4 : Serial.println("Wakeup caused by touchpad"); break;
- case 5 : Serial.println("Wakeup caused by ULP program"); break;
- default : Serial.println("Wakeup was not caused by deep sleep"); break;
- }
- }
- void setup() {
- Serial.begin(115200);
- Serial.println(F("initating DHT22..."));
- dht.begin();
- // Create the BLE Device
- BLEDevice::init("UART"); // Name must not be longer than 5 chars!!!
- // Create the BLE Server
- BLEServer *pServer = BLEDevice::createServer();
- pServer->setCallbacks(new MyServerCallbacks());
- // Create the BLE Service
- BLEService *pService = pServer->createService(SERVICE_UUID);
- // Create a BLE Characteristic
- pCharacteristic = pService->createCharacteristic(
- CHARACTERISTIC_UUID_TX,
- BLECharacteristic::PROPERTY_NOTIFY|BLECharacteristic::PROPERTY_READ|BLECharacteristic::PROPERTY_WRITE
- );
- BLE2902 *desc = new BLE2902();
- desc->setNotifications(true);
- pCharacteristic->addDescriptor(desc);
- // Start the service
- pService->start();
- pServer->getAdvertising()->addServiceUUID(SERVICE_UUID);
- // Start advertising
- pServer->getAdvertising()->start();
- Serial.println(pService->getUUID().toString().c_str());
- Serial.println("Waiting for a client connection to notify...");
- if (deviceConnected) {
- float f = dht.readTemperature(true);
- char fStr[10];
- sprintf(fStr, "%4.4f", f);
- Serial.print("Temperature reading: ");
- Serial.println(fStr);
- Serial.printf("*** Sent Value: %d ***\n", fStr);
- pCharacteristic->setValue(fStr);
- delay(3000);
- pCharacteristic->setValue(fStr);
- pCharacteristic->notify();
- //Set timer to 5 seconds
- esp_sleep_enable_timer_wakeup(TIME_TO_SLEEP * uS_TO_S_FACTOR);
- Serial.println("Setup ESP32 to sleep for every " + String(TIME_TO_SLEEP) +
- " Seconds");
- //Go to sleep now
- esp_deep_sleep_start();
- }
- //delay(60000);
- }
- void loop() {}
rst:0x1 (POWERON_RESET),boot:0x17 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:1
load:0x3fff0018,len:4
load:0x3fff001c,len:1216
ho 0 tail 12 room 4
load:0x40078000,len:9720
ho 0 tail 12 room 4
load:0x40080400,len:6352
entry 0x400806b8
initating DHT22...
4fafc201-1fb5-459e-8fcc-c5c9c331914b
Waiting a client connection to notify...
Client code:
- #include "BLEDevice.h"
- // The remote service we wish to connect to.
- static BLEUUID serviceUUID("4fafc201-1fb5-459e-8fcc-c5c9c331914b");
- static BLEUUID charUUID("beb5483e-36e1-4688-b7f5-ea07361b26a8");
- static BLEAddress *pServerAddress;
- static boolean doConnect = false;
- static boolean connected = false;
- static BLERemoteCharacteristic* pRemoteCharacteristic;
- static void notifyCallback(
- BLERemoteCharacteristic* pBLERemoteCharacteristic,
- uint8_t* pData,
- size_t length,
- bool isNotify) {
- Serial.print(pBLERemoteCharacteristic->getUUID().toString().c_str());
- Serial.print(" of data length ");
- Serial.println(length);
- byte buffer[42];
- Serial.print("The characteristic value sent was: ");
- std::string farhenheight = pRemoteCharacteristic->readValue();
- Serial.print("Farheinheight: ");
- Serial.println(farhenheight.c_str());
- }
- class MyClientCallback : public BLEClientCallbacks {
- void onConnect(BLEClient* pclient) {
- Serial.println("connected again ... ");
- }
- void onDisconnect(BLEClient* pclient) {
- connected = false;
- Serial.println("onDisconnect");
- }
- };
- bool connectToServer(BLEAddress pAddress) {
- Serial.print("Forming a connection to ");
- Serial.println(pAddress.toString().c_str());
- BLEClient* pClient = BLEDevice::createClient();
- Serial.println(" - Created client");
- pClient->setClientCallbacks(new MyClientCallback());
- // Connect to the remove BLE Server.
- pClient->connect(pAddress);
- Serial.println(" - Connected to server");
- // Obtain a reference to the service we are after in the remote BLE server.
- BLERemoteService* pRemoteService = pClient->getService(serviceUUID);
- Serial.println(pRemoteService->toString().c_str());
- if (pRemoteService == nullptr) {
- Serial.print("Failed to find our service UUID: ");
- Serial.println(serviceUUID.toString().c_str());
- return false;
- }
- Serial.println(" - Found our service");
- // Obtain a reference to the characteristic in the service of the remote BLE server.
- pRemoteCharacteristic = pRemoteService->getCharacteristic(charUUID);
- if (pRemoteCharacteristic == nullptr) {
- Serial.print("Failed to find our characteristic UUID: ");
- Serial.println(charUUID.toString().c_str());
- return false;
- }
- Serial.println(" - Found our characteristic");
- //
- // Serial.print("The characteristic value sent was: ");
- // std::string farhenheight = pRemoteCharacteristic->readValue();
- // Serial.print("Farheinheight: ");
- // Serial.println(farhenheight.c_str());
- pRemoteCharacteristic->registerForNotify(notifyCallback);
- }
- class MyAdvertisedDeviceCallbacks: public BLEAdvertisedDeviceCallbacks {
- void onResult(BLEAdvertisedDevice advertisedDevice) {
- Serial.print("BLE Advertised Device found: ");
- Serial.println(advertisedDevice.toString().c_str());
- //Serial.print(advertisedDevice.haveServiceUUID());
- if(advertisedDevice.haveServiceUUID()){
- Serial.println(advertisedDevice.getServiceUUID().toString().c_str());
- }
- // We have found a device, let us now see if it contains the service we are looking for.
- if (advertisedDevice.haveServiceUUID() && advertisedDevice.getServiceUUID().equals(serviceUUID)) {
- //
- Serial.print("Found our device! address: ");
- advertisedDevice.getScan()->stop();
- pServerAddress = new BLEAddress(advertisedDevice.getAddress());
- doConnect = true;
- } // Found our server
- } // onResult
- }; // MyAdvertisedDeviceCallbacks
- void setup() {
- Serial.begin(115200);
- Serial.println("Starting Arduino BLE Client application...");
- BLEDevice::init("");
- BLEScan* pBLEScan = BLEDevice::getScan();
- pBLEScan->setAdvertisedDeviceCallbacks(new MyAdvertisedDeviceCallbacks());
- pBLEScan->setActiveScan(true);
- pBLEScan->start(30);
- } // End of setup.
- // This is the Arduino main loop function.
- void loop() {
- if (doConnect == true) {
- if (connectToServer(*pServerAddress)) {
- Serial.println("We are now connected to the BLE Server.");
- connected = true;
- } else {
- Serial.println("We have failed to connect to the server; there is nothin more we will do.");
- }
- //doConnect = false;
- }
- if (connected == false){
- BLEDevice::getScan()->start(0);
- }
- else{
- doConnect = false;
- }
- delay(1000); // Delay a second between loops.
- } // End of loop
rst:0x1 (POWERON_RESET),boot:0x13 (SPI_FAST_FLASH_BOOT)
configsip: 0, SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:1
load:0x3fff0018,len:4
load:0x3fff001c,len:1216
ho 0 tail 12 room 4
load:0x40078000,len:9720
ho 0 tail 12 room 4
load:0x40080400,len:6352
entry 0x400806b8
Starting Arduino BLE Client application...
BLE Advertised Device found: Name: , Address: 19:e7:99:d9:32:64, manufacturer data: 060001092002e206e435e8b3b0de4daa475d8a7609aad95f554fc87cd5
BLE Advertised Device found: Name: , Address: 78:bd:bc:41:75:fc, manufacturer data: 7500420401808078bdbc4175fc7abdbc819fc201000000000000
BLE Advertised Device found: Name: , Address: 79:1a:60:1b:5a:40, manufacturer data: 4c001005481c78327b, txPower: 12
BLE Advertised Device found: Name: , Address: 74:3e:c8:ef:1b:57, manufacturer data: 4c001005051c4e8858, txPower: 12
BLE Advertised Device found: Name: , Address: 5500:9a:4d:f7, manufacturer data: 4c001006131a07f82cda, txPower: 12
BLE Advertised Device found: Name: UART, Address: 80:7d:3a:c5:06:e6, serviceUUID: 4fafc201-1fb5-459e-8fcc-c5c9c331914b, txPower: 3
4fafc201-1fb5-459e-8fcc-c5c9c331914b
Found our device! address: Forming a connection to 80:7d:3a:c5:06:e6
- Created client
connected again ...
- Connected to server
Service: uuid: 4fafc201-1fb5-459e-8fcc-c5c9c331914b, start_handle: 40 0x0028, end_handle: 65535 0xffff
- Found our service
- Found our characteristic
We are now connected to the BLE Server.
As you can see, the code in the client never reaches the notifyCallback handler method. I have looked for answers on this forum, tried quite a few things, but no luck. Any idea what I am doing wrong?
Thx in advance for any suggestions.