1 /******************************************************************************
2 *
3 * Copyright 2016 The Android Open Source Project
4 * Copyright 2009-2012 Broadcom Corporation
5 *
6 * Licensed under the Apache License, Version 2.0 (the "License");
7 * you may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at:
9 *
10 * http://www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
17 *
18 ******************************************************************************/
19
20 #define LOG_TAG "bt_btif_a2dp_control"
21
22 #include <base/logging.h>
23 #include <stdbool.h>
24 #include <stdint.h>
25
26 #include "audio_a2dp_hw/include/audio_a2dp_hw.h"
27 #include "bt_common.h"
28 #include "btif_a2dp.h"
29 #include "btif_a2dp_control.h"
30 #include "btif_a2dp_sink.h"
31 #include "btif_a2dp_source.h"
32 #include "btif_av.h"
33 #include "btif_av_co.h"
34 #include "btif_hf.h"
35 #include "osi/include/osi.h"
36 #include "uipc.h"
37
38 #define A2DP_DATA_READ_POLL_MS 10
39
40 struct {
41 uint64_t total_bytes_read = 0;
42 uint16_t audio_delay = 0;
43 struct timespec timestamp = {};
44 } delay_report_stats;
45
46 static void btif_a2dp_data_cb(tUIPC_CH_ID ch_id, tUIPC_EVENT event);
47 static void btif_a2dp_ctrl_cb(tUIPC_CH_ID ch_id, tUIPC_EVENT event);
48
49 /* We can have max one command pending */
50 static tA2DP_CTRL_CMD a2dp_cmd_pending = A2DP_CTRL_CMD_NONE;
51 std::unique_ptr<tUIPC_STATE> a2dp_uipc = nullptr;
52
btif_a2dp_control_init(void)53 void btif_a2dp_control_init(void) {
54 a2dp_uipc = UIPC_Init();
55 UIPC_Open(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, btif_a2dp_ctrl_cb, A2DP_CTRL_PATH);
56 }
57
btif_a2dp_control_cleanup(void)58 void btif_a2dp_control_cleanup(void) {
59 /* This calls blocks until UIPC is fully closed */
60 if (a2dp_uipc != nullptr) {
61 UIPC_Close(*a2dp_uipc, UIPC_CH_ID_ALL);
62 }
63 }
64
btif_a2dp_recv_ctrl_data(void)65 static void btif_a2dp_recv_ctrl_data(void) {
66 tA2DP_CTRL_CMD cmd = A2DP_CTRL_CMD_NONE;
67 int n;
68
69 uint8_t read_cmd = 0; /* The read command size is one octet */
70 n = UIPC_Read(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, NULL, &read_cmd, 1);
71 cmd = static_cast<tA2DP_CTRL_CMD>(read_cmd);
72
73 /* detach on ctrl channel means audioflinger process was terminated */
74 if (n == 0) {
75 APPL_TRACE_WARNING("%s: CTRL CH DETACHED", __func__);
76 UIPC_Close(*a2dp_uipc, UIPC_CH_ID_AV_CTRL);
77 return;
78 }
79
80 // Don't log A2DP_CTRL_GET_PRESENTATION_POSITION by default, because it
81 // could be very chatty when audio is streaming.
82 if (cmd == A2DP_CTRL_GET_PRESENTATION_POSITION) {
83 APPL_TRACE_DEBUG("%s: a2dp-ctrl-cmd : %s", __func__,
84 audio_a2dp_hw_dump_ctrl_event(cmd));
85 } else {
86 APPL_TRACE_WARNING("%s: a2dp-ctrl-cmd : %s", __func__,
87 audio_a2dp_hw_dump_ctrl_event(cmd));
88 }
89
90 a2dp_cmd_pending = cmd;
91 switch (cmd) {
92 case A2DP_CTRL_CMD_CHECK_READY:
93 if (btif_a2dp_source_media_task_is_shutting_down()) {
94 APPL_TRACE_WARNING("%s: A2DP command %s while media task shutting down",
95 __func__, audio_a2dp_hw_dump_ctrl_event(cmd));
96 btif_a2dp_command_ack(A2DP_CTRL_ACK_FAILURE);
97 return;
98 }
99
100 /* check whether AV is ready to setup A2DP datapath */
101 if (btif_av_stream_ready() || btif_av_stream_started_ready()) {
102 btif_a2dp_command_ack(A2DP_CTRL_ACK_SUCCESS);
103 } else {
104 APPL_TRACE_WARNING("%s: A2DP command %s while AV stream is not ready",
105 __func__, audio_a2dp_hw_dump_ctrl_event(cmd));
106 btif_a2dp_command_ack(A2DP_CTRL_ACK_FAILURE);
107 }
108 break;
109
110 case A2DP_CTRL_CMD_START:
111 /*
112 * Don't send START request to stack while we are in a call.
113 * Some headsets such as "Sony MW600", don't allow AVDTP START
114 * while in a call, and respond with BAD_STATE.
115 */
116 if (!bluetooth::headset::IsCallIdle()) {
117 APPL_TRACE_WARNING("%s: A2DP command %s while call state is busy",
118 __func__, audio_a2dp_hw_dump_ctrl_event(cmd));
119 btif_a2dp_command_ack(A2DP_CTRL_ACK_INCALL_FAILURE);
120 break;
121 }
122
123 if (btif_a2dp_source_is_streaming()) {
124 APPL_TRACE_WARNING("%s: A2DP command %s while source is streaming",
125 __func__, audio_a2dp_hw_dump_ctrl_event(cmd));
126 btif_a2dp_command_ack(A2DP_CTRL_ACK_FAILURE);
127 break;
128 }
129
130 if (btif_av_stream_ready()) {
131 /* Setup audio data channel listener */
132 UIPC_Open(*a2dp_uipc, UIPC_CH_ID_AV_AUDIO, btif_a2dp_data_cb,
133 A2DP_DATA_PATH);
134
135 /*
136 * Post start event and wait for audio path to open.
137 * If we are the source, the ACK will be sent after the start
138 * procedure is completed, othewise send it now.
139 */
140 btif_av_stream_start();
141 if (btif_av_get_peer_sep() == AVDT_TSEP_SRC)
142 btif_a2dp_command_ack(A2DP_CTRL_ACK_SUCCESS);
143 break;
144 }
145
146 if (btif_av_stream_started_ready()) {
147 /*
148 * Already started, setup audio data channel listener and ACK
149 * back immediately.
150 */
151 UIPC_Open(*a2dp_uipc, UIPC_CH_ID_AV_AUDIO, btif_a2dp_data_cb,
152 A2DP_DATA_PATH);
153 btif_a2dp_command_ack(A2DP_CTRL_ACK_SUCCESS);
154 break;
155 }
156 APPL_TRACE_WARNING("%s: A2DP command %s while AV stream is not ready",
157 __func__, audio_a2dp_hw_dump_ctrl_event(cmd));
158 btif_a2dp_command_ack(A2DP_CTRL_ACK_FAILURE);
159 break;
160
161 case A2DP_CTRL_CMD_STOP:
162 if (btif_av_get_peer_sep() == AVDT_TSEP_SNK &&
163 !btif_a2dp_source_is_streaming()) {
164 /* We are already stopped, just ack back */
165 btif_a2dp_command_ack(A2DP_CTRL_ACK_SUCCESS);
166 break;
167 }
168 btif_av_stream_stop(RawAddress::kEmpty);
169 btif_a2dp_command_ack(A2DP_CTRL_ACK_SUCCESS);
170 break;
171
172 case A2DP_CTRL_CMD_SUSPEND:
173 /* Local suspend */
174 if (btif_av_stream_started_ready()) {
175 btif_av_stream_suspend();
176 break;
177 }
178 /* If we are not in started state, just ack back ok and let
179 * audioflinger close the channel. This can happen if we are
180 * remotely suspended, clear REMOTE SUSPEND flag.
181 */
182 btif_av_clear_remote_suspend_flag();
183 btif_a2dp_command_ack(A2DP_CTRL_ACK_SUCCESS);
184 break;
185
186 case A2DP_CTRL_GET_INPUT_AUDIO_CONFIG: {
187 tA2DP_SAMPLE_RATE sample_rate = btif_a2dp_sink_get_sample_rate();
188 tA2DP_CHANNEL_COUNT channel_count = btif_a2dp_sink_get_channel_count();
189
190 btif_a2dp_command_ack(A2DP_CTRL_ACK_SUCCESS);
191 UIPC_Send(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
192 reinterpret_cast<uint8_t*>(&sample_rate),
193 sizeof(tA2DP_SAMPLE_RATE));
194 UIPC_Send(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0, &channel_count,
195 sizeof(tA2DP_CHANNEL_COUNT));
196 break;
197 }
198
199 case A2DP_CTRL_GET_OUTPUT_AUDIO_CONFIG: {
200 btav_a2dp_codec_config_t codec_config;
201 btav_a2dp_codec_config_t codec_capability;
202 codec_config.sample_rate = BTAV_A2DP_CODEC_SAMPLE_RATE_NONE;
203 codec_config.bits_per_sample = BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE;
204 codec_config.channel_mode = BTAV_A2DP_CODEC_CHANNEL_MODE_NONE;
205 codec_capability.sample_rate = BTAV_A2DP_CODEC_SAMPLE_RATE_NONE;
206 codec_capability.bits_per_sample = BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE;
207 codec_capability.channel_mode = BTAV_A2DP_CODEC_CHANNEL_MODE_NONE;
208
209 A2dpCodecConfig* current_codec = bta_av_get_a2dp_current_codec();
210 if (current_codec != nullptr) {
211 codec_config = current_codec->getCodecConfig();
212 codec_capability = current_codec->getCodecCapability();
213 }
214
215 btif_a2dp_command_ack(A2DP_CTRL_ACK_SUCCESS);
216 // Send the current codec config
217 UIPC_Send(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
218 reinterpret_cast<const uint8_t*>(&codec_config.sample_rate),
219 sizeof(btav_a2dp_codec_sample_rate_t));
220 UIPC_Send(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
221 reinterpret_cast<const uint8_t*>(&codec_config.bits_per_sample),
222 sizeof(btav_a2dp_codec_bits_per_sample_t));
223 UIPC_Send(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
224 reinterpret_cast<const uint8_t*>(&codec_config.channel_mode),
225 sizeof(btav_a2dp_codec_channel_mode_t));
226 // Send the current codec capability
227 UIPC_Send(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
228 reinterpret_cast<const uint8_t*>(&codec_capability.sample_rate),
229 sizeof(btav_a2dp_codec_sample_rate_t));
230 UIPC_Send(
231 *a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
232 reinterpret_cast<const uint8_t*>(&codec_capability.bits_per_sample),
233 sizeof(btav_a2dp_codec_bits_per_sample_t));
234 UIPC_Send(
235 *a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
236 reinterpret_cast<const uint8_t*>(&codec_capability.channel_mode),
237 sizeof(btav_a2dp_codec_channel_mode_t));
238 break;
239 }
240
241 case A2DP_CTRL_SET_OUTPUT_AUDIO_CONFIG: {
242 btav_a2dp_codec_config_t codec_config;
243 codec_config.sample_rate = BTAV_A2DP_CODEC_SAMPLE_RATE_NONE;
244 codec_config.bits_per_sample = BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE;
245 codec_config.channel_mode = BTAV_A2DP_CODEC_CHANNEL_MODE_NONE;
246
247 btif_a2dp_command_ack(A2DP_CTRL_ACK_SUCCESS);
248 // Send the current codec config
249 if (UIPC_Read(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
250 reinterpret_cast<uint8_t*>(&codec_config.sample_rate),
251 sizeof(btav_a2dp_codec_sample_rate_t)) !=
252 sizeof(btav_a2dp_codec_sample_rate_t)) {
253 APPL_TRACE_ERROR("%s: Error reading sample rate from audio HAL",
254 __func__);
255 break;
256 }
257 if (UIPC_Read(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
258 reinterpret_cast<uint8_t*>(&codec_config.bits_per_sample),
259 sizeof(btav_a2dp_codec_bits_per_sample_t)) !=
260 sizeof(btav_a2dp_codec_bits_per_sample_t)) {
261 APPL_TRACE_ERROR("%s: Error reading bits per sample from audio HAL",
262 __func__);
263 break;
264 }
265 if (UIPC_Read(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
266 reinterpret_cast<uint8_t*>(&codec_config.channel_mode),
267 sizeof(btav_a2dp_codec_channel_mode_t)) !=
268 sizeof(btav_a2dp_codec_channel_mode_t)) {
269 APPL_TRACE_ERROR("%s: Error reading channel mode from audio HAL",
270 __func__);
271 break;
272 }
273 APPL_TRACE_DEBUG(
274 "%s: A2DP_CTRL_SET_OUTPUT_AUDIO_CONFIG: "
275 "sample_rate=0x%x bits_per_sample=0x%x "
276 "channel_mode=0x%x",
277 __func__, codec_config.sample_rate, codec_config.bits_per_sample,
278 codec_config.channel_mode);
279 btif_a2dp_source_feeding_update_req(codec_config);
280 break;
281 }
282
283 case A2DP_CTRL_CMD_OFFLOAD_START:
284 btif_av_stream_start_offload();
285 break;
286
287 case A2DP_CTRL_GET_PRESENTATION_POSITION: {
288 btif_a2dp_command_ack(A2DP_CTRL_ACK_SUCCESS);
289
290 UIPC_Send(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
291 (uint8_t*)&(delay_report_stats.total_bytes_read),
292 sizeof(uint64_t));
293 UIPC_Send(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0,
294 (uint8_t*)&(delay_report_stats.audio_delay), sizeof(uint16_t));
295
296 uint32_t seconds = delay_report_stats.timestamp.tv_sec;
297 UIPC_Send(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0, (uint8_t*)&seconds,
298 sizeof(seconds));
299
300 uint32_t nsec = delay_report_stats.timestamp.tv_nsec;
301 UIPC_Send(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0, (uint8_t*)&nsec,
302 sizeof(nsec));
303 break;
304 }
305 default:
306 APPL_TRACE_ERROR("%s: UNSUPPORTED CMD (%d)", __func__, cmd);
307 btif_a2dp_command_ack(A2DP_CTRL_ACK_FAILURE);
308 break;
309 }
310
311 // Don't log A2DP_CTRL_GET_PRESENTATION_POSITION by default, because it
312 // could be very chatty when audio is streaming.
313 if (cmd == A2DP_CTRL_GET_PRESENTATION_POSITION) {
314 APPL_TRACE_DEBUG("%s: a2dp-ctrl-cmd : %s DONE", __func__,
315 audio_a2dp_hw_dump_ctrl_event(cmd));
316 } else {
317 APPL_TRACE_WARNING("%s: a2dp-ctrl-cmd : %s DONE", __func__,
318 audio_a2dp_hw_dump_ctrl_event(cmd));
319 }
320 }
321
btif_a2dp_ctrl_cb(UNUSED_ATTR tUIPC_CH_ID ch_id,tUIPC_EVENT event)322 static void btif_a2dp_ctrl_cb(UNUSED_ATTR tUIPC_CH_ID ch_id,
323 tUIPC_EVENT event) {
324 // Don't log UIPC_RX_DATA_READY_EVT by default, because it
325 // could be very chatty when audio is streaming.
326 if (event == UIPC_RX_DATA_READY_EVT) {
327 APPL_TRACE_DEBUG("%s: A2DP-CTRL-CHANNEL EVENT %s", __func__,
328 dump_uipc_event(event));
329 } else {
330 APPL_TRACE_WARNING("%s: A2DP-CTRL-CHANNEL EVENT %s", __func__,
331 dump_uipc_event(event));
332 }
333
334 switch (event) {
335 case UIPC_OPEN_EVT:
336 break;
337
338 case UIPC_CLOSE_EVT:
339 /* restart ctrl server unless we are shutting down */
340 if (btif_a2dp_source_media_task_is_running())
341 UIPC_Open(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, btif_a2dp_ctrl_cb,
342 A2DP_CTRL_PATH);
343 break;
344
345 case UIPC_RX_DATA_READY_EVT:
346 btif_a2dp_recv_ctrl_data();
347 break;
348
349 default:
350 APPL_TRACE_ERROR("%s: ### A2DP-CTRL-CHANNEL EVENT %d NOT HANDLED ###",
351 __func__, event);
352 break;
353 }
354 }
355
btif_a2dp_data_cb(UNUSED_ATTR tUIPC_CH_ID ch_id,tUIPC_EVENT event)356 static void btif_a2dp_data_cb(UNUSED_ATTR tUIPC_CH_ID ch_id,
357 tUIPC_EVENT event) {
358 APPL_TRACE_WARNING("%s: BTIF MEDIA (A2DP-DATA) EVENT %s", __func__,
359 dump_uipc_event(event));
360
361 switch (event) {
362 case UIPC_OPEN_EVT:
363 /*
364 * Read directly from media task from here on (keep callback for
365 * connection events.
366 */
367 UIPC_Ioctl(*a2dp_uipc, UIPC_CH_ID_AV_AUDIO,
368 UIPC_REG_REMOVE_ACTIVE_READSET, NULL);
369 UIPC_Ioctl(*a2dp_uipc, UIPC_CH_ID_AV_AUDIO, UIPC_SET_READ_POLL_TMO,
370 reinterpret_cast<void*>(A2DP_DATA_READ_POLL_MS));
371
372 if (btif_av_get_peer_sep() == AVDT_TSEP_SNK) {
373 /* Start the media task to encode the audio */
374 btif_a2dp_source_start_audio_req();
375 }
376
377 /* ACK back when media task is fully started */
378 break;
379
380 case UIPC_CLOSE_EVT:
381 APPL_TRACE_EVENT("%s: ## AUDIO PATH DETACHED ##", __func__);
382 btif_a2dp_command_ack(A2DP_CTRL_ACK_SUCCESS);
383 /*
384 * Send stop request only if we are actively streaming and haven't
385 * received a stop request. Potentially, the audioflinger detached
386 * abnormally.
387 */
388 if (btif_a2dp_source_is_streaming()) {
389 /* Post stop event and wait for audio path to stop */
390 btif_av_stream_stop(RawAddress::kEmpty);
391 }
392 break;
393
394 default:
395 APPL_TRACE_ERROR("%s: ### A2DP-DATA EVENT %d NOT HANDLED ###", __func__,
396 event);
397 break;
398 }
399 }
400
btif_a2dp_command_ack(tA2DP_CTRL_ACK status)401 void btif_a2dp_command_ack(tA2DP_CTRL_ACK status) {
402 uint8_t ack = status;
403
404 // Don't log A2DP_CTRL_GET_PRESENTATION_POSITION by default, because it
405 // could be very chatty when audio is streaming.
406 if (a2dp_cmd_pending == A2DP_CTRL_GET_PRESENTATION_POSITION) {
407 APPL_TRACE_DEBUG("%s: ## a2dp ack : %s, status %d ##", __func__,
408 audio_a2dp_hw_dump_ctrl_event(a2dp_cmd_pending), status);
409 } else {
410 APPL_TRACE_WARNING("%s: ## a2dp ack : %s, status %d ##", __func__,
411 audio_a2dp_hw_dump_ctrl_event(a2dp_cmd_pending), status);
412 }
413
414 /* Sanity check */
415 if (a2dp_cmd_pending == A2DP_CTRL_CMD_NONE) {
416 APPL_TRACE_ERROR("%s: warning : no command pending, ignore ack", __func__);
417 return;
418 }
419
420 /* Clear pending */
421 a2dp_cmd_pending = A2DP_CTRL_CMD_NONE;
422
423 /* Acknowledge start request */
424 if (a2dp_uipc != nullptr) {
425 UIPC_Send(*a2dp_uipc, UIPC_CH_ID_AV_CTRL, 0, &ack, sizeof(ack));
426 }
427 }
428
btif_a2dp_control_log_bytes_read(uint32_t bytes_read)429 void btif_a2dp_control_log_bytes_read(uint32_t bytes_read) {
430 delay_report_stats.total_bytes_read += bytes_read;
431 clock_gettime(CLOCK_MONOTONIC, &delay_report_stats.timestamp);
432 }
433
btif_a2dp_control_set_audio_delay(uint16_t delay)434 void btif_a2dp_control_set_audio_delay(uint16_t delay) {
435 APPL_TRACE_DEBUG("%s: DELAY: %.1f ms", __func__, (float)delay / 10);
436 delay_report_stats.audio_delay = delay;
437 }
438
btif_a2dp_control_reset_audio_delay(void)439 void btif_a2dp_control_reset_audio_delay(void) {
440 APPL_TRACE_DEBUG("%s", __func__);
441 delay_report_stats.audio_delay = 0;
442 delay_report_stats.total_bytes_read = 0;
443 delay_report_stats.timestamp = {};
444 }
445