4949
5050static int init_reset (void );
5151static int prepare_cb (struct lll_prepare_param * p );
52+ #if !defined(CONFIG_BT_TICKER_EXT_EXPIRE_INFO ) || \
53+ defined(CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK )
54+ static int aux_ptr_get (struct pdu_adv * pdu , struct pdu_adv_aux_ptr * * aux_ptr );
55+ #endif /* !CONFIG_BT_TICKER_EXT_EXPIRE_INFO ||
56+ * CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK
57+ */
5258#if !defined(CONFIG_BT_TICKER_EXT_EXPIRE_INFO )
5359static void isr_early_abort (void * param );
5460#endif /* !CONFIG_BT_TICKER_EXT_EXPIRE_INFO */
5561static void isr_done (void * param );
5662#if defined(CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK )
5763static void isr_tx_chain (void * param );
64+ static void chain_pdu_aux_ptr_chan_idx_set (struct lll_adv_aux * lll );
65+ static void aux_ptr_chan_idx_set (struct lll_adv_aux * lll , struct pdu_adv * pdu );
5866#endif /* CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK */
5967static void isr_tx_rx (void * param );
6068static void isr_rx (void * param );
@@ -150,47 +158,22 @@ static int prepare_cb(struct lll_prepare_param *p)
150158
151159#else /* !CONFIG_BT_TICKER_EXT_EXPIRE_INFO */
152160 struct pdu_adv_aux_ptr * aux_ptr ;
153- struct pdu_adv_ext_hdr * pri_hdr ;
154161 struct pdu_adv * pri_pdu ;
155- uint8_t * pri_dptr ;
162+ int err ;
156163
157164 /* Get reference to primary PDU */
158165 pri_pdu = lll_adv_data_curr_get (lll_adv );
159166 LL_ASSERT (pri_pdu -> type == PDU_ADV_TYPE_EXT_IND );
160167
161- /* Get reference to extended header */
168+ /* Get reference to common extended header */
162169 com_hdr = (void * )& pri_pdu -> adv_ext_ind ;
163- pri_hdr = (void * )com_hdr -> ext_hdr_adv_data ;
164- pri_dptr = pri_hdr -> data ;
165-
166- /* NOTE: We shall be here in auxiliary PDU prepare due to
167- * aux_ptr flag being set in the extended common header
168- * flags. Hence, ext_hdr_len is non-zero, an explicit check
169- * is not needed.
170- */
171- LL_ASSERT (com_hdr -> ext_hdr_len );
172-
173- /* traverse through adv_addr, if present */
174- if (pri_hdr -> adv_addr ) {
175- pri_dptr += BDADDR_SIZE ;
176- }
177-
178- /* traverse through tgt_addr, if present */
179- if (pri_hdr -> tgt_addr ) {
180- pri_dptr += BDADDR_SIZE ;
181- }
182-
183- /* No CTEInfo flag in primary and secondary channel PDU */
184170
185- /* traverse through adi, if present */
186- if (pri_hdr -> adi ) {
187- pri_dptr += sizeof (struct pdu_adv_adi );
188- }
189-
190- aux_ptr = (void * )pri_dptr ;
171+ /* Get reference to aux pointer structure */
172+ err = aux_ptr_get (pri_pdu , & aux_ptr );
173+ LL_ASSERT (!err );
191174
192175 /* Abort if no aux_ptr filled */
193- if (unlikely (!pri_hdr -> aux_ptr || !PDU_ADV_AUX_PTR_OFFSET_GET (aux_ptr ))) {
176+ if (unlikely (!aux_ptr || !PDU_ADV_AUX_PTR_OFFSET_GET (aux_ptr ))) {
194177 radio_isr_set (isr_early_abort , lll );
195178 radio_disable ();
196179
@@ -200,7 +183,7 @@ static int prepare_cb(struct lll_prepare_param *p)
200183 chan_idx = aux_ptr -> chan_idx ;
201184#endif /* !CONFIG_BT_TICKER_EXT_EXPIRE_INFO */
202185
203- /* Increment counter used in ULL for channel index calculation */
186+ /* Increment counter, for next channel index calculation */
204187 lll -> data_chan_counter ++ ;
205188
206189 /* Set up Radio H/W */
@@ -228,9 +211,6 @@ static int prepare_cb(struct lll_prepare_param *p)
228211 /* Use channel idx calculated or that was in aux_ptr */
229212 lll_chan_set (chan_idx );
230213
231- /* Set the Radio Tx Packet */
232- radio_pkt_tx_set (sec_pdu );
233-
234214 /* Switch to Rx if connectable or scannable */
235215 if (com_hdr -> adv_mode & (BT_HCI_LE_ADV_PROP_CONN |
236216 BT_HCI_LE_ADV_PROP_SCAN )) {
@@ -282,19 +262,38 @@ static int prepare_cb(struct lll_prepare_param *p)
282262#if defined(CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK )
283263 } else if (sec_pdu -> adv_ext_ind .ext_hdr_len &&
284264 sec_pdu -> adv_ext_ind .ext_hdr .aux_ptr ) {
265+ /* Set the last used auxiliary PDU for transmission */
285266 lll -> last_pdu = sec_pdu ;
286267
268+ /* Populate chan idx for AUX_ADV_IND PDU */
269+ aux_ptr_chan_idx_set (lll , sec_pdu );
270+
287271 radio_isr_set (isr_tx_chain , lll );
288272 radio_tmr_tifs_set (EVENT_B2B_MAFS_US );
289273 radio_switch_complete_and_b2b_tx (phy_s , lll_adv -> phy_flags ,
290274 phy_s , lll_adv -> phy_flags );
291- #endif /* CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK */
275+ } else {
276+ /* No chain PDU */
277+ lll -> last_pdu = NULL ;
292278
279+ #else /* !CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK */
293280 } else {
281+ #endif /* !CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK */
282+
294283 radio_isr_set (isr_done , lll );
295284 radio_switch_complete_and_disable ();
296285 }
297286
287+ if (IS_ENABLED (CONFIG_BT_CTLR_ADV_PERIODIC ) &&
288+ IS_ENABLED (CONFIG_BT_TICKER_EXT_EXPIRE_INFO ) &&
289+ sec_pdu -> adv_ext_ind .ext_hdr_len &&
290+ sec_pdu -> adv_ext_ind .ext_hdr .sync_info ) {
291+ ull_adv_sync_lll_syncinfo_fill (sec_pdu , lll );
292+ }
293+
294+ /* Set the Radio Tx Packet */
295+ radio_pkt_tx_set (sec_pdu );
296+
298297 ticks_at_event = p -> ticks_at_expire ;
299298 ull = HDR_LLL2ULL (lll );
300299 ticks_at_event += lll_event_offset_get (ull );
@@ -335,12 +334,10 @@ static int prepare_cb(struct lll_prepare_param *p)
335334 }
336335#endif /* CONFIG_BT_CTLR_XTAL_ADVANCED */
337336
338- if (IS_ENABLED (CONFIG_BT_CTLR_ADV_PERIODIC ) &&
339- IS_ENABLED (CONFIG_BT_TICKER_EXT_EXPIRE_INFO ) &&
340- sec_pdu -> adv_ext_ind .ext_hdr_len &&
341- sec_pdu -> adv_ext_ind .ext_hdr .sync_info ) {
342- ull_adv_sync_lll_syncinfo_fill (sec_pdu , lll );
343- }
337+ #if defined(CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK )
338+ /* Populate chan idx for AUX_CHAIN_IND PDU */
339+ chain_pdu_aux_ptr_chan_idx_set (lll );
340+ #endif /* CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK */
344341
345342 ret = lll_prepare_done (lll );
346343 LL_ASSERT (!ret );
@@ -350,6 +347,57 @@ static int prepare_cb(struct lll_prepare_param *p)
350347 return 0 ;
351348}
352349
350+ #if !defined(CONFIG_BT_TICKER_EXT_EXPIRE_INFO ) || \
351+ defined(CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK )
352+ static int aux_ptr_get (struct pdu_adv * pdu , struct pdu_adv_aux_ptr * * aux_ptr )
353+ {
354+ struct pdu_adv_com_ext_adv * com_hdr ;
355+ struct pdu_adv_ext_hdr * hdr ;
356+ uint8_t * dptr ;
357+
358+ /* Get reference to common extended header */
359+ com_hdr = (void * )& pdu -> adv_ext_ind ;
360+ if (com_hdr -> ext_hdr_len == 0U ) {
361+ * aux_ptr = NULL ;
362+
363+ return - EINVAL ;
364+ }
365+
366+ /* Get reference to extended header flags and header fields */
367+ hdr = (void * )com_hdr -> ext_hdr_adv_data ;
368+ dptr = hdr -> data ;
369+
370+ /* traverse through adv_addr, if present */
371+ if (hdr -> adv_addr ) {
372+ dptr += BDADDR_SIZE ;
373+ }
374+
375+ /* traverse through tgt_addr, if present */
376+ if (hdr -> tgt_addr ) {
377+ dptr += BDADDR_SIZE ;
378+ }
379+
380+ /* No CTEInfo flag in primary and secondary channel PDU */
381+
382+ /* traverse through adi, if present */
383+ if (hdr -> adi ) {
384+ dptr += sizeof (struct pdu_adv_adi );
385+ }
386+
387+ /* check for aux_ptr flag */
388+ if (hdr -> aux_ptr ) {
389+ /* Return reference to aux pointer structure */
390+ * aux_ptr = (void * )dptr ;
391+ } else {
392+ * aux_ptr = NULL ;
393+ }
394+
395+ return 0 ;
396+ }
397+ #endif /* !CONFIG_BT_TICKER_EXT_EXPIRE_INFO ||
398+ * CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK
399+ */
400+
353401#if !defined(CONFIG_BT_TICKER_EXT_EXPIRE_INFO )
354402static void isr_race (void * param )
355403{
@@ -395,9 +443,11 @@ static void isr_done(void *param)
395443#if defined(CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK )
396444static void isr_tx_chain (void * param )
397445{
446+ struct pdu_adv_aux_ptr * aux_ptr ;
398447 struct lll_adv_aux * lll_aux ;
399448 struct lll_adv * lll ;
400449 struct pdu_adv * pdu ;
450+ int err ;
401451
402452 if (IS_ENABLED (CONFIG_BT_CTLR_PROFILE_ISR )) {
403453 lll_prof_latency_capture ();
@@ -406,14 +456,22 @@ static void isr_tx_chain(void *param)
406456 /* Clear radio tx status and events */
407457 lll_isr_tx_status_reset ();
408458
459+ /* Get reference to auxiliary and primary advertising LLL contexts */
409460 lll_aux = param ;
410461 lll = lll_aux -> adv ;
411462
412- /* FIXME: Use implementation defined channel index */
413- lll_chan_set (0 );
463+ /* Get reference to aux pointer structure */
464+ err = aux_ptr_get (lll_aux -> last_pdu , & aux_ptr );
465+ LL_ASSERT (!err && aux_ptr );
414466
467+ /* Use channel idx that was in aux_ptr */
468+ lll_chan_set (aux_ptr -> chan_idx );
469+
470+ /* Get reference to the auxiliary chain PDU */
415471 pdu = lll_adv_pdu_linked_next_get (lll_aux -> last_pdu );
416472 LL_ASSERT (pdu );
473+
474+ /* Set the last used auxiliary PDU for transmission */
417475 lll_aux -> last_pdu = pdu ;
418476
419477 /* setup tIFS switching */
@@ -458,10 +516,56 @@ static void isr_tx_chain(void *param)
458516 HAL_RADIO_GPIO_PA_OFFSET );
459517#endif /* HAL_RADIO_GPIO_HAVE_PA_PIN */
460518
519+ /* Populate chan idx for AUX_CHAIN_IND PDU */
520+ chain_pdu_aux_ptr_chan_idx_set (lll_aux );
521+
461522 if (IS_ENABLED (CONFIG_BT_CTLR_PROFILE_ISR )) {
462523 lll_prof_send ();
463524 }
464525}
526+
527+ static void chain_pdu_aux_ptr_chan_idx_set (struct lll_adv_aux * lll )
528+ {
529+ struct pdu_adv * chain_pdu ;
530+
531+ /* No chain PDU */
532+ if (!lll -> last_pdu ) {
533+ return ;
534+ }
535+
536+ /* Get reference to the auxiliary chain PDU */
537+ chain_pdu = lll_adv_pdu_linked_next_get (lll -> last_pdu );
538+
539+ /* Check if there is further chain PDU */
540+ if (chain_pdu && chain_pdu -> adv_ext_ind .ext_hdr_len &&
541+ chain_pdu -> adv_ext_ind .ext_hdr .aux_ptr ) {
542+ aux_ptr_chan_idx_set (lll , chain_pdu );
543+ }
544+ }
545+
546+ static void aux_ptr_chan_idx_set (struct lll_adv_aux * lll , struct pdu_adv * pdu )
547+ {
548+ struct pdu_adv_aux_ptr * aux_ptr ;
549+ struct ll_adv_aux_set * aux ;
550+ uint8_t chan_idx ;
551+ int err ;
552+
553+ /* Get reference to aux pointer structure */
554+ err = aux_ptr_get (pdu , & aux_ptr );
555+ LL_ASSERT (!err && aux_ptr );
556+
557+ /* Calculate a new channel index */
558+ aux = HDR_LLL2ULL (lll );
559+ chan_idx = lll_chan_sel_2 (lll -> data_chan_counter , aux -> data_chan_id ,
560+ aux -> chm [aux -> chm_first ].data_chan_map ,
561+ aux -> chm [aux -> chm_first ].data_chan_count );
562+
563+ /* Increment counter, for next channel index calculation */
564+ lll -> data_chan_counter ++ ;
565+
566+ /* Set the channel index for the auxiliary chain PDU */
567+ aux_ptr -> chan_idx = chan_idx ;
568+ }
465569#endif /* CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK */
466570
467571static void isr_tx_rx (void * param )
@@ -682,6 +786,7 @@ static inline int isr_rx_pdu(struct lll_adv_aux *lll_aux, uint8_t phy_flags_rx,
682786#if defined(CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK )
683787 } else if (sr_pdu -> adv_ext_ind .ext_hdr_len &&
684788 sr_pdu -> adv_ext_ind .ext_hdr .aux_ptr ) {
789+ /* Set the last used auxiliary PDU for transmission */
685790 lll_aux -> last_pdu = sr_pdu ;
686791
687792 radio_isr_set (isr_tx_chain , lll_aux );
@@ -710,20 +815,6 @@ static inline int isr_rx_pdu(struct lll_adv_aux *lll_aux, uint8_t phy_flags_rx,
710815 lll_prof_cputime_capture ();
711816 }
712817
713- #if defined(CONFIG_BT_CTLR_SCAN_REQ_NOTIFY )
714- if (lll -> scan_req_notify ) {
715- uint32_t err ;
716-
717- /* Generate the scan request event */
718- err = lll_adv_scan_req_report (lll , pdu_rx , rl_idx ,
719- rssi_ready );
720- if (err ) {
721- /* Scan Response will not be transmitted */
722- return err ;
723- }
724- }
725- #endif /* CONFIG_BT_CTLR_SCAN_REQ_NOTIFY */
726-
727818#if defined(HAL_RADIO_GPIO_HAVE_PA_PIN )
728819 if (IS_ENABLED (CONFIG_BT_CTLR_PROFILE_ISR )) {
729820 /* PA/LNA enable is overwriting packet end used in ISR
@@ -739,6 +830,26 @@ static inline int isr_rx_pdu(struct lll_adv_aux *lll_aux, uint8_t phy_flags_rx,
739830 phy_flags_rx ) -
740831 HAL_RADIO_GPIO_PA_OFFSET );
741832#endif /* HAL_RADIO_GPIO_HAVE_PA_PIN */
833+
834+ #if defined(CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK )
835+ /* Populate chan idx for AUX_CHAIN_IND PDU */
836+ chain_pdu_aux_ptr_chan_idx_set (lll_aux );
837+ #endif /* CONFIG_BT_CTLR_ADV_AUX_PDU_BACK2BACK */
838+
839+ #if defined(CONFIG_BT_CTLR_SCAN_REQ_NOTIFY )
840+ if (lll -> scan_req_notify ) {
841+ uint32_t err ;
842+
843+ /* Generate the scan request event */
844+ err = lll_adv_scan_req_report (lll , pdu_rx , rl_idx ,
845+ rssi_ready );
846+ if (err ) {
847+ /* Scan Response will not be transmitted */
848+ return err ;
849+ }
850+ }
851+ #endif /* CONFIG_BT_CTLR_SCAN_REQ_NOTIFY */
852+
742853 return 0 ;
743854
744855#if defined(CONFIG_BT_PERIPHERAL )
0 commit comments