Skip to content

Commit be91cfe

Browse files
cvinayakkartben
authored andcommitted
Bluetooth: Controller: Fix incorrect event_count when CIG overlaps
Fix incorrect event_count use in CIG events when the next CIG interval's prepare overlaps with the current CIG event. Use separate event_count_prepare variable in ULL and copy the value in LLL event. Signed-off-by: Vinayak Kariappa Chettimada <[email protected]>
1 parent 3bf3308 commit be91cfe

File tree

6 files changed

+30
-7
lines changed

6 files changed

+30
-7
lines changed

subsys/bluetooth/controller/ll_sw/lll_conn_iso.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,8 @@ struct lll_conn_iso_stream {
4545
struct lll_conn_iso_stream_rxtx tx; /* TX parameters */
4646

4747
/* Event and payload counters */
48-
uint64_t event_count:39; /* cisEventCount */
48+
uint64_t event_count_prepare:39; /* cisEventCount in overlapping CIG prepare */
49+
uint64_t event_count:39; /* cisEventCount in current CIG event */
4950

5051
/* Acknowledgment and flow control */
5152
uint8_t sn:1; /* Sequence number */

subsys/bluetooth/controller/ll_sw/nordic/lll/lll_central_iso.c

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -150,6 +150,9 @@ static int prepare_cb(struct lll_prepare_param *p)
150150
/* Get reference to ACL context */
151151
conn_lll = ull_conn_lll_get(cis_lll->acl_handle);
152152

153+
/* Pick the event_count calculated in the ULL prepare */
154+
cis_lll->event_count = cis_lll->event_count_prepare;
155+
153156
/* Event counter value, 0-15 bit of cisEventCounter */
154157
event_counter = cis_lll->event_count;
155158

@@ -357,6 +360,9 @@ static int prepare_cb(struct lll_prepare_param *p)
357360
do {
358361
cis_lll = ull_conn_iso_lll_stream_get_by_group(cig_lll, &cis_handle);
359362
if (cis_lll && cis_lll->active) {
363+
/* Pick the event_count calculated in the ULL prepare */
364+
cis_lll->event_count = cis_lll->event_count_prepare;
365+
360366
/* Adjust sn and nesn for skipped CIG events */
361367
payload_count_lazy_update(cis_lll, cig_lll->latency_event);
362368

subsys/bluetooth/controller/ll_sw/nordic/lll/lll_peripheral_iso.c

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -164,6 +164,9 @@ static int prepare_cb(struct lll_prepare_param *p)
164164
/* Get reference to ACL context */
165165
conn_lll = ull_conn_lll_get(cis_lll->acl_handle);
166166

167+
/* Pick the event_count calculated in the ULL prepare */
168+
cis_lll->event_count = cis_lll->event_count_prepare;
169+
167170
/* Event counter value, 0-15 bit of cisEventCounter */
168171
event_counter = cis_lll->event_count;
169172

@@ -374,6 +377,9 @@ static int prepare_cb(struct lll_prepare_param *p)
374377
break;
375378
}
376379

380+
/* Pick the event_count calculated in the ULL prepare */
381+
cis_lll->event_count = cis_lll->event_count_prepare;
382+
377383
/* Adjust sn and nesn for skipped CIG events */
378384
payload_count_lazy(cis_lll, cig_lll->latency_event);
379385

subsys/bluetooth/controller/ll_sw/ull_central_iso.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -929,6 +929,11 @@ uint8_t ull_central_iso_setup(uint16_t cis_handle,
929929
#if defined(CONFIG_BT_CTLR_ISOAL_PSN_IGNORE)
930930
cis->pkt_seq_num = 0U;
931931
#endif /* CONFIG_BT_CTLR_ISOAL_PSN_IGNORE */
932+
/* It is intentional to initialize to the 39 bit maximum value and rollover to 0 in the
933+
* prepare function, the event counter is pre-incremented in prepare function for the
934+
* current ISO event.
935+
*/
936+
cis->lll.event_count_prepare = LLL_CONN_ISO_EVENT_COUNT_MAX;
932937
cis->lll.event_count = LLL_CONN_ISO_EVENT_COUNT_MAX;
933938
cis->lll.next_subevent = 0U;
934939
cis->lll.tifs_us = conn->lll.tifs_cis_us;

subsys/bluetooth/controller/ll_sw/ull_conn_iso.c

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -711,17 +711,17 @@ void ull_conn_iso_ticker_cb(uint32_t ticks_at_expire, uint32_t ticks_drift,
711711
* has been reached, and offset calculated.
712712
*/
713713
if (cis->lll.handle != 0xFFFF && cis->lll.active) {
714-
cis->lll.event_count += (lazy + 1U);
714+
cis->lll.event_count_prepare += (lazy + 1U);
715715

716716
#if !defined(CONFIG_BT_CTLR_JIT_SCHEDULING)
717-
cis->lll.event_count -= cis->lll.lazy_active;
717+
cis->lll.event_count_prepare -= cis->lll.lazy_active;
718718
cis->lll.lazy_active = 0U;
719719
#endif /* !CONFIG_BT_CTLR_JIT_SCHEDULING */
720720

721721
leading_event_count = MAX(leading_event_count,
722-
cis->lll.event_count);
722+
cis->lll.event_count_prepare);
723723

724-
ull_iso_lll_event_prepare(cis->lll.handle, cis->lll.event_count);
724+
ull_iso_lll_event_prepare(cis->lll.handle, cis->lll.event_count_prepare);
725725
}
726726

727727
/* Latch datapath validity entering event */
@@ -975,7 +975,7 @@ void ull_conn_iso_start(struct ll_conn *conn, uint16_t cis_handle,
975975
cis_offset = cis->offset + iso_interval_us - acl_latency_us;
976976
}
977977

978-
cis->lll.event_count += lost_cig_events;
978+
cis->lll.event_count_prepare += lost_cig_events;
979979

980980
lost_payloads = (lost_cig_events - (cis->lll.rx.ft - 1)) * cis->lll.rx.bn;
981981
cis->lll.rx.payload_count += lost_payloads;
@@ -1520,7 +1520,7 @@ void ull_conn_iso_transmit_test_cig_interval(uint16_t handle, uint32_t ticks_at_
15201520
* on 64-bit sdu_counter:
15211521
* (39 bits x 22 bits (4x10^6 us) = 61 bits / 8 bits (255 us) = 53 bits)
15221522
*/
1523-
sdu_counter = DIV_ROUND_UP((cis->lll.event_count + 1U) * iso_interval,
1523+
sdu_counter = DIV_ROUND_UP((cis->lll.event_count_prepare + 1U) * iso_interval,
15241524
sdu_interval);
15251525

15261526
if (cis->hdr.test_mode.tx.sdu_counter == 0U) {

subsys/bluetooth/controller/ll_sw/ull_peripheral_iso.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -333,6 +333,11 @@ uint8_t ull_peripheral_iso_setup(struct pdu_data_llctrl_cis_ind *ind,
333333
#if defined(CONFIG_BT_CTLR_ISOAL_PSN_IGNORE)
334334
cis->pkt_seq_num = 0U;
335335
#endif /* CONFIG_BT_CTLR_ISOAL_PSN_IGNORE */
336+
/* It is intentional to initialize to the 39 bit maximum value and rollover to 0 in the
337+
* prepare function, the event counter is pre-incremented in prepare function for the
338+
* current ISO event.
339+
*/
340+
cis->lll.event_count_prepare = LLL_CONN_ISO_EVENT_COUNT_MAX;
336341
cis->lll.event_count = LLL_CONN_ISO_EVENT_COUNT_MAX;
337342
cis->lll.next_subevent = 0U;
338343
cis->lll.tifs_us = conn->lll.tifs_cis_us;

0 commit comments

Comments
 (0)