@@ -51,6 +51,9 @@ static void isr_done(void *param);
51
51
52
52
#if defined(CONFIG_BT_CTLR_ADV_SYNC_PDU_BACK2BACK )
53
53
static void isr_tx (void * param );
54
+ static int aux_ptr_get (struct pdu_adv * pdu , struct pdu_adv_aux_ptr * * aux_ptr );
55
+ static void chain_pdu_aux_ptr_chan_idx_set (struct lll_adv_sync * lll );
56
+ static void aux_ptr_chan_idx_set (struct lll_adv_sync * lll , struct pdu_adv * pdu );
54
57
static void switch_radio_complete_and_b2b_tx (const struct lll_adv_sync * lll , uint8_t phy_s );
55
58
#endif /* CONFIG_BT_CTLR_ADV_SYNC_PDU_BACK2BACK */
56
59
@@ -181,22 +184,38 @@ static int prepare_cb(struct lll_prepare_param *p)
181
184
cte_len_us = 0U ;
182
185
#endif /* CONFIG_BT_CTLR_DF_ADV_CTE_TX) */
183
186
184
- radio_pkt_tx_set (pdu );
185
-
186
187
#if defined(CONFIG_BT_CTLR_ADV_SYNC_PDU_BACK2BACK )
187
188
if (pdu -> adv_ext_ind .ext_hdr_len && pdu -> adv_ext_ind .ext_hdr .aux_ptr ) {
189
+ /* Set the last used auxiliary PDU for transmission */
188
190
lll -> last_pdu = pdu ;
189
191
192
+ /* Populate chan idx for AUX_ADV_IND PDU */
193
+ aux_ptr_chan_idx_set (lll , pdu );
194
+
190
195
radio_isr_set (isr_tx , lll );
191
196
radio_tmr_tifs_set (EVENT_SYNC_B2B_MAFS_US );
192
197
switch_radio_complete_and_b2b_tx (lll , phy_s );
193
- } else
194
- #endif /* CONFIG_BT_CTLR_ADV_SYNC_PDU_BACK2BACK */
198
+ } else {
199
+ /* No chain PDU */
200
+ lll -> last_pdu = NULL ;
201
+
202
+ #else /* !CONFIG_BT_CTLR_ADV_SYNC_PDU_BACK2BACK */
195
203
{
204
+ #endif /* !CONFIG_BT_CTLR_ADV_SYNC_PDU_BACK2BACK */
205
+
196
206
radio_isr_set (isr_done , lll );
197
207
radio_switch_complete_and_disable ();
198
208
}
199
209
210
+ #if defined(CONFIG_BT_CTLR_ADV_ISO ) && defined(CONFIG_BT_TICKER_EXT_EXPIRE_INFO )
211
+ if (lll -> iso ) {
212
+ ull_adv_iso_lll_biginfo_fill (pdu , lll );
213
+ }
214
+ #endif /* CONFIG_BT_CTLR_ADV_ISO && CONFIG_BT_TICKER_EXT_EXPIRE_INFO */
215
+
216
+ /* Set the Radio Tx Packet */
217
+ radio_pkt_tx_set (pdu );
218
+
200
219
ticks_at_event = p -> ticks_at_expire ;
201
220
ull = HDR_LLL2ULL (lll );
202
221
ticks_at_event += lll_event_offset_get (ull );
@@ -253,11 +272,10 @@ static int prepare_cb(struct lll_prepare_param *p)
253
272
}
254
273
#endif /* CONFIG_BT_CTLR_XTAL_ADVANCED */
255
274
256
- #if defined(CONFIG_BT_CTLR_ADV_ISO ) && defined(CONFIG_BT_TICKER_EXT_EXPIRE_INFO )
257
- if (lll -> iso ) {
258
- ull_adv_iso_lll_biginfo_fill (pdu , lll );
259
- }
260
- #endif /* CONFIG_BT_CTLR_ADV_ISO && CONFIG_BT_TICKER_EXT_EXPIRE_INFO */
275
+ #if defined(CONFIG_BT_CTLR_ADV_SYNC_PDU_BACK2BACK )
276
+ /* Populate chan idx for AUX_CHAIN_IND PDU */
277
+ chain_pdu_aux_ptr_chan_idx_set (lll );
278
+ #endif /* CONFIG_BT_CTLR_ADV_SYNC_PDU_BACK2BACK */
261
279
262
280
ret = lll_prepare_done (lll );
263
281
LL_ASSERT (!ret );
@@ -332,10 +350,12 @@ static void isr_done(void *param)
332
350
#if defined(CONFIG_BT_CTLR_ADV_SYNC_PDU_BACK2BACK )
333
351
static void isr_tx (void * param )
334
352
{
353
+ struct pdu_adv_aux_ptr * aux_ptr ;
335
354
struct lll_adv_sync * lll_sync ;
336
355
struct pdu_adv * pdu ;
337
356
struct lll_adv * lll ;
338
357
uint32_t cte_len_us ;
358
+ int err ;
339
359
340
360
if (IS_ENABLED (CONFIG_BT_CTLR_PROFILE_ISR )) {
341
361
lll_prof_latency_capture ();
@@ -344,14 +364,22 @@ static void isr_tx(void *param)
344
364
/* Clear radio tx status and events */
345
365
lll_isr_tx_status_reset ();
346
366
367
+ /* Get reference to sync and primary advertising LLL contexts */
347
368
lll_sync = param ;
348
369
lll = lll_sync -> adv ;
349
370
350
- /* FIXME: Use implementation defined channel index */
351
- lll_chan_set (0 );
371
+ /* Get reference to aux pointer structure */
372
+ err = aux_ptr_get (lll_sync -> last_pdu , & aux_ptr );
373
+ LL_ASSERT (!err && aux_ptr );
352
374
375
+ /* Use channel idx that was in aux_ptr */
376
+ lll_chan_set (aux_ptr -> chan_idx );
377
+
378
+ /* Get reference to the auxiliary chain PDU */
353
379
pdu = lll_adv_pdu_linked_next_get (lll_sync -> last_pdu );
354
380
LL_ASSERT (pdu );
381
+
382
+ /* Set the last used auxiliary PDU for transmission */
355
383
lll_sync -> last_pdu = pdu ;
356
384
357
385
#if defined(CONFIG_BT_CTLR_DF_ADV_CTE_TX )
@@ -403,11 +431,97 @@ static void isr_tx(void *param)
403
431
HAL_RADIO_GPIO_PA_OFFSET );
404
432
#endif /* HAL_RADIO_GPIO_HAVE_PA_PIN */
405
433
434
+ /* Populate chan idx for AUX_CHAIN_IND PDU */
435
+ chain_pdu_aux_ptr_chan_idx_set (lll_sync );
436
+
406
437
if (IS_ENABLED (CONFIG_BT_CTLR_PROFILE_ISR )) {
407
438
lll_prof_send ();
408
439
}
409
440
}
410
441
442
+ static int aux_ptr_get (struct pdu_adv * pdu , struct pdu_adv_aux_ptr * * aux_ptr )
443
+ {
444
+ struct pdu_adv_com_ext_adv * com_hdr ;
445
+ struct pdu_adv_ext_hdr * hdr ;
446
+ uint8_t * dptr ;
447
+
448
+ /* Get reference to common extended header */
449
+ com_hdr = (void * )& pdu -> adv_ext_ind ;
450
+ if (com_hdr -> ext_hdr_len == 0U ) {
451
+ return - EINVAL ;
452
+ }
453
+
454
+ /* Get reference to extended header flags and header fields */
455
+ hdr = (void * )com_hdr -> ext_hdr_adv_data ;
456
+ dptr = hdr -> data ;
457
+
458
+ /* No traverse through of AdvA and TargetA.
459
+ * These are RFU for periodic advertising, is not set by local device.
460
+ */
461
+
462
+ /* traverse through CTEInfo flag, if present */
463
+ #if defined(CONFIG_BT_CTLR_DF_ADV_CTE_TX )
464
+ if (hdr -> cte_info ) {
465
+ dptr += sizeof (struct pdu_cte_info );
466
+ }
467
+ #endif /* CONFIG_BT_CTLR_DF_ADV_CTE_TX */
468
+
469
+ /* traverse through adi, if present */
470
+ if (hdr -> adi ) {
471
+ dptr += sizeof (struct pdu_adv_adi );
472
+ }
473
+
474
+ /* check for aux_ptr flag */
475
+ if (hdr -> aux_ptr ) {
476
+ /* Return reference to aux pointer structure */
477
+ * aux_ptr = (void * )dptr ;
478
+ } else {
479
+ * aux_ptr = NULL ;
480
+ }
481
+
482
+ return 0 ;
483
+ }
484
+
485
+ static void chain_pdu_aux_ptr_chan_idx_set (struct lll_adv_sync * lll )
486
+ {
487
+ struct pdu_adv * chain_pdu ;
488
+
489
+ /* No chain PDU */
490
+ if (!lll -> last_pdu ) {
491
+ return ;
492
+ }
493
+
494
+ /* Get reference to the auxiliary chain PDU */
495
+ chain_pdu = lll_adv_pdu_linked_next_get (lll -> last_pdu );
496
+
497
+ /* Check if there is further chain PDU */
498
+ if (chain_pdu && chain_pdu -> adv_ext_ind .ext_hdr_len &&
499
+ chain_pdu -> adv_ext_ind .ext_hdr .aux_ptr ) {
500
+ aux_ptr_chan_idx_set (lll , chain_pdu );
501
+ }
502
+ }
503
+
504
+ static void aux_ptr_chan_idx_set (struct lll_adv_sync * lll , struct pdu_adv * pdu )
505
+ {
506
+ struct pdu_adv_aux_ptr * aux_ptr ;
507
+ uint8_t chan_idx ;
508
+ int err ;
509
+
510
+ /* Get reference to aux pointer structure */
511
+ err = aux_ptr_get (pdu , & aux_ptr );
512
+ LL_ASSERT (!err && aux_ptr );
513
+
514
+ /* Calculate a new channel index */
515
+ chan_idx = lll_chan_sel_2 (lll -> data_chan_counter , lll -> data_chan_id ,
516
+ lll -> chm [lll -> chm_first ].data_chan_map ,
517
+ lll -> chm [lll -> chm_first ].data_chan_count );
518
+
519
+ /* Increment counter, for next channel index calculation */
520
+ lll -> data_chan_counter ++ ;
521
+
522
+ /* Set the channel index for the auxiliary chain PDU */
523
+ aux_ptr -> chan_idx = chan_idx ;
524
+ }
411
525
static void switch_radio_complete_and_b2b_tx (const struct lll_adv_sync * lll ,
412
526
uint8_t phy_s )
413
527
{
0 commit comments