From 8510ecf6e30101d0861052905b3d5fdeefb555b5 Mon Sep 17 00:00:00 2001 From: Nirosharn Amarasinghe Date: Wed, 30 Nov 2022 09:42:43 +0100 Subject: [PATCH] Bluetooth: controller: corrected time stamps for unframed RX Corrected an omission in the ISO-AL that required an SDU interval to be added to the reconstructed RX time stamps for each SDU after the first. Signed-off-by: Nirosharn Amarasinghe --- subsys/bluetooth/controller/ll_sw/isoal.c | 36 ++++++++++++++++++++++- subsys/bluetooth/controller/ll_sw/isoal.h | 1 + 2 files changed, 36 insertions(+), 1 deletion(-) diff --git a/subsys/bluetooth/controller/ll_sw/isoal.c b/subsys/bluetooth/controller/ll_sw/isoal.c index ef9a41d24cb..60612b7002c 100644 --- a/subsys/bluetooth/controller/ll_sw/isoal.c +++ b/subsys/bluetooth/controller/ll_sw/isoal.c @@ -208,6 +208,7 @@ isoal_status_t isoal_sink_create( session->handle = handle; session->framed = framed; session->sdu_interval = sdu_interval; + session->burst_number = burst_number; /* Todo: Next section computing various constants, should potentially be a * function in itself as a number of the dependencies could be changed while @@ -703,6 +704,7 @@ static isoal_status_t isoal_rx_unframed_consume(struct isoal_sink *sink, if (sp->fsm == ISOAL_START) { struct isoal_sdu_produced *sdu; uint32_t anchorpoint; + uint16_t sdu_offset; int32_t latency; sp->sdu_status = ISOAL_SDU_STATUS_VALID; @@ -711,11 +713,43 @@ static isoal_status_t isoal_rx_unframed_consume(struct isoal_sink *sink, session->seqn++; seq_err = false; - /* Todo: anchorpoint must be reference anchor point, should be fixed in LL */ + /* The incoming time stamp for each PDU is expected to be the + * CIS / BIS reference anchor point. SDU reference point is + * reconstructed by adding the precalculated latency constant. + * + * BT Core V5.3 : Vol 6 Low Energy Controller : Part G IS0-AL: + * 3.2.2 SDU synchronization reference using unframed PDUs: + * + * The CIS reference anchor point is computed excluding any + * retransmissions or missed subevents and shall be set to the + * start of the isochronous event in which the first PDU + * containing the SDU could have been transferred. + * + * The BIG reference anchor point is the anchor point of the BIG + * event that the PDU is associated with. + */ anchorpoint = meta->timestamp; latency = session->latency_unframed; sdu = &sp->sdu; sdu->timestamp = isoal_get_wrapped_time_us(anchorpoint, latency); + + /* If there are multiple SDUs in an ISO interval + * (SDU interval < ISO Interval) every SDU after the first + * should add an SDU interval to the time stamp. + * + * BT Core V5.3 : Vol 6 Low Energy Controller : Part G IS0-AL: + * 3.2.2 SDU synchronization reference using unframed PDUs: + * + * All PDUs belonging to a burst as defined by the configuration + * of BN have the same reference anchor point. When multiple + * SDUs have the same reference anchor point, the first SDU uses + * the reference anchor point timing. Each subsequent SDU + * increases the SDU synchronization reference timing with one + * SDU interval. + */ + sdu_offset = (meta->payload_number % session->burst_number) / session->pdus_per_sdu; + sdu->timestamp = isoal_get_wrapped_time_us(sdu->timestamp, + sdu_offset * session->sdu_interval); } else { sp->pdu_cnt++; } diff --git a/subsys/bluetooth/controller/ll_sw/isoal.h b/subsys/bluetooth/controller/ll_sw/isoal.h index dd5d0005b89..9d6a5be6d8a 100644 --- a/subsys/bluetooth/controller/ll_sw/isoal.h +++ b/subsys/bluetooth/controller/ll_sw/isoal.h @@ -262,6 +262,7 @@ struct isoal_sink_session { uint16_t handle; uint8_t pdus_per_sdu; uint8_t framed; + uint8_t burst_number; uint32_t sdu_interval; uint32_t latency_unframed; uint32_t latency_framed;