1 /*
2 * Copyright (c) 2021-2023 Nordic Semiconductor ASA
3 *
4 * SPDX-License-Identifier: Apache-2.0
5 */
6 #include <stdbool.h>
7 #include <stddef.h>
8 #include <stdint.h>
9 #include <string.h>
10
11 #include <zephyr/autoconf.h>
12 #include <zephyr/bluetooth/audio/audio.h>
13 #include <zephyr/bluetooth/audio/bap.h>
14 #include <zephyr/bluetooth/audio/bap_lc3_preset.h>
15 #include <zephyr/bluetooth/audio/lc3.h>
16 #include <zephyr/bluetooth/bluetooth.h>
17 #include <zephyr/bluetooth/byteorder.h>
18 #include <zephyr/bluetooth/gap.h>
19 #include <zephyr/bluetooth/iso.h>
20 #include <zephyr/bluetooth/uuid.h>
21 #include <zephyr/kernel.h>
22 #include <zephyr/net/buf.h>
23 #include <zephyr/sys/printk.h>
24 #include <zephyr/sys/util.h>
25 #include <zephyr/toolchain.h>
26
27 #include "bap_common.h"
28 #include "bstests.h"
29 #include "common.h"
30
31 #define SUPPORTED_CHAN_COUNTS BT_AUDIO_CODEC_CAP_CHAN_COUNT_SUPPORT(1, 2)
32 #define SUPPORTED_MIN_OCTETS_PER_FRAME 30
33 #define SUPPORTED_MAX_OCTETS_PER_FRAME 155
34 #define SUPPORTED_MAX_FRAMES_PER_SDU 1
35
36 #if defined(CONFIG_BT_BAP_BROADCAST_SOURCE)
37 /* When BROADCAST_ENQUEUE_COUNT > 1 we can enqueue enough buffers to ensure that
38 * the controller is never idle
39 */
40 #define BROADCAST_ENQUEUE_COUNT 2U
41 #define TOTAL_BUF_NEEDED (BROADCAST_ENQUEUE_COUNT * CONFIG_BT_BAP_BROADCAST_SRC_STREAM_COUNT)
42
43 BUILD_ASSERT(CONFIG_BT_ISO_TX_BUF_COUNT >= TOTAL_BUF_NEEDED,
44 "CONFIG_BT_ISO_TX_BUF_COUNT should be at least "
45 "BROADCAST_ENQUEUE_COUNT * CONFIG_BT_BAP_BROADCAST_SRC_STREAM_COUNT");
46
47 NET_BUF_POOL_FIXED_DEFINE(tx_pool,
48 TOTAL_BUF_NEEDED,
49 BT_ISO_SDU_BUF_SIZE(CONFIG_BT_ISO_TX_MTU),
50 CONFIG_BT_CONN_TX_USER_DATA_SIZE, NULL);
51
52 extern enum bst_result_t bst_result;
53 static struct audio_test_stream broadcast_source_streams[CONFIG_BT_BAP_BROADCAST_SRC_STREAM_COUNT];
54 static struct bt_bap_lc3_preset preset_16_2_1 = BT_BAP_LC3_BROADCAST_PRESET_16_2_1(
55 BT_AUDIO_LOCATION_FRONT_LEFT, BT_AUDIO_CONTEXT_TYPE_UNSPECIFIED);
56 static struct bt_bap_lc3_preset preset_16_1_1 = BT_BAP_LC3_BROADCAST_PRESET_16_1_1(
57 BT_AUDIO_LOCATION_FRONT_LEFT, BT_AUDIO_CONTEXT_TYPE_UNSPECIFIED);
58
59 static uint8_t bis_codec_data[] = {
60 BT_AUDIO_CODEC_DATA(BT_AUDIO_CODEC_CFG_CHAN_ALLOC,
61 BT_BYTES_LIST_LE32(BT_AUDIO_LOCATION_FRONT_CENTER)),
62 };
63
64 static K_SEM_DEFINE(sem_started, 0U, ARRAY_SIZE(broadcast_source_streams));
65 static K_SEM_DEFINE(sem_stopped, 0U, ARRAY_SIZE(broadcast_source_streams));
66
validate_stream_codec_cfg(const struct bt_bap_stream * stream)67 static void validate_stream_codec_cfg(const struct bt_bap_stream *stream)
68 {
69 const struct bt_audio_codec_cfg *codec_cfg = stream->codec_cfg;
70 const struct bt_audio_codec_cfg *exp_codec_cfg = &preset_16_1_1.codec_cfg;
71 enum bt_audio_location chan_allocation;
72 uint8_t frames_blocks_per_sdu;
73 size_t min_sdu_size_required;
74 uint16_t octets_per_frame;
75 uint8_t chan_cnt;
76 int ret;
77 int exp_ret;
78
79 ret = bt_audio_codec_cfg_get_freq(codec_cfg);
80 exp_ret = bt_audio_codec_cfg_get_freq(exp_codec_cfg);
81 if (ret >= 0) {
82 const int freq = bt_audio_codec_cfg_freq_to_freq_hz(ret);
83 const int exp_freq = bt_audio_codec_cfg_freq_to_freq_hz(exp_ret);
84
85 if (freq != exp_freq) {
86 FAIL("Invalid frequency: %d Expected: %d\n", freq, exp_freq);
87
88 return;
89 }
90 } else {
91 FAIL("Could not get frequency: %d\n", ret);
92
93 return;
94 }
95
96 ret = bt_audio_codec_cfg_get_frame_dur(codec_cfg);
97 exp_ret = bt_audio_codec_cfg_get_frame_dur(exp_codec_cfg);
98 if (ret >= 0) {
99 const int frm_dur_us = bt_audio_codec_cfg_frame_dur_to_frame_dur_us(ret);
100 const int exp_frm_dur_us = bt_audio_codec_cfg_frame_dur_to_frame_dur_us(exp_ret);
101
102 if (frm_dur_us != exp_frm_dur_us) {
103 FAIL("Invalid frame duration: %d Exp: %d\n", frm_dur_us, exp_frm_dur_us);
104
105 return;
106 }
107 } else {
108 FAIL("Could not get frame duration: %d\n", ret);
109
110 return;
111 }
112
113 /* The broadcast source sets the channel allocation in the BIS to
114 * BT_AUDIO_LOCATION_FRONT_CENTER
115 */
116 ret = bt_audio_codec_cfg_get_chan_allocation(codec_cfg, &chan_allocation, false);
117 if (ret == 0) {
118 if (chan_allocation != BT_AUDIO_LOCATION_FRONT_CENTER) {
119 FAIL("Unexpected channel allocation: 0x%08X", chan_allocation);
120
121 return;
122 }
123
124 chan_cnt = bt_audio_get_chan_count(chan_allocation);
125 } else {
126 FAIL("Could not get subgroup channel allocation: %d\n", ret);
127
128 return;
129 }
130
131 if (chan_cnt == 0 || (BIT(chan_cnt - 1) & SUPPORTED_CHAN_COUNTS) == 0) {
132 FAIL("Unsupported channel count: %u\n", chan_cnt);
133
134 return;
135 }
136
137 ret = bt_audio_codec_cfg_get_octets_per_frame(codec_cfg);
138 if (ret > 0) {
139 octets_per_frame = (uint16_t)ret;
140 } else {
141 FAIL("Could not get subgroup octets per frame: %d\n", ret);
142
143 return;
144 }
145
146 if (!IN_RANGE(octets_per_frame, SUPPORTED_MIN_OCTETS_PER_FRAME,
147 SUPPORTED_MAX_OCTETS_PER_FRAME)) {
148 FAIL("Unsupported octets per frame: %u\n", octets_per_frame);
149
150 return;
151 }
152
153 ret = bt_audio_codec_cfg_get_frame_blocks_per_sdu(codec_cfg, false);
154 if (ret > 0) {
155 frames_blocks_per_sdu = (uint8_t)ret;
156 } else {
157 printk("Could not get octets per frame: %d\n", ret);
158 /* Frame blocks per SDU is optional and is implicitly 1 */
159 frames_blocks_per_sdu = 1U;
160 }
161
162 /* An SDU can consist of X frame blocks, each with Y frames (one per channel) of size Z in
163 * them. The minimum SDU size required for this is X * Y * Z.
164 */
165 min_sdu_size_required = chan_cnt * octets_per_frame * frames_blocks_per_sdu;
166 if (min_sdu_size_required > stream->qos->sdu) {
167 FAIL("With %zu channels and %u octets per frame and %u frames per block, SDUs "
168 "shall be at minimum %zu, but the stream has been configured for %u\n",
169 chan_cnt, octets_per_frame, frames_blocks_per_sdu, min_sdu_size_required,
170 stream->qos->sdu);
171
172 return;
173 }
174 }
175
started_cb(struct bt_bap_stream * stream)176 static void started_cb(struct bt_bap_stream *stream)
177 {
178 struct bt_bap_ep_info info;
179 int err;
180
181 err = bt_bap_ep_get_info(stream->ep, &info);
182 if (err != 0) {
183 FAIL("Failed to get EP info: %d\n", err);
184 return;
185 }
186
187 if (info.state != BT_BAP_EP_STATE_STREAMING) {
188 FAIL("Unexpected EP state: %d\n", info.state);
189 return;
190 }
191
192 if (info.dir != BT_AUDIO_DIR_SOURCE) {
193 FAIL("Unexpected info.dir: %d\n", info.dir);
194 return;
195 }
196
197 if (!info.can_send) {
198 FAIL("info.can_send is false\n");
199 return;
200 }
201
202 if (info.can_recv) {
203 FAIL("info.can_recv is true\n");
204 return;
205 }
206
207 if (info.paired_ep != NULL) {
208 FAIL("Unexpected info.paired_ep: %p\n", info.paired_ep);
209 return;
210 }
211
212 printk("Stream %p started\n", stream);
213 validate_stream_codec_cfg(stream);
214 k_sem_give(&sem_started);
215 }
216
stopped_cb(struct bt_bap_stream * stream,uint8_t reason)217 static void stopped_cb(struct bt_bap_stream *stream, uint8_t reason)
218 {
219 printk("Stream %p stopped with reason 0x%02X\n", stream, reason);
220 k_sem_give(&sem_stopped);
221 }
222
stream_sent_cb(struct bt_bap_stream * stream)223 static void stream_sent_cb(struct bt_bap_stream *stream)
224 {
225 struct audio_test_stream *test_stream = audio_test_stream_from_bap_stream(stream);
226 struct net_buf *buf;
227 int ret;
228
229 if (!test_stream->tx_active) {
230 return;
231 }
232
233 if ((test_stream->tx_cnt % 100U) == 0U) {
234 printk("Sent with seq_num %u\n", test_stream->seq_num);
235 }
236
237 buf = net_buf_alloc(&tx_pool, K_FOREVER);
238 if (buf == NULL) {
239 printk("Could not allocate buffer when sending on %p\n",
240 stream);
241 return;
242 }
243
244 net_buf_reserve(buf, BT_ISO_CHAN_SEND_RESERVE);
245 net_buf_add_mem(buf, mock_iso_data, test_stream->tx_sdu_size);
246 ret = bt_bap_stream_send(stream, buf, test_stream->seq_num++);
247 if (ret < 0) {
248 /* This will end broadcasting on this stream. */
249 net_buf_unref(buf);
250
251 /* Only fail if tx is active (may fail if we are disabling the stream) */
252 if (test_stream->tx_active) {
253 FAIL("Unable to broadcast data on %p: %d\n", stream, ret);
254 }
255
256 return;
257 }
258
259 test_stream->tx_cnt++;
260 }
261
262 static struct bt_bap_stream_ops stream_ops = {
263 .started = started_cb,
264 .stopped = stopped_cb,
265 .sent = stream_sent_cb,
266 };
267
setup_broadcast_source(struct bt_bap_broadcast_source ** source,bool encryption)268 static int setup_broadcast_source(struct bt_bap_broadcast_source **source, bool encryption)
269 {
270 struct bt_bap_broadcast_source_stream_param
271 stream_params[ARRAY_SIZE(broadcast_source_streams)];
272 struct bt_bap_broadcast_source_subgroup_param
273 subgroup_params[CONFIG_BT_BAP_BROADCAST_SRC_SUBGROUP_COUNT];
274 struct bt_bap_broadcast_source_param create_param;
275 int err;
276
277 (void)memset(broadcast_source_streams, 0,
278 sizeof(broadcast_source_streams));
279
280 for (size_t i = 0; i < ARRAY_SIZE(stream_params); i++) {
281 stream_params[i].stream =
282 bap_stream_from_audio_test_stream(&broadcast_source_streams[i]);
283 bt_bap_stream_cb_register(stream_params[i].stream,
284 &stream_ops);
285 #if CONFIG_BT_AUDIO_CODEC_CFG_MAX_DATA_SIZE > 0
286 stream_params[i].data_len = ARRAY_SIZE(bis_codec_data);
287 stream_params[i].data = bis_codec_data;
288 #endif /* CONFIG_BT_AUDIO_CODEC_CFG_MAX_DATA_SIZE > 0 */
289 }
290
291 for (size_t i = 0U; i < ARRAY_SIZE(subgroup_params); i++) {
292 subgroup_params[i].params_count = ARRAY_SIZE(stream_params);
293 subgroup_params[i].params = &stream_params[i];
294 subgroup_params[i].codec_cfg = &preset_16_1_1.codec_cfg;
295 }
296
297 create_param.params_count = ARRAY_SIZE(subgroup_params);
298 create_param.params = subgroup_params;
299 create_param.qos = &preset_16_2_1.qos;
300 create_param.packing = BT_ISO_PACKING_SEQUENTIAL;
301 create_param.encryption = encryption;
302 if (encryption) {
303 memcpy(create_param.broadcast_code, BROADCAST_CODE, sizeof(BROADCAST_CODE));
304 }
305
306 printk("Creating broadcast source with %zu subgroups and %zu streams\n",
307 ARRAY_SIZE(subgroup_params), ARRAY_SIZE(stream_params));
308 err = bt_bap_broadcast_source_create(&create_param, source);
309 if (err != 0) {
310 printk("Unable to create broadcast source: %d\n", err);
311 return err;
312 }
313
314 for (size_t i = 0U; i < ARRAY_SIZE(broadcast_source_streams); i++) {
315 struct audio_test_stream *test_stream = &broadcast_source_streams[i];
316
317 test_stream->tx_sdu_size = preset_16_1_1.qos.sdu;
318 }
319
320 return 0;
321 }
322
test_broadcast_source_get_id(struct bt_bap_broadcast_source * source,uint32_t * broadcast_id_out)323 static void test_broadcast_source_get_id(struct bt_bap_broadcast_source *source,
324 uint32_t *broadcast_id_out)
325 {
326 int err;
327
328 err = bt_bap_broadcast_source_get_id(source, broadcast_id_out);
329 if (err != 0) {
330 FAIL("Unable to get broadcast ID: %d\n", err);
331 return;
332 }
333 }
334
test_broadcast_source_get_base(struct bt_bap_broadcast_source * source,struct net_buf_simple * base_buf)335 static void test_broadcast_source_get_base(struct bt_bap_broadcast_source *source,
336 struct net_buf_simple *base_buf)
337 {
338 int err;
339
340 err = bt_bap_broadcast_source_get_base(source, base_buf);
341 if (err != 0) {
342 FAIL("Failed to get encoded BASE: %d\n", err);
343 return;
344 }
345 }
346
setup_extended_adv(struct bt_bap_broadcast_source * source,struct bt_le_ext_adv ** adv)347 static int setup_extended_adv(struct bt_bap_broadcast_source *source, struct bt_le_ext_adv **adv)
348 {
349 /* Broadcast Audio Streaming Endpoint advertising data */
350 NET_BUF_SIMPLE_DEFINE(ad_buf,
351 BT_UUID_SIZE_16 + BT_AUDIO_BROADCAST_ID_SIZE);
352 struct bt_le_adv_param adv_param = BT_LE_ADV_PARAM_INIT(
353 BT_LE_ADV_OPT_EXT_ADV, 0x80, 0x80, NULL);
354 NET_BUF_SIMPLE_DEFINE(base_buf, 128);
355 struct bt_data ext_ad;
356 struct bt_data per_ad;
357 uint32_t broadcast_id;
358 int err;
359
360 /* Create a non-connectable advertising set */
361 err = bt_le_ext_adv_create(&adv_param, NULL, adv);
362 if (err != 0) {
363 printk("Unable to create extended advertising set: %d\n", err);
364 return err;
365 }
366
367 /* Set periodic advertising parameters */
368 err = bt_le_per_adv_set_param(*adv, BT_LE_PER_ADV_DEFAULT);
369 if (err) {
370 printk("Failed to set periodic advertising parameters: %d\n",
371 err);
372 return err;
373 }
374
375 test_broadcast_source_get_id(source, &broadcast_id);
376
377 /* Setup extended advertising data */
378 net_buf_simple_add_le16(&ad_buf, BT_UUID_BROADCAST_AUDIO_VAL);
379 net_buf_simple_add_le24(&ad_buf, broadcast_id);
380 ext_ad.type = BT_DATA_SVC_DATA16;
381 ext_ad.data_len = ad_buf.len;
382 ext_ad.data = ad_buf.data;
383 err = bt_le_ext_adv_set_data(*adv, &ext_ad, 1, NULL, 0);
384 if (err != 0) {
385 printk("Failed to set extended advertising data: %d\n", err);
386 return err;
387 }
388
389 /* Setup periodic advertising data */
390 test_broadcast_source_get_base(source, &base_buf);
391
392 per_ad.type = BT_DATA_SVC_DATA16;
393 per_ad.data_len = base_buf.len;
394 per_ad.data = base_buf.data;
395 err = bt_le_per_adv_set_data(*adv, &per_ad, 1);
396 if (err != 0) {
397 printk("Failed to set periodic advertising data: %d\n", err);
398 return err;
399 }
400
401 /* Start extended advertising */
402 err = bt_le_ext_adv_start(*adv, BT_LE_EXT_ADV_START_DEFAULT);
403 if (err) {
404 printk("Failed to start extended advertising: %d\n", err);
405 return err;
406 }
407
408 /* Enable Periodic Advertising */
409 err = bt_le_per_adv_start(*adv);
410 if (err) {
411 printk("Failed to enable periodic advertising: %d\n", err);
412 return err;
413 }
414
415 return 0;
416 }
417
test_broadcast_source_reconfig(struct bt_bap_broadcast_source * source)418 static void test_broadcast_source_reconfig(struct bt_bap_broadcast_source *source)
419 {
420 struct bt_bap_broadcast_source_stream_param
421 stream_params[ARRAY_SIZE(broadcast_source_streams)];
422 struct bt_bap_broadcast_source_subgroup_param
423 subgroup_params[CONFIG_BT_BAP_BROADCAST_SRC_SUBGROUP_COUNT];
424 struct bt_bap_broadcast_source_param reconfig_param;
425 int err;
426
427 for (size_t i = 0; i < ARRAY_SIZE(stream_params); i++) {
428 stream_params[i].stream =
429 bap_stream_from_audio_test_stream(&broadcast_source_streams[i]);
430 stream_params[i].data_len = ARRAY_SIZE(bis_codec_data);
431 stream_params[i].data = bis_codec_data;
432 }
433
434 for (size_t i = 0U; i < ARRAY_SIZE(subgroup_params); i++) {
435 subgroup_params[i].params_count = 1U;
436 subgroup_params[i].params = &stream_params[i];
437 subgroup_params[i].codec_cfg = &preset_16_1_1.codec_cfg;
438 }
439
440 reconfig_param.params_count = ARRAY_SIZE(subgroup_params);
441 reconfig_param.params = subgroup_params;
442 reconfig_param.qos = &preset_16_1_1.qos;
443 reconfig_param.packing = BT_ISO_PACKING_SEQUENTIAL;
444 reconfig_param.encryption = false;
445
446 printk("Reconfiguring broadcast source\n");
447 err = bt_bap_broadcast_source_reconfig(source, &reconfig_param);
448 if (err != 0) {
449 FAIL("Unable to reconfigure broadcast source: %d\n", err);
450 return;
451 }
452
453 for (size_t i = 0U; i < ARRAY_SIZE(broadcast_source_streams); i++) {
454 struct audio_test_stream *test_stream = &broadcast_source_streams[i];
455
456 test_stream->tx_sdu_size = preset_16_1_1.qos.sdu;
457 }
458 }
459
test_broadcast_source_start(struct bt_bap_broadcast_source * source,struct bt_le_ext_adv * adv)460 static void test_broadcast_source_start(struct bt_bap_broadcast_source *source,
461 struct bt_le_ext_adv *adv)
462 {
463 int err;
464
465 printk("Starting broadcast source\n");
466 err = bt_bap_broadcast_source_start(source, adv);
467 if (err != 0) {
468 FAIL("Unable to start broadcast source: %d\n", err);
469 return;
470 }
471
472 /* Wait for all to be started */
473 printk("Waiting for streams to be started\n");
474 for (size_t i = 0U; i < ARRAY_SIZE(broadcast_source_streams); i++) {
475 k_sem_take(&sem_started, K_FOREVER);
476 }
477 }
478
test_broadcast_source_update_metadata(struct bt_bap_broadcast_source * source,struct bt_le_ext_adv * adv)479 static void test_broadcast_source_update_metadata(struct bt_bap_broadcast_source *source,
480 struct bt_le_ext_adv *adv)
481 {
482 uint8_t new_metadata[] = BT_AUDIO_CODEC_CFG_LC3_META(BT_AUDIO_CONTEXT_TYPE_ALERTS);
483 struct bt_data per_ad;
484 int err;
485
486 NET_BUF_SIMPLE_DEFINE(base_buf, 128);
487
488 printk("Updating metadata\n");
489 err = bt_bap_broadcast_source_update_metadata(source, new_metadata,
490 ARRAY_SIZE(new_metadata));
491 if (err != 0) {
492 FAIL("Failed to update metadata broadcast source: %d\n", err);
493 return;
494 }
495
496 /* Get the new BASE */
497 test_broadcast_source_get_base(source, &base_buf);
498
499 /* Update the periodic advertising data with the new BASE */
500 per_ad.type = BT_DATA_SVC_DATA16;
501 per_ad.data_len = base_buf.len;
502 per_ad.data = base_buf.data;
503 err = bt_le_per_adv_set_data(adv, &per_ad, 1);
504 if (err != 0) {
505 FAIL("Failed to set periodic advertising data: %d\n", err);
506 }
507 }
508
test_broadcast_source_stop(struct bt_bap_broadcast_source * source)509 static void test_broadcast_source_stop(struct bt_bap_broadcast_source *source)
510 {
511 int err;
512
513 printk("Stopping broadcast source\n");
514
515 for (size_t i = 0U; i < ARRAY_SIZE(broadcast_source_streams); i++) {
516 broadcast_source_streams[i].tx_active = false;
517 }
518
519 err = bt_bap_broadcast_source_stop(source);
520 if (err != 0) {
521 FAIL("Unable to stop broadcast source: %d\n", err);
522 return;
523 }
524
525 /* Wait for all to be stopped */
526 printk("Waiting for streams to be stopped\n");
527 for (size_t i = 0U; i < ARRAY_SIZE(broadcast_source_streams); i++) {
528 k_sem_take(&sem_stopped, K_FOREVER);
529 }
530 }
531
test_broadcast_source_delete(struct bt_bap_broadcast_source * source)532 static void test_broadcast_source_delete(struct bt_bap_broadcast_source *source)
533 {
534 int err;
535
536 printk("Deleting broadcast source\n");
537
538 err = bt_bap_broadcast_source_delete(source);
539 if (err != 0) {
540 FAIL("Unable to stop broadcast source: %d\n", err);
541 return;
542 }
543 }
544
stop_extended_adv(struct bt_le_ext_adv * adv)545 static int stop_extended_adv(struct bt_le_ext_adv *adv)
546 {
547 int err;
548
549 err = bt_le_per_adv_stop(adv);
550 if (err) {
551 printk("Failed to stop periodic advertising: %d\n", err);
552 return err;
553 }
554
555 err = bt_le_ext_adv_stop(adv);
556 if (err) {
557 printk("Failed to stop extended advertising: %d\n", err);
558 return err;
559 }
560
561 err = bt_le_ext_adv_delete(adv);
562 if (err) {
563 printk("Failed to delete extended advertising: %d\n", err);
564 return err;
565 }
566
567 return 0;
568 }
569
test_main(void)570 static void test_main(void)
571 {
572 struct bt_bap_broadcast_source *source;
573 struct bt_le_ext_adv *adv;
574 int err;
575
576 err = bt_enable(NULL);
577 if (err) {
578 FAIL("Bluetooth init failed (err %d)\n", err);
579 return;
580 }
581
582 printk("Bluetooth initialized\n");
583
584 err = setup_broadcast_source(&source, false);
585 if (err != 0) {
586 FAIL("Unable to setup broadcast source: %d\n", err);
587 return;
588 }
589
590 err = setup_extended_adv(source, &adv);
591 if (err != 0) {
592 FAIL("Failed to setup extended advertising: %d\n", err);
593 return;
594 }
595
596 test_broadcast_source_reconfig(source);
597
598 test_broadcast_source_start(source, adv);
599
600 /* Initialize sending */
601 printk("Sending data\n");
602 for (size_t i = 0U; i < ARRAY_SIZE(broadcast_source_streams); i++) {
603 for (unsigned int j = 0U; j < BROADCAST_ENQUEUE_COUNT; j++) {
604 struct audio_test_stream *test_stream = &broadcast_source_streams[i];
605
606 test_stream->tx_active = true;
607 stream_sent_cb(&test_stream->stream.bap_stream);
608 }
609 }
610
611 /* Wait for other devices to have received what they wanted */
612 backchannel_sync_wait_any();
613
614 /* Update metadata while streaming */
615 test_broadcast_source_update_metadata(source, adv);
616
617 /* Wait for other devices to have received what they wanted */
618 backchannel_sync_wait_any();
619
620 /* Wait for other devices to let us know when we can stop the source */
621 backchannel_sync_wait_any();
622
623 test_broadcast_source_stop(source);
624
625 test_broadcast_source_delete(source);
626 source = NULL;
627
628 err = stop_extended_adv(adv);
629 if (err != 0) {
630 FAIL("Unable to stop extended advertising: %d\n", err);
631 return;
632 }
633 adv = NULL;
634
635 /* Recreate broadcast source to verify that it's possible */
636 printk("Recreating broadcast source\n");
637 err = setup_broadcast_source(&source, false);
638 if (err != 0) {
639 FAIL("Unable to setup broadcast source: %d\n", err);
640 return;
641 }
642
643 printk("Deleting broadcast source\n");
644 test_broadcast_source_delete(source);
645 source = NULL;
646
647 PASS("Broadcast source passed\n");
648 }
649
test_main_encrypted(void)650 static void test_main_encrypted(void)
651 {
652 struct bt_bap_broadcast_source *source;
653 struct bt_le_ext_adv *adv;
654 int err;
655
656 err = bt_enable(NULL);
657 if (err) {
658 FAIL("Bluetooth init failed (err %d)\n", err);
659 return;
660 }
661
662 printk("Bluetooth initialized\n");
663
664 err = setup_broadcast_source(&source, true);
665 if (err != 0) {
666 FAIL("Unable to setup broadcast source: %d\n", err);
667 return;
668 }
669
670 err = setup_extended_adv(source, &adv);
671 if (err != 0) {
672 FAIL("Failed to setup extended advertising: %d\n", err);
673 return;
674 }
675
676 test_broadcast_source_start(source, adv);
677
678 /* Initialize sending */
679 printk("Sending data\n");
680 for (size_t i = 0U; i < ARRAY_SIZE(broadcast_source_streams); i++) {
681 for (unsigned int j = 0U; j < BROADCAST_ENQUEUE_COUNT; j++) {
682 struct audio_test_stream *test_stream = &broadcast_source_streams[i];
683
684 test_stream->tx_active = true;
685 stream_sent_cb(&test_stream->stream.bap_stream);
686 }
687 }
688
689 /* Wait for other devices to have received data */
690 backchannel_sync_wait_any();
691
692 /* Wait for other devices to let us know when we can stop the source */
693 backchannel_sync_wait_any();
694
695 test_broadcast_source_stop(source);
696
697 test_broadcast_source_delete(source);
698 source = NULL;
699
700 err = stop_extended_adv(adv);
701 if (err != 0) {
702 FAIL("Unable to stop extended advertising: %d\n", err);
703 return;
704 }
705 adv = NULL;
706
707 PASS("Broadcast source encrypted passed\n");
708 }
709
710 static const struct bst_test_instance test_broadcast_source[] = {
711 {
712 .test_id = "broadcast_source",
713 .test_pre_init_f = test_init,
714 .test_tick_f = test_tick,
715 .test_main_f = test_main,
716 },
717 {
718 .test_id = "broadcast_source_encrypted",
719 .test_pre_init_f = test_init,
720 .test_tick_f = test_tick,
721 .test_main_f = test_main_encrypted,
722 },
723 BSTEST_END_MARKER,
724 };
725
test_broadcast_source_install(struct bst_test_list * tests)726 struct bst_test_list *test_broadcast_source_install(struct bst_test_list *tests)
727 {
728 return bst_add_tests(tests, test_broadcast_source);
729 }
730
731 #else /* CONFIG_BT_BAP_BROADCAST_SOURCE */
732
test_broadcast_source_install(struct bst_test_list * tests)733 struct bst_test_list *test_broadcast_source_install(struct bst_test_list *tests)
734 {
735 return tests;
736 }
737
738 #endif /* CONFIG_BT_BAP_BROADCAST_SOURCE */
739