1 /******************************************************************************
2  *
3  *  Copyright (c) 2014 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 /*******************************************************************************
21  *
22  *  Filename:      btif_hf_client.c
23  *
24  *  Description:   Handsfree Profile (HF role) Bluetooth Interface
25  *
26  *  Notes:
27  *  a) Lifecycle of a control block
28  *  Control block handles the lifecycle for a particular remote device's
29  *  connection. The connection can go via the classic phases but more
30  *  importantly there's only two messages from BTA that affect this.
31  *  BTA_HF_CLIENT_OPEN_EVT and BTA_HF_CLIENT_CLOSE_EVT. Since the API between
32  *  BTIF and BTA is controlled entirely by handles it's important to know where
33  *  the handles are created and destroyed. Handles can be created at two
34  *  locations:
35  *  -- While connect() is called from BTIF. This is an outgoing connection
36  *  -- While accepting an incoming connection (see BTA_HF_CLIENT_OPEN_EVT
37  *  handling).
38  *
39  *  The destruction or rather reuse of handles can be done when
40  *  BTA_HF_CLIENT_CLOSE_EVT is called. Refer to the event handling for details
41  *  of this.
42  *
43  ******************************************************************************/
44 
45 #ifndef LOG_TAG
46 #define LOG_TAG "bt_btif_hfc"
47 #endif
48 
49 #include <string.h>
50 
51 #include <hardware/bluetooth.h>
52 #include <hardware/bt_hf_client.h>
53 
54 #include "bta_hf_client_api.h"
55 #include "btif_common.h"
56 #include "btif_profile_queue.h"
57 #include "btif_util.h"
58 #include "osi/include/osi.h"
59 #include "osi/include/properties.h"
60 
61 /*******************************************************************************
62  *  Constants & Macros
63  ******************************************************************************/
64 
65 #ifndef BTIF_HF_CLIENT_SERVICE_NAME
66 #define BTIF_HF_CLIENT_SERVICE_NAME ("Handsfree")
67 #endif
68 
69 #ifndef BTIF_HF_CLIENT_FEATURES
70 #define BTIF_HF_CLIENT_FEATURES                                                \
71   (BTA_HF_CLIENT_FEAT_ECNR | BTA_HF_CLIENT_FEAT_3WAY |                         \
72    BTA_HF_CLIENT_FEAT_CLI | BTA_HF_CLIENT_FEAT_VREC | BTA_HF_CLIENT_FEAT_VOL | \
73    BTA_HF_CLIENT_FEAT_ECS | BTA_HF_CLIENT_FEAT_ECC | BTA_HF_CLIENT_FEAT_CODEC)
74 #endif
75 
76 /*******************************************************************************
77  *  Local type definitions
78  ******************************************************************************/
79 /* BTIF-HF control block to map bdaddr to BTA handle */
80 typedef struct {
81   uint16_t handle;                       // Handle obtained frm the BTA
82   RawAddress peer_bda;                   // Device corresponding to handle
83   bthf_client_connection_state_t state;  // State of current connection
84   tBTA_HF_CLIENT_PEER_FEAT peer_feat;    // HF features
85   tBTA_HF_CLIENT_CHLD_FEAT chld_feat;    // AT+CHLD=<> command features
86 } btif_hf_client_cb_t;
87 
88 /* Max devices supported by BTIF (useful to match the value in BTA) */
89 #define HF_CLIENT_MAX_DEVICES 10
90 typedef struct {
91   btif_hf_client_cb_t cb[HF_CLIENT_MAX_DEVICES];
92 } btif_hf_client_cb_arr_t;
93 
94 /******************************************************************************
95  * Local function declarations
96  ******************************************************************************/
97 btif_hf_client_cb_t* btif_hf_client_get_cb_by_handle(uint16_t handle);
98 btif_hf_client_cb_t* btif_hf_client_get_cb_by_bda(const RawAddress& addr);
99 bool is_connected(const btif_hf_client_cb_t* cb);
100 
101 /*******************************************************************************
102  *  Static variables
103  ******************************************************************************/
104 static bthf_client_callbacks_t* bt_hf_client_callbacks = NULL;
105 
106 char btif_hf_client_version[PROPERTY_VALUE_MAX];
107 
dump_hf_client_conn_state(uint16_t event)108 static const char* dump_hf_client_conn_state(uint16_t event) {
109   switch (event) {
110     CASE_RETURN_STR(BTHF_CLIENT_CONNECTION_STATE_DISCONNECTED)
111     CASE_RETURN_STR(BTHF_CLIENT_CONNECTION_STATE_CONNECTING)
112     CASE_RETURN_STR(BTHF_CLIENT_CONNECTION_STATE_CONNECTED)
113     CASE_RETURN_STR(BTHF_CLIENT_CONNECTION_STATE_SLC_CONNECTED)
114     CASE_RETURN_STR(BTHF_CLIENT_CONNECTION_STATE_DISCONNECTING)
115     default:
116       return "UNKNOWN MSG ID";
117   }
118 }
119 
120 #define CHECK_BTHF_CLIENT_INIT()                                        \
121   do {                                                                  \
122     if (bt_hf_client_callbacks == NULL) {                               \
123       BTIF_TRACE_WARNING("BTHF CLIENT: %s: not initialized", __func__); \
124       return BT_STATUS_NOT_READY;                                       \
125     } else {                                                            \
126       BTIF_TRACE_EVENT("BTHF CLIENT: %s", __func__);                    \
127     }                                                                   \
128   } while (0)
129 
130 #define CHECK_BTHF_CLIENT_SLC_CONNECTED(cb)                                  \
131   do {                                                                       \
132     if (bt_hf_client_callbacks == NULL) {                                    \
133       BTIF_TRACE_WARNING("BTHF CLIENT: %s: not initialized", __func__);      \
134       return BT_STATUS_NOT_READY;                                            \
135     } else if ((cb)->state != BTHF_CLIENT_CONNECTION_STATE_SLC_CONNECTED) {  \
136       BTIF_TRACE_WARNING("BTHF CLIENT: %s: SLC connection not up. state=%s", \
137                          __func__, dump_hf_client_conn_state((cb)->state));  \
138       return BT_STATUS_NOT_READY;                                            \
139     } else {                                                                 \
140       BTIF_TRACE_EVENT("BTHF CLIENT: %s", __func__);                         \
141     }                                                                        \
142   } while (0)
143 
144 static btif_hf_client_cb_arr_t btif_hf_client_cb_arr;
145 
146 /*******************************************************************************
147  *  Static functions
148  ******************************************************************************/
149 
150 /*******************************************************************************
151  *
152  * Function        btif_in_hf_client_generic_evt
153  *
154  * Description     Processes generic events to be sent to JNI that are not
155  *                 triggered from the BTA.
156  *                 Always runs in BTIF context
157  *
158  * Returns          void
159  *
160  ******************************************************************************/
btif_in_hf_client_generic_evt(uint16_t event,char * p_param)161 static void btif_in_hf_client_generic_evt(uint16_t event, char* p_param) {
162   BTIF_TRACE_DEBUG("%s", __func__);
163   RawAddress* bd_addr = (RawAddress*)p_param;
164   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
165   if (cb == NULL || !is_connected(cb)) {
166     BTIF_TRACE_ERROR("%s: failed to find block for bda", __func__);
167     return;
168   }
169 
170   BTIF_TRACE_EVENT("%s: event=%d", __func__, event);
171   switch (event) {
172     case BTIF_HF_CLIENT_CB_AUDIO_CONNECTING: {
173       HAL_CBACK(bt_hf_client_callbacks, audio_state_cb, &cb->peer_bda,
174                 (bthf_client_audio_state_t)BTHF_CLIENT_AUDIO_STATE_CONNECTING);
175     } break;
176     default: {
177       BTIF_TRACE_WARNING("%s: : Unknown event 0x%x", __func__, event);
178     } break;
179   }
180 }
181 
182 /*******************************************************************************
183  *  Functions
184  ******************************************************************************/
is_connected(const btif_hf_client_cb_t * cb)185 bool is_connected(const btif_hf_client_cb_t* cb) {
186   if ((cb->state == BTHF_CLIENT_CONNECTION_STATE_CONNECTED) ||
187       (cb->state == BTHF_CLIENT_CONNECTION_STATE_SLC_CONNECTED))
188     return true;
189 
190   BTIF_TRACE_ERROR("%s: not connected!", __func__);
191   return false;
192 }
193 
194 /*******************************************************************************
195  *
196  * Function        btif_hf_client_get_cb_by_handle
197  *
198  * Description     Get control block by handle
199  *
200  * Returns         btif_hf_client_cb_t pointer if available NULL otherwise
201  *
202  ******************************************************************************/
btif_hf_client_get_cb_by_handle(uint16_t handle)203 btif_hf_client_cb_t* btif_hf_client_get_cb_by_handle(uint16_t handle) {
204   BTIF_TRACE_DEBUG("%s: cb by handle %d", __func__, handle);
205   for (int i = 0; i < HF_CLIENT_MAX_DEVICES; i++) {
206     // Block is valid only if it is allocated i.e. state is not DISCONNECTED
207     if (btif_hf_client_cb_arr.cb[i].state !=
208             BTHF_CLIENT_CONNECTION_STATE_DISCONNECTED &&
209         btif_hf_client_cb_arr.cb[i].handle == handle) {
210       return &btif_hf_client_cb_arr.cb[i];
211     }
212   }
213   BTIF_TRACE_ERROR("%s: could not find block for handle %d", __func__, handle);
214   return NULL;
215 }
216 
217 /*******************************************************************************
218  *
219  * Function        btif_hf_client_get_cb_by_bda
220  *
221  * Description     Get control block by bda
222  *
223  * Returns         btif_hf_client_cb_t pointer if available NULL otherwise
224  *
225  ******************************************************************************/
btif_hf_client_get_cb_by_bda(const RawAddress & bd_addr)226 btif_hf_client_cb_t* btif_hf_client_get_cb_by_bda(const RawAddress& bd_addr) {
227   VLOG(1) << __func__ << " incoming addr " << bd_addr;
228 
229   for (int i = 0; i < HF_CLIENT_MAX_DEVICES; i++) {
230     // Block is valid only if it is allocated i.e. state is not DISCONNECTED
231     if (btif_hf_client_cb_arr.cb[i].state !=
232             BTHF_CLIENT_CONNECTION_STATE_DISCONNECTED &&
233         btif_hf_client_cb_arr.cb[i].peer_bda == bd_addr) {
234       return &btif_hf_client_cb_arr.cb[i];
235     }
236   }
237   BTIF_TRACE_ERROR("%s: could not find block for bdaddr", __func__);
238   return NULL;
239 }
240 
241 /*******************************************************************************
242  *
243  * Function        btif_hf_client_allocate_cb
244  *
245  * Description     Get control block by bda
246  *
247  * Returns         btif_hf_client_cb_t pointer if available NULL otherwise
248  *
249  ******************************************************************************/
btif_hf_client_allocate_cb()250 btif_hf_client_cb_t* btif_hf_client_allocate_cb() {
251   for (int i = 0; i < HF_CLIENT_MAX_DEVICES; i++) {
252     btif_hf_client_cb_t* cb = &btif_hf_client_cb_arr.cb[i];
253     if (cb->state == BTHF_CLIENT_CONNECTION_STATE_DISCONNECTED) {
254       return cb;
255     }
256   }
257   BTIF_TRACE_ERROR("%s: unable to allocate control block", __func__);
258   return NULL;
259 }
260 
261 /*****************************************************************************
262  *
263  *   btif hf api functions (no context switch)
264  *
265  ****************************************************************************/
266 
267 /*******************************************************************************
268  *
269  * Function         btif_hf_client_init
270  *
271  * Description     initializes the hf interface
272  *
273  * Returns         bt_status_t
274  *
275  ******************************************************************************/
init(bthf_client_callbacks_t * callbacks)276 static bt_status_t init(bthf_client_callbacks_t* callbacks) {
277   BTIF_TRACE_EVENT("%s", __func__);
278 
279   bt_hf_client_callbacks = callbacks;
280 
281   btif_enable_service(BTA_HFP_HS_SERVICE_ID);
282 
283   memset(&btif_hf_client_cb_arr, 0, sizeof(btif_hf_client_cb_arr_t));
284 
285   return BT_STATUS_SUCCESS;
286 }
287 
288 /*******************************************************************************
289  *
290  * Function         connect
291  *
292  * Description     connect to audio gateway
293  *
294  * Returns         bt_status_t
295  *
296  ******************************************************************************/
connect_int(RawAddress * bd_addr,uint16_t uuid)297 static bt_status_t connect_int(RawAddress* bd_addr, uint16_t uuid) {
298   btif_hf_client_cb_t* cb = btif_hf_client_allocate_cb();
299   if (cb == NULL) {
300     BTIF_TRACE_ERROR("%s: could not allocate block!", __func__);
301     return BT_STATUS_BUSY;
302   }
303 
304   cb->peer_bda = *bd_addr;
305   if (is_connected(cb)) return BT_STATUS_BUSY;
306 
307   cb->state = BTHF_CLIENT_CONNECTION_STATE_CONNECTING;
308   cb->peer_bda = *bd_addr;
309 
310   /* Open HF connection to remote device and get the relevant handle.
311    * The handle is valid until we have called BTA_HfClientClose or the LL
312    * has notified us of channel close due to remote closing, error etc.
313    */
314   BTA_HfClientOpen(cb->peer_bda, &cb->handle);
315 
316   return BT_STATUS_SUCCESS;
317 }
318 
connect(RawAddress * bd_addr)319 static bt_status_t connect(RawAddress* bd_addr) {
320   BTIF_TRACE_EVENT("HFP Client version is  %s", btif_hf_client_version);
321   CHECK_BTHF_CLIENT_INIT();
322   return btif_queue_connect(UUID_SERVCLASS_HF_HANDSFREE, bd_addr, connect_int);
323 }
324 
325 /*******************************************************************************
326  *
327  * Function         disconnect
328  *
329  * Description      disconnect from audio gateway
330  *
331  * Returns         bt_status_t
332  *
333  ******************************************************************************/
disconnect(const RawAddress * bd_addr)334 static bt_status_t disconnect(const RawAddress* bd_addr) {
335   CHECK_BTHF_CLIENT_INIT();
336 
337   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
338   if (cb != NULL) {
339     BTA_HfClientClose(cb->handle);
340     return BT_STATUS_SUCCESS;
341   } else {
342     return BT_STATUS_BUSY;
343   }
344 }
345 
346 /*******************************************************************************
347  *
348  * Function         connect_audio
349  *
350  * Description     create an audio connection
351  *
352  * Returns         bt_status_t
353  *
354  ******************************************************************************/
connect_audio(const RawAddress * bd_addr)355 static bt_status_t connect_audio(const RawAddress* bd_addr) {
356   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
357   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
358 
359   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
360 
361   if ((BTIF_HF_CLIENT_FEATURES & BTA_HF_CLIENT_FEAT_CODEC) &&
362       (cb->peer_feat & BTA_HF_CLIENT_PEER_CODEC)) {
363     BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_BCC, 0, 0, NULL);
364   } else {
365     BTA_HfClientAudioOpen(cb->handle);
366   }
367 
368   /* Inform the application that the audio connection has been initiated
369    * successfully */
370   btif_transfer_context(btif_in_hf_client_generic_evt,
371                         BTIF_HF_CLIENT_CB_AUDIO_CONNECTING, (char*)bd_addr,
372                         sizeof(RawAddress), NULL);
373   return BT_STATUS_SUCCESS;
374 }
375 
376 /*******************************************************************************
377  *
378  * Function         disconnect_audio
379  *
380  * Description      close the audio connection
381  *
382  * Returns         bt_status_t
383  *
384  ******************************************************************************/
disconnect_audio(const RawAddress * bd_addr)385 static bt_status_t disconnect_audio(const RawAddress* bd_addr) {
386   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
387   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
388 
389   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
390 
391   BTA_HfClientAudioClose(cb->handle);
392   return BT_STATUS_SUCCESS;
393 }
394 
395 /*******************************************************************************
396  *
397  * Function         start_voice_recognition
398  *
399  * Description      start voice recognition
400  *
401  * Returns          bt_status_t
402  *
403  ******************************************************************************/
start_voice_recognition(const RawAddress * bd_addr)404 static bt_status_t start_voice_recognition(const RawAddress* bd_addr) {
405   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
406   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
407 
408   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
409 
410   if (cb->peer_feat & BTA_HF_CLIENT_PEER_FEAT_VREC) {
411     BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_BVRA, 1, 0, NULL);
412     return BT_STATUS_SUCCESS;
413   }
414   return BT_STATUS_UNSUPPORTED;
415 }
416 
417 /*******************************************************************************
418  *
419  * Function         stop_voice_recognition
420  *
421  * Description      stop voice recognition
422  *
423  * Returns          bt_status_t
424  *
425  ******************************************************************************/
stop_voice_recognition(const RawAddress * bd_addr)426 static bt_status_t stop_voice_recognition(const RawAddress* bd_addr) {
427   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
428   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
429 
430   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
431 
432   if (cb->peer_feat & BTA_HF_CLIENT_PEER_FEAT_VREC) {
433     BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_BVRA, 0, 0, NULL);
434     return BT_STATUS_SUCCESS;
435   }
436   return BT_STATUS_UNSUPPORTED;
437 }
438 
439 /*******************************************************************************
440  *
441  * Function         volume_control
442  *
443  * Description      volume control
444  *
445  * Returns          bt_status_t
446  *
447  ******************************************************************************/
volume_control(const RawAddress * bd_addr,bthf_client_volume_type_t type,int volume)448 static bt_status_t volume_control(const RawAddress* bd_addr,
449                                   bthf_client_volume_type_t type, int volume) {
450   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
451   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
452 
453   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
454 
455   switch (type) {
456     case BTHF_CLIENT_VOLUME_TYPE_SPK:
457       BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_VGS, volume, 0, NULL);
458       break;
459     case BTHF_CLIENT_VOLUME_TYPE_MIC:
460       BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_VGM, volume, 0, NULL);
461       break;
462     default:
463       return BT_STATUS_UNSUPPORTED;
464   }
465 
466   return BT_STATUS_SUCCESS;
467 }
468 
469 /*******************************************************************************
470  *
471  * Function         dial
472  *
473  * Description      place a call
474  *
475  * Returns          bt_status_t
476  *
477  ******************************************************************************/
dial(UNUSED_ATTR const RawAddress * bd_addr,const char * number)478 static bt_status_t dial(UNUSED_ATTR const RawAddress* bd_addr,
479                         const char* number) {
480   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
481   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
482 
483   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
484 
485   if (number) {
486     BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_ATD, 0, 0, number);
487   } else {
488     BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_BLDN, 0, 0, NULL);
489   }
490   return BT_STATUS_SUCCESS;
491 }
492 
493 /*******************************************************************************
494  *
495  * Function         dial_memory
496  *
497  * Description      place a call with number specified by location (speed dial)
498  *
499  * Returns          bt_status_t
500  *
501  ******************************************************************************/
dial_memory(const RawAddress * bd_addr,int location)502 static bt_status_t dial_memory(const RawAddress* bd_addr, int location) {
503   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
504   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
505 
506   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
507 
508   BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_ATD, location, 0, NULL);
509   return BT_STATUS_SUCCESS;
510 }
511 
512 /*******************************************************************************
513  *
514  * Function         handle_call_action
515  *
516  * Description      handle specified call related action
517  *
518  * Returns          bt_status_t
519  *
520  ******************************************************************************/
handle_call_action(const RawAddress * bd_addr,bthf_client_call_action_t action,int idx)521 static bt_status_t handle_call_action(const RawAddress* bd_addr,
522                                       bthf_client_call_action_t action,
523                                       int idx) {
524   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
525   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
526 
527   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
528 
529   switch (action) {
530     case BTHF_CLIENT_CALL_ACTION_CHLD_0:
531       if (cb->chld_feat & BTA_HF_CLIENT_CHLD_REL) {
532         BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_CHLD, 0, 0, NULL);
533         break;
534       }
535       return BT_STATUS_UNSUPPORTED;
536     case BTHF_CLIENT_CALL_ACTION_CHLD_1:
537       // CHLD 1 is mandatory for 3 way calling
538       if (cb->peer_feat & BTA_HF_CLIENT_PEER_FEAT_3WAY) {
539         BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_CHLD, 1, 0, NULL);
540         break;
541       }
542       return BT_STATUS_UNSUPPORTED;
543     case BTHF_CLIENT_CALL_ACTION_CHLD_2:
544       // CHLD 2 is mandatory for 3 way calling
545       if (cb->peer_feat & BTA_HF_CLIENT_PEER_FEAT_3WAY) {
546         BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_CHLD, 2, 0, NULL);
547         break;
548       }
549       return BT_STATUS_UNSUPPORTED;
550     case BTHF_CLIENT_CALL_ACTION_CHLD_3:
551       if (cb->chld_feat & BTA_HF_CLIENT_CHLD_MERGE) {
552         BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_CHLD, 3, 0, NULL);
553         break;
554       }
555       return BT_STATUS_UNSUPPORTED;
556     case BTHF_CLIENT_CALL_ACTION_CHLD_4:
557       if (cb->chld_feat & BTA_HF_CLIENT_CHLD_MERGE_DETACH) {
558         BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_CHLD, 4, 0, NULL);
559         break;
560       }
561       return BT_STATUS_UNSUPPORTED;
562     case BTHF_CLIENT_CALL_ACTION_CHLD_1x:
563       if (cb->peer_feat & BTA_HF_CLIENT_PEER_ECC) {
564         if (idx < 1) {
565           return BT_STATUS_FAIL;
566         }
567         BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_CHLD, 1, idx, NULL);
568         break;
569       }
570       return BT_STATUS_UNSUPPORTED;
571     case BTHF_CLIENT_CALL_ACTION_CHLD_2x:
572       if (cb->peer_feat & BTA_HF_CLIENT_PEER_ECC) {
573         if (idx < 1) {
574           return BT_STATUS_FAIL;
575         }
576         BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_CHLD, 2, idx, NULL);
577         break;
578       }
579       return BT_STATUS_UNSUPPORTED;
580     case BTHF_CLIENT_CALL_ACTION_ATA:
581       BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_ATA, 0, 0, NULL);
582       break;
583     case BTHF_CLIENT_CALL_ACTION_CHUP:
584       BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_CHUP, 0, 0, NULL);
585       break;
586     case BTHF_CLIENT_CALL_ACTION_BTRH_0:
587       BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_BTRH, 0, 0, NULL);
588       break;
589     case BTHF_CLIENT_CALL_ACTION_BTRH_1:
590       BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_BTRH, 1, 0, NULL);
591       break;
592     case BTHF_CLIENT_CALL_ACTION_BTRH_2:
593       BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_BTRH, 2, 0, NULL);
594       break;
595     default:
596       return BT_STATUS_FAIL;
597   }
598 
599   return BT_STATUS_SUCCESS;
600 }
601 
602 /*******************************************************************************
603  *
604  * Function         query_current_calls
605  *
606  * Description      query list of current calls
607  *
608  * Returns          bt_status_t
609  *
610  ******************************************************************************/
query_current_calls(UNUSED_ATTR const RawAddress * bd_addr)611 static bt_status_t query_current_calls(UNUSED_ATTR const RawAddress* bd_addr) {
612   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
613   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
614 
615   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
616 
617   if (cb->peer_feat & BTA_HF_CLIENT_PEER_ECS) {
618     BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_CLCC, 0, 0, NULL);
619     return BT_STATUS_SUCCESS;
620   }
621 
622   return BT_STATUS_UNSUPPORTED;
623 }
624 
625 /*******************************************************************************
626  *
627  * Function         query_current_operator_name
628  *
629  * Description      query current selected operator name
630  *
631  * Returns          bt_status_t
632  *
633  ******************************************************************************/
query_current_operator_name(const RawAddress * bd_addr)634 static bt_status_t query_current_operator_name(const RawAddress* bd_addr) {
635   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
636   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
637 
638   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
639 
640   BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_COPS, 0, 0, NULL);
641   return BT_STATUS_SUCCESS;
642 }
643 
644 /*******************************************************************************
645  *
646  * Function         retieve_subscriber_info
647  *
648  * Description      retrieve subscriber number information
649  *
650  * Returns          bt_status_t
651  *
652  ******************************************************************************/
retrieve_subscriber_info(const RawAddress * bd_addr)653 static bt_status_t retrieve_subscriber_info(const RawAddress* bd_addr) {
654   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
655   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
656 
657   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
658 
659   BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_CNUM, 0, 0, NULL);
660   return BT_STATUS_SUCCESS;
661 }
662 
663 /*******************************************************************************
664  *
665  * Function         send_dtmf
666  *
667  * Description      send dtmf
668  *
669  * Returns          bt_status_t
670  *
671  ******************************************************************************/
send_dtmf(const RawAddress * bd_addr,char code)672 static bt_status_t send_dtmf(const RawAddress* bd_addr, char code) {
673   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
674   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
675 
676   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
677 
678   BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_VTS, code, 0, NULL);
679   return BT_STATUS_SUCCESS;
680 }
681 
682 /*******************************************************************************
683  *
684  * Function         request_last_voice_tag_number
685  *
686  * Description      Request number from AG for VR purposes
687  *
688  * Returns          bt_status_t
689  *
690  ******************************************************************************/
request_last_voice_tag_number(const RawAddress * bd_addr)691 static bt_status_t request_last_voice_tag_number(const RawAddress* bd_addr) {
692   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
693   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
694 
695   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
696 
697   if (cb->peer_feat & BTA_HF_CLIENT_PEER_VTAG) {
698     BTA_HfClientSendAT(cb->handle, BTA_HF_CLIENT_AT_CMD_BINP, 1, 0, NULL);
699     return BT_STATUS_SUCCESS;
700   }
701   return BT_STATUS_UNSUPPORTED;
702 }
703 
704 /*******************************************************************************
705  *
706  * Function         cleanup
707  *
708  * Description      Closes the HF interface
709  *
710  * Returns          bt_status_t
711  *
712  ******************************************************************************/
cleanup(void)713 static void cleanup(void) {
714   BTIF_TRACE_EVENT("%s", __func__);
715 
716   btif_queue_cleanup(UUID_SERVCLASS_HF_HANDSFREE);
717   if (bt_hf_client_callbacks) {
718     btif_disable_service(BTA_HFP_HS_SERVICE_ID);
719     bt_hf_client_callbacks = NULL;
720   }
721 }
722 
723 /*******************************************************************************
724  *
725  * Function         send_at_cmd
726  *
727  * Description      Send requested AT command to rempte device.
728  *
729  * Returns          bt_status_t
730  *
731  ******************************************************************************/
send_at_cmd(const RawAddress * bd_addr,int cmd,int val1,int val2,const char * arg)732 static bt_status_t send_at_cmd(const RawAddress* bd_addr, int cmd, int val1,
733                                int val2, const char* arg) {
734   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(*bd_addr);
735   if (cb == NULL || !is_connected(cb)) return BT_STATUS_FAIL;
736 
737   CHECK_BTHF_CLIENT_SLC_CONNECTED(cb);
738 
739   BTIF_TRACE_EVENT("%s: Cmd %d val1 %d val2 %d arg %s", __func__, cmd, val1,
740                    val2, (arg != NULL) ? arg : "<null>");
741   BTA_HfClientSendAT(cb->handle, cmd, val1, val2, arg);
742 
743   return BT_STATUS_SUCCESS;
744 }
745 
746 static const bthf_client_interface_t bthfClientInterface = {
747     .size = sizeof(bthf_client_interface_t),
748     .init = init,
749     .connect = connect,
750     .disconnect = disconnect,
751     .connect_audio = connect_audio,
752     .disconnect_audio = disconnect_audio,
753     .start_voice_recognition = start_voice_recognition,
754     .stop_voice_recognition = stop_voice_recognition,
755     .volume_control = volume_control,
756     .dial = dial,
757     .dial_memory = dial_memory,
758     .handle_call_action = handle_call_action,
759     .query_current_calls = query_current_calls,
760     .query_current_operator_name = query_current_operator_name,
761     .retrieve_subscriber_info = retrieve_subscriber_info,
762     .send_dtmf = send_dtmf,
763     .request_last_voice_tag_number = request_last_voice_tag_number,
764     .cleanup = cleanup,
765     .send_at_cmd = send_at_cmd,
766 };
767 
process_ind_evt(tBTA_HF_CLIENT_IND * ind)768 static void process_ind_evt(tBTA_HF_CLIENT_IND* ind) {
769   BTIF_TRACE_DEBUG("%s", __func__);
770 
771   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(ind->bd_addr);
772   if (cb == NULL || !is_connected(cb)) return;
773 
774   switch (ind->type) {
775     case BTA_HF_CLIENT_IND_CALL:
776       HAL_CBACK(bt_hf_client_callbacks, call_cb, &cb->peer_bda,
777                 (bthf_client_call_t)ind->value);
778       break;
779 
780     case BTA_HF_CLIENT_IND_CALLSETUP:
781       HAL_CBACK(bt_hf_client_callbacks, callsetup_cb, &cb->peer_bda,
782                 (bthf_client_callsetup_t)ind->value);
783       break;
784     case BTA_HF_CLIENT_IND_CALLHELD:
785       HAL_CBACK(bt_hf_client_callbacks, callheld_cb, &cb->peer_bda,
786                 (bthf_client_callheld_t)ind->value);
787       break;
788 
789     case BTA_HF_CLIENT_IND_SERVICE:
790       HAL_CBACK(bt_hf_client_callbacks, network_state_cb, &cb->peer_bda,
791                 (bthf_client_network_state_t)ind->value);
792       break;
793 
794     case BTA_HF_CLIENT_IND_SIGNAL:
795       HAL_CBACK(bt_hf_client_callbacks, network_signal_cb, &cb->peer_bda,
796                 ind->value);
797       break;
798 
799     case BTA_HF_CLIENT_IND_ROAM:
800       HAL_CBACK(bt_hf_client_callbacks, network_roaming_cb, &cb->peer_bda,
801                 (bthf_client_service_type_t)ind->value);
802       break;
803 
804     case BTA_HF_CLIENT_IND_BATTCH:
805       HAL_CBACK(bt_hf_client_callbacks, battery_level_cb, &cb->peer_bda,
806                 ind->value);
807       break;
808 
809     default:
810       break;
811   }
812 }
813 
814 /*******************************************************************************
815  *
816  * Function         btif_hf_client_upstreams_evt
817  *
818  * Description      Executes HF CLIENT UPSTREAMS events in btif context
819  *
820  * Returns          void
821  *
822  ******************************************************************************/
btif_hf_client_upstreams_evt(uint16_t event,char * p_param)823 static void btif_hf_client_upstreams_evt(uint16_t event, char* p_param) {
824   tBTA_HF_CLIENT* p_data = (tBTA_HF_CLIENT*)p_param;
825 
826   btif_hf_client_cb_t* cb = btif_hf_client_get_cb_by_bda(p_data->bd_addr);
827   if (cb == NULL && event == BTA_HF_CLIENT_OPEN_EVT) {
828     BTIF_TRACE_DEBUG("%s: event BTA_HF_CLIENT_OPEN_EVT allocating block",
829                      __func__);
830     cb = btif_hf_client_allocate_cb();
831     cb->handle = p_data->open.handle;
832     cb->peer_bda = p_data->open.bd_addr;
833   } else if (cb == NULL) {
834     BTIF_TRACE_ERROR("%s: event %d but not allocating block: cb not found",
835                      __func__, event);
836     return;
837   }
838 
839   BTIF_TRACE_DEBUG("%s: event=%s (%u)", __func__, dump_hf_client_event(event),
840                    event);
841 
842   switch (event) {
843     case BTA_HF_CLIENT_OPEN_EVT:
844       if (p_data->open.status == BTA_HF_CLIENT_SUCCESS) {
845         cb->state = BTHF_CLIENT_CONNECTION_STATE_CONNECTED;
846         cb->peer_feat = 0;
847         cb->chld_feat = 0;
848       } else if (cb->state == BTHF_CLIENT_CONNECTION_STATE_CONNECTING) {
849         cb->state = BTHF_CLIENT_CONNECTION_STATE_DISCONNECTED;
850       } else {
851         BTIF_TRACE_WARNING(
852             "%s: HF CLient open failed, but another device connected. "
853             "status=%d state=%d connected device=%s",
854             __func__, p_data->open.status, cb->state,
855             cb->peer_bda.ToString().c_str());
856         break;
857       }
858 
859       HAL_CBACK(bt_hf_client_callbacks, connection_state_cb, &cb->peer_bda,
860                 cb->state, 0, /* peer feat */
861                 0 /* AT+CHLD feat */);
862 
863       if (cb->state == BTHF_CLIENT_CONNECTION_STATE_DISCONNECTED)
864         cb->peer_bda = RawAddress::kAny;
865 
866       if (p_data->open.status != BTA_HF_CLIENT_SUCCESS) btif_queue_advance();
867       break;
868 
869     case BTA_HF_CLIENT_CONN_EVT:
870       cb->peer_feat = p_data->conn.peer_feat;
871       cb->chld_feat = p_data->conn.chld_feat;
872       cb->state = BTHF_CLIENT_CONNECTION_STATE_SLC_CONNECTED;
873 
874       HAL_CBACK(bt_hf_client_callbacks, connection_state_cb, &cb->peer_bda,
875                 cb->state, cb->peer_feat, cb->chld_feat);
876 
877       /* Inform the application about in-band ringtone */
878       if (cb->peer_feat & BTA_HF_CLIENT_PEER_INBAND) {
879         HAL_CBACK(bt_hf_client_callbacks, in_band_ring_tone_cb, &cb->peer_bda,
880                   BTHF_CLIENT_IN_BAND_RINGTONE_PROVIDED);
881       }
882 
883       btif_queue_advance();
884       break;
885 
886     case BTA_HF_CLIENT_CLOSE_EVT:
887       cb->state = BTHF_CLIENT_CONNECTION_STATE_DISCONNECTED;
888       HAL_CBACK(bt_hf_client_callbacks, connection_state_cb, &cb->peer_bda,
889                 cb->state, 0, 0);
890       cb->peer_bda = RawAddress::kAny;
891       cb->peer_feat = 0;
892       cb->chld_feat = 0;
893       btif_queue_advance();
894       break;
895 
896     case BTA_HF_CLIENT_IND_EVT:
897       process_ind_evt(&p_data->ind);
898       break;
899 
900     case BTA_HF_CLIENT_MIC_EVT:
901       HAL_CBACK(bt_hf_client_callbacks, volume_change_cb, &cb->peer_bda,
902                 BTHF_CLIENT_VOLUME_TYPE_MIC, p_data->val.value);
903       break;
904 
905     case BTA_HF_CLIENT_SPK_EVT:
906       HAL_CBACK(bt_hf_client_callbacks, volume_change_cb, &cb->peer_bda,
907                 BTHF_CLIENT_VOLUME_TYPE_SPK, p_data->val.value);
908       break;
909 
910     case BTA_HF_CLIENT_VOICE_REC_EVT:
911       HAL_CBACK(bt_hf_client_callbacks, vr_cmd_cb, &cb->peer_bda,
912                 (bthf_client_vr_state_t)p_data->val.value);
913       break;
914 
915     case BTA_HF_CLIENT_OPERATOR_NAME_EVT:
916       HAL_CBACK(bt_hf_client_callbacks, current_operator_cb, &cb->peer_bda,
917                 p_data->operator_name.name);
918       break;
919 
920     case BTA_HF_CLIENT_CLIP_EVT:
921       HAL_CBACK(bt_hf_client_callbacks, clip_cb, &cb->peer_bda,
922                 p_data->number.number);
923       break;
924 
925     case BTA_HF_CLIENT_BINP_EVT:
926       HAL_CBACK(bt_hf_client_callbacks, last_voice_tag_number_callback,
927                 &cb->peer_bda, p_data->number.number);
928       break;
929 
930     case BTA_HF_CLIENT_CCWA_EVT:
931       HAL_CBACK(bt_hf_client_callbacks, call_waiting_cb, &cb->peer_bda,
932                 p_data->number.number);
933       break;
934 
935     case BTA_HF_CLIENT_AT_RESULT_EVT:
936       HAL_CBACK(bt_hf_client_callbacks, cmd_complete_cb, &cb->peer_bda,
937                 (bthf_client_cmd_complete_t)p_data->result.type,
938                 p_data->result.cme);
939       break;
940 
941     case BTA_HF_CLIENT_CLCC_EVT:
942       HAL_CBACK(bt_hf_client_callbacks, current_calls_cb, &cb->peer_bda,
943                 p_data->clcc.idx,
944                 p_data->clcc.inc ? BTHF_CLIENT_CALL_DIRECTION_INCOMING
945                                  : BTHF_CLIENT_CALL_DIRECTION_OUTGOING,
946                 (bthf_client_call_state_t)p_data->clcc.status,
947                 p_data->clcc.mpty ? BTHF_CLIENT_CALL_MPTY_TYPE_MULTI
948                                   : BTHF_CLIENT_CALL_MPTY_TYPE_SINGLE,
949                 p_data->clcc.number_present ? p_data->clcc.number : "");
950       break;
951 
952     case BTA_HF_CLIENT_CNUM_EVT:
953       if (p_data->cnum.service == 4) {
954         HAL_CBACK(bt_hf_client_callbacks, subscriber_info_cb, &cb->peer_bda,
955                   p_data->cnum.number, BTHF_CLIENT_SERVICE_VOICE);
956       } else if (p_data->cnum.service == 5) {
957         HAL_CBACK(bt_hf_client_callbacks, subscriber_info_cb, &cb->peer_bda,
958                   p_data->cnum.number, BTHF_CLIENT_SERVICE_FAX);
959       } else {
960         HAL_CBACK(bt_hf_client_callbacks, subscriber_info_cb, &cb->peer_bda,
961                   p_data->cnum.number, BTHF_CLIENT_SERVICE_UNKNOWN);
962       }
963       break;
964 
965     case BTA_HF_CLIENT_BTRH_EVT:
966       if (p_data->val.value <= BTRH_CLIENT_RESP_AND_HOLD_REJECT) {
967         HAL_CBACK(bt_hf_client_callbacks, resp_and_hold_cb, &cb->peer_bda,
968                   (bthf_client_resp_and_hold_t)p_data->val.value);
969       }
970       break;
971 
972     case BTA_HF_CLIENT_BSIR_EVT:
973       if (p_data->val.value != 0) {
974         HAL_CBACK(bt_hf_client_callbacks, in_band_ring_tone_cb, &cb->peer_bda,
975                   BTHF_CLIENT_IN_BAND_RINGTONE_PROVIDED);
976       } else {
977         HAL_CBACK(bt_hf_client_callbacks, in_band_ring_tone_cb, &cb->peer_bda,
978                   BTHF_CLIENT_IN_BAND_RINGTONE_NOT_PROVIDED);
979       }
980       break;
981 
982     case BTA_HF_CLIENT_AUDIO_OPEN_EVT:
983       HAL_CBACK(bt_hf_client_callbacks, audio_state_cb, &cb->peer_bda,
984                 BTHF_CLIENT_AUDIO_STATE_CONNECTED);
985       break;
986 
987     case BTA_HF_CLIENT_AUDIO_MSBC_OPEN_EVT:
988       HAL_CBACK(bt_hf_client_callbacks, audio_state_cb, &cb->peer_bda,
989                 BTHF_CLIENT_AUDIO_STATE_CONNECTED_MSBC);
990       break;
991 
992     case BTA_HF_CLIENT_AUDIO_CLOSE_EVT:
993       HAL_CBACK(bt_hf_client_callbacks, audio_state_cb, &cb->peer_bda,
994                 BTHF_CLIENT_AUDIO_STATE_DISCONNECTED);
995       break;
996     case BTA_HF_CLIENT_RING_INDICATION:
997       HAL_CBACK(bt_hf_client_callbacks, ring_indication_cb, &cb->peer_bda);
998       break;
999     case BTA_HF_CLIENT_UNKNOWN_EVT:
1000       HAL_CBACK(bt_hf_client_callbacks, unknown_event_cb, &cb->peer_bda,
1001                 p_data->unknown.event_string);
1002       break;
1003     default:
1004       BTIF_TRACE_WARNING("%s: Unhandled event: %d", __func__, event);
1005       break;
1006   }
1007 }
1008 
1009 /*******************************************************************************
1010  *
1011  * Function         bta_hf_client_evt
1012  *
1013  * Description      Switches context from BTA to BTIF for all HF Client events
1014  *
1015  * Returns          void
1016  *
1017  ******************************************************************************/
1018 
bta_hf_client_evt(tBTA_HF_CLIENT_EVT event,tBTA_HF_CLIENT * p_data)1019 static void bta_hf_client_evt(tBTA_HF_CLIENT_EVT event,
1020                               tBTA_HF_CLIENT* p_data) {
1021   bt_status_t status;
1022 
1023   /* switch context to btif task context (copy full union size for convenience)
1024    */
1025   status = btif_transfer_context(btif_hf_client_upstreams_evt, (uint16_t)event,
1026                                  (char*)p_data, sizeof(*p_data), NULL);
1027 
1028   /* catch any failed context transfers */
1029   ASSERTC(status == BT_STATUS_SUCCESS, "context transfer failed", status);
1030 }
1031 
1032 /*******************************************************************************
1033  *
1034  * Function         btif_hf_client_execute_service
1035  *
1036  * Description      Initializes/Shuts down the service
1037  *
1038  * Returns          BT_STATUS_SUCCESS on success, BT_STATUS_FAIL otherwise
1039  *
1040  ******************************************************************************/
btif_hf_client_execute_service(bool b_enable)1041 bt_status_t btif_hf_client_execute_service(bool b_enable) {
1042   BTIF_TRACE_EVENT("%s: enable: %d", __func__, b_enable);
1043 
1044   tBTA_HF_CLIENT_FEAT features = BTIF_HF_CLIENT_FEATURES;
1045   uint16_t hfp_version = BTA_HFP_VERSION;
1046   if (hfp_version >= HFP_VERSION_1_7) {
1047     features |= BTA_HF_CLIENT_FEAT_ESCO_S4;
1048   }
1049 
1050   if (b_enable) {
1051     /* Enable and register with BTA-HFClient */
1052     BTIF_TRACE_EVENT("%s: support codec negotiation %d ", __func__,
1053                      features);
1054     BTA_HfClientEnable(bta_hf_client_evt, features,
1055                        BTIF_HF_CLIENT_SERVICE_NAME);
1056   } else {
1057     BTA_HfClientDisable();
1058   }
1059   return BT_STATUS_SUCCESS;
1060 }
1061 
1062 /*******************************************************************************
1063  *
1064  * Function         btif_hf_get_interface
1065  *
1066  * Description      Get the hf callback interface
1067  *
1068  * Returns          bthf_interface_t
1069  *
1070  ******************************************************************************/
btif_hf_client_get_interface(void)1071 const bthf_client_interface_t* btif_hf_client_get_interface(void) {
1072   BTIF_TRACE_EVENT("%s", __func__);
1073   return &bthfClientInterface;
1074 }
1075