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 * Filename: btif_hf.c 22 * 23 * Description: Handsfree Profile Bluetooth Interface 24 * 25 * 26 ******************************************************************************/ 27 28 #define LOG_TAG "bt_btif_hf" 29 30 #include <stdlib.h> 31 #include <string.h> 32 #include <time.h> 33 34 #include <hardware/bluetooth.h> 35 #include <hardware/bt_hf.h> 36 37 #include "bta/include/utl.h" 38 #include "bta_ag_api.h" 39 #include "btif_common.h" 40 #include "btif_hf.h" 41 #include "btif_profile_queue.h" 42 #include "btif_util.h" 43 #include "osi/include/properties.h" 44 45 /******************************************************************************* 46 * Constants & Macros 47 ******************************************************************************/ 48 #ifndef BTIF_HSAG_SERVICE_NAME 49 #define BTIF_HSAG_SERVICE_NAME ("Headset Gateway") 50 #endif 51 52 #ifndef BTIF_HFAG_SERVICE_NAME 53 #define BTIF_HFAG_SERVICE_NAME ("Handsfree Gateway") 54 #endif 55 56 #ifndef BTIF_HF_SERVICES 57 #define BTIF_HF_SERVICES (BTA_HSP_SERVICE_MASK | BTA_HFP_SERVICE_MASK) 58 #endif 59 60 #ifndef BTIF_HF_SERVICE_NAMES 61 #define BTIF_HF_SERVICE_NAMES \ 62 { BTIF_HSAG_SERVICE_NAME, BTIF_HFAG_SERVICE_NAME } 63 #endif 64 65 #ifndef BTIF_HF_SECURITY 66 #define BTIF_HF_SECURITY (BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT) 67 #endif 68 69 #ifndef BTIF_HF_FEATURES 70 #define BTIF_HF_FEATURES \ 71 (BTA_AG_FEAT_3WAY | BTA_AG_FEAT_ECNR | BTA_AG_FEAT_REJECT | \ 72 BTA_AG_FEAT_ECS | BTA_AG_FEAT_EXTERR | BTA_AG_FEAT_VREC | \ 73 BTA_AG_FEAT_CODEC | BTA_AG_FEAT_HF_IND | BTA_AG_FEAT_ESCO | \ 74 BTA_AG_FEAT_UNAT) 75 #endif 76 77 /* HF features supported at runtime */ 78 static uint32_t btif_hf_features = BTIF_HF_FEATURES; 79 80 #define BTIF_HF_CALL_END_TIMEOUT 6 81 82 #define BTIF_HF_INVALID_IDX (-1) 83 84 /* Number of BTIF-HF control blocks */ 85 #define BTIF_HF_NUM_CB 2 86 87 /* Max HF clients supported from App */ 88 uint16_t btif_max_hf_clients = 1; 89 90 /* HF app ids for service registration */ 91 typedef enum { 92 BTIF_HF_ID_1 = 0, 93 BTIF_HF_ID_2, 94 #if (BTIF_HF_NUM_CB == 3) 95 BTIF_HF_ID_3 96 #endif 97 } bthf_hf_id_t; 98 99 uint16_t bthf_hf_id[BTIF_HF_NUM_CB] = {BTIF_HF_ID_1, BTIF_HF_ID_2, 100 #if (BTIF_HF_NUM_CB == 3) 101 BTIF_HF_ID_3 102 #endif 103 }; 104 105 /******************************************************************************* 106 * Local type definitions 107 ******************************************************************************/ 108 109 /******************************************************************************* 110 * Static variables 111 ******************************************************************************/ 112 static bthf_callbacks_t* bt_hf_callbacks = NULL; 113 static int hf_idx = BTIF_HF_INVALID_IDX; 114 115 #define CHECK_BTHF_INIT() \ 116 do { \ 117 if (bt_hf_callbacks == NULL) { \ 118 BTIF_TRACE_WARNING("BTHF: %s: BTHF not initialized", __func__); \ 119 return BT_STATUS_NOT_READY; \ 120 } else { \ 121 BTIF_TRACE_EVENT("BTHF: %s", __func__); \ 122 } \ 123 } while (0) 124 125 /* BTIF-HF control block to map bdaddr to BTA handle */ 126 typedef struct _btif_hf_cb { 127 uint16_t handle; 128 RawAddress connected_bda; 129 bthf_connection_state_t state; 130 bthf_vr_state_t vr_state; 131 tBTA_AG_PEER_FEAT peer_feat; 132 int num_active; 133 int num_held; 134 struct timespec call_end_timestamp; 135 struct timespec connected_timestamp; 136 bthf_call_state_t call_setup_state; 137 } btif_hf_cb_t; 138 139 static btif_hf_cb_t btif_hf_cb[BTIF_HF_NUM_CB]; 140 141 /******************************************************************************* 142 * Static functions 143 ******************************************************************************/ 144 145 /******************************************************************************* 146 * Externs 147 ******************************************************************************/ 148 /* By default, even though codec negotiation is enabled, we will not use WBS as 149 * the default 150 * codec unless this variable is set to true. 151 */ 152 #ifndef BTIF_HF_WBS_PREFERRED 153 #define BTIF_HF_WBS_PREFERRED false 154 #endif 155 156 bool btif_conf_hf_force_wbs = BTIF_HF_WBS_PREFERRED; 157 158 /******************************************************************************* 159 * Functions 160 ******************************************************************************/ 161 162 /******************************************************************************* 163 * 164 * Function is_connected 165 * 166 * Description Internal function to check if HF is connected 167 * 168 * Returns true if connected 169 * 170 ******************************************************************************/ 171 static bool is_connected(RawAddress* bd_addr) { 172 int i; 173 for (i = 0; i < btif_max_hf_clients; ++i) { 174 if (((btif_hf_cb[i].state == BTHF_CONNECTION_STATE_CONNECTED) || 175 (btif_hf_cb[i].state == BTHF_CONNECTION_STATE_SLC_CONNECTED)) && 176 (!bd_addr || *bd_addr == btif_hf_cb[i].connected_bda)) 177 return true; 178 } 179 return false; 180 } 181 182 /******************************************************************************* 183 * 184 * Function btif_hf_idx_by_bdaddr 185 * 186 * Description Internal function to get idx by bdaddr 187 * 188 * Returns idx 189 * 190 ******************************************************************************/ 191 static int btif_hf_idx_by_bdaddr(RawAddress* bd_addr) { 192 int i; 193 for (i = 0; i < btif_max_hf_clients; ++i) { 194 if (*bd_addr == btif_hf_cb[i].connected_bda) return i; 195 } 196 return BTIF_HF_INVALID_IDX; 197 } 198 199 /******************************************************************************* 200 * 201 * Function callstate_to_callsetup 202 * 203 * Description Converts HAL call state to BTA call setup indicator value 204 * 205 * Returns BTA call indicator value 206 * 207 ******************************************************************************/ 208 static uint8_t callstate_to_callsetup(bthf_call_state_t call_state) { 209 uint8_t call_setup = 0; 210 if (call_state == BTHF_CALL_STATE_INCOMING) call_setup = 1; 211 if (call_state == BTHF_CALL_STATE_DIALING) call_setup = 2; 212 if (call_state == BTHF_CALL_STATE_ALERTING) call_setup = 3; 213 214 return call_setup; 215 } 216 217 /******************************************************************************* 218 * 219 * Function send_at_result 220 * 221 * Description Send AT result code (OK/ERROR) 222 * 223 * Returns void 224 * 225 ******************************************************************************/ 226 static void send_at_result(uint8_t ok_flag, uint16_t errcode, int idx) { 227 tBTA_AG_RES_DATA ag_res; 228 memset(&ag_res, 0, sizeof(ag_res)); 229 230 ag_res.ok_flag = ok_flag; 231 if (ok_flag == BTA_AG_OK_ERROR) { 232 ag_res.errcode = errcode; 233 } 234 235 BTA_AgResult(btif_hf_cb[idx].handle, BTA_AG_UNAT_RES, &ag_res); 236 } 237 238 /******************************************************************************* 239 * 240 * Function send_indicator_update 241 * 242 * Description Send indicator update (CIEV) 243 * 244 * Returns void 245 * 246 ******************************************************************************/ 247 static void send_indicator_update(uint16_t indicator, uint16_t value) { 248 tBTA_AG_RES_DATA ag_res; 249 250 memset(&ag_res, 0, sizeof(tBTA_AG_RES_DATA)); 251 ag_res.ind.id = indicator; 252 ag_res.ind.value = value; 253 254 BTA_AgResult(BTA_AG_HANDLE_ALL, BTA_AG_IND_RES, &ag_res); 255 } 256 257 void clear_phone_state_multihf(int idx) { 258 btif_hf_cb[idx].call_setup_state = BTHF_CALL_STATE_IDLE; 259 btif_hf_cb[idx].num_active = btif_hf_cb[idx].num_held = 0; 260 } 261 262 /******************************************************************************* 263 * 264 * Function btif_hf_latest_connected_idx 265 * 266 * Description Returns idx for latest connected HF 267 * 268 * Returns int 269 * 270 ******************************************************************************/ 271 static int btif_hf_latest_connected_idx() { 272 struct timespec now, conn_time_delta; 273 int latest_conn_idx = BTIF_HF_INVALID_IDX, i; 274 275 clock_gettime(CLOCK_MONOTONIC, &now); 276 conn_time_delta.tv_sec = now.tv_sec; 277 278 for (i = 0; i < btif_max_hf_clients; i++) { 279 if (btif_hf_cb[i].state == BTHF_CONNECTION_STATE_SLC_CONNECTED) { 280 if ((now.tv_sec - btif_hf_cb[i].connected_timestamp.tv_sec) < 281 conn_time_delta.tv_sec) { 282 conn_time_delta.tv_sec = 283 now.tv_sec - btif_hf_cb[i].connected_timestamp.tv_sec; 284 latest_conn_idx = i; 285 } 286 } 287 } 288 return latest_conn_idx; 289 } 290 291 /******************************************************************************* 292 * 293 * Function btif_hf_check_if_slc_connected 294 * 295 * Description Returns BT_STATUS_SUCCESS if SLC is up for any HF 296 * 297 * Returns bt_status_t 298 * 299 ******************************************************************************/ 300 static bt_status_t btif_hf_check_if_slc_connected() { 301 if (bt_hf_callbacks == NULL) { 302 BTIF_TRACE_WARNING("BTHF: %s: BTHF not initialized", __func__); 303 return BT_STATUS_NOT_READY; 304 } else { 305 int i; 306 for (i = 0; i < btif_max_hf_clients; i++) { 307 if (btif_hf_cb[i].state == BTHF_CONNECTION_STATE_SLC_CONNECTED) { 308 BTIF_TRACE_EVENT("BTHF: %s: slc connected for idx = %d", __func__, i); 309 return BT_STATUS_SUCCESS; 310 } 311 } 312 BTIF_TRACE_WARNING("BTHF: %s: No SLC connection up", __func__); 313 return BT_STATUS_NOT_READY; 314 } 315 } 316 317 /***************************************************************************** 318 * Section name (Group of functions) 319 ****************************************************************************/ 320 321 /***************************************************************************** 322 * 323 * btif hf api functions (no context switch) 324 * 325 ****************************************************************************/ 326 327 /******************************************************************************* 328 * 329 * Function btif_hf_upstreams_evt 330 * 331 * Description Executes HF UPSTREAMS events in btif context 332 * 333 * Returns void 334 * 335 ******************************************************************************/ 336 static void btif_hf_upstreams_evt(uint16_t event, char* p_param) { 337 tBTA_AG* p_data = (tBTA_AG*)p_param; 338 int idx = p_data->hdr.handle - 1; 339 340 BTIF_TRACE_DEBUG("%s: event=%s", __func__, dump_hf_event(event)); 341 342 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 343 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 344 return; 345 } 346 347 switch (event) { 348 case BTA_AG_ENABLE_EVT: 349 case BTA_AG_DISABLE_EVT: 350 break; 351 352 case BTA_AG_REGISTER_EVT: 353 btif_hf_cb[idx].handle = p_data->reg.hdr.handle; 354 BTIF_TRACE_DEBUG( 355 "%s: BTA_AG_REGISTER_EVT," 356 "btif_hf_cb.handle = %d", 357 __func__, btif_hf_cb[idx].handle); 358 break; 359 360 case BTA_AG_OPEN_EVT: 361 if (p_data->open.status == BTA_AG_SUCCESS) { 362 btif_hf_cb[idx].connected_bda = p_data->open.bd_addr; 363 btif_hf_cb[idx].state = BTHF_CONNECTION_STATE_CONNECTED; 364 btif_hf_cb[idx].peer_feat = 0; 365 clear_phone_state_multihf(idx); 366 } else if (btif_hf_cb[idx].state == BTHF_CONNECTION_STATE_CONNECTING) { 367 btif_hf_cb[idx].state = BTHF_CONNECTION_STATE_DISCONNECTED; 368 } else { 369 BTIF_TRACE_WARNING( 370 "%s: AG open failed, but another device connected. status=%d " 371 "state=%d connected device=%s", 372 __func__, p_data->open.status, btif_hf_cb[idx].state, 373 btif_hf_cb[idx].connected_bda.ToString().c_str()); 374 break; 375 } 376 377 HAL_CBACK(bt_hf_callbacks, connection_state_cb, btif_hf_cb[idx].state, 378 &btif_hf_cb[idx].connected_bda); 379 380 if (btif_hf_cb[idx].state == BTHF_CONNECTION_STATE_DISCONNECTED) 381 btif_hf_cb[idx].connected_bda = RawAddress::kAny; 382 383 if (p_data->open.status != BTA_AG_SUCCESS) btif_queue_advance(); 384 break; 385 386 case BTA_AG_CLOSE_EVT: 387 btif_hf_cb[idx].connected_timestamp.tv_sec = 0; 388 btif_hf_cb[idx].state = BTHF_CONNECTION_STATE_DISCONNECTED; 389 BTIF_TRACE_DEBUG( 390 "%s: BTA_AG_CLOSE_EVT," 391 "idx = %d, btif_hf_cb.handle = %d", 392 __func__, idx, btif_hf_cb[idx].handle); 393 HAL_CBACK(bt_hf_callbacks, connection_state_cb, btif_hf_cb[idx].state, 394 &btif_hf_cb[idx].connected_bda); 395 btif_hf_cb[idx].connected_bda = RawAddress::kAny; 396 btif_hf_cb[idx].peer_feat = 0; 397 clear_phone_state_multihf(idx); 398 hf_idx = btif_hf_latest_connected_idx(); 399 /* If AG_OPEN was received but SLC was not setup in a specified time (10 400 *seconds), 401 ** then AG_CLOSE may be received. We need to advance the queue here 402 */ 403 btif_queue_advance(); 404 break; 405 406 case BTA_AG_CONN_EVT: 407 clock_gettime(CLOCK_MONOTONIC, &btif_hf_cb[idx].connected_timestamp); 408 BTIF_TRACE_DEBUG("%s: BTA_AG_CONN_EVT, idx = %d ", __func__, idx); 409 btif_hf_cb[idx].peer_feat = p_data->conn.peer_feat; 410 btif_hf_cb[idx].state = BTHF_CONNECTION_STATE_SLC_CONNECTED; 411 hf_idx = btif_hf_latest_connected_idx(); 412 413 HAL_CBACK(bt_hf_callbacks, connection_state_cb, btif_hf_cb[idx].state, 414 &btif_hf_cb[idx].connected_bda); 415 btif_queue_advance(); 416 break; 417 418 case BTA_AG_AUDIO_OPEN_EVT: 419 hf_idx = idx; 420 HAL_CBACK(bt_hf_callbacks, audio_state_cb, BTHF_AUDIO_STATE_CONNECTED, 421 &btif_hf_cb[idx].connected_bda); 422 break; 423 424 case BTA_AG_AUDIO_CLOSE_EVT: 425 HAL_CBACK(bt_hf_callbacks, audio_state_cb, BTHF_AUDIO_STATE_DISCONNECTED, 426 &btif_hf_cb[idx].connected_bda); 427 break; 428 429 /* BTA auto-responds, silently discard */ 430 case BTA_AG_SPK_EVT: 431 case BTA_AG_MIC_EVT: 432 HAL_CBACK(bt_hf_callbacks, volume_cmd_cb, 433 (event == BTA_AG_SPK_EVT) ? BTHF_VOLUME_TYPE_SPK 434 : BTHF_VOLUME_TYPE_MIC, 435 p_data->val.num, &btif_hf_cb[idx].connected_bda); 436 break; 437 438 case BTA_AG_AT_A_EVT: 439 if ((btif_hf_cb[0].num_held + btif_hf_cb[0].num_active) == 0) 440 hf_idx = idx; 441 else 442 BTIF_TRACE_DEBUG("Donot set hf_idx for ATA since already in a call"); 443 444 HAL_CBACK(bt_hf_callbacks, answer_call_cmd_cb, 445 &btif_hf_cb[idx].connected_bda); 446 break; 447 448 /* Java needs to send OK/ERROR for these commands */ 449 case BTA_AG_AT_BLDN_EVT: 450 case BTA_AG_AT_D_EVT: 451 if ((btif_hf_cb[0].num_held + btif_hf_cb[0].num_active) == 0) 452 hf_idx = idx; 453 else 454 BTIF_TRACE_DEBUG("Donot set hf_idx for BLDN/D since already in a call"); 455 456 HAL_CBACK(bt_hf_callbacks, dial_call_cmd_cb, 457 (event == BTA_AG_AT_D_EVT) ? p_data->val.str : NULL, 458 &btif_hf_cb[idx].connected_bda); 459 break; 460 461 case BTA_AG_AT_CHUP_EVT: 462 HAL_CBACK(bt_hf_callbacks, hangup_call_cmd_cb, 463 &btif_hf_cb[idx].connected_bda); 464 break; 465 466 case BTA_AG_AT_CIND_EVT: 467 HAL_CBACK(bt_hf_callbacks, cind_cmd_cb, &btif_hf_cb[idx].connected_bda); 468 break; 469 470 case BTA_AG_AT_VTS_EVT: 471 HAL_CBACK(bt_hf_callbacks, dtmf_cmd_cb, p_data->val.str[0], 472 &btif_hf_cb[idx].connected_bda); 473 break; 474 475 case BTA_AG_AT_BVRA_EVT: 476 HAL_CBACK(bt_hf_callbacks, vr_cmd_cb, 477 (p_data->val.num == 1) ? BTHF_VR_STATE_STARTED 478 : BTHF_VR_STATE_STOPPED, 479 &btif_hf_cb[idx].connected_bda); 480 break; 481 482 case BTA_AG_AT_NREC_EVT: 483 HAL_CBACK(bt_hf_callbacks, nrec_cmd_cb, 484 (p_data->val.num == 1) ? BTHF_NREC_START : BTHF_NREC_STOP, 485 &btif_hf_cb[idx].connected_bda); 486 break; 487 488 /* TODO: Add a callback for CBC */ 489 case BTA_AG_AT_CBC_EVT: 490 break; 491 492 case BTA_AG_AT_CKPD_EVT: 493 HAL_CBACK(bt_hf_callbacks, key_pressed_cmd_cb, 494 &btif_hf_cb[idx].connected_bda); 495 break; 496 497 case BTA_AG_WBS_EVT: 498 BTIF_TRACE_DEBUG( 499 "BTA_AG_WBS_EVT Set codec status %d codec %d 1=CVSD 2=MSBC", 500 p_data->val.hdr.status, p_data->val.num); 501 if (p_data->val.num == BTA_AG_CODEC_CVSD) { 502 HAL_CBACK(bt_hf_callbacks, wbs_cb, BTHF_WBS_NO, 503 &btif_hf_cb[idx].connected_bda); 504 } else if (p_data->val.num == BTA_AG_CODEC_MSBC) { 505 HAL_CBACK(bt_hf_callbacks, wbs_cb, BTHF_WBS_YES, 506 &btif_hf_cb[idx].connected_bda); 507 } else { 508 HAL_CBACK(bt_hf_callbacks, wbs_cb, BTHF_WBS_NONE, 509 &btif_hf_cb[idx].connected_bda); 510 } 511 break; 512 513 /* Java needs to send OK/ERROR for these commands */ 514 case BTA_AG_AT_CHLD_EVT: 515 HAL_CBACK(bt_hf_callbacks, chld_cmd_cb, 516 (bthf_chld_type_t)atoi(p_data->val.str), 517 &btif_hf_cb[idx].connected_bda); 518 break; 519 520 case BTA_AG_AT_CLCC_EVT: 521 HAL_CBACK(bt_hf_callbacks, clcc_cmd_cb, &btif_hf_cb[idx].connected_bda); 522 break; 523 524 case BTA_AG_AT_COPS_EVT: 525 HAL_CBACK(bt_hf_callbacks, cops_cmd_cb, &btif_hf_cb[idx].connected_bda); 526 break; 527 528 case BTA_AG_AT_UNAT_EVT: 529 HAL_CBACK(bt_hf_callbacks, unknown_at_cmd_cb, p_data->val.str, 530 &btif_hf_cb[idx].connected_bda); 531 break; 532 533 case BTA_AG_AT_CNUM_EVT: 534 HAL_CBACK(bt_hf_callbacks, cnum_cmd_cb, &btif_hf_cb[idx].connected_bda); 535 break; 536 537 /* TODO: Some of these commands may need to be sent to app. For now respond 538 * with error */ 539 case BTA_AG_AT_BINP_EVT: 540 case BTA_AG_AT_BTRH_EVT: 541 send_at_result(BTA_AG_OK_ERROR, BTA_AG_ERR_OP_NOT_SUPPORTED, idx); 542 break; 543 case BTA_AG_AT_BAC_EVT: 544 BTIF_TRACE_DEBUG("AG Bitmap of peer-codecs %d", p_data->val.num); 545 /* If the peer supports mSBC and the BTIF preferred codec is also mSBC, 546 then 547 we should set the BTA AG Codec to mSBC. This would trigger a +BCS to mSBC 548 at the time 549 of SCO connection establishment */ 550 if ((btif_conf_hf_force_wbs == true) && 551 (p_data->val.num & BTA_AG_CODEC_MSBC)) { 552 BTIF_TRACE_EVENT("%s: btif_hf override-Preferred Codec to MSBC", 553 __func__); 554 BTA_AgSetCodec(btif_hf_cb[idx].handle, BTA_AG_CODEC_MSBC); 555 } else { 556 BTIF_TRACE_EVENT("%s btif_hf override-Preferred Codec to CVSD", 557 __func__); 558 BTA_AgSetCodec(btif_hf_cb[idx].handle, BTA_AG_CODEC_CVSD); 559 } 560 break; 561 case BTA_AG_AT_BCS_EVT: 562 BTIF_TRACE_DEBUG("%s: AG final selected codec is 0x%02x 1=CVSD 2=MSBC", 563 __func__, p_data->val.num); 564 /* No BTHF_WBS_NONE case, because HF1.6 supported device can send BCS */ 565 /* Only CVSD is considered narrow band speech */ 566 HAL_CBACK( 567 bt_hf_callbacks, wbs_cb, 568 (p_data->val.num == BTA_AG_CODEC_CVSD) ? BTHF_WBS_NO : BTHF_WBS_YES, 569 &btif_hf_cb[idx].connected_bda); 570 break; 571 572 case BTA_AG_AT_BIND_EVT: 573 if (p_data->val.hdr.status == BTA_AG_SUCCESS) { 574 HAL_CBACK(bt_hf_callbacks, bind_cb, p_data->val.str, 575 &btif_hf_cb[idx].connected_bda); 576 } 577 break; 578 579 case BTA_AG_AT_BIEV_EVT: 580 if (p_data->val.hdr.status == BTA_AG_SUCCESS) { 581 HAL_CBACK(bt_hf_callbacks, biev_cb, 582 (bthf_hf_ind_type_t)p_data->val.lidx, (int)p_data->val.num, 583 &btif_hf_cb[idx].connected_bda); 584 } 585 break; 586 default: 587 BTIF_TRACE_WARNING("%s: Unhandled event: %d", __func__, event); 588 break; 589 } 590 } 591 592 /******************************************************************************* 593 * 594 * Function bte_hf_evt 595 * 596 * Description Switches context from BTE to BTIF for all HF events 597 * 598 * Returns void 599 * 600 ******************************************************************************/ 601 602 static void bte_hf_evt(tBTA_AG_EVT event, tBTA_AG* p_data) { 603 bt_status_t status; 604 int param_len = 0; 605 606 /* TODO: BTA sends the union members and not tBTA_AG. If using 607 * param_len=sizeof(tBTA_AG), we get a crash on memcpy */ 608 if (BTA_AG_REGISTER_EVT == event) 609 param_len = sizeof(tBTA_AG_REGISTER); 610 else if (BTA_AG_OPEN_EVT == event) 611 param_len = sizeof(tBTA_AG_OPEN); 612 else if (BTA_AG_CONN_EVT == event) 613 param_len = sizeof(tBTA_AG_CONN); 614 else if ((BTA_AG_CLOSE_EVT == event) || (BTA_AG_AUDIO_OPEN_EVT == event) || 615 (BTA_AG_AUDIO_CLOSE_EVT == event)) 616 param_len = sizeof(tBTA_AG_HDR); 617 else if (p_data) 618 param_len = sizeof(tBTA_AG_VAL); 619 620 /* switch context to btif task context (copy full union size for convenience) 621 */ 622 status = btif_transfer_context(btif_hf_upstreams_evt, (uint16_t)event, 623 (char*)p_data, param_len, NULL); 624 625 /* catch any failed context transfers */ 626 ASSERTC(status == BT_STATUS_SUCCESS, "context transfer failed", status); 627 } 628 629 /******************************************************************************* 630 * 631 * Function btif_in_hf_generic_evt 632 * 633 * Description Processes generic events to be sent to JNI that are not 634 * triggered from the BTA. 635 * Always runs in BTIF context 636 * 637 * Returns void 638 * 639 ******************************************************************************/ 640 static void btif_in_hf_generic_evt(uint16_t event, char* p_param) { 641 int idx = btif_hf_idx_by_bdaddr((RawAddress*)p_param); 642 643 BTIF_TRACE_EVENT("%s: event=%d", __func__, event); 644 645 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 646 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 647 return; 648 } 649 650 switch (event) { 651 case BTIF_HFP_CB_AUDIO_CONNECTING: { 652 HAL_CBACK(bt_hf_callbacks, audio_state_cb, BTHF_AUDIO_STATE_CONNECTING, 653 &btif_hf_cb[idx].connected_bda); 654 } break; 655 default: { 656 BTIF_TRACE_WARNING("%s : Unknown event 0x%x", __func__, event); 657 } break; 658 } 659 } 660 661 static bool inband_ringing_property_enabled() { 662 char inband_ringing_flag[PROPERTY_VALUE_MAX] = {0}; 663 osi_property_get("persist.bluetooth.enableinbandringing", inband_ringing_flag, 664 "true"); 665 if (strncmp(inband_ringing_flag, "true", 4) == 0) { 666 BTIF_TRACE_DEBUG("%s: In-band ringing enabled by property", __func__); 667 return true; 668 } 669 return false; 670 } 671 672 /******************************************************************************* 673 * 674 * Function btif_hf_init 675 * 676 * Description initializes the hf interface 677 * 678 * Returns bt_status_t 679 * 680 ******************************************************************************/ 681 static bt_status_t init(bthf_callbacks_t* callbacks, int max_hf_clients, 682 bool inband_ringing_supported) { 683 bool inband_ringing_property_enable = inband_ringing_property_enabled(); 684 if (inband_ringing_supported && inband_ringing_property_enable) { 685 btif_hf_features |= BTA_AG_FEAT_INBAND; 686 } else { 687 btif_hf_features &= ~BTA_AG_FEAT_INBAND; 688 } 689 btif_max_hf_clients = max_hf_clients; 690 BTIF_TRACE_DEBUG( 691 "%s: btif_hf_features=%zu, max_hf_clients=%d, " 692 "inband_ringing=[supported=%d, enabled=%d]", 693 __func__, btif_hf_features, btif_max_hf_clients, inband_ringing_supported, 694 inband_ringing_property_enable); 695 bt_hf_callbacks = callbacks; 696 memset(&btif_hf_cb, 0, sizeof(btif_hf_cb)); 697 698 /* Invoke the enable service API to the core to set the appropriate service_id 699 * Internally, the HSP_SERVICE_ID shall also be enabled if HFP is enabled 700 * (phone) 701 * othwerwise only HSP is enabled (tablet) 702 */ 703 #if (defined(BTIF_HF_SERVICES) && (BTIF_HF_SERVICES & BTA_HFP_SERVICE_MASK)) 704 btif_enable_service(BTA_HFP_SERVICE_ID); 705 #else 706 btif_enable_service(BTA_HSP_SERVICE_ID); 707 #endif 708 709 for (int i = 0; i < btif_max_hf_clients; i++) clear_phone_state_multihf(i); 710 711 return BT_STATUS_SUCCESS; 712 } 713 714 /******************************************************************************* 715 * 716 * Function connect 717 * 718 * Description connect to headset 719 * 720 * Returns bt_status_t 721 * 722 ******************************************************************************/ 723 static bt_status_t connect_int(RawAddress* bd_addr, uint16_t uuid) { 724 CHECK_BTHF_INIT(); 725 int i; 726 for (i = 0; i < btif_max_hf_clients;) { 727 if (((btif_hf_cb[i].state == BTHF_CONNECTION_STATE_CONNECTED) || 728 (btif_hf_cb[i].state == BTHF_CONNECTION_STATE_SLC_CONNECTED))) 729 i++; 730 else 731 break; 732 } 733 734 if (i == btif_max_hf_clients) return BT_STATUS_BUSY; 735 736 if (!is_connected(bd_addr)) { 737 btif_hf_cb[i].state = BTHF_CONNECTION_STATE_CONNECTING; 738 btif_hf_cb[i].connected_bda = *bd_addr; 739 740 BTA_AgOpen(btif_hf_cb[i].handle, btif_hf_cb[i].connected_bda, 741 BTIF_HF_SECURITY, BTIF_HF_SERVICES); 742 return BT_STATUS_SUCCESS; 743 } 744 745 return BT_STATUS_BUSY; 746 } 747 748 static bt_status_t connect(RawAddress* bd_addr) { 749 CHECK_BTHF_INIT(); 750 return btif_queue_connect(UUID_SERVCLASS_AG_HANDSFREE, bd_addr, connect_int); 751 } 752 753 /******************************************************************************* 754 * 755 * Function disconnect 756 * 757 * Description disconnect from headset 758 * 759 * Returns bt_status_t 760 * 761 ******************************************************************************/ 762 static bt_status_t disconnect(RawAddress* bd_addr) { 763 CHECK_BTHF_INIT(); 764 765 int idx = btif_hf_idx_by_bdaddr(bd_addr); 766 767 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 768 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 769 return BT_STATUS_FAIL; 770 } 771 772 if (is_connected(bd_addr) && (idx != BTIF_HF_INVALID_IDX)) { 773 BTA_AgClose(btif_hf_cb[idx].handle); 774 return BT_STATUS_SUCCESS; 775 } 776 777 return BT_STATUS_FAIL; 778 } 779 780 /******************************************************************************* 781 * 782 * Function connect_audio 783 * 784 * Description create an audio connection 785 * 786 * Returns bt_status_t 787 * 788 ******************************************************************************/ 789 static bt_status_t connect_audio(RawAddress* bd_addr) { 790 CHECK_BTHF_INIT(); 791 792 int idx = btif_hf_idx_by_bdaddr(bd_addr); 793 794 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 795 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 796 return BT_STATUS_FAIL; 797 } 798 799 /* Check if SLC is connected */ 800 if (btif_hf_check_if_slc_connected() != BT_STATUS_SUCCESS) 801 return BT_STATUS_NOT_READY; 802 803 if (is_connected(bd_addr) && (idx != BTIF_HF_INVALID_IDX)) { 804 BTA_AgAudioOpen(btif_hf_cb[idx].handle); 805 806 /* Inform the application that the audio connection has been initiated 807 * successfully */ 808 btif_transfer_context(btif_in_hf_generic_evt, BTIF_HFP_CB_AUDIO_CONNECTING, 809 (char*)bd_addr, sizeof(RawAddress), NULL); 810 return BT_STATUS_SUCCESS; 811 } 812 813 return BT_STATUS_FAIL; 814 } 815 816 /******************************************************************************* 817 * 818 * Function disconnect_audio 819 * 820 * Description close the audio connection 821 * 822 * Returns bt_status_t 823 * 824 ******************************************************************************/ 825 static bt_status_t disconnect_audio(RawAddress* bd_addr) { 826 CHECK_BTHF_INIT(); 827 828 int idx = btif_hf_idx_by_bdaddr(bd_addr); 829 830 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 831 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 832 return BT_STATUS_FAIL; 833 } 834 835 if (is_connected(bd_addr) && (idx != BTIF_HF_INVALID_IDX)) { 836 BTA_AgAudioClose(btif_hf_cb[idx].handle); 837 return BT_STATUS_SUCCESS; 838 } 839 840 return BT_STATUS_FAIL; 841 } 842 843 /******************************************************************************* 844 * 845 * Function start_voice_recognition 846 * 847 * Description start voice recognition 848 * 849 * Returns bt_status_t 850 * 851 ******************************************************************************/ 852 static bt_status_t start_voice_recognition(RawAddress* bd_addr) { 853 CHECK_BTHF_INIT(); 854 855 int idx = btif_hf_idx_by_bdaddr(bd_addr); 856 857 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 858 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 859 return BT_STATUS_FAIL; 860 } 861 862 if (is_connected(bd_addr) && (idx != BTIF_HF_INVALID_IDX)) { 863 if (btif_hf_cb[idx].peer_feat & BTA_AG_PEER_FEAT_VREC) { 864 tBTA_AG_RES_DATA ag_res; 865 memset(&ag_res, 0, sizeof(ag_res)); 866 ag_res.state = 1; 867 BTA_AgResult(btif_hf_cb[idx].handle, BTA_AG_BVRA_RES, &ag_res); 868 869 return BT_STATUS_SUCCESS; 870 } else { 871 return BT_STATUS_UNSUPPORTED; 872 } 873 } 874 875 return BT_STATUS_NOT_READY; 876 } 877 878 /******************************************************************************* 879 * 880 * Function stop_voice_recognition 881 * 882 * Description stop voice recognition 883 * 884 * Returns bt_status_t 885 * 886 ******************************************************************************/ 887 static bt_status_t stop_voice_recognition(RawAddress* bd_addr) { 888 CHECK_BTHF_INIT(); 889 890 int idx = btif_hf_idx_by_bdaddr(bd_addr); 891 892 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 893 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 894 return BT_STATUS_FAIL; 895 } 896 897 if (is_connected(bd_addr) && (idx != BTIF_HF_INVALID_IDX)) { 898 if (btif_hf_cb[idx].peer_feat & BTA_AG_PEER_FEAT_VREC) { 899 tBTA_AG_RES_DATA ag_res; 900 memset(&ag_res, 0, sizeof(ag_res)); 901 ag_res.state = 0; 902 BTA_AgResult(btif_hf_cb[idx].handle, BTA_AG_BVRA_RES, &ag_res); 903 904 return BT_STATUS_SUCCESS; 905 } else { 906 return BT_STATUS_UNSUPPORTED; 907 } 908 } 909 910 return BT_STATUS_NOT_READY; 911 } 912 913 /******************************************************************************* 914 * 915 * Function volume_control 916 * 917 * Description volume control 918 * 919 * Returns bt_status_t 920 * 921 ******************************************************************************/ 922 static bt_status_t volume_control(bthf_volume_type_t type, int volume, 923 RawAddress* bd_addr) { 924 CHECK_BTHF_INIT(); 925 926 int idx = btif_hf_idx_by_bdaddr(bd_addr); 927 928 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 929 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 930 return BT_STATUS_FAIL; 931 } 932 933 tBTA_AG_RES_DATA ag_res; 934 memset(&ag_res, 0, sizeof(tBTA_AG_RES_DATA)); 935 if (is_connected(bd_addr) && (idx != BTIF_HF_INVALID_IDX)) { 936 ag_res.num = volume; 937 BTA_AgResult( 938 btif_hf_cb[idx].handle, 939 (type == BTHF_VOLUME_TYPE_SPK) ? BTA_AG_SPK_RES : BTA_AG_MIC_RES, 940 &ag_res); 941 return BT_STATUS_SUCCESS; 942 } 943 944 return BT_STATUS_FAIL; 945 } 946 947 /******************************************************************************* 948 * 949 * Function device_status_notification 950 * 951 * Description Combined device status change notification 952 * 953 * Returns bt_status_t 954 * 955 ******************************************************************************/ 956 static bt_status_t device_status_notification(bthf_network_state_t ntk_state, 957 bthf_service_type_t svc_type, 958 int signal, int batt_chg) { 959 CHECK_BTHF_INIT(); 960 961 if (is_connected(NULL)) { 962 /* send all indicators to BTA. 963 ** BTA will make sure no duplicates are sent out 964 */ 965 send_indicator_update(BTA_AG_IND_SERVICE, 966 (ntk_state == BTHF_NETWORK_STATE_AVAILABLE) ? 1 : 0); 967 send_indicator_update(BTA_AG_IND_ROAM, 968 (svc_type == BTHF_SERVICE_TYPE_HOME) ? 0 : 1); 969 send_indicator_update(BTA_AG_IND_SIGNAL, signal); 970 send_indicator_update(BTA_AG_IND_BATTCHG, batt_chg); 971 return BT_STATUS_SUCCESS; 972 } 973 974 return BT_STATUS_SUCCESS; 975 } 976 977 /******************************************************************************* 978 * 979 * Function cops_response 980 * 981 * Description Response for COPS command 982 * 983 * Returns bt_status_t 984 * 985 ******************************************************************************/ 986 static bt_status_t cops_response(const char* cops, RawAddress* bd_addr) { 987 CHECK_BTHF_INIT(); 988 989 int idx = btif_hf_idx_by_bdaddr(bd_addr); 990 991 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 992 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 993 return BT_STATUS_FAIL; 994 } 995 996 if (is_connected(bd_addr) && (idx != BTIF_HF_INVALID_IDX)) { 997 tBTA_AG_RES_DATA ag_res; 998 999 /* Format the response */ 1000 snprintf(ag_res.str, sizeof(ag_res.str), "0,0,\"%.16s\"", cops); 1001 ag_res.ok_flag = BTA_AG_OK_DONE; 1002 1003 BTA_AgResult(btif_hf_cb[idx].handle, BTA_AG_COPS_RES, &ag_res); 1004 return BT_STATUS_SUCCESS; 1005 } 1006 return BT_STATUS_FAIL; 1007 } 1008 1009 /******************************************************************************* 1010 * 1011 * Function cind_response 1012 * 1013 * Description Response for CIND command 1014 * 1015 * Returns bt_status_t 1016 * 1017 ******************************************************************************/ 1018 static bt_status_t cind_response(int svc, int num_active, int num_held, 1019 bthf_call_state_t call_setup_state, int signal, 1020 int roam, int batt_chg, RawAddress* bd_addr) { 1021 CHECK_BTHF_INIT(); 1022 1023 int idx = btif_hf_idx_by_bdaddr(bd_addr); 1024 1025 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 1026 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 1027 return BT_STATUS_FAIL; 1028 } 1029 1030 if (is_connected(bd_addr) && (idx != BTIF_HF_INVALID_IDX)) { 1031 tBTA_AG_RES_DATA ag_res; 1032 1033 memset(&ag_res, 0, sizeof(ag_res)); 1034 /* per the errata 2043, call=1 implies atleast one call is in progress 1035 *(active/held) 1036 ** https://www.bluetooth.org/errata/errata_view.cfm?errata_id=2043 1037 **/ 1038 snprintf( 1039 ag_res.str, sizeof(ag_res.str), "%d,%d,%d,%d,%d,%d,%d", 1040 (num_active + num_held) ? 1 : 0, /* Call state */ 1041 callstate_to_callsetup(call_setup_state), /* Callsetup state */ 1042 svc, /* network service */ 1043 signal, /* Signal strength */ 1044 roam, /* Roaming indicator */ 1045 batt_chg, /* Battery level */ 1046 ((num_held == 0) ? 0 : ((num_active == 0) ? 2 : 1))); /* Call held */ 1047 1048 BTA_AgResult(btif_hf_cb[idx].handle, BTA_AG_CIND_RES, &ag_res); 1049 1050 return BT_STATUS_SUCCESS; 1051 } 1052 1053 return BT_STATUS_FAIL; 1054 } 1055 1056 /******************************************************************************* 1057 * 1058 * Function bind_response 1059 * 1060 * Description Send +BIND response 1061 * 1062 * Returns bt_status_t 1063 * 1064 ******************************************************************************/ 1065 static bt_status_t bind_response(bthf_hf_ind_type_t ind_id, 1066 bthf_hf_ind_status_t ind_status, 1067 RawAddress* bd_addr) { 1068 CHECK_BTHF_INIT(); 1069 1070 int index = btif_hf_idx_by_bdaddr(bd_addr); 1071 if (!is_connected(bd_addr) || index == BTIF_HF_INVALID_IDX) 1072 return BT_STATUS_FAIL; 1073 1074 tBTA_AG_RES_DATA ag_res; 1075 memset(&ag_res, 0, sizeof(ag_res)); 1076 ag_res.ind.id = ind_id; 1077 ag_res.ind.on_demand = (ind_status == BTHF_HF_IND_ENABLED); 1078 1079 BTA_AgResult(btif_hf_cb[index].handle, BTA_AG_BIND_RES, &ag_res); 1080 return BT_STATUS_SUCCESS; 1081 } 1082 1083 static bt_status_t set_sco_allowed(bool value) { 1084 CHECK_BTHF_INIT(); 1085 1086 BTA_AgSetScoAllowed(value); 1087 return BT_STATUS_SUCCESS; 1088 } 1089 1090 /******************************************************************************* 1091 * 1092 * Function formatted_at_response 1093 * 1094 * Description Pre-formatted AT response, typically in response to unknown 1095 * AT cmd 1096 * 1097 * Returns bt_status_t 1098 * 1099 ******************************************************************************/ 1100 static bt_status_t formatted_at_response(const char* rsp, RawAddress* bd_addr) { 1101 CHECK_BTHF_INIT(); 1102 tBTA_AG_RES_DATA ag_res; 1103 int idx = btif_hf_idx_by_bdaddr(bd_addr); 1104 1105 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 1106 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 1107 return BT_STATUS_FAIL; 1108 } 1109 1110 if (is_connected(bd_addr) && (idx != BTIF_HF_INVALID_IDX)) { 1111 /* Format the response and send */ 1112 memset(&ag_res, 0, sizeof(ag_res)); 1113 strncpy(ag_res.str, rsp, BTA_AG_AT_MAX_LEN); 1114 BTA_AgResult(btif_hf_cb[idx].handle, BTA_AG_UNAT_RES, &ag_res); 1115 1116 return BT_STATUS_SUCCESS; 1117 } 1118 1119 return BT_STATUS_FAIL; 1120 } 1121 1122 /******************************************************************************* 1123 * 1124 * Function at_response 1125 * 1126 * Description ok/error response 1127 * 1128 * Returns bt_status_t 1129 * 1130 ******************************************************************************/ 1131 static bt_status_t at_response(bthf_at_response_t response_code, int error_code, 1132 RawAddress* bd_addr) { 1133 CHECK_BTHF_INIT(); 1134 1135 int idx = btif_hf_idx_by_bdaddr(bd_addr); 1136 1137 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 1138 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 1139 return BT_STATUS_FAIL; 1140 } 1141 1142 if (is_connected(bd_addr) && (idx != BTIF_HF_INVALID_IDX)) { 1143 send_at_result((response_code == BTHF_AT_RESPONSE_OK) ? BTA_AG_OK_DONE 1144 : BTA_AG_OK_ERROR, 1145 error_code, idx); 1146 return BT_STATUS_SUCCESS; 1147 } 1148 1149 return BT_STATUS_FAIL; 1150 } 1151 1152 /******************************************************************************* 1153 * 1154 * Function clcc_response 1155 * 1156 * Description response for CLCC command 1157 * Can be iteratively called for each call index. Call index 1158 * of 0 will be treated as NULL termination (Completes 1159 * response) 1160 * 1161 * Returns bt_status_t 1162 * 1163 ******************************************************************************/ 1164 static bt_status_t clcc_response(int index, bthf_call_direction_t dir, 1165 bthf_call_state_t state, bthf_call_mode_t mode, 1166 bthf_call_mpty_type_t mpty, const char* number, 1167 bthf_call_addrtype_t type, 1168 RawAddress* bd_addr) { 1169 CHECK_BTHF_INIT(); 1170 1171 int idx = btif_hf_idx_by_bdaddr(bd_addr); 1172 1173 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 1174 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 1175 return BT_STATUS_FAIL; 1176 } 1177 1178 if (is_connected(bd_addr) && (idx != BTIF_HF_INVALID_IDX)) { 1179 tBTA_AG_RES_DATA ag_res; 1180 memset(&ag_res, 0, sizeof(ag_res)); 1181 1182 /* Format the response */ 1183 if (index == 0) { 1184 ag_res.ok_flag = BTA_AG_OK_DONE; 1185 } else { 1186 BTIF_TRACE_EVENT( 1187 "clcc_response: [%d] dir %d state %d mode %d number = %s type = %d", 1188 index, dir, state, mode, number, type); 1189 int res_strlen = 1190 snprintf(ag_res.str, sizeof(ag_res.str), "%d,%d,%d,%d,%d", index, dir, 1191 state, mode, mpty); 1192 1193 if (number) { 1194 size_t rem_bytes = sizeof(ag_res.str) - res_strlen; 1195 char dialnum[sizeof(ag_res.str)]; 1196 size_t newidx = 0; 1197 if (type == BTHF_CALL_ADDRTYPE_INTERNATIONAL && *number != '+') { 1198 dialnum[newidx++] = '+'; 1199 } 1200 for (size_t i = 0; number[i] != 0; i++) { 1201 if (utl_isdialchar(number[i])) { 1202 dialnum[newidx++] = number[i]; 1203 } 1204 } 1205 dialnum[newidx] = 0; 1206 snprintf(&ag_res.str[res_strlen], rem_bytes, ",\"%s\",%d", dialnum, 1207 type); 1208 } 1209 } 1210 BTA_AgResult(btif_hf_cb[idx].handle, BTA_AG_CLCC_RES, &ag_res); 1211 1212 return BT_STATUS_SUCCESS; 1213 } 1214 1215 return BT_STATUS_FAIL; 1216 } 1217 1218 /******************************************************************************* 1219 * 1220 * Function phone_state_change 1221 * 1222 * Description notify of a call state change 1223 * number & type: valid only for incoming & waiting call 1224 * 1225 * Returns bt_status_t 1226 * 1227 ******************************************************************************/ 1228 1229 static bt_status_t phone_state_change(int num_active, int num_held, 1230 bthf_call_state_t call_setup_state, 1231 const char* number, 1232 bthf_call_addrtype_t type) { 1233 tBTA_AG_RES res = 0xff; 1234 tBTA_AG_RES_DATA ag_res; 1235 bt_status_t status = BT_STATUS_SUCCESS; 1236 bool activeCallUpdated = false; 1237 int idx, i; 1238 1239 /* hf_idx is index of connected HS that sent ATA/BLDN, 1240 otherwise index of latest connected HS */ 1241 if (hf_idx != BTIF_HF_INVALID_IDX) 1242 idx = hf_idx; 1243 else 1244 idx = btif_hf_latest_connected_idx(); 1245 1246 BTIF_TRACE_DEBUG("phone_state_change: idx = %d", idx); 1247 1248 /* Check if SLC is connected */ 1249 if (btif_hf_check_if_slc_connected() != BT_STATUS_SUCCESS) 1250 return BT_STATUS_NOT_READY; 1251 1252 BTIF_TRACE_DEBUG( 1253 "phone_state_change: num_active=%d [prev: %d] num_held=%d[prev: %d]" 1254 " call_setup=%s [prev: %s]", 1255 num_active, btif_hf_cb[idx].num_active, num_held, 1256 btif_hf_cb[idx].num_held, dump_hf_call_state(call_setup_state), 1257 dump_hf_call_state(btif_hf_cb[idx].call_setup_state)); 1258 1259 /* if all indicators are 0, send end call and return */ 1260 if (num_active == 0 && num_held == 0 && 1261 call_setup_state == BTHF_CALL_STATE_IDLE) { 1262 BTIF_TRACE_DEBUG("%s: Phone on hook", __func__); 1263 1264 /* record call termination timestamp if there was an active/held call or 1265 callsetup state > BTHF_CALL_STATE_IDLE */ 1266 if ((btif_hf_cb[idx].call_setup_state != BTHF_CALL_STATE_IDLE) || 1267 (btif_hf_cb[idx].num_active) || (btif_hf_cb[idx].num_held)) { 1268 BTIF_TRACE_DEBUG("%s: Record call termination timestamp", __func__); 1269 clock_gettime(CLOCK_MONOTONIC, &btif_hf_cb[0].call_end_timestamp); 1270 } 1271 BTA_AgResult(BTA_AG_HANDLE_ALL, BTA_AG_END_CALL_RES, NULL); 1272 hf_idx = BTIF_HF_INVALID_IDX; 1273 1274 /* if held call was present, reset that as well */ 1275 if (btif_hf_cb[idx].num_held) send_indicator_update(BTA_AG_IND_CALLHELD, 0); 1276 1277 goto update_call_states; 1278 } 1279 1280 /* active state can change when: 1281 ** 1. an outgoing/incoming call was answered 1282 ** 2. an held was resumed 1283 ** 3. without callsetup notifications, call became active 1284 ** (3) can happen if call is active and a headset connects to us 1285 ** 1286 ** In the case of (3), we will have to notify the stack of an active 1287 ** call, instead of sending an indicator update. This will also 1288 ** force the SCO to be setup. Handle this special case here prior to 1289 ** call setup handling 1290 */ 1291 if (((num_active + num_held) > 0) && (btif_hf_cb[idx].num_active == 0) && 1292 (btif_hf_cb[idx].num_held == 0) && 1293 (btif_hf_cb[idx].call_setup_state == BTHF_CALL_STATE_IDLE)) { 1294 BTIF_TRACE_DEBUG( 1295 "%s: Active/Held call notification received without call setup update", 1296 __func__); 1297 1298 memset(&ag_res, 0, sizeof(tBTA_AG_RES_DATA)); 1299 ag_res.audio_handle = BTA_AG_HANDLE_SCO_NO_CHANGE; 1300 /* Addition call setup with the Active call 1301 ** CIND response should have been updated. 1302 ** just open SCO connection. 1303 */ 1304 if (call_setup_state != BTHF_CALL_STATE_IDLE) 1305 res = BTA_AG_MULTI_CALL_RES; 1306 else 1307 res = BTA_AG_OUT_CALL_CONN_RES; 1308 BTA_AgResult(BTA_AG_HANDLE_ALL, res, &ag_res); 1309 activeCallUpdated = true; 1310 } 1311 1312 /* Ringing call changed? */ 1313 if (call_setup_state != btif_hf_cb[idx].call_setup_state) { 1314 BTIF_TRACE_DEBUG("%s: Call setup states changed. old: %s new: %s", __func__, 1315 dump_hf_call_state(btif_hf_cb[idx].call_setup_state), 1316 dump_hf_call_state(call_setup_state)); 1317 memset(&ag_res, 0, sizeof(tBTA_AG_RES_DATA)); 1318 1319 switch (call_setup_state) { 1320 case BTHF_CALL_STATE_IDLE: { 1321 switch (btif_hf_cb[idx].call_setup_state) { 1322 case BTHF_CALL_STATE_INCOMING: 1323 if (num_active > btif_hf_cb[idx].num_active) { 1324 res = BTA_AG_IN_CALL_CONN_RES; 1325 ag_res.audio_handle = btif_hf_cb[idx].handle; 1326 } else if (num_held > btif_hf_cb[idx].num_held) 1327 res = BTA_AG_IN_CALL_HELD_RES; 1328 else 1329 res = BTA_AG_CALL_CANCEL_RES; 1330 break; 1331 case BTHF_CALL_STATE_DIALING: 1332 case BTHF_CALL_STATE_ALERTING: 1333 if (num_active > btif_hf_cb[idx].num_active) { 1334 ag_res.audio_handle = BTA_AG_HANDLE_SCO_NO_CHANGE; 1335 res = BTA_AG_OUT_CALL_CONN_RES; 1336 } else 1337 res = BTA_AG_CALL_CANCEL_RES; 1338 break; 1339 default: 1340 BTIF_TRACE_ERROR("%s: Incorrect Call setup state transition", 1341 __func__); 1342 status = BT_STATUS_PARM_INVALID; 1343 break; 1344 } 1345 } break; 1346 1347 case BTHF_CALL_STATE_INCOMING: 1348 if (num_active || num_held) { 1349 res = BTA_AG_CALL_WAIT_RES; 1350 } else { 1351 res = BTA_AG_IN_CALL_RES; 1352 } 1353 if (number) { 1354 int xx = 0; 1355 if ((type == BTHF_CALL_ADDRTYPE_INTERNATIONAL) && (*number != '+')) 1356 xx = snprintf(ag_res.str, sizeof(ag_res.str), "\"+%s\"", number); 1357 else 1358 xx = snprintf(ag_res.str, sizeof(ag_res.str), "\"%s\"", number); 1359 ag_res.num = type; 1360 1361 if (res == BTA_AG_CALL_WAIT_RES) 1362 snprintf(&ag_res.str[xx], sizeof(ag_res.str) - xx, ",%d", type); 1363 } 1364 break; 1365 case BTHF_CALL_STATE_DIALING: 1366 if (!(num_active + num_held)) 1367 ag_res.audio_handle = btif_hf_cb[idx].handle; 1368 res = BTA_AG_OUT_CALL_ORIG_RES; 1369 break; 1370 case BTHF_CALL_STATE_ALERTING: 1371 /* if we went from idle->alert, force SCO setup here. dialing usually 1372 * triggers it */ 1373 if ((btif_hf_cb[idx].call_setup_state == BTHF_CALL_STATE_IDLE) && 1374 !(num_active + num_held)) 1375 ag_res.audio_handle = btif_hf_cb[idx].handle; 1376 res = BTA_AG_OUT_CALL_ALERT_RES; 1377 break; 1378 default: 1379 BTIF_TRACE_ERROR("%s: Incorrect new ringing call state", __func__); 1380 status = BT_STATUS_PARM_INVALID; 1381 break; 1382 } 1383 BTIF_TRACE_DEBUG("%s: Call setup state changed. res=%d, audio_handle=%d", 1384 __func__, res, ag_res.audio_handle); 1385 1386 if (res) BTA_AgResult(BTA_AG_HANDLE_ALL, res, &ag_res); 1387 1388 /* if call setup is idle, we have already updated call indicator, jump out 1389 */ 1390 if (call_setup_state == BTHF_CALL_STATE_IDLE) { 1391 /* check & update callheld */ 1392 if ((num_held > 0) && (num_active > 0)) 1393 send_indicator_update(BTA_AG_IND_CALLHELD, 1); 1394 goto update_call_states; 1395 } 1396 } 1397 1398 memset(&ag_res, 0, sizeof(tBTA_AG_RES_DATA)); 1399 1400 /* per the errata 2043, call=1 implies atleast one call is in progress 1401 *(active/held) 1402 ** https://www.bluetooth.org/errata/errata_view.cfm?errata_id=2043 1403 ** Handle call indicator change 1404 **/ 1405 if (!activeCallUpdated && 1406 ((num_active + num_held) != 1407 (btif_hf_cb[idx].num_active + btif_hf_cb[idx].num_held))) { 1408 BTIF_TRACE_DEBUG("%s: Active call states changed. old: %d new: %d", 1409 __func__, btif_hf_cb[idx].num_active, num_active); 1410 send_indicator_update(BTA_AG_IND_CALL, 1411 ((num_active + num_held) > 0) ? 1 : 0); 1412 } 1413 1414 /* Held Changed? */ 1415 if (num_held != btif_hf_cb[idx].num_held || 1416 ((num_active == 0) && ((num_held + btif_hf_cb[idx].num_held) > 1))) { 1417 BTIF_TRACE_DEBUG("%s: Held call states changed. old: %d new: %d", __func__, 1418 btif_hf_cb[idx].num_held, num_held); 1419 send_indicator_update(BTA_AG_IND_CALLHELD, 1420 ((num_held == 0) ? 0 : ((num_active == 0) ? 2 : 1))); 1421 } 1422 1423 /* Calls Swapped? */ 1424 if ((call_setup_state == btif_hf_cb[idx].call_setup_state) && 1425 (num_active && num_held) && (num_active == btif_hf_cb[idx].num_active) && 1426 (num_held == btif_hf_cb[idx].num_held)) { 1427 BTIF_TRACE_DEBUG("%s: Calls swapped", __func__); 1428 send_indicator_update(BTA_AG_IND_CALLHELD, 1); 1429 } 1430 1431 update_call_states: 1432 for (i = 0; i < btif_max_hf_clients; i++) { 1433 if (btif_hf_cb[i].state == BTHF_CONNECTION_STATE_SLC_CONNECTED) { 1434 btif_hf_cb[i].num_active = num_active; 1435 btif_hf_cb[i].num_held = num_held; 1436 btif_hf_cb[i].call_setup_state = call_setup_state; 1437 } 1438 } 1439 return status; 1440 } 1441 1442 /******************************************************************************* 1443 * 1444 * Function btif_hf_is_call_idle 1445 * 1446 * Description returns true if no call is in progress 1447 * 1448 * Returns bt_status_t 1449 * 1450 ******************************************************************************/ 1451 bool btif_hf_is_call_idle(void) { 1452 if (bt_hf_callbacks == NULL) return true; 1453 1454 for (int i = 0; i < btif_max_hf_clients; ++i) { 1455 if ((btif_hf_cb[i].call_setup_state != BTHF_CALL_STATE_IDLE) || 1456 ((btif_hf_cb[i].num_held + btif_hf_cb[i].num_active) > 0)) 1457 return false; 1458 } 1459 1460 return true; 1461 } 1462 1463 /******************************************************************************* 1464 * 1465 * Function btif_hf_call_terminated_recently 1466 * 1467 * Description Checks if a call has been terminated 1468 * 1469 * Returns bt_status_t 1470 * 1471 ******************************************************************************/ 1472 bool btif_hf_call_terminated_recently() { 1473 struct timespec now; 1474 1475 clock_gettime(CLOCK_MONOTONIC, &now); 1476 if (now.tv_sec < 1477 btif_hf_cb[0].call_end_timestamp.tv_sec + BTIF_HF_CALL_END_TIMEOUT) { 1478 return true; 1479 } else { 1480 btif_hf_cb[0].call_end_timestamp.tv_sec = 0; 1481 return false; 1482 } 1483 } 1484 1485 /******************************************************************************* 1486 * 1487 * Function cleanup 1488 * 1489 * Description Closes the HF interface 1490 * 1491 * Returns bt_status_t 1492 * 1493 ******************************************************************************/ 1494 static void cleanup(void) { 1495 BTIF_TRACE_EVENT("%s", __func__); 1496 1497 btif_queue_cleanup(UUID_SERVCLASS_AG_HANDSFREE); 1498 if (bt_hf_callbacks) { 1499 #if (defined(BTIF_HF_SERVICES) && (BTIF_HF_SERVICES & BTA_HFP_SERVICE_MASK)) 1500 btif_disable_service(BTA_HFP_SERVICE_ID); 1501 #else 1502 btif_disable_service(BTA_HSP_SERVICE_ID); 1503 #endif 1504 bt_hf_callbacks = NULL; 1505 } 1506 } 1507 1508 /******************************************************************************* 1509 * 1510 * Function configure_wbs 1511 * 1512 * Description set to over-ride the current WBS configuration. 1513 * It will not send codec setting cmd to the controller now. 1514 * It just change the configure. 1515 * 1516 * Returns bt_status_t 1517 * 1518 ******************************************************************************/ 1519 static bt_status_t configure_wbs(RawAddress* bd_addr, 1520 bthf_wbs_config_t config) { 1521 CHECK_BTHF_INIT(); 1522 1523 int idx = btif_hf_idx_by_bdaddr(bd_addr); 1524 1525 if ((idx < 0) || (idx >= BTIF_HF_NUM_CB)) { 1526 BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx); 1527 return BT_STATUS_FAIL; 1528 } 1529 1530 BTIF_TRACE_EVENT("%s config is %d", __func__, config); 1531 if (config == BTHF_WBS_YES) 1532 BTA_AgSetCodec(btif_hf_cb[idx].handle, BTA_AG_CODEC_MSBC); 1533 else if (config == BTHF_WBS_NO) 1534 BTA_AgSetCodec(btif_hf_cb[idx].handle, BTA_AG_CODEC_CVSD); 1535 else 1536 BTA_AgSetCodec(btif_hf_cb[idx].handle, BTA_AG_CODEC_NONE); 1537 1538 return BT_STATUS_SUCCESS; 1539 } 1540 1541 static const bthf_interface_t bthfInterface = { 1542 sizeof(bthfInterface), 1543 init, 1544 connect, 1545 disconnect, 1546 connect_audio, 1547 disconnect_audio, 1548 start_voice_recognition, 1549 stop_voice_recognition, 1550 volume_control, 1551 device_status_notification, 1552 cops_response, 1553 cind_response, 1554 formatted_at_response, 1555 at_response, 1556 clcc_response, 1557 phone_state_change, 1558 cleanup, 1559 configure_wbs, 1560 bind_response, 1561 set_sco_allowed, 1562 }; 1563 1564 /******************************************************************************* 1565 * 1566 * Function btif_hf_execute_service 1567 * 1568 * Description Initializes/Shuts down the service 1569 * 1570 * Returns BT_STATUS_SUCCESS on success, BT_STATUS_FAIL otherwise 1571 * 1572 ******************************************************************************/ 1573 bt_status_t btif_hf_execute_service(bool b_enable) { 1574 const char* p_service_names[] = BTIF_HF_SERVICE_NAMES; 1575 int i; 1576 if (b_enable) { 1577 /* Enable and register with BTA-AG */ 1578 BTA_AgEnable(BTA_AG_PARSE, bte_hf_evt); 1579 for (i = 0; i < btif_max_hf_clients; i++) { 1580 BTA_AgRegister(BTIF_HF_SERVICES, BTIF_HF_SECURITY, btif_hf_features, 1581 p_service_names, bthf_hf_id[i]); 1582 } 1583 } else { 1584 /* De-register AG */ 1585 for (i = 0; i < btif_max_hf_clients; i++) { 1586 BTA_AgDeregister(btif_hf_cb[i].handle); 1587 } 1588 /* Disable AG */ 1589 BTA_AgDisable(); 1590 } 1591 return BT_STATUS_SUCCESS; 1592 } 1593 1594 /******************************************************************************* 1595 * 1596 * Function btif_hf_get_interface 1597 * 1598 * Description Get the hf callback interface 1599 * 1600 * Returns bthf_interface_t 1601 * 1602 ******************************************************************************/ 1603 const bthf_interface_t* btif_hf_get_interface() { 1604 BTIF_TRACE_EVENT("%s", __func__); 1605 return &bthfInterface; 1606 } 1607