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