1 /****************************************************************************** 2 * 3 * Copyright (C) 2003-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 * This file contains the GATT client action functions for the state 22 * machine. 23 * 24 ******************************************************************************/ 25 26 #define LOG_TAG "bt_bta_gattc" 27 28 #include <string.h> 29 30 #include <base/callback.h> 31 #include "bt_common.h" 32 #include "bt_target.h" 33 #include "bta_closure_api.h" 34 #include "bta_gattc_int.h" 35 #include "bta_sys.h" 36 #include "btif/include/btif_debug_conn.h" 37 #include "l2c_api.h" 38 #include "osi/include/log.h" 39 #include "osi/include/osi.h" 40 #include "stack/l2cap/l2c_int.h" 41 #include "utl.h" 42 43 #if (BTA_HH_LE_INCLUDED == TRUE) 44 #include "bta_hh_int.h" 45 #endif 46 47 /***************************************************************************** 48 * Constants 49 ****************************************************************************/ 50 static void bta_gattc_conn_cback(tGATT_IF gattc_if, const RawAddress& bda, 51 uint16_t conn_id, bool connected, 52 tGATT_DISCONN_REASON reason, 53 tBT_TRANSPORT transport); 54 55 static void bta_gattc_cmpl_cback(uint16_t conn_id, tGATTC_OPTYPE op, 56 tGATT_STATUS status, 57 tGATT_CL_COMPLETE* p_data); 58 static void bta_gattc_cmpl_sendmsg(uint16_t conn_id, tGATTC_OPTYPE op, 59 tBTA_GATT_STATUS status, 60 tGATT_CL_COMPLETE* p_data); 61 62 static void bta_gattc_deregister_cmpl(tBTA_GATTC_RCB* p_clreg); 63 static void bta_gattc_enc_cmpl_cback(tGATT_IF gattc_if, const RawAddress& bda); 64 static void bta_gattc_cong_cback(uint16_t conn_id, bool congested); 65 static void bta_gattc_phy_update_cback(tGATT_IF gatt_if, uint16_t conn_id, 66 uint8_t tx_phy, uint8_t rx_phy, 67 uint8_t status); 68 static void bta_gattc_conn_update_cback(tGATT_IF gatt_if, uint16_t conn_id, 69 uint16_t interval, uint16_t latency, 70 uint16_t timeout, uint8_t status); 71 72 static tGATT_CBACK bta_gattc_cl_cback = {bta_gattc_conn_cback, 73 bta_gattc_cmpl_cback, 74 bta_gattc_disc_res_cback, 75 bta_gattc_disc_cmpl_cback, 76 NULL, 77 bta_gattc_enc_cmpl_cback, 78 bta_gattc_cong_cback, 79 bta_gattc_phy_update_cback, 80 bta_gattc_conn_update_cback}; 81 82 /* opcode(tGATTC_OPTYPE) order has to be comply with internal event order */ 83 static uint16_t bta_gattc_opcode_to_int_evt[] = { 84 BTA_GATTC_API_READ_EVT, BTA_GATTC_API_WRITE_EVT, BTA_GATTC_API_EXEC_EVT, 85 BTA_GATTC_API_CFG_MTU_EVT}; 86 87 static const char* bta_gattc_op_code_name[] = { 88 "Unknown", "Discovery", "Read", "Write", 89 "Exec", "Config", "Notification", "Indication"}; 90 /***************************************************************************** 91 * Action Functions 92 ****************************************************************************/ 93 94 void bta_gattc_reset_discover_st(tBTA_GATTC_SERV* p_srcb, 95 tBTA_GATT_STATUS status); 96 97 /******************************************************************************* 98 * 99 * Function bta_gattc_enable 100 * 101 * Description Enables GATTC module 102 * 103 * 104 * Returns void 105 * 106 ******************************************************************************/ 107 static void bta_gattc_enable() { 108 APPL_TRACE_DEBUG("%s", __func__); 109 110 if (bta_gattc_cb.state == BTA_GATTC_STATE_DISABLED) { 111 /* initialize control block */ 112 memset(&bta_gattc_cb, 0, sizeof(tBTA_GATTC_CB)); 113 bta_gattc_cb.state = BTA_GATTC_STATE_ENABLED; 114 } else { 115 APPL_TRACE_DEBUG("GATTC is already enabled"); 116 } 117 } 118 119 /******************************************************************************* 120 * 121 * Function bta_gattc_disable 122 * 123 * Description Disable GATTC module by cleaning up all active connections 124 * and deregister all application. 125 * 126 * Returns void 127 * 128 ******************************************************************************/ 129 void bta_gattc_disable() { 130 uint8_t i; 131 132 APPL_TRACE_DEBUG("%s", __func__); 133 134 if (bta_gattc_cb.state != BTA_GATTC_STATE_ENABLED) { 135 APPL_TRACE_ERROR("not enabled, or disabled in progress"); 136 return; 137 } 138 139 for (i = 0; i < BTA_GATTC_CL_MAX; i++) { 140 if (bta_gattc_cb.cl_rcb[i].in_use) { 141 bta_gattc_cb.state = BTA_GATTC_STATE_DISABLING; 142 /* don't deregister HH GATT IF */ 143 /* HH GATT IF will be deregistered by bta_hh_le_deregister when disable HH */ 144 #if (BTA_HH_LE_INCLUDED == TRUE) 145 if (!bta_hh_le_is_hh_gatt_if(bta_gattc_cb.cl_rcb[i].client_if)) { 146 #endif 147 bta_gattc_deregister(&bta_gattc_cb.cl_rcb[i]); 148 #if (BTA_HH_LE_INCLUDED == TRUE) 149 } 150 #endif 151 } 152 } 153 154 /* no registered apps, indicate disable completed */ 155 if (bta_gattc_cb.state != BTA_GATTC_STATE_DISABLING) { 156 memset(&bta_gattc_cb, 0, sizeof(tBTA_GATTC_CB)); 157 bta_gattc_cb.state = BTA_GATTC_STATE_DISABLED; 158 } 159 } 160 161 /** start an application interface */ 162 void bta_gattc_start_if(uint8_t client_if) { 163 if (!bta_gattc_cl_get_regcb(client_if)) { 164 APPL_TRACE_ERROR("Unable to start app.: Unknown interface =%d", client_if); 165 return; 166 } 167 168 GATT_StartIf(client_if); 169 } 170 171 /** Register a GATT client application with BTA */ 172 void bta_gattc_register(tBT_UUID* p_app_uuid, tBTA_GATTC_CBACK* p_cback, 173 BtaAppRegisterCallback cb) { 174 tBTA_GATT_STATUS status = BTA_GATT_NO_RESOURCES; 175 uint8_t client_if = 0; 176 APPL_TRACE_DEBUG("%s: state %d", __func__, bta_gattc_cb.state); 177 178 /* check if GATTC module is already enabled . Else enable */ 179 if (bta_gattc_cb.state == BTA_GATTC_STATE_DISABLED) { 180 bta_gattc_enable(); 181 } 182 /* todo need to check duplicate uuid */ 183 for (uint8_t i = 0; i < BTA_GATTC_CL_MAX; i++) { 184 if (!bta_gattc_cb.cl_rcb[i].in_use) { 185 if ((p_app_uuid == NULL) || 186 (bta_gattc_cb.cl_rcb[i].client_if = 187 GATT_Register(p_app_uuid, &bta_gattc_cl_cback)) == 0) { 188 APPL_TRACE_ERROR("Register with GATT stack failed."); 189 status = BTA_GATT_ERROR; 190 } else { 191 bta_gattc_cb.cl_rcb[i].in_use = true; 192 bta_gattc_cb.cl_rcb[i].p_cback = p_cback; 193 memcpy(&bta_gattc_cb.cl_rcb[i].app_uuid, p_app_uuid, sizeof(tBT_UUID)); 194 195 /* BTA use the same client interface as BTE GATT statck */ 196 client_if = bta_gattc_cb.cl_rcb[i].client_if; 197 198 do_in_bta_thread(FROM_HERE, base::Bind(&bta_gattc_start_if, client_if)); 199 200 status = BTA_GATT_OK; 201 break; 202 } 203 } 204 } 205 206 if (!cb.is_null()) cb.Run(client_if, status); 207 } 208 209 /******************************************************************************* 210 * 211 * Function bta_gattc_deregister 212 * 213 * Description De-Register a GATT client application with BTA. 214 * 215 * Returns void 216 * 217 ******************************************************************************/ 218 void bta_gattc_deregister(tBTA_GATTC_RCB* p_clreg) { 219 uint8_t i; 220 BT_HDR buf; 221 222 if (p_clreg != NULL) { 223 /* remove bg connection associated with this rcb */ 224 for (i = 0; i < BTA_GATTC_KNOWN_SR_MAX; i++) { 225 if (bta_gattc_cb.bg_track[i].in_use) { 226 if (bta_gattc_cb.bg_track[i].cif_mask & 227 (1 << (p_clreg->client_if - 1))) { 228 bta_gattc_mark_bg_conn(p_clreg->client_if, 229 bta_gattc_cb.bg_track[i].remote_bda, false); 230 GATT_CancelConnect(p_clreg->client_if, 231 bta_gattc_cb.bg_track[i].remote_bda, false); 232 } 233 } 234 } 235 236 if (p_clreg->num_clcb > 0) { 237 /* close all CLCB related to this app */ 238 for (i = 0; i < BTA_GATTC_CLCB_MAX; i++) { 239 if (bta_gattc_cb.clcb[i].in_use && 240 (bta_gattc_cb.clcb[i].p_rcb == p_clreg)) { 241 p_clreg->dereg_pending = true; 242 243 buf.event = BTA_GATTC_API_CLOSE_EVT; 244 buf.layer_specific = bta_gattc_cb.clcb[i].bta_conn_id; 245 bta_gattc_close(&bta_gattc_cb.clcb[i], (tBTA_GATTC_DATA*)&buf); 246 } 247 } 248 } else 249 bta_gattc_deregister_cmpl(p_clreg); 250 } else { 251 APPL_TRACE_ERROR("%s: Deregister Failed unknown client cif", __func__); 252 bta_hh_cleanup_disable(BTA_HH_OK); 253 } 254 } 255 /******************************************************************************* 256 * 257 * Function bta_gattc_process_api_open 258 * 259 * Description process connect API request. 260 * 261 * Returns void 262 * 263 ******************************************************************************/ 264 void bta_gattc_process_api_open(tBTA_GATTC_DATA* p_msg) { 265 uint16_t event = ((BT_HDR*)p_msg)->event; 266 tBTA_GATTC_CLCB* p_clcb = NULL; 267 tBTA_GATTC_RCB* p_clreg = bta_gattc_cl_get_regcb(p_msg->api_conn.client_if); 268 269 if (p_clreg != NULL) { 270 if (p_msg->api_conn.is_direct) { 271 p_clcb = bta_gattc_find_alloc_clcb(p_msg->api_conn.client_if, 272 p_msg->api_conn.remote_bda, 273 p_msg->api_conn.transport); 274 if (p_clcb != NULL) { 275 bta_gattc_sm_execute(p_clcb, event, p_msg); 276 } else { 277 APPL_TRACE_ERROR("No resources to open a new connection."); 278 279 bta_gattc_send_open_cback( 280 p_clreg, BTA_GATT_NO_RESOURCES, p_msg->api_conn.remote_bda, 281 BTA_GATT_INVALID_CONN_ID, p_msg->api_conn.transport, 0); 282 } 283 } else { 284 bta_gattc_init_bk_conn(&p_msg->api_conn, p_clreg); 285 } 286 } else { 287 APPL_TRACE_ERROR("%s: Failed, unknown client_if: %d", __func__, 288 p_msg->api_conn.client_if); 289 } 290 } 291 /******************************************************************************* 292 * 293 * Function bta_gattc_process_api_open_cancel 294 * 295 * Description process connect API request. 296 * 297 * Returns void 298 * 299 ******************************************************************************/ 300 void bta_gattc_process_api_open_cancel(tBTA_GATTC_DATA* p_msg) { 301 uint16_t event = ((BT_HDR*)p_msg)->event; 302 tBTA_GATTC_CLCB* p_clcb = NULL; 303 tBTA_GATTC_RCB* p_clreg; 304 tBTA_GATTC cb_data; 305 306 if (p_msg->api_cancel_conn.is_direct) { 307 p_clcb = bta_gattc_find_clcb_by_cif(p_msg->api_cancel_conn.client_if, 308 p_msg->api_cancel_conn.remote_bda, 309 BTA_GATT_TRANSPORT_LE); 310 if (p_clcb != NULL) { 311 bta_gattc_sm_execute(p_clcb, event, p_msg); 312 } else { 313 APPL_TRACE_ERROR("No such connection need to be cancelled"); 314 315 p_clreg = bta_gattc_cl_get_regcb(p_msg->api_cancel_conn.client_if); 316 317 if (p_clreg && p_clreg->p_cback) { 318 cb_data.status = BTA_GATT_ERROR; 319 (*p_clreg->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data); 320 } 321 } 322 } else { 323 bta_gattc_cancel_bk_conn(&p_msg->api_cancel_conn); 324 } 325 } 326 327 /** process encryption complete message */ 328 void bta_gattc_process_enc_cmpl(tGATT_IF client_if, const RawAddress& bda) { 329 tBTA_GATTC_RCB* p_clreg; 330 tBTA_GATTC cb_data; 331 332 p_clreg = bta_gattc_cl_get_regcb(client_if); 333 334 if (p_clreg && p_clreg->p_cback) { 335 memset(&cb_data, 0, sizeof(tBTA_GATTC)); 336 337 cb_data.enc_cmpl.client_if = client_if; 338 cb_data.enc_cmpl.remote_bda = bda; 339 340 (*p_clreg->p_cback)(BTA_GATTC_ENC_CMPL_CB_EVT, &cb_data); 341 } 342 } 343 344 /******************************************************************************* 345 * 346 * Function bta_gattc_cancel_open_error 347 * 348 * Description 349 * 350 * Returns void 351 * 352 ******************************************************************************/ 353 void bta_gattc_cancel_open_error(tBTA_GATTC_CLCB* p_clcb, 354 UNUSED_ATTR tBTA_GATTC_DATA* p_data) { 355 tBTA_GATTC cb_data; 356 357 cb_data.status = BTA_GATT_ERROR; 358 359 if (p_clcb && p_clcb->p_rcb && p_clcb->p_rcb->p_cback) 360 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data); 361 } 362 363 /******************************************************************************* 364 * 365 * Function bta_gattc_open_error 366 * 367 * Description 368 * 369 * Returns void 370 * 371 ******************************************************************************/ 372 void bta_gattc_open_error(tBTA_GATTC_CLCB* p_clcb, 373 UNUSED_ATTR tBTA_GATTC_DATA* p_data) { 374 APPL_TRACE_ERROR("Connection already opened. wrong state"); 375 376 bta_gattc_send_open_cback(p_clcb->p_rcb, BTA_GATT_OK, p_clcb->bda, 377 p_clcb->bta_conn_id, p_clcb->transport, 0); 378 } 379 /******************************************************************************* 380 * 381 * Function bta_gattc_open_fail 382 * 383 * Description 384 * 385 * Returns void 386 * 387 ******************************************************************************/ 388 void bta_gattc_open_fail(tBTA_GATTC_CLCB* p_clcb, 389 UNUSED_ATTR tBTA_GATTC_DATA* p_data) { 390 bta_gattc_send_open_cback(p_clcb->p_rcb, BTA_GATT_ERROR, p_clcb->bda, 391 p_clcb->bta_conn_id, p_clcb->transport, 0); 392 /* open failure, remove clcb */ 393 bta_gattc_clcb_dealloc(p_clcb); 394 } 395 396 /******************************************************************************* 397 * 398 * Function bta_gattc_open 399 * 400 * Description Process API connection function. 401 * 402 * Returns void 403 * 404 ******************************************************************************/ 405 void bta_gattc_open(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 406 tBTA_GATTC_DATA gattc_data; 407 408 /* open/hold a connection */ 409 if (!GATT_Connect(p_clcb->p_rcb->client_if, p_data->api_conn.remote_bda, true, 410 p_data->api_conn.transport, p_data->api_conn.opportunistic, 411 p_data->api_conn.initiating_phys)) { 412 APPL_TRACE_ERROR("Connection open failure"); 413 414 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_OPEN_FAIL_EVT, p_data); 415 } else { 416 /* a connected remote device */ 417 if (GATT_GetConnIdIfConnected( 418 p_clcb->p_rcb->client_if, p_data->api_conn.remote_bda, 419 &p_clcb->bta_conn_id, p_data->api_conn.transport)) { 420 gattc_data.int_conn.hdr.layer_specific = p_clcb->bta_conn_id; 421 422 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CONN_EVT, &gattc_data); 423 } 424 /* else wait for the callback event */ 425 } 426 } 427 /******************************************************************************* 428 * 429 * Function bta_gattc_init_bk_conn 430 * 431 * Description Process API Open for a background connection 432 * 433 * Returns void 434 * 435 ******************************************************************************/ 436 void bta_gattc_init_bk_conn(tBTA_GATTC_API_OPEN* p_data, 437 tBTA_GATTC_RCB* p_clreg) { 438 tBTA_GATT_STATUS status = BTA_GATT_NO_RESOURCES; 439 uint16_t conn_id; 440 tBTA_GATTC_CLCB* p_clcb; 441 tBTA_GATTC_DATA gattc_data; 442 443 if (bta_gattc_mark_bg_conn(p_data->client_if, p_data->remote_bda, true)) { 444 /* always call open to hold a connection */ 445 if (!GATT_Connect(p_data->client_if, p_data->remote_bda, false, 446 p_data->transport, false)) { 447 status = BTA_GATT_ERROR; 448 LOG(ERROR) << __func__ << " unable to connect to remote bd_addr:" 449 << p_data->remote_bda; 450 451 } else { 452 status = BTA_GATT_OK; 453 454 /* if is a connected remote device */ 455 if (GATT_GetConnIdIfConnected(p_data->client_if, p_data->remote_bda, 456 &conn_id, p_data->transport)) { 457 p_clcb = bta_gattc_find_alloc_clcb( 458 p_data->client_if, p_data->remote_bda, BTA_GATT_TRANSPORT_LE); 459 if (p_clcb != NULL) { 460 gattc_data.hdr.layer_specific = p_clcb->bta_conn_id = conn_id; 461 462 /* open connection */ 463 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CONN_EVT, &gattc_data); 464 status = BTA_GATT_OK; 465 } 466 } 467 } 468 } 469 470 /* open failure, report OPEN_EVT */ 471 if (status != BTA_GATT_OK) { 472 bta_gattc_send_open_cback(p_clreg, status, p_data->remote_bda, 473 BTA_GATT_INVALID_CONN_ID, BTA_GATT_TRANSPORT_LE, 474 0); 475 } 476 } 477 /******************************************************************************* 478 * 479 * Function bta_gattc_cancel_bk_conn 480 * 481 * Description Process API Cancel Open for a background connection 482 * 483 * Returns void 484 * 485 ******************************************************************************/ 486 void bta_gattc_cancel_bk_conn(tBTA_GATTC_API_CANCEL_OPEN* p_data) { 487 tBTA_GATTC_RCB* p_clreg; 488 tBTA_GATTC cb_data; 489 cb_data.status = BTA_GATT_ERROR; 490 491 /* remove the device from the bg connection mask */ 492 if (bta_gattc_mark_bg_conn(p_data->client_if, p_data->remote_bda, false)) { 493 if (GATT_CancelConnect(p_data->client_if, p_data->remote_bda, false)) { 494 cb_data.status = BTA_GATT_OK; 495 } else { 496 APPL_TRACE_ERROR("%s: failed", __func__); 497 } 498 } 499 p_clreg = bta_gattc_cl_get_regcb(p_data->client_if); 500 501 if (p_clreg && p_clreg->p_cback) { 502 (*p_clreg->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data); 503 } 504 } 505 /******************************************************************************* 506 * 507 * Function bta_gattc_int_cancel_open_ok 508 * 509 * Description 510 * 511 * Returns void 512 * 513 ******************************************************************************/ 514 void bta_gattc_cancel_open_ok(tBTA_GATTC_CLCB* p_clcb, 515 UNUSED_ATTR tBTA_GATTC_DATA* p_data) { 516 tBTA_GATTC cb_data; 517 518 if (p_clcb->p_rcb->p_cback) { 519 cb_data.status = BTA_GATT_OK; 520 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data); 521 } 522 523 bta_gattc_clcb_dealloc(p_clcb); 524 } 525 /******************************************************************************* 526 * 527 * Function bta_gattc_cancel_open 528 * 529 * Description 530 * 531 * Returns void 532 * 533 ******************************************************************************/ 534 void bta_gattc_cancel_open(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 535 tBTA_GATTC cb_data; 536 537 if (GATT_CancelConnect(p_clcb->p_rcb->client_if, 538 p_data->api_cancel_conn.remote_bda, true)) { 539 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CANCEL_OPEN_OK_EVT, p_data); 540 } else { 541 if (p_clcb->p_rcb->p_cback) { 542 cb_data.status = BTA_GATT_ERROR; 543 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data); 544 } 545 } 546 } 547 /******************************************************************************* 548 * 549 * Function bta_gattc_conn 550 * 551 * Description receive connection callback from stack 552 * 553 * Returns void 554 * 555 ******************************************************************************/ 556 void bta_gattc_conn(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 557 tBTA_GATTC_IF gatt_if; 558 APPL_TRACE_DEBUG("%s: server cache state=%d", __func__, 559 p_clcb->p_srcb->state); 560 561 if (p_data != NULL) { 562 APPL_TRACE_DEBUG("%s: conn_id=%d", __func__, p_data->hdr.layer_specific); 563 p_clcb->bta_conn_id = p_data->int_conn.hdr.layer_specific; 564 565 GATT_GetConnectionInfor(p_data->hdr.layer_specific, &gatt_if, p_clcb->bda, 566 &p_clcb->transport); 567 } 568 569 p_clcb->p_srcb->connected = true; 570 571 if (p_clcb->p_srcb->mtu == 0) p_clcb->p_srcb->mtu = GATT_DEF_BLE_MTU_SIZE; 572 573 /* start database cache if needed */ 574 if (p_clcb->p_srcb->p_srvc_cache == NULL || 575 p_clcb->p_srcb->state != BTA_GATTC_SERV_IDLE) { 576 if (p_clcb->p_srcb->state == BTA_GATTC_SERV_IDLE) { 577 p_clcb->p_srcb->state = BTA_GATTC_SERV_LOAD; 578 if (bta_gattc_cache_load(p_clcb)) { 579 p_clcb->p_srcb->state = BTA_GATTC_SERV_IDLE; 580 bta_gattc_reset_discover_st(p_clcb->p_srcb, BTA_GATT_OK); 581 } else { 582 p_clcb->p_srcb->state = BTA_GATTC_SERV_DISC; 583 /* cache load failure, start discovery */ 584 bta_gattc_start_discover(p_clcb, NULL); 585 } 586 } else /* cache is building */ 587 p_clcb->state = BTA_GATTC_DISCOVER_ST; 588 } 589 590 else { 591 /* a pending service handle change indication */ 592 if (p_clcb->p_srcb->srvc_hdl_chg) { 593 p_clcb->p_srcb->srvc_hdl_chg = false; 594 /* start discovery */ 595 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL); 596 } 597 } 598 599 if (p_clcb->p_rcb) { 600 /* there is no RM for GATT */ 601 if (p_clcb->transport == BTA_TRANSPORT_BR_EDR) 602 bta_sys_conn_open(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda); 603 604 bta_gattc_send_open_cback(p_clcb->p_rcb, BTA_GATT_OK, p_clcb->bda, 605 p_clcb->bta_conn_id, p_clcb->transport, 606 p_clcb->p_srcb->mtu); 607 } 608 } 609 /******************************************************************************* 610 * 611 * Function bta_gattc_close_fail 612 * 613 * Description close a connection. 614 * 615 * Returns void 616 * 617 ******************************************************************************/ 618 void bta_gattc_close_fail(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 619 tBTA_GATTC cb_data; 620 621 if (p_clcb->p_rcb->p_cback) { 622 memset(&cb_data, 0, sizeof(tBTA_GATTC)); 623 cb_data.close.client_if = p_clcb->p_rcb->client_if; 624 cb_data.close.conn_id = p_data->hdr.layer_specific; 625 cb_data.close.remote_bda = p_clcb->bda; 626 cb_data.close.status = BTA_GATT_ERROR; 627 cb_data.close.reason = BTA_GATT_CONN_NONE; 628 629 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CLOSE_EVT, &cb_data); 630 } 631 } 632 /******************************************************************************* 633 * 634 * Function bta_gattc_api_close 635 * 636 * Description close a GATTC connection. 637 * 638 * Returns void 639 * 640 ******************************************************************************/ 641 void bta_gattc_close(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 642 tBTA_GATTC_CBACK* p_cback = p_clcb->p_rcb->p_cback; 643 tBTA_GATTC_RCB* p_clreg = p_clcb->p_rcb; 644 tBTA_GATTC cb_data; 645 646 APPL_TRACE_DEBUG("%s: conn_id=%d", __func__, p_clcb->bta_conn_id); 647 648 cb_data.close.client_if = p_clcb->p_rcb->client_if; 649 cb_data.close.conn_id = p_clcb->bta_conn_id; 650 cb_data.close.reason = p_clcb->reason; 651 cb_data.close.status = p_clcb->status; 652 cb_data.close.remote_bda = p_clcb->bda; 653 654 if (p_clcb->transport == BTA_TRANSPORT_BR_EDR) 655 bta_sys_conn_close(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda); 656 657 bta_gattc_clcb_dealloc(p_clcb); 658 659 if (p_data->hdr.event == BTA_GATTC_API_CLOSE_EVT) { 660 cb_data.close.status = GATT_Disconnect(p_data->hdr.layer_specific); 661 } else if (p_data->hdr.event == BTA_GATTC_INT_DISCONN_EVT) { 662 cb_data.close.status = p_data->int_conn.reason; 663 cb_data.close.reason = p_data->int_conn.reason; 664 } 665 666 if (p_cback) (*p_cback)(BTA_GATTC_CLOSE_EVT, &cb_data); 667 668 if (p_clreg->num_clcb == 0 && p_clreg->dereg_pending) { 669 bta_gattc_deregister_cmpl(p_clreg); 670 } 671 } 672 /******************************************************************************* 673 * 674 * Function bta_gattc_reset_discover_st 675 * 676 * Description when a SRCB finished discovery, tell all related clcb. 677 * 678 * Returns None. 679 * 680 ******************************************************************************/ 681 void bta_gattc_reset_discover_st(tBTA_GATTC_SERV* p_srcb, 682 tBTA_GATT_STATUS status) { 683 uint8_t i; 684 685 for (i = 0; i < BTA_GATTC_CLCB_MAX; i++) { 686 if (bta_gattc_cb.clcb[i].p_srcb == p_srcb) { 687 bta_gattc_cb.clcb[i].status = status; 688 bta_gattc_sm_execute(&bta_gattc_cb.clcb[i], BTA_GATTC_DISCOVER_CMPL_EVT, 689 NULL); 690 } 691 } 692 } 693 /******************************************************************************* 694 * 695 * Function bta_gattc_disc_close 696 * 697 * Description close a GATTC connection while in discovery state. 698 * 699 * Returns void 700 * 701 ******************************************************************************/ 702 void bta_gattc_disc_close(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 703 APPL_TRACE_DEBUG("%s: Discovery cancel conn_id=%d", __func__, 704 p_clcb->bta_conn_id); 705 706 if (p_clcb->disc_active) 707 bta_gattc_reset_discover_st(p_clcb->p_srcb, BTA_GATT_ERROR); 708 else 709 p_clcb->state = BTA_GATTC_CONN_ST; 710 711 // This function only gets called as the result of a BTA_GATTC_API_CLOSE_EVT 712 // while in the BTA_GATTC_DISCOVER_ST state. Once the state changes, the 713 // connection itself still needs to be closed to resolve the original event. 714 if (p_clcb->state == BTA_GATTC_CONN_ST) { 715 APPL_TRACE_DEBUG( 716 "State is back to BTA_GATTC_CONN_ST. " 717 "Trigger connection close"); 718 bta_gattc_close(p_clcb, p_data); 719 } 720 } 721 /******************************************************************************* 722 * 723 * Function bta_gattc_set_discover_st 724 * 725 * Description when a SRCB start discovery, tell all related clcb and set 726 * the state. 727 * 728 * Returns None. 729 * 730 ******************************************************************************/ 731 void bta_gattc_set_discover_st(tBTA_GATTC_SERV* p_srcb) { 732 uint8_t i; 733 734 L2CA_EnableUpdateBleConnParams(p_srcb->server_bda, false); 735 for (i = 0; i < BTA_GATTC_CLCB_MAX; i++) { 736 if (bta_gattc_cb.clcb[i].p_srcb == p_srcb) { 737 bta_gattc_cb.clcb[i].status = BTA_GATT_OK; 738 bta_gattc_cb.clcb[i].state = BTA_GATTC_DISCOVER_ST; 739 } 740 } 741 } 742 /******************************************************************************* 743 * 744 * Function bta_gattc_restart_discover 745 * 746 * Description process service change in discovery state, mark up the auto 747 * update flag and set status to be discovery cancel for 748 * current discovery. 749 * 750 * Returns None. 751 * 752 ******************************************************************************/ 753 void bta_gattc_restart_discover(tBTA_GATTC_CLCB* p_clcb, 754 UNUSED_ATTR tBTA_GATTC_DATA* p_data) { 755 p_clcb->status = BTA_GATT_CANCEL; 756 p_clcb->auto_update = BTA_GATTC_DISC_WAITING; 757 } 758 759 /******************************************************************************* 760 * 761 * Function bta_gattc_cfg_mtu 762 * 763 * Description Configure MTU size on the GATT connection. 764 * 765 * Returns None. 766 * 767 ******************************************************************************/ 768 void bta_gattc_cfg_mtu(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 769 tBTA_GATT_STATUS status; 770 771 if (bta_gattc_enqueue(p_clcb, p_data)) { 772 status = GATTC_ConfigureMTU(p_clcb->bta_conn_id, p_data->api_mtu.mtu); 773 774 /* if failed, return callback here */ 775 if (status != GATT_SUCCESS && status != GATT_CMD_STARTED) { 776 /* Dequeue the data, if it was enqueued */ 777 if (p_clcb->p_q_cmd == p_data) p_clcb->p_q_cmd = NULL; 778 779 bta_gattc_cmpl_sendmsg(p_clcb->bta_conn_id, GATTC_OPTYPE_CONFIG, status, 780 NULL); 781 } 782 } 783 } 784 /******************************************************************************* 785 * 786 * Function bta_gattc_start_discover 787 * 788 * Description Start a discovery on server. 789 * 790 * Returns None. 791 * 792 ******************************************************************************/ 793 void bta_gattc_start_discover(tBTA_GATTC_CLCB* p_clcb, 794 UNUSED_ATTR tBTA_GATTC_DATA* p_data) { 795 APPL_TRACE_DEBUG("%s: conn_id=%d p_clcb->p_srcb->state = %d ", __func__, 796 p_clcb->bta_conn_id, p_clcb->p_srcb->state); 797 798 if (((p_clcb->p_q_cmd == NULL || 799 p_clcb->auto_update == BTA_GATTC_REQ_WAITING) && 800 p_clcb->p_srcb->state == BTA_GATTC_SERV_IDLE) || 801 p_clcb->p_srcb->state == BTA_GATTC_SERV_DISC) 802 /* no pending operation, start discovery right away */ 803 { 804 p_clcb->auto_update = BTA_GATTC_NO_SCHEDULE; 805 806 if (p_clcb->p_srcb != NULL) { 807 /* clear the service change mask */ 808 p_clcb->p_srcb->srvc_hdl_chg = false; 809 p_clcb->p_srcb->update_count = 0; 810 p_clcb->p_srcb->state = BTA_GATTC_SERV_DISC_ACT; 811 812 if (p_clcb->transport == BTA_TRANSPORT_LE) 813 L2CA_EnableUpdateBleConnParams(p_clcb->p_srcb->server_bda, false); 814 815 /* set all srcb related clcb into discovery ST */ 816 bta_gattc_set_discover_st(p_clcb->p_srcb); 817 818 p_clcb->status = bta_gattc_init_cache(p_clcb->p_srcb); 819 if (p_clcb->status == BTA_GATT_OK) { 820 p_clcb->status = bta_gattc_discover_pri_service( 821 p_clcb->bta_conn_id, p_clcb->p_srcb, GATT_DISC_SRVC_ALL); 822 } 823 if (p_clcb->status != BTA_GATT_OK) { 824 APPL_TRACE_ERROR("discovery on server failed"); 825 bta_gattc_reset_discover_st(p_clcb->p_srcb, p_clcb->status); 826 } else 827 p_clcb->disc_active = true; 828 } else { 829 APPL_TRACE_ERROR("unknown device, can not start discovery"); 830 } 831 } 832 /* pending operation, wait until it finishes */ 833 else { 834 p_clcb->auto_update = BTA_GATTC_DISC_WAITING; 835 836 if (p_clcb->p_srcb->state == BTA_GATTC_SERV_IDLE) 837 p_clcb->state = BTA_GATTC_CONN_ST; /* set clcb state */ 838 } 839 } 840 /******************************************************************************* 841 * 842 * Function bta_gattc_disc_cmpl 843 * 844 * Description discovery on server is finished 845 * 846 * Returns None. 847 * 848 ******************************************************************************/ 849 void bta_gattc_disc_cmpl(tBTA_GATTC_CLCB* p_clcb, 850 UNUSED_ATTR tBTA_GATTC_DATA* p_data) { 851 tBTA_GATTC_DATA* p_q_cmd = p_clcb->p_q_cmd; 852 853 APPL_TRACE_DEBUG("%s: conn_id=%d", __func__, p_clcb->bta_conn_id); 854 855 if (p_clcb->transport == BTA_TRANSPORT_LE) 856 L2CA_EnableUpdateBleConnParams(p_clcb->p_srcb->server_bda, true); 857 p_clcb->p_srcb->state = BTA_GATTC_SERV_IDLE; 858 p_clcb->disc_active = false; 859 860 if (p_clcb->status != GATT_SUCCESS) { 861 /* clean up cache */ 862 if (p_clcb->p_srcb && p_clcb->p_srcb->p_srvc_cache) { 863 list_free(p_clcb->p_srcb->p_srvc_cache); 864 p_clcb->p_srcb->p_srvc_cache = NULL; 865 } 866 867 /* used to reset cache in application */ 868 bta_gattc_cache_reset(p_clcb->p_srcb->server_bda); 869 } 870 if (p_clcb->p_srcb && p_clcb->p_srcb->p_srvc_list) { 871 /* release pending attribute list buffer */ 872 osi_free_and_reset((void**)&p_clcb->p_srcb->p_srvc_list); 873 } 874 875 if (p_clcb->auto_update == BTA_GATTC_DISC_WAITING) { 876 /* start discovery again */ 877 p_clcb->auto_update = BTA_GATTC_REQ_WAITING; 878 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL); 879 } 880 /* get any queued command to proceed */ 881 else if (p_q_cmd != NULL) { 882 p_clcb->p_q_cmd = NULL; 883 /* execute pending operation of link block still present */ 884 if (l2cu_find_lcb_by_bd_addr(p_clcb->p_srcb->server_bda, BT_TRANSPORT_LE)) { 885 bta_gattc_sm_execute(p_clcb, p_q_cmd->hdr.event, p_q_cmd); 886 } 887 /* if the command executed requeued the cmd, we don't 888 * want to free the underlying buffer that's being 889 * referenced by p_clcb->p_q_cmd 890 */ 891 if (p_q_cmd != p_clcb->p_q_cmd) osi_free_and_reset((void**)&p_q_cmd); 892 } 893 } 894 /******************************************************************************* 895 * 896 * Function bta_gattc_read 897 * 898 * Description Read an attribute 899 * 900 * Returns None. 901 * 902 ******************************************************************************/ 903 void bta_gattc_read(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 904 if (!bta_gattc_enqueue(p_clcb, p_data)) return; 905 906 tBTA_GATT_STATUS status; 907 if (p_data->api_read.handle != 0) { 908 tGATT_READ_PARAM read_param; 909 memset(&read_param, 0, sizeof(tGATT_READ_PARAM)); 910 read_param.by_handle.handle = p_data->api_read.handle; 911 read_param.by_handle.auth_req = p_data->api_read.auth_req; 912 status = GATTC_Read(p_clcb->bta_conn_id, GATT_READ_BY_HANDLE, &read_param); 913 } else { 914 tGATT_READ_PARAM read_param; 915 memset(&read_param, 0, sizeof(tGATT_READ_BY_TYPE)); 916 917 read_param.char_type.s_handle = p_data->api_read.s_handle; 918 read_param.char_type.e_handle = p_data->api_read.e_handle; 919 read_param.char_type.uuid = p_data->api_read.uuid; 920 read_param.char_type.auth_req = p_data->api_read.auth_req; 921 status = GATTC_Read(p_clcb->bta_conn_id, GATT_READ_BY_TYPE, &read_param); 922 } 923 924 /* read fail */ 925 if (status != BTA_GATT_OK) { 926 /* Dequeue the data, if it was enqueued */ 927 if (p_clcb->p_q_cmd == p_data) p_clcb->p_q_cmd = NULL; 928 929 bta_gattc_cmpl_sendmsg(p_clcb->bta_conn_id, GATTC_OPTYPE_READ, status, 930 NULL); 931 } 932 } 933 /******************************************************************************* 934 * 935 * Function bta_gattc_read_multi 936 * 937 * Description read multiple 938 * 939 * Returns None. 940 ******************************************************************************/ 941 void bta_gattc_read_multi(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 942 tBTA_GATT_STATUS status = BTA_GATT_OK; 943 tGATT_READ_PARAM read_param; 944 945 if (bta_gattc_enqueue(p_clcb, p_data)) { 946 memset(&read_param, 0, sizeof(tGATT_READ_PARAM)); 947 948 if (status == BTA_GATT_OK) { 949 read_param.read_multiple.num_handles = p_data->api_read_multi.num_attr; 950 read_param.read_multiple.auth_req = p_data->api_read_multi.auth_req; 951 memcpy(&read_param.read_multiple.handles, p_data->api_read_multi.handles, 952 sizeof(uint16_t) * p_data->api_read_multi.num_attr); 953 954 status = GATTC_Read(p_clcb->bta_conn_id, GATT_READ_MULTIPLE, &read_param); 955 } 956 957 /* read fail */ 958 if (status != BTA_GATT_OK) { 959 /* Dequeue the data, if it was enqueued */ 960 if (p_clcb->p_q_cmd == p_data) p_clcb->p_q_cmd = NULL; 961 962 bta_gattc_cmpl_sendmsg(p_clcb->bta_conn_id, GATTC_OPTYPE_READ, status, 963 NULL); 964 } 965 } 966 } 967 /******************************************************************************* 968 * 969 * Function bta_gattc_write 970 * 971 * Description Write an attribute 972 * 973 * Returns None. 974 * 975 ******************************************************************************/ 976 void bta_gattc_write(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 977 if (!bta_gattc_enqueue(p_clcb, p_data)) return; 978 979 tBTA_GATT_STATUS status = BTA_GATT_OK; 980 tGATT_VALUE attr; 981 982 attr.conn_id = p_clcb->bta_conn_id; 983 attr.handle = p_data->api_write.handle; 984 attr.offset = p_data->api_write.offset; 985 attr.len = p_data->api_write.len; 986 attr.auth_req = p_data->api_write.auth_req; 987 988 if (p_data->api_write.p_value) 989 memcpy(attr.value, p_data->api_write.p_value, p_data->api_write.len); 990 991 status = 992 GATTC_Write(p_clcb->bta_conn_id, p_data->api_write.write_type, &attr); 993 994 /* write fail */ 995 if (status != BTA_GATT_OK) { 996 /* Dequeue the data, if it was enqueued */ 997 if (p_clcb->p_q_cmd == p_data) p_clcb->p_q_cmd = NULL; 998 999 bta_gattc_cmpl_sendmsg(p_clcb->bta_conn_id, GATTC_OPTYPE_WRITE, status, 1000 NULL); 1001 } 1002 } 1003 /******************************************************************************* 1004 * 1005 * Function bta_gattc_execute 1006 * 1007 * Description send execute write 1008 * 1009 * Returns None. 1010 ******************************************************************************/ 1011 void bta_gattc_execute(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 1012 tBTA_GATT_STATUS status; 1013 1014 if (bta_gattc_enqueue(p_clcb, p_data)) { 1015 status = 1016 GATTC_ExecuteWrite(p_clcb->bta_conn_id, p_data->api_exec.is_execute); 1017 1018 if (status != BTA_GATT_OK) { 1019 /* Dequeue the data, if it was enqueued */ 1020 if (p_clcb->p_q_cmd == p_data) p_clcb->p_q_cmd = NULL; 1021 1022 bta_gattc_cmpl_sendmsg(p_clcb->bta_conn_id, GATTC_OPTYPE_EXE_WRITE, 1023 status, NULL); 1024 } 1025 } 1026 } 1027 /******************************************************************************* 1028 * 1029 * Function bta_gattc_confirm 1030 * 1031 * Description send handle value confirmation 1032 * 1033 * Returns None. 1034 * 1035 ******************************************************************************/ 1036 void bta_gattc_confirm(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 1037 uint16_t handle = p_data->api_confirm.handle; 1038 1039 if (GATTC_SendHandleValueConfirm(p_data->api_confirm.hdr.layer_specific, 1040 handle) != GATT_SUCCESS) { 1041 APPL_TRACE_ERROR("%s: to handle [0x%04x] failed", __func__, handle); 1042 } else { 1043 /* if over BR_EDR, inform PM for mode change */ 1044 if (p_clcb->transport == BTA_TRANSPORT_BR_EDR) { 1045 bta_sys_busy(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda); 1046 bta_sys_idle(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda); 1047 } 1048 } 1049 } 1050 /******************************************************************************* 1051 * 1052 * Function bta_gattc_read_cmpl 1053 * 1054 * Description read complete 1055 * 1056 * Returns None. 1057 * 1058 ******************************************************************************/ 1059 void bta_gattc_read_cmpl(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_OP_CMPL* p_data) { 1060 GATT_READ_OP_CB cb = p_clcb->p_q_cmd->api_read.read_cb; 1061 void* my_cb_data = p_clcb->p_q_cmd->api_read.read_cb_data; 1062 1063 /* if it was read by handle, return the handle requested, if read by UUID, use 1064 * handle returned from remote 1065 */ 1066 uint16_t handle = p_clcb->p_q_cmd->api_read.handle; 1067 if (handle == 0) handle = p_data->p_cmpl->att_value.handle; 1068 1069 osi_free_and_reset((void**)&p_clcb->p_q_cmd); 1070 1071 if (cb) { 1072 cb(p_clcb->bta_conn_id, p_data->status, handle, 1073 p_data->p_cmpl->att_value.len, p_data->p_cmpl->att_value.value, 1074 my_cb_data); 1075 } 1076 } 1077 /******************************************************************************* 1078 * 1079 * Function bta_gattc_write_cmpl 1080 * 1081 * Description write complete 1082 * 1083 * Returns None. 1084 * 1085 ******************************************************************************/ 1086 void bta_gattc_write_cmpl(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_OP_CMPL* p_data) { 1087 GATT_WRITE_OP_CB cb = p_clcb->p_q_cmd->api_write.write_cb; 1088 void* my_cb_data = p_clcb->p_q_cmd->api_write.write_cb_data; 1089 1090 osi_free_and_reset((void**)&p_clcb->p_q_cmd); 1091 1092 if (cb) { 1093 cb(p_clcb->bta_conn_id, p_data->status, p_data->p_cmpl->att_value.handle, 1094 my_cb_data); 1095 } 1096 } 1097 /******************************************************************************* 1098 * 1099 * Function bta_gattc_exec_cmpl 1100 * 1101 * Description execute write complete 1102 * 1103 * Returns None. 1104 * 1105 ******************************************************************************/ 1106 void bta_gattc_exec_cmpl(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_OP_CMPL* p_data) { 1107 tBTA_GATTC cb_data; 1108 1109 osi_free_and_reset((void**)&p_clcb->p_q_cmd); 1110 p_clcb->status = BTA_GATT_OK; 1111 1112 /* execute complete, callback */ 1113 cb_data.exec_cmpl.conn_id = p_clcb->bta_conn_id; 1114 cb_data.exec_cmpl.status = p_data->status; 1115 1116 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_EXEC_EVT, &cb_data); 1117 } 1118 1119 /******************************************************************************* 1120 * 1121 * Function bta_gattc_cfg_mtu_cmpl 1122 * 1123 * Description configure MTU operation complete 1124 * 1125 * Returns None. 1126 * 1127 ******************************************************************************/ 1128 void bta_gattc_cfg_mtu_cmpl(tBTA_GATTC_CLCB* p_clcb, 1129 tBTA_GATTC_OP_CMPL* p_data) { 1130 tBTA_GATTC cb_data; 1131 1132 osi_free_and_reset((void**)&p_clcb->p_q_cmd); 1133 1134 if (p_data->p_cmpl && p_data->status == BTA_GATT_OK) 1135 p_clcb->p_srcb->mtu = p_data->p_cmpl->mtu; 1136 1137 /* configure MTU complete, callback */ 1138 p_clcb->status = p_data->status; 1139 cb_data.cfg_mtu.conn_id = p_clcb->bta_conn_id; 1140 cb_data.cfg_mtu.status = p_data->status; 1141 cb_data.cfg_mtu.mtu = p_clcb->p_srcb->mtu; 1142 1143 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CFG_MTU_EVT, &cb_data); 1144 } 1145 /******************************************************************************* 1146 * 1147 * Function bta_gattc_op_cmpl 1148 * 1149 * Description operation completed. 1150 * 1151 * Returns None. 1152 * 1153 ******************************************************************************/ 1154 void bta_gattc_op_cmpl(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 1155 uint8_t op = (uint8_t)p_data->op_cmpl.op_code; 1156 uint8_t mapped_op = 0; 1157 1158 APPL_TRACE_DEBUG("%s: op = %d", __func__, op); 1159 1160 if (op == GATTC_OPTYPE_INDICATION || op == GATTC_OPTYPE_NOTIFICATION) { 1161 APPL_TRACE_ERROR("unexpected operation, ignored"); 1162 } else if (op >= GATTC_OPTYPE_READ) { 1163 if (p_clcb->p_q_cmd == NULL) { 1164 APPL_TRACE_ERROR("No pending command"); 1165 return; 1166 } 1167 if (p_clcb->p_q_cmd->hdr.event != 1168 bta_gattc_opcode_to_int_evt[op - GATTC_OPTYPE_READ]) { 1169 mapped_op = p_clcb->p_q_cmd->hdr.event - BTA_GATTC_API_READ_EVT + 1170 GATTC_OPTYPE_READ; 1171 if (mapped_op > GATTC_OPTYPE_INDICATION) mapped_op = 0; 1172 1173 APPL_TRACE_ERROR( 1174 "expect op:(%s :0x%04x), receive unexpected operation (%s).", 1175 bta_gattc_op_code_name[mapped_op], p_clcb->p_q_cmd->hdr.event, 1176 bta_gattc_op_code_name[op]); 1177 return; 1178 } 1179 1180 /* Except for MTU configuration, discard responses if service change 1181 * indication is received before operation completed 1182 */ 1183 if (p_clcb->auto_update == BTA_GATTC_DISC_WAITING && 1184 p_clcb->p_srcb->srvc_hdl_chg && op != GATTC_OPTYPE_CONFIG) { 1185 APPL_TRACE_DEBUG( 1186 "Discard all responses when service change indication is received."); 1187 p_data->op_cmpl.status = GATT_ERROR; 1188 } 1189 1190 /* service handle change void the response, discard it */ 1191 if (op == GATTC_OPTYPE_READ) 1192 bta_gattc_read_cmpl(p_clcb, &p_data->op_cmpl); 1193 1194 else if (op == GATTC_OPTYPE_WRITE) 1195 bta_gattc_write_cmpl(p_clcb, &p_data->op_cmpl); 1196 1197 else if (op == GATTC_OPTYPE_EXE_WRITE) 1198 bta_gattc_exec_cmpl(p_clcb, &p_data->op_cmpl); 1199 1200 else if (op == GATTC_OPTYPE_CONFIG) 1201 bta_gattc_cfg_mtu_cmpl(p_clcb, &p_data->op_cmpl); 1202 1203 if (p_clcb->auto_update == BTA_GATTC_DISC_WAITING) { 1204 p_clcb->auto_update = BTA_GATTC_REQ_WAITING; 1205 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL); 1206 } 1207 } 1208 } 1209 /******************************************************************************* 1210 * 1211 * Function bta_gattc_op_cmpl 1212 * 1213 * Description operation completed. 1214 * 1215 * Returns None. 1216 * 1217 ******************************************************************************/ 1218 void bta_gattc_ignore_op_cmpl(UNUSED_ATTR tBTA_GATTC_CLCB* p_clcb, 1219 tBTA_GATTC_DATA* p_data) { 1220 /* receive op complete when discovery is started, ignore the response, 1221 and wait for discovery finish and resent */ 1222 APPL_TRACE_DEBUG("%s: op = %d", __func__, p_data->hdr.layer_specific); 1223 } 1224 /******************************************************************************* 1225 * 1226 * Function bta_gattc_search 1227 * 1228 * Description start a search in the local server cache 1229 * 1230 * Returns None. 1231 * 1232 ******************************************************************************/ 1233 void bta_gattc_search(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 1234 tBTA_GATT_STATUS status = GATT_INTERNAL_ERROR; 1235 tBTA_GATTC cb_data; 1236 APPL_TRACE_DEBUG("%s: conn_id=%d", __func__, p_clcb->bta_conn_id); 1237 if (p_clcb->p_srcb && p_clcb->p_srcb->p_srvc_cache) { 1238 status = BTA_GATT_OK; 1239 /* search the local cache of a server device */ 1240 bta_gattc_search_service(p_clcb, p_data->api_search.p_srvc_uuid); 1241 } 1242 cb_data.search_cmpl.status = status; 1243 cb_data.search_cmpl.conn_id = p_clcb->bta_conn_id; 1244 1245 /* end of search or no server cache available */ 1246 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_SEARCH_CMPL_EVT, &cb_data); 1247 } 1248 /******************************************************************************* 1249 * 1250 * Function bta_gattc_q_cmd 1251 * 1252 * Description enqueue a command into control block, usually because 1253 * discovery operation is busy. 1254 * 1255 * Returns None. 1256 * 1257 ******************************************************************************/ 1258 void bta_gattc_q_cmd(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) { 1259 bta_gattc_enqueue(p_clcb, p_data); 1260 } 1261 1262 /******************************************************************************* 1263 * 1264 * Function bta_gattc_fail 1265 * 1266 * Description report API call failure back to apps 1267 * 1268 * Returns None. 1269 * 1270 ******************************************************************************/ 1271 void bta_gattc_fail(tBTA_GATTC_CLCB* p_clcb, 1272 UNUSED_ATTR tBTA_GATTC_DATA* p_data) { 1273 if (p_clcb->status == BTA_GATT_OK) { 1274 APPL_TRACE_ERROR("operation not supported at current state [%d]", 1275 p_clcb->state); 1276 } 1277 } 1278 1279 /******************************************************************************* 1280 * 1281 * Function bta_gattc_deregister_cmpl 1282 * 1283 * Description De-Register a GATT client application with BTA completed. 1284 * 1285 * Returns void 1286 * 1287 ******************************************************************************/ 1288 static void bta_gattc_deregister_cmpl(tBTA_GATTC_RCB* p_clreg) { 1289 tBTA_GATTC_IF client_if = p_clreg->client_if; 1290 tBTA_GATTC cb_data; 1291 tBTA_GATTC_CBACK* p_cback = p_clreg->p_cback; 1292 1293 memset(&cb_data, 0, sizeof(tBTA_GATTC)); 1294 1295 GATT_Deregister(p_clreg->client_if); 1296 memset(p_clreg, 0, sizeof(tBTA_GATTC_RCB)); 1297 1298 cb_data.reg_oper.client_if = client_if; 1299 cb_data.reg_oper.status = BTA_GATT_OK; 1300 1301 if (p_cback) /* callback with de-register event */ 1302 (*p_cback)(BTA_GATTC_DEREG_EVT, &cb_data); 1303 1304 if (bta_gattc_num_reg_app() == 0 && 1305 bta_gattc_cb.state == BTA_GATTC_STATE_DISABLING) { 1306 bta_gattc_cb.state = BTA_GATTC_STATE_DISABLED; 1307 } 1308 } 1309 /******************************************************************************* 1310 * 1311 * Function bta_gattc_conn_cback 1312 * 1313 * Description callback functions to GATT client stack. 1314 * 1315 * Returns void 1316 * 1317 ******************************************************************************/ 1318 static void bta_gattc_conn_cback(tGATT_IF gattc_if, const RawAddress& bdaddr, 1319 uint16_t conn_id, bool connected, 1320 tGATT_DISCONN_REASON reason, 1321 tBT_TRANSPORT transport) { 1322 if (reason != 0) { 1323 APPL_TRACE_WARNING("%s() - cif=%d connected=%d conn_id=%d reason=0x%04x", 1324 __func__, gattc_if, connected, conn_id, reason); 1325 } 1326 1327 if (connected) 1328 btif_debug_conn_state(bdaddr, BTIF_DEBUG_CONNECTED, GATT_CONN_UNKNOWN); 1329 else 1330 btif_debug_conn_state(bdaddr, BTIF_DEBUG_DISCONNECTED, reason); 1331 1332 tBTA_GATTC_DATA* p_buf = 1333 (tBTA_GATTC_DATA*)osi_calloc(sizeof(tBTA_GATTC_DATA)); 1334 p_buf->int_conn.hdr.event = 1335 connected ? BTA_GATTC_INT_CONN_EVT : BTA_GATTC_INT_DISCONN_EVT; 1336 p_buf->int_conn.hdr.layer_specific = conn_id; 1337 p_buf->int_conn.client_if = gattc_if; 1338 p_buf->int_conn.role = L2CA_GetBleConnRole(bdaddr); 1339 p_buf->int_conn.reason = reason; 1340 p_buf->int_conn.transport = transport; 1341 p_buf->int_conn.remote_bda = bdaddr; 1342 1343 bta_sys_sendmsg(p_buf); 1344 } 1345 1346 /******************************************************************************* 1347 * 1348 * Function bta_gattc_enc_cmpl_cback 1349 * 1350 * Description encryption complete callback function to GATT client stack. 1351 * 1352 * Returns void 1353 * 1354 ******************************************************************************/ 1355 static void bta_gattc_enc_cmpl_cback(tGATT_IF gattc_if, const RawAddress& bda) { 1356 tBTA_GATTC_CLCB* p_clcb = 1357 bta_gattc_find_clcb_by_cif(gattc_if, bda, BTA_GATT_TRANSPORT_LE); 1358 1359 if (p_clcb == NULL) return; 1360 1361 #if (BTA_HH_LE_INCLUDED == TRUE) 1362 /* filter this event just for BTA HH LE GATT client, 1363 * In the future, if we want to enable encryption complete event 1364 * for all GATT clients, we can remove this code 1365 */ 1366 if (!bta_hh_le_is_hh_gatt_if(gattc_if)) { 1367 return; 1368 } 1369 #endif 1370 1371 APPL_TRACE_DEBUG("%s: cif = %d", __func__, gattc_if); 1372 1373 do_in_bta_thread(FROM_HERE, 1374 base::Bind(&bta_gattc_process_enc_cmpl, gattc_if, bda)); 1375 } 1376 1377 /******************************************************************************* 1378 * 1379 * Function bta_gattc_process_api_refresh 1380 * 1381 * Description process refresh API to delete cache and start a new 1382 * discovery if currently connected. 1383 * 1384 * Returns None. 1385 * 1386 ******************************************************************************/ 1387 void bta_gattc_process_api_refresh(const RawAddress& remote_bda) { 1388 tBTA_GATTC_SERV* p_srvc_cb = bta_gattc_find_srvr_cache(remote_bda); 1389 tBTA_GATTC_CLCB* p_clcb = &bta_gattc_cb.clcb[0]; 1390 bool found = false; 1391 uint8_t i; 1392 1393 if (p_srvc_cb != NULL) { 1394 /* try to find a CLCB */ 1395 if (p_srvc_cb->connected && p_srvc_cb->num_clcb != 0) { 1396 for (i = 0; i < BTA_GATTC_CLCB_MAX; i++, p_clcb++) { 1397 if (p_clcb->in_use && p_clcb->p_srcb == p_srvc_cb) { 1398 found = true; 1399 break; 1400 } 1401 } 1402 if (found) { 1403 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL); 1404 return; 1405 } 1406 } 1407 /* in all other cases, mark it and delete the cache */ 1408 if (p_srvc_cb->p_srvc_cache != NULL) { 1409 list_free(p_srvc_cb->p_srvc_cache); 1410 p_srvc_cb->p_srvc_cache = NULL; 1411 } 1412 } 1413 /* used to reset cache in application */ 1414 bta_gattc_cache_reset(remote_bda); 1415 } 1416 /******************************************************************************* 1417 * 1418 * Function bta_gattc_process_srvc_chg_ind 1419 * 1420 * Description process service change indication. 1421 * 1422 * Returns None. 1423 * 1424 ******************************************************************************/ 1425 bool bta_gattc_process_srvc_chg_ind(uint16_t conn_id, tBTA_GATTC_RCB* p_clrcb, 1426 tBTA_GATTC_SERV* p_srcb, 1427 tBTA_GATTC_CLCB* p_clcb, 1428 tBTA_GATTC_NOTIFY* p_notify, 1429 tGATT_VALUE* att_value) { 1430 tBT_UUID gattp_uuid, srvc_chg_uuid; 1431 bool processed = false; 1432 uint8_t i; 1433 1434 gattp_uuid.len = 2; 1435 gattp_uuid.uu.uuid16 = UUID_SERVCLASS_GATT_SERVER; 1436 1437 srvc_chg_uuid.len = 2; 1438 srvc_chg_uuid.uu.uuid16 = GATT_UUID_GATT_SRV_CHGD; 1439 1440 const tBTA_GATTC_CHARACTERISTIC* p_char = 1441 bta_gattc_get_characteristic_srcb(p_srcb, p_notify->handle); 1442 if (p_char && 1443 bta_gattc_uuid_compare(&p_char->service->uuid, &gattp_uuid, true) && 1444 bta_gattc_uuid_compare(&p_char->uuid, &srvc_chg_uuid, true)) { 1445 if (att_value->len != BTA_GATTC_SERVICE_CHANGED_LEN) { 1446 APPL_TRACE_ERROR( 1447 "%s: received malformed service changed indication, skipping", 1448 __func__); 1449 return false; 1450 } 1451 1452 uint8_t* p = att_value->value; 1453 uint16_t s_handle = ((uint16_t)(*(p)) + (((uint16_t)(*(p + 1))) << 8)); 1454 uint16_t e_handle = ((uint16_t)(*(p + 2)) + (((uint16_t)(*(p + 3))) << 8)); 1455 1456 APPL_TRACE_ERROR("%s: service changed s_handle:0x%04x e_handle:0x%04x", 1457 __func__, s_handle, e_handle); 1458 1459 processed = true; 1460 /* mark service handle change pending */ 1461 p_srcb->srvc_hdl_chg = true; 1462 /* clear up all notification/indication registration */ 1463 bta_gattc_clear_notif_registration(p_srcb, conn_id, s_handle, e_handle); 1464 /* service change indication all received, do discovery update */ 1465 if (++p_srcb->update_count == bta_gattc_num_reg_app()) { 1466 /* not an opened connection; or connection busy */ 1467 /* search for first available clcb and start discovery */ 1468 if (p_clcb == NULL || (p_clcb && p_clcb->p_q_cmd != NULL)) { 1469 for (i = 0; i < BTA_GATTC_CLCB_MAX; i++) { 1470 if (bta_gattc_cb.clcb[i].in_use && 1471 bta_gattc_cb.clcb[i].p_srcb == p_srcb && 1472 bta_gattc_cb.clcb[i].p_q_cmd == NULL) { 1473 p_clcb = &bta_gattc_cb.clcb[i]; 1474 break; 1475 } 1476 } 1477 } 1478 /* send confirmation here if this is an indication, it should always be */ 1479 GATTC_SendHandleValueConfirm(conn_id, att_value->handle); 1480 1481 /* if connection available, refresh cache by doing discovery now */ 1482 if (p_clcb != NULL) 1483 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL); 1484 } 1485 /* notify applicationf or service change */ 1486 if (p_clrcb->p_cback != NULL) { 1487 tBTA_GATTC bta_gattc; 1488 bta_gattc.remote_bda = p_srcb->server_bda; 1489 (*p_clrcb->p_cback)(BTA_GATTC_SRVC_CHG_EVT, &bta_gattc); 1490 } 1491 } 1492 1493 return processed; 1494 } 1495 /******************************************************************************* 1496 * 1497 * Function bta_gattc_proc_other_indication 1498 * 1499 * Description process all non-service change indication/notification. 1500 * 1501 * Returns None. 1502 * 1503 ******************************************************************************/ 1504 void bta_gattc_proc_other_indication(tBTA_GATTC_CLCB* p_clcb, uint8_t op, 1505 tGATT_CL_COMPLETE* p_data, 1506 tBTA_GATTC_NOTIFY* p_notify) { 1507 APPL_TRACE_DEBUG("%s: check p_data->att_value.handle=%d p_data->handle=%d", 1508 __func__, p_data->att_value.handle, p_data->handle); 1509 APPL_TRACE_DEBUG("is_notify", p_notify->is_notify); 1510 1511 p_notify->is_notify = (op == GATTC_OPTYPE_INDICATION) ? false : true; 1512 p_notify->len = p_data->att_value.len; 1513 p_notify->bda = p_clcb->bda; 1514 memcpy(p_notify->value, p_data->att_value.value, p_data->att_value.len); 1515 p_notify->conn_id = p_clcb->bta_conn_id; 1516 1517 if (p_clcb->p_rcb->p_cback) { 1518 tBTA_GATTC bta_gattc; 1519 bta_gattc.notify = *p_notify; 1520 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_NOTIF_EVT, &bta_gattc); 1521 } 1522 } 1523 /******************************************************************************* 1524 * 1525 * Function bta_gattc_process_indicate 1526 * 1527 * Description process indication/notification. 1528 * 1529 * Returns None. 1530 * 1531 ******************************************************************************/ 1532 void bta_gattc_process_indicate(uint16_t conn_id, tGATTC_OPTYPE op, 1533 tGATT_CL_COMPLETE* p_data) { 1534 uint16_t handle = p_data->att_value.handle; 1535 tBTA_GATTC_CLCB* p_clcb; 1536 tBTA_GATTC_RCB* p_clrcb = NULL; 1537 tBTA_GATTC_SERV* p_srcb = NULL; 1538 tBTA_GATTC_NOTIFY notify; 1539 RawAddress remote_bda; 1540 tBTA_GATTC_IF gatt_if; 1541 tBTA_TRANSPORT transport; 1542 1543 if (!GATT_GetConnectionInfor(conn_id, &gatt_if, remote_bda, &transport)) { 1544 APPL_TRACE_ERROR("%s indication/notif for unknown app", __func__); 1545 if (op == GATTC_OPTYPE_INDICATION) 1546 GATTC_SendHandleValueConfirm(conn_id, handle); 1547 return; 1548 } 1549 1550 p_clrcb = bta_gattc_cl_get_regcb(gatt_if); 1551 if (p_clrcb == NULL) { 1552 APPL_TRACE_ERROR("%s indication/notif for unregistered app", __func__); 1553 if (op == GATTC_OPTYPE_INDICATION) 1554 GATTC_SendHandleValueConfirm(conn_id, handle); 1555 return; 1556 } 1557 1558 p_srcb = bta_gattc_find_srcb(remote_bda); 1559 if (p_srcb == NULL) { 1560 APPL_TRACE_ERROR("%s indication/notif for unknown device, ignore", 1561 __func__); 1562 if (op == GATTC_OPTYPE_INDICATION) 1563 GATTC_SendHandleValueConfirm(conn_id, handle); 1564 return; 1565 } 1566 1567 p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id); 1568 1569 notify.handle = handle; 1570 /* if non-service change indication/notification, forward to application */ 1571 if (!bta_gattc_process_srvc_chg_ind(conn_id, p_clrcb, p_srcb, p_clcb, ¬ify, 1572 &p_data->att_value)) { 1573 /* if app registered for the notification */ 1574 if (bta_gattc_check_notif_registry(p_clrcb, p_srcb, ¬ify)) { 1575 /* connection not open yet */ 1576 if (p_clcb == NULL) { 1577 p_clcb = bta_gattc_clcb_alloc(gatt_if, remote_bda, transport); 1578 1579 if (p_clcb == NULL) { 1580 APPL_TRACE_ERROR("No resources"); 1581 return; 1582 } 1583 1584 p_clcb->bta_conn_id = conn_id; 1585 p_clcb->transport = transport; 1586 1587 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CONN_EVT, NULL); 1588 } 1589 1590 if (p_clcb != NULL) 1591 bta_gattc_proc_other_indication(p_clcb, op, p_data, ¬ify); 1592 } 1593 /* no one intersted and need ack? */ 1594 else if (op == GATTC_OPTYPE_INDICATION) { 1595 APPL_TRACE_DEBUG("%s no one interested, ack now", __func__); 1596 GATTC_SendHandleValueConfirm(conn_id, handle); 1597 } 1598 } 1599 } 1600 /******************************************************************************* 1601 * 1602 * Function bta_gattc_cmpl_cback 1603 * 1604 * Description client operation complete callback register with BTE GATT. 1605 * 1606 * Returns None. 1607 * 1608 ******************************************************************************/ 1609 static void bta_gattc_cmpl_cback(uint16_t conn_id, tGATTC_OPTYPE op, 1610 tGATT_STATUS status, 1611 tGATT_CL_COMPLETE* p_data) { 1612 tBTA_GATTC_CLCB* p_clcb; 1613 APPL_TRACE_DEBUG("bta_gattc_cmpl_cback: conn_id = %d op = %d status = %d", 1614 conn_id, op, status); 1615 1616 /* notification and indication processed right away */ 1617 if (op == GATTC_OPTYPE_NOTIFICATION || op == GATTC_OPTYPE_INDICATION) { 1618 bta_gattc_process_indicate(conn_id, op, p_data); 1619 return; 1620 } 1621 /* for all other operation, not expected if w/o connection */ 1622 else { 1623 p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id); 1624 if (p_clcb == NULL) { 1625 APPL_TRACE_ERROR("%s: unknown conn_id = %d, ignore data", __func__, 1626 conn_id); 1627 return; 1628 } 1629 } 1630 1631 /* if over BR_EDR, inform PM for mode change */ 1632 if (p_clcb->transport == BTA_TRANSPORT_BR_EDR) { 1633 bta_sys_busy(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda); 1634 bta_sys_idle(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda); 1635 } 1636 1637 bta_gattc_cmpl_sendmsg(conn_id, op, status, p_data); 1638 } 1639 1640 /******************************************************************************* 1641 * 1642 * Function bta_gattc_cmpl_sendmsg 1643 * 1644 * Description client operation complete send message 1645 * 1646 * Returns None. 1647 * 1648 ******************************************************************************/ 1649 static void bta_gattc_cmpl_sendmsg(uint16_t conn_id, tGATTC_OPTYPE op, 1650 tBTA_GATT_STATUS status, 1651 tGATT_CL_COMPLETE* p_data) { 1652 const size_t len = sizeof(tBTA_GATTC_OP_CMPL) + sizeof(tGATT_CL_COMPLETE); 1653 tBTA_GATTC_OP_CMPL* p_buf = (tBTA_GATTC_OP_CMPL*)osi_calloc(len); 1654 1655 p_buf->hdr.event = BTA_GATTC_OP_CMPL_EVT; 1656 p_buf->hdr.layer_specific = conn_id; 1657 p_buf->status = status; 1658 p_buf->op_code = op; 1659 1660 if (p_data != NULL) { 1661 p_buf->p_cmpl = (tGATT_CL_COMPLETE*)(p_buf + 1); 1662 memcpy(p_buf->p_cmpl, p_data, sizeof(tGATT_CL_COMPLETE)); 1663 } 1664 1665 bta_sys_sendmsg(p_buf); 1666 } 1667 1668 /******************************************************************************* 1669 * 1670 * Function bta_gattc_cong_cback 1671 * 1672 * Description congestion callback for BTA GATT client. 1673 * 1674 * Returns void 1675 * 1676 ******************************************************************************/ 1677 static void bta_gattc_cong_cback(uint16_t conn_id, bool congested) { 1678 tBTA_GATTC_CLCB* p_clcb; 1679 tBTA_GATTC cb_data; 1680 1681 p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id); 1682 if (p_clcb != NULL) { 1683 if (p_clcb->p_rcb->p_cback) { 1684 cb_data.congest.conn_id = conn_id; 1685 cb_data.congest.congested = congested; 1686 1687 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CONGEST_EVT, &cb_data); 1688 } 1689 } 1690 } 1691 1692 static void bta_gattc_phy_update_cback(tGATT_IF gatt_if, uint16_t conn_id, 1693 uint8_t tx_phy, uint8_t rx_phy, 1694 uint8_t status) { 1695 tBTA_GATTC_RCB* p_clreg = bta_gattc_cl_get_regcb(gatt_if); 1696 1697 if (!p_clreg || !p_clreg->p_cback) { 1698 APPL_TRACE_ERROR("%s: client_if=%d not found", __func__, gatt_if); 1699 return; 1700 } 1701 1702 tBTA_GATTC cb_data; 1703 cb_data.phy_update.conn_id = conn_id; 1704 cb_data.phy_update.server_if = gatt_if; 1705 cb_data.phy_update.tx_phy = tx_phy; 1706 cb_data.phy_update.rx_phy = rx_phy; 1707 cb_data.phy_update.status = status; 1708 (*p_clreg->p_cback)(BTA_GATTC_PHY_UPDATE_EVT, &cb_data); 1709 } 1710 1711 static void bta_gattc_conn_update_cback(tGATT_IF gatt_if, uint16_t conn_id, 1712 uint16_t interval, uint16_t latency, 1713 uint16_t timeout, uint8_t status) { 1714 tBTA_GATTC_RCB* p_clreg = bta_gattc_cl_get_regcb(gatt_if); 1715 1716 if (!p_clreg || !p_clreg->p_cback) { 1717 APPL_TRACE_ERROR("%s: client_if=%d not found", __func__, gatt_if); 1718 return; 1719 } 1720 1721 tBTA_GATTC cb_data; 1722 cb_data.conn_update.conn_id = conn_id; 1723 cb_data.conn_update.interval = interval; 1724 cb_data.conn_update.latency = latency; 1725 cb_data.conn_update.timeout = timeout; 1726 cb_data.conn_update.status = status; 1727 (*p_clreg->p_cback)(BTA_GATTC_CONN_UPDATE_EVT, &cb_data); 1728 } 1729