1 /******************************************************************************
2 *
3 * Copyright (C) 2009-2012 Broadcom Corporation
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 ******************************************************************************/
18
19 /******************************************************************************
20 **
21 ** Name: btif_media_task.c
22 **
23 ** Description: This is the multimedia module for the BTIF system. It
24 ** contains task implementations AV, HS and HF profiles
25 ** audio & video processing
26 **
27 ******************************************************************************/
28
29 #define LOG_TAG "bt_btif_media"
30
31 #include <assert.h>
32 #include <fcntl.h>
33 #include <limits.h>
34 #include <pthread.h>
35 #include <stdint.h>
36 #include <stdio.h>
37 #include <string.h>
38 #include <sys/stat.h>
39 #include <sys/time.h>
40 #include <sys/types.h>
41 #include <unistd.h>
42
43 #include <hardware/bluetooth.h>
44
45 #include "a2d_api.h"
46 #include "a2d_int.h"
47 #include "a2d_sbc.h"
48 #include "audio_a2dp_hw.h"
49 #include "bt_target.h"
50 #include "bta_api.h"
51 #include "bta_av_api.h"
52 #include "bta_av_ci.h"
53 #include "bta_av_sbc.h"
54 #include "bta_sys.h"
55 #include "bta_sys_int.h"
56 #include "btif_av.h"
57 #include "btif_av_co.h"
58 #include "btif_media.h"
59 #include "btif_sm.h"
60 #include "btif_util.h"
61 #include "btu.h"
62 #include "bt_common.h"
63 #include "device/include/controller.h"
64 #include "l2c_api.h"
65 #include "osi/include/alarm.h"
66 #include "osi/include/fixed_queue.h"
67 #include "osi/include/log.h"
68 #include "osi/include/metrics.h"
69 #include "osi/include/mutex.h"
70 #include "osi/include/thread.h"
71
72 #if (BTA_AV_INCLUDED == TRUE)
73 #include "sbc_encoder.h"
74 #endif
75
76 #if (BTA_AV_SINK_INCLUDED == TRUE)
77 #include "oi_codec_sbc.h"
78 #include "oi_status.h"
79 #endif
80
81 #ifdef USE_AUDIO_TRACK
82 #include "btif_avrcp_audio_track.h"
83 #endif
84
85 #if (BTA_AV_SINK_INCLUDED == TRUE)
86 OI_CODEC_SBC_DECODER_CONTEXT context;
87 OI_UINT32 contextData[CODEC_DATA_WORDS(2, SBC_CODEC_FAST_FILTER_BUFFERS)];
88 OI_INT16 pcmData[15*SBC_MAX_SAMPLES_PER_FRAME*SBC_MAX_CHANNELS];
89 #endif
90
91 /*****************************************************************************
92 ** Constants
93 *****************************************************************************/
94 #ifndef AUDIO_CHANNEL_OUT_MONO
95 #define AUDIO_CHANNEL_OUT_MONO 0x01
96 #endif
97
98 #ifndef AUDIO_CHANNEL_OUT_STEREO
99 #define AUDIO_CHANNEL_OUT_STEREO 0x03
100 #endif
101
102 /* BTIF media cmd event definition : BTIF_MEDIA_TASK_CMD */
103 enum
104 {
105 BTIF_MEDIA_START_AA_TX = 1,
106 BTIF_MEDIA_STOP_AA_TX,
107 BTIF_MEDIA_AA_RX_RDY,
108 BTIF_MEDIA_UIPC_RX_RDY,
109 BTIF_MEDIA_SBC_ENC_INIT,
110 BTIF_MEDIA_SBC_ENC_UPDATE,
111 BTIF_MEDIA_SBC_DEC_INIT,
112 BTIF_MEDIA_VIDEO_DEC_INIT,
113 BTIF_MEDIA_FLUSH_AA_TX,
114 BTIF_MEDIA_FLUSH_AA_RX,
115 BTIF_MEDIA_AUDIO_FEEDING_INIT,
116 BTIF_MEDIA_AUDIO_RECEIVING_INIT,
117 BTIF_MEDIA_AUDIO_SINK_CFG_UPDATE,
118 BTIF_MEDIA_AUDIO_SINK_CLEAR_TRACK,
119 BTIF_MEDIA_AUDIO_SINK_SET_FOCUS_STATE
120 };
121
122 enum {
123 MEDIA_TASK_STATE_OFF = 0,
124 MEDIA_TASK_STATE_ON = 1,
125 MEDIA_TASK_STATE_SHUTTING_DOWN = 2
126 };
127
128 /* Macro to multiply the media task tick */
129 #ifndef BTIF_MEDIA_NUM_TICK
130 #define BTIF_MEDIA_NUM_TICK 1
131 #endif
132
133 /* Media task tick in milliseconds, must be set to multiple of
134 (1000/TICKS_PER_SEC) (10) */
135
136 #define BTIF_MEDIA_TIME_TICK (20 * BTIF_MEDIA_NUM_TICK)
137 #define A2DP_DATA_READ_POLL_MS (BTIF_MEDIA_TIME_TICK / 2)
138 #define BTIF_SINK_MEDIA_TIME_TICK_MS (20 * BTIF_MEDIA_NUM_TICK)
139
140
141 /* buffer pool */
142 #define BTIF_MEDIA_AA_BUF_SIZE BT_DEFAULT_BUFFER_SIZE
143
144 /* offset */
145 #if (BTA_AV_CO_CP_SCMS_T == TRUE)
146 #define BTIF_MEDIA_AA_SBC_OFFSET (AVDT_MEDIA_OFFSET + BTA_AV_SBC_HDR_SIZE + 1)
147 #else
148 #define BTIF_MEDIA_AA_SBC_OFFSET (AVDT_MEDIA_OFFSET + BTA_AV_SBC_HDR_SIZE)
149 #endif
150
151 /* Define the bitrate step when trying to match bitpool value */
152 #ifndef BTIF_MEDIA_BITRATE_STEP
153 #define BTIF_MEDIA_BITRATE_STEP 5
154 #endif
155
156 #ifndef BTIF_A2DP_DEFAULT_BITRATE
157 /* High quality quality setting @ 44.1 khz */
158 #define BTIF_A2DP_DEFAULT_BITRATE 328
159 #endif
160
161 #ifndef BTIF_A2DP_NON_EDR_MAX_RATE
162 #define BTIF_A2DP_NON_EDR_MAX_RATE 229
163 #endif
164
165 #if (BTA_AV_CO_CP_SCMS_T == TRUE)
166 /* A2DP header will contain a CP header of size 1 */
167 #define A2DP_HDR_SIZE 2
168 #else
169 #define A2DP_HDR_SIZE 1
170 #endif
171 #define MAX_SBC_HQ_FRAME_SIZE_44_1 119
172 #define MAX_SBC_HQ_FRAME_SIZE_48 115
173
174 /* 2DH5 payload size of 679 bytes - (4 bytes L2CAP Header + 12 bytes AVDTP Header) */
175 #define MAX_2MBPS_AVDTP_MTU 663
176 #define USEC_PER_SEC 1000000L
177 #define TPUT_STATS_INTERVAL_US (3000*1000)
178
179 /**
180 * CONGESTION COMPENSATION CTRL ::
181 *
182 * Thus setting controls how many buffers we will hold in media task
183 * during temp link congestion. Together with the stack buffer queues
184 * it controls much temporary a2dp link congestion we can
185 * compensate for. It however also depends on the default run level of sinks
186 * jitterbuffers. Depending on type of sink this would vary.
187 * Ideally the (SRC) max tx buffer capacity should equal the sinks
188 * jitterbuffer runlevel including any intermediate buffers on the way
189 * towards the sinks codec.
190 */
191 #ifndef MAX_PCM_FRAME_NUM_PER_TICK
192 #define MAX_PCM_FRAME_NUM_PER_TICK 14
193 #endif
194 #define MAX_PCM_ITER_NUM_PER_TICK 3
195
196 /**
197 * The typical runlevel of the tx queue size is ~1 buffer
198 * but due to link flow control or thread preemption in lower
199 * layers we might need to temporarily buffer up data.
200 */
201 #define MAX_OUTPUT_A2DP_FRAME_QUEUE_SZ (MAX_PCM_FRAME_NUM_PER_TICK * 2)
202
203 /* In case of A2DP SINK, we will delay start by 5 AVDTP Packets*/
204 #define MAX_A2DP_DELAYED_START_FRAME_COUNT 5
205 #define PACKET_PLAYED_PER_TICK_48 8
206 #define PACKET_PLAYED_PER_TICK_44 7
207 #define PACKET_PLAYED_PER_TICK_32 5
208 #define PACKET_PLAYED_PER_TICK_16 3
209
210 /* Readability constants */
211 #define SBC_FRAME_HEADER_SIZE_BYTES 4 // A2DP Spec v1.3, 12.4, Table 12.12
212 #define SBC_SCALE_FACTOR_BITS 4 // A2DP Spec v1.3, 12.4, Table 12.13
213
214 typedef struct {
215 // Counter for total updates
216 size_t total_updates;
217
218 // Last update timestamp (in us)
219 uint64_t last_update_us;
220
221 // Counter for overdue scheduling
222 size_t overdue_scheduling_count;
223
224 // Accumulated overdue scheduling deviations (in us)
225 uint64_t total_overdue_scheduling_delta_us;
226
227 // Max. overdue scheduling delta time (in us)
228 uint64_t max_overdue_scheduling_delta_us;
229
230 // Counter for premature scheduling
231 size_t premature_scheduling_count;
232
233 // Accumulated premature scheduling deviations (in us)
234 uint64_t total_premature_scheduling_delta_us;
235
236 // Max. premature scheduling delta time (in us)
237 uint64_t max_premature_scheduling_delta_us;
238
239 // Counter for exact scheduling
240 size_t exact_scheduling_count;
241
242 // Accumulated and counted scheduling time (in us)
243 uint64_t total_scheduling_time_us;
244 } scheduling_stats_t;
245
246 typedef struct {
247 uint64_t session_start_us;
248
249 scheduling_stats_t tx_queue_enqueue_stats;
250 scheduling_stats_t tx_queue_dequeue_stats;
251
252 size_t tx_queue_total_frames;
253 size_t tx_queue_max_frames_per_packet;
254
255 uint64_t tx_queue_total_queueing_time_us;
256 uint64_t tx_queue_max_queueing_time_us;
257
258 size_t tx_queue_total_readbuf_calls;
259 uint64_t tx_queue_last_readbuf_us;
260
261 size_t tx_queue_total_flushed_messages;
262 uint64_t tx_queue_last_flushed_us;
263
264 size_t tx_queue_total_dropped_messages;
265 size_t tx_queue_dropouts;
266 uint64_t tx_queue_last_dropouts_us;
267
268 size_t media_read_total_underflow_bytes;
269 size_t media_read_total_underflow_count;
270 uint64_t media_read_last_underflow_us;
271
272 size_t media_read_total_underrun_bytes;
273 size_t media_read_total_underrun_count;
274 uint64_t media_read_last_underrun_us;
275
276 size_t media_read_total_expected_frames;
277 size_t media_read_max_expected_frames;
278 size_t media_read_expected_count;
279
280 size_t media_read_total_limited_frames;
281 size_t media_read_max_limited_frames;
282 size_t media_read_limited_count;
283 } btif_media_stats_t;
284
285 typedef struct
286 {
287 UINT16 num_frames_to_be_processed;
288 UINT16 len;
289 UINT16 offset;
290 UINT16 layer_specific;
291 } tBT_SBC_HDR;
292
293 typedef struct
294 {
295 UINT32 aa_frame_counter;
296 INT32 aa_feed_counter;
297 INT32 aa_feed_residue;
298 UINT32 counter;
299 UINT32 bytes_per_tick; /* pcm bytes read each media task tick */
300 } tBTIF_AV_MEDIA_FEEDINGS_PCM_STATE;
301
302 typedef union
303 {
304 tBTIF_AV_MEDIA_FEEDINGS_PCM_STATE pcm;
305 } tBTIF_AV_MEDIA_FEEDINGS_STATE;
306
307 typedef struct
308 {
309 #if (BTA_AV_INCLUDED == TRUE)
310 fixed_queue_t *TxAaQ;
311 fixed_queue_t *RxSbcQ;
312 UINT16 TxAaMtuSize;
313 UINT32 timestamp;
314 UINT8 TxTranscoding;
315 tBTIF_AV_FEEDING_MODE feeding_mode;
316 tBTIF_AV_MEDIA_FEEDINGS media_feeding;
317 tBTIF_AV_MEDIA_FEEDINGS_STATE media_feeding_state;
318 SBC_ENC_PARAMS encoder;
319 UINT8 busy_level;
320 void* av_sm_hdl;
321 UINT8 a2dp_cmd_pending; /* we can have max one command pending */
322 BOOLEAN tx_flush; /* discards any outgoing data when true */
323 BOOLEAN rx_flush; /* discards any incoming data when true */
324 UINT8 peer_sep;
325 BOOLEAN data_channel_open;
326 UINT8 frames_to_process;
327 UINT8 tx_sbc_frames;
328
329 UINT32 sample_rate;
330 UINT8 channel_count;
331 #ifdef USE_AUDIO_TRACK
332 btif_media_audio_focus_state rx_audio_focus_state;
333 void *audio_track;
334 #endif
335 alarm_t *media_alarm;
336 alarm_t *decode_alarm;
337 btif_media_stats_t stats;
338 #endif
339 } tBTIF_MEDIA_CB;
340
341 typedef struct {
342 long long rx;
343 long long rx_tot;
344 long long tx;
345 long long tx_tot;
346 long long ts_prev_us;
347 } t_stat;
348
349 static UINT64 last_frame_us = 0;
350
351 static void btif_a2dp_data_cb(tUIPC_CH_ID ch_id, tUIPC_EVENT event);
352 static void btif_a2dp_ctrl_cb(tUIPC_CH_ID ch_id, tUIPC_EVENT event);
353 static void btif_a2dp_encoder_update(void);
354 #if (BTA_AV_SINK_INCLUDED == TRUE)
355 extern OI_STATUS OI_CODEC_SBC_DecodeFrame(OI_CODEC_SBC_DECODER_CONTEXT *context,
356 const OI_BYTE **frameData,
357 unsigned long *frameBytes,
358 OI_INT16 *pcmData,
359 unsigned long *pcmBytes);
360 extern OI_STATUS OI_CODEC_SBC_DecoderReset(OI_CODEC_SBC_DECODER_CONTEXT *context,
361 unsigned long *decoderData,
362 unsigned long decoderDataBytes,
363 OI_UINT8 maxChannels,
364 OI_UINT8 pcmStride,
365 OI_BOOL enhanced);
366 #endif
367 static void btif_media_flush_q(fixed_queue_t *p_q);
368 static void btif_media_task_aa_handle_stop_decoding(void );
369 static void btif_media_task_aa_rx_flush(void);
370
371 static UINT8 calculate_max_frames_per_packet();
372 static const char *dump_media_event(UINT16 event);
373 static void btif_media_thread_init(void *context);
374 static void btif_media_thread_cleanup(void *context);
375 static void btif_media_thread_handle_cmd(fixed_queue_t *queue, void *context);
376
377 /* Handle incoming media packets A2DP SINK streaming*/
378 #if (BTA_AV_SINK_INCLUDED == TRUE)
379 static void btif_media_task_handle_inc_media(tBT_SBC_HDR*p_msg);
380 #endif
381
382 #if (BTA_AV_INCLUDED == TRUE)
383 static void btif_media_send_aa_frame(uint64_t timestamp_us);
384 static void btif_media_task_feeding_state_reset(void);
385 static void btif_media_task_aa_start_tx(void);
386 static void btif_media_task_aa_stop_tx(void);
387 static void btif_media_task_enc_init(BT_HDR *p_msg);
388 static void btif_media_task_enc_update(BT_HDR *p_msg);
389 static void btif_media_task_audio_feeding_init(BT_HDR *p_msg);
390 static void btif_media_task_aa_tx_flush(BT_HDR *p_msg);
391 static void btif_media_aa_prep_2_send(UINT8 nb_frame, uint64_t timestamp_us);
392 #if (BTA_AV_SINK_INCLUDED == TRUE)
393 static void btif_media_task_aa_handle_decoder_reset(BT_HDR *p_msg);
394 static void btif_media_task_aa_handle_clear_track(void);
395 #endif
396 static void btif_media_task_aa_handle_start_decoding(void);
397 #endif
398 BOOLEAN btif_media_task_clear_track(void);
399
400 static void btif_media_task_aa_handle_timer(UNUSED_ATTR void *context);
401 static void btif_media_task_avk_handle_timer(UNUSED_ATTR void *context);
402 extern BOOLEAN btif_hf_is_call_idle();
403
404 static tBTIF_MEDIA_CB btif_media_cb;
405 static int media_task_running = MEDIA_TASK_STATE_OFF;
406
407 static fixed_queue_t *btif_media_cmd_msg_queue;
408 static thread_t *worker_thread;
409
410 /*****************************************************************************
411 ** Misc helper functions
412 *****************************************************************************/
413
update_scheduling_stats(scheduling_stats_t * stats,uint64_t now_us,uint64_t expected_delta)414 static void update_scheduling_stats(scheduling_stats_t *stats,
415 uint64_t now_us, uint64_t expected_delta)
416 {
417 uint64_t last_us = stats->last_update_us;
418
419 stats->total_updates++;
420 stats->last_update_us = now_us;
421
422 if (last_us == 0)
423 return; // First update: expected delta doesn't apply
424
425 uint64_t deadline_us = last_us + expected_delta;
426 if (deadline_us < now_us) {
427 // Overdue scheduling
428 uint64_t delta_us = now_us - deadline_us;
429 // Ignore extreme outliers
430 if (delta_us < 10 * expected_delta) {
431 if (stats->max_overdue_scheduling_delta_us < delta_us)
432 stats->max_overdue_scheduling_delta_us = delta_us;
433 stats->total_overdue_scheduling_delta_us += delta_us;
434 stats->overdue_scheduling_count++;
435 stats->total_scheduling_time_us += now_us - last_us;
436 }
437 } else if (deadline_us > now_us) {
438 // Premature scheduling
439 uint64_t delta_us = deadline_us - now_us;
440 // Ignore extreme outliers
441 if (delta_us < 10 * expected_delta) {
442 if (stats->max_premature_scheduling_delta_us < delta_us)
443 stats->max_premature_scheduling_delta_us = delta_us;
444 stats->total_premature_scheduling_delta_us += delta_us;
445 stats->premature_scheduling_count++;
446 stats->total_scheduling_time_us += now_us - last_us;
447 }
448 } else {
449 // On-time scheduling
450 stats->exact_scheduling_count++;
451 stats->total_scheduling_time_us += now_us - last_us;
452 }
453 }
454
time_now_us()455 static UINT64 time_now_us()
456 {
457 struct timespec ts_now;
458 clock_gettime(CLOCK_BOOTTIME, &ts_now);
459 return ((UINT64)ts_now.tv_sec * USEC_PER_SEC) + ((UINT64)ts_now.tv_nsec / 1000);
460 }
461
log_tstamps_us(char * comment,uint64_t now_us)462 static void log_tstamps_us(char *comment, uint64_t now_us)
463 {
464 static uint64_t prev_us = 0;
465 APPL_TRACE_DEBUG("[%s] ts %08llu, diff : %08llu, queue sz %d", comment, now_us, now_us - prev_us,
466 fixed_queue_length(btif_media_cb.TxAaQ));
467 prev_us = now_us;
468 }
469
dump_media_event(UINT16 event)470 UNUSED_ATTR static const char *dump_media_event(UINT16 event)
471 {
472 switch (event)
473 {
474 CASE_RETURN_STR(BTIF_MEDIA_START_AA_TX)
475 CASE_RETURN_STR(BTIF_MEDIA_STOP_AA_TX)
476 CASE_RETURN_STR(BTIF_MEDIA_AA_RX_RDY)
477 CASE_RETURN_STR(BTIF_MEDIA_UIPC_RX_RDY)
478 CASE_RETURN_STR(BTIF_MEDIA_SBC_ENC_INIT)
479 CASE_RETURN_STR(BTIF_MEDIA_SBC_ENC_UPDATE)
480 CASE_RETURN_STR(BTIF_MEDIA_SBC_DEC_INIT)
481 CASE_RETURN_STR(BTIF_MEDIA_VIDEO_DEC_INIT)
482 CASE_RETURN_STR(BTIF_MEDIA_FLUSH_AA_TX)
483 CASE_RETURN_STR(BTIF_MEDIA_FLUSH_AA_RX)
484 CASE_RETURN_STR(BTIF_MEDIA_AUDIO_FEEDING_INIT)
485 CASE_RETURN_STR(BTIF_MEDIA_AUDIO_RECEIVING_INIT)
486 CASE_RETURN_STR(BTIF_MEDIA_AUDIO_SINK_CFG_UPDATE)
487 CASE_RETURN_STR(BTIF_MEDIA_AUDIO_SINK_CLEAR_TRACK)
488 CASE_RETURN_STR(BTIF_MEDIA_AUDIO_SINK_SET_FOCUS_STATE)
489
490 default:
491 return "UNKNOWN MEDIA EVENT";
492 }
493 }
494
495 /*****************************************************************************
496 ** A2DP CTRL PATH
497 *****************************************************************************/
498
dump_a2dp_ctrl_event(UINT8 event)499 static const char* dump_a2dp_ctrl_event(UINT8 event)
500 {
501 switch (event)
502 {
503 CASE_RETURN_STR(A2DP_CTRL_CMD_NONE)
504 CASE_RETURN_STR(A2DP_CTRL_CMD_CHECK_READY)
505 CASE_RETURN_STR(A2DP_CTRL_CMD_START)
506 CASE_RETURN_STR(A2DP_CTRL_CMD_STOP)
507 CASE_RETURN_STR(A2DP_CTRL_CMD_SUSPEND)
508 CASE_RETURN_STR(A2DP_CTRL_CMD_OFFLOAD_START)
509
510 default:
511 return "UNKNOWN MSG ID";
512 }
513 }
514
btif_audiopath_detached(void)515 static void btif_audiopath_detached(void)
516 {
517 APPL_TRACE_EVENT("## AUDIO PATH DETACHED ##");
518
519 /* send stop request only if we are actively streaming and haven't received
520 a stop request. Potentially audioflinger detached abnormally */
521 if (alarm_is_scheduled(btif_media_cb.media_alarm)) {
522 /* post stop event and wait for audio path to stop */
523 btif_dispatch_sm_event(BTIF_AV_STOP_STREAM_REQ_EVT, NULL, 0);
524 }
525 }
526
a2dp_cmd_acknowledge(int status)527 static void a2dp_cmd_acknowledge(int status)
528 {
529 UINT8 ack = status;
530
531 APPL_TRACE_EVENT("## a2dp ack : %s, status %d ##",
532 dump_a2dp_ctrl_event(btif_media_cb.a2dp_cmd_pending), status);
533
534 /* sanity check */
535 if (btif_media_cb.a2dp_cmd_pending == A2DP_CTRL_CMD_NONE)
536 {
537 APPL_TRACE_ERROR("warning : no command pending, ignore ack");
538 return;
539 }
540
541 /* clear pending */
542 btif_media_cb.a2dp_cmd_pending = A2DP_CTRL_CMD_NONE;
543
544 /* acknowledge start request */
545 UIPC_Send(UIPC_CH_ID_AV_CTRL, 0, &ack, 1);
546 }
547
548
btif_recv_ctrl_data(void)549 static void btif_recv_ctrl_data(void)
550 {
551 UINT8 cmd = 0;
552 int n;
553 n = UIPC_Read(UIPC_CH_ID_AV_CTRL, NULL, &cmd, 1);
554
555 /* detach on ctrl channel means audioflinger process was terminated */
556 if (n == 0)
557 {
558 APPL_TRACE_EVENT("CTRL CH DETACHED");
559 UIPC_Close(UIPC_CH_ID_AV_CTRL);
560 /* we can operate only on datachannel, if af client wants to
561 do send additional commands the ctrl channel would be reestablished */
562 //btif_audiopath_detached();
563 return;
564 }
565
566 APPL_TRACE_DEBUG("a2dp-ctrl-cmd : %s", dump_a2dp_ctrl_event(cmd));
567
568 btif_media_cb.a2dp_cmd_pending = cmd;
569
570 switch (cmd)
571 {
572 case A2DP_CTRL_CMD_CHECK_READY:
573
574 if (media_task_running == MEDIA_TASK_STATE_SHUTTING_DOWN)
575 {
576 APPL_TRACE_WARNING("%s: A2DP command %s while media task shutting down",
577 __func__, dump_a2dp_ctrl_event(cmd));
578 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_FAILURE);
579 return;
580 }
581
582 /* check whether av is ready to setup a2dp datapath */
583 if ((btif_av_stream_ready() == TRUE) || (btif_av_stream_started_ready() == TRUE))
584 {
585 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_SUCCESS);
586 }
587 else
588 {
589 APPL_TRACE_WARNING("%s: A2DP command %s while AV stream is not ready",
590 __func__, dump_a2dp_ctrl_event(cmd));
591 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_FAILURE);
592 }
593 break;
594
595 case A2DP_CTRL_CMD_START:
596 /* Don't sent START request to stack while we are in call.
597 Some headsets like the Sony MW600, don't allow AVDTP START
598 in call and respond BAD_STATE. */
599 if (!btif_hf_is_call_idle())
600 {
601 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_INCALL_FAILURE);
602 break;
603 }
604
605 if (alarm_is_scheduled(btif_media_cb.media_alarm))
606 {
607 APPL_TRACE_WARNING("%s: A2DP command %s when media alarm already scheduled",
608 __func__, dump_a2dp_ctrl_event(cmd));
609 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_FAILURE);
610 break;
611 }
612
613 if (btif_av_stream_ready() == TRUE)
614 {
615 /* setup audio data channel listener */
616 UIPC_Open(UIPC_CH_ID_AV_AUDIO, btif_a2dp_data_cb);
617
618 /* post start event and wait for audio path to open */
619 btif_dispatch_sm_event(BTIF_AV_START_STREAM_REQ_EVT, NULL, 0);
620
621 #if (BTA_AV_SINK_INCLUDED == TRUE)
622 if (btif_media_cb.peer_sep == AVDT_TSEP_SRC)
623 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_SUCCESS);
624 #endif
625 }
626 else if (btif_av_stream_started_ready())
627 {
628 /* already started, setup audio data channel listener
629 and ack back immediately */
630 UIPC_Open(UIPC_CH_ID_AV_AUDIO, btif_a2dp_data_cb);
631
632 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_SUCCESS);
633 }
634 else
635 {
636 APPL_TRACE_WARNING("%s: A2DP command %s while AV stream is not ready",
637 __func__, dump_a2dp_ctrl_event(cmd));
638 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_FAILURE);
639 break;
640 }
641 break;
642
643 case A2DP_CTRL_CMD_STOP:
644 if (btif_media_cb.peer_sep == AVDT_TSEP_SNK &&
645 (!alarm_is_scheduled(btif_media_cb.media_alarm)))
646 {
647 /* we are already stopped, just ack back */
648 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_SUCCESS);
649 break;
650 }
651
652 btif_dispatch_sm_event(BTIF_AV_STOP_STREAM_REQ_EVT, NULL, 0);
653 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_SUCCESS);
654 break;
655
656 case A2DP_CTRL_CMD_SUSPEND:
657 /* local suspend */
658 if (btif_av_stream_started_ready())
659 {
660 btif_dispatch_sm_event(BTIF_AV_SUSPEND_STREAM_REQ_EVT, NULL, 0);
661 }
662 else
663 {
664 /* if we are not in started state, just ack back ok and let
665 audioflinger close the channel. This can happen if we are
666 remotely suspended, clear REMOTE SUSPEND Flag */
667 btif_av_clear_remote_suspend_flag();
668 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_SUCCESS);
669 }
670 break;
671
672 case A2DP_CTRL_GET_AUDIO_CONFIG:
673 {
674 uint32_t sample_rate = btif_media_cb.sample_rate;
675 uint8_t channel_count = btif_media_cb.channel_count;
676
677 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_SUCCESS);
678 UIPC_Send(UIPC_CH_ID_AV_CTRL, 0, (UINT8 *)&sample_rate, 4);
679 UIPC_Send(UIPC_CH_ID_AV_CTRL, 0, &channel_count, 1);
680 break;
681 }
682
683 case A2DP_CTRL_CMD_OFFLOAD_START:
684 btif_dispatch_sm_event(BTIF_AV_OFFLOAD_START_REQ_EVT, NULL, 0);
685 break;
686
687 default:
688 APPL_TRACE_ERROR("UNSUPPORTED CMD (%d)", cmd);
689 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_FAILURE);
690 break;
691 }
692 APPL_TRACE_DEBUG("a2dp-ctrl-cmd : %s DONE", dump_a2dp_ctrl_event(cmd));
693 }
694
btif_a2dp_ctrl_cb(tUIPC_CH_ID ch_id,tUIPC_EVENT event)695 static void btif_a2dp_ctrl_cb(tUIPC_CH_ID ch_id, tUIPC_EVENT event)
696 {
697 UNUSED(ch_id);
698
699 APPL_TRACE_DEBUG("A2DP-CTRL-CHANNEL EVENT %s", dump_uipc_event(event));
700
701 switch (event)
702 {
703 case UIPC_OPEN_EVT:
704 /* fetch av statemachine handle */
705 btif_media_cb.av_sm_hdl = btif_av_get_sm_handle();
706 break;
707
708 case UIPC_CLOSE_EVT:
709 /* restart ctrl server unless we are shutting down */
710 if (media_task_running == MEDIA_TASK_STATE_ON)
711 UIPC_Open(UIPC_CH_ID_AV_CTRL , btif_a2dp_ctrl_cb);
712 break;
713
714 case UIPC_RX_DATA_READY_EVT:
715 btif_recv_ctrl_data();
716 break;
717
718 default :
719 APPL_TRACE_ERROR("### A2DP-CTRL-CHANNEL EVENT %d NOT HANDLED ###", event);
720 break;
721 }
722 }
723
btif_a2dp_data_cb(tUIPC_CH_ID ch_id,tUIPC_EVENT event)724 static void btif_a2dp_data_cb(tUIPC_CH_ID ch_id, tUIPC_EVENT event)
725 {
726 UNUSED(ch_id);
727
728 APPL_TRACE_DEBUG("BTIF MEDIA (A2DP-DATA) EVENT %s", dump_uipc_event(event));
729
730 switch (event)
731 {
732 case UIPC_OPEN_EVT:
733
734 /* read directly from media task from here on (keep callback for
735 connection events */
736 UIPC_Ioctl(UIPC_CH_ID_AV_AUDIO, UIPC_REG_REMOVE_ACTIVE_READSET, NULL);
737 UIPC_Ioctl(UIPC_CH_ID_AV_AUDIO, UIPC_SET_READ_POLL_TMO,
738 (void *)A2DP_DATA_READ_POLL_MS);
739
740 if (btif_media_cb.peer_sep == AVDT_TSEP_SNK) {
741 /* Start the media task to encode SBC */
742 btif_media_task_start_aa_req();
743
744 /* make sure we update any changed sbc encoder params */
745 btif_a2dp_encoder_update();
746 }
747 btif_media_cb.data_channel_open = TRUE;
748
749 /* ack back when media task is fully started */
750 break;
751
752 case UIPC_CLOSE_EVT:
753 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_SUCCESS);
754 btif_audiopath_detached();
755 btif_media_cb.data_channel_open = FALSE;
756 break;
757
758 default :
759 APPL_TRACE_ERROR("### A2DP-DATA EVENT %d NOT HANDLED ###", event);
760 break;
761 }
762 }
763
764
765 /*****************************************************************************
766 ** BTIF ADAPTATION
767 *****************************************************************************/
768
btif_media_task_get_sbc_rate(void)769 static UINT16 btif_media_task_get_sbc_rate(void)
770 {
771 UINT16 rate = BTIF_A2DP_DEFAULT_BITRATE;
772
773 /* restrict bitrate if a2dp link is non-edr */
774 if (!btif_av_is_peer_edr())
775 {
776 rate = BTIF_A2DP_NON_EDR_MAX_RATE;
777 APPL_TRACE_DEBUG("non-edr a2dp sink detected, restrict rate to %d", rate);
778 }
779
780 return rate;
781 }
782
btif_a2dp_encoder_init(void)783 static void btif_a2dp_encoder_init(void)
784 {
785 UINT16 minmtu;
786 tBTIF_MEDIA_INIT_AUDIO msg;
787 tA2D_SBC_CIE sbc_config;
788
789 /* lookup table for converting channel mode */
790 UINT16 codec_mode_tbl[5] = { SBC_JOINT_STEREO, SBC_STEREO, SBC_DUAL, 0, SBC_MONO };
791
792 /* lookup table for converting number of blocks */
793 UINT16 codec_block_tbl[5] = { 16, 12, 8, 0, 4 };
794
795 /* lookup table to convert freq */
796 UINT16 freq_block_tbl[5] = { SBC_sf48000, SBC_sf44100, SBC_sf32000, 0, SBC_sf16000 };
797
798 APPL_TRACE_DEBUG("btif_a2dp_encoder_init");
799
800 /* Retrieve the current SBC configuration (default if currently not used) */
801 bta_av_co_audio_get_sbc_config(&sbc_config, &minmtu);
802 msg.NumOfSubBands = (sbc_config.num_subbands == A2D_SBC_IE_SUBBAND_4) ? 4 : 8;
803 msg.NumOfBlocks = codec_block_tbl[sbc_config.block_len >> 5];
804 msg.AllocationMethod = (sbc_config.alloc_mthd == A2D_SBC_IE_ALLOC_MD_L) ? SBC_LOUDNESS : SBC_SNR;
805 msg.ChannelMode = codec_mode_tbl[sbc_config.ch_mode >> 1];
806 msg.SamplingFreq = freq_block_tbl[sbc_config.samp_freq >> 5];
807 msg.MtuSize = minmtu;
808
809 APPL_TRACE_EVENT("msg.ChannelMode %x", msg.ChannelMode);
810
811 /* Init the media task to encode SBC properly */
812 btif_media_task_enc_init_req(&msg);
813 }
814
btif_a2dp_encoder_update(void)815 static void btif_a2dp_encoder_update(void)
816 {
817 UINT16 minmtu;
818 tA2D_SBC_CIE sbc_config;
819 tBTIF_MEDIA_UPDATE_AUDIO msg;
820 UINT8 pref_min;
821 UINT8 pref_max;
822
823 APPL_TRACE_DEBUG("btif_a2dp_encoder_update");
824
825 /* Retrieve the current SBC configuration (default if currently not used) */
826 bta_av_co_audio_get_sbc_config(&sbc_config, &minmtu);
827
828 APPL_TRACE_DEBUG("btif_a2dp_encoder_update: Common min_bitpool:%d(0x%x) max_bitpool:%d(0x%x)",
829 sbc_config.min_bitpool, sbc_config.min_bitpool,
830 sbc_config.max_bitpool, sbc_config.max_bitpool);
831
832 if (sbc_config.min_bitpool > sbc_config.max_bitpool)
833 {
834 APPL_TRACE_ERROR("btif_a2dp_encoder_update: ERROR btif_a2dp_encoder_update min_bitpool > max_bitpool");
835 }
836
837 /* check if remote sink has a preferred bitpool range */
838 if (bta_av_co_get_remote_bitpool_pref(&pref_min, &pref_max) == TRUE)
839 {
840 /* adjust our preferred bitpool with the remote preference if within
841 our capable range */
842
843 if (pref_min < sbc_config.min_bitpool)
844 pref_min = sbc_config.min_bitpool;
845
846 if (pref_max > sbc_config.max_bitpool)
847 pref_max = sbc_config.max_bitpool;
848
849 msg.MinBitPool = pref_min;
850 msg.MaxBitPool = pref_max;
851
852 if ((pref_min != sbc_config.min_bitpool) || (pref_max != sbc_config.max_bitpool))
853 {
854 APPL_TRACE_EVENT("## adjusted our bitpool range to peer pref [%d:%d] ##",
855 pref_min, pref_max);
856 }
857 }
858 else
859 {
860 msg.MinBitPool = sbc_config.min_bitpool;
861 msg.MaxBitPool = sbc_config.max_bitpool;
862 }
863
864 msg.MinMtuSize = minmtu;
865
866 /* Update the media task to encode SBC properly */
867 btif_media_task_enc_update_req(&msg);
868 }
869
btif_a2dp_start_media_task(void)870 bool btif_a2dp_start_media_task(void)
871 {
872 if (media_task_running != MEDIA_TASK_STATE_OFF)
873 {
874 APPL_TRACE_ERROR("warning : media task already running");
875 return false;
876 }
877
878 APPL_TRACE_EVENT("## A2DP START MEDIA THREAD ##");
879
880 btif_media_cmd_msg_queue = fixed_queue_new(SIZE_MAX);
881
882 /* start a2dp media task */
883 worker_thread = thread_new("media_worker");
884 if (worker_thread == NULL)
885 goto error_exit;
886
887 fixed_queue_register_dequeue(btif_media_cmd_msg_queue,
888 thread_get_reactor(worker_thread),
889 btif_media_thread_handle_cmd,
890 NULL);
891
892 thread_post(worker_thread, btif_media_thread_init, NULL);
893 APPL_TRACE_EVENT("## A2DP MEDIA THREAD STARTED ##");
894
895 return true;
896
897 error_exit:;
898 APPL_TRACE_ERROR("%s unable to start up media thread", __func__);
899 return false;
900 }
901
btif_a2dp_stop_media_task(void)902 void btif_a2dp_stop_media_task(void)
903 {
904 APPL_TRACE_EVENT("## A2DP STOP MEDIA THREAD ##");
905
906 // Stop timer
907 alarm_free(btif_media_cb.media_alarm);
908 btif_media_cb.media_alarm = NULL;
909
910 // Exit thread
911 fixed_queue_free(btif_media_cmd_msg_queue, NULL);
912 btif_media_cmd_msg_queue = NULL;
913 thread_post(worker_thread, btif_media_thread_cleanup, NULL);
914 thread_free(worker_thread);
915 worker_thread = NULL;
916 }
917
918 /*****************************************************************************
919 **
920 ** Function btif_a2dp_on_init
921 **
922 ** Description
923 **
924 ** Returns
925 **
926 *******************************************************************************/
927
btif_a2dp_on_init(void)928 void btif_a2dp_on_init(void)
929 {
930 #ifdef USE_AUDIO_TRACK
931 btif_media_cb.rx_audio_focus_state = BTIF_MEDIA_FOCUS_NOT_GRANTED;
932 btif_media_cb.audio_track = NULL;
933 #endif
934 }
935
936
937 /*****************************************************************************
938 **
939 ** Function btif_a2dp_setup_codec
940 **
941 ** Description
942 **
943 ** Returns
944 **
945 *******************************************************************************/
946
btif_a2dp_setup_codec(void)947 void btif_a2dp_setup_codec(void)
948 {
949 tBTIF_AV_MEDIA_FEEDINGS media_feeding;
950 tBTIF_STATUS status;
951
952 APPL_TRACE_EVENT("## A2DP SETUP CODEC ##");
953
954 mutex_global_lock();
955
956 /* for now hardcode 44.1 khz 16 bit stereo PCM format */
957 media_feeding.cfg.pcm.sampling_freq = BTIF_A2DP_SRC_SAMPLING_RATE;
958 media_feeding.cfg.pcm.bit_per_sample = BTIF_A2DP_SRC_BIT_DEPTH;
959 media_feeding.cfg.pcm.num_channel = BTIF_A2DP_SRC_NUM_CHANNELS;
960 media_feeding.format = BTIF_AV_CODEC_PCM;
961
962 if (bta_av_co_audio_set_codec(&media_feeding, &status))
963 {
964 tBTIF_MEDIA_INIT_AUDIO_FEEDING mfeed;
965
966 /* Init the encoding task */
967 btif_a2dp_encoder_init();
968
969 /* Build the media task configuration */
970 mfeed.feeding = media_feeding;
971 mfeed.feeding_mode = BTIF_AV_FEEDING_ASYNCHRONOUS;
972 /* Send message to Media task to configure transcoding */
973 btif_media_task_audio_feeding_init_req(&mfeed);
974 }
975
976 mutex_global_unlock();
977 }
978
979
980 /*****************************************************************************
981 **
982 ** Function btif_a2dp_on_idle
983 **
984 ** Description
985 **
986 ** Returns
987 **
988 *******************************************************************************/
989
btif_a2dp_on_idle(void)990 void btif_a2dp_on_idle(void)
991 {
992 APPL_TRACE_EVENT("## ON A2DP IDLE ## peer_sep = %d", btif_media_cb.peer_sep);
993 if (btif_media_cb.peer_sep == AVDT_TSEP_SNK)
994 {
995 /* Make sure media task is stopped */
996 btif_media_task_stop_aa_req();
997 }
998
999 bta_av_co_init();
1000 #if (BTA_AV_SINK_INCLUDED == TRUE)
1001 if (btif_media_cb.peer_sep == AVDT_TSEP_SRC)
1002 {
1003 btif_media_cb.rx_flush = TRUE;
1004 btif_media_task_aa_rx_flush_req();
1005 btif_media_task_aa_handle_stop_decoding();
1006 btif_media_task_clear_track();
1007 APPL_TRACE_DEBUG("Stopped BT track");
1008 }
1009 #endif
1010 }
1011
1012 /*****************************************************************************
1013 **
1014 ** Function btif_a2dp_on_open
1015 **
1016 ** Description
1017 **
1018 ** Returns
1019 **
1020 *******************************************************************************/
1021
btif_a2dp_on_open(void)1022 void btif_a2dp_on_open(void)
1023 {
1024 APPL_TRACE_EVENT("## ON A2DP OPEN ##");
1025
1026 /* always use callback to notify socket events */
1027 UIPC_Open(UIPC_CH_ID_AV_AUDIO, btif_a2dp_data_cb);
1028 }
1029
1030 /*******************************************************************************
1031 **
1032 ** Function btif_media_task_clear_track
1033 **
1034 ** Description
1035 **
1036 ** Returns TRUE is success
1037 **
1038 *******************************************************************************/
btif_media_task_clear_track(void)1039 BOOLEAN btif_media_task_clear_track(void)
1040 {
1041 BT_HDR *p_buf = osi_malloc(sizeof(BT_HDR));
1042
1043 p_buf->event = BTIF_MEDIA_AUDIO_SINK_CLEAR_TRACK;
1044 fixed_queue_enqueue(btif_media_cmd_msg_queue, p_buf);
1045
1046 return TRUE;
1047 }
1048
1049 /*****************************************************************************
1050 **
1051 ** Function btif_reset_decoder
1052 **
1053 ** Description
1054 **
1055 ** Returns
1056 **
1057 *******************************************************************************/
1058
btif_reset_decoder(UINT8 * p_av)1059 void btif_reset_decoder(UINT8 *p_av)
1060 {
1061 tBTIF_MEDIA_SINK_CFG_UPDATE *p_buf =
1062 osi_malloc(sizeof(tBTIF_MEDIA_SINK_CFG_UPDATE));
1063
1064 APPL_TRACE_EVENT("btif_reset_decoder");
1065 APPL_TRACE_DEBUG("btif_reset_decoder p_codec_info[%x:%x:%x:%x:%x:%x]",
1066 p_av[1], p_av[2], p_av[3],
1067 p_av[4], p_av[5], p_av[6]);
1068
1069 memcpy(p_buf->codec_info,p_av, AVDT_CODEC_SIZE);
1070 p_buf->hdr.event = BTIF_MEDIA_AUDIO_SINK_CFG_UPDATE;
1071
1072 fixed_queue_enqueue(btif_media_cmd_msg_queue, p_buf);
1073 }
1074
1075 /*****************************************************************************
1076 **
1077 ** Function btif_a2dp_on_started
1078 **
1079 ** Description
1080 **
1081 ** Returns
1082 **
1083 *******************************************************************************/
1084
btif_a2dp_on_started(tBTA_AV_START * p_av,BOOLEAN pending_start)1085 BOOLEAN btif_a2dp_on_started(tBTA_AV_START *p_av, BOOLEAN pending_start)
1086 {
1087 BOOLEAN ack = FALSE;
1088
1089 APPL_TRACE_EVENT("## ON A2DP STARTED ##");
1090
1091 if (p_av == NULL)
1092 {
1093 /* ack back a local start request */
1094 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_SUCCESS);
1095 return TRUE;
1096 }
1097
1098 if (p_av->status == BTA_AV_SUCCESS)
1099 {
1100 if (p_av->suspending == FALSE)
1101 {
1102 if (p_av->initiator)
1103 {
1104 if (pending_start) {
1105 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_SUCCESS);
1106 ack = TRUE;
1107 }
1108 }
1109 else
1110 {
1111 /* we were remotely started, make sure codec
1112 is setup before datapath is started */
1113 btif_a2dp_setup_codec();
1114 }
1115
1116 /* media task is autostarted upon a2dp audiopath connection */
1117 }
1118 }
1119 else if (pending_start)
1120 {
1121 APPL_TRACE_WARNING("%s: A2DP start request failed: status = %d",
1122 __func__, p_av->status);
1123 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_FAILURE);
1124 ack = TRUE;
1125 }
1126 return ack;
1127 }
1128
1129
1130 /*****************************************************************************
1131 **
1132 ** Function btif_a2dp_ack_fail
1133 **
1134 ** Description
1135 **
1136 ** Returns
1137 **
1138 *******************************************************************************/
1139
btif_a2dp_ack_fail(void)1140 void btif_a2dp_ack_fail(void)
1141 {
1142 APPL_TRACE_EVENT("## A2DP_CTRL_ACK_FAILURE ##");
1143 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_FAILURE);
1144 }
1145
1146 /*****************************************************************************
1147 **
1148 ** Function btif_a2dp_on_stopped
1149 **
1150 ** Description
1151 **
1152 ** Returns
1153 **
1154 *******************************************************************************/
1155
btif_a2dp_on_stopped(tBTA_AV_SUSPEND * p_av)1156 void btif_a2dp_on_stopped(tBTA_AV_SUSPEND *p_av)
1157 {
1158 APPL_TRACE_EVENT("## ON A2DP STOPPED ##");
1159 if (btif_media_cb.peer_sep == AVDT_TSEP_SRC) /* Handling for A2DP SINK cases*/
1160 {
1161 btif_media_cb.rx_flush = TRUE;
1162 btif_media_task_aa_rx_flush_req();
1163 btif_media_task_aa_handle_stop_decoding();
1164 #ifndef USE_AUDIO_TRACK
1165 UIPC_Close(UIPC_CH_ID_AV_AUDIO);
1166 #endif
1167 btif_media_cb.data_channel_open = FALSE;
1168 return;
1169 }
1170 /* allow using this api for other than suspend */
1171 if (p_av != NULL)
1172 {
1173 if (p_av->status != BTA_AV_SUCCESS)
1174 {
1175 APPL_TRACE_EVENT("AV STOP FAILED (%d)", p_av->status);
1176
1177 if (p_av->initiator) {
1178 APPL_TRACE_WARNING("%s: A2DP stop request failed: status = %d",
1179 __func__, p_av->status);
1180 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_FAILURE);
1181 }
1182 return;
1183 }
1184 }
1185
1186 /* ensure tx frames are immediately suspended */
1187 btif_media_cb.tx_flush = 1;
1188
1189 /* request to stop media task */
1190 btif_media_task_aa_tx_flush_req();
1191 btif_media_task_stop_aa_req();
1192
1193 /* once stream is fully stopped we will ack back */
1194 }
1195
1196
1197 /*****************************************************************************
1198 **
1199 ** Function btif_a2dp_on_suspended
1200 **
1201 ** Description
1202 **
1203 ** Returns
1204 **
1205 *******************************************************************************/
1206
btif_a2dp_on_suspended(tBTA_AV_SUSPEND * p_av)1207 void btif_a2dp_on_suspended(tBTA_AV_SUSPEND *p_av)
1208 {
1209 APPL_TRACE_EVENT("## ON A2DP SUSPENDED ##");
1210 if (btif_media_cb.peer_sep == AVDT_TSEP_SRC)
1211 {
1212 btif_media_cb.rx_flush = TRUE;
1213 btif_media_task_aa_rx_flush_req();
1214 btif_media_task_aa_handle_stop_decoding();
1215 #ifndef USE_AUDIO_TRACK
1216 UIPC_Close(UIPC_CH_ID_AV_AUDIO);
1217 #endif
1218 return;
1219 }
1220
1221 /* check for status failures */
1222 if (p_av->status != BTA_AV_SUCCESS)
1223 {
1224 if (p_av->initiator == TRUE) {
1225 APPL_TRACE_WARNING("%s: A2DP suspend request failed: status = %d",
1226 __func__, p_av->status);
1227 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_FAILURE);
1228 }
1229 }
1230
1231 /* once stream is fully stopped we will ack back */
1232
1233 /* ensure tx frames are immediately flushed */
1234 btif_media_cb.tx_flush = 1;
1235
1236 /* stop timer tick */
1237 btif_media_task_stop_aa_req();
1238 }
1239
1240
1241 /*****************************************************************************
1242 **
1243 ** Function btif_a2dp_on_offload_started
1244 **
1245 ** Description
1246 **
1247 ** Returns
1248 **
1249 *******************************************************************************/
btif_a2dp_on_offload_started(tBTA_AV_STATUS status)1250 void btif_a2dp_on_offload_started(tBTA_AV_STATUS status)
1251 {
1252 tA2DP_CTRL_ACK ack;
1253 APPL_TRACE_EVENT("%s status %d", __func__, status);
1254
1255 switch (status) {
1256 case BTA_AV_SUCCESS:
1257 ack = A2DP_CTRL_ACK_SUCCESS;
1258 break;
1259
1260 case BTA_AV_FAIL_RESOURCES:
1261 APPL_TRACE_ERROR("%s FAILED UNSUPPORTED", __func__);
1262 ack = A2DP_CTRL_ACK_UNSUPPORTED;
1263 break;
1264 default:
1265 APPL_TRACE_ERROR("%s FAILED: status = %d", __func__, status);
1266 ack = A2DP_CTRL_ACK_FAILURE;
1267 break;
1268 }
1269 a2dp_cmd_acknowledge(ack);
1270 }
1271
1272 /* when true media task discards any rx frames */
btif_a2dp_set_rx_flush(BOOLEAN enable)1273 void btif_a2dp_set_rx_flush(BOOLEAN enable)
1274 {
1275 APPL_TRACE_EVENT("## DROP RX %d ##", enable);
1276 btif_media_cb.rx_flush = enable;
1277 }
1278
1279 /* when true media task discards any tx frames */
btif_a2dp_set_tx_flush(BOOLEAN enable)1280 void btif_a2dp_set_tx_flush(BOOLEAN enable)
1281 {
1282 APPL_TRACE_EVENT("## DROP TX %d ##", enable);
1283 btif_media_cb.tx_flush = enable;
1284 }
1285
1286 #ifdef USE_AUDIO_TRACK
btif_a2dp_set_audio_focus_state(btif_media_audio_focus_state state)1287 void btif_a2dp_set_audio_focus_state(btif_media_audio_focus_state state)
1288 {
1289 tBTIF_MEDIA_SINK_FOCUS_UPDATE *p_buf =
1290 osi_malloc(sizeof(tBTIF_MEDIA_SINK_FOCUS_UPDATE));
1291
1292 APPL_TRACE_EVENT("%s", __func__);
1293
1294 p_buf->focus_state = state;
1295 p_buf->hdr.event = BTIF_MEDIA_AUDIO_SINK_SET_FOCUS_STATE;
1296 fixed_queue_enqueue(btif_media_cmd_msg_queue, p_buf);
1297 }
1298
btif_a2dp_set_audio_track_gain(float gain)1299 void btif_a2dp_set_audio_track_gain(float gain)
1300 {
1301 APPL_TRACE_DEBUG("%s set gain to %f", __func__, gain);
1302 BtifAvrcpSetAudioTrackGain(btif_media_cb.audio_track, gain);
1303 }
1304 #endif
1305
1306 #if (BTA_AV_SINK_INCLUDED == TRUE)
btif_media_task_avk_handle_timer(UNUSED_ATTR void * context)1307 static void btif_media_task_avk_handle_timer(UNUSED_ATTR void *context)
1308 {
1309 tBT_SBC_HDR *p_msg;
1310 int num_sbc_frames;
1311 int num_frames_to_process;
1312
1313 if (fixed_queue_is_empty(btif_media_cb.RxSbcQ))
1314 {
1315 APPL_TRACE_DEBUG(" QUE EMPTY ");
1316 }
1317 else
1318 {
1319 #ifdef USE_AUDIO_TRACK
1320 /* Don't Do anything in case of Not granted */
1321 if (btif_media_cb.rx_audio_focus_state == BTIF_MEDIA_FOCUS_NOT_GRANTED)
1322 {
1323 APPL_TRACE_DEBUG("%s skipping frames since focus is not present.", __func__);
1324 return;
1325 }
1326 /* play only in BTIF_MEDIA_FOCUS_GRANTED case */
1327 #endif
1328 if (btif_media_cb.rx_flush == TRUE)
1329 {
1330 btif_media_flush_q(btif_media_cb.RxSbcQ);
1331 return;
1332 }
1333
1334 num_frames_to_process = btif_media_cb.frames_to_process;
1335 APPL_TRACE_DEBUG(" Process Frames + ");
1336
1337 do
1338 {
1339 p_msg = (tBT_SBC_HDR *)fixed_queue_try_peek_first(btif_media_cb.RxSbcQ);
1340 if (p_msg == NULL)
1341 return;
1342 num_sbc_frames = p_msg->num_frames_to_be_processed; /* num of frames in Que Packets */
1343 APPL_TRACE_DEBUG(" Frames left in topmost packet %d", num_sbc_frames);
1344 APPL_TRACE_DEBUG(" Remaining frames to process in tick %d", num_frames_to_process);
1345 APPL_TRACE_DEBUG(" Num of Packets in Que %d",
1346 fixed_queue_length(btif_media_cb.RxSbcQ));
1347
1348 if ( num_sbc_frames > num_frames_to_process) /* Que Packet has more frames*/
1349 {
1350 p_msg->num_frames_to_be_processed= num_frames_to_process;
1351 btif_media_task_handle_inc_media(p_msg);
1352 p_msg->num_frames_to_be_processed = num_sbc_frames - num_frames_to_process;
1353 num_frames_to_process = 0;
1354 break;
1355 }
1356 else /* Que packet has less frames */
1357 {
1358 btif_media_task_handle_inc_media(p_msg);
1359 p_msg = (tBT_SBC_HDR *)fixed_queue_try_dequeue(btif_media_cb.RxSbcQ);
1360 if( p_msg == NULL )
1361 {
1362 APPL_TRACE_ERROR("Insufficient data in que ");
1363 break;
1364 }
1365 num_frames_to_process = num_frames_to_process - p_msg->num_frames_to_be_processed;
1366 osi_free(p_msg);
1367 }
1368 } while(num_frames_to_process > 0);
1369
1370 APPL_TRACE_DEBUG(" Process Frames - ");
1371 }
1372 }
1373 #else
btif_media_task_avk_handle_timer(UNUSED_ATTR void * context)1374 static void btif_media_task_avk_handle_timer(UNUSED_ATTR void *context) {}
1375 #endif
1376
btif_media_task_aa_handle_timer(UNUSED_ATTR void * context)1377 static void btif_media_task_aa_handle_timer(UNUSED_ATTR void *context)
1378 {
1379 uint64_t timestamp_us = time_now_us();
1380 log_tstamps_us("media task tx timer", timestamp_us);
1381
1382 #if (BTA_AV_INCLUDED == TRUE)
1383 if (alarm_is_scheduled(btif_media_cb.media_alarm))
1384 {
1385 btif_media_send_aa_frame(timestamp_us);
1386 }
1387 else
1388 {
1389 APPL_TRACE_ERROR("ERROR Media task Scheduled after Suspend");
1390 }
1391 #endif
1392 }
1393
1394 #if (BTA_AV_INCLUDED == TRUE)
btif_media_task_aa_handle_uipc_rx_rdy(void)1395 static void btif_media_task_aa_handle_uipc_rx_rdy(void)
1396 {
1397 /* process all the UIPC data */
1398 btif_media_aa_prep_2_send(0xFF, time_now_us());
1399
1400 /* send it */
1401 LOG_VERBOSE(LOG_TAG, "%s calls bta_av_ci_src_data_ready", __func__);
1402 bta_av_ci_src_data_ready(BTA_AV_CHNL_AUDIO);
1403 }
1404 #endif
1405
btif_media_thread_init(UNUSED_ATTR void * context)1406 static void btif_media_thread_init(UNUSED_ATTR void *context) {
1407 // Check to make sure the platform has 8 bits/byte since
1408 // we're using that in frame size calculations now.
1409 assert(CHAR_BIT == 8);
1410
1411 memset(&btif_media_cb, 0, sizeof(btif_media_cb));
1412 btif_media_cb.stats.session_start_us = time_now_us();
1413
1414 UIPC_Init(NULL);
1415
1416 #if (BTA_AV_INCLUDED == TRUE)
1417 btif_media_cb.TxAaQ = fixed_queue_new(SIZE_MAX);
1418 btif_media_cb.RxSbcQ = fixed_queue_new(SIZE_MAX);
1419 UIPC_Open(UIPC_CH_ID_AV_CTRL , btif_a2dp_ctrl_cb);
1420 #endif
1421
1422 raise_priority_a2dp(TASK_HIGH_MEDIA);
1423 media_task_running = MEDIA_TASK_STATE_ON;
1424 }
1425
btif_media_thread_cleanup(UNUSED_ATTR void * context)1426 static void btif_media_thread_cleanup(UNUSED_ATTR void *context) {
1427 /* make sure no channels are restarted while shutting down */
1428 media_task_running = MEDIA_TASK_STATE_SHUTTING_DOWN;
1429
1430 /* this calls blocks until uipc is fully closed */
1431 UIPC_Close(UIPC_CH_ID_ALL);
1432
1433 #if (BTA_AV_INCLUDED == TRUE)
1434 fixed_queue_free(btif_media_cb.TxAaQ, NULL);
1435 btif_media_cb.TxAaQ = NULL;
1436 fixed_queue_free(btif_media_cb.RxSbcQ, NULL);
1437 btif_media_cb.RxSbcQ = NULL;
1438 #endif
1439
1440 /* Clear media task flag */
1441 media_task_running = MEDIA_TASK_STATE_OFF;
1442 }
1443
1444 /*******************************************************************************
1445 **
1446 ** Function btif_media_task_send_cmd_evt
1447 **
1448 ** Description
1449 **
1450 ** Returns TRUE is success
1451 **
1452 *******************************************************************************/
btif_media_task_send_cmd_evt(UINT16 Evt)1453 BOOLEAN btif_media_task_send_cmd_evt(UINT16 Evt)
1454 {
1455 BT_HDR *p_buf = osi_malloc(sizeof(BT_HDR));
1456
1457 p_buf->event = Evt;
1458 fixed_queue_enqueue(btif_media_cmd_msg_queue, p_buf);
1459
1460 return TRUE;
1461 }
1462
1463 /*******************************************************************************
1464 **
1465 ** Function btif_media_flush_q
1466 **
1467 ** Description
1468 **
1469 ** Returns void
1470 **
1471 *******************************************************************************/
btif_media_flush_q(fixed_queue_t * p_q)1472 static void btif_media_flush_q(fixed_queue_t *p_q)
1473 {
1474 while (! fixed_queue_is_empty(p_q))
1475 {
1476 osi_free(fixed_queue_try_dequeue(p_q));
1477 }
1478 }
1479
btif_media_thread_handle_cmd(fixed_queue_t * queue,UNUSED_ATTR void * context)1480 static void btif_media_thread_handle_cmd(fixed_queue_t *queue, UNUSED_ATTR void *context)
1481 {
1482 BT_HDR *p_msg = (BT_HDR *)fixed_queue_dequeue(queue);
1483 LOG_VERBOSE(LOG_TAG, "btif_media_thread_handle_cmd : %d %s", p_msg->event,
1484 dump_media_event(p_msg->event));
1485
1486 switch (p_msg->event)
1487 {
1488 #if (BTA_AV_INCLUDED == TRUE)
1489 case BTIF_MEDIA_START_AA_TX:
1490 btif_media_task_aa_start_tx();
1491 break;
1492 case BTIF_MEDIA_STOP_AA_TX:
1493 btif_media_task_aa_stop_tx();
1494 break;
1495 case BTIF_MEDIA_SBC_ENC_INIT:
1496 btif_media_task_enc_init(p_msg);
1497 break;
1498 case BTIF_MEDIA_SBC_ENC_UPDATE:
1499 btif_media_task_enc_update(p_msg);
1500 break;
1501 case BTIF_MEDIA_AUDIO_FEEDING_INIT:
1502 btif_media_task_audio_feeding_init(p_msg);
1503 break;
1504 case BTIF_MEDIA_FLUSH_AA_TX:
1505 btif_media_task_aa_tx_flush(p_msg);
1506 break;
1507 case BTIF_MEDIA_UIPC_RX_RDY:
1508 btif_media_task_aa_handle_uipc_rx_rdy();
1509 break;
1510 #ifdef USE_AUDIO_TRACK
1511 case BTIF_MEDIA_AUDIO_SINK_SET_FOCUS_STATE:
1512 if(!btif_av_is_connected())
1513 break;
1514 btif_media_cb.rx_audio_focus_state = ((tBTIF_MEDIA_SINK_FOCUS_UPDATE *)p_msg)->focus_state;
1515 APPL_TRACE_DEBUG("Setting focus state to %d ",btif_media_cb.rx_audio_focus_state);
1516 break;
1517 #endif
1518 case BTIF_MEDIA_AUDIO_SINK_CFG_UPDATE:
1519 #if (BTA_AV_SINK_INCLUDED == TRUE)
1520 btif_media_task_aa_handle_decoder_reset(p_msg);
1521 #endif
1522 break;
1523 case BTIF_MEDIA_AUDIO_SINK_CLEAR_TRACK:
1524 #if (BTA_AV_SINK_INCLUDED == TRUE)
1525 btif_media_task_aa_handle_clear_track();
1526 #endif
1527 break;
1528 case BTIF_MEDIA_FLUSH_AA_RX:
1529 btif_media_task_aa_rx_flush();
1530 break;
1531 #endif
1532 default:
1533 APPL_TRACE_ERROR("ERROR in %s unknown event %d", __func__, p_msg->event);
1534 }
1535 osi_free(p_msg);
1536 LOG_VERBOSE(LOG_TAG, "%s: %s DONE", __func__, dump_media_event(p_msg->event));
1537 }
1538
1539 #if (BTA_AV_SINK_INCLUDED == TRUE)
1540 /*******************************************************************************
1541 **
1542 ** Function btif_media_task_handle_inc_media
1543 **
1544 ** Description
1545 **
1546 ** Returns void
1547 **
1548 *******************************************************************************/
btif_media_task_handle_inc_media(tBT_SBC_HDR * p_msg)1549 static void btif_media_task_handle_inc_media(tBT_SBC_HDR*p_msg)
1550 {
1551 UINT8 *sbc_start_frame = ((UINT8*)(p_msg + 1) + p_msg->offset + 1);
1552 int count;
1553 UINT32 pcmBytes, availPcmBytes;
1554 OI_INT16 *pcmDataPointer = pcmData; /*Will be overwritten on next packet receipt*/
1555 OI_STATUS status;
1556 int num_sbc_frames = p_msg->num_frames_to_be_processed;
1557 UINT32 sbc_frame_len = p_msg->len - 1;
1558 availPcmBytes = sizeof(pcmData);
1559
1560 if ((btif_media_cb.peer_sep == AVDT_TSEP_SNK) || (btif_media_cb.rx_flush))
1561 {
1562 APPL_TRACE_DEBUG(" State Changed happened in this tick ");
1563 return;
1564 }
1565 #ifndef USE_AUDIO_TRACK
1566 // ignore data if no one is listening
1567 if (!btif_media_cb.data_channel_open)
1568 {
1569 APPL_TRACE_ERROR("%s Channel not open, returning", __func__);
1570 return;
1571 }
1572 #endif
1573 APPL_TRACE_DEBUG("%s Number of sbc frames %d, frame_len %d",
1574 __func__, num_sbc_frames, sbc_frame_len);
1575
1576 for(count = 0; count < num_sbc_frames && sbc_frame_len != 0; count ++)
1577 {
1578 pcmBytes = availPcmBytes;
1579 status = OI_CODEC_SBC_DecodeFrame(&context, (const OI_BYTE**)&sbc_start_frame,
1580 (OI_UINT32 *)&sbc_frame_len,
1581 (OI_INT16 *)pcmDataPointer,
1582 (OI_UINT32 *)&pcmBytes);
1583 if (!OI_SUCCESS(status)) {
1584 APPL_TRACE_ERROR("Decoding failure: %d\n", status);
1585 break;
1586 }
1587 availPcmBytes -= pcmBytes;
1588 pcmDataPointer += pcmBytes/2;
1589 p_msg->offset += (p_msg->len - 1) - sbc_frame_len;
1590 p_msg->len = sbc_frame_len + 1;
1591 }
1592
1593 #ifdef USE_AUDIO_TRACK
1594 BtifAvrcpAudioTrackWriteData(
1595 btif_media_cb.audio_track, (void*)pcmData, (sizeof(pcmData) - availPcmBytes));
1596 #else
1597 UIPC_Send(UIPC_CH_ID_AV_AUDIO, 0, (UINT8 *)pcmData, (sizeof(pcmData) - availPcmBytes));
1598 #endif
1599 }
1600 #endif
1601
1602 #if (BTA_AV_INCLUDED == TRUE)
1603 /*******************************************************************************
1604 **
1605 ** Function btif_media_task_enc_init_req
1606 **
1607 ** Description
1608 **
1609 ** Returns TRUE is success
1610 **
1611 *******************************************************************************/
btif_media_task_enc_init_req(tBTIF_MEDIA_INIT_AUDIO * p_msg)1612 BOOLEAN btif_media_task_enc_init_req(tBTIF_MEDIA_INIT_AUDIO *p_msg)
1613 {
1614 tBTIF_MEDIA_INIT_AUDIO *p_buf = osi_malloc(sizeof(tBTIF_MEDIA_INIT_AUDIO));
1615
1616 memcpy(p_buf, p_msg, sizeof(tBTIF_MEDIA_INIT_AUDIO));
1617 p_buf->hdr.event = BTIF_MEDIA_SBC_ENC_INIT;
1618 fixed_queue_enqueue(btif_media_cmd_msg_queue, p_buf);
1619
1620 return TRUE;
1621 }
1622
1623 /*******************************************************************************
1624 **
1625 ** Function btif_media_task_enc_update_req
1626 **
1627 ** Description
1628 **
1629 ** Returns TRUE is success
1630 **
1631 *******************************************************************************/
btif_media_task_enc_update_req(tBTIF_MEDIA_UPDATE_AUDIO * p_msg)1632 BOOLEAN btif_media_task_enc_update_req(tBTIF_MEDIA_UPDATE_AUDIO *p_msg)
1633 {
1634 tBTIF_MEDIA_UPDATE_AUDIO *p_buf =
1635 osi_malloc(sizeof(tBTIF_MEDIA_UPDATE_AUDIO));
1636
1637 memcpy(p_buf, p_msg, sizeof(tBTIF_MEDIA_UPDATE_AUDIO));
1638 p_buf->hdr.event = BTIF_MEDIA_SBC_ENC_UPDATE;
1639 fixed_queue_enqueue(btif_media_cmd_msg_queue, p_buf);
1640
1641 return TRUE;
1642 }
1643
1644 /*******************************************************************************
1645 **
1646 ** Function btif_media_task_audio_feeding_init_req
1647 **
1648 ** Description
1649 **
1650 ** Returns TRUE is success
1651 **
1652 *******************************************************************************/
btif_media_task_audio_feeding_init_req(tBTIF_MEDIA_INIT_AUDIO_FEEDING * p_msg)1653 BOOLEAN btif_media_task_audio_feeding_init_req(tBTIF_MEDIA_INIT_AUDIO_FEEDING *p_msg)
1654 {
1655 tBTIF_MEDIA_INIT_AUDIO_FEEDING *p_buf =
1656 osi_malloc(sizeof(tBTIF_MEDIA_INIT_AUDIO_FEEDING));
1657
1658 memcpy(p_buf, p_msg, sizeof(tBTIF_MEDIA_INIT_AUDIO_FEEDING));
1659 p_buf->hdr.event = BTIF_MEDIA_AUDIO_FEEDING_INIT;
1660 fixed_queue_enqueue(btif_media_cmd_msg_queue, p_buf);
1661
1662 return TRUE;
1663 }
1664
1665 /*******************************************************************************
1666 **
1667 ** Function btif_media_task_start_aa_req
1668 **
1669 ** Description
1670 **
1671 ** Returns TRUE is success
1672 **
1673 *******************************************************************************/
btif_media_task_start_aa_req(void)1674 BOOLEAN btif_media_task_start_aa_req(void)
1675 {
1676 BT_HDR *p_buf = osi_malloc(sizeof(BT_HDR));
1677
1678 p_buf->event = BTIF_MEDIA_START_AA_TX;
1679 fixed_queue_enqueue(btif_media_cmd_msg_queue, p_buf);
1680
1681 return TRUE;
1682 }
1683
1684 /*******************************************************************************
1685 **
1686 ** Function btif_media_task_stop_aa_req
1687 **
1688 ** Description
1689 **
1690 ** Returns TRUE is success
1691 **
1692 *******************************************************************************/
btif_media_task_stop_aa_req(void)1693 BOOLEAN btif_media_task_stop_aa_req(void)
1694 {
1695 BT_HDR *p_buf = osi_malloc(sizeof(BT_HDR));
1696
1697 p_buf->event = BTIF_MEDIA_STOP_AA_TX;
1698
1699 /*
1700 * Explicitly check whether the btif_media_cmd_msg_queue is not NULL to
1701 * avoid a race condition during shutdown of the Bluetooth stack.
1702 * This race condition is triggered when A2DP audio is streaming on
1703 * shutdown:
1704 * "btif_a2dp_on_stopped() -> btif_media_task_stop_aa_req()" is called
1705 * to stop the particular audio stream, and this happens right after
1706 * the "cleanup() -> btif_a2dp_stop_media_task()" processing during
1707 * the shutdown of the Bluetooth stack.
1708 */
1709 if (btif_media_cmd_msg_queue != NULL)
1710 fixed_queue_enqueue(btif_media_cmd_msg_queue, p_buf);
1711
1712 return TRUE;
1713 }
1714 /*******************************************************************************
1715 **
1716 ** Function btif_media_task_aa_rx_flush_req
1717 **
1718 ** Description
1719 **
1720 ** Returns TRUE is success
1721 **
1722 *******************************************************************************/
btif_media_task_aa_rx_flush_req(void)1723 BOOLEAN btif_media_task_aa_rx_flush_req(void)
1724 {
1725 if (fixed_queue_is_empty(btif_media_cb.RxSbcQ)) /* Que is already empty */
1726 return TRUE;
1727
1728 BT_HDR *p_buf = osi_malloc(sizeof(BT_HDR));
1729 p_buf->event = BTIF_MEDIA_FLUSH_AA_RX;
1730 fixed_queue_enqueue(btif_media_cmd_msg_queue, p_buf);
1731
1732 return TRUE;
1733 }
1734
1735 /*******************************************************************************
1736 **
1737 ** Function btif_media_task_aa_tx_flush_req
1738 **
1739 ** Description
1740 **
1741 ** Returns TRUE is success
1742 **
1743 *******************************************************************************/
btif_media_task_aa_tx_flush_req(void)1744 BOOLEAN btif_media_task_aa_tx_flush_req(void)
1745 {
1746 BT_HDR *p_buf = osi_malloc(sizeof(BT_HDR));
1747
1748 p_buf->event = BTIF_MEDIA_FLUSH_AA_TX;
1749
1750 /*
1751 * Explicitly check whether the btif_media_cmd_msg_queue is not NULL to
1752 * avoid a race condition during shutdown of the Bluetooth stack.
1753 * This race condition is triggered when A2DP audio is streaming on
1754 * shutdown:
1755 * "btif_a2dp_on_stopped() -> btif_media_task_aa_tx_flush_req()" is called
1756 * to stop the particular audio stream, and this happens right after
1757 * the "cleanup() -> btif_a2dp_stop_media_task()" processing during
1758 * the shutdown of the Bluetooth stack.
1759 */
1760 if (btif_media_cmd_msg_queue != NULL)
1761 fixed_queue_enqueue(btif_media_cmd_msg_queue, p_buf);
1762
1763 return TRUE;
1764 }
1765 /*******************************************************************************
1766 **
1767 ** Function btif_media_task_aa_rx_flush
1768 **
1769 ** Description
1770 **
1771 ** Returns void
1772 **
1773 *******************************************************************************/
btif_media_task_aa_rx_flush(void)1774 static void btif_media_task_aa_rx_flush(void)
1775 {
1776 /* Flush all enqueued GKI SBC buffers (encoded) */
1777 APPL_TRACE_DEBUG("btif_media_task_aa_rx_flush");
1778
1779 btif_media_flush_q(btif_media_cb.RxSbcQ);
1780 }
1781
1782
1783 /*******************************************************************************
1784 **
1785 ** Function btif_media_task_aa_tx_flush
1786 **
1787 ** Description
1788 **
1789 ** Returns void
1790 **
1791 *******************************************************************************/
btif_media_task_aa_tx_flush(BT_HDR * p_msg)1792 static void btif_media_task_aa_tx_flush(BT_HDR *p_msg)
1793 {
1794 UNUSED(p_msg);
1795
1796 /* Flush all enqueued GKI music buffers (encoded) */
1797 APPL_TRACE_DEBUG("btif_media_task_aa_tx_flush");
1798
1799 btif_media_cb.media_feeding_state.pcm.counter = 0;
1800 btif_media_cb.media_feeding_state.pcm.aa_feed_residue = 0;
1801
1802 btif_media_cb.stats.tx_queue_total_flushed_messages +=
1803 fixed_queue_length(btif_media_cb.TxAaQ);
1804 btif_media_cb.stats.tx_queue_last_flushed_us = time_now_us();
1805 btif_media_flush_q(btif_media_cb.TxAaQ);
1806
1807 UIPC_Ioctl(UIPC_CH_ID_AV_AUDIO, UIPC_REQ_RX_FLUSH, NULL);
1808 }
1809
1810 /*******************************************************************************
1811 **
1812 ** Function btif_media_task_enc_init
1813 **
1814 ** Description Initialize encoding task
1815 **
1816 ** Returns void
1817 **
1818 *******************************************************************************/
btif_media_task_enc_init(BT_HDR * p_msg)1819 static void btif_media_task_enc_init(BT_HDR *p_msg)
1820 {
1821 tBTIF_MEDIA_INIT_AUDIO *pInitAudio = (tBTIF_MEDIA_INIT_AUDIO *) p_msg;
1822
1823 APPL_TRACE_DEBUG("btif_media_task_enc_init");
1824
1825 btif_media_cb.timestamp = 0;
1826
1827 /* SBC encoder config (enforced even if not used) */
1828 btif_media_cb.encoder.s16ChannelMode = pInitAudio->ChannelMode;
1829 btif_media_cb.encoder.s16NumOfSubBands = pInitAudio->NumOfSubBands;
1830 btif_media_cb.encoder.s16NumOfBlocks = pInitAudio->NumOfBlocks;
1831 btif_media_cb.encoder.s16AllocationMethod = pInitAudio->AllocationMethod;
1832 btif_media_cb.encoder.s16SamplingFreq = pInitAudio->SamplingFreq;
1833
1834 btif_media_cb.encoder.u16BitRate = btif_media_task_get_sbc_rate();
1835
1836 /* Default transcoding is PCM to SBC, modified by feeding configuration */
1837 btif_media_cb.TxTranscoding = BTIF_MEDIA_TRSCD_PCM_2_SBC;
1838 btif_media_cb.TxAaMtuSize = ((BTIF_MEDIA_AA_BUF_SIZE-BTIF_MEDIA_AA_SBC_OFFSET-sizeof(BT_HDR))
1839 < pInitAudio->MtuSize) ? (BTIF_MEDIA_AA_BUF_SIZE - BTIF_MEDIA_AA_SBC_OFFSET
1840 - sizeof(BT_HDR)) : pInitAudio->MtuSize;
1841
1842 APPL_TRACE_EVENT("btif_media_task_enc_init busy %d, mtu %d, peer mtu %d",
1843 btif_media_cb.busy_level, btif_media_cb.TxAaMtuSize, pInitAudio->MtuSize);
1844 APPL_TRACE_EVENT(" ch mode %d, subnd %d, nb blk %d, alloc %d, rate %d, freq %d",
1845 btif_media_cb.encoder.s16ChannelMode, btif_media_cb.encoder.s16NumOfSubBands,
1846 btif_media_cb.encoder.s16NumOfBlocks,
1847 btif_media_cb.encoder.s16AllocationMethod, btif_media_cb.encoder.u16BitRate,
1848 btif_media_cb.encoder.s16SamplingFreq);
1849
1850 /* Reset entirely the SBC encoder */
1851 SBC_Encoder_Init(&(btif_media_cb.encoder));
1852
1853 btif_media_cb.tx_sbc_frames = calculate_max_frames_per_packet();
1854
1855 APPL_TRACE_DEBUG("%s bit pool %d", __func__, btif_media_cb.encoder.s16BitPool);
1856 }
1857
1858 /*******************************************************************************
1859 **
1860 ** Function btif_media_task_enc_update
1861 **
1862 ** Description Update encoding task
1863 **
1864 ** Returns void
1865 **
1866 *******************************************************************************/
1867
btif_media_task_enc_update(BT_HDR * p_msg)1868 static void btif_media_task_enc_update(BT_HDR *p_msg)
1869 {
1870 tBTIF_MEDIA_UPDATE_AUDIO * pUpdateAudio = (tBTIF_MEDIA_UPDATE_AUDIO *) p_msg;
1871 SBC_ENC_PARAMS *pstrEncParams = &btif_media_cb.encoder;
1872 UINT16 s16SamplingFreq;
1873 SINT16 s16BitPool = 0;
1874 SINT16 s16BitRate;
1875 SINT16 s16FrameLen;
1876 UINT8 protect = 0;
1877
1878 APPL_TRACE_DEBUG("%s : minmtu %d, maxbp %d minbp %d", __func__,
1879 pUpdateAudio->MinMtuSize, pUpdateAudio->MaxBitPool,
1880 pUpdateAudio->MinBitPool);
1881
1882 if (!pstrEncParams->s16NumOfSubBands)
1883 {
1884 APPL_TRACE_WARNING("%s SubBands are set to 0, resetting to max (%d)",
1885 __func__, SBC_MAX_NUM_OF_SUBBANDS);
1886 pstrEncParams->s16NumOfSubBands = SBC_MAX_NUM_OF_SUBBANDS;
1887 }
1888
1889 if (!pstrEncParams->s16NumOfBlocks)
1890 {
1891 APPL_TRACE_WARNING("%s Blocks are set to 0, resetting to max (%d)",
1892 __func__, SBC_MAX_NUM_OF_BLOCKS);
1893 pstrEncParams->s16NumOfBlocks = SBC_MAX_NUM_OF_BLOCKS;
1894 }
1895
1896 if (!pstrEncParams->s16NumOfChannels)
1897 {
1898 APPL_TRACE_WARNING("%s Channels are set to 0, resetting to max (%d)",
1899 __func__, SBC_MAX_NUM_OF_CHANNELS);
1900 pstrEncParams->s16NumOfChannels = SBC_MAX_NUM_OF_CHANNELS;
1901 }
1902
1903 btif_media_cb.TxAaMtuSize = ((BTIF_MEDIA_AA_BUF_SIZE -
1904 BTIF_MEDIA_AA_SBC_OFFSET - sizeof(BT_HDR))
1905 < pUpdateAudio->MinMtuSize) ? (BTIF_MEDIA_AA_BUF_SIZE - BTIF_MEDIA_AA_SBC_OFFSET
1906 - sizeof(BT_HDR)) : pUpdateAudio->MinMtuSize;
1907
1908 /* Set the initial target bit rate */
1909 pstrEncParams->u16BitRate = btif_media_task_get_sbc_rate();
1910
1911 if (pstrEncParams->s16SamplingFreq == SBC_sf16000)
1912 s16SamplingFreq = 16000;
1913 else if (pstrEncParams->s16SamplingFreq == SBC_sf32000)
1914 s16SamplingFreq = 32000;
1915 else if (pstrEncParams->s16SamplingFreq == SBC_sf44100)
1916 s16SamplingFreq = 44100;
1917 else
1918 s16SamplingFreq = 48000;
1919
1920 do {
1921 if (pstrEncParams->s16NumOfBlocks == 0 ||
1922 pstrEncParams->s16NumOfSubBands == 0 ||
1923 pstrEncParams->s16NumOfChannels == 0) {
1924 APPL_TRACE_ERROR("%s - Avoiding division by zero...", __func__);
1925 APPL_TRACE_ERROR("%s - block=%d, subBands=%d, channels=%d",
1926 __func__,
1927 pstrEncParams->s16NumOfBlocks,
1928 pstrEncParams->s16NumOfSubBands,
1929 pstrEncParams->s16NumOfChannels);
1930 break;
1931 }
1932
1933 if ((pstrEncParams->s16ChannelMode == SBC_JOINT_STEREO) ||
1934 (pstrEncParams->s16ChannelMode == SBC_STEREO)) {
1935 s16BitPool = (SINT16)((pstrEncParams->u16BitRate *
1936 pstrEncParams->s16NumOfSubBands * 1000 / s16SamplingFreq)
1937 - ((32 + (4 * pstrEncParams->s16NumOfSubBands *
1938 pstrEncParams->s16NumOfChannels)
1939 + ((pstrEncParams->s16ChannelMode - 2) *
1940 pstrEncParams->s16NumOfSubBands))
1941 / pstrEncParams->s16NumOfBlocks));
1942
1943 s16FrameLen = 4 + (4*pstrEncParams->s16NumOfSubBands *
1944 pstrEncParams->s16NumOfChannels) / 8
1945 + (((pstrEncParams->s16ChannelMode - 2) *
1946 pstrEncParams->s16NumOfSubBands)
1947 + (pstrEncParams->s16NumOfBlocks * s16BitPool)) / 8;
1948
1949 s16BitRate = (8 * s16FrameLen * s16SamplingFreq)
1950 / (pstrEncParams->s16NumOfSubBands *
1951 pstrEncParams->s16NumOfBlocks * 1000);
1952
1953 if (s16BitRate > pstrEncParams->u16BitRate)
1954 s16BitPool--;
1955
1956 if (pstrEncParams->s16NumOfSubBands == 8)
1957 s16BitPool = (s16BitPool > 255) ? 255 : s16BitPool;
1958 else
1959 s16BitPool = (s16BitPool > 128) ? 128 : s16BitPool;
1960 } else {
1961 s16BitPool = (SINT16)(((pstrEncParams->s16NumOfSubBands *
1962 pstrEncParams->u16BitRate * 1000)
1963 / (s16SamplingFreq * pstrEncParams->s16NumOfChannels))
1964 - (((32 / pstrEncParams->s16NumOfChannels) +
1965 (4 * pstrEncParams->s16NumOfSubBands))
1966 / pstrEncParams->s16NumOfBlocks));
1967
1968 pstrEncParams->s16BitPool =
1969 (s16BitPool > (16 * pstrEncParams->s16NumOfSubBands)) ?
1970 (16 * pstrEncParams->s16NumOfSubBands) : s16BitPool;
1971 }
1972
1973 if (s16BitPool < 0)
1974 s16BitPool = 0;
1975
1976 APPL_TRACE_EVENT("%s bitpool candidate : %d (%d kbps)", __func__,
1977 s16BitPool, pstrEncParams->u16BitRate);
1978
1979 if (s16BitPool > pUpdateAudio->MaxBitPool) {
1980 APPL_TRACE_DEBUG("%s computed bitpool too large (%d)", __func__,
1981 s16BitPool);
1982 /* Decrease bitrate */
1983 btif_media_cb.encoder.u16BitRate -= BTIF_MEDIA_BITRATE_STEP;
1984 /* Record that we have decreased the bitrate */
1985 protect |= 1;
1986 } else if (s16BitPool < pUpdateAudio->MinBitPool) {
1987 APPL_TRACE_WARNING("%s computed bitpool too small (%d)", __func__,
1988 s16BitPool);
1989
1990 /* Increase bitrate */
1991 UINT16 previous_u16BitRate = btif_media_cb.encoder.u16BitRate;
1992 btif_media_cb.encoder.u16BitRate += BTIF_MEDIA_BITRATE_STEP;
1993 /* Record that we have increased the bitrate */
1994 protect |= 2;
1995 /* Check over-flow */
1996 if (btif_media_cb.encoder.u16BitRate < previous_u16BitRate)
1997 protect |= 3;
1998 } else {
1999 break;
2000 }
2001 /* In case we have already increased and decreased the bitrate, just stop */
2002 if (protect == 3) {
2003 APPL_TRACE_ERROR("%s could not find bitpool in range", __func__);
2004 break;
2005 }
2006 } while (1);
2007
2008 /* Finally update the bitpool in the encoder structure */
2009 pstrEncParams->s16BitPool = s16BitPool;
2010
2011 APPL_TRACE_DEBUG("%s final bit rate %d, final bit pool %d", __func__,
2012 btif_media_cb.encoder.u16BitRate,
2013 btif_media_cb.encoder.s16BitPool);
2014
2015 /* make sure we reinitialize encoder with new settings */
2016 SBC_Encoder_Init(&(btif_media_cb.encoder));
2017
2018 btif_media_cb.tx_sbc_frames = calculate_max_frames_per_packet();
2019 }
2020
2021 /*******************************************************************************
2022 **
2023 ** Function btif_media_task_pcm2sbc_init
2024 **
2025 ** Description Init encoding task for PCM to SBC according to feeding
2026 **
2027 ** Returns void
2028 **
2029 *******************************************************************************/
btif_media_task_pcm2sbc_init(tBTIF_MEDIA_INIT_AUDIO_FEEDING * p_feeding)2030 static void btif_media_task_pcm2sbc_init(tBTIF_MEDIA_INIT_AUDIO_FEEDING * p_feeding)
2031 {
2032 BOOLEAN reconfig_needed = FALSE;
2033
2034 APPL_TRACE_DEBUG("PCM feeding:");
2035 APPL_TRACE_DEBUG("sampling_freq:%d", p_feeding->feeding.cfg.pcm.sampling_freq);
2036 APPL_TRACE_DEBUG("num_channel:%d", p_feeding->feeding.cfg.pcm.num_channel);
2037 APPL_TRACE_DEBUG("bit_per_sample:%d", p_feeding->feeding.cfg.pcm.bit_per_sample);
2038
2039 /* Check the PCM feeding sampling_freq */
2040 switch (p_feeding->feeding.cfg.pcm.sampling_freq)
2041 {
2042 case 8000:
2043 case 12000:
2044 case 16000:
2045 case 24000:
2046 case 32000:
2047 case 48000:
2048 /* For these sampling_freq the AV connection must be 48000 */
2049 if (btif_media_cb.encoder.s16SamplingFreq != SBC_sf48000)
2050 {
2051 /* Reconfiguration needed at 48000 */
2052 APPL_TRACE_DEBUG("SBC Reconfiguration needed at 48000");
2053 btif_media_cb.encoder.s16SamplingFreq = SBC_sf48000;
2054 reconfig_needed = TRUE;
2055 }
2056 break;
2057
2058 case 11025:
2059 case 22050:
2060 case 44100:
2061 /* For these sampling_freq the AV connection must be 44100 */
2062 if (btif_media_cb.encoder.s16SamplingFreq != SBC_sf44100)
2063 {
2064 /* Reconfiguration needed at 44100 */
2065 APPL_TRACE_DEBUG("SBC Reconfiguration needed at 44100");
2066 btif_media_cb.encoder.s16SamplingFreq = SBC_sf44100;
2067 reconfig_needed = TRUE;
2068 }
2069 break;
2070 default:
2071 APPL_TRACE_DEBUG("Feeding PCM sampling_freq unsupported");
2072 break;
2073 }
2074
2075 /* Some AV Headsets do not support Mono => always ask for Stereo */
2076 if (btif_media_cb.encoder.s16ChannelMode == SBC_MONO)
2077 {
2078 APPL_TRACE_DEBUG("SBC Reconfiguration needed in Stereo");
2079 btif_media_cb.encoder.s16ChannelMode = SBC_JOINT_STEREO;
2080 reconfig_needed = TRUE;
2081 }
2082
2083 if (reconfig_needed != FALSE)
2084 {
2085 APPL_TRACE_DEBUG("btif_media_task_pcm2sbc_init :: mtu %d", btif_media_cb.TxAaMtuSize);
2086 APPL_TRACE_DEBUG("ch mode %d, nbsubd %d, nb %d, alloc %d, rate %d, freq %d",
2087 btif_media_cb.encoder.s16ChannelMode,
2088 btif_media_cb.encoder.s16NumOfSubBands, btif_media_cb.encoder.s16NumOfBlocks,
2089 btif_media_cb.encoder.s16AllocationMethod, btif_media_cb.encoder.u16BitRate,
2090 btif_media_cb.encoder.s16SamplingFreq);
2091
2092 SBC_Encoder_Init(&(btif_media_cb.encoder));
2093 }
2094 else
2095 {
2096 APPL_TRACE_DEBUG("btif_media_task_pcm2sbc_init no SBC reconfig needed");
2097 }
2098 }
2099
2100
2101 /*******************************************************************************
2102 **
2103 ** Function btif_media_task_audio_feeding_init
2104 **
2105 ** Description Initialize the audio path according to the feeding format
2106 **
2107 ** Returns void
2108 **
2109 *******************************************************************************/
btif_media_task_audio_feeding_init(BT_HDR * p_msg)2110 static void btif_media_task_audio_feeding_init(BT_HDR *p_msg)
2111 {
2112 tBTIF_MEDIA_INIT_AUDIO_FEEDING *p_feeding = (tBTIF_MEDIA_INIT_AUDIO_FEEDING *) p_msg;
2113
2114 APPL_TRACE_DEBUG("btif_media_task_audio_feeding_init format:%d", p_feeding->feeding.format);
2115
2116 /* Save Media Feeding information */
2117 btif_media_cb.feeding_mode = p_feeding->feeding_mode;
2118 btif_media_cb.media_feeding = p_feeding->feeding;
2119
2120 /* Handle different feeding formats */
2121 switch (p_feeding->feeding.format)
2122 {
2123 case BTIF_AV_CODEC_PCM:
2124 btif_media_cb.TxTranscoding = BTIF_MEDIA_TRSCD_PCM_2_SBC;
2125 btif_media_task_pcm2sbc_init(p_feeding);
2126 break;
2127
2128 default :
2129 APPL_TRACE_ERROR("unknown feeding format %d", p_feeding->feeding.format);
2130 break;
2131 }
2132 }
2133
btif_a2dp_get_track_frequency(UINT8 frequency)2134 int btif_a2dp_get_track_frequency(UINT8 frequency) {
2135 int freq = 48000;
2136 switch (frequency) {
2137 case A2D_SBC_IE_SAMP_FREQ_16:
2138 freq = 16000;
2139 break;
2140 case A2D_SBC_IE_SAMP_FREQ_32:
2141 freq = 32000;
2142 break;
2143 case A2D_SBC_IE_SAMP_FREQ_44:
2144 freq = 44100;
2145 break;
2146 case A2D_SBC_IE_SAMP_FREQ_48:
2147 freq = 48000;
2148 break;
2149 }
2150 return freq;
2151 }
2152
btif_a2dp_get_track_channel_count(UINT8 channeltype)2153 int btif_a2dp_get_track_channel_count(UINT8 channeltype) {
2154 int count = 1;
2155 switch (channeltype) {
2156 case A2D_SBC_IE_CH_MD_MONO:
2157 count = 1;
2158 break;
2159 case A2D_SBC_IE_CH_MD_DUAL:
2160 case A2D_SBC_IE_CH_MD_STEREO:
2161 case A2D_SBC_IE_CH_MD_JOINT:
2162 count = 2;
2163 break;
2164 }
2165 return count;
2166 }
2167
2168 #ifdef USE_AUDIO_TRACK
a2dp_get_track_channel_type(UINT8 channeltype)2169 int a2dp_get_track_channel_type(UINT8 channeltype) {
2170 int count = 1;
2171 switch (channeltype) {
2172 case A2D_SBC_IE_CH_MD_MONO:
2173 count = 1;
2174 break;
2175 case A2D_SBC_IE_CH_MD_DUAL:
2176 case A2D_SBC_IE_CH_MD_STEREO:
2177 case A2D_SBC_IE_CH_MD_JOINT:
2178 count = 3;
2179 break;
2180 }
2181 return count;
2182 }
2183 #endif
2184
btif_a2dp_set_peer_sep(UINT8 sep)2185 void btif_a2dp_set_peer_sep(UINT8 sep) {
2186 btif_media_cb.peer_sep = sep;
2187 }
2188
btif_decode_alarm_cb(UNUSED_ATTR void * context)2189 static void btif_decode_alarm_cb(UNUSED_ATTR void *context) {
2190 if(worker_thread != NULL)
2191 thread_post(worker_thread, btif_media_task_avk_handle_timer, NULL);
2192 }
2193
btif_media_task_aa_handle_stop_decoding(void)2194 static void btif_media_task_aa_handle_stop_decoding(void) {
2195 alarm_free(btif_media_cb.decode_alarm);
2196 btif_media_cb.decode_alarm = NULL;
2197 #ifdef USE_AUDIO_TRACK
2198 BtifAvrcpAudioTrackPause(btif_media_cb.audio_track);
2199 #endif
2200 }
2201
btif_media_task_aa_handle_start_decoding(void)2202 static void btif_media_task_aa_handle_start_decoding(void) {
2203 if (btif_media_cb.decode_alarm)
2204 return;
2205 #ifdef USE_AUDIO_TRACK
2206 BtifAvrcpAudioTrackStart(btif_media_cb.audio_track);
2207 #endif
2208 btif_media_cb.decode_alarm = alarm_new_periodic("btif.media_decode");
2209 if (!btif_media_cb.decode_alarm) {
2210 LOG_ERROR(LOG_TAG, "%s unable to allocate decode alarm.", __func__);
2211 return;
2212 }
2213
2214 alarm_set(btif_media_cb.decode_alarm, BTIF_SINK_MEDIA_TIME_TICK_MS,
2215 btif_decode_alarm_cb, NULL);
2216 }
2217
2218 #if (BTA_AV_SINK_INCLUDED == TRUE)
2219
btif_media_task_aa_handle_clear_track(void)2220 static void btif_media_task_aa_handle_clear_track (void)
2221 {
2222 APPL_TRACE_DEBUG("btif_media_task_aa_handle_clear_track");
2223 #ifdef USE_AUDIO_TRACK
2224 BtifAvrcpAudioTrackStop(btif_media_cb.audio_track);
2225 BtifAvrcpAudioTrackDelete(btif_media_cb.audio_track);
2226 btif_media_cb.audio_track = NULL;
2227 #endif
2228 }
2229
2230 /*******************************************************************************
2231 **
2232 ** Function btif_media_task_aa_handle_decoder_reset
2233 **
2234 ** Description
2235 **
2236 ** Returns void
2237 **
2238 *******************************************************************************/
btif_media_task_aa_handle_decoder_reset(BT_HDR * p_msg)2239 static void btif_media_task_aa_handle_decoder_reset(BT_HDR *p_msg)
2240 {
2241 tBTIF_MEDIA_SINK_CFG_UPDATE *p_buf = (tBTIF_MEDIA_SINK_CFG_UPDATE*) p_msg;
2242 tA2D_STATUS a2d_status;
2243 tA2D_SBC_CIE sbc_cie;
2244 OI_STATUS status;
2245 UINT32 freq_multiple = 48*20; /* frequency multiple for 20ms of data , initialize with 48K*/
2246 UINT32 num_blocks = 16;
2247 UINT32 num_subbands = 8;
2248
2249 APPL_TRACE_DEBUG("btif_media_task_aa_handle_decoder_reset p_codec_info[%x:%x:%x:%x:%x:%x]",
2250 p_buf->codec_info[1], p_buf->codec_info[2], p_buf->codec_info[3],
2251 p_buf->codec_info[4], p_buf->codec_info[5], p_buf->codec_info[6]);
2252
2253 a2d_status = A2D_ParsSbcInfo(&sbc_cie, p_buf->codec_info, FALSE);
2254 if (a2d_status != A2D_SUCCESS)
2255 {
2256 APPL_TRACE_ERROR("ERROR dump_codec_info A2D_ParsSbcInfo fail:%d", a2d_status);
2257 return;
2258 }
2259
2260 btif_media_cb.sample_rate = btif_a2dp_get_track_frequency(sbc_cie.samp_freq);
2261 btif_media_cb.channel_count = btif_a2dp_get_track_channel_count(sbc_cie.ch_mode);
2262
2263 btif_media_cb.rx_flush = FALSE;
2264 APPL_TRACE_DEBUG("Reset to sink role");
2265 status = OI_CODEC_SBC_DecoderReset(&context, contextData, sizeof(contextData), 2, 2, FALSE);
2266 if (!OI_SUCCESS(status)) {
2267 APPL_TRACE_ERROR("OI_CODEC_SBC_DecoderReset failed with error code %d\n", status);
2268 }
2269
2270 #ifdef USE_AUDIO_TRACK
2271 APPL_TRACE_DEBUG("%s A2dpSink: sbc Create Track", __func__);
2272 btif_media_cb.audio_track =
2273 BtifAvrcpAudioTrackCreate(btif_a2dp_get_track_frequency(sbc_cie.samp_freq),
2274 a2dp_get_track_channel_type(sbc_cie.ch_mode));
2275 if (btif_media_cb.audio_track == NULL) {
2276 APPL_TRACE_ERROR("%s A2dpSink: Track creation fails!!!", __func__);
2277 return;
2278 }
2279 #else
2280 UIPC_Open(UIPC_CH_ID_AV_AUDIO, btif_a2dp_data_cb);
2281 #endif
2282
2283 switch (sbc_cie.samp_freq)
2284 {
2285 case A2D_SBC_IE_SAMP_FREQ_16:
2286 APPL_TRACE_DEBUG("\tsamp_freq:%d (16000)", sbc_cie.samp_freq);
2287 freq_multiple = 16*20;
2288 break;
2289 case A2D_SBC_IE_SAMP_FREQ_32:
2290 APPL_TRACE_DEBUG("\tsamp_freq:%d (32000)", sbc_cie.samp_freq);
2291 freq_multiple = 32*20;
2292 break;
2293 case A2D_SBC_IE_SAMP_FREQ_44:
2294 APPL_TRACE_DEBUG("\tsamp_freq:%d (44100)", sbc_cie.samp_freq);
2295 freq_multiple = 441*2;
2296 break;
2297 case A2D_SBC_IE_SAMP_FREQ_48:
2298 APPL_TRACE_DEBUG("\tsamp_freq:%d (48000)", sbc_cie.samp_freq);
2299 freq_multiple = 48*20;
2300 break;
2301 default:
2302 APPL_TRACE_DEBUG(" Unknown Frequency ");
2303 break;
2304 }
2305
2306 switch (sbc_cie.ch_mode)
2307 {
2308 case A2D_SBC_IE_CH_MD_MONO:
2309 APPL_TRACE_DEBUG("\tch_mode:%d (Mono)", sbc_cie.ch_mode);
2310 break;
2311 case A2D_SBC_IE_CH_MD_DUAL:
2312 APPL_TRACE_DEBUG("\tch_mode:%d (DUAL)", sbc_cie.ch_mode);
2313 break;
2314 case A2D_SBC_IE_CH_MD_STEREO:
2315 APPL_TRACE_DEBUG("\tch_mode:%d (STEREO)", sbc_cie.ch_mode);
2316 break;
2317 case A2D_SBC_IE_CH_MD_JOINT:
2318 APPL_TRACE_DEBUG("\tch_mode:%d (JOINT)", sbc_cie.ch_mode);
2319 break;
2320 default:
2321 APPL_TRACE_DEBUG(" Unknown Mode ");
2322 break;
2323 }
2324
2325 switch (sbc_cie.block_len)
2326 {
2327 case A2D_SBC_IE_BLOCKS_4:
2328 APPL_TRACE_DEBUG("\tblock_len:%d (4)", sbc_cie.block_len);
2329 num_blocks = 4;
2330 break;
2331 case A2D_SBC_IE_BLOCKS_8:
2332 APPL_TRACE_DEBUG("\tblock_len:%d (8)", sbc_cie.block_len);
2333 num_blocks = 8;
2334 break;
2335 case A2D_SBC_IE_BLOCKS_12:
2336 APPL_TRACE_DEBUG("\tblock_len:%d (12)", sbc_cie.block_len);
2337 num_blocks = 12;
2338 break;
2339 case A2D_SBC_IE_BLOCKS_16:
2340 APPL_TRACE_DEBUG("\tblock_len:%d (16)", sbc_cie.block_len);
2341 num_blocks = 16;
2342 break;
2343 default:
2344 APPL_TRACE_DEBUG(" Unknown BlockLen ");
2345 break;
2346 }
2347
2348 switch (sbc_cie.num_subbands)
2349 {
2350 case A2D_SBC_IE_SUBBAND_4:
2351 APPL_TRACE_DEBUG("\tnum_subbands:%d (4)", sbc_cie.num_subbands);
2352 num_subbands = 4;
2353 break;
2354 case A2D_SBC_IE_SUBBAND_8:
2355 APPL_TRACE_DEBUG("\tnum_subbands:%d (8)", sbc_cie.num_subbands);
2356 num_subbands = 8;
2357 break;
2358 default:
2359 APPL_TRACE_DEBUG(" Unknown SubBands ");
2360 break;
2361 }
2362
2363 switch (sbc_cie.alloc_mthd)
2364 {
2365 case A2D_SBC_IE_ALLOC_MD_S:
2366 APPL_TRACE_DEBUG("\talloc_mthd:%d (SNR)", sbc_cie.alloc_mthd);
2367 break;
2368 case A2D_SBC_IE_ALLOC_MD_L:
2369 APPL_TRACE_DEBUG("\talloc_mthd:%d (Loudness)", sbc_cie.alloc_mthd);
2370 break;
2371 default:
2372 APPL_TRACE_DEBUG(" Unknown Allocation Method");
2373 break;
2374 }
2375
2376 APPL_TRACE_DEBUG("\tBit pool Min:%d Max:%d", sbc_cie.min_bitpool, sbc_cie.max_bitpool);
2377
2378 btif_media_cb.frames_to_process = ((freq_multiple)/(num_blocks*num_subbands)) + 1;
2379 APPL_TRACE_DEBUG(" Frames to be processed in 20 ms %d",btif_media_cb.frames_to_process);
2380 }
2381 #endif
2382
2383 /*******************************************************************************
2384 **
2385 ** Function btif_media_task_feeding_state_reset
2386 **
2387 ** Description Reset the media feeding state
2388 **
2389 ** Returns void
2390 **
2391 *******************************************************************************/
btif_media_task_feeding_state_reset(void)2392 static void btif_media_task_feeding_state_reset(void)
2393 {
2394 /* By default, just clear the entire state */
2395 memset(&btif_media_cb.media_feeding_state, 0, sizeof(btif_media_cb.media_feeding_state));
2396
2397 if (btif_media_cb.TxTranscoding == BTIF_MEDIA_TRSCD_PCM_2_SBC)
2398 {
2399 btif_media_cb.media_feeding_state.pcm.bytes_per_tick =
2400 (btif_media_cb.media_feeding.cfg.pcm.sampling_freq *
2401 btif_media_cb.media_feeding.cfg.pcm.bit_per_sample / 8 *
2402 btif_media_cb.media_feeding.cfg.pcm.num_channel *
2403 BTIF_MEDIA_TIME_TICK)/1000;
2404
2405 APPL_TRACE_WARNING("pcm bytes per tick %d",
2406 (int)btif_media_cb.media_feeding_state.pcm.bytes_per_tick);
2407 }
2408 }
2409
btif_media_task_alarm_cb(UNUSED_ATTR void * context)2410 static void btif_media_task_alarm_cb(UNUSED_ATTR void *context) {
2411 thread_post(worker_thread, btif_media_task_aa_handle_timer, NULL);
2412 }
2413
2414 /*******************************************************************************
2415 **
2416 ** Function btif_media_task_aa_start_tx
2417 **
2418 ** Description Start media task encoding
2419 **
2420 ** Returns void
2421 **
2422 *******************************************************************************/
btif_media_task_aa_start_tx(void)2423 static void btif_media_task_aa_start_tx(void)
2424 {
2425 APPL_TRACE_DEBUG("%s media_alarm %srunning, feeding mode %d", __func__,
2426 alarm_is_scheduled(btif_media_cb.media_alarm)? "" : "not ",
2427 btif_media_cb.feeding_mode);
2428
2429 last_frame_us = 0;
2430
2431 /* Reset the media feeding state */
2432 btif_media_task_feeding_state_reset();
2433
2434 APPL_TRACE_EVENT("starting timer %dms", BTIF_MEDIA_TIME_TICK);
2435
2436 alarm_free(btif_media_cb.media_alarm);
2437 btif_media_cb.media_alarm = alarm_new_periodic("btif.media_task");
2438 if (!btif_media_cb.media_alarm) {
2439 LOG_ERROR(LOG_TAG, "%s unable to allocate media alarm.", __func__);
2440 return;
2441 }
2442
2443 alarm_set(btif_media_cb.media_alarm, BTIF_MEDIA_TIME_TICK,
2444 btif_media_task_alarm_cb, NULL);
2445 }
2446
2447 /*******************************************************************************
2448 **
2449 ** Function btif_media_task_aa_stop_tx
2450 **
2451 ** Description Stop media task encoding
2452 **
2453 ** Returns void
2454 **
2455 *******************************************************************************/
btif_media_task_aa_stop_tx(void)2456 static void btif_media_task_aa_stop_tx(void)
2457 {
2458 APPL_TRACE_DEBUG("%s media_alarm is %srunning", __func__,
2459 alarm_is_scheduled(btif_media_cb.media_alarm)? "" : "not ");
2460
2461 const bool send_ack = alarm_is_scheduled(btif_media_cb.media_alarm);
2462
2463 /* Stop the timer first */
2464 alarm_free(btif_media_cb.media_alarm);
2465 btif_media_cb.media_alarm = NULL;
2466
2467 UIPC_Close(UIPC_CH_ID_AV_AUDIO);
2468
2469 /* Try to send acknowldegment once the media stream is
2470 stopped. This will make sure that the A2DP HAL layer is
2471 un-blocked on wait for acknowledgment for the sent command.
2472 This resolves a corner cases AVDTP SUSPEND collision
2473 when the DUT and the remote device issue SUSPEND simultaneously
2474 and due to the processing of the SUSPEND request from the remote,
2475 the media path is torn down. If the A2DP HAL happens to wait
2476 for ACK for the initiated SUSPEND, it would never receive it casuing
2477 a block/wait. Due to this acknowledgement, the A2DP HAL is guranteed
2478 to get the ACK for any pending command in such cases. */
2479
2480 if (send_ack)
2481 a2dp_cmd_acknowledge(A2DP_CTRL_ACK_SUCCESS);
2482
2483 /* audio engine stopped, reset tx suspended flag */
2484 btif_media_cb.tx_flush = 0;
2485 last_frame_us = 0;
2486
2487 /* Reset the media feeding state */
2488 btif_media_task_feeding_state_reset();
2489 }
2490
get_frame_length()2491 static UINT32 get_frame_length()
2492 {
2493 UINT32 frame_len = 0;
2494 APPL_TRACE_DEBUG("%s channel mode: %d, sub-band: %d, number of block: %d, \
2495 bitpool: %d, sampling frequency: %d, num channels: %d",
2496 __func__,
2497 btif_media_cb.encoder.s16ChannelMode,
2498 btif_media_cb.encoder.s16NumOfSubBands,
2499 btif_media_cb.encoder.s16NumOfBlocks,
2500 btif_media_cb.encoder.s16BitPool,
2501 btif_media_cb.encoder.s16SamplingFreq,
2502 btif_media_cb.encoder.s16NumOfChannels);
2503
2504 switch (btif_media_cb.encoder.s16ChannelMode) {
2505 case SBC_MONO:
2506 /* FALLTHROUGH */
2507 case SBC_DUAL:
2508 frame_len = SBC_FRAME_HEADER_SIZE_BYTES +
2509 ((UINT32)(SBC_SCALE_FACTOR_BITS * btif_media_cb.encoder.s16NumOfSubBands *
2510 btif_media_cb.encoder.s16NumOfChannels) / CHAR_BIT) +
2511 ((UINT32)(btif_media_cb.encoder.s16NumOfBlocks *
2512 btif_media_cb.encoder.s16NumOfChannels *
2513 btif_media_cb.encoder.s16BitPool) / CHAR_BIT);
2514 break;
2515 case SBC_STEREO:
2516 frame_len = SBC_FRAME_HEADER_SIZE_BYTES +
2517 ((UINT32)(SBC_SCALE_FACTOR_BITS * btif_media_cb.encoder.s16NumOfSubBands *
2518 btif_media_cb.encoder.s16NumOfChannels) / CHAR_BIT) +
2519 ((UINT32)(btif_media_cb.encoder.s16NumOfBlocks *
2520 btif_media_cb.encoder.s16BitPool) / CHAR_BIT);
2521 break;
2522 case SBC_JOINT_STEREO:
2523 frame_len = SBC_FRAME_HEADER_SIZE_BYTES +
2524 ((UINT32)(SBC_SCALE_FACTOR_BITS * btif_media_cb.encoder.s16NumOfSubBands *
2525 btif_media_cb.encoder.s16NumOfChannels) / CHAR_BIT) +
2526 ((UINT32)(btif_media_cb.encoder.s16NumOfSubBands +
2527 (btif_media_cb.encoder.s16NumOfBlocks *
2528 btif_media_cb.encoder.s16BitPool)) / CHAR_BIT);
2529 break;
2530 default:
2531 APPL_TRACE_DEBUG("%s Invalid channel number: %d",
2532 __func__, btif_media_cb.encoder.s16ChannelMode);
2533 break;
2534 }
2535 APPL_TRACE_DEBUG("%s calculated frame length: %d", __func__, frame_len);
2536 return frame_len;
2537 }
2538
calculate_max_frames_per_packet()2539 static UINT8 calculate_max_frames_per_packet()
2540 {
2541 UINT16 result = 0;
2542 UINT16 effective_mtu_size = btif_media_cb.TxAaMtuSize;
2543 UINT32 frame_len;
2544
2545 APPL_TRACE_DEBUG("%s original AVDTP MTU size: %d", __func__, btif_media_cb.TxAaMtuSize);
2546 if (btif_av_is_peer_edr() && (btif_av_peer_supports_3mbps() == FALSE)) {
2547 // This condition would be satisfied only if the remote device is
2548 // EDR and supports only 2 Mbps, but the effective AVDTP MTU size
2549 // exceeds the 2DH5 packet size.
2550 APPL_TRACE_DEBUG("%s The remote devce is EDR but does not support 3 Mbps", __func__);
2551
2552 if (effective_mtu_size > MAX_2MBPS_AVDTP_MTU) {
2553 APPL_TRACE_WARNING("%s Restricting AVDTP MTU size to %d",
2554 __func__, MAX_2MBPS_AVDTP_MTU);
2555 effective_mtu_size = MAX_2MBPS_AVDTP_MTU;
2556 btif_media_cb.TxAaMtuSize = effective_mtu_size;
2557 }
2558 }
2559
2560 if (!btif_media_cb.encoder.s16NumOfSubBands) {
2561 APPL_TRACE_ERROR("%s SubBands are set to 0, resetting to %d",
2562 __func__, SBC_MAX_NUM_OF_SUBBANDS);
2563 btif_media_cb.encoder.s16NumOfSubBands = SBC_MAX_NUM_OF_SUBBANDS;
2564 }
2565 if (!btif_media_cb.encoder.s16NumOfBlocks) {
2566 APPL_TRACE_ERROR("%s Blocks are set to 0, resetting to %d",
2567 __func__, SBC_MAX_NUM_OF_BLOCKS);
2568 btif_media_cb.encoder.s16NumOfBlocks = SBC_MAX_NUM_OF_BLOCKS;
2569 }
2570 if (!btif_media_cb.encoder.s16NumOfChannels) {
2571 APPL_TRACE_ERROR("%s Channels are set to 0, resetting to %d",
2572 __func__, SBC_MAX_NUM_OF_CHANNELS);
2573 btif_media_cb.encoder.s16NumOfChannels = SBC_MAX_NUM_OF_CHANNELS;
2574 }
2575
2576 frame_len = get_frame_length();
2577
2578 APPL_TRACE_DEBUG("%s Effective Tx MTU to be considered: %d",
2579 __func__, effective_mtu_size);
2580
2581 switch (btif_media_cb.encoder.s16SamplingFreq) {
2582 case SBC_sf44100:
2583 if (frame_len == 0) {
2584 APPL_TRACE_ERROR("%s Calculating frame length, \
2585 resetting it to default 119", __func__);
2586 frame_len = MAX_SBC_HQ_FRAME_SIZE_44_1;
2587 }
2588 result = (effective_mtu_size - A2DP_HDR_SIZE) / frame_len;
2589 APPL_TRACE_DEBUG("%s Max number of SBC frames: %d", __func__, result);
2590 break;
2591
2592 case SBC_sf48000:
2593 if (frame_len == 0) {
2594 APPL_TRACE_ERROR("%s Calculating frame length, \
2595 resetting it to default 115", __func__);
2596 frame_len = MAX_SBC_HQ_FRAME_SIZE_48;
2597 }
2598 result = (effective_mtu_size - A2DP_HDR_SIZE) / frame_len;
2599 APPL_TRACE_DEBUG("%s Max number of SBC frames: %d", __func__, result);
2600 break;
2601
2602 default:
2603 APPL_TRACE_ERROR("%s Max number of SBC frames: %d", __func__, result);
2604 break;
2605
2606 }
2607 return result;
2608 }
2609
2610 /*******************************************************************************
2611 **
2612 ** Function btif_get_num_aa_frame_iteration
2613 **
2614 ** Description returns number of frames to send and number of iterations
2615 ** to be used. num_of_ietrations and num_of_frames parameters
2616 ** are used as output param for returning the respective values
2617 **
2618 ** Returns void
2619 **
2620 *******************************************************************************/
btif_get_num_aa_frame_iteration(UINT8 * num_of_iterations,UINT8 * num_of_frames)2621 static void btif_get_num_aa_frame_iteration(UINT8 *num_of_iterations, UINT8 *num_of_frames)
2622 {
2623 UINT8 nof = 0;
2624 UINT8 noi = 1;
2625
2626 switch (btif_media_cb.TxTranscoding)
2627 {
2628 case BTIF_MEDIA_TRSCD_PCM_2_SBC:
2629 {
2630 UINT32 projected_nof = 0;
2631 UINT32 pcm_bytes_per_frame = btif_media_cb.encoder.s16NumOfSubBands *
2632 btif_media_cb.encoder.s16NumOfBlocks *
2633 btif_media_cb.media_feeding.cfg.pcm.num_channel *
2634 btif_media_cb.media_feeding.cfg.pcm.bit_per_sample / 8;
2635 APPL_TRACE_DEBUG("%s pcm_bytes_per_frame %u", __func__, pcm_bytes_per_frame);
2636
2637 UINT32 us_this_tick = BTIF_MEDIA_TIME_TICK * 1000;
2638 UINT64 now_us = time_now_us();
2639 if (last_frame_us != 0)
2640 us_this_tick = (now_us - last_frame_us);
2641 last_frame_us = now_us;
2642
2643 btif_media_cb.media_feeding_state.pcm.counter +=
2644 btif_media_cb.media_feeding_state.pcm.bytes_per_tick *
2645 us_this_tick / (BTIF_MEDIA_TIME_TICK * 1000);
2646
2647 /* calculate nbr of frames pending for this media tick */
2648 projected_nof = btif_media_cb.media_feeding_state.pcm.counter / pcm_bytes_per_frame;
2649 if (projected_nof > btif_media_cb.stats.media_read_max_expected_frames)
2650 btif_media_cb.stats.media_read_max_expected_frames = projected_nof;
2651 btif_media_cb.stats.media_read_total_expected_frames += projected_nof;
2652 btif_media_cb.stats.media_read_expected_count++;
2653 if (projected_nof > MAX_PCM_FRAME_NUM_PER_TICK)
2654 {
2655 APPL_TRACE_WARNING("%s() - Limiting frames to be sent from %d to %d"
2656 , __FUNCTION__, projected_nof, MAX_PCM_FRAME_NUM_PER_TICK);
2657 size_t delta = projected_nof - MAX_PCM_FRAME_NUM_PER_TICK;
2658 btif_media_cb.stats.media_read_limited_count++;
2659 btif_media_cb.stats.media_read_total_limited_frames += delta;
2660 if (delta > btif_media_cb.stats.media_read_max_limited_frames)
2661 btif_media_cb.stats.media_read_max_limited_frames = delta;
2662 projected_nof = MAX_PCM_FRAME_NUM_PER_TICK;
2663 }
2664
2665 APPL_TRACE_DEBUG("%s frames for available PCM data %u", __func__, projected_nof);
2666
2667 if (btif_av_is_peer_edr())
2668 {
2669 if (!btif_media_cb.tx_sbc_frames)
2670 {
2671 APPL_TRACE_ERROR("%s tx_sbc_frames not updated, update from here", __func__);
2672 btif_media_cb.tx_sbc_frames = calculate_max_frames_per_packet();
2673 }
2674
2675 nof = btif_media_cb.tx_sbc_frames;
2676 if (!nof) {
2677 APPL_TRACE_ERROR("%s Number of frames not updated, set calculated values",
2678 __func__);
2679 nof = projected_nof;
2680 noi = 1;
2681 } else {
2682 if (nof < projected_nof)
2683 {
2684 noi = projected_nof / nof; // number of iterations would vary
2685 if (noi > MAX_PCM_ITER_NUM_PER_TICK)
2686 {
2687 APPL_TRACE_ERROR("%s ## Audio Congestion (iterations:%d > max (%d))",
2688 __func__, noi, MAX_PCM_ITER_NUM_PER_TICK);
2689 noi = MAX_PCM_ITER_NUM_PER_TICK;
2690 btif_media_cb.media_feeding_state.pcm.counter
2691 = noi * nof * pcm_bytes_per_frame;
2692 }
2693 projected_nof = nof;
2694 } else {
2695 noi = 1; // number of iterations is 1
2696 APPL_TRACE_DEBUG("%s reducing frames for available PCM data", __func__);
2697 nof = projected_nof;
2698 }
2699 }
2700 } else {
2701 // For BR cases nof will be same as the value retrieved at projected_nof
2702 APPL_TRACE_DEBUG("%s headset BR, number of frames %u", __func__, nof);
2703 if (projected_nof > MAX_PCM_FRAME_NUM_PER_TICK)
2704 {
2705 APPL_TRACE_ERROR("%s ## Audio Congestion (frames: %d > max (%d))",
2706 __func__, projected_nof, MAX_PCM_FRAME_NUM_PER_TICK);
2707 projected_nof = MAX_PCM_FRAME_NUM_PER_TICK;
2708 btif_media_cb.media_feeding_state.pcm.counter =
2709 noi * projected_nof * pcm_bytes_per_frame;
2710 }
2711 nof = projected_nof;
2712 }
2713 btif_media_cb.media_feeding_state.pcm.counter -= noi * nof * pcm_bytes_per_frame;
2714 APPL_TRACE_DEBUG("%s effective num of frames %u, iterations %u", __func__, nof, noi);
2715 }
2716 break;
2717
2718 default:
2719 APPL_TRACE_ERROR("%s Unsupported transcoding format 0x%x",
2720 __func__, btif_media_cb.TxTranscoding);
2721 nof = 0;
2722 noi = 0;
2723 break;
2724 }
2725 *num_of_frames = nof;
2726 *num_of_iterations = noi;
2727 }
2728
2729 /*******************************************************************************
2730 **
2731 ** Function btif_media_sink_enque_buf
2732 **
2733 ** Description This function is called by the av_co to fill A2DP Sink Queue
2734 **
2735 **
2736 ** Returns size of the queue
2737 *******************************************************************************/
btif_media_sink_enque_buf(BT_HDR * p_pkt)2738 UINT8 btif_media_sink_enque_buf(BT_HDR *p_pkt)
2739 {
2740 if (btif_media_cb.rx_flush == TRUE) /* Flush enabled, do not enque */
2741 return fixed_queue_length(btif_media_cb.RxSbcQ);
2742 if (fixed_queue_length(btif_media_cb.RxSbcQ) == MAX_OUTPUT_A2DP_FRAME_QUEUE_SZ)
2743 {
2744 UINT8 ret = fixed_queue_length(btif_media_cb.RxSbcQ);
2745 osi_free(fixed_queue_try_dequeue(btif_media_cb.RxSbcQ));
2746 return ret;
2747 }
2748
2749 BTIF_TRACE_VERBOSE("%s +", __func__);
2750 /* allocate and Queue this buffer */
2751 tBT_SBC_HDR *p_msg =
2752 (tBT_SBC_HDR *)osi_malloc(sizeof(tBT_SBC_HDR) + p_pkt->offset +
2753 p_pkt->len);
2754 memcpy((UINT8 *)(p_msg + 1), (UINT8 *)(p_pkt + 1) + p_pkt->offset,
2755 p_pkt->len);
2756 p_msg->num_frames_to_be_processed = (*((UINT8 *)(p_pkt + 1) + p_pkt->offset))& 0x0f;
2757 p_msg->len = p_pkt->len;
2758 p_msg->offset = 0;
2759 p_msg->layer_specific = p_pkt->layer_specific;
2760 BTIF_TRACE_VERBOSE("%s frames to process %d, len %d ",
2761 __func__, p_msg->num_frames_to_be_processed,p_msg->len);
2762 fixed_queue_enqueue(btif_media_cb.RxSbcQ, p_msg);
2763 if (fixed_queue_length(btif_media_cb.RxSbcQ) == MAX_A2DP_DELAYED_START_FRAME_COUNT) {
2764 BTIF_TRACE_DEBUG(" Initiate Decoding ");
2765 btif_media_task_aa_handle_start_decoding();
2766 }
2767
2768 return fixed_queue_length(btif_media_cb.RxSbcQ);
2769 }
2770
2771 /*******************************************************************************
2772 **
2773 ** Function btif_media_aa_readbuf
2774 **
2775 ** Description This function is called by the av_co to get the next buffer to send
2776 **
2777 **
2778 ** Returns void
2779 *******************************************************************************/
btif_media_aa_readbuf(void)2780 BT_HDR *btif_media_aa_readbuf(void)
2781 {
2782 uint64_t now_us = time_now_us();
2783 BT_HDR *p_buf = fixed_queue_try_dequeue(btif_media_cb.TxAaQ);
2784
2785 btif_media_cb.stats.tx_queue_total_readbuf_calls++;
2786 btif_media_cb.stats.tx_queue_last_readbuf_us = now_us;
2787 if (p_buf != NULL) {
2788 // Update the statistics
2789 update_scheduling_stats(&btif_media_cb.stats.tx_queue_dequeue_stats,
2790 now_us, BTIF_SINK_MEDIA_TIME_TICK_MS * 1000);
2791 }
2792
2793 return p_buf;
2794 }
2795
2796 /*******************************************************************************
2797 **
2798 ** Function btif_media_aa_read_feeding
2799 **
2800 ** Description
2801 **
2802 ** Returns void
2803 **
2804 *******************************************************************************/
2805
btif_media_aa_read_feeding(tUIPC_CH_ID channel_id)2806 BOOLEAN btif_media_aa_read_feeding(tUIPC_CH_ID channel_id)
2807 {
2808 UINT16 event;
2809 UINT16 blocm_x_subband = btif_media_cb.encoder.s16NumOfSubBands * \
2810 btif_media_cb.encoder.s16NumOfBlocks;
2811 UINT32 read_size;
2812 UINT16 sbc_sampling = 48000;
2813 UINT32 src_samples;
2814 UINT16 bytes_needed = blocm_x_subband * btif_media_cb.encoder.s16NumOfChannels * \
2815 btif_media_cb.media_feeding.cfg.pcm.bit_per_sample / 8;
2816 static UINT16 up_sampled_buffer[SBC_MAX_NUM_FRAME * SBC_MAX_NUM_OF_BLOCKS
2817 * SBC_MAX_NUM_OF_CHANNELS * SBC_MAX_NUM_OF_SUBBANDS * 2];
2818 static UINT16 read_buffer[SBC_MAX_NUM_FRAME * SBC_MAX_NUM_OF_BLOCKS
2819 * SBC_MAX_NUM_OF_CHANNELS * SBC_MAX_NUM_OF_SUBBANDS];
2820 UINT32 src_size_used;
2821 UINT32 dst_size_used;
2822 BOOLEAN fract_needed;
2823 INT32 fract_max;
2824 INT32 fract_threshold;
2825 UINT32 nb_byte_read;
2826
2827 /* Get the SBC sampling rate */
2828 switch (btif_media_cb.encoder.s16SamplingFreq)
2829 {
2830 case SBC_sf48000:
2831 sbc_sampling = 48000;
2832 break;
2833 case SBC_sf44100:
2834 sbc_sampling = 44100;
2835 break;
2836 case SBC_sf32000:
2837 sbc_sampling = 32000;
2838 break;
2839 case SBC_sf16000:
2840 sbc_sampling = 16000;
2841 break;
2842 }
2843
2844 if (sbc_sampling == btif_media_cb.media_feeding.cfg.pcm.sampling_freq) {
2845 read_size = bytes_needed - btif_media_cb.media_feeding_state.pcm.aa_feed_residue;
2846 nb_byte_read = UIPC_Read(channel_id, &event,
2847 ((UINT8 *)btif_media_cb.encoder.as16PcmBuffer) +
2848 btif_media_cb.media_feeding_state.pcm.aa_feed_residue,
2849 read_size);
2850 if (nb_byte_read == read_size) {
2851 btif_media_cb.media_feeding_state.pcm.aa_feed_residue = 0;
2852 return TRUE;
2853 } else {
2854 APPL_TRACE_WARNING("### UNDERFLOW :: ONLY READ %d BYTES OUT OF %d ###",
2855 nb_byte_read, read_size);
2856 btif_media_cb.media_feeding_state.pcm.aa_feed_residue += nb_byte_read;
2857 btif_media_cb.stats.media_read_total_underflow_bytes += (read_size - nb_byte_read);
2858 btif_media_cb.stats.media_read_total_underflow_count++;
2859 btif_media_cb.stats.media_read_last_underflow_us = time_now_us();
2860 return FALSE;
2861 }
2862 }
2863
2864 /* Some Feeding PCM frequencies require to split the number of sample */
2865 /* to read. */
2866 /* E.g 128/6=21.3333 => read 22 and 21 and 21 => max = 2; threshold = 0*/
2867 fract_needed = FALSE; /* Default */
2868 switch (btif_media_cb.media_feeding.cfg.pcm.sampling_freq)
2869 {
2870 case 32000:
2871 case 8000:
2872 fract_needed = TRUE;
2873 fract_max = 2; /* 0, 1 and 2 */
2874 fract_threshold = 0; /* Add one for the first */
2875 break;
2876 case 16000:
2877 fract_needed = TRUE;
2878 fract_max = 2; /* 0, 1 and 2 */
2879 fract_threshold = 1; /* Add one for the first two frames*/
2880 break;
2881 }
2882
2883 /* Compute number of sample to read from source */
2884 src_samples = blocm_x_subband;
2885 src_samples *= btif_media_cb.media_feeding.cfg.pcm.sampling_freq;
2886 src_samples /= sbc_sampling;
2887
2888 /* The previous division may have a remainder not null */
2889 if (fract_needed)
2890 {
2891 if (btif_media_cb.media_feeding_state.pcm.aa_feed_counter <= fract_threshold)
2892 {
2893 src_samples++; /* for every read before threshold add one sample */
2894 }
2895
2896 /* do nothing if counter >= threshold */
2897 btif_media_cb.media_feeding_state.pcm.aa_feed_counter++; /* one more read */
2898 if (btif_media_cb.media_feeding_state.pcm.aa_feed_counter > fract_max)
2899 {
2900 btif_media_cb.media_feeding_state.pcm.aa_feed_counter = 0;
2901 }
2902 }
2903
2904 /* Compute number of bytes to read from source */
2905 read_size = src_samples;
2906 read_size *= btif_media_cb.media_feeding.cfg.pcm.num_channel;
2907 read_size *= (btif_media_cb.media_feeding.cfg.pcm.bit_per_sample / 8);
2908
2909 /* Read Data from UIPC channel */
2910 nb_byte_read = UIPC_Read(channel_id, &event, (UINT8 *)read_buffer, read_size);
2911
2912 //tput_mon(TRUE, nb_byte_read, FALSE);
2913
2914 if (nb_byte_read < read_size)
2915 {
2916 APPL_TRACE_WARNING("### UNDERRUN :: ONLY READ %d BYTES OUT OF %d ###",
2917 nb_byte_read, read_size);
2918 btif_media_cb.stats.media_read_total_underrun_bytes += (read_size - nb_byte_read);
2919 btif_media_cb.stats.media_read_total_underrun_count++;
2920 btif_media_cb.stats.media_read_last_underrun_us = time_now_us();
2921
2922 if (nb_byte_read == 0)
2923 return FALSE;
2924
2925 if(btif_media_cb.feeding_mode == BTIF_AV_FEEDING_ASYNCHRONOUS)
2926 {
2927 /* Fill the unfilled part of the read buffer with silence (0) */
2928 memset(((UINT8 *)read_buffer) + nb_byte_read, 0, read_size - nb_byte_read);
2929 nb_byte_read = read_size;
2930 }
2931 }
2932
2933 /* Initialize PCM up-sampling engine */
2934 bta_av_sbc_init_up_sample(btif_media_cb.media_feeding.cfg.pcm.sampling_freq,
2935 sbc_sampling, btif_media_cb.media_feeding.cfg.pcm.bit_per_sample,
2936 btif_media_cb.media_feeding.cfg.pcm.num_channel);
2937
2938 /* re-sample read buffer */
2939 /* The output PCM buffer will be stereo, 16 bit per sample */
2940 dst_size_used = bta_av_sbc_up_sample((UINT8 *)read_buffer,
2941 (UINT8 *)up_sampled_buffer + btif_media_cb.media_feeding_state.pcm.aa_feed_residue,
2942 nb_byte_read,
2943 sizeof(up_sampled_buffer) - btif_media_cb.media_feeding_state.pcm.aa_feed_residue,
2944 &src_size_used);
2945
2946 /* update the residue */
2947 btif_media_cb.media_feeding_state.pcm.aa_feed_residue += dst_size_used;
2948
2949 /* only copy the pcm sample when we have up-sampled enough PCM */
2950 if(btif_media_cb.media_feeding_state.pcm.aa_feed_residue >= bytes_needed)
2951 {
2952 /* Copy the output pcm samples in SBC encoding buffer */
2953 memcpy((UINT8 *)btif_media_cb.encoder.as16PcmBuffer,
2954 (UINT8 *)up_sampled_buffer,
2955 bytes_needed);
2956 /* update the residue */
2957 btif_media_cb.media_feeding_state.pcm.aa_feed_residue -= bytes_needed;
2958
2959 if (btif_media_cb.media_feeding_state.pcm.aa_feed_residue != 0)
2960 {
2961 memcpy((UINT8 *)up_sampled_buffer,
2962 (UINT8 *)up_sampled_buffer + bytes_needed,
2963 btif_media_cb.media_feeding_state.pcm.aa_feed_residue);
2964 }
2965 return TRUE;
2966 }
2967
2968 return FALSE;
2969 }
2970
2971 /*******************************************************************************
2972 **
2973 ** Function btif_media_aa_prep_sbc_2_send
2974 **
2975 ** Description
2976 **
2977 ** Returns void
2978 **
2979 *******************************************************************************/
btif_media_aa_prep_sbc_2_send(UINT8 nb_frame,uint64_t timestamp_us)2980 static void btif_media_aa_prep_sbc_2_send(UINT8 nb_frame,
2981 uint64_t timestamp_us)
2982 {
2983 uint8_t remain_nb_frame = nb_frame;
2984 UINT16 blocm_x_subband = btif_media_cb.encoder.s16NumOfSubBands *
2985 btif_media_cb.encoder.s16NumOfBlocks;
2986
2987 while (nb_frame) {
2988 BT_HDR *p_buf = osi_malloc(BTIF_MEDIA_AA_BUF_SIZE);
2989
2990 /* Init buffer */
2991 p_buf->offset = BTIF_MEDIA_AA_SBC_OFFSET;
2992 p_buf->len = 0;
2993 p_buf->layer_specific = 0;
2994
2995 do
2996 {
2997 /* Write @ of allocated buffer in encoder.pu8Packet */
2998 btif_media_cb.encoder.pu8Packet = (UINT8 *) (p_buf + 1) + p_buf->offset + p_buf->len;
2999 /* Fill allocated buffer with 0 */
3000 memset(btif_media_cb.encoder.as16PcmBuffer, 0, blocm_x_subband
3001 * btif_media_cb.encoder.s16NumOfChannels);
3002
3003 /* Read PCM data and upsample them if needed */
3004 if (btif_media_aa_read_feeding(UIPC_CH_ID_AV_AUDIO))
3005 {
3006 SBC_Encoder(&(btif_media_cb.encoder));
3007
3008 /* Update SBC frame length */
3009 p_buf->len += btif_media_cb.encoder.u16PacketLength;
3010 nb_frame--;
3011 p_buf->layer_specific++;
3012 }
3013 else
3014 {
3015 APPL_TRACE_WARNING("btif_media_aa_prep_sbc_2_send underflow %d, %d",
3016 nb_frame, btif_media_cb.media_feeding_state.pcm.aa_feed_residue);
3017 btif_media_cb.media_feeding_state.pcm.counter += nb_frame *
3018 btif_media_cb.encoder.s16NumOfSubBands *
3019 btif_media_cb.encoder.s16NumOfBlocks *
3020 btif_media_cb.media_feeding.cfg.pcm.num_channel *
3021 btif_media_cb.media_feeding.cfg.pcm.bit_per_sample / 8;
3022 /* no more pcm to read */
3023 nb_frame = 0;
3024
3025 /* break read loop if timer was stopped (media task stopped) */
3026 if (! alarm_is_scheduled(btif_media_cb.media_alarm))
3027 {
3028 osi_free(p_buf);
3029 return;
3030 }
3031 }
3032
3033 } while (((p_buf->len + btif_media_cb.encoder.u16PacketLength) < btif_media_cb.TxAaMtuSize)
3034 && (p_buf->layer_specific < 0x0F) && nb_frame);
3035
3036 if(p_buf->len)
3037 {
3038 /* timestamp of the media packet header represent the TS of the first SBC frame
3039 i.e the timestamp before including this frame */
3040 *((UINT32 *) (p_buf + 1)) = btif_media_cb.timestamp;
3041
3042 btif_media_cb.timestamp += p_buf->layer_specific * blocm_x_subband;
3043
3044 if (btif_media_cb.tx_flush)
3045 {
3046 APPL_TRACE_DEBUG("### tx suspended, discarded frame ###");
3047
3048 btif_media_cb.stats.tx_queue_total_flushed_messages +=
3049 fixed_queue_length(btif_media_cb.TxAaQ);
3050 btif_media_cb.stats.tx_queue_last_flushed_us =
3051 timestamp_us;
3052 btif_media_flush_q(btif_media_cb.TxAaQ);
3053
3054 osi_free(p_buf);
3055 return;
3056 }
3057
3058 /* Enqueue the encoded SBC frame in AA Tx Queue */
3059 update_scheduling_stats(&btif_media_cb.stats.tx_queue_enqueue_stats,
3060 timestamp_us,
3061 BTIF_SINK_MEDIA_TIME_TICK_MS * 1000);
3062 uint8_t done_nb_frame = remain_nb_frame - nb_frame;
3063 remain_nb_frame = nb_frame;
3064 btif_media_cb.stats.tx_queue_total_frames += done_nb_frame;
3065 if (done_nb_frame > btif_media_cb.stats.tx_queue_max_frames_per_packet)
3066 btif_media_cb.stats.tx_queue_max_frames_per_packet = done_nb_frame;
3067 fixed_queue_enqueue(btif_media_cb.TxAaQ, p_buf);
3068 }
3069 else
3070 {
3071 osi_free(p_buf);
3072 }
3073 }
3074 }
3075
3076
3077 /*******************************************************************************
3078 **
3079 ** Function btif_media_aa_prep_2_send
3080 **
3081 ** Description
3082 **
3083 ** Returns void
3084 **
3085 *******************************************************************************/
3086
btif_media_aa_prep_2_send(UINT8 nb_frame,uint64_t timestamp_us)3087 static void btif_media_aa_prep_2_send(UINT8 nb_frame, uint64_t timestamp_us)
3088 {
3089 // Check for TX queue overflow
3090
3091 if (nb_frame > MAX_OUTPUT_A2DP_FRAME_QUEUE_SZ)
3092 nb_frame = MAX_OUTPUT_A2DP_FRAME_QUEUE_SZ;
3093
3094 if (fixed_queue_length(btif_media_cb.TxAaQ) > (MAX_OUTPUT_A2DP_FRAME_QUEUE_SZ - nb_frame))
3095 {
3096 APPL_TRACE_WARNING("%s() - TX queue buffer count %d/%d", __func__,
3097 fixed_queue_length(btif_media_cb.TxAaQ),
3098 MAX_OUTPUT_A2DP_FRAME_QUEUE_SZ - nb_frame);
3099 btif_media_cb.stats.tx_queue_dropouts++;
3100 btif_media_cb.stats.tx_queue_last_dropouts_us = timestamp_us;
3101
3102 while (fixed_queue_length(btif_media_cb.TxAaQ)) {
3103 btif_media_cb.stats.tx_queue_total_dropped_messages++;
3104 osi_free(fixed_queue_try_dequeue(btif_media_cb.TxAaQ));
3105 }
3106 }
3107
3108 // Transcode frame
3109
3110 switch (btif_media_cb.TxTranscoding)
3111 {
3112 case BTIF_MEDIA_TRSCD_PCM_2_SBC:
3113 btif_media_aa_prep_sbc_2_send(nb_frame, timestamp_us);
3114 break;
3115
3116 default:
3117 APPL_TRACE_ERROR("%s unsupported transcoding format 0x%x", __func__, btif_media_cb.TxTranscoding);
3118 break;
3119 }
3120 }
3121
3122 /*******************************************************************************
3123 **
3124 ** Function btif_media_send_aa_frame
3125 **
3126 ** Description
3127 **
3128 ** Returns void
3129 **
3130 *******************************************************************************/
btif_media_send_aa_frame(uint64_t timestamp_us)3131 static void btif_media_send_aa_frame(uint64_t timestamp_us)
3132 {
3133 UINT8 nb_frame_2_send = 0;
3134 UINT8 nb_iterations = 0;
3135
3136 btif_get_num_aa_frame_iteration(&nb_iterations, &nb_frame_2_send);
3137
3138 if (nb_frame_2_send != 0) {
3139 for (UINT8 counter = 0; counter < nb_iterations; counter++)
3140 {
3141 /* format and queue buffer to send */
3142 btif_media_aa_prep_2_send(nb_frame_2_send, timestamp_us);
3143 }
3144 }
3145
3146 LOG_VERBOSE(LOG_TAG, "%s Sent %d frames per iteration, %d iterations",
3147 __func__, nb_frame_2_send, nb_iterations);
3148 bta_av_ci_src_data_ready(BTA_AV_CHNL_AUDIO);
3149 }
3150
3151 #endif /* BTA_AV_INCLUDED == TRUE */
3152
3153 /*******************************************************************************
3154 **
3155 ** Function dump_codec_info
3156 **
3157 ** Description Decode and display codec_info (for debug)
3158 **
3159 ** Returns void
3160 **
3161 *******************************************************************************/
dump_codec_info(unsigned char * p_codec)3162 void dump_codec_info(unsigned char *p_codec)
3163 {
3164 tA2D_STATUS a2d_status;
3165 tA2D_SBC_CIE sbc_cie;
3166
3167 a2d_status = A2D_ParsSbcInfo(&sbc_cie, p_codec, FALSE);
3168 if (a2d_status != A2D_SUCCESS)
3169 {
3170 APPL_TRACE_ERROR("ERROR dump_codec_info A2D_ParsSbcInfo fail:%d", a2d_status);
3171 return;
3172 }
3173
3174 APPL_TRACE_DEBUG("dump_codec_info");
3175
3176 if (sbc_cie.samp_freq == A2D_SBC_IE_SAMP_FREQ_16)
3177 { APPL_TRACE_DEBUG("\tsamp_freq:%d (16000)", sbc_cie.samp_freq);}
3178 else if (sbc_cie.samp_freq == A2D_SBC_IE_SAMP_FREQ_32)
3179 { APPL_TRACE_DEBUG("\tsamp_freq:%d (32000)", sbc_cie.samp_freq);}
3180 else if (sbc_cie.samp_freq == A2D_SBC_IE_SAMP_FREQ_44)
3181 { APPL_TRACE_DEBUG("\tsamp_freq:%d (44.100)", sbc_cie.samp_freq);}
3182 else if (sbc_cie.samp_freq == A2D_SBC_IE_SAMP_FREQ_48)
3183 { APPL_TRACE_DEBUG("\tsamp_freq:%d (48000)", sbc_cie.samp_freq);}
3184 else
3185 { APPL_TRACE_DEBUG("\tBAD samp_freq:%d", sbc_cie.samp_freq);}
3186
3187 if (sbc_cie.ch_mode == A2D_SBC_IE_CH_MD_MONO)
3188 { APPL_TRACE_DEBUG("\tch_mode:%d (Mono)", sbc_cie.ch_mode);}
3189 else if (sbc_cie.ch_mode == A2D_SBC_IE_CH_MD_DUAL)
3190 { APPL_TRACE_DEBUG("\tch_mode:%d (Dual)", sbc_cie.ch_mode);}
3191 else if (sbc_cie.ch_mode == A2D_SBC_IE_CH_MD_STEREO)
3192 { APPL_TRACE_DEBUG("\tch_mode:%d (Stereo)", sbc_cie.ch_mode);}
3193 else if (sbc_cie.ch_mode == A2D_SBC_IE_CH_MD_JOINT)
3194 { APPL_TRACE_DEBUG("\tch_mode:%d (Joint)", sbc_cie.ch_mode);}
3195 else
3196 { APPL_TRACE_DEBUG("\tBAD ch_mode:%d", sbc_cie.ch_mode);}
3197
3198 if (sbc_cie.block_len == A2D_SBC_IE_BLOCKS_4)
3199 { APPL_TRACE_DEBUG("\tblock_len:%d (4)", sbc_cie.block_len);}
3200 else if (sbc_cie.block_len == A2D_SBC_IE_BLOCKS_8)
3201 { APPL_TRACE_DEBUG("\tblock_len:%d (8)", sbc_cie.block_len);}
3202 else if (sbc_cie.block_len == A2D_SBC_IE_BLOCKS_12)
3203 { APPL_TRACE_DEBUG("\tblock_len:%d (12)", sbc_cie.block_len);}
3204 else if (sbc_cie.block_len == A2D_SBC_IE_BLOCKS_16)
3205 { APPL_TRACE_DEBUG("\tblock_len:%d (16)", sbc_cie.block_len);}
3206 else
3207 { APPL_TRACE_DEBUG("\tBAD block_len:%d", sbc_cie.block_len);}
3208
3209 if (sbc_cie.num_subbands == A2D_SBC_IE_SUBBAND_4)
3210 { APPL_TRACE_DEBUG("\tnum_subbands:%d (4)", sbc_cie.num_subbands);}
3211 else if (sbc_cie.num_subbands == A2D_SBC_IE_SUBBAND_8)
3212 { APPL_TRACE_DEBUG("\tnum_subbands:%d (8)", sbc_cie.num_subbands);}
3213 else
3214 { APPL_TRACE_DEBUG("\tBAD num_subbands:%d", sbc_cie.num_subbands);}
3215
3216 if (sbc_cie.alloc_mthd == A2D_SBC_IE_ALLOC_MD_S)
3217 { APPL_TRACE_DEBUG("\talloc_mthd:%d (SNR)", sbc_cie.alloc_mthd);}
3218 else if (sbc_cie.alloc_mthd == A2D_SBC_IE_ALLOC_MD_L)
3219 { APPL_TRACE_DEBUG("\talloc_mthd:%d (Loundess)", sbc_cie.alloc_mthd);}
3220 else
3221 { APPL_TRACE_DEBUG("\tBAD alloc_mthd:%d", sbc_cie.alloc_mthd);}
3222
3223 APPL_TRACE_DEBUG("\tBit pool Min:%d Max:%d", sbc_cie.min_bitpool, sbc_cie.max_bitpool);
3224
3225 }
3226
btif_debug_a2dp_dump(int fd)3227 void btif_debug_a2dp_dump(int fd)
3228 {
3229 uint64_t now_us = time_now_us();
3230 btif_media_stats_t *stats = &btif_media_cb.stats;
3231 scheduling_stats_t *enqueue_stats = &stats->tx_queue_enqueue_stats;
3232 scheduling_stats_t *dequeue_stats = &stats->tx_queue_dequeue_stats;
3233 size_t ave_size;
3234 uint64_t ave_time_us;
3235
3236 dprintf(fd, "\nA2DP State:\n");
3237 dprintf(fd, " TxQueue:\n");
3238
3239 dprintf(fd, " Counts (enqueue/dequeue/readbuf) : %zu / %zu / %zu\n",
3240 enqueue_stats->total_updates,
3241 dequeue_stats->total_updates,
3242 stats->tx_queue_total_readbuf_calls);
3243
3244 dprintf(fd, " Last update time ago in ms (enqueue/dequeue/readbuf) : %llu / %llu / %llu\n",
3245 (enqueue_stats->last_update_us > 0) ?
3246 (unsigned long long)(now_us - enqueue_stats->last_update_us) / 1000 : 0,
3247 (dequeue_stats->last_update_us > 0) ?
3248 (unsigned long long)(now_us - dequeue_stats->last_update_us) / 1000 : 0,
3249 (stats->tx_queue_last_readbuf_us > 0)?
3250 (unsigned long long)(now_us - stats->tx_queue_last_readbuf_us) / 1000 : 0);
3251
3252 ave_size = 0;
3253 if (stats->media_read_expected_count != 0)
3254 ave_size = stats->media_read_total_expected_frames / stats->media_read_expected_count;
3255 dprintf(fd, " Frames expected (total/max/ave) : %zu / %zu / %zu\n",
3256 stats->media_read_total_expected_frames,
3257 stats->media_read_max_expected_frames,
3258 ave_size);
3259
3260 ave_size = 0;
3261 if (stats->media_read_limited_count != 0)
3262 ave_size = stats->media_read_total_limited_frames / stats->media_read_limited_count;
3263 dprintf(fd, " Frames limited (total/max/ave) : %zu / %zu / %zu\n",
3264 stats->media_read_total_limited_frames,
3265 stats->media_read_max_limited_frames,
3266 ave_size);
3267
3268 dprintf(fd, " Counts (expected/limited) : %zu / %zu\n",
3269 stats->media_read_expected_count,
3270 stats->media_read_limited_count);
3271
3272 ave_size = 0;
3273 if (enqueue_stats->total_updates != 0)
3274 ave_size = stats->tx_queue_total_frames / enqueue_stats->total_updates;
3275 dprintf(fd, " Frames per packet (total/max/ave) : %zu / %zu / %zu\n",
3276 stats->tx_queue_total_frames,
3277 stats->tx_queue_max_frames_per_packet,
3278 ave_size);
3279
3280 dprintf(fd, " Counts (flushed/dropped/dropouts) : %zu / %zu / %zu\n",
3281 stats->tx_queue_total_flushed_messages,
3282 stats->tx_queue_total_dropped_messages,
3283 stats->tx_queue_dropouts);
3284
3285 dprintf(fd, " Last update time ago in ms (flushed/dropped) : %llu / %llu\n",
3286 (stats->tx_queue_last_flushed_us > 0) ?
3287 (unsigned long long)(now_us - stats->tx_queue_last_flushed_us) / 1000 : 0,
3288 (stats->tx_queue_last_dropouts_us > 0)?
3289 (unsigned long long)(now_us - stats->tx_queue_last_dropouts_us)/ 1000 : 0);
3290
3291 dprintf(fd, " Counts (underflow/underrun) : %zu / %zu\n",
3292 stats->media_read_total_underflow_count,
3293 stats->media_read_total_underrun_count);
3294
3295 dprintf(fd, " Bytes (underflow/underrun) : %zu / %zu\n",
3296 stats->media_read_total_underflow_bytes,
3297 stats->media_read_total_underrun_bytes);
3298
3299 dprintf(fd, " Last update time ago in ms (underflow/underrun) : %llu / %llu\n",
3300 (stats->media_read_last_underflow_us > 0) ?
3301 (unsigned long long)(now_us - stats->media_read_last_underflow_us) / 1000 : 0,
3302 (stats->media_read_last_underrun_us > 0)?
3303 (unsigned long long)(now_us - stats->media_read_last_underrun_us) / 1000 : 0);
3304
3305 //
3306 // TxQueue enqueue stats
3307 //
3308 dprintf(fd, " Enqueue deviation counts (overdue/premature) : %zu / %zu\n",
3309 enqueue_stats->overdue_scheduling_count,
3310 enqueue_stats->premature_scheduling_count);
3311
3312 ave_time_us = 0;
3313 if (enqueue_stats->overdue_scheduling_count != 0) {
3314 ave_time_us = enqueue_stats->total_overdue_scheduling_delta_us /
3315 enqueue_stats->overdue_scheduling_count;
3316 }
3317 dprintf(fd, " Enqueue overdue scheduling time in ms (total/max/ave) : %llu / %llu / %llu\n",
3318 (unsigned long long)enqueue_stats->total_overdue_scheduling_delta_us / 1000,
3319 (unsigned long long)enqueue_stats->max_overdue_scheduling_delta_us / 1000,
3320 (unsigned long long)ave_time_us / 1000);
3321
3322 ave_time_us = 0;
3323 if (enqueue_stats->premature_scheduling_count != 0) {
3324 ave_time_us = enqueue_stats->total_premature_scheduling_delta_us /
3325 enqueue_stats->premature_scheduling_count;
3326 }
3327 dprintf(fd, " Enqueue premature scheduling time in ms (total/max/ave) : %llu / %llu / %llu\n",
3328 (unsigned long long)enqueue_stats->total_premature_scheduling_delta_us / 1000,
3329 (unsigned long long)enqueue_stats->max_premature_scheduling_delta_us / 1000,
3330 (unsigned long long)ave_time_us / 1000);
3331
3332
3333 //
3334 // TxQueue dequeue stats
3335 //
3336 dprintf(fd, " Dequeue deviation counts (overdue/premature) : %zu / %zu\n",
3337 dequeue_stats->overdue_scheduling_count,
3338 dequeue_stats->premature_scheduling_count);
3339
3340 ave_time_us = 0;
3341 if (dequeue_stats->overdue_scheduling_count != 0) {
3342 ave_time_us = dequeue_stats->total_overdue_scheduling_delta_us /
3343 dequeue_stats->overdue_scheduling_count;
3344 }
3345 dprintf(fd, " Dequeue overdue scheduling time in ms (total/max/ave) : %llu / %llu / %llu\n",
3346 (unsigned long long)dequeue_stats->total_overdue_scheduling_delta_us / 1000,
3347 (unsigned long long)dequeue_stats->max_overdue_scheduling_delta_us / 1000,
3348 (unsigned long long)ave_time_us / 1000);
3349
3350 ave_time_us = 0;
3351 if (dequeue_stats->premature_scheduling_count != 0) {
3352 ave_time_us = dequeue_stats->total_premature_scheduling_delta_us /
3353 dequeue_stats->premature_scheduling_count;
3354 }
3355 dprintf(fd, " Dequeue premature scheduling time in ms (total/max/ave) : %llu / %llu / %llu\n",
3356 (unsigned long long)dequeue_stats->total_premature_scheduling_delta_us / 1000,
3357 (unsigned long long)dequeue_stats->max_premature_scheduling_delta_us / 1000,
3358 (unsigned long long)ave_time_us / 1000);
3359
3360 }
3361
btif_update_a2dp_metrics(void)3362 void btif_update_a2dp_metrics(void)
3363 {
3364 uint64_t now_us = time_now_us();
3365 btif_media_stats_t *stats = &btif_media_cb.stats;
3366 scheduling_stats_t *dequeue_stats = &stats->tx_queue_dequeue_stats;
3367 int32_t media_timer_min_ms = 0;
3368 int32_t media_timer_max_ms = 0;
3369 int32_t media_timer_avg_ms = 0;
3370 int32_t buffer_overruns_max_count = 0;
3371 int32_t buffer_overruns_total = 0;
3372 float buffer_underruns_average = 0.0;
3373 int32_t buffer_underruns_count = 0;
3374
3375 int64_t session_duration_sec =
3376 (now_us - stats->session_start_us) / (1000 * 1000);
3377
3378 /* NOTE: Disconnect reason is unused */
3379 const char *disconnect_reason = NULL;
3380 uint32_t device_class = BTM_COD_MAJOR_AUDIO;
3381
3382 if (dequeue_stats->total_updates > 1) {
3383 media_timer_min_ms = BTIF_SINK_MEDIA_TIME_TICK_MS -
3384 (dequeue_stats->max_premature_scheduling_delta_us / 1000);
3385 media_timer_max_ms = BTIF_SINK_MEDIA_TIME_TICK_MS +
3386 (dequeue_stats->max_overdue_scheduling_delta_us / 1000);
3387
3388 uint64_t total_scheduling_count =
3389 dequeue_stats->overdue_scheduling_count +
3390 dequeue_stats->premature_scheduling_count +
3391 dequeue_stats->exact_scheduling_count;
3392 if (total_scheduling_count > 0) {
3393 media_timer_avg_ms = dequeue_stats->total_scheduling_time_us /
3394 (1000 * total_scheduling_count);
3395 }
3396
3397 buffer_overruns_max_count = stats->media_read_max_expected_frames;
3398 buffer_overruns_total = stats->tx_queue_total_dropped_messages;
3399 buffer_underruns_count = stats->media_read_total_underflow_count +
3400 stats->media_read_total_underrun_count;
3401 if (buffer_underruns_count > 0) {
3402 buffer_underruns_average =
3403 (stats->media_read_total_underflow_bytes + stats->media_read_total_underrun_bytes) / buffer_underruns_count;
3404 }
3405 }
3406
3407 metrics_a2dp_session(session_duration_sec, disconnect_reason, device_class,
3408 media_timer_min_ms, media_timer_max_ms,
3409 media_timer_avg_ms, buffer_overruns_max_count,
3410 buffer_overruns_total, buffer_underruns_average,
3411 buffer_underruns_count);
3412 }
3413