Skip to content

Commit 653b911

Browse files
committed
reset HVC state before sending indication to prevent stale signals
1 parent 2458c77 commit 653b911

3 files changed

Lines changed: 20 additions & 24 deletions

File tree

libraries/Bluefruit52Lib/src/BLECharacteristic.cpp

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -874,7 +874,9 @@ bool BLECharacteristic::indicate(uint16_t conn_hdl, const void* data, uint16_t l
874874

875875
LOG_LV2("CHR", "Indicate %d bytes", packet_len);
876876

877-
// Blocking wait until receiving confirmation from peer
877+
// Blocking wait until receiving confirmation from peer.
878+
// Reset HVC state BEFORE hvx() so a fast HVC event isn't drained as stale.
879+
VERIFY ( conn->prepareForIndicateConfirm() );
878880
VERIFY_STATUS( sd_ble_gatts_hvx(conn_hdl, &hvx_params), false );
879881
VERIFY ( conn->waitForIndicateConfirm() );
880882

libraries/Bluefruit52Lib/src/BLEConnection.cpp

Lines changed: 16 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -56,11 +56,11 @@ BLEConnection::BLEConnection(uint16_t conn_hdl, ble_gap_evt_connected_t const* e
5656

5757
_hvn_sem = xSemaphoreCreateCounting(hvn_qsize, hvn_qsize);
5858
_wrcmd_sem = xSemaphoreCreateCounting(wrcmd_qsize, wrcmd_qsize);
59+
_hvc_sem = xSemaphoreCreateBinary();
5960

6061
_sec_mode.sm = _sec_mode.lv = 1; // default to open
6162

6263
_bonded = false;
63-
_hvc_sem = NULL;
6464
_hvc_received = false;
6565

6666
_ediv = 0xFFFF;
@@ -70,11 +70,9 @@ BLEConnection::BLEConnection(uint16_t conn_hdl, ble_gap_evt_connected_t const* e
7070

7171
BLEConnection::~BLEConnection()
7272
{
73-
vSemaphoreDelete( _hvn_sem );
74-
vSemaphoreDelete( _wrcmd_sem );
75-
76-
//------------- on-the-fly data must be freed -------------//
77-
if (_hvc_sem ) vSemaphoreDelete(_hvc_sem );
73+
vSemaphoreDelete(_hvn_sem);
74+
vSemaphoreDelete(_wrcmd_sem);
75+
vSemaphoreDelete(_hvc_sem);
7876
}
7977

8078
uint16_t BLEConnection::handle (void)
@@ -289,25 +287,22 @@ bool BLEConnection::requestPairing(void)
289287

290288
void BLEConnection::setIndicateConfirmTimeout(uint32_t timeout_ms)
291289
{
292-
_indicate_confirm_timeout = (timeout_ms == portMAX_DELAY) ? portMAX_DELAY : pdMS_TO_TICKS(timeout_ms);
290+
_indicate_confirm_timeout = (timeout_ms == UINT32_MAX) ? portMAX_DELAY : pdMS_TO_TICKS(timeout_ms);
293291
}
294292

295-
bool BLEConnection::waitForIndicateConfirm(void)
293+
// Must be called BEFORE sd_ble_gatts_hvx() to clear any stale HVC state from a
294+
// previous indication (e.g. a late HVC that arrived after a timeout). Pairs with
295+
// waitForIndicateConfirm().
296+
bool BLEConnection::prepareForIndicateConfirm(void)
296297
{
297-
// Lazy-allocate once per connection and reuse. Avoids a create/delete race
298-
// with the BLE event handler that may give the semaphore on HVC/timeout.
299-
if (_hvc_sem == NULL)
300-
{
301-
_hvc_sem = xSemaphoreCreateBinary();
302-
if (_hvc_sem == NULL) return false;
303-
}
304-
305-
// Drain any stale signal left from a previous call (e.g. late HVC after timeout)
306298
xSemaphoreTake(_hvc_sem, 0);
307-
308299
_hvc_received = false;
309-
xSemaphoreTake(_hvc_sem, _indicate_confirm_timeout);
300+
return true;
301+
}
310302

303+
bool BLEConnection::waitForIndicateConfirm(void)
304+
{
305+
xSemaphoreTake(_hvc_sem, _indicate_confirm_timeout);
311306
return _hvc_received;
312307
}
313308

@@ -440,7 +435,7 @@ void BLEConnection::_eventHandler(ble_evt_t* evt)
440435
LOG_LV2("GATTS", "Confirm received handle = 0x%04X", evt->evt.gatts_evt.params.hvc.handle);
441436

442437
_hvc_received = true;
443-
if ( _hvc_sem ) xSemaphoreGive(_hvc_sem);
438+
xSemaphoreGive(_hvc_sem);
444439
}
445440
break;
446441

@@ -452,7 +447,7 @@ void BLEConnection::_eventHandler(ble_evt_t* evt)
452447
if (BLE_GATT_TIMEOUT_SRC_PROTOCOL == timeout_src)
453448
{
454449
_hvc_received = false;
455-
if ( _hvc_sem ) xSemaphoreGive(_hvc_sem);
450+
xSemaphoreGive(_hvc_sem);
456451
}
457452
}
458453
break;

libraries/Bluefruit52Lib/src/BLEConnection.h

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -66,8 +66,6 @@ class BLEConnection
6666

6767
SemaphoreHandle_t _hvn_sem;
6868
SemaphoreHandle_t _wrcmd_sem;
69-
70-
// On-demand semaphore/data that are created on the fly
7169
SemaphoreHandle_t _hvc_sem;
7270

7371
TickType_t _indicate_confirm_timeout;
@@ -112,6 +110,7 @@ class BLEConnection
112110
bool getHvnPacket(void);
113111
bool releaseHvnPacket(void);
114112
bool getWriteCmdPacket(void);
113+
bool prepareForIndicateConfirm(void);
115114
bool waitForIndicateConfirm(void);
116115

117116
bool saveBondKey(bond_keys_t const* ltkey);

0 commit comments

Comments
 (0)