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 #include "bt_target.h" 27 28 #include "utl.h" 29 #include "gki.h" 30 #include "bd.h" 31 #include "bta_sys.h" 32 33 #include "bta_gattc_int.h" 34 #include "l2c_api.h" 35 36 37 #include <string.h> 38 39 #if BTA_GATT_INCLUDED && BLE_INCLUDED == TRUE 40 41 /***************************************************************************** 42 ** Constants 43 *****************************************************************************/ 44 static void bta_gattc_conn_cback(tGATT_IF gattc_if, BD_ADDR bda, UINT16 conn_id, 45 BOOLEAN connected, tGATT_DISCONN_REASON reason); 46 47 static void bta_gattc_cmpl_cback(UINT16 conn_id, tGATTC_OPTYPE op, tGATT_STATUS status, 48 tGATT_CL_COMPLETE *p_data); 49 50 static void bta_gattc_deregister_cmpl(tBTA_GATTC_RCB *p_clreg); 51 52 static tGATT_CBACK bta_gattc_cl_cback = 53 { 54 bta_gattc_conn_cback, 55 bta_gattc_cmpl_cback, 56 bta_gattc_disc_res_cback, 57 bta_gattc_disc_cmpl_cback, 58 NULL 59 }; 60 61 /* opcode(tGATTC_OPTYPE) order has to be comply with internal event order */ 62 static UINT16 bta_gattc_opcode_to_int_evt[] = 63 { 64 BTA_GATTC_API_READ_EVT, 65 BTA_GATTC_API_WRITE_EVT, 66 BTA_GATTC_API_EXEC_EVT 67 }; 68 69 #if (BT_TRACE_VERBOSE == TRUE) 70 static const char *bta_gattc_op_code_name[] = 71 { 72 "Unknown", 73 "Discovery", 74 "Read", 75 "Write", 76 "Exec", 77 "Config", 78 "Notification", 79 "Indication" 80 }; 81 #endif 82 /***************************************************************************** 83 ** Action Functions 84 *****************************************************************************/ 85 86 /******************************************************************************* 87 ** 88 ** Function bta_gattc_enable 89 ** 90 ** Description Enables GATTC module 91 ** 92 ** 93 ** Returns void 94 ** 95 *******************************************************************************/ 96 static void bta_gattc_enable(tBTA_GATTC_CB *p_cb) 97 { 98 APPL_TRACE_DEBUG0("bta_gattc_enable"); 99 100 if (p_cb->state == BTA_GATTC_STATE_DISABLED) 101 { 102 /* initialize control block */ 103 memset(&bta_gattc_cb, 0, sizeof(tBTA_GATTC_CB)); 104 p_cb->state = BTA_GATTC_STATE_ENABLED; 105 } 106 else 107 { 108 APPL_TRACE_DEBUG0("GATTC is arelady enabled"); 109 } 110 } 111 112 113 /******************************************************************************* 114 ** 115 ** Function bta_gattc_disable 116 ** 117 ** Description Disable GATTC module by cleaning up all active connections 118 ** and deregister all application. 119 ** 120 ** Returns void 121 ** 122 *******************************************************************************/ 123 void bta_gattc_disable(tBTA_GATTC_CB *p_cb) 124 { 125 UINT8 i; 126 127 APPL_TRACE_DEBUG0("bta_gattc_disable"); 128 129 if (p_cb->state != BTA_GATTC_STATE_ENABLED) 130 { 131 APPL_TRACE_ERROR0("not enabled or disable in pogress"); 132 return; 133 } 134 135 for (i = 0; i <BTA_GATTC_CL_MAX; i ++) 136 { 137 if (p_cb->cl_rcb[i].in_use) 138 { 139 p_cb->state = BTA_GATTC_STATE_DISABLING; 140 bta_gattc_deregister(p_cb, &p_cb->cl_rcb[i]); 141 } 142 } 143 144 /* no registered apps, indicate disable completed */ 145 if (p_cb->state != BTA_GATTC_STATE_DISABLING) 146 { 147 p_cb->state = BTA_GATTC_STATE_DISABLED; 148 memset(p_cb, 0, sizeof(tBTA_GATTC_CB)); 149 } 150 } 151 152 /******************************************************************************* 153 ** 154 ** Function bta_gattc_register 155 ** 156 ** Description Register a GATT client application with BTA. 157 ** 158 ** Returns void 159 ** 160 *******************************************************************************/ 161 void bta_gattc_register(tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA *p_data) 162 { 163 tBTA_GATTC cb_data; 164 UINT8 i; 165 tBT_UUID *p_app_uuid = &p_data->api_reg.app_uuid; 166 tBTA_GATTC_INT_START_IF *p_buf; 167 tBTA_GATT_STATUS status = BTA_GATT_NO_RESOURCES; 168 169 170 APPL_TRACE_DEBUG1("bta_gattc_register state %d",p_cb->state); 171 memset(&cb_data, 0, sizeof(cb_data)); 172 cb_data.reg_oper.status = BTA_GATT_NO_RESOURCES; 173 174 /* check if GATTC module is already enabled . Else enable */ 175 if (p_cb->state == BTA_GATTC_STATE_DISABLED) 176 { 177 bta_gattc_enable (p_cb); 178 } 179 /* todo need to check duplicate uuid */ 180 for (i = 0; i < BTA_GATTC_CL_MAX; i ++) 181 { 182 if (!p_cb->cl_rcb[i].in_use) 183 { 184 if ((p_app_uuid == NULL) || (p_cb->cl_rcb[i].client_if = GATT_Register(p_app_uuid, &bta_gattc_cl_cback)) == 0) 185 { 186 APPL_TRACE_ERROR0("Register with GATT stack failed."); 187 status = BTA_GATT_ERROR; 188 } 189 else 190 { 191 p_cb->cl_rcb[i].in_use = TRUE; 192 p_cb->cl_rcb[i].p_cback = p_data->api_reg.p_cback; 193 memcpy(&p_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 cb_data.reg_oper.client_if = p_cb->cl_rcb[i].client_if; 197 198 if ((p_buf = (tBTA_GATTC_INT_START_IF *) GKI_getbuf(sizeof(tBTA_GATTC_INT_START_IF))) != NULL) 199 { 200 p_buf->hdr.event = BTA_GATTC_INT_START_IF_EVT; 201 p_buf->client_if = p_cb->cl_rcb[i].client_if; 202 203 bta_sys_sendmsg(p_buf); 204 status = BTA_GATT_OK; 205 } 206 else 207 { 208 GATT_Deregister(p_cb->cl_rcb[i].client_if); 209 210 status = BTA_GATT_NO_RESOURCES; 211 memset( &p_cb->cl_rcb[i], 0 , sizeof(tBTA_GATTC_RCB)); 212 } 213 break; 214 } 215 } 216 } 217 218 /* callback with register event */ 219 if (p_data->api_reg.p_cback) 220 { 221 if (p_app_uuid != NULL) 222 memcpy(&(cb_data.reg_oper.app_uuid),p_app_uuid,sizeof(tBT_UUID)); 223 224 cb_data.reg_oper.status = status; 225 (*p_data->api_reg.p_cback)(BTA_GATTC_REG_EVT, (tBTA_GATTC *)&cb_data); 226 } 227 } 228 /******************************************************************************* 229 ** 230 ** Function bta_gattc_start_if 231 ** 232 ** Description start an application interface. 233 ** 234 ** Returns none. 235 ** 236 *******************************************************************************/ 237 void bta_gattc_start_if(tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA *p_msg) 238 { 239 if (bta_gattc_cl_get_regcb(p_msg->int_start_if.client_if) !=NULL ) 240 { 241 GATT_StartIf(p_msg->int_start_if.client_if); 242 } 243 else 244 { 245 APPL_TRACE_ERROR1("Unable to start app.: Unknown interface =%d",p_msg->int_start_if.client_if ); 246 } 247 } 248 /******************************************************************************* 249 ** 250 ** Function bta_gattc_deregister 251 ** 252 ** Description De-Register a GATT client application with BTA. 253 ** 254 ** Returns void 255 ** 256 *******************************************************************************/ 257 void bta_gattc_deregister(tBTA_GATTC_CB *p_cb, tBTA_GATTC_RCB *p_clreg) 258 { 259 UINT8 i; 260 BT_HDR buf; 261 262 if (p_clreg != NULL) 263 { 264 /* remove bg connection associated with this rcb */ 265 for (i = 0; i < BTA_GATTC_KNOWN_SR_MAX; i ++) 266 { 267 if (p_cb->bg_track[i].in_use) 268 { 269 if (p_cb->bg_track[i].cif_mask & (1 <<(p_clreg->client_if - 1))) 270 { 271 bta_gattc_mark_bg_conn(p_clreg->client_if, p_cb->bg_track[i].remote_bda, FALSE, FALSE); 272 GATT_CancelConnect(p_clreg->client_if, p_cb->bg_track[i].remote_bda, FALSE); 273 } 274 if (p_cb->bg_track[i].cif_adv_mask & (1 <<(p_clreg->client_if - 1))) 275 { 276 bta_gattc_mark_bg_conn(p_clreg->client_if, p_cb->bg_track[i].remote_bda, FALSE, TRUE); 277 } 278 } 279 } 280 281 if (p_clreg->num_clcb > 0) 282 { 283 /* close all CLCB related to this app */ 284 for (i= 0; i < BTA_GATTC_CLCB_MAX; i ++) 285 { 286 if (p_cb->clcb[i].in_use && (p_cb->clcb[i].p_rcb == p_clreg)) 287 { 288 p_clreg->dereg_pending = TRUE; 289 290 buf.event = BTA_GATTC_API_CLOSE_EVT; 291 buf.layer_specific = p_cb->clcb[i].bta_conn_id; 292 bta_gattc_close(&p_cb->clcb[i], (tBTA_GATTC_DATA *)&buf) ; 293 } 294 } 295 } 296 else 297 bta_gattc_deregister_cmpl(p_clreg); 298 } 299 else 300 { 301 APPL_TRACE_ERROR0("bta_gattc_deregister Deregister Failedm unknown client cif"); 302 } 303 } 304 /******************************************************************************* 305 ** 306 ** Function bta_gattc_process_api_open 307 ** 308 ** Description process connect API request. 309 ** 310 ** Returns void 311 ** 312 *******************************************************************************/ 313 void bta_gattc_process_api_open (tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA * p_msg) 314 { 315 UINT16 event = ((BT_HDR *)p_msg)->event; 316 tBTA_GATTC_CLCB *p_clcb = NULL; 317 tBTA_GATTC_RCB *p_clreg = bta_gattc_cl_get_regcb(p_msg->api_conn.client_if); 318 319 if (p_clreg != NULL) 320 { 321 if (p_msg->api_conn.is_direct) 322 { 323 if ((p_clcb = bta_gattc_find_alloc_clcb(p_msg->api_conn.client_if, 324 p_msg->api_conn.remote_bda)) != NULL) 325 { 326 bta_gattc_sm_execute(p_clcb, event, p_msg); 327 } 328 else 329 { 330 APPL_TRACE_ERROR0("No resources to open a new connection."); 331 332 bta_gattc_send_open_cback(p_clreg, 333 BTA_GATT_NO_RESOURCES, 334 p_msg->api_conn.remote_bda, 335 BTA_GATT_INVALID_CONN_ID); 336 } 337 } 338 else 339 { 340 bta_gattc_init_bk_conn(&p_msg->api_conn, p_clreg); 341 } 342 } 343 else 344 { 345 APPL_TRACE_ERROR1("bta_gattc_process_api_open Failed, unknown client_if: %d", 346 p_msg->api_conn.client_if); 347 } 348 } 349 /******************************************************************************* 350 ** 351 ** Function bta_gattc_process_api_open_cancel 352 ** 353 ** Description process connect API request. 354 ** 355 ** Returns void 356 ** 357 *******************************************************************************/ 358 void bta_gattc_process_api_open_cancel (tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA * p_msg) 359 { 360 UINT16 event = ((BT_HDR *)p_msg)->event; 361 tBTA_GATTC_CLCB *p_clcb = NULL; 362 tBTA_GATTC_RCB *p_clreg; 363 tBTA_GATTC cb_data; 364 365 if (p_msg->api_cancel_conn.is_direct) 366 { 367 if ((p_clcb = bta_gattc_find_clcb_by_cif(p_msg->api_cancel_conn.client_if, 368 p_msg->api_cancel_conn.remote_bda)) != NULL) 369 { 370 bta_gattc_sm_execute(p_clcb, event, p_msg); 371 } 372 else 373 { 374 APPL_TRACE_ERROR0("No such connection need to be cancelled"); 375 376 p_clreg = bta_gattc_cl_get_regcb(p_msg->api_cancel_conn.client_if); 377 378 if (p_clreg && p_clreg->p_cback) 379 { 380 cb_data.status = BTA_GATT_ERROR; 381 (*p_clreg->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data); 382 } 383 } 384 } 385 else 386 { 387 bta_gattc_cancel_bk_conn(&p_msg->api_cancel_conn); 388 389 } 390 } 391 /******************************************************************************* 392 ** 393 ** Function bta_gattc_cancel_open_error 394 ** 395 ** Description 396 ** 397 ** Returns void 398 ** 399 *******************************************************************************/ 400 void bta_gattc_cancel_open_error(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 401 { 402 tBTA_GATTC cb_data; 403 cb_data.status=BTA_GATT_ERROR; 404 405 if ( p_clcb && p_clcb->p_rcb && p_clcb->p_rcb->p_cback ) 406 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data); 407 } 408 409 /******************************************************************************* 410 ** 411 ** Function bta_gattc_open_error 412 ** 413 ** Description 414 ** 415 ** Returns void 416 ** 417 *******************************************************************************/ 418 void bta_gattc_open_error(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 419 { 420 APPL_TRACE_ERROR0("Connection already opened. wrong state"); 421 422 bta_gattc_send_open_cback(p_clcb->p_rcb, 423 BTA_GATT_OK, 424 p_clcb->bda, 425 p_clcb->bta_conn_id); 426 } 427 /******************************************************************************* 428 ** 429 ** Function bta_gattc_open_fail 430 ** 431 ** Description 432 ** 433 ** Returns void 434 ** 435 *******************************************************************************/ 436 void bta_gattc_open_fail(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 437 { 438 bta_gattc_send_open_cback(p_clcb->p_rcb, 439 BTA_GATT_ERROR, 440 p_clcb->bda, 441 p_clcb->bta_conn_id); 442 443 /* open failure, remove clcb */ 444 bta_gattc_clcb_dealloc(p_clcb); 445 } 446 447 /******************************************************************************* 448 ** 449 ** Function bta_gattc_open 450 ** 451 ** Description Process API connection function. 452 ** 453 ** Returns void 454 ** 455 *******************************************************************************/ 456 void bta_gattc_open(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 457 { 458 tBTA_GATTC_DATA gattc_data; 459 460 /* open/hold a connection */ 461 if (!GATT_Connect(p_clcb->p_rcb->client_if, p_data->api_conn.remote_bda, TRUE)) 462 { 463 APPL_TRACE_ERROR0("Connection open failure"); 464 465 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_OPEN_FAIL_EVT, p_data); 466 } 467 else 468 { 469 /* a connected remote device */ 470 if (GATT_GetConnIdIfConnected(p_clcb->p_rcb->client_if, 471 p_data->api_conn.remote_bda, 472 &p_clcb->bta_conn_id)) 473 { 474 gattc_data.int_conn.hdr.layer_specific = p_clcb->bta_conn_id; 475 476 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CONN_EVT, &gattc_data); 477 } 478 /* else wait for the callback event */ 479 } 480 } 481 /******************************************************************************* 482 ** 483 ** Function bta_gattc_init_bk_conn 484 ** 485 ** Description Process API Open for a background connection 486 ** 487 ** Returns void 488 ** 489 *******************************************************************************/ 490 void bta_gattc_init_bk_conn(tBTA_GATTC_API_OPEN *p_data, tBTA_GATTC_RCB *p_clreg) 491 { 492 tBTA_GATT_STATUS status = BTA_GATT_NO_RESOURCES; 493 UINT16 conn_id; 494 tBTA_GATTC_CLCB *p_clcb; 495 tBTA_GATTC_DATA gattc_data; 496 497 if (bta_gattc_mark_bg_conn(p_data->client_if, p_data->remote_bda, TRUE, FALSE)) 498 { 499 /* alwaya call open to hold a connection */ 500 if (!GATT_Connect(p_data->client_if, p_data->remote_bda, FALSE)) 501 { 502 status = BTA_GATT_ERROR; 503 APPL_TRACE_ERROR0("bta_gattc_init_bk_conn failed"); 504 } 505 else 506 { 507 status = BTA_GATT_OK; 508 509 /* if is a connected remote device */ 510 if (GATT_GetConnIdIfConnected(p_data->client_if, 511 p_data->remote_bda, 512 &conn_id)) 513 { 514 if ((p_clcb = bta_gattc_find_alloc_clcb(p_data->client_if, p_data->remote_bda)) != NULL) 515 { 516 gattc_data.hdr.layer_specific = p_clcb->bta_conn_id = conn_id; 517 518 /* open connection */ 519 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CONN_EVT, &gattc_data); 520 status = BTA_GATT_OK; 521 } 522 } 523 } 524 } 525 526 /* open failure, report OPEN_EVT */ 527 if (status != BTA_GATT_OK) 528 { 529 bta_gattc_send_open_cback(p_clreg, status, p_data->remote_bda, BTA_GATT_INVALID_CONN_ID); 530 } 531 } 532 /******************************************************************************* 533 ** 534 ** Function bta_gattc_cancel_bk_conn 535 ** 536 ** Description Process API Cancel Open for a background connection 537 ** 538 ** Returns void 539 ** 540 *******************************************************************************/ 541 void bta_gattc_cancel_bk_conn(tBTA_GATTC_API_CANCEL_OPEN *p_data) 542 { 543 tBTA_GATTC_RCB *p_clreg; 544 tBTA_GATTC cb_data; 545 cb_data.status = BTA_GATT_ERROR; 546 547 /* remove the device from the bg connection mask */ 548 if (bta_gattc_mark_bg_conn(p_data->client_if, p_data->remote_bda, FALSE, FALSE)) 549 { 550 if (GATT_CancelConnect(p_data->client_if, p_data->remote_bda, FALSE)) 551 { 552 cb_data.status = BTA_GATT_OK; 553 } 554 else 555 { 556 APPL_TRACE_ERROR0("bta_gattc_cancel_bk_conn failed"); 557 } 558 } 559 p_clreg = bta_gattc_cl_get_regcb(p_data->client_if); 560 561 if (p_clreg && p_clreg->p_cback) 562 { 563 (*p_clreg->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data); 564 } 565 566 } 567 /******************************************************************************* 568 ** 569 ** Function bta_gattc_int_cancel_open_ok 570 ** 571 ** Description 572 ** 573 ** Returns void 574 ** 575 *******************************************************************************/ 576 void bta_gattc_cancel_open_ok(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 577 { 578 tBTA_GATTC cb_data; 579 580 if ( p_clcb->p_rcb->p_cback ) 581 { 582 cb_data.status = BTA_GATT_OK; 583 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data); 584 } 585 586 bta_gattc_clcb_dealloc(p_clcb); 587 } 588 /******************************************************************************* 589 ** 590 ** Function bta_gattc_cancel_open 591 ** 592 ** Description 593 ** 594 ** Returns void 595 ** 596 *******************************************************************************/ 597 void bta_gattc_cancel_open(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 598 { 599 tBTA_GATTC cb_data; 600 601 if (GATT_CancelConnect(p_clcb->p_rcb->client_if, p_data->api_cancel_conn.remote_bda, TRUE)) 602 { 603 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CANCEL_OPEN_OK_EVT, p_data); 604 } 605 else 606 { 607 if ( p_clcb->p_rcb->p_cback ) 608 { 609 cb_data.status = BTA_GATT_ERROR; 610 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data); 611 } 612 } 613 } 614 /******************************************************************************* 615 ** 616 ** Function bta_gattc_conn 617 ** 618 ** Description receive connection callback from stack 619 ** 620 ** Returns void 621 ** 622 *******************************************************************************/ 623 void bta_gattc_conn(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 624 { 625 tBTA_GATTC_IF gatt_if; 626 APPL_TRACE_DEBUG1("bta_gattc_conn server cache state=%d",p_clcb->p_srcb->state); 627 628 if (p_data != NULL) 629 { 630 APPL_TRACE_DEBUG1("bta_gattc_conn conn_id=%d",p_data->hdr.layer_specific); 631 p_clcb->bta_conn_id = p_data->int_conn.hdr.layer_specific; 632 GATT_GetConnectionInfor(p_data->int_conn.hdr.layer_specific, &gatt_if, p_clcb->bda); 633 } 634 635 p_clcb->p_srcb->connected = TRUE; 636 /* start database cache if needed */ 637 if (p_clcb->p_srcb->p_srvc_cache == NULL || 638 p_clcb->p_srcb->state != BTA_GATTC_SERV_IDLE) 639 { 640 if (p_clcb->p_srcb->state == BTA_GATTC_SERV_IDLE) 641 { 642 p_clcb->p_srcb->state = BTA_GATTC_SERV_LOAD; 643 bta_gattc_sm_execute(p_clcb, BTA_GATTC_START_CACHE_EVT, NULL); 644 } 645 else /* cache is building */ 646 p_clcb->state = BTA_GATTC_DISCOVER_ST; 647 } 648 649 else 650 { 651 /* a pending service handle change indication */ 652 if (p_clcb->p_srcb->srvc_hdl_chg) 653 { 654 p_clcb->p_srcb->srvc_hdl_chg = FALSE; 655 /* start discovery */ 656 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL); 657 } 658 } 659 660 if (p_clcb->p_rcb) 661 { 662 /* there is no RM for GATT */ 663 if (!BTM_IsBleLink(p_clcb->bda)) 664 bta_sys_conn_open(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda); 665 bta_gattc_send_open_cback(p_clcb->p_rcb, 666 BTA_GATT_OK, 667 p_clcb->bda, 668 p_clcb->bta_conn_id); 669 } 670 } 671 /******************************************************************************* 672 ** 673 ** Function bta_gattc_close_fail 674 ** 675 ** Description close a connection. 676 ** 677 ** Returns void 678 ** 679 *******************************************************************************/ 680 void bta_gattc_close_fail(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 681 { 682 tBTA_GATTC cb_data; 683 684 if ( p_clcb->p_rcb->p_cback ) 685 { 686 memset(&cb_data, 0, sizeof(tBTA_GATTC)); 687 cb_data.close.client_if = p_clcb->p_rcb->client_if; 688 cb_data.close.conn_id = p_data->hdr.layer_specific; 689 bdcpy(cb_data.close.remote_bda, p_clcb->bda); 690 cb_data.close.status = BTA_GATT_ERROR; 691 cb_data.close.reason = BTA_GATT_CONN_NONE; 692 693 694 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CLOSE_EVT, &cb_data); 695 } 696 } 697 /******************************************************************************* 698 ** 699 ** Function bta_gattc_api_close 700 ** 701 ** Description close a GATTC connection. 702 ** 703 ** Returns void 704 ** 705 *******************************************************************************/ 706 void bta_gattc_close(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 707 { 708 tBTA_GATTC_CBACK *p_cback = p_clcb->p_rcb->p_cback; 709 tBTA_GATTC_RCB *p_clreg = p_clcb->p_rcb; 710 tBTA_GATTC cb_data; 711 712 APPL_TRACE_DEBUG1("bta_gattc_close conn_id=%d",p_clcb->bta_conn_id); 713 714 cb_data.close.client_if = p_clcb->p_rcb->client_if; 715 cb_data.close.conn_id = p_clcb->bta_conn_id; 716 cb_data.close.reason = p_clcb->reason; 717 cb_data.close.status = p_clcb->status; 718 bdcpy(cb_data.close.remote_bda, p_clcb->bda); 719 720 if (!BTM_IsBleLink(p_clcb->bda)) 721 bta_sys_conn_close( BTA_ID_GATTC ,BTA_ALL_APP_ID, p_clcb->bda); 722 723 bta_gattc_clcb_dealloc(p_clcb); 724 725 if (p_data->hdr.event == BTA_GATTC_API_CLOSE_EVT) 726 cb_data.close.status = GATT_Disconnect(p_data->hdr.layer_specific); 727 728 if(p_cback) 729 (* p_cback)(BTA_GATTC_CLOSE_EVT, (tBTA_GATTC *)&cb_data); 730 731 if (p_clreg->num_clcb == 0 && p_clreg->dereg_pending) 732 { 733 bta_gattc_deregister_cmpl(p_clreg); 734 } 735 } 736 /******************************************************************************* 737 ** 738 ** Function bta_gattc_reset_discover_st 739 ** 740 ** Description when a SRCB finished discovery, tell all related clcb. 741 ** 742 ** Returns None. 743 ** 744 *******************************************************************************/ 745 void bta_gattc_reset_discover_st(tBTA_GATTC_SERV *p_srcb, tBTA_GATT_STATUS status) 746 { 747 tBTA_GATTC_CB *p_cb = &bta_gattc_cb; 748 UINT8 i; 749 750 for (i = 0; i < BTA_GATTC_CLCB_MAX; i ++) 751 { 752 if (p_cb->clcb[i].p_srcb == p_srcb) 753 { 754 p_cb->clcb[i].status = status; 755 bta_gattc_sm_execute(&p_cb->clcb[i], BTA_GATTC_DISCOVER_CMPL_EVT, NULL); 756 } 757 } 758 } 759 /******************************************************************************* 760 ** 761 ** Function bta_gattc_disc_close 762 ** 763 ** Description close a GATTC connection while in discovery state. 764 ** 765 ** Returns void 766 ** 767 *******************************************************************************/ 768 void bta_gattc_disc_close(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 769 { 770 APPL_TRACE_DEBUG1("Discovery cancel conn_id=%d",p_clcb->bta_conn_id); 771 772 bta_gattc_reset_discover_st(p_clcb->p_srcb, BTA_GATT_ERROR); 773 bta_gattc_sm_execute(p_clcb, BTA_GATTC_API_CLOSE_EVT, p_data); 774 } 775 /******************************************************************************* 776 ** 777 ** Function bta_gattc_set_discover_st 778 ** 779 ** Description when a SRCB start discovery, tell all related clcb and set 780 ** the state. 781 ** 782 ** Returns None. 783 ** 784 *******************************************************************************/ 785 void bta_gattc_set_discover_st(tBTA_GATTC_SERV *p_srcb) 786 { 787 tBTA_GATTC_CB *p_cb = &bta_gattc_cb; 788 UINT8 i; 789 790 #if BLE_INCLUDED == TRUE 791 L2CA_EnableUpdateBleConnParams(p_srcb->server_bda, FALSE); 792 #endif 793 for (i = 0; i < BTA_GATTC_CLCB_MAX; i ++) 794 { 795 if (p_cb->clcb[i].p_srcb == p_srcb) 796 { 797 p_cb->clcb[i].status = BTA_GATT_OK; 798 p_cb->clcb[i].state = BTA_GATTC_DISCOVER_ST; 799 } 800 } 801 } 802 /******************************************************************************* 803 ** 804 ** Function bta_gattc_restart_discover 805 ** 806 ** Description process service change in discovery state, mark up the auto 807 ** update flag and set status to be discovery cancel for current 808 ** discovery. 809 ** 810 ** Returns None. 811 ** 812 *******************************************************************************/ 813 void bta_gattc_restart_discover(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 814 { 815 p_clcb->status = BTA_GATT_CANCEL; 816 p_clcb->auto_update = BTA_GATTC_DISC_WAITING; 817 } 818 /******************************************************************************* 819 ** 820 ** Function bta_gattc_start_discover 821 ** 822 ** Description Start a discovery on server. 823 ** 824 ** Returns None. 825 ** 826 *******************************************************************************/ 827 void bta_gattc_start_discover(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 828 { 829 830 APPL_TRACE_DEBUG2("bta_gattc_start_discover conn_id=%d p_clcb->p_srcb->state = %d ", 831 p_clcb->bta_conn_id, p_clcb->p_srcb->state); 832 833 if (((p_clcb->p_q_cmd == NULL || p_clcb->auto_update == BTA_GATTC_REQ_WAITING) && 834 p_clcb->p_srcb->state == BTA_GATTC_SERV_IDLE) || 835 p_clcb->p_srcb->state == BTA_GATTC_SERV_DISC) 836 /* no pending operation, start discovery right away */ 837 { 838 p_clcb->auto_update = BTA_GATTC_NO_SCHEDULE; 839 840 if (p_clcb->p_srcb != NULL) 841 { 842 /* clear the service change mask */ 843 p_clcb->p_srcb->srvc_hdl_chg = FALSE; 844 p_clcb->p_srcb->update_count = 0; 845 p_clcb->p_srcb->state = BTA_GATTC_SERV_DISC_ACT; 846 847 /* set all srcb related clcb into discovery ST */ 848 bta_gattc_set_discover_st(p_clcb->p_srcb); 849 850 if ((p_clcb->status = bta_gattc_init_cache(p_clcb->p_srcb)) == BTA_GATT_OK) 851 { 852 p_clcb->status = bta_gattc_discover_pri_service(p_clcb->bta_conn_id, p_clcb->p_srcb, GATT_DISC_SRVC_ALL); 853 } 854 if (p_clcb->status != BTA_GATT_OK) 855 { 856 APPL_TRACE_ERROR0("discovery on server failed"); 857 bta_gattc_reset_discover_st(p_clcb->p_srcb, p_clcb->status); 858 } 859 } 860 else 861 { 862 APPL_TRACE_ERROR0("unknown device, can not start discovery"); 863 } 864 } 865 /* pending operation, wait until it finishes */ 866 else 867 { 868 p_clcb->auto_update = BTA_GATTC_DISC_WAITING; 869 870 if (p_clcb->p_srcb->state == BTA_GATTC_SERV_IDLE) 871 p_clcb->state = BTA_GATTC_CONN_ST; /* set clcb state */ 872 } 873 874 } 875 /******************************************************************************* 876 ** 877 ** Function bta_gattc_disc_cmpl 878 ** 879 ** Description discovery on server is finished 880 ** 881 ** Returns None. 882 ** 883 *******************************************************************************/ 884 void bta_gattc_disc_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 885 { 886 tBTA_GATTC_DATA *p_q_cmd = p_clcb->p_q_cmd; 887 APPL_TRACE_DEBUG1("bta_gattc_disc_cmpl conn_id=%d",p_clcb->bta_conn_id); 888 889 #if BLE_INCLUDED == TRUE 890 L2CA_EnableUpdateBleConnParams(p_clcb->p_srcb->server_bda, TRUE); 891 #endif 892 p_clcb->p_srcb->state = BTA_GATTC_SERV_IDLE; 893 894 if (p_clcb->status != GATT_SUCCESS) 895 { 896 /* clean up cache */ 897 if(p_clcb->p_srcb && p_clcb->p_srcb->p_srvc_cache) 898 { 899 while (p_clcb->p_srcb->cache_buffer.p_first) 900 { 901 GKI_freebuf (GKI_dequeue (&p_clcb->p_srcb->cache_buffer)); 902 } 903 p_clcb->p_srcb->p_srvc_cache = NULL; 904 } 905 906 /* used to reset cache in application */ 907 bta_gattc_co_cache_reset(p_clcb->p_srcb->server_bda); 908 } 909 /* release pending attribute list buffer */ 910 utl_freebuf((void **)&p_clcb->p_srcb->p_srvc_list); 911 912 if (p_clcb->auto_update == BTA_GATTC_DISC_WAITING) 913 { 914 /* start discovery again */ 915 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL); 916 } 917 /* get any queued command to proceed */ 918 else if (p_q_cmd != NULL) 919 { 920 p_clcb->p_q_cmd = NULL; 921 922 bta_gattc_sm_execute(p_clcb, p_q_cmd->hdr.event, p_q_cmd); 923 924 utl_freebuf((void **)&p_q_cmd); 925 926 } 927 } 928 /******************************************************************************* 929 ** 930 ** Function bta_gattc_read 931 ** 932 ** Description Read an attribute 933 ** 934 ** Returns None. 935 ** 936 *******************************************************************************/ 937 void bta_gattc_read(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 938 { 939 UINT16 handle = 0; 940 tGATT_READ_PARAM read_param; 941 tBTA_GATTC_OP_CMPL op_cmpl; 942 943 memset (&read_param, 0 ,sizeof(tGATT_READ_PARAM)); 944 memset (&op_cmpl, 0 ,sizeof(tBTA_GATTC_OP_CMPL)); 945 946 if (bta_gattc_enqueue(p_clcb, p_data)) 947 { 948 if ((handle = bta_gattc_id2handle(p_clcb->p_srcb, 949 &p_data->api_read.srvc_id, 950 &p_data->api_read.char_id, 951 p_data->api_read.p_descr_type)) == 0) 952 { 953 op_cmpl.status = BTA_GATT_ERROR; 954 } 955 else 956 { 957 read_param.by_handle.handle = handle; 958 read_param.by_handle.auth_req = p_data->api_read.auth_req; 959 960 op_cmpl.status = GATTC_Read(p_clcb->bta_conn_id, GATT_READ_BY_HANDLE, &read_param); 961 } 962 963 /* read fail */ 964 if (op_cmpl.status != BTA_GATT_OK) 965 { 966 op_cmpl.op_code = GATTC_OPTYPE_READ; 967 op_cmpl.p_cmpl = NULL; 968 969 bta_gattc_sm_execute(p_clcb, BTA_GATTC_OP_CMPL_EVT, (tBTA_GATTC_DATA *)&op_cmpl); 970 } 971 } 972 } 973 /******************************************************************************* 974 ** 975 ** Function bta_gattc_read_multi 976 ** 977 ** Description read multiple 978 ** 979 ** Returns None. 980 *********************************************************************************/ 981 void bta_gattc_read_multi(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 982 { 983 UINT16 i, handle; 984 tBTA_GATT_STATUS status = BTA_GATT_OK; 985 tGATT_READ_PARAM read_param; 986 tBTA_GATTC_OP_CMPL op_cmpl; 987 tBTA_GATTC_ATTR_ID *p_id; 988 989 if (bta_gattc_enqueue(p_clcb, p_data)) 990 { 991 memset(&read_param, 0, sizeof(tGATT_READ_PARAM)); 992 993 p_id = p_data->api_read_multi.p_id_list; 994 995 for (i = 0; i < p_data->api_read_multi.num_attr && p_id; i ++, p_id ++) 996 { 997 handle = 0; 998 999 if (p_id->id_type == BTA_GATT_TYPE_CHAR) 1000 { 1001 handle = bta_gattc_id2handle(p_clcb->p_srcb, 1002 &p_id->id_value.char_id.srvc_id, 1003 &p_id->id_value.char_id.char_id, 1004 NULL); 1005 } 1006 else if (p_id->id_type == BTA_GATT_TYPE_CHAR_DESCR) 1007 { 1008 handle = bta_gattc_id2handle(p_clcb->p_srcb, 1009 &p_id->id_value.char_descr_id.char_id.srvc_id, 1010 &p_id->id_value.char_descr_id.char_id.char_id, 1011 &p_id->id_value.char_descr_id.descr_id); 1012 } 1013 else 1014 { 1015 APPL_TRACE_ERROR1("invalud ID type: %d", p_id->id_type); 1016 } 1017 1018 if (handle == 0) 1019 { 1020 status = BTA_GATT_ERROR; 1021 break; 1022 } 1023 } 1024 if (status == BTA_GATT_OK) 1025 { 1026 read_param.read_multiple.num_handles = p_data->api_read_multi.num_attr; 1027 read_param.read_multiple.auth_req = p_data->api_read_multi.auth_req; 1028 1029 status = GATTC_Read(p_clcb->bta_conn_id, GATT_READ_MULTIPLE, &read_param); 1030 } 1031 1032 /* read fail */ 1033 if (status != BTA_GATT_OK) 1034 { 1035 memset(&op_cmpl, 0, sizeof(tBTA_GATTC_OP_CMPL)); 1036 1037 op_cmpl.status = status; 1038 op_cmpl.op_code = GATTC_OPTYPE_READ; 1039 op_cmpl.p_cmpl = NULL; 1040 1041 bta_gattc_sm_execute(p_clcb, BTA_GATTC_OP_CMPL_EVT, (tBTA_GATTC_DATA *)&op_cmpl); 1042 } 1043 } 1044 } 1045 /******************************************************************************* 1046 ** 1047 ** Function bta_gattc_write 1048 ** 1049 ** Description Write an attribute 1050 ** 1051 ** Returns None. 1052 ** 1053 *******************************************************************************/ 1054 void bta_gattc_write(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1055 { 1056 UINT16 handle = 0; 1057 tGATT_VALUE attr = {0}; 1058 tBTA_GATTC_OP_CMPL op_cmpl; 1059 tBTA_GATT_STATUS status = BTA_GATT_OK; 1060 1061 if (bta_gattc_enqueue(p_clcb, p_data)) 1062 { 1063 if ((handle = bta_gattc_id2handle(p_clcb->p_srcb, 1064 &p_data->api_write.srvc_id, 1065 &p_data->api_write.char_id, 1066 p_data->api_write.p_descr_type)) == 0) 1067 { 1068 status = BTA_GATT_ERROR; 1069 } 1070 else 1071 { 1072 attr.handle= handle; 1073 attr.offset = p_data->api_write.offset; 1074 attr.len = p_data->api_write.len; 1075 attr.auth_req = p_data->api_write.auth_req; 1076 1077 if (p_data->api_write.p_value) 1078 memcpy(attr.value, p_data->api_write.p_value, p_data->api_write.len); 1079 1080 status = GATTC_Write(p_clcb->bta_conn_id, p_data->api_write.write_type, &attr); 1081 } 1082 1083 /* write fail */ 1084 if (status != BTA_GATT_OK) 1085 { 1086 memset(&op_cmpl, 0, sizeof(tBTA_GATTC_OP_CMPL)); 1087 1088 op_cmpl.status = status; 1089 op_cmpl.op_code = GATTC_OPTYPE_WRITE; 1090 op_cmpl.p_cmpl = NULL; 1091 1092 bta_gattc_sm_execute(p_clcb, BTA_GATTC_OP_CMPL_EVT, (tBTA_GATTC_DATA *)&op_cmpl); 1093 } 1094 } 1095 } 1096 /******************************************************************************* 1097 ** 1098 ** Function bta_gattc_execute 1099 ** 1100 ** Description send execute write 1101 ** 1102 ** Returns None. 1103 *********************************************************************************/ 1104 void bta_gattc_execute(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1105 { 1106 tBTA_GATTC_OP_CMPL op_cmpl; 1107 tBTA_GATT_STATUS status; 1108 1109 if (bta_gattc_enqueue(p_clcb, p_data)) 1110 { 1111 status = GATTC_ExecuteWrite(p_clcb->bta_conn_id, p_data->api_exec.is_execute); 1112 1113 if (status != BTA_GATT_OK) 1114 { 1115 memset(&op_cmpl, 0, sizeof(tBTA_GATTC_OP_CMPL)); 1116 1117 op_cmpl.status = status; 1118 op_cmpl.op_code = GATTC_OPTYPE_EXE_WRITE; 1119 op_cmpl.p_cmpl = NULL; 1120 1121 bta_gattc_sm_execute(p_clcb, BTA_GATTC_OP_CMPL_EVT, (tBTA_GATTC_DATA *)&op_cmpl); 1122 } 1123 } 1124 } 1125 /******************************************************************************* 1126 ** 1127 ** Function bta_gattc_confirm 1128 ** 1129 ** Description send handle value confirmation 1130 ** 1131 ** Returns None. 1132 ** 1133 *******************************************************************************/ 1134 void bta_gattc_confirm(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1135 { 1136 UINT16 handle; 1137 1138 if ((handle = bta_gattc_id2handle(p_clcb->p_srcb, 1139 &p_data->api_confirm.srvc_id, 1140 &p_data->api_confirm.char_id, 1141 NULL)) == 0) 1142 { 1143 APPL_TRACE_ERROR0("Can not map service/char ID into valid handle"); 1144 } 1145 else 1146 { 1147 if (GATTC_SendHandleValueConfirm(p_data->api_confirm.hdr.layer_specific, handle) 1148 != GATT_SUCCESS) 1149 { 1150 APPL_TRACE_ERROR1("bta_gattc_confirm to handle [0x%04x] failed", handle); 1151 } 1152 /* if over BR_EDR, inform PM for mode change */ 1153 else if (!BTM_IsBleLink(p_clcb->bda)) 1154 { 1155 bta_sys_busy(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda); 1156 bta_sys_idle(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda); 1157 } 1158 } 1159 } 1160 /******************************************************************************* 1161 ** 1162 ** Function bta_gattc_read_cmpl 1163 ** 1164 ** Description read complete 1165 ** 1166 ** Returns None. 1167 ** 1168 *******************************************************************************/ 1169 void bta_gattc_read_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_OP_CMPL *p_data) 1170 { 1171 UINT8 event; 1172 tBTA_GATTC cb_data; 1173 tBTA_GATT_READ_VAL read_value; 1174 1175 memset(&cb_data, 0, sizeof(tBTA_GATTC)); 1176 memset(&read_value, 0, sizeof(tBTA_GATT_READ_VAL)); 1177 1178 cb_data.read.status = p_data->status; 1179 1180 if (p_data->p_cmpl != NULL && p_data->status == BTA_GATT_OK) 1181 { 1182 if (bta_gattc_handle2id(p_clcb->p_srcb, 1183 p_data->p_cmpl->att_value.handle, 1184 &cb_data.read.srvc_id, 1185 &cb_data.read.char_id, 1186 &cb_data.read.descr_type) == FALSE) 1187 { 1188 cb_data.read.status = BTA_GATT_INTERNAL_ERROR; 1189 APPL_TRACE_ERROR1("can not map to GATT ID. handle = 0x%04x", p_data->p_cmpl->att_value.handle); 1190 } 1191 else 1192 { 1193 cb_data.read.status = bta_gattc_pack_read_cb_data(p_clcb->p_srcb, 1194 &cb_data.read.descr_type.uuid, 1195 &p_data->p_cmpl->att_value, 1196 &read_value); 1197 cb_data.read.p_value = &read_value; 1198 } 1199 } 1200 else 1201 { 1202 cb_data.read.srvc_id = p_clcb->p_q_cmd->api_read.srvc_id; 1203 cb_data.read.char_id = p_clcb->p_q_cmd->api_read.char_id; 1204 if (p_clcb->p_q_cmd->api_read.p_descr_type) 1205 memcpy(&cb_data.read.descr_type, p_clcb->p_q_cmd->api_read.p_descr_type, sizeof(tBTA_GATT_ID)); 1206 } 1207 1208 event = (p_clcb->p_q_cmd->api_read.p_descr_type == NULL) ? BTA_GATTC_READ_CHAR_EVT: BTA_GATTC_READ_DESCR_EVT; 1209 cb_data.read.conn_id = p_clcb->bta_conn_id; 1210 1211 utl_freebuf((void **)&p_clcb->p_q_cmd); 1212 /* read complete, callback */ 1213 ( *p_clcb->p_rcb->p_cback)(event, (tBTA_GATTC *)&cb_data); 1214 1215 } 1216 /******************************************************************************* 1217 ** 1218 ** Function bta_gattc_write_cmpl 1219 ** 1220 ** Description read complete 1221 ** 1222 ** Returns None. 1223 ** 1224 *******************************************************************************/ 1225 void bta_gattc_write_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_OP_CMPL *p_data) 1226 { 1227 tBTA_GATTC cb_data = {0}; 1228 UINT8 event; 1229 1230 memset(&cb_data, 0, sizeof(tBTA_GATTC)); 1231 1232 cb_data.write.status = p_data->status; 1233 1234 if (p_data->p_cmpl != NULL) 1235 { 1236 bta_gattc_handle2id(p_clcb->p_srcb, p_data->p_cmpl->handle, 1237 &cb_data.write.srvc_id, &cb_data.write.char_id, 1238 &cb_data.write.descr_type); 1239 } 1240 else 1241 { 1242 memcpy(&cb_data.write.srvc_id, &p_clcb->p_q_cmd->api_write.srvc_id, sizeof(tBTA_GATT_SRVC_ID)); 1243 memcpy(&cb_data.write.char_id, &p_clcb->p_q_cmd->api_write.char_id, sizeof(tBTA_GATT_ID)); 1244 if (p_clcb->p_q_cmd->api_write.p_descr_type) 1245 memcpy(&cb_data.write.descr_type, p_clcb->p_q_cmd->api_write.p_descr_type, sizeof(tBTA_GATT_ID)); 1246 } 1247 1248 if (p_clcb->p_q_cmd->api_write.hdr.event == BTA_GATTC_API_WRITE_EVT && 1249 p_clcb->p_q_cmd->api_write.write_type == BTA_GATTC_WRITE_PREPARE) 1250 1251 event = BTA_GATTC_PREP_WRITE_EVT; 1252 1253 else if (p_clcb->p_q_cmd->api_write.p_descr_type == NULL) 1254 1255 event = BTA_GATTC_WRITE_CHAR_EVT; 1256 1257 else 1258 event = BTA_GATTC_WRITE_DESCR_EVT; 1259 1260 utl_freebuf((void **)&p_clcb->p_q_cmd); 1261 cb_data.write.conn_id = p_clcb->bta_conn_id; 1262 /* write complete, callback */ 1263 ( *p_clcb->p_rcb->p_cback)(event, (tBTA_GATTC *)&cb_data); 1264 1265 } 1266 /******************************************************************************* 1267 ** 1268 ** Function bta_gattc_exec_cmpl 1269 ** 1270 ** Description execute write complete 1271 ** 1272 ** Returns None. 1273 ** 1274 *******************************************************************************/ 1275 void bta_gattc_exec_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_OP_CMPL *p_data) 1276 { 1277 tBTA_GATTC cb_data; 1278 1279 utl_freebuf((void **)&p_clcb->p_q_cmd); 1280 1281 p_clcb->status = BTA_GATT_OK; 1282 1283 /* execute complete, callback */ 1284 cb_data.exec_cmpl.conn_id = p_clcb->bta_conn_id; 1285 cb_data.exec_cmpl.status = p_data->status; 1286 1287 ( *p_clcb->p_rcb->p_cback)(BTA_GATTC_EXEC_EVT, &cb_data); 1288 1289 } 1290 /******************************************************************************* 1291 ** 1292 ** Function bta_gattc_op_cmpl 1293 ** 1294 ** Description operation completed. 1295 ** 1296 ** Returns None. 1297 ** 1298 *******************************************************************************/ 1299 void bta_gattc_op_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1300 { 1301 UINT8 op = (UINT8)p_data->op_cmpl.op_code; 1302 UINT8 mapped_op = 0; 1303 1304 APPL_TRACE_DEBUG1("bta_gattc_op_cmpl op = %d", op); 1305 1306 if (op == GATTC_OPTYPE_INDICATION || op == GATTC_OPTYPE_NOTIFICATION) 1307 { 1308 APPL_TRACE_ERROR0("unexpected operation, ignored"); 1309 } 1310 else if (op >= GATTC_OPTYPE_READ) 1311 { 1312 if (p_clcb->p_q_cmd == NULL) 1313 { 1314 APPL_TRACE_ERROR0("No pending command"); 1315 return; 1316 } 1317 if (p_clcb->p_q_cmd->hdr.event != bta_gattc_opcode_to_int_evt[op - GATTC_OPTYPE_READ]) 1318 { 1319 mapped_op = p_clcb->p_q_cmd->hdr.event - BTA_GATTC_API_READ_EVT + GATTC_OPTYPE_READ; 1320 if ( mapped_op > GATTC_OPTYPE_INDICATION) mapped_op = 0; 1321 1322 #if (BT_TRACE_VERBOSE == TRUE) 1323 APPL_TRACE_ERROR3("expect op:(%s :0x%04x), receive unexpected operation (%s).", 1324 bta_gattc_op_code_name[mapped_op] , p_clcb->p_q_cmd->hdr.event, 1325 bta_gattc_op_code_name[op]); 1326 #else 1327 APPL_TRACE_ERROR3("expect op:(%u :0x%04x), receive unexpected operation (%u).", 1328 mapped_op , p_clcb->p_q_cmd->hdr.event, op); 1329 #endif 1330 return; 1331 } 1332 1333 /* service handle change void the response, discard it */ 1334 if (p_clcb->auto_update == BTA_GATTC_DISC_WAITING) 1335 { 1336 p_clcb->auto_update = BTA_GATTC_REQ_WAITING; 1337 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL); 1338 } 1339 else if (op == GATTC_OPTYPE_READ) 1340 bta_gattc_read_cmpl(p_clcb, &p_data->op_cmpl); 1341 1342 else if (op == GATTC_OPTYPE_WRITE) 1343 bta_gattc_write_cmpl(p_clcb, &p_data->op_cmpl); 1344 1345 else if (op == GATTC_OPTYPE_EXE_WRITE) 1346 bta_gattc_exec_cmpl(p_clcb, &p_data->op_cmpl); 1347 /* 1348 else if (op == GATTC_OPTYPE_CONFIG) // API to be added 1349 { 1350 } 1351 */ 1352 } 1353 } 1354 /******************************************************************************* 1355 ** 1356 ** Function bta_gattc_op_cmpl 1357 ** 1358 ** Description operation completed. 1359 ** 1360 ** Returns None. 1361 ** 1362 *******************************************************************************/ 1363 void bta_gattc_ignore_op_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1364 { 1365 /* receive op complete when discovery is started, ignore the response, 1366 and wait for discovery finish and resent */ 1367 APPL_TRACE_DEBUG1("bta_gattc_ignore_op_cmpl op = %d", p_data->hdr.layer_specific); 1368 1369 } 1370 /******************************************************************************* 1371 ** 1372 ** Function bta_gattc_search 1373 ** 1374 ** Description start a search in the local server cache 1375 ** 1376 ** Returns None. 1377 ** 1378 *******************************************************************************/ 1379 void bta_gattc_search(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1380 { 1381 tBTA_GATT_STATUS status = GATT_INTERNAL_ERROR; 1382 tBTA_GATTC cb_data; 1383 APPL_TRACE_DEBUG1("bta_gattc_search conn_id=%d",p_clcb->bta_conn_id); 1384 if (p_clcb->p_srcb && p_clcb->p_srcb->p_srvc_cache) 1385 { 1386 status = BTA_GATT_OK; 1387 /* search the local cache of a server device */ 1388 bta_gattc_search_service(p_clcb, p_data->api_search.p_srvc_uuid); 1389 } 1390 cb_data.search_cmpl.status = status; 1391 cb_data.search_cmpl.conn_id = p_clcb->bta_conn_id; 1392 1393 /* end of search or no server cache available */ 1394 ( *p_clcb->p_rcb->p_cback)(BTA_GATTC_SEARCH_CMPL_EVT, &cb_data); 1395 } 1396 /******************************************************************************* 1397 ** 1398 ** Function bta_gattc_q_cmd 1399 ** 1400 ** Description enqueue a command into control block, usually because discovery 1401 ** operation is busy. 1402 ** 1403 ** Returns None. 1404 ** 1405 *******************************************************************************/ 1406 void bta_gattc_q_cmd(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1407 { 1408 bta_gattc_enqueue(p_clcb, p_data); 1409 } 1410 /******************************************************************************* 1411 ** 1412 ** Function bta_gattc_cache_open 1413 ** 1414 ** Description open a NV cache for loading 1415 ** 1416 ** Returns void 1417 ** 1418 *******************************************************************************/ 1419 void bta_gattc_cache_open(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1420 { 1421 bta_gattc_set_discover_st(p_clcb->p_srcb); 1422 1423 APPL_TRACE_DEBUG1("bta_gattc_cache_open conn_id=%d",p_clcb->bta_conn_id); 1424 bta_gattc_co_cache_open(p_clcb->p_srcb->server_bda, BTA_GATTC_CI_CACHE_OPEN_EVT, 1425 p_clcb->bta_conn_id, FALSE); 1426 } 1427 /******************************************************************************* 1428 ** 1429 ** Function bta_gattc_start_load 1430 ** 1431 ** Description start cache loading by sending callout open cache 1432 ** 1433 ** Returns None. 1434 ** 1435 *******************************************************************************/ 1436 void bta_gattc_ci_open(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1437 { 1438 APPL_TRACE_DEBUG2("bta_gattc_ci_open conn_id=%d server state=%d" , 1439 p_clcb->bta_conn_id, p_clcb->p_srcb->state); 1440 if (p_clcb->p_srcb->state == BTA_GATTC_SERV_LOAD) 1441 { 1442 if (p_data->ci_open.status == BTA_GATT_OK) 1443 { 1444 p_clcb->p_srcb->attr_index = 0; 1445 bta_gattc_co_cache_load(p_clcb->p_srcb->server_bda, 1446 BTA_GATTC_CI_CACHE_LOAD_EVT, 1447 p_clcb->p_srcb->attr_index, 1448 p_clcb->bta_conn_id); 1449 } 1450 else 1451 { 1452 p_clcb->p_srcb->state = BTA_GATTC_SERV_DISC; 1453 /* cache open failure, start discovery */ 1454 bta_gattc_start_discover(p_clcb, NULL); 1455 } 1456 } 1457 if (p_clcb->p_srcb->state == BTA_GATTC_SERV_SAVE) 1458 { 1459 if (p_data->ci_open.status == BTA_GATT_OK) 1460 { 1461 if (!bta_gattc_cache_save(p_clcb->p_srcb, p_clcb->bta_conn_id)) 1462 { 1463 p_data->ci_open.status = BTA_GATT_ERROR; 1464 } 1465 } 1466 if (p_data->ci_open.status != BTA_GATT_OK) 1467 { 1468 p_clcb->p_srcb->attr_index = 0; 1469 bta_gattc_co_cache_close(p_clcb->p_srcb->server_bda, p_clcb->bta_conn_id); 1470 bta_gattc_reset_discover_st(p_clcb->p_srcb, p_clcb->status); 1471 1472 } 1473 } 1474 } 1475 /******************************************************************************* 1476 ** 1477 ** Function bta_gattc_ci_load 1478 ** 1479 ** Description cache loading received. 1480 ** 1481 ** Returns None. 1482 ** 1483 *******************************************************************************/ 1484 void bta_gattc_ci_load(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1485 { 1486 1487 APPL_TRACE_DEBUG2("bta_gattc_ci_load conn_id=%d load status=%d" , 1488 p_clcb->bta_conn_id, p_data->ci_load.status ); 1489 bta_gattc_co_cache_close(p_clcb->p_srcb->server_bda, 0); 1490 1491 if ((p_data->ci_load.status == BTA_GATT_OK || 1492 p_data->ci_load.status == BTA_GATT_MORE) && 1493 p_data->ci_load.num_attr > 0) 1494 { 1495 bta_gattc_rebuild_cache(p_clcb->p_srcb, p_data->ci_load.num_attr, p_data->ci_load.attr, p_clcb->p_srcb->attr_index); 1496 1497 if (p_data->ci_load.status == BTA_GATT_OK) 1498 { 1499 p_clcb->p_srcb->attr_index = 0; 1500 bta_gattc_reset_discover_st(p_clcb->p_srcb, BTA_GATT_OK); 1501 1502 } 1503 else /* load more */ 1504 { 1505 p_clcb->p_srcb->attr_index += p_data->ci_load.num_attr; 1506 1507 bta_gattc_co_cache_load(p_clcb->p_srcb->server_bda, 1508 BTA_GATTC_CI_CACHE_LOAD_EVT, 1509 p_clcb->p_srcb->attr_index, 1510 p_clcb->bta_conn_id); 1511 } 1512 } 1513 else 1514 { 1515 p_clcb->p_srcb->state = BTA_GATTC_SERV_DISC; 1516 p_clcb->p_srcb->attr_index = 0; 1517 /* cache load failure, start discovery */ 1518 bta_gattc_start_discover(p_clcb, NULL); 1519 } 1520 } 1521 /******************************************************************************* 1522 ** 1523 ** Function bta_gattc_ci_load 1524 ** 1525 ** Description cache loading received. 1526 ** 1527 ** Returns None. 1528 ** 1529 *******************************************************************************/ 1530 void bta_gattc_ci_save(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1531 { 1532 APPL_TRACE_DEBUG1("bta_gattc_ci_save conn_id=%d " , 1533 p_clcb->bta_conn_id ); 1534 1535 if (!bta_gattc_cache_save(p_clcb->p_srcb, p_clcb->bta_conn_id)) 1536 { 1537 p_clcb->p_srcb->attr_index = 0; 1538 bta_gattc_co_cache_close(p_clcb->p_srcb->server_bda, 0); 1539 bta_gattc_reset_discover_st(p_clcb->p_srcb, p_clcb->status); 1540 } 1541 } 1542 /******************************************************************************* 1543 ** 1544 ** Function bta_gattc_fail 1545 ** 1546 ** Description report API call failure back to apps 1547 ** 1548 ** Returns None. 1549 ** 1550 *******************************************************************************/ 1551 void bta_gattc_fail(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data) 1552 { 1553 if (p_clcb->status == BTA_GATT_OK) 1554 { 1555 APPL_TRACE_ERROR1("operation not supported at current state [%d]", p_clcb->state); 1556 } 1557 } 1558 1559 /******************************************************************************* 1560 ** 1561 ** Function bta_gattc_deregister_cmpl 1562 ** 1563 ** Description De-Register a GATT client application with BTA completed. 1564 ** 1565 ** Returns void 1566 ** 1567 *******************************************************************************/ 1568 static void bta_gattc_deregister_cmpl(tBTA_GATTC_RCB *p_clreg) 1569 { 1570 tBTA_GATTC_CB *p_cb = &bta_gattc_cb; 1571 tBTA_GATTC_IF client_if = p_clreg->client_if; 1572 tBTA_GATTC cb_data; 1573 tBTA_GATTC_CBACK *p_cback = p_clreg->p_cback; 1574 1575 memset(&cb_data, 0, sizeof(tBTA_GATTC)); 1576 1577 GATT_Deregister(p_clreg->client_if); 1578 memset(p_clreg, 0, sizeof(tBTA_GATTC_RCB)); 1579 1580 cb_data.reg_oper.client_if = client_if; 1581 cb_data.reg_oper.status = BTA_GATT_OK; 1582 1583 if (p_cback) 1584 /* callback with de-register event */ 1585 (*p_cback)(BTA_GATTC_DEREG_EVT, (tBTA_GATTC *)&cb_data); 1586 1587 if (bta_gattc_num_reg_app() == 0 && p_cb->state == BTA_GATTC_STATE_DISABLING) 1588 { 1589 p_cb->state = BTA_GATTC_STATE_DISABLED; 1590 } 1591 } 1592 /******************************************************************************* 1593 ** 1594 ** Function bta_gattc_conn_cback 1595 ** bta_gattc_cmpl_cback 1596 ** 1597 ** Description callback functions to GATT client stack. 1598 ** 1599 ** Returns void 1600 ** 1601 *******************************************************************************/ 1602 static void bta_gattc_conn_cback(tGATT_IF gattc_if, BD_ADDR bda, UINT16 conn_id, 1603 BOOLEAN connected, tGATT_DISCONN_REASON reason) 1604 { 1605 tBTA_GATTC_DATA *p_buf; 1606 1607 APPL_TRACE_DEBUG4("bta_gattc_conn_cback: cif = %d connected = %d conn_id = %d reaosn = 0x%04x", 1608 gattc_if, connected, conn_id, reason); 1609 1610 if ((p_buf = (tBTA_GATTC_DATA *) GKI_getbuf(sizeof(tBTA_GATTC_DATA))) != NULL) 1611 { 1612 memset(p_buf, 0, sizeof(tBTA_GATTC_DATA)); 1613 1614 p_buf->int_conn.hdr.event = connected ? BTA_GATTC_INT_CONN_EVT: BTA_GATTC_INT_DISCONN_EVT; 1615 p_buf->int_conn.hdr.layer_specific = conn_id; 1616 p_buf->int_conn.client_if = gattc_if; 1617 p_buf->int_conn.role = L2CA_GetBleConnRole(bda); 1618 p_buf->int_conn.reason = reason; 1619 bdcpy(p_buf->int_conn.remote_bda, bda); 1620 1621 bta_sys_sendmsg(p_buf); 1622 } 1623 } 1624 1625 /******************************************************************************* 1626 ** 1627 ** Function bta_gattc_process_api_refresh 1628 ** 1629 ** Description process refresh API to delete cache and start a new discovery 1630 ** if currently connected. 1631 ** 1632 ** Returns None. 1633 ** 1634 *******************************************************************************/ 1635 void bta_gattc_process_api_refresh(tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA * p_msg) 1636 { 1637 tBTA_GATTC_SERV *p_srvc_cb = bta_gattc_find_srvr_cache(p_msg->api_conn.remote_bda); 1638 tBTA_GATTC_CLCB *p_clcb = &bta_gattc_cb.clcb[0]; 1639 BOOLEAN found = FALSE; 1640 UINT8 i; 1641 1642 if (p_srvc_cb != NULL) 1643 { 1644 /* try to find a CLCB */ 1645 if (p_srvc_cb->connected && p_srvc_cb->num_clcb != 0) 1646 { 1647 for (i = 0; i < BTA_GATTC_CLCB_MAX; i ++, p_clcb ++) 1648 { 1649 if (p_clcb->in_use && p_clcb->p_srcb == p_srvc_cb) 1650 { 1651 found = TRUE; 1652 break; 1653 } 1654 } 1655 if (found) 1656 { 1657 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL); 1658 return; 1659 } 1660 } 1661 /* in all other cases, mark it and delete the cache */ 1662 if (p_srvc_cb->p_srvc_cache != NULL) 1663 { 1664 while (p_srvc_cb->cache_buffer.p_first) 1665 GKI_freebuf (GKI_dequeue (&p_srvc_cb->cache_buffer)); 1666 1667 p_srvc_cb->p_srvc_cache = NULL; 1668 } 1669 } 1670 /* used to reset cache in application */ 1671 bta_gattc_co_cache_reset(p_msg->api_conn.remote_bda); 1672 1673 } 1674 /******************************************************************************* 1675 ** 1676 ** Function bta_gattc_process_srvc_chg_ind 1677 ** 1678 ** Description process service change indication. 1679 ** 1680 ** Returns None. 1681 ** 1682 *******************************************************************************/ 1683 BOOLEAN bta_gattc_process_srvc_chg_ind(UINT16 conn_id, 1684 tBTA_GATTC_RCB *p_clrcb, 1685 tBTA_GATTC_SERV *p_srcb, 1686 tBTA_GATTC_CLCB *p_clcb, 1687 tBTA_GATTC_NOTIFY *p_notify, 1688 UINT16 handle) 1689 { 1690 tBT_UUID gattp_uuid, srvc_chg_uuid; 1691 BOOLEAN processed = FALSE; 1692 UINT8 i; 1693 1694 gattp_uuid.len = 2; 1695 gattp_uuid.uu.uuid16 = UUID_SERVCLASS_GATT_SERVER; 1696 1697 srvc_chg_uuid.len = 2; 1698 srvc_chg_uuid.uu.uuid16 = GATT_UUID_GATT_SRV_CHGD; 1699 1700 if (bta_gattc_uuid_compare(&p_notify->char_id.srvc_id.id.uuid, &gattp_uuid, TRUE) && 1701 bta_gattc_uuid_compare(&p_notify->char_id.char_id.uuid, &srvc_chg_uuid, TRUE)) 1702 { 1703 processed = TRUE; 1704 /* mark service handle change pending */ 1705 p_srcb->srvc_hdl_chg = TRUE; 1706 /* clear up all notification/indication registration */ 1707 bta_gattc_clear_notif_registration(conn_id); 1708 /* service change indication all received, do discovery update */ 1709 if ( ++ p_srcb->update_count == bta_gattc_num_reg_app()) 1710 { 1711 /* not an opened connection; or connection busy */ 1712 /* search for first available clcb and start discovery */ 1713 if (p_clcb == NULL || (p_clcb && p_clcb->p_q_cmd != NULL)) 1714 { 1715 for (i = 0 ; i < BTA_GATTC_CLCB_MAX; i ++) 1716 { 1717 if (bta_gattc_cb.clcb[i].in_use && 1718 bta_gattc_cb.clcb[i].p_srcb == p_srcb && 1719 bta_gattc_cb.clcb[i].p_q_cmd == NULL) 1720 { 1721 p_clcb = &bta_gattc_cb.clcb[i]; 1722 break; 1723 } 1724 } 1725 } 1726 /* send confirmation here if this is an indication, it should always be */ 1727 GATTC_SendHandleValueConfirm(conn_id, handle); 1728 1729 /* if connection available, refresh cache by doing discovery now */ 1730 if (p_clcb != NULL) 1731 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL); 1732 } 1733 /* notify applicationf or service change */ 1734 if (p_clrcb->p_cback != NULL) 1735 { 1736 (* p_clrcb->p_cback)(BTA_GATTC_SRVC_CHG_EVT, (tBTA_GATTC *)p_srcb->server_bda); 1737 } 1738 1739 } 1740 1741 return processed; 1742 1743 } 1744 /******************************************************************************* 1745 ** 1746 ** Function bta_gattc_proc_other_indication 1747 ** 1748 ** Description process all non-service change indication/notification. 1749 ** 1750 ** Returns None. 1751 ** 1752 *******************************************************************************/ 1753 void bta_gattc_proc_other_indication(tBTA_GATTC_CLCB *p_clcb, UINT8 op, 1754 tGATT_CL_COMPLETE *p_data, 1755 tBTA_GATTC_NOTIFY *p_notify) 1756 { 1757 APPL_TRACE_DEBUG2("bta_gattc_proc_other_indication check \ 1758 p_data->att_value.handle=%d p_data->handle=%d", 1759 p_data->att_value.handle, p_data->handle); 1760 APPL_TRACE_DEBUG1("is_notify", p_notify->is_notify); 1761 1762 p_notify->is_notify = (op == GATTC_OPTYPE_INDICATION) ? FALSE : TRUE; 1763 p_notify->len = p_data->att_value.len; 1764 bdcpy(p_notify->bda, p_clcb->bda); 1765 memcpy(p_notify->value, p_data->att_value.value, p_data->att_value.len); 1766 p_notify->conn_id = p_clcb->bta_conn_id; 1767 1768 if (p_clcb->p_rcb->p_cback) 1769 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_NOTIF_EVT, (tBTA_GATTC *)p_notify); 1770 1771 } 1772 /******************************************************************************* 1773 ** 1774 ** Function bta_gattc_process_indicate 1775 ** 1776 ** Description process indication/notification. 1777 ** 1778 ** Returns None. 1779 ** 1780 *******************************************************************************/ 1781 void bta_gattc_process_indicate(UINT16 conn_id, tGATTC_OPTYPE op, tGATT_CL_COMPLETE *p_data) 1782 { 1783 UINT16 handle = p_data->att_value.handle; 1784 tBTA_GATTC_CLCB *p_clcb ; 1785 tBTA_GATTC_RCB *p_clrcb = NULL; 1786 tBTA_GATTC_SERV *p_srcb = NULL; 1787 tBTA_GATTC_NOTIFY notify; 1788 BD_ADDR remote_bda; 1789 tBTA_GATTC_IF gatt_if; 1790 1791 if (!GATT_GetConnectionInfor(conn_id, &gatt_if, remote_bda)) 1792 { 1793 APPL_TRACE_ERROR0("indication/notif for unknown app"); 1794 return; 1795 } 1796 1797 if ((p_clrcb = bta_gattc_cl_get_regcb(gatt_if)) == NULL) 1798 { 1799 APPL_TRACE_ERROR0("indication/notif for unregistered app"); 1800 return; 1801 } 1802 1803 if ((p_srcb = bta_gattc_find_srcb(remote_bda)) == NULL) 1804 { 1805 APPL_TRACE_ERROR0("indication/notif for unknown device, ignore"); 1806 return; 1807 } 1808 1809 p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id); 1810 1811 if (bta_gattc_handle2id(p_srcb, handle, 1812 ¬ify.char_id.srvc_id, 1813 ¬ify.char_id.char_id, 1814 ¬ify.descr_type)) 1815 { 1816 /* if non-service change indication/notification, forward to application */ 1817 if (!bta_gattc_process_srvc_chg_ind(conn_id, p_clrcb, p_srcb, p_clcb, ¬ify, handle)) 1818 { 1819 /* if app registered for the notification */ 1820 if (bta_gattc_check_notif_registry(p_clrcb, p_srcb, ¬ify)) 1821 { 1822 /* connection not open yet */ 1823 if (p_clcb == NULL) 1824 { 1825 if ((p_clcb = bta_gattc_clcb_alloc(gatt_if, remote_bda)) != NULL) 1826 { 1827 p_clcb->bta_conn_id = conn_id; 1828 1829 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CONN_EVT, NULL); 1830 } 1831 else 1832 { 1833 APPL_TRACE_ERROR0("No resources"); 1834 } 1835 } 1836 1837 if (p_clcb != NULL) 1838 bta_gattc_proc_other_indication(p_clcb, op, p_data, ¬ify); 1839 } 1840 /* no one intersted and need ack? */ 1841 else if (op == GATTC_OPTYPE_INDICATION) 1842 { 1843 APPL_TRACE_DEBUG0("no one interested, ack now"); 1844 GATTC_SendHandleValueConfirm(conn_id, handle); 1845 } 1846 } 1847 } 1848 else 1849 { 1850 APPL_TRACE_ERROR1("Indi/Notif for Unknown handle[0x%04x], can not find in local cache.", handle); 1851 } 1852 } 1853 /******************************************************************************* 1854 ** 1855 ** Function bta_gattc_cmpl_cback 1856 ** 1857 ** Description client operation complete callback register with BTE GATT. 1858 ** 1859 ** Returns None. 1860 ** 1861 *******************************************************************************/ 1862 static void bta_gattc_cmpl_cback(UINT16 conn_id, tGATTC_OPTYPE op, tGATT_STATUS status, 1863 tGATT_CL_COMPLETE *p_data) 1864 { 1865 tBTA_GATTC_CLCB *p_clcb ; 1866 tBTA_GATTC_OP_CMPL *p_buf; 1867 UINT16 len = sizeof(tBTA_GATTC_OP_CMPL) + sizeof(tGATT_CL_COMPLETE); 1868 1869 APPL_TRACE_DEBUG3("bta_gattc_cmpl_cback: conn_id = %d op = %d status = %d", 1870 conn_id, op, status); 1871 1872 /* notification and indication processed right away */ 1873 if (op == GATTC_OPTYPE_NOTIFICATION || op == GATTC_OPTYPE_INDICATION) 1874 { 1875 bta_gattc_process_indicate(conn_id, op, p_data); 1876 return; 1877 } 1878 /* for all other operation, not expected if w/o connection */ 1879 else if ((p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id)) == NULL) 1880 { 1881 APPL_TRACE_ERROR1("bta_gattc_cmpl_cback unknown conn_id = %d, ignore data", conn_id); 1882 return; 1883 } 1884 1885 1886 /* if over BR_EDR, inform PM for mode change */ 1887 if (!BTM_IsBleLink(p_clcb->bda)) 1888 { 1889 bta_sys_busy(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda); 1890 bta_sys_idle(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda); 1891 } 1892 1893 if ((p_buf = (tBTA_GATTC_OP_CMPL *) GKI_getbuf(len)) != NULL) 1894 { 1895 memset(p_buf, 0, len); 1896 p_buf->hdr.event = BTA_GATTC_OP_CMPL_EVT; 1897 p_buf->hdr.layer_specific = conn_id; 1898 p_buf->status = status; 1899 p_buf->op_code = op; 1900 1901 if (p_data != NULL) 1902 { 1903 p_buf->p_cmpl = (tGATT_CL_COMPLETE *)(p_buf + 1); 1904 memcpy(p_buf->p_cmpl, p_data, sizeof(tGATT_CL_COMPLETE)); 1905 } 1906 1907 bta_sys_sendmsg(p_buf); 1908 } 1909 1910 return; 1911 } 1912 #if BLE_INCLUDED == TRUE 1913 /******************************************************************************* 1914 ** 1915 ** Function bta_gattc_init_clcb_conn 1916 ** 1917 ** Description Initaite a BTA CLCB connection 1918 ** 1919 ** Returns void 1920 ** 1921 ********************************************************************************/ 1922 void bta_gattc_init_clcb_conn(UINT8 cif, BD_ADDR remote_bda) 1923 { 1924 tBTA_GATTC_CLCB *p_clcb = NULL; 1925 tBTA_GATTC_DATA gattc_data; 1926 UINT16 conn_id; 1927 1928 /* should always get the connection ID */ 1929 if (GATT_GetConnIdIfConnected(cif, remote_bda,&conn_id) == FALSE) 1930 { 1931 APPL_TRACE_ERROR0("bta_gattc_init_clcb_conn ERROR: not a connected device"); 1932 return; 1933 } 1934 1935 /* initaite a new connection here */ 1936 if ((p_clcb = bta_gattc_clcb_alloc(cif, remote_bda)) != NULL) 1937 { 1938 gattc_data.hdr.layer_specific = p_clcb->bta_conn_id = conn_id; 1939 1940 gattc_data.api_conn.client_if = cif; 1941 memcpy(gattc_data.api_conn.remote_bda, remote_bda, BD_ADDR_LEN); 1942 gattc_data.api_conn.is_direct = TRUE; 1943 1944 bta_gattc_sm_execute(p_clcb, BTA_GATTC_API_OPEN_EVT, &gattc_data); 1945 } 1946 else 1947 { 1948 APPL_TRACE_ERROR0("No resources"); 1949 } 1950 } 1951 /******************************************************************************* 1952 ** 1953 ** Function bta_gattc_process_listen_all 1954 ** 1955 ** Description process listen all, send open callback to application for all 1956 ** connected slave LE link. 1957 ** 1958 ** Returns void 1959 ** 1960 ********************************************************************************/ 1961 void bta_gattc_process_listen_all(UINT8 cif) 1962 { 1963 UINT8 i_conn = 0; 1964 tBTA_GATTC_CONN *p_conn = &bta_gattc_cb.conn_track[0]; 1965 1966 for (i_conn = 0; i_conn < BTA_GATTC_CONN_MAX; i_conn++, p_conn ++) 1967 { 1968 if (p_conn->in_use ) 1969 { 1970 if (bta_gattc_find_clcb_by_cif(cif, p_conn->remote_bda) == NULL) 1971 { 1972 bta_gattc_init_clcb_conn(cif, p_conn->remote_bda); 1973 } 1974 /* else already connected */ 1975 } 1976 } 1977 } 1978 /******************************************************************************* 1979 ** 1980 ** Function bta_gattc_listen 1981 ** 1982 ** Description Start or stop a listen for connection 1983 ** 1984 ** Returns void 1985 ** 1986 ********************************************************************************/ 1987 void bta_gattc_listen(tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA * p_msg) 1988 { 1989 tBTA_GATTC_RCB *p_clreg = bta_gattc_cl_get_regcb(p_msg->api_listen.client_if); 1990 tBTA_GATTC cb_data; 1991 cb_data.reg_oper.status = BTA_GATT_ERROR; 1992 cb_data.reg_oper.client_if = p_msg->api_listen.client_if; 1993 1994 if (p_clreg == NULL) 1995 { 1996 APPL_TRACE_ERROR1("bta_gattc_listen failed, unknown client_if: %d", 1997 p_msg->api_listen.client_if); 1998 return; 1999 } 2000 /* mark bg conn record */ 2001 if (bta_gattc_mark_bg_conn(p_msg->api_listen.client_if, 2002 (BD_ADDR_PTR) p_msg->api_listen.remote_bda, 2003 p_msg->api_listen.start, 2004 TRUE)) 2005 { 2006 if (!GATT_Listen(p_msg->api_listen.client_if, 2007 p_msg->api_listen.start, 2008 p_msg->api_listen.remote_bda)) 2009 { 2010 APPL_TRACE_ERROR0("Listen failure"); 2011 (*p_clreg->p_cback)(BTA_GATTC_LISTEN_EVT, &cb_data); 2012 } 2013 else 2014 { 2015 cb_data.status = BTA_GATT_OK; 2016 2017 (*p_clreg->p_cback)(BTA_GATTC_LISTEN_EVT, &cb_data); 2018 2019 if (p_msg->api_listen.start) 2020 { 2021 /* if listen to a specific target */ 2022 if (p_msg->api_listen.remote_bda != NULL) 2023 { 2024 2025 /* if is a connected remote device */ 2026 if (L2CA_GetBleConnRole(p_msg->api_listen.remote_bda) == HCI_ROLE_SLAVE && 2027 bta_gattc_find_clcb_by_cif(p_msg->api_listen.client_if, p_msg->api_listen.remote_bda) == NULL) 2028 { 2029 2030 bta_gattc_init_clcb_conn(p_msg->api_listen.client_if, 2031 p_msg->api_listen.remote_bda); 2032 } 2033 } 2034 /* if listen to all */ 2035 else 2036 { 2037 APPL_TRACE_ERROR0("Listen For All now"); 2038 /* go through all connected device and send callback for all connected slave connection */ 2039 bta_gattc_process_listen_all(p_msg->api_listen.client_if); 2040 } 2041 } 2042 } 2043 } 2044 } 2045 #endif 2046 #endif 2047