Remove semaphores, use task notifications instead.

This commit is contained in:
h2zero 2020-06-11 08:06:16 -06:00
parent e987ad58b2
commit 74f48f5d5e
8 changed files with 34 additions and 36 deletions

View file

@ -27,7 +27,6 @@
/**************************/ /**************************/
#include "NimBLEUUID.h" #include "NimBLEUUID.h"
#include "FreeRTOS.h"
#include <vector> #include <vector>

View file

@ -19,7 +19,6 @@
#include "NimBLE2902.h" #include "NimBLE2902.h"
#include "NimBLE2904.h" #include "NimBLE2904.h"
#include "NimBLEDevice.h" #include "NimBLEDevice.h"
#include "NimBLEUtils.h"
#include "NimBLELog.h" #include "NimBLELog.h"
#define NULL_HANDLE (0xffff) #define NULL_HANDLE (0xffff)
@ -51,21 +50,13 @@ NimBLECharacteristic::NimBLECharacteristic(const NimBLEUUID &uuid, uint16_t prop
m_pService = pService; m_pService = pService;
m_value = ""; m_value = "";
m_valMux = portMUX_INITIALIZER_UNLOCKED; m_valMux = portMUX_INITIALIZER_UNLOCKED;
m_pTaskData = nullptr;
if(properties & NIMBLE_PROPERTY::INDICATE){
m_pIndSemaphore = new FreeRTOS::Semaphore("ConfEvt");
} else {
m_pIndSemaphore = nullptr;
}
} // NimBLECharacteristic } // NimBLECharacteristic
/** /**
* @brief Destructor. * @brief Destructor.
*/ */
NimBLECharacteristic::~NimBLECharacteristic() { NimBLECharacteristic::~NimBLECharacteristic() {
if(m_pIndSemaphore != nullptr) {
delete(m_pIndSemaphore);
}
} // ~NimBLECharacteristic } // ~NimBLECharacteristic
@ -271,9 +262,10 @@ void NimBLECharacteristic::setSubscribe(struct ble_gap_event *event) {
subVal |= NIMBLE_DESC_FLAG_INDICATE; subVal |= NIMBLE_DESC_FLAG_INDICATE;
} }
if(m_pIndSemaphore != nullptr) { if(m_pTaskData != nullptr) {
m_pIndSemaphore->give((subVal & NIMBLE_DESC_FLAG_INDICATE) ? 0 : m_pTaskData->rc = (subVal & NIMBLE_DESC_FLAG_INDICATE) ? 0 :
NimBLECharacteristicCallbacks::Status::ERROR_INDICATE_DISABLED); NimBLECharacteristicCallbacks::Status::ERROR_INDICATE_DISABLED;
xTaskNotifyGive(m_pTaskData->task);
} }
NIMBLE_LOGI(LOG_TAG, "New subscribe value for conn: %d val: %d", NIMBLE_LOGI(LOG_TAG, "New subscribe value for conn: %d val: %d",
@ -358,18 +350,13 @@ void NimBLECharacteristic::notify(bool is_notification) {
for (auto &it : p2902->m_subscribedVec) { for (auto &it : p2902->m_subscribedVec) {
uint16_t _mtu = getService()->getServer()->getPeerMTU(it.conn_id); uint16_t _mtu = getService()->getServer()->getPeerMTU(it.conn_id);
os_mbuf *om;
if(_mtu == 0) { // check if connected and subscribed
if(_mtu == 0 || it.sub_val == 0) {
//NIMBLE_LOGD(LOG_TAG, "peer not connected"); //NIMBLE_LOGD(LOG_TAG, "peer not connected");
continue; continue;
} }
if(it.sub_val == 0) {
//NIMBLE_LOGD(LOG_TAG, "Skipping unsubscribed client");
continue;
}
if (length > _mtu - 3) { if (length > _mtu - 3) {
NIMBLE_LOGW(LOG_TAG, "- Truncating to %d bytes (maximum notify size)", _mtu - 3); NIMBLE_LOGW(LOG_TAG, "- Truncating to %d bytes (maximum notify size)", _mtu - 3);
} }
@ -389,20 +376,25 @@ void NimBLECharacteristic::notify(bool is_notification) {
// don't create the m_buf until we are sure to send the data or else // don't create the m_buf until we are sure to send the data or else
// we could be allocating a buffer that doesn't get released. // we could be allocating a buffer that doesn't get released.
// We also must create it in each loop iteration because it is consumed with each host call. // We also must create it in each loop iteration because it is consumed with each host call.
om = ble_hs_mbuf_from_flat((uint8_t*)value.data(), length); os_mbuf *om = ble_hs_mbuf_from_flat((uint8_t*)value.data(), length);
NimBLECharacteristicCallbacks::Status statusRC; NimBLECharacteristicCallbacks::Status statusRC;
if(m_pIndSemaphore != nullptr && !is_notification) {
m_pIndSemaphore->take("indicate"); if(!is_notification && (m_properties & NIMBLE_PROPERTY::INDICATE)) {
ble_task_data_t taskData = {nullptr, xTaskGetCurrentTaskHandle(),0, nullptr};
m_pTaskData = &taskData;
rc = ble_gattc_indicate_custom(it.conn_id, m_handle, om); rc = ble_gattc_indicate_custom(it.conn_id, m_handle, om);
if(rc != 0){ if(rc != 0){
m_pIndSemaphore->give();
statusRC = NimBLECharacteristicCallbacks::Status::ERROR_GATT; statusRC = NimBLECharacteristicCallbacks::Status::ERROR_GATT;
} else { } else {
rc = m_pIndSemaphore->wait(); ulTaskNotifyTake(pdTRUE, portMAX_DELAY);
rc = m_pTaskData->rc;
} }
if(rc == 0 || rc == BLE_HS_EDONE) { m_pTaskData = nullptr;
if(rc == BLE_HS_EDONE) {
rc = 0; rc = 0;
statusRC = NimBLECharacteristicCallbacks::Status::SUCCESS_INDICATE; statusRC = NimBLECharacteristicCallbacks::Status::SUCCESS_INDICATE;
} else if(rc == BLE_HS_ETIMEOUT) { } else if(rc == BLE_HS_ETIMEOUT) {

View file

@ -42,7 +42,6 @@ typedef enum {
#include "NimBLEService.h" #include "NimBLEService.h"
#include "NimBLEDescriptor.h" #include "NimBLEDescriptor.h"
#include "FreeRTOS.h"
#include <string> #include <string>
#include <vector> #include <vector>
@ -120,7 +119,7 @@ private:
NimBLEService* m_pService; NimBLEService* m_pService;
std::string m_value; std::string m_value;
std::vector<NimBLEDescriptor*> m_dscVec; std::vector<NimBLEDescriptor*> m_dscVec;
FreeRTOS::Semaphore *m_pIndSemaphore; ble_task_data_t *m_pTaskData;
portMUX_TYPE m_valMux; portMUX_TYPE m_valMux;
}; // NimBLECharacteristic }; // NimBLECharacteristic

View file

@ -22,7 +22,6 @@
#include "NimBLECharacteristic.h" #include "NimBLECharacteristic.h"
#include "NimBLEUUID.h" #include "NimBLEUUID.h"
#include "FreeRTOS.h"
#include <string> #include <string>

View file

@ -19,7 +19,6 @@
#if defined(CONFIG_BT_NIMBLE_ROLE_PERIPHERAL) #if defined(CONFIG_BT_NIMBLE_ROLE_PERIPHERAL)
#include "NimBLEServer.h" #include "NimBLEServer.h"
#include "NimBLEUtils.h"
#include "NimBLEDevice.h" #include "NimBLEDevice.h"
#include "NimBLELog.h" #include "NimBLELog.h"
@ -296,8 +295,9 @@ size_t NimBLEServer::getConnectedCount() {
if(event->notify_tx.indication && event->notify_tx.status != 0) { if(event->notify_tx.indication && event->notify_tx.status != 0) {
for(auto &it : server->m_notifyChrVec) { for(auto &it : server->m_notifyChrVec) {
if(it->getHandle() == event->notify_tx.attr_handle) { if(it->getHandle() == event->notify_tx.attr_handle) {
if(it->m_pIndSemaphore != nullptr) { if(it->m_pTaskData != nullptr) {
it->m_pIndSemaphore->give(event->notify_tx.status); it->m_pTaskData->rc = event->notify_tx.status;
xTaskNotifyGive(it->m_pTaskData->task);
} }
break; break;
} }

View file

@ -20,11 +20,12 @@
#include "nimconfig.h" #include "nimconfig.h"
#if defined(CONFIG_BT_NIMBLE_ROLE_PERIPHERAL) #if defined(CONFIG_BT_NIMBLE_ROLE_PERIPHERAL)
#include "NimBLEUtils.h"
#include "NimBLEAddress.h" #include "NimBLEAddress.h"
#include "NimBLEAdvertising.h" #include "NimBLEAdvertising.h"
#include "NimBLEService.h" #include "NimBLEService.h"
#include "NimBLESecurity.h" #include "NimBLESecurity.h"
#include "FreeRTOS.h"
class NimBLEService; class NimBLEService;
class NimBLECharacteristic; class NimBLECharacteristic;

View file

@ -20,10 +20,9 @@
#include "nimconfig.h" #include "nimconfig.h"
#if defined(CONFIG_BT_NIMBLE_ROLE_PERIPHERAL) #if defined(CONFIG_BT_NIMBLE_ROLE_PERIPHERAL)
#include "NimBLECharacteristic.h"
#include "NimBLEServer.h" #include "NimBLEServer.h"
#include "NimBLECharacteristic.h"
#include "NimBLEUUID.h" #include "NimBLEUUID.h"
#include "FreeRTOS.h"
class NimBLEServer; class NimBLEServer;

View file

@ -13,6 +13,15 @@
#include "host/ble_gap.h" #include "host/ble_gap.h"
#include <string>
typedef struct {
void *pATT;
TaskHandle_t task;
int rc;
std::string *buf;
} ble_task_data_t;
extern "C"{ extern "C"{
char *addr_str(const void *addr); char *addr_str(const void *addr);
void print_conn_desc(const struct ble_gap_conn_desc *desc); void print_conn_desc(const struct ble_gap_conn_desc *desc);