1 /******************************************************************************
3 * Copyright (C) 2003-2012 Broadcom Corporation
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:
9 * http://www.apache.org/licenses/LICENSE-2.0
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.
17 ******************************************************************************/
19 /******************************************************************************
21 * This file contains the GATT client action functions for the state
24 ******************************************************************************/
25 #define LOG_TAG "bt_bta_gattc"
27 #include "bt_target.h"
33 #include "bta_gattc_int.h"
36 #if (defined BTA_HH_LE_INCLUDED && BTA_HH_LE_INCLUDED == TRUE)
37 #include "bta_hh_int.h"
40 #include "btif/include/btif_debug_conn.h"
44 #include "osi/include/log.h"
46 #if BTA_GATT_INCLUDED && BLE_INCLUDED == TRUE
48 /*****************************************************************************
50 *****************************************************************************/
51 static void bta_gattc_conn_cback(tGATT_IF gattc_if, BD_ADDR bda, UINT16 conn_id,
52 BOOLEAN connected, tGATT_DISCONN_REASON reason,
53 tBT_TRANSPORT transport);
55 static void bta_gattc_cmpl_cback(UINT16 conn_id, tGATTC_OPTYPE op, tGATT_STATUS status,
56 tGATT_CL_COMPLETE *p_data);
58 static void bta_gattc_deregister_cmpl(tBTA_GATTC_RCB *p_clreg);
59 static void bta_gattc_enc_cmpl_cback(tGATT_IF gattc_if, BD_ADDR bda);
60 static void bta_gattc_cong_cback (UINT16 conn_id, BOOLEAN congested);
62 static tGATT_CBACK bta_gattc_cl_cback =
66 bta_gattc_disc_res_cback,
67 bta_gattc_disc_cmpl_cback,
69 bta_gattc_enc_cmpl_cback,
73 /* opcode(tGATTC_OPTYPE) order has to be comply with internal event order */
74 static UINT16 bta_gattc_opcode_to_int_evt[] =
76 BTA_GATTC_API_READ_EVT,
77 BTA_GATTC_API_WRITE_EVT,
78 BTA_GATTC_API_EXEC_EVT,
79 BTA_GATTC_API_CFG_MTU_EVT
82 #if (BT_TRACE_VERBOSE == TRUE)
83 static const char *bta_gattc_op_code_name[] =
95 /*****************************************************************************
97 *****************************************************************************/
99 /*******************************************************************************
101 ** Function bta_gattc_enable
103 ** Description Enables GATTC module
108 *******************************************************************************/
109 static void bta_gattc_enable(tBTA_GATTC_CB *p_cb)
111 APPL_TRACE_DEBUG("bta_gattc_enable");
113 if (p_cb->state == BTA_GATTC_STATE_DISABLED)
115 /* initialize control block */
116 memset(&bta_gattc_cb, 0, sizeof(tBTA_GATTC_CB));
117 p_cb->state = BTA_GATTC_STATE_ENABLED;
121 APPL_TRACE_DEBUG("GATTC is arelady enabled");
126 /*******************************************************************************
128 ** Function bta_gattc_disable
130 ** Description Disable GATTC module by cleaning up all active connections
131 ** and deregister all application.
135 *******************************************************************************/
136 void bta_gattc_disable(tBTA_GATTC_CB *p_cb)
140 APPL_TRACE_DEBUG("bta_gattc_disable");
142 if (p_cb->state != BTA_GATTC_STATE_ENABLED)
144 APPL_TRACE_ERROR("not enabled or disable in pogress");
148 for (i = 0; i <BTA_GATTC_CL_MAX; i ++)
150 if (p_cb->cl_rcb[i].in_use)
152 p_cb->state = BTA_GATTC_STATE_DISABLING;
153 /* don't deregister HH GATT IF */
154 /* HH GATT IF will be deregistered by bta_hh_le_deregister when disable HH */
155 #if (defined BTA_HH_LE_INCLUDED && BTA_HH_LE_INCLUDED == TRUE)
156 if (!bta_hh_le_is_hh_gatt_if(p_cb->cl_rcb[i].client_if)) {
158 bta_gattc_deregister(p_cb, &p_cb->cl_rcb[i]);
159 #if (defined BTA_HH_LE_INCLUDED && BTA_HH_LE_INCLUDED == TRUE)
165 /* no registered apps, indicate disable completed */
166 if (p_cb->state != BTA_GATTC_STATE_DISABLING)
168 p_cb->state = BTA_GATTC_STATE_DISABLED;
169 memset(p_cb, 0, sizeof(tBTA_GATTC_CB));
173 /*******************************************************************************
175 ** Function bta_gattc_register
177 ** Description Register a GATT client application with BTA.
181 *******************************************************************************/
182 void bta_gattc_register(tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA *p_data)
186 tBT_UUID *p_app_uuid = &p_data->api_reg.app_uuid;
187 tBTA_GATTC_INT_START_IF *p_buf;
188 tBTA_GATT_STATUS status = BTA_GATT_NO_RESOURCES;
191 APPL_TRACE_DEBUG("bta_gattc_register state %d",p_cb->state);
192 memset(&cb_data, 0, sizeof(cb_data));
193 cb_data.reg_oper.status = BTA_GATT_NO_RESOURCES;
195 /* check if GATTC module is already enabled . Else enable */
196 if (p_cb->state == BTA_GATTC_STATE_DISABLED)
198 bta_gattc_enable (p_cb);
200 /* todo need to check duplicate uuid */
201 for (i = 0; i < BTA_GATTC_CL_MAX; i ++)
203 if (!p_cb->cl_rcb[i].in_use)
205 if ((p_app_uuid == NULL) || (p_cb->cl_rcb[i].client_if = GATT_Register(p_app_uuid, &bta_gattc_cl_cback)) == 0)
207 APPL_TRACE_ERROR("Register with GATT stack failed.");
208 status = BTA_GATT_ERROR;
212 p_cb->cl_rcb[i].in_use = TRUE;
213 p_cb->cl_rcb[i].p_cback = p_data->api_reg.p_cback;
214 memcpy(&p_cb->cl_rcb[i].app_uuid, p_app_uuid, sizeof(tBT_UUID));
216 /* BTA use the same client interface as BTE GATT statck */
217 cb_data.reg_oper.client_if = p_cb->cl_rcb[i].client_if;
219 if ((p_buf = (tBTA_GATTC_INT_START_IF *) GKI_getbuf(sizeof(tBTA_GATTC_INT_START_IF))) != NULL)
221 p_buf->hdr.event = BTA_GATTC_INT_START_IF_EVT;
222 p_buf->client_if = p_cb->cl_rcb[i].client_if;
224 bta_sys_sendmsg(p_buf);
225 status = BTA_GATT_OK;
229 GATT_Deregister(p_cb->cl_rcb[i].client_if);
231 status = BTA_GATT_NO_RESOURCES;
232 memset( &p_cb->cl_rcb[i], 0 , sizeof(tBTA_GATTC_RCB));
239 /* callback with register event */
240 if (p_data->api_reg.p_cback)
242 if (p_app_uuid != NULL)
243 memcpy(&(cb_data.reg_oper.app_uuid),p_app_uuid,sizeof(tBT_UUID));
245 cb_data.reg_oper.status = status;
246 (*p_data->api_reg.p_cback)(BTA_GATTC_REG_EVT, (tBTA_GATTC *)&cb_data);
249 /*******************************************************************************
251 ** Function bta_gattc_start_if
253 ** Description start an application interface.
257 *******************************************************************************/
258 void bta_gattc_start_if(tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA *p_msg)
262 if (bta_gattc_cl_get_regcb(p_msg->int_start_if.client_if) !=NULL )
264 GATT_StartIf(p_msg->int_start_if.client_if);
268 APPL_TRACE_ERROR("Unable to start app.: Unknown interface =%d",p_msg->int_start_if.client_if );
271 /*******************************************************************************
273 ** Function bta_gattc_deregister
275 ** Description De-Register a GATT client application with BTA.
279 *******************************************************************************/
280 void bta_gattc_deregister(tBTA_GATTC_CB *p_cb, tBTA_GATTC_RCB *p_clreg)
287 /* remove bg connection associated with this rcb */
288 for (i = 0; i < BTA_GATTC_KNOWN_SR_MAX; i ++)
290 if (p_cb->bg_track[i].in_use)
292 if (p_cb->bg_track[i].cif_mask & (1 <<(p_clreg->client_if - 1)))
294 bta_gattc_mark_bg_conn(p_clreg->client_if, p_cb->bg_track[i].remote_bda, FALSE, FALSE);
295 GATT_CancelConnect(p_clreg->client_if, p_cb->bg_track[i].remote_bda, FALSE);
297 if (p_cb->bg_track[i].cif_adv_mask & (1 <<(p_clreg->client_if - 1)))
299 bta_gattc_mark_bg_conn(p_clreg->client_if, p_cb->bg_track[i].remote_bda, FALSE, TRUE);
304 if (p_clreg->num_clcb > 0)
306 /* close all CLCB related to this app */
307 for (i= 0; i < BTA_GATTC_CLCB_MAX; i ++)
309 if (p_cb->clcb[i].in_use && (p_cb->clcb[i].p_rcb == p_clreg))
311 p_clreg->dereg_pending = TRUE;
313 buf.event = BTA_GATTC_API_CLOSE_EVT;
314 buf.layer_specific = p_cb->clcb[i].bta_conn_id;
315 bta_gattc_close(&p_cb->clcb[i], (tBTA_GATTC_DATA *)&buf) ;
320 bta_gattc_deregister_cmpl(p_clreg);
324 APPL_TRACE_ERROR("bta_gattc_deregister Deregister Failedm unknown client cif");
327 /*******************************************************************************
329 ** Function bta_gattc_process_api_open
331 ** Description process connect API request.
335 *******************************************************************************/
336 void bta_gattc_process_api_open (tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA * p_msg)
338 UINT16 event = ((BT_HDR *)p_msg)->event;
339 tBTA_GATTC_CLCB *p_clcb = NULL;
340 tBTA_GATTC_RCB *p_clreg = bta_gattc_cl_get_regcb(p_msg->api_conn.client_if);
345 if (p_msg->api_conn.is_direct)
347 if ((p_clcb = bta_gattc_find_alloc_clcb(p_msg->api_conn.client_if,
348 p_msg->api_conn.remote_bda,
349 p_msg->api_conn.transport)) != NULL)
351 bta_gattc_sm_execute(p_clcb, event, p_msg);
355 APPL_TRACE_ERROR("No resources to open a new connection.");
357 bta_gattc_send_open_cback(p_clreg,
358 BTA_GATT_NO_RESOURCES,
359 p_msg->api_conn.remote_bda,
360 BTA_GATT_INVALID_CONN_ID,
361 p_msg->api_conn.transport, 0);
366 bta_gattc_init_bk_conn(&p_msg->api_conn, p_clreg);
371 APPL_TRACE_ERROR("bta_gattc_process_api_open Failed, unknown client_if: %d",
372 p_msg->api_conn.client_if);
375 /*******************************************************************************
377 ** Function bta_gattc_process_api_open_cancel
379 ** Description process connect API request.
383 *******************************************************************************/
384 void bta_gattc_process_api_open_cancel (tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA * p_msg)
386 UINT16 event = ((BT_HDR *)p_msg)->event;
387 tBTA_GATTC_CLCB *p_clcb = NULL;
388 tBTA_GATTC_RCB *p_clreg;
392 if (p_msg->api_cancel_conn.is_direct)
394 if ((p_clcb = bta_gattc_find_clcb_by_cif(p_msg->api_cancel_conn.client_if,
395 p_msg->api_cancel_conn.remote_bda,
396 BTA_GATT_TRANSPORT_LE)) != NULL)
398 bta_gattc_sm_execute(p_clcb, event, p_msg);
402 APPL_TRACE_ERROR("No such connection need to be cancelled");
404 p_clreg = bta_gattc_cl_get_regcb(p_msg->api_cancel_conn.client_if);
406 if (p_clreg && p_clreg->p_cback)
408 cb_data.status = BTA_GATT_ERROR;
409 (*p_clreg->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data);
415 bta_gattc_cancel_bk_conn(&p_msg->api_cancel_conn);
420 /*******************************************************************************
422 ** Function bta_gattc_process_enc_cmpl
424 ** Description process encryption complete message.
428 *******************************************************************************/
429 void bta_gattc_process_enc_cmpl(tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA *p_msg)
431 tBTA_GATTC_RCB *p_clreg;
435 p_clreg = bta_gattc_cl_get_regcb(p_msg->enc_cmpl.client_if);
437 if (p_clreg && p_clreg->p_cback)
439 memset(&cb_data, 0, sizeof(tBTA_GATTC));
441 cb_data.enc_cmpl.client_if = p_msg->enc_cmpl.client_if;
442 bdcpy(cb_data.enc_cmpl.remote_bda, p_msg->enc_cmpl.remote_bda);
444 (*p_clreg->p_cback)(BTA_GATTC_ENC_CMPL_CB_EVT, &cb_data);
448 /*******************************************************************************
450 ** Function bta_gattc_cancel_open_error
456 *******************************************************************************/
457 void bta_gattc_cancel_open_error(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
462 cb_data.status=BTA_GATT_ERROR;
464 if ( p_clcb && p_clcb->p_rcb && p_clcb->p_rcb->p_cback )
465 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data);
468 /*******************************************************************************
470 ** Function bta_gattc_open_error
476 *******************************************************************************/
477 void bta_gattc_open_error(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
481 APPL_TRACE_ERROR("Connection already opened. wrong state");
483 bta_gattc_send_open_cback(p_clcb->p_rcb,
490 /*******************************************************************************
492 ** Function bta_gattc_open_fail
498 *******************************************************************************/
499 void bta_gattc_open_fail(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
503 bta_gattc_send_open_cback(p_clcb->p_rcb,
509 /* open failure, remove clcb */
510 bta_gattc_clcb_dealloc(p_clcb);
513 /*******************************************************************************
515 ** Function bta_gattc_open
517 ** Description Process API connection function.
521 *******************************************************************************/
522 void bta_gattc_open(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
524 tBTA_GATTC_DATA gattc_data;
526 /* open/hold a connection */
527 if (!GATT_Connect(p_clcb->p_rcb->client_if, p_data->api_conn.remote_bda,
528 TRUE, p_data->api_conn.transport))
530 APPL_TRACE_ERROR("Connection open failure");
532 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_OPEN_FAIL_EVT, p_data);
536 /* a connected remote device */
537 if (GATT_GetConnIdIfConnected(p_clcb->p_rcb->client_if,
538 p_data->api_conn.remote_bda,
539 &p_clcb->bta_conn_id,
540 p_data->api_conn.transport))
542 gattc_data.int_conn.hdr.layer_specific = p_clcb->bta_conn_id;
544 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CONN_EVT, &gattc_data);
546 /* else wait for the callback event */
549 /*******************************************************************************
551 ** Function bta_gattc_init_bk_conn
553 ** Description Process API Open for a background connection
557 *******************************************************************************/
558 void bta_gattc_init_bk_conn(tBTA_GATTC_API_OPEN *p_data, tBTA_GATTC_RCB *p_clreg)
560 tBTA_GATT_STATUS status = BTA_GATT_NO_RESOURCES;
562 tBTA_GATTC_CLCB *p_clcb;
563 tBTA_GATTC_DATA gattc_data;
565 if (bta_gattc_mark_bg_conn(p_data->client_if, p_data->remote_bda, TRUE, FALSE))
567 /* always call open to hold a connection */
568 if (!GATT_Connect(p_data->client_if, p_data->remote_bda, FALSE, p_data->transport))
570 uint8_t *bda = (uint8_t *)p_data->remote_bda;
571 status = BTA_GATT_ERROR;
572 APPL_TRACE_ERROR("%s unable to connect to remote bd_addr:%02x:%02x:%02x:%02x:%02x:%02x",
573 __func__, bda[0], bda[1], bda[2], bda[3], bda[4], bda[5]);
578 status = BTA_GATT_OK;
580 /* if is a connected remote device */
581 if (GATT_GetConnIdIfConnected(p_data->client_if,
586 if ((p_clcb = bta_gattc_find_alloc_clcb(p_data->client_if, p_data->remote_bda,
587 BTA_GATT_TRANSPORT_LE)) != NULL)
589 gattc_data.hdr.layer_specific = p_clcb->bta_conn_id = conn_id;
591 /* open connection */
592 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CONN_EVT, &gattc_data);
593 status = BTA_GATT_OK;
599 /* open failure, report OPEN_EVT */
600 if (status != BTA_GATT_OK)
602 bta_gattc_send_open_cback(p_clreg, status, p_data->remote_bda,
603 BTA_GATT_INVALID_CONN_ID, BTA_GATT_TRANSPORT_LE, 0);
606 /*******************************************************************************
608 ** Function bta_gattc_cancel_bk_conn
610 ** Description Process API Cancel Open for a background connection
614 *******************************************************************************/
615 void bta_gattc_cancel_bk_conn(tBTA_GATTC_API_CANCEL_OPEN *p_data)
617 tBTA_GATTC_RCB *p_clreg;
619 cb_data.status = BTA_GATT_ERROR;
621 /* remove the device from the bg connection mask */
622 if (bta_gattc_mark_bg_conn(p_data->client_if, p_data->remote_bda, FALSE, FALSE))
624 if (GATT_CancelConnect(p_data->client_if, p_data->remote_bda, FALSE))
626 cb_data.status = BTA_GATT_OK;
630 APPL_TRACE_ERROR("bta_gattc_cancel_bk_conn failed");
633 p_clreg = bta_gattc_cl_get_regcb(p_data->client_if);
635 if (p_clreg && p_clreg->p_cback)
637 (*p_clreg->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data);
641 /*******************************************************************************
643 ** Function bta_gattc_int_cancel_open_ok
649 *******************************************************************************/
650 void bta_gattc_cancel_open_ok(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
655 if ( p_clcb->p_rcb->p_cback )
657 cb_data.status = BTA_GATT_OK;
658 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data);
661 bta_gattc_clcb_dealloc(p_clcb);
663 /*******************************************************************************
665 ** Function bta_gattc_cancel_open
671 *******************************************************************************/
672 void bta_gattc_cancel_open(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
676 if (GATT_CancelConnect(p_clcb->p_rcb->client_if, p_data->api_cancel_conn.remote_bda, TRUE))
678 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CANCEL_OPEN_OK_EVT, p_data);
682 if ( p_clcb->p_rcb->p_cback )
684 cb_data.status = BTA_GATT_ERROR;
685 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CANCEL_OPEN_EVT, &cb_data);
689 /*******************************************************************************
691 ** Function bta_gattc_conn
693 ** Description receive connection callback from stack
697 *******************************************************************************/
698 void bta_gattc_conn(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
700 tBTA_GATTC_IF gatt_if;
701 APPL_TRACE_DEBUG("bta_gattc_conn server cache state=%d",p_clcb->p_srcb->state);
705 APPL_TRACE_DEBUG("bta_gattc_conn conn_id=%d",p_data->hdr.layer_specific);
706 p_clcb->bta_conn_id = p_data->int_conn.hdr.layer_specific;
708 GATT_GetConnectionInfor(p_data->hdr.layer_specific,
709 &gatt_if, p_clcb->bda, &p_clcb->transport);
712 p_clcb->p_srcb->connected = TRUE;
714 if (p_clcb->p_srcb->mtu == 0)
715 p_clcb->p_srcb->mtu = GATT_DEF_BLE_MTU_SIZE;
717 /* start database cache if needed */
718 if (p_clcb->p_srcb->p_srvc_cache == NULL ||
719 p_clcb->p_srcb->state != BTA_GATTC_SERV_IDLE)
721 if (p_clcb->p_srcb->state == BTA_GATTC_SERV_IDLE)
723 p_clcb->p_srcb->state = BTA_GATTC_SERV_LOAD;
724 bta_gattc_sm_execute(p_clcb, BTA_GATTC_START_CACHE_EVT, NULL);
726 else /* cache is building */
727 p_clcb->state = BTA_GATTC_DISCOVER_ST;
732 /* a pending service handle change indication */
733 if (p_clcb->p_srcb->srvc_hdl_chg)
735 p_clcb->p_srcb->srvc_hdl_chg = FALSE;
736 /* start discovery */
737 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL);
743 /* there is no RM for GATT */
744 if (p_clcb->transport == BTA_TRANSPORT_BR_EDR)
745 bta_sys_conn_open(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda);
747 bta_gattc_send_open_cback(p_clcb->p_rcb,
752 p_clcb->p_srcb->mtu);
755 /*******************************************************************************
757 ** Function bta_gattc_close_fail
759 ** Description close a connection.
763 *******************************************************************************/
764 void bta_gattc_close_fail(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
768 if ( p_clcb->p_rcb->p_cback )
770 memset(&cb_data, 0, sizeof(tBTA_GATTC));
771 cb_data.close.client_if = p_clcb->p_rcb->client_if;
772 cb_data.close.conn_id = p_data->hdr.layer_specific;
773 bdcpy(cb_data.close.remote_bda, p_clcb->bda);
774 cb_data.close.status = BTA_GATT_ERROR;
775 cb_data.close.reason = BTA_GATT_CONN_NONE;
778 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CLOSE_EVT, &cb_data);
781 /*******************************************************************************
783 ** Function bta_gattc_api_close
785 ** Description close a GATTC connection.
789 *******************************************************************************/
790 void bta_gattc_close(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
792 tBTA_GATTC_CBACK *p_cback = p_clcb->p_rcb->p_cback;
793 tBTA_GATTC_RCB *p_clreg = p_clcb->p_rcb;
796 APPL_TRACE_DEBUG("bta_gattc_close conn_id=%d",p_clcb->bta_conn_id);
798 cb_data.close.client_if = p_clcb->p_rcb->client_if;
799 cb_data.close.conn_id = p_clcb->bta_conn_id;
800 cb_data.close.reason = p_clcb->reason;
801 cb_data.close.status = p_clcb->status;
802 bdcpy(cb_data.close.remote_bda, p_clcb->bda);
804 if (p_clcb->transport == BTA_TRANSPORT_BR_EDR)
805 bta_sys_conn_close( BTA_ID_GATTC ,BTA_ALL_APP_ID, p_clcb->bda);
807 bta_gattc_clcb_dealloc(p_clcb);
809 if (p_data->hdr.event == BTA_GATTC_API_CLOSE_EVT)
811 cb_data.close.status = GATT_Disconnect(p_data->hdr.layer_specific);
813 else if (p_data->hdr.event == BTA_GATTC_INT_DISCONN_EVT)
815 cb_data.close.status = p_data->int_conn.reason;
816 cb_data.close.reason = p_data->int_conn.reason;
820 (* p_cback)(BTA_GATTC_CLOSE_EVT, (tBTA_GATTC *)&cb_data);
822 if (p_clreg->num_clcb == 0 && p_clreg->dereg_pending)
824 bta_gattc_deregister_cmpl(p_clreg);
827 /*******************************************************************************
829 ** Function bta_gattc_reset_discover_st
831 ** Description when a SRCB finished discovery, tell all related clcb.
835 *******************************************************************************/
836 void bta_gattc_reset_discover_st(tBTA_GATTC_SERV *p_srcb, tBTA_GATT_STATUS status)
838 tBTA_GATTC_CB *p_cb = &bta_gattc_cb;
841 for (i = 0; i < BTA_GATTC_CLCB_MAX; i ++)
843 if (p_cb->clcb[i].p_srcb == p_srcb)
845 p_cb->clcb[i].status = status;
846 bta_gattc_sm_execute(&p_cb->clcb[i], BTA_GATTC_DISCOVER_CMPL_EVT, NULL);
850 /*******************************************************************************
852 ** Function bta_gattc_disc_close
854 ** Description close a GATTC connection while in discovery state.
858 *******************************************************************************/
859 void bta_gattc_disc_close(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
861 APPL_TRACE_DEBUG("%s: Discovery cancel conn_id=%d", __func__,
862 p_clcb->bta_conn_id);
864 if (p_clcb->disc_active)
865 bta_gattc_reset_discover_st(p_clcb->p_srcb, BTA_GATT_ERROR);
867 p_clcb->state = BTA_GATTC_CONN_ST;
869 // This function only gets called as the result of a BTA_GATTC_API_CLOSE_EVT
870 // while in the BTA_GATTC_DISCOVER_ST state. Once the state changes, the
871 // connection itself still needs to be closed to resolve the original event.
872 if (p_clcb->state == BTA_GATTC_CONN_ST)
874 APPL_TRACE_DEBUG("State is back to BTA_GATTC_CONN_ST. "
875 "Trigger connection close");
876 bta_gattc_close(p_clcb, p_data);
879 /*******************************************************************************
881 ** Function bta_gattc_set_discover_st
883 ** Description when a SRCB start discovery, tell all related clcb and set
888 *******************************************************************************/
889 void bta_gattc_set_discover_st(tBTA_GATTC_SERV *p_srcb)
891 tBTA_GATTC_CB *p_cb = &bta_gattc_cb;
894 #if BLE_INCLUDED == TRUE
895 L2CA_EnableUpdateBleConnParams(p_srcb->server_bda, FALSE);
897 for (i = 0; i < BTA_GATTC_CLCB_MAX; i ++)
899 if (p_cb->clcb[i].p_srcb == p_srcb)
901 p_cb->clcb[i].status = BTA_GATT_OK;
902 p_cb->clcb[i].state = BTA_GATTC_DISCOVER_ST;
906 /*******************************************************************************
908 ** Function bta_gattc_restart_discover
910 ** Description process service change in discovery state, mark up the auto
911 ** update flag and set status to be discovery cancel for current
916 *******************************************************************************/
917 void bta_gattc_restart_discover(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
921 p_clcb->status = BTA_GATT_CANCEL;
922 p_clcb->auto_update = BTA_GATTC_DISC_WAITING;
925 /*******************************************************************************
927 ** Function bta_gattc_cfg_mtu
929 ** Description Configure MTU size on the GATT connection.
933 *******************************************************************************/
934 void bta_gattc_cfg_mtu(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
936 tBTA_GATTC_OP_CMPL op_cmpl;
937 tBTA_GATT_STATUS status;
939 if (bta_gattc_enqueue(p_clcb, p_data))
941 status = GATTC_ConfigureMTU (p_clcb->bta_conn_id, p_data->api_mtu.mtu);
943 /* if failed, return callback here */
944 if (status != GATT_SUCCESS && status != GATT_CMD_STARTED)
946 memset(&op_cmpl, 0, sizeof(tBTA_GATTC_OP_CMPL));
948 op_cmpl.status = status;
949 op_cmpl.op_code = GATTC_OPTYPE_CONFIG;
950 op_cmpl.p_cmpl = NULL;
952 bta_gattc_sm_execute(p_clcb, BTA_GATTC_OP_CMPL_EVT, (tBTA_GATTC_DATA *)&op_cmpl);
956 /*******************************************************************************
958 ** Function bta_gattc_start_discover
960 ** Description Start a discovery on server.
964 *******************************************************************************/
965 void bta_gattc_start_discover(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
969 APPL_TRACE_DEBUG("bta_gattc_start_discover conn_id=%d p_clcb->p_srcb->state = %d ",
970 p_clcb->bta_conn_id, p_clcb->p_srcb->state);
972 if (((p_clcb->p_q_cmd == NULL || p_clcb->auto_update == BTA_GATTC_REQ_WAITING) &&
973 p_clcb->p_srcb->state == BTA_GATTC_SERV_IDLE) ||
974 p_clcb->p_srcb->state == BTA_GATTC_SERV_DISC)
975 /* no pending operation, start discovery right away */
977 p_clcb->auto_update = BTA_GATTC_NO_SCHEDULE;
979 if (p_clcb->p_srcb != NULL)
981 /* clear the service change mask */
982 p_clcb->p_srcb->srvc_hdl_chg = FALSE;
983 p_clcb->p_srcb->update_count = 0;
984 p_clcb->p_srcb->state = BTA_GATTC_SERV_DISC_ACT;
986 if (p_clcb->transport == BTA_TRANSPORT_LE)
987 L2CA_EnableUpdateBleConnParams(p_clcb->p_srcb->server_bda, FALSE);
989 /* set all srcb related clcb into discovery ST */
990 bta_gattc_set_discover_st(p_clcb->p_srcb);
992 if ((p_clcb->status = bta_gattc_init_cache(p_clcb->p_srcb)) == BTA_GATT_OK)
994 p_clcb->status = bta_gattc_discover_pri_service(p_clcb->bta_conn_id,
995 p_clcb->p_srcb, GATT_DISC_SRVC_ALL);
997 if (p_clcb->status != BTA_GATT_OK)
999 APPL_TRACE_ERROR("discovery on server failed");
1000 bta_gattc_reset_discover_st(p_clcb->p_srcb, p_clcb->status);
1003 p_clcb->disc_active = TRUE;
1007 APPL_TRACE_ERROR("unknown device, can not start discovery");
1010 /* pending operation, wait until it finishes */
1013 p_clcb->auto_update = BTA_GATTC_DISC_WAITING;
1015 if (p_clcb->p_srcb->state == BTA_GATTC_SERV_IDLE)
1016 p_clcb->state = BTA_GATTC_CONN_ST; /* set clcb state */
1020 /*******************************************************************************
1022 ** Function bta_gattc_disc_cmpl
1024 ** Description discovery on server is finished
1028 *******************************************************************************/
1029 void bta_gattc_disc_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1031 tBTA_GATTC_DATA *p_q_cmd = p_clcb->p_q_cmd;
1034 APPL_TRACE_DEBUG("bta_gattc_disc_cmpl conn_id=%d",p_clcb->bta_conn_id);
1036 #if BLE_INCLUDED == TRUE
1037 if(p_clcb->transport == BTA_TRANSPORT_LE)
1038 L2CA_EnableUpdateBleConnParams(p_clcb->p_srcb->server_bda, TRUE);
1040 p_clcb->p_srcb->state = BTA_GATTC_SERV_IDLE;
1041 p_clcb->disc_active = FALSE;
1043 if (p_clcb->status != GATT_SUCCESS)
1045 /* clean up cache */
1046 if(p_clcb->p_srcb && p_clcb->p_srcb->p_srvc_cache)
1048 while (!GKI_queue_is_empty(&p_clcb->p_srcb->cache_buffer))
1050 GKI_freebuf (GKI_dequeue (&p_clcb->p_srcb->cache_buffer));
1052 p_clcb->p_srcb->p_srvc_cache = NULL;
1055 /* used to reset cache in application */
1056 bta_gattc_co_cache_reset(p_clcb->p_srcb->server_bda);
1058 /* release pending attribute list buffer */
1059 utl_freebuf((void **)&p_clcb->p_srcb->p_srvc_list);
1061 if (p_clcb->auto_update == BTA_GATTC_DISC_WAITING)
1063 /* start discovery again */
1064 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL);
1066 /* get any queued command to proceed */
1067 else if (p_q_cmd != NULL)
1069 p_clcb->p_q_cmd = NULL;
1071 bta_gattc_sm_execute(p_clcb, p_q_cmd->hdr.event, p_q_cmd);
1072 /* if the command executed requeued the cmd, we don't
1073 * want to free the underlying buffer that's being
1074 * referenced by p_clcb->p_q_cmd
1076 if (p_q_cmd != p_clcb->p_q_cmd) {
1077 utl_freebuf((void **)&p_q_cmd);
1081 /*******************************************************************************
1083 ** Function bta_gattc_read
1085 ** Description Read an attribute
1089 *******************************************************************************/
1090 void bta_gattc_read(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1093 tGATT_READ_PARAM read_param;
1094 tBTA_GATTC_OP_CMPL op_cmpl;
1096 memset (&read_param, 0 ,sizeof(tGATT_READ_PARAM));
1097 memset (&op_cmpl, 0 ,sizeof(tBTA_GATTC_OP_CMPL));
1099 if (bta_gattc_enqueue(p_clcb, p_data))
1101 if ((handle = bta_gattc_id2handle(p_clcb->p_srcb,
1102 &p_data->api_read.srvc_id,
1103 &p_data->api_read.char_id,
1104 p_data->api_read.p_descr_type)) == 0)
1106 op_cmpl.status = BTA_GATT_ERROR;
1110 read_param.by_handle.handle = handle;
1111 read_param.by_handle.auth_req = p_data->api_read.auth_req;
1113 op_cmpl.status = GATTC_Read(p_clcb->bta_conn_id, GATT_READ_BY_HANDLE, &read_param);
1117 if (op_cmpl.status != BTA_GATT_OK)
1119 op_cmpl.op_code = GATTC_OPTYPE_READ;
1120 op_cmpl.p_cmpl = NULL;
1122 bta_gattc_sm_execute(p_clcb, BTA_GATTC_OP_CMPL_EVT, (tBTA_GATTC_DATA *)&op_cmpl);
1126 /*******************************************************************************
1128 ** Function bta_gattc_read_multi
1130 ** Description read multiple
1133 *********************************************************************************/
1134 void bta_gattc_read_multi(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1137 tBTA_GATT_STATUS status = BTA_GATT_OK;
1138 tGATT_READ_PARAM read_param;
1139 tBTA_GATTC_OP_CMPL op_cmpl;
1140 tBTA_GATTC_ATTR_ID *p_id;
1142 if (bta_gattc_enqueue(p_clcb, p_data))
1144 memset(&read_param, 0, sizeof(tGATT_READ_PARAM));
1146 p_id = p_data->api_read_multi.p_id_list;
1148 for (i = 0; i < p_data->api_read_multi.num_attr && p_id; i ++, p_id ++)
1152 if (p_id->id_type == BTA_GATT_TYPE_CHAR)
1154 handle = bta_gattc_id2handle(p_clcb->p_srcb,
1155 &p_id->id_value.char_id.srvc_id,
1156 &p_id->id_value.char_id.char_id,
1159 else if (p_id->id_type == BTA_GATT_TYPE_CHAR_DESCR)
1161 handle = bta_gattc_id2handle(p_clcb->p_srcb,
1162 &p_id->id_value.char_descr_id.char_id.srvc_id,
1163 &p_id->id_value.char_descr_id.char_id.char_id,
1164 &p_id->id_value.char_descr_id.descr_id);
1168 APPL_TRACE_ERROR("invalud ID type: %d", p_id->id_type);
1173 status = BTA_GATT_ERROR;
1177 if (status == BTA_GATT_OK)
1179 read_param.read_multiple.num_handles = p_data->api_read_multi.num_attr;
1180 read_param.read_multiple.auth_req = p_data->api_read_multi.auth_req;
1182 status = GATTC_Read(p_clcb->bta_conn_id, GATT_READ_MULTIPLE, &read_param);
1186 if (status != BTA_GATT_OK)
1188 memset(&op_cmpl, 0, sizeof(tBTA_GATTC_OP_CMPL));
1190 op_cmpl.status = status;
1191 op_cmpl.op_code = GATTC_OPTYPE_READ;
1192 op_cmpl.p_cmpl = NULL;
1194 bta_gattc_sm_execute(p_clcb, BTA_GATTC_OP_CMPL_EVT, (tBTA_GATTC_DATA *)&op_cmpl);
1198 /*******************************************************************************
1200 ** Function bta_gattc_write
1202 ** Description Write an attribute
1206 *******************************************************************************/
1207 void bta_gattc_write(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1210 tGATT_VALUE attr = {0};
1211 tBTA_GATTC_OP_CMPL op_cmpl;
1212 tBTA_GATT_STATUS status = BTA_GATT_OK;
1214 if (bta_gattc_enqueue(p_clcb, p_data))
1216 if ((handle = bta_gattc_id2handle(p_clcb->p_srcb,
1217 &p_data->api_write.srvc_id,
1218 &p_data->api_write.char_id,
1219 p_data->api_write.p_descr_type)) == 0)
1221 status = BTA_GATT_ERROR;
1225 attr.handle= handle;
1226 attr.offset = p_data->api_write.offset;
1227 attr.len = p_data->api_write.len;
1228 attr.auth_req = p_data->api_write.auth_req;
1230 if (p_data->api_write.p_value)
1231 memcpy(attr.value, p_data->api_write.p_value, p_data->api_write.len);
1233 status = GATTC_Write(p_clcb->bta_conn_id, p_data->api_write.write_type, &attr);
1237 if (status != BTA_GATT_OK)
1239 memset(&op_cmpl, 0, sizeof(tBTA_GATTC_OP_CMPL));
1241 op_cmpl.status = status;
1242 op_cmpl.op_code = GATTC_OPTYPE_WRITE;
1243 op_cmpl.p_cmpl = NULL;
1245 bta_gattc_sm_execute(p_clcb, BTA_GATTC_OP_CMPL_EVT, (tBTA_GATTC_DATA *)&op_cmpl);
1249 /*******************************************************************************
1251 ** Function bta_gattc_execute
1253 ** Description send execute write
1256 *********************************************************************************/
1257 void bta_gattc_execute(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1259 tBTA_GATTC_OP_CMPL op_cmpl;
1260 tBTA_GATT_STATUS status;
1262 if (bta_gattc_enqueue(p_clcb, p_data))
1264 status = GATTC_ExecuteWrite(p_clcb->bta_conn_id, p_data->api_exec.is_execute);
1266 if (status != BTA_GATT_OK)
1268 memset(&op_cmpl, 0, sizeof(tBTA_GATTC_OP_CMPL));
1270 op_cmpl.status = status;
1271 op_cmpl.op_code = GATTC_OPTYPE_EXE_WRITE;
1272 op_cmpl.p_cmpl = NULL;
1274 bta_gattc_sm_execute(p_clcb, BTA_GATTC_OP_CMPL_EVT, (tBTA_GATTC_DATA *)&op_cmpl);
1278 /*******************************************************************************
1280 ** Function bta_gattc_confirm
1282 ** Description send handle value confirmation
1286 *******************************************************************************/
1287 void bta_gattc_confirm(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1291 if ((handle = bta_gattc_id2handle(p_clcb->p_srcb,
1292 &p_data->api_confirm.srvc_id,
1293 &p_data->api_confirm.char_id,
1296 APPL_TRACE_ERROR("Can not map service/char ID into valid handle");
1300 if (GATTC_SendHandleValueConfirm(p_data->api_confirm.hdr.layer_specific, handle)
1303 APPL_TRACE_ERROR("bta_gattc_confirm to handle [0x%04x] failed", handle);
1307 /* if over BR_EDR, inform PM for mode change */
1308 if (p_clcb->transport == BTA_TRANSPORT_BR_EDR)
1310 bta_sys_busy(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda);
1311 bta_sys_idle(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda);
1316 /*******************************************************************************
1318 ** Function bta_gattc_read_cmpl
1320 ** Description read complete
1324 *******************************************************************************/
1325 void bta_gattc_read_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_OP_CMPL *p_data)
1329 tBTA_GATT_READ_VAL read_value;
1331 memset(&cb_data, 0, sizeof(tBTA_GATTC));
1332 memset(&read_value, 0, sizeof(tBTA_GATT_READ_VAL));
1334 cb_data.read.status = p_data->status;
1336 if (p_data->p_cmpl != NULL && p_data->status == BTA_GATT_OK)
1338 if (bta_gattc_handle2id(p_clcb->p_srcb,
1339 p_data->p_cmpl->att_value.handle,
1340 &cb_data.read.srvc_id,
1341 &cb_data.read.char_id,
1342 &cb_data.read.descr_type) == FALSE)
1344 cb_data.read.status = BTA_GATT_INTERNAL_ERROR;
1345 APPL_TRACE_ERROR("can not map to GATT ID. handle = 0x%04x",
1346 p_data->p_cmpl->att_value.handle);
1350 cb_data.read.status = bta_gattc_pack_read_cb_data(p_clcb->p_srcb,
1351 &cb_data.read.descr_type.uuid,
1352 &p_data->p_cmpl->att_value,
1354 cb_data.read.p_value = &read_value;
1359 cb_data.read.srvc_id = p_clcb->p_q_cmd->api_read.srvc_id;
1360 cb_data.read.char_id = p_clcb->p_q_cmd->api_read.char_id;
1361 if (p_clcb->p_q_cmd->api_read.p_descr_type)
1362 memcpy(&cb_data.read.descr_type, p_clcb->p_q_cmd->api_read.p_descr_type,
1363 sizeof(tBTA_GATT_ID));
1366 event = (p_clcb->p_q_cmd->api_read.p_descr_type == NULL) ?
1367 BTA_GATTC_READ_CHAR_EVT: BTA_GATTC_READ_DESCR_EVT;
1368 cb_data.read.conn_id = p_clcb->bta_conn_id;
1370 utl_freebuf((void **)&p_clcb->p_q_cmd);
1371 /* read complete, callback */
1372 ( *p_clcb->p_rcb->p_cback)(event, (tBTA_GATTC *)&cb_data);
1375 /*******************************************************************************
1377 ** Function bta_gattc_write_cmpl
1379 ** Description write complete
1383 *******************************************************************************/
1384 void bta_gattc_write_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_OP_CMPL *p_data)
1386 tBTA_GATTC cb_data = {0};
1389 memset(&cb_data, 0, sizeof(tBTA_GATTC));
1391 cb_data.write.status = p_data->status;
1393 if (p_data->p_cmpl != NULL)
1395 bta_gattc_handle2id(p_clcb->p_srcb, p_data->p_cmpl->att_value.handle,
1396 &cb_data.write.srvc_id, &cb_data.write.char_id,
1397 &cb_data.write.descr_type);
1401 memcpy(&cb_data.write.srvc_id, &p_clcb->p_q_cmd->api_write.srvc_id,
1402 sizeof(tBTA_GATT_SRVC_ID));
1403 memcpy(&cb_data.write.char_id, &p_clcb->p_q_cmd->api_write.char_id,
1404 sizeof(tBTA_GATT_ID));
1405 if (p_clcb->p_q_cmd->api_write.p_descr_type)
1406 memcpy(&cb_data.write.descr_type, p_clcb->p_q_cmd->api_write.p_descr_type,
1407 sizeof(tBTA_GATT_ID));
1410 if (p_clcb->p_q_cmd->api_write.hdr.event == BTA_GATTC_API_WRITE_EVT &&
1411 p_clcb->p_q_cmd->api_write.write_type == BTA_GATTC_WRITE_PREPARE)
1413 event = BTA_GATTC_PREP_WRITE_EVT;
1415 else if (p_clcb->p_q_cmd->api_write.p_descr_type == NULL)
1417 event = BTA_GATTC_WRITE_CHAR_EVT;
1420 event = BTA_GATTC_WRITE_DESCR_EVT;
1422 utl_freebuf((void **)&p_clcb->p_q_cmd);
1423 cb_data.write.conn_id = p_clcb->bta_conn_id;
1424 /* write complete, callback */
1425 ( *p_clcb->p_rcb->p_cback)(event, (tBTA_GATTC *)&cb_data);
1428 /*******************************************************************************
1430 ** Function bta_gattc_exec_cmpl
1432 ** Description execute write complete
1436 *******************************************************************************/
1437 void bta_gattc_exec_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_OP_CMPL *p_data)
1441 utl_freebuf((void **)&p_clcb->p_q_cmd);
1443 p_clcb->status = BTA_GATT_OK;
1445 /* execute complete, callback */
1446 cb_data.exec_cmpl.conn_id = p_clcb->bta_conn_id;
1447 cb_data.exec_cmpl.status = p_data->status;
1449 ( *p_clcb->p_rcb->p_cback)(BTA_GATTC_EXEC_EVT, &cb_data);
1453 /*******************************************************************************
1455 ** Function bta_gattc_cfg_mtu_cmpl
1457 ** Description configure MTU operation complete
1461 *******************************************************************************/
1462 void bta_gattc_cfg_mtu_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_OP_CMPL *p_data)
1466 utl_freebuf((void **)&p_clcb->p_q_cmd);
1469 if (p_data->p_cmpl && p_data->status == BTA_GATT_OK)
1470 p_clcb->p_srcb->mtu = p_data->p_cmpl->mtu;
1472 /* configure MTU complete, callback */
1473 p_clcb->status = p_data->status;
1474 cb_data.cfg_mtu.conn_id = p_clcb->bta_conn_id;
1475 cb_data.cfg_mtu.status = p_data->status;
1476 cb_data.cfg_mtu.mtu = p_clcb->p_srcb->mtu;
1478 (*p_clcb->p_rcb->p_cback) (BTA_GATTC_CFG_MTU_EVT, &cb_data);
1481 /*******************************************************************************
1483 ** Function bta_gattc_op_cmpl
1485 ** Description operation completed.
1489 *******************************************************************************/
1490 void bta_gattc_op_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1492 UINT8 op = (UINT8)p_data->op_cmpl.op_code;
1493 UINT8 mapped_op = 0;
1495 APPL_TRACE_DEBUG("bta_gattc_op_cmpl op = %d", op);
1497 if (op == GATTC_OPTYPE_INDICATION || op == GATTC_OPTYPE_NOTIFICATION)
1499 APPL_TRACE_ERROR("unexpected operation, ignored");
1501 else if (op >= GATTC_OPTYPE_READ)
1503 if (p_clcb->p_q_cmd == NULL)
1505 APPL_TRACE_ERROR("No pending command");
1508 if (p_clcb->p_q_cmd->hdr.event != bta_gattc_opcode_to_int_evt[op - GATTC_OPTYPE_READ])
1510 mapped_op = p_clcb->p_q_cmd->hdr.event - BTA_GATTC_API_READ_EVT + GATTC_OPTYPE_READ;
1511 if ( mapped_op > GATTC_OPTYPE_INDICATION) mapped_op = 0;
1513 #if (BT_TRACE_VERBOSE == TRUE)
1514 APPL_TRACE_ERROR("expect op:(%s :0x%04x), receive unexpected operation (%s).",
1515 bta_gattc_op_code_name[mapped_op] , p_clcb->p_q_cmd->hdr.event,
1516 bta_gattc_op_code_name[op]);
1518 APPL_TRACE_ERROR("expect op:(%u :0x%04x), receive unexpected operation (%u).",
1519 mapped_op , p_clcb->p_q_cmd->hdr.event, op);
1524 /* discard responses if service change indication is received before operation completed */
1525 if (p_clcb->auto_update == BTA_GATTC_DISC_WAITING && p_clcb->p_srcb->srvc_hdl_chg)
1527 APPL_TRACE_DEBUG("Discard all responses when service change indication is received.");
1528 p_data->op_cmpl.status = GATT_ERROR;
1531 /* service handle change void the response, discard it */
1532 if (op == GATTC_OPTYPE_READ)
1533 bta_gattc_read_cmpl(p_clcb, &p_data->op_cmpl);
1535 else if (op == GATTC_OPTYPE_WRITE)
1536 bta_gattc_write_cmpl(p_clcb, &p_data->op_cmpl);
1538 else if (op == GATTC_OPTYPE_EXE_WRITE)
1539 bta_gattc_exec_cmpl(p_clcb, &p_data->op_cmpl);
1541 else if (op == GATTC_OPTYPE_CONFIG)
1542 bta_gattc_cfg_mtu_cmpl(p_clcb, &p_data->op_cmpl);
1544 if (p_clcb->auto_update == BTA_GATTC_DISC_WAITING)
1546 p_clcb->auto_update = BTA_GATTC_REQ_WAITING;
1547 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL);
1551 /*******************************************************************************
1553 ** Function bta_gattc_op_cmpl
1555 ** Description operation completed.
1559 *******************************************************************************/
1560 void bta_gattc_ignore_op_cmpl(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1564 /* receive op complete when discovery is started, ignore the response,
1565 and wait for discovery finish and resent */
1566 APPL_TRACE_DEBUG("bta_gattc_ignore_op_cmpl op = %d", p_data->hdr.layer_specific);
1569 /*******************************************************************************
1571 ** Function bta_gattc_search
1573 ** Description start a search in the local server cache
1577 *******************************************************************************/
1578 void bta_gattc_search(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1580 tBTA_GATT_STATUS status = GATT_INTERNAL_ERROR;
1582 APPL_TRACE_DEBUG("bta_gattc_search conn_id=%d",p_clcb->bta_conn_id);
1583 if (p_clcb->p_srcb && p_clcb->p_srcb->p_srvc_cache)
1585 status = BTA_GATT_OK;
1586 /* search the local cache of a server device */
1587 bta_gattc_search_service(p_clcb, p_data->api_search.p_srvc_uuid);
1589 cb_data.search_cmpl.status = status;
1590 cb_data.search_cmpl.conn_id = p_clcb->bta_conn_id;
1592 /* end of search or no server cache available */
1593 ( *p_clcb->p_rcb->p_cback)(BTA_GATTC_SEARCH_CMPL_EVT, &cb_data);
1595 /*******************************************************************************
1597 ** Function bta_gattc_q_cmd
1599 ** Description enqueue a command into control block, usually because discovery
1600 ** operation is busy.
1604 *******************************************************************************/
1605 void bta_gattc_q_cmd(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1607 bta_gattc_enqueue(p_clcb, p_data);
1609 /*******************************************************************************
1611 ** Function bta_gattc_cache_open
1613 ** Description open a NV cache for loading
1617 *******************************************************************************/
1618 void bta_gattc_cache_open(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1622 bta_gattc_set_discover_st(p_clcb->p_srcb);
1624 APPL_TRACE_DEBUG("bta_gattc_cache_open conn_id=%d",p_clcb->bta_conn_id);
1625 bta_gattc_co_cache_open(p_clcb->p_srcb->server_bda, BTA_GATTC_CI_CACHE_OPEN_EVT,
1626 p_clcb->bta_conn_id, FALSE);
1628 /*******************************************************************************
1630 ** Function bta_gattc_start_load
1632 ** Description start cache loading by sending callout open cache
1636 *******************************************************************************/
1637 void bta_gattc_ci_open(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1639 APPL_TRACE_DEBUG("bta_gattc_ci_open conn_id=%d server state=%d" ,
1640 p_clcb->bta_conn_id, p_clcb->p_srcb->state);
1641 if (p_clcb->p_srcb->state == BTA_GATTC_SERV_LOAD)
1643 if (p_data->ci_open.status == BTA_GATT_OK)
1645 p_clcb->p_srcb->attr_index = 0;
1646 bta_gattc_co_cache_load(p_clcb->p_srcb->server_bda,
1647 BTA_GATTC_CI_CACHE_LOAD_EVT,
1648 p_clcb->p_srcb->attr_index,
1649 p_clcb->bta_conn_id);
1653 p_clcb->p_srcb->state = BTA_GATTC_SERV_DISC;
1654 /* cache open failure, start discovery */
1655 bta_gattc_start_discover(p_clcb, NULL);
1658 if (p_clcb->p_srcb->state == BTA_GATTC_SERV_SAVE)
1660 if (p_data->ci_open.status == BTA_GATT_OK)
1662 if (!bta_gattc_cache_save(p_clcb->p_srcb, p_clcb->bta_conn_id))
1664 p_data->ci_open.status = BTA_GATT_ERROR;
1667 if (p_data->ci_open.status != BTA_GATT_OK)
1669 p_clcb->p_srcb->attr_index = 0;
1670 bta_gattc_co_cache_close(p_clcb->p_srcb->server_bda, p_clcb->bta_conn_id);
1671 bta_gattc_reset_discover_st(p_clcb->p_srcb, p_clcb->status);
1676 /*******************************************************************************
1678 ** Function bta_gattc_ci_load
1680 ** Description cache loading received.
1684 *******************************************************************************/
1685 void bta_gattc_ci_load(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1688 APPL_TRACE_DEBUG("bta_gattc_ci_load conn_id=%d load status=%d",
1689 p_clcb->bta_conn_id, p_data->ci_load.status);
1691 if (p_data->ci_load.status == BTA_GATT_OK ||
1692 p_data->ci_load.status == BTA_GATT_MORE)
1694 if (p_data->ci_load.num_attr != 0)
1695 bta_gattc_rebuild_cache(p_clcb->p_srcb, p_data->ci_load.num_attr,
1696 p_data->ci_load.attr, p_clcb->p_srcb->attr_index);
1698 if (p_data->ci_load.status == BTA_GATT_OK)
1700 p_clcb->p_srcb->attr_index = 0;
1701 bta_gattc_reset_discover_st(p_clcb->p_srcb, BTA_GATT_OK);
1702 bta_gattc_co_cache_close(p_clcb->p_srcb->server_bda, 0);
1704 else /* load more */
1706 p_clcb->p_srcb->attr_index += p_data->ci_load.num_attr;
1708 bta_gattc_co_cache_load(p_clcb->p_srcb->server_bda,
1709 BTA_GATTC_CI_CACHE_LOAD_EVT,
1710 p_clcb->p_srcb->attr_index,
1711 p_clcb->bta_conn_id);
1716 bta_gattc_co_cache_close(p_clcb->p_srcb->server_bda, 0);
1717 p_clcb->p_srcb->state = BTA_GATTC_SERV_DISC;
1718 p_clcb->p_srcb->attr_index = 0;
1719 /* cache load failure, start discovery */
1720 bta_gattc_start_discover(p_clcb, NULL);
1723 /*******************************************************************************
1725 ** Function bta_gattc_ci_save
1727 ** Description cache loading received.
1731 *******************************************************************************/
1732 void bta_gattc_ci_save(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1736 APPL_TRACE_DEBUG("bta_gattc_ci_save conn_id=%d " ,
1737 p_clcb->bta_conn_id );
1739 if (!bta_gattc_cache_save(p_clcb->p_srcb, p_clcb->bta_conn_id))
1741 p_clcb->p_srcb->attr_index = 0;
1742 bta_gattc_co_cache_close(p_clcb->p_srcb->server_bda, 0);
1743 bta_gattc_reset_discover_st(p_clcb->p_srcb, p_clcb->status);
1746 /*******************************************************************************
1748 ** Function bta_gattc_fail
1750 ** Description report API call failure back to apps
1754 *******************************************************************************/
1755 void bta_gattc_fail(tBTA_GATTC_CLCB *p_clcb, tBTA_GATTC_DATA *p_data)
1759 if (p_clcb->status == BTA_GATT_OK)
1761 APPL_TRACE_ERROR("operation not supported at current state [%d]", p_clcb->state);
1765 /*******************************************************************************
1767 ** Function bta_gattc_deregister_cmpl
1769 ** Description De-Register a GATT client application with BTA completed.
1773 *******************************************************************************/
1774 static void bta_gattc_deregister_cmpl(tBTA_GATTC_RCB *p_clreg)
1776 tBTA_GATTC_CB *p_cb = &bta_gattc_cb;
1777 tBTA_GATTC_IF client_if = p_clreg->client_if;
1779 tBTA_GATTC_CBACK *p_cback = p_clreg->p_cback;
1781 memset(&cb_data, 0, sizeof(tBTA_GATTC));
1783 GATT_Deregister(p_clreg->client_if);
1784 memset(p_clreg, 0, sizeof(tBTA_GATTC_RCB));
1786 cb_data.reg_oper.client_if = client_if;
1787 cb_data.reg_oper.status = BTA_GATT_OK;
1790 /* callback with de-register event */
1791 (*p_cback)(BTA_GATTC_DEREG_EVT, (tBTA_GATTC *)&cb_data);
1793 if (bta_gattc_num_reg_app() == 0 && p_cb->state == BTA_GATTC_STATE_DISABLING)
1795 p_cb->state = BTA_GATTC_STATE_DISABLED;
1798 /*******************************************************************************
1800 ** Function bta_gattc_conn_cback
1801 ** bta_gattc_cmpl_cback
1803 ** Description callback functions to GATT client stack.
1807 *******************************************************************************/
1808 static void bta_gattc_conn_cback(tGATT_IF gattc_if, BD_ADDR bda, UINT16 conn_id,
1809 BOOLEAN connected, tGATT_DISCONN_REASON reason,
1810 tBT_TRANSPORT transport)
1812 tBTA_GATTC_DATA *p_buf;
1816 APPL_TRACE_WARNING("%s() - cif=%d connected=%d conn_id=%d reason=0x%04x",
1817 __FUNCTION__, gattc_if, connected, conn_id, reason);
1821 bdcpy(bdaddr.address, bda);
1823 btif_debug_conn_state(bdaddr, BTIF_DEBUG_CONNECTED, GATT_CONN_UNKNOWN);
1825 btif_debug_conn_state(bdaddr, BTIF_DEBUG_DISCONNECTED, reason);
1827 if ((p_buf = (tBTA_GATTC_DATA *) GKI_getbuf(sizeof(tBTA_GATTC_DATA))) != NULL)
1829 memset(p_buf, 0, sizeof(tBTA_GATTC_DATA));
1831 p_buf->int_conn.hdr.event = connected ? BTA_GATTC_INT_CONN_EVT:
1832 BTA_GATTC_INT_DISCONN_EVT;
1833 p_buf->int_conn.hdr.layer_specific = conn_id;
1834 p_buf->int_conn.client_if = gattc_if;
1835 p_buf->int_conn.role = L2CA_GetBleConnRole(bda);
1836 p_buf->int_conn.reason = reason;
1837 p_buf->int_conn.transport = transport;
1838 bdcpy(p_buf->int_conn.remote_bda, bda);
1840 bta_sys_sendmsg(p_buf);
1844 /*******************************************************************************
1846 ** Function bta_gattc_enc_cmpl_cback
1848 ** Description encryption complete callback function to GATT client stack.
1852 *******************************************************************************/
1853 static void bta_gattc_enc_cmpl_cback(tGATT_IF gattc_if, BD_ADDR bda)
1855 tBTA_GATTC_DATA *p_buf;
1856 tBTA_GATTC_CLCB *p_clcb = NULL;
1858 if ((p_clcb = bta_gattc_find_clcb_by_cif(gattc_if, bda, BTA_GATT_TRANSPORT_LE)) == NULL)
1863 #if (defined BTA_HH_LE_INCLUDED && BTA_HH_LE_INCLUDED == TRUE)
1864 /* filter this event just for BTA HH LE GATT client,
1865 In the future, if we want to enable encryption complete event
1866 for all GATT clients, we can remove this code */
1867 if (!bta_hh_le_is_hh_gatt_if(gattc_if))
1873 APPL_TRACE_DEBUG("bta_gattc_enc_cmpl_cback: cif = %d", gattc_if);
1875 if ((p_buf = (tBTA_GATTC_DATA *) GKI_getbuf(sizeof(tBTA_GATTC_DATA))) != NULL)
1877 memset(p_buf, 0, sizeof(tBTA_GATTC_DATA));
1879 p_buf->enc_cmpl.hdr.event = BTA_GATTC_ENC_CMPL_EVT;
1880 p_buf->enc_cmpl.hdr.layer_specific = p_clcb->bta_conn_id;
1881 p_buf->enc_cmpl.client_if = gattc_if;
1882 bdcpy(p_buf->enc_cmpl.remote_bda, bda);
1884 bta_sys_sendmsg(p_buf);
1888 /*******************************************************************************
1890 ** Function bta_gattc_process_api_refresh
1892 ** Description process refresh API to delete cache and start a new discovery
1893 ** if currently connected.
1897 *******************************************************************************/
1898 void bta_gattc_process_api_refresh(tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA * p_msg)
1900 tBTA_GATTC_SERV *p_srvc_cb = bta_gattc_find_srvr_cache(p_msg->api_conn.remote_bda);
1901 tBTA_GATTC_CLCB *p_clcb = &bta_gattc_cb.clcb[0];
1902 BOOLEAN found = FALSE;
1906 if (p_srvc_cb != NULL)
1908 /* try to find a CLCB */
1909 if (p_srvc_cb->connected && p_srvc_cb->num_clcb != 0)
1911 for (i = 0; i < BTA_GATTC_CLCB_MAX; i ++, p_clcb ++)
1913 if (p_clcb->in_use && p_clcb->p_srcb == p_srvc_cb)
1921 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL);
1925 /* in all other cases, mark it and delete the cache */
1926 if (p_srvc_cb->p_srvc_cache != NULL)
1928 while (!GKI_queue_is_empty(&p_srvc_cb->cache_buffer))
1929 GKI_freebuf (GKI_dequeue (&p_srvc_cb->cache_buffer));
1931 p_srvc_cb->p_srvc_cache = NULL;
1934 /* used to reset cache in application */
1935 bta_gattc_co_cache_reset(p_msg->api_conn.remote_bda);
1938 /*******************************************************************************
1940 ** Function bta_gattc_process_srvc_chg_ind
1942 ** Description process service change indication.
1946 *******************************************************************************/
1947 BOOLEAN bta_gattc_process_srvc_chg_ind(UINT16 conn_id,
1948 tBTA_GATTC_RCB *p_clrcb,
1949 tBTA_GATTC_SERV *p_srcb,
1950 tBTA_GATTC_CLCB *p_clcb,
1951 tBTA_GATTC_NOTIFY *p_notify,
1954 tBT_UUID gattp_uuid, srvc_chg_uuid;
1955 BOOLEAN processed = FALSE;
1959 gattp_uuid.uu.uuid16 = UUID_SERVCLASS_GATT_SERVER;
1961 srvc_chg_uuid.len = 2;
1962 srvc_chg_uuid.uu.uuid16 = GATT_UUID_GATT_SRV_CHGD;
1964 if (bta_gattc_uuid_compare(&p_notify->char_id.srvc_id.id.uuid, &gattp_uuid, TRUE) &&
1965 bta_gattc_uuid_compare(&p_notify->char_id.char_id.uuid, &srvc_chg_uuid, TRUE))
1968 /* mark service handle change pending */
1969 p_srcb->srvc_hdl_chg = TRUE;
1970 /* clear up all notification/indication registration */
1971 bta_gattc_clear_notif_registration(conn_id);
1972 /* service change indication all received, do discovery update */
1973 if ( ++ p_srcb->update_count == bta_gattc_num_reg_app())
1975 /* not an opened connection; or connection busy */
1976 /* search for first available clcb and start discovery */
1977 if (p_clcb == NULL || (p_clcb && p_clcb->p_q_cmd != NULL))
1979 for (i = 0 ; i < BTA_GATTC_CLCB_MAX; i ++)
1981 if (bta_gattc_cb.clcb[i].in_use &&
1982 bta_gattc_cb.clcb[i].p_srcb == p_srcb &&
1983 bta_gattc_cb.clcb[i].p_q_cmd == NULL)
1985 p_clcb = &bta_gattc_cb.clcb[i];
1990 /* send confirmation here if this is an indication, it should always be */
1991 GATTC_SendHandleValueConfirm(conn_id, handle);
1993 /* if connection available, refresh cache by doing discovery now */
1995 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL);
1997 /* notify applicationf or service change */
1998 if (p_clrcb->p_cback != NULL)
2000 (* p_clrcb->p_cback)(BTA_GATTC_SRVC_CHG_EVT, (tBTA_GATTC *)p_srcb->server_bda);
2008 /*******************************************************************************
2010 ** Function bta_gattc_proc_other_indication
2012 ** Description process all non-service change indication/notification.
2016 *******************************************************************************/
2017 void bta_gattc_proc_other_indication(tBTA_GATTC_CLCB *p_clcb, UINT8 op,
2018 tGATT_CL_COMPLETE *p_data,
2019 tBTA_GATTC_NOTIFY *p_notify)
2021 APPL_TRACE_DEBUG("bta_gattc_proc_other_indication check \
2022 p_data->att_value.handle=%d p_data->handle=%d",
2023 p_data->att_value.handle, p_data->handle);
2024 APPL_TRACE_DEBUG("is_notify", p_notify->is_notify);
2026 p_notify->is_notify = (op == GATTC_OPTYPE_INDICATION) ? FALSE : TRUE;
2027 p_notify->len = p_data->att_value.len;
2028 bdcpy(p_notify->bda, p_clcb->bda);
2029 memcpy(p_notify->value, p_data->att_value.value, p_data->att_value.len);
2030 p_notify->conn_id = p_clcb->bta_conn_id;
2032 if (p_clcb->p_rcb->p_cback)
2033 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_NOTIF_EVT, (tBTA_GATTC *)p_notify);
2036 /*******************************************************************************
2038 ** Function bta_gattc_process_indicate
2040 ** Description process indication/notification.
2044 *******************************************************************************/
2045 void bta_gattc_process_indicate(UINT16 conn_id, tGATTC_OPTYPE op, tGATT_CL_COMPLETE *p_data)
2047 UINT16 handle = p_data->att_value.handle;
2048 tBTA_GATTC_CLCB *p_clcb ;
2049 tBTA_GATTC_RCB *p_clrcb = NULL;
2050 tBTA_GATTC_SERV *p_srcb = NULL;
2051 tBTA_GATTC_NOTIFY notify;
2053 tBTA_GATTC_IF gatt_if;
2054 tBTA_TRANSPORT transport;
2056 if (!GATT_GetConnectionInfor(conn_id, &gatt_if, remote_bda, &transport))
2058 APPL_TRACE_ERROR("%s indication/notif for unknown app", __func__);
2059 if (op == GATTC_OPTYPE_INDICATION)
2060 GATTC_SendHandleValueConfirm(conn_id, handle);
2064 if ((p_clrcb = bta_gattc_cl_get_regcb(gatt_if)) == NULL)
2066 APPL_TRACE_ERROR("%s indication/notif for unregistered app", __func__);
2067 if (op == GATTC_OPTYPE_INDICATION)
2068 GATTC_SendHandleValueConfirm(conn_id, handle);
2072 if ((p_srcb = bta_gattc_find_srcb(remote_bda)) == NULL)
2074 APPL_TRACE_ERROR("%s indication/notif for unknown device, ignore", __func__);
2075 if (op == GATTC_OPTYPE_INDICATION)
2076 GATTC_SendHandleValueConfirm(conn_id, handle);
2080 p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id);
2082 if (bta_gattc_handle2id(p_srcb, handle,
2083 ¬ify.char_id.srvc_id,
2084 ¬ify.char_id.char_id,
2085 ¬ify.descr_type))
2087 /* if non-service change indication/notification, forward to application */
2088 if (!bta_gattc_process_srvc_chg_ind(conn_id, p_clrcb, p_srcb, p_clcb, ¬ify, handle))
2090 /* if app registered for the notification */
2091 if (bta_gattc_check_notif_registry(p_clrcb, p_srcb, ¬ify))
2093 /* connection not open yet */
2096 if ((p_clcb = bta_gattc_clcb_alloc(gatt_if, remote_bda, transport)) != NULL)
2098 p_clcb->bta_conn_id = conn_id;
2099 p_clcb->transport = transport;
2101 bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CONN_EVT, NULL);
2105 APPL_TRACE_ERROR("No resources");
2110 bta_gattc_proc_other_indication(p_clcb, op, p_data, ¬ify);
2112 /* no one intersted and need ack? */
2113 else if (op == GATTC_OPTYPE_INDICATION)
2115 APPL_TRACE_DEBUG("%s no one interested, ack now", __func__);
2116 GATTC_SendHandleValueConfirm(conn_id, handle);
2122 APPL_TRACE_ERROR("%s Indi/Notif for Unknown handle[0x%04x], can not find in local cache.",
2124 if (op == GATTC_OPTYPE_INDICATION)
2125 GATTC_SendHandleValueConfirm(conn_id, handle);
2128 /*******************************************************************************
2130 ** Function bta_gattc_cmpl_cback
2132 ** Description client operation complete callback register with BTE GATT.
2136 *******************************************************************************/
2137 static void bta_gattc_cmpl_cback(UINT16 conn_id, tGATTC_OPTYPE op, tGATT_STATUS status,
2138 tGATT_CL_COMPLETE *p_data)
2140 tBTA_GATTC_CLCB *p_clcb ;
2141 tBTA_GATTC_OP_CMPL *p_buf;
2142 UINT16 len = sizeof(tBTA_GATTC_OP_CMPL) + sizeof(tGATT_CL_COMPLETE);
2144 APPL_TRACE_DEBUG("bta_gattc_cmpl_cback: conn_id = %d op = %d status = %d",
2145 conn_id, op, status);
2147 /* notification and indication processed right away */
2148 if (op == GATTC_OPTYPE_NOTIFICATION || op == GATTC_OPTYPE_INDICATION)
2150 bta_gattc_process_indicate(conn_id, op, p_data);
2153 /* for all other operation, not expected if w/o connection */
2154 else if ((p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id)) == NULL)
2156 APPL_TRACE_ERROR("bta_gattc_cmpl_cback unknown conn_id = %d, ignore data", conn_id);
2160 /* if over BR_EDR, inform PM for mode change */
2161 if (p_clcb->transport == BTA_TRANSPORT_BR_EDR)
2163 bta_sys_busy(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda);
2164 bta_sys_idle(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda);
2167 if ((p_buf = (tBTA_GATTC_OP_CMPL *) GKI_getbuf(len)) != NULL)
2169 memset(p_buf, 0, len);
2170 p_buf->hdr.event = BTA_GATTC_OP_CMPL_EVT;
2171 p_buf->hdr.layer_specific = conn_id;
2172 p_buf->status = status;
2173 p_buf->op_code = op;
2177 p_buf->p_cmpl = (tGATT_CL_COMPLETE *)(p_buf + 1);
2178 memcpy(p_buf->p_cmpl, p_data, sizeof(tGATT_CL_COMPLETE));
2181 bta_sys_sendmsg(p_buf);
2187 /*******************************************************************************
2189 ** Function bta_gattc_cong_cback
2191 ** Description congestion callback for BTA GATT client.
2195 ********************************************************************************/
2196 static void bta_gattc_cong_cback (UINT16 conn_id, BOOLEAN congested)
2198 tBTA_GATTC_CLCB *p_clcb;
2201 if ((p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id)) != NULL)
2203 if (p_clcb->p_rcb->p_cback)
2205 cb_data.congest.conn_id = conn_id;
2206 cb_data.congest.congested = congested;
2208 (*p_clcb->p_rcb->p_cback)(BTA_GATTC_CONGEST_EVT, &cb_data);
2213 #if BLE_INCLUDED == TRUE
2214 /*******************************************************************************
2216 ** Function bta_gattc_init_clcb_conn
2218 ** Description Initaite a BTA CLCB connection
2222 ********************************************************************************/
2223 void bta_gattc_init_clcb_conn(UINT8 cif, BD_ADDR remote_bda)
2225 tBTA_GATTC_CLCB *p_clcb = NULL;
2226 tBTA_GATTC_DATA gattc_data;
2229 /* should always get the connection ID */
2230 if (GATT_GetConnIdIfConnected(cif, remote_bda, &conn_id, BTA_GATT_TRANSPORT_LE) == FALSE)
2232 APPL_TRACE_ERROR("bta_gattc_init_clcb_conn ERROR: not a connected device");
2236 /* initaite a new connection here */
2237 if ((p_clcb = bta_gattc_clcb_alloc(cif, remote_bda, BTA_GATT_TRANSPORT_LE)) != NULL)
2239 gattc_data.hdr.layer_specific = p_clcb->bta_conn_id = conn_id;
2241 gattc_data.api_conn.client_if = cif;
2242 memcpy(gattc_data.api_conn.remote_bda, remote_bda, BD_ADDR_LEN);
2243 gattc_data.api_conn.is_direct = TRUE;
2245 bta_gattc_sm_execute(p_clcb, BTA_GATTC_API_OPEN_EVT, &gattc_data);
2249 APPL_TRACE_ERROR("No resources");
2252 /*******************************************************************************
2254 ** Function bta_gattc_process_listen_all
2256 ** Description process listen all, send open callback to application for all
2257 ** connected slave LE link.
2261 ********************************************************************************/
2262 void bta_gattc_process_listen_all(UINT8 cif)
2265 tBTA_GATTC_CONN *p_conn = &bta_gattc_cb.conn_track[0];
2267 for (i_conn = 0; i_conn < BTA_GATTC_CONN_MAX; i_conn++, p_conn ++)
2269 if (p_conn->in_use )
2271 if (bta_gattc_find_clcb_by_cif(cif, p_conn->remote_bda, BTA_GATT_TRANSPORT_LE) == NULL)
2273 bta_gattc_init_clcb_conn(cif, p_conn->remote_bda);
2275 /* else already connected */
2279 /*******************************************************************************
2281 ** Function bta_gattc_listen
2283 ** Description Start or stop a listen for connection
2287 ********************************************************************************/
2288 void bta_gattc_listen(tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA * p_msg)
2290 tBTA_GATTC_RCB *p_clreg = bta_gattc_cl_get_regcb(p_msg->api_listen.client_if);
2294 cb_data.reg_oper.status = BTA_GATT_ERROR;
2295 cb_data.reg_oper.client_if = p_msg->api_listen.client_if;
2297 if (p_clreg == NULL)
2299 APPL_TRACE_ERROR("bta_gattc_listen failed, unknown client_if: %d",
2300 p_msg->api_listen.client_if);
2303 /* mark bg conn record */
2304 if (bta_gattc_mark_bg_conn(p_msg->api_listen.client_if,
2305 (BD_ADDR_PTR) p_msg->api_listen.remote_bda,
2306 p_msg->api_listen.start,
2309 if (!GATT_Listen(p_msg->api_listen.client_if,
2310 p_msg->api_listen.start,
2311 p_msg->api_listen.remote_bda))
2313 APPL_TRACE_ERROR("Listen failure");
2314 (*p_clreg->p_cback)(BTA_GATTC_LISTEN_EVT, &cb_data);
2318 cb_data.status = BTA_GATT_OK;
2320 (*p_clreg->p_cback)(BTA_GATTC_LISTEN_EVT, &cb_data);
2322 if (p_msg->api_listen.start)
2324 /* if listen to a specific target */
2325 if (p_msg->api_listen.remote_bda != NULL)
2328 /* if is a connected remote device */
2329 if (L2CA_GetBleConnRole(p_msg->api_listen.remote_bda) == HCI_ROLE_SLAVE &&
2330 bta_gattc_find_clcb_by_cif(p_msg->api_listen.client_if,
2331 p_msg->api_listen.remote_bda,
2332 BTA_GATT_TRANSPORT_LE) == NULL)
2335 bta_gattc_init_clcb_conn(p_msg->api_listen.client_if,
2336 p_msg->api_listen.remote_bda);
2339 /* if listen to all */
2342 LOG_DEBUG("Listen For All now");
2343 /* go through all connected device and send
2344 callback for all connected slave connection */
2345 bta_gattc_process_listen_all(p_msg->api_listen.client_if);
2352 /*******************************************************************************
2354 ** Function bta_gattc_broadcast
2356 ** Description Start or stop broadcasting
2360 ********************************************************************************/
2361 void bta_gattc_broadcast(tBTA_GATTC_CB *p_cb, tBTA_GATTC_DATA * p_msg)
2363 tBTA_GATTC_RCB *p_clreg = bta_gattc_cl_get_regcb(p_msg->api_listen.client_if);
2367 cb_data.reg_oper.client_if = p_msg->api_listen.client_if;
2368 cb_data.reg_oper.status = BTM_BleBroadcast(p_msg->api_listen.start);
2370 if (p_clreg && p_clreg->p_cback)
2371 (*p_clreg->p_cback)(BTA_GATTC_LISTEN_EVT, &cb_data);