15738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
25738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
35738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  Copyright (C) 2009-2012 Broadcom Corporation
45738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
55738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  Licensed under the Apache License, Version 2.0 (the "License");
65738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  you may not use this file except in compliance with the License.
75738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  You may obtain a copy of the License at:
85738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
95738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  http://www.apache.org/licenses/LICENSE-2.0
105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  Unless required by applicable law or agreed to in writing, software
125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  distributed under the License is distributed on an "AS IS" BASIS,
135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  See the License for the specific language governing permissions and
155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  limitations under the License.
165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project ******************************************************************************/
185738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/******************************************************************************
205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *  this file contains GATT utility functions
225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project *
235738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project ******************************************************************************/
245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project#include "bt_target.h"
255cd8bff2dd0337cb52bf48f312e3d2d55a8882fbMike J. Chen#include "bt_utils.h"
26d7ffd64accbd50a27289a388856e56244ccbb5daMyles Watson#include "osi/include/osi.h"
275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2884baa7f16e830394408278dbb8c508dd9fa02887Myles Watson#include <string.h>
2984baa7f16e830394408278dbb8c508dd9fa02887Myles Watson#include "bt_common.h"
30911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson#include "stdio.h"
3184baa7f16e830394408278dbb8c508dd9fa02887Myles Watson
32911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson#include "btm_int.h"
3384baa7f16e830394408278dbb8c508dd9fa02887Myles Watson#include "gatt_api.h"
34911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson#include "gatt_int.h"
3584baa7f16e830394408278dbb8c508dd9fa02887Myles Watson#include "gattdefs.h"
36911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson#include "l2cdefs.h"
3784baa7f16e830394408278dbb8c508dd9fa02887Myles Watson#include "sdp_api.h"
38d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski
39d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowskiusing base::StringPrintf;
40d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski
415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/* check if [x, y] and [a, b] have overlapping range */
42911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson#define GATT_VALIDATE_HANDLE_RANGE(x, y, a, b) ((y) >= (a) && (x) <= (b))
43911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
44911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson#define GATT_GET_NEXT_VALID_HANDLE(x) (((x) / 10 + 1) * 10)
45911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
46911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonconst char* const op_code_name[] = {"UNKNOWN",
47911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_RSP_ERROR",
48911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_REQ_MTU",
49911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_RSP_MTU",
50911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_REQ_READ_INFO",
51911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_RSP_READ_INFO",
52911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_REQ_FIND_TYPE_VALUE",
53911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_RSP_FIND_TYPE_VALUE",
54911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_REQ_READ_BY_TYPE",
55911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_RSP_READ_BY_TYPE",
56911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_REQ_READ",
57911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_RSP_READ",
58911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_REQ_READ_BLOB",
59911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_RSP_READ_BLOB",
60911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "GATT_REQ_READ_MULTI",
61911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "GATT_RSP_READ_MULTI",
62911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "GATT_REQ_READ_BY_GRP_TYPE",
63911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "GATT_RSP_READ_BY_GRP_TYPE",
64911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_REQ_WRITE",
65911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_RSP_WRITE",
66911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_CMD_WRITE",
67911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_SIGN_CMD_WRITE",
68911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_REQ_PREPARE_WRITE",
69911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_RSP_PREPARE_WRITE",
70911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_REQ_EXEC_WRITE",
71911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_RSP_EXEC_WRITE",
72911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "Reserved",
73911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_HANDLE_VALUE_NOTIF",
74911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "Reserved",
75911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_HANDLE_VALUE_IND",
76911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_HANDLE_VALUE_CONF",
77911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    "ATT_OP_CODE_MAX"};
78911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
79911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonstatic const uint8_t base_uuid[LEN_UUID_128] = {
80911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    0xFB, 0x34, 0x9B, 0x5F, 0x80, 0x00, 0x00, 0x80,
815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
84ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
85ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_free_pending_ind
86ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
87ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description    Free all pending indications
88ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
89ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns       None
90ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
91ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
92911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_free_pending_ind(tGATT_TCB* p_tcb) {
93d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__;
941a3844f933bd63c8a381371dabfb35c6a0249e3ePavlin Radoslavov
95911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_tcb->pending_ind_q == NULL) return;
961a3844f933bd63c8a381371dabfb35c6a0249e3ePavlin Radoslavov
97911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* release all queued indications */
98911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  while (!fixed_queue_is_empty(p_tcb->pending_ind_q))
99911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    osi_free(fixed_queue_try_dequeue(p_tcb->pending_ind_q));
100911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  fixed_queue_free(p_tcb->pending_ind_q, NULL);
101911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  p_tcb->pending_ind_q = NULL;
1025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
1035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
105ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
106ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_delete_dev_from_srv_chg_clt_list
107ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
108ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description    Delete a device from the service changed client lit
109ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
110ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns       None
111ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
112ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1139e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskivoid gatt_delete_dev_from_srv_chg_clt_list(const RawAddress& bd_addr) {
114d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__;
1155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
116911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATTS_SRV_CHG* p_buf = gatt_is_bda_in_the_srv_chg_clt_list(bd_addr);
117911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_buf != NULL) {
118911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (gatt_cb.cb_info.p_srv_chg_callback) {
119911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      /* delete from NV */
120911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      tGATTS_SRV_CHG_REQ req;
121c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski      req.srv_chg.bda = bd_addr;
122911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      (*gatt_cb.cb_info.p_srv_chg_callback)(GATTS_SRV_CHG_CMD_REMOVE_CLIENT,
123911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                            &req, NULL);
1245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
125911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    osi_free(fixed_queue_try_remove_from_queue(gatt_cb.srv_chg_clt_q, p_buf));
126911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
1275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
1285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
130ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
131ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_set_srv_chg
132ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
133ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Set the service changed flag to true
134ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
135ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns        None
136ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
137ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
138911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_set_srv_chg(void) {
139d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__;
1401a3844f933bd63c8a381371dabfb35c6a0249e3ePavlin Radoslavov
141911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (fixed_queue_is_empty(gatt_cb.srv_chg_clt_q)) return;
142577862e0d87891164a469afcecd1135bf04d1f6ePavlin Radoslavov
143911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  list_t* list = fixed_queue_get_list(gatt_cb.srv_chg_clt_q);
144911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  for (const list_node_t* node = list_begin(list); node != list_end(list);
145911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson       node = list_next(node)) {
146d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski    VLOG(1) << "found a srv_chg clt";
147911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
148911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    tGATTS_SRV_CHG* p_buf = (tGATTS_SRV_CHG*)list_node(node);
149911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (!p_buf->srv_changed) {
150d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski      VLOG(1) << "set srv_changed to true";
151911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_buf->srv_changed = true;
152911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      tGATTS_SRV_CHG_REQ req;
153911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      memcpy(&req.srv_chg, p_buf, sizeof(tGATTS_SRV_CHG));
154911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      if (gatt_cb.cb_info.p_srv_chg_callback)
155911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        (*gatt_cb.cb_info.p_srv_chg_callback)(GATTS_SRV_CHG_CMD_UPDATE_CLIENT,
156911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                              &req, NULL);
1575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
158911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
1595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
1605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1615738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
162ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
163ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function     gatt_add_pending_ind
164ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
165ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description  Add a pending indication
166ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1679ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Returns    Pointer to the current pending indication buffer, NULL no buffer
1689ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson *            available
169ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
170ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
171911d1ae03efec2d54c3b1b605589d790d1745488Myles WatsontGATT_VALUE* gatt_add_pending_ind(tGATT_TCB* p_tcb, tGATT_VALUE* p_ind) {
172911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_VALUE* p_buf = (tGATT_VALUE*)osi_malloc(sizeof(tGATT_VALUE));
173717a4a9f3a044f264ec2482c2d1806ec3093707aPavlin Radoslavov
174d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__ << "enqueue a pending indication";
175717a4a9f3a044f264ec2482c2d1806ec3093707aPavlin Radoslavov
176911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  memcpy(p_buf, p_ind, sizeof(tGATT_VALUE));
177911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  fixed_queue_enqueue(p_tcb->pending_ind_q, p_buf);
1781a3844f933bd63c8a381371dabfb35c6a0249e3ePavlin Radoslavov
179911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return p_buf;
1805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
1815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
183ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
184ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function     gatt_add_srv_chg_clt
185ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
186ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description  Add a service chnage client to the service change client queue
187ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1889ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Returns    Pointer to the service change client buffer; Null no buffer
1899ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson *            available
190ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
191ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
192911d1ae03efec2d54c3b1b605589d790d1745488Myles WatsontGATTS_SRV_CHG* gatt_add_srv_chg_clt(tGATTS_SRV_CHG* p_srv_chg) {
193911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATTS_SRV_CHG* p_buf = (tGATTS_SRV_CHG*)osi_malloc(sizeof(tGATTS_SRV_CHG));
194d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__ << "enqueue a srv chg client";
195717a4a9f3a044f264ec2482c2d1806ec3093707aPavlin Radoslavov
196911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  memcpy(p_buf, p_srv_chg, sizeof(tGATTS_SRV_CHG));
197911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  fixed_queue_enqueue(gatt_cb.srv_chg_clt_q, p_buf);
1985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
199911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return p_buf;
2005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
2015738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2026395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski/**
2036395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski * Returns pointer to the handle range buffer starting at handle |handle|,
2046395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski * nullptr
2056395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski * if no buffer available
2066395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski */
207911d1ae03efec2d54c3b1b605589d790d1745488Myles WatsontGATT_HDL_LIST_ELEM* gatt_find_hdl_buffer_by_handle(uint16_t handle) {
2086395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski  for (auto& elem : *gatt_cb.hdl_list_info) {
2096395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski    if (elem.asgn_range.s_handle == handle) return &elem;
210911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
2116395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski
2126395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski  return nullptr;
2135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
2145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
215ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
2169ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Description  Find handle range buffer by app ID, service and service instance
2179ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson *              ID.
218ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
219ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns    Pointer to the buffer, NULL no buffer available
220ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
221ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
2226395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowskistd::list<tGATT_HDL_LIST_ELEM>::iterator gatt_find_hdl_buffer_by_app_id(
2236395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski    tBT_UUID* p_app_uuid128, tBT_UUID* p_svc_uuid, uint16_t start_handle) {
2246395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski  auto end_it = gatt_cb.hdl_list_info->end();
2256395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski  auto it = gatt_cb.hdl_list_info->begin();
2266395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski  for (; it != end_it; it++) {
2276395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski    if (gatt_uuid_compare(*p_app_uuid128, it->asgn_range.app_uuid128) &&
2286395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski        gatt_uuid_compare(*p_svc_uuid, it->asgn_range.svc_uuid) &&
2296395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski        (start_handle == it->asgn_range.s_handle)) {
2306395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski      return it;
2315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
232911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
2335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2346395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski  return it;
2355738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
2365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2376395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski/**
2386395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski * free the service attribute database buffers by the owner of the service app
2396395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski * ID.
2406395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski */
2416395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowskivoid gatt_free_srvc_db_buffer_app_id(tBT_UUID* p_app_id) {
242bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski  auto it = gatt_cb.hdl_list_info->begin();
243bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski  auto end = gatt_cb.hdl_list_info->end();
244bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski  while (it != end) {
2456395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski    if (memcmp(p_app_id, &it->asgn_range.app_uuid128, sizeof(tBT_UUID)) == 0) {
2466395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski      it = gatt_cb.hdl_list_info->erase(it);
247bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski    } else {
248bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski      it++;
2495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
250911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
2515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
2525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
254ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
255ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_find_the_connected_bda
256ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
257ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      This function find the connected bda
258ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
259ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns           true if found
260ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
261ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
2629e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskibool gatt_find_the_connected_bda(uint8_t start_idx, RawAddress& bda,
263911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                 uint8_t* p_found_idx,
264911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                 tBT_TRANSPORT* p_transport) {
265911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t i;
266911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  bool found = false;
267d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__ << " start_idx=" << +start_idx;
268911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
269911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  for (i = start_idx; i < GATT_MAX_PHY_CHANNEL; i++) {
270911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (gatt_cb.tcb[i].in_use && gatt_cb.tcb[i].ch_state == GATT_CH_OPEN) {
271c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski      bda = gatt_cb.tcb[i].peer_bda;
272911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      *p_found_idx = i;
273911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      *p_transport = gatt_cb.tcb[i].transport;
274911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      found = true;
275c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski      VLOG(1) << " bda :" << bda;
276911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
2775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
278911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
279d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << StringPrintf(" found=%d found_idx=%d", found, i);
280911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return found;
2815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
2825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
2835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
284ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
285ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_is_srv_chg_ind_pending
286ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
2879ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Description      Check whether a service chnaged is in the indication pending
2889ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson *                  queue or waiting for an Ack already
289ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
290ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns         bool
291ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
292ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
293911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonbool gatt_is_srv_chg_ind_pending(tGATT_TCB* p_tcb) {
294911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  bool srv_chg_ind_pending = false;
2955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
296d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__
297d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski          << " is_queue_empty=" << fixed_queue_is_empty(p_tcb->pending_ind_q);
2985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
299911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_tcb->indicate_handle == gatt_cb.handle_of_h_r) {
300911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    srv_chg_ind_pending = true;
301911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else if (!fixed_queue_is_empty(p_tcb->pending_ind_q)) {
302911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    list_t* list = fixed_queue_get_list(p_tcb->pending_ind_q);
303911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    for (const list_node_t* node = list_begin(list); node != list_end(list);
304911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson         node = list_next(node)) {
305911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      tGATT_VALUE* p_buf = (tGATT_VALUE*)list_node(node);
306911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      if (p_buf->handle == gatt_cb.handle_of_h_r) {
307d19e0785e662e640191a075eda07acce61c2aedaMarie Janssen        srv_chg_ind_pending = true;
308911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        break;
309911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      }
3105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
311911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
3125738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
313d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__ << "srv_chg_ind_pending = %d", srv_chg_ind_pending;
314911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return srv_chg_ind_pending;
3155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
3165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
318ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
319ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_is_bda_in_the_srv_chg_clt_list
320ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
3219ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Description      This function check the specified bda is in the srv chg
3229ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson *                  client list or not
323ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
324ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns         pointer to the found elemenet otherwise NULL
325ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
326ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
3279e030fde05352ec4385d7baf6cc2af89e95e039cJakub PawlowskitGATTS_SRV_CHG* gatt_is_bda_in_the_srv_chg_clt_list(const RawAddress& bda) {
328911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATTS_SRV_CHG* p_buf = NULL;
3295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
330c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski  VLOG(1) << __func__ << ": " << bda;
3315738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
332911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (fixed_queue_is_empty(gatt_cb.srv_chg_clt_q)) return NULL;
333577862e0d87891164a469afcecd1135bf04d1f6ePavlin Radoslavov
334911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  list_t* list = fixed_queue_get_list(gatt_cb.srv_chg_clt_q);
335911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  for (const list_node_t* node = list_begin(list); node != list_end(list);
336911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson       node = list_next(node)) {
337911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    tGATTS_SRV_CHG* p_buf = (tGATTS_SRV_CHG*)list_node(node);
338c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski    if (bda == p_buf->bda) {
339d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski      VLOG(1) << "bda is in the srv chg clt list";
340911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
3415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
342911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
3435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
344911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return p_buf;
3455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
3465738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
348ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
349ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_is_bda_connected
350ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
351ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description
352ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
3539ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Returns          GATT_INDEX_INVALID if not found. Otherwise index to the tcb.
354ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
355ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
3569e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskibool gatt_is_bda_connected(const RawAddress& bda) {
357911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t i = 0;
358911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  bool connected = false;
3595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
360911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  for (i = 0; i < GATT_MAX_PHY_CHANNEL; i++) {
361c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski    if (gatt_cb.tcb[i].in_use && gatt_cb.tcb[i].peer_bda == bda) {
362911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      connected = true;
363911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
3645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
365911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
366911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return connected;
3675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
3685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
370ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
371ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_find_i_tcb_by_addr
372ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
3739ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Description      Search for an empty tcb entry, and return the index.
374ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
3759ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Returns          GATT_INDEX_INVALID if not found. Otherwise index to the tcb.
376ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
377ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
3789e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskiuint8_t gatt_find_i_tcb_by_addr(const RawAddress& bda,
379c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski                                tBT_TRANSPORT transport) {
380911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t i = 0;
3815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
382911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  for (; i < GATT_MAX_PHY_CHANNEL; i++) {
383c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski    if (gatt_cb.tcb[i].peer_bda == bda &&
384911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        gatt_cb.tcb[i].transport == transport) {
385911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      return i;
3865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
387911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
388911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return GATT_INDEX_INVALID;
3895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
3905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
3915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
392ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
393ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_get_tcb_by_idx
394ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
395ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      The function get TCB using the TCB index
396ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
397ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns           NULL if not found. Otherwise index to the tcb.
398ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
399ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
400911d1ae03efec2d54c3b1b605589d790d1745488Myles WatsontGATT_TCB* gatt_get_tcb_by_idx(uint8_t tcb_idx) {
401911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_TCB* p_tcb = NULL;
4025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
403911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if ((tcb_idx < GATT_MAX_PHY_CHANNEL) && gatt_cb.tcb[tcb_idx].in_use)
404911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    p_tcb = &gatt_cb.tcb[tcb_idx];
4055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
406911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return p_tcb;
4075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
4085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
410ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
411ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_find_tcb_by_addr
412ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
4139ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Description      Search for an empty tcb entry, and return pointer.
414ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
4159ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Returns          NULL if not found. Otherwise index to the tcb.
416ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
417ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
4189e030fde05352ec4385d7baf6cc2af89e95e039cJakub PawlowskitGATT_TCB* gatt_find_tcb_by_addr(const RawAddress& bda,
419c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski                                 tBT_TRANSPORT transport) {
420911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_TCB* p_tcb = NULL;
421911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t i = 0;
4225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
423911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  i = gatt_find_i_tcb_by_addr(bda, transport);
424911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (i != GATT_INDEX_INVALID) p_tcb = &gatt_cb.tcb[i];
4255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
426911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return p_tcb;
4275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
4285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
430ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
431ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_allocate_tcb_by_bdaddr
432ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
4339ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Description      Locate or allocate a new tcb entry for matching bda.
434ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
4359ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Returns          GATT_INDEX_INVALID if not found. Otherwise index to the tcb.
436ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
437ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
4389e030fde05352ec4385d7baf6cc2af89e95e039cJakub PawlowskitGATT_TCB* gatt_allocate_tcb_by_bdaddr(const RawAddress& bda,
439c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski                                       tBT_TRANSPORT transport) {
440911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* search for existing tcb with matching bda    */
441eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski  uint8_t j = gatt_find_i_tcb_by_addr(bda, transport);
442eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski  if (j != GATT_INDEX_INVALID) return &gatt_cb.tcb[j];
443eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski
444911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* find free tcb */
445eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski  for (int i = 0; i < GATT_MAX_PHY_CHANNEL; i++) {
446eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski    tGATT_TCB* p_tcb = &gatt_cb.tcb[i];
447eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski    if (p_tcb->in_use) continue;
448eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski
449eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski    *p_tcb = tGATT_TCB();
450eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski
451eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski    p_tcb->pending_ind_q = fixed_queue_new(SIZE_MAX);
452eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski    p_tcb->conf_timer = alarm_new("gatt.conf_timer");
453eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski    p_tcb->ind_ack_timer = alarm_new("gatt.ind_ack_timer");
454eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski    p_tcb->in_use = true;
455eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski    p_tcb->tcb_idx = i;
456eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski    p_tcb->transport = transport;
457c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski    p_tcb->peer_bda = bda;
458eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski    return p_tcb;
459911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
460eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski
461eb3ab848f8361d54faa3a997fbecfe48af9de731Jakub Pawlowski  return NULL;
4625738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
4635738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
465ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
466ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_convert_uuid16_to_uuid128
467ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
468ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Convert a 16 bits UUID to be an standard 128 bits one.
469ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
470ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          true if two uuid match; false otherwise.
471ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
472ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
473911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_convert_uuid16_to_uuid128(uint8_t uuid_128[LEN_UUID_128],
474911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    uint16_t uuid_16) {
475911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t* p = &uuid_128[LEN_UUID_128 - 4];
4765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
477911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  memcpy(uuid_128, base_uuid, LEN_UUID_128);
4785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
479911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  UINT16_TO_STREAM(p, uuid_16);
4805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
4815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
4825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
483ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
484ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_convert_uuid32_to_uuid128
485ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
486ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Convert a 32 bits UUID to be an standard 128 bits one.
487ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
488ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          true if two uuid match; false otherwise.
489ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
490ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
491911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_convert_uuid32_to_uuid128(uint8_t uuid_128[LEN_UUID_128],
492911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                    uint32_t uuid_32) {
493911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t* p = &uuid_128[LEN_UUID_128 - 4];
4948fe58875ce67c6e1099e7ba2339dcd2b979491b0Ganesh Ganapathi Batta
495911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  memcpy(uuid_128, base_uuid, LEN_UUID_128);
4968fe58875ce67c6e1099e7ba2339dcd2b979491b0Ganesh Ganapathi Batta
497911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  UINT32_TO_STREAM(p, uuid_32);
4988fe58875ce67c6e1099e7ba2339dcd2b979491b0Ganesh Ganapathi Batta}
4998fe58875ce67c6e1099e7ba2339dcd2b979491b0Ganesh Ganapathi Batta/*******************************************************************************
500ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
501ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_uuid_compare
502ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
503ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Compare two UUID to see if they are the same.
504ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
505ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          true if two uuid match; false otherwise.
506ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
507ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
508911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonbool gatt_uuid_compare(tBT_UUID src, tBT_UUID tar) {
509911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t su[LEN_UUID_128], tu[LEN_UUID_128];
510911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t *ps, *pt;
5115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
512911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* any of the UUID is unspecified */
513911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (src.len == 0 || tar.len == 0) {
514911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    return true;
515911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
5165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
517911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* If both are 16-bit, we can do a simple compare */
518911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (src.len == LEN_UUID_16 && tar.len == LEN_UUID_16) {
519911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    return src.uu.uuid16 == tar.uu.uuid16;
520911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
5215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
522911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* If both are 32-bit, we can do a simple compare */
523911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (src.len == LEN_UUID_32 && tar.len == LEN_UUID_32) {
524911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    return src.uu.uuid32 == tar.uu.uuid32;
525911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
5268fe58875ce67c6e1099e7ba2339dcd2b979491b0Ganesh Ganapathi Batta
527911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* One or both of the UUIDs is 128-bit */
528911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (src.len == LEN_UUID_16) {
529911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    /* convert a 16 bits UUID to 128 bits value */
530911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    gatt_convert_uuid16_to_uuid128(su, src.uu.uuid16);
531911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    ps = su;
532911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else if (src.len == LEN_UUID_32) {
533911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    gatt_convert_uuid32_to_uuid128(su, src.uu.uuid32);
534911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    ps = su;
535911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else
536911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    ps = src.uu.uuid128;
537911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
538911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (tar.len == LEN_UUID_16) {
539911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    /* convert a 16 bits UUID to 128 bits value */
540911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    gatt_convert_uuid16_to_uuid128(tu, tar.uu.uuid16);
541911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    pt = tu;
542911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else if (tar.len == LEN_UUID_32) {
543911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    /* convert a 32 bits UUID to 128 bits value */
544911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    gatt_convert_uuid32_to_uuid128(tu, tar.uu.uuid32);
545911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    pt = tu;
546911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else
547911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    pt = tar.uu.uuid128;
5485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
549911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return (memcmp(ps, pt, LEN_UUID_128) == 0);
5505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
5515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
553ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
554ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_build_uuid_to_stream
555ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
556ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Add UUID into stream.
557ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
558ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          UUID length.
559ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
560ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
561911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonuint8_t gatt_build_uuid_to_stream(uint8_t** p_dst, tBT_UUID uuid) {
562911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t* p = *p_dst;
563911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t len = 0;
5645738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
565911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (uuid.len == LEN_UUID_16) {
566911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    UINT16_TO_STREAM(p, uuid.uu.uuid16);
567911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    len = LEN_UUID_16;
568911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else if (uuid.len ==
569911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson             LEN_UUID_32) /* always convert 32 bits into 128 bits as alwats */
570911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  {
571911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    gatt_convert_uuid32_to_uuid128(p, uuid.uu.uuid32);
572911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    p += LEN_UUID_128;
573911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    len = LEN_UUID_128;
574911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else if (uuid.len == LEN_UUID_128) {
575911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    ARRAY_TO_STREAM(p, uuid.uu.uuid128, LEN_UUID_128);
576911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    len = LEN_UUID_128;
577911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
5785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
579911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  *p_dst = p;
580911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return len;
5815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
5825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
5835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
584ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
585ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_parse_uuid_from_cmd
586ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
587ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Convert a 128 bits UUID into a 16 bits UUID.
588ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
589ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          true if command sent, otherwise false.
590ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
591ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
592911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonbool gatt_parse_uuid_from_cmd(tBT_UUID* p_uuid_rec, uint16_t uuid_size,
593911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                              uint8_t** p_data) {
594911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  bool is_base_uuid, ret = true;
595911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t xx;
596911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t* p_uuid = *p_data;
597911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
598911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  memset(p_uuid_rec, 0, sizeof(tBT_UUID));
599911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
600911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  switch (uuid_size) {
601911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    case LEN_UUID_16:
602911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_uuid_rec->len = uuid_size;
603911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      STREAM_TO_UINT16(p_uuid_rec->uu.uuid16, p_uuid);
604911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      *p_data += LEN_UUID_16;
605911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
606911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
607911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    case LEN_UUID_128:
608911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      /* See if we can compress his UUID down to 16 or 32bit UUIDs */
609911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      is_base_uuid = true;
610911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      for (xx = 0; xx < LEN_UUID_128 - 4; xx++) {
611911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        if (p_uuid[xx] != base_uuid[xx]) {
612911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson          is_base_uuid = false;
613911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson          break;
614911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        }
615911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      }
616911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      if (is_base_uuid) {
617911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        if ((p_uuid[LEN_UUID_128 - 1] == 0) &&
618911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson            (p_uuid[LEN_UUID_128 - 2] == 0)) {
619911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson          p_uuid += (LEN_UUID_128 - 4);
620911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson          p_uuid_rec->len = LEN_UUID_16;
621911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson          STREAM_TO_UINT16(p_uuid_rec->uu.uuid16, p_uuid);
622911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        } else {
623911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson          p_uuid += (LEN_UUID_128 - LEN_UUID_32);
624911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson          p_uuid_rec->len = LEN_UUID_32;
625911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson          STREAM_TO_UINT32(p_uuid_rec->uu.uuid32, p_uuid);
626911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        }
627911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      }
628911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      if (!is_base_uuid) {
629911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        p_uuid_rec->len = LEN_UUID_128;
630911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        memcpy(p_uuid_rec->uu.uuid128, p_uuid, LEN_UUID_128);
631911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      }
632911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      *p_data += LEN_UUID_128;
633911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
634911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
635911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    /* do not allow 32 bits UUID in ATT PDU now */
636911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    case LEN_UUID_32:
637d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski      LOG(ERROR) << "DO NOT ALLOW 32 BITS UUID IN ATT PDU";
638911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      return false;
639911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    case 0:
640911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    default:
641911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      if (uuid_size != 0) ret = false;
642d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski      LOG(WARNING) << __func__ << ": invalid uuid size";
643911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
644911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
6455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
646911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return (ret);
6475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
6485738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
6495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
650ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
651ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_start_rsp_timer
652ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
653ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Start a wait_for_response timer.
654ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
655ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          void
656ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
657ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
658e4f42abab339b3329aec07502199e11d3d8b3d80Jakub Pawlowskivoid gatt_start_rsp_timer(tGATT_CLCB* p_clcb) {
659911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  period_ms_t timeout_ms = GATT_WAIT_FOR_RSP_TIMEOUT_MS;
66078bcff79e1b1f0efce436b33bdd6da88745bfc8aPavlin Radoslavov
661911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY &&
662911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_clcb->op_subtype == GATT_DISC_SRVC_ALL) {
663911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    timeout_ms = GATT_WAIT_FOR_DISC_RSP_TIMEOUT_MS;
664911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
66578bcff79e1b1f0efce436b33bdd6da88745bfc8aPavlin Radoslavov
666911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  // TODO: The tGATT_CLCB memory and state management needs cleanup,
667911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  // and then the timers can be allocated elsewhere.
668911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_clcb->gatt_rsp_timer_ent == NULL) {
669911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    p_clcb->gatt_rsp_timer_ent = alarm_new("gatt.gatt_rsp_timer_ent");
670911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
67147616530ceea2ea6432ffb35cd8a3fc0a56365b5Jakub Pawlowski  alarm_set_on_mloop(p_clcb->gatt_rsp_timer_ent, timeout_ms, gatt_rsp_timeout,
67247616530ceea2ea6432ffb35cd8a3fc0a56365b5Jakub Pawlowski                     p_clcb);
6735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
67478bcff79e1b1f0efce436b33bdd6da88745bfc8aPavlin Radoslavov
6755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
676ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
677ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_start_conf_timer
678ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
679ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Start a wait_for_confirmation timer.
680ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
681ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          void
682ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
683ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
684911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_start_conf_timer(tGATT_TCB* p_tcb) {
68547616530ceea2ea6432ffb35cd8a3fc0a56365b5Jakub Pawlowski  alarm_set_on_mloop(p_tcb->conf_timer, GATT_WAIT_FOR_RSP_TIMEOUT_MS,
68647616530ceea2ea6432ffb35cd8a3fc0a56365b5Jakub Pawlowski                     gatt_indication_confirmation_timeout, p_tcb);
6875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
68878bcff79e1b1f0efce436b33bdd6da88745bfc8aPavlin Radoslavov
6895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
690ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
691ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_start_ind_ack_timer
692ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
693ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      start the application ack timer
694ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
695ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          void
696ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
697ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
698f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowskivoid gatt_start_ind_ack_timer(tGATT_TCB& tcb) {
699911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* start notification cache timer */
70047616530ceea2ea6432ffb35cd8a3fc0a56365b5Jakub Pawlowski  alarm_set_on_mloop(tcb.ind_ack_timer, GATT_WAIT_FOR_RSP_TIMEOUT_MS,
70147616530ceea2ea6432ffb35cd8a3fc0a56365b5Jakub Pawlowski                     gatt_ind_ack_timeout, &tcb);
7025738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
70378bcff79e1b1f0efce436b33bdd6da88745bfc8aPavlin Radoslavov
7045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
705ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
706ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_rsp_timeout
707ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
708ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Called when GATT wait for ATT command response timer expires
709ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
710ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          void
711ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
712ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
713911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_rsp_timeout(void* data) {
714911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_CLCB* p_clcb = (tGATT_CLCB*)data;
71578bcff79e1b1f0efce436b33bdd6da88745bfc8aPavlin Radoslavov
716911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_clcb == NULL || p_clcb->p_tcb == NULL) {
717d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski    LOG(WARNING) << __func__ << " clcb is already deleted";
718911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    return;
719911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
720911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY &&
721911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_clcb->op_subtype == GATT_DISC_SRVC_ALL &&
722911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_clcb->retry_count < GATT_REQ_RETRY_LIMIT) {
723911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    uint8_t rsp_code;
724d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski    LOG(WARNING) << __func__ << " retry discovery primary service";
725f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    if (p_clcb != gatt_cmd_dequeue(*p_clcb->p_tcb, &rsp_code)) {
726d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski      LOG(ERROR) << __func__ << " command queue out of sync, disconnect";
727911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    } else {
728911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_clcb->retry_count++;
729911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      gatt_act_discovery(p_clcb);
730911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      return;
7315fba60a8761b28adec2704dcbf69376ebde4f19bZhihai Xu    }
732911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
7335fba60a8761b28adec2704dcbf69376ebde4f19bZhihai Xu
734d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  LOG(WARNING) << __func__ << " disconnecting...";
735911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  gatt_disconnect(p_clcb->p_tcb);
7365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
7375738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
739ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
740ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_indication_confirmation_timeout
741ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
742ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Called when the indication confirmation timer expires
743ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
744ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          void
745ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
746ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
747911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_indication_confirmation_timeout(void* data) {
748911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_TCB* p_tcb = (tGATT_TCB*)data;
74978bcff79e1b1f0efce436b33bdd6da88745bfc8aPavlin Radoslavov
750d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  LOG(WARNING) << __func__ << " disconnecting...";
751911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  gatt_disconnect(p_tcb);
75278bcff79e1b1f0efce436b33bdd6da88745bfc8aPavlin Radoslavov}
75378bcff79e1b1f0efce436b33bdd6da88745bfc8aPavlin Radoslavov
75478bcff79e1b1f0efce436b33bdd6da88745bfc8aPavlin Radoslavov/*******************************************************************************
755ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
756ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_ind_ack_timeout
757ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
758ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Called when GATT wait for ATT handle confirmation timeout
759ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
760ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          void
761ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
762ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
763911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_ind_ack_timeout(void* data) {
764911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_TCB* p_tcb = (tGATT_TCB*)data;
765f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  CHECK(p_tcb);
7665738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
767d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  LOG(WARNING) << __func__ << ": send ack now";
768f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  p_tcb->ind_count = 0;
769e4f42abab339b3329aec07502199e11d3d8b3d80Jakub Pawlowski  attp_send_cl_msg(*p_tcb, nullptr, GATT_HANDLE_VALUE_CONF, NULL);
7705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
7715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
772ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
7739ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Description      Search for a service that owns a specific handle.
774ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
7759ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Returns          GATT_MAX_SR_PROFILES if not found. Otherwise the index of
7769ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson *                  the service.
777ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
778ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
7796395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowskistd::list<tGATT_SRV_LIST_ELEM>::iterator gatt_sr_find_i_rcb_by_handle(
7806395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski    uint16_t handle) {
7816395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski  auto it = gatt_cb.srv_list_info->begin();
7825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7836395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski  for (; it != gatt_cb.srv_list_info->end(); it++) {
7846395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski    if (it->s_hdl <= handle && it->e_hdl >= handle) {
7856395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski      return it;
7865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
787911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
788911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
7896395f1547ed6179dcdeed392bd9909d18772fb25Jakub Pawlowski  return it;
7905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
7915738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
7925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
793ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
794ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_sr_get_sec_info
795ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
796ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Get the security flag and key size information for the peer
797ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *                  device.
798ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
799ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          void
800ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
801ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
8029e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskivoid gatt_sr_get_sec_info(const RawAddress& rem_bda, tBT_TRANSPORT transport,
803911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                          uint8_t* p_sec_flag, uint8_t* p_key_size) {
804911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t sec_flag = 0;
8055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
806911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  BTM_GetSecurityFlagsByTransport(rem_bda, &sec_flag, transport);
8075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
808911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  sec_flag &= (GATT_SEC_FLAG_LKEY_UNAUTHED | GATT_SEC_FLAG_LKEY_AUTHED |
809911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson               GATT_SEC_FLAG_ENCRYPTED);
8105738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
811911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  *p_key_size = btm_ble_read_sec_key_size(rem_bda);
812911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  *p_sec_flag = sec_flag;
8135738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
8145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
815ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
816ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_sr_send_req_callback
817ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
818ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description
819ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
820ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
821ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          void
822ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
823ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
824911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_sr_send_req_callback(uint16_t conn_id, uint32_t trans_id,
825911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                               tGATTS_REQ_TYPE type, tGATTS_DATA* p_data) {
826911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_IF gatt_if = GATT_GET_GATT_IF(conn_id);
827911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_REG* p_reg = gatt_get_regcb(gatt_if);
8285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
829911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (!p_reg) {
830d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski    LOG(ERROR) << "p_reg not found discard request";
831911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    return;
832911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
8335738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
834911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_reg->in_use && p_reg->app_cb.p_req_cb) {
835911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    (*p_reg->app_cb.p_req_cb)(conn_id, trans_id, type, p_data);
836911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else {
837d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski    LOG(WARNING) << "Call back not found for application conn_id=" << conn_id;
838911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
8395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
8405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
842ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
843ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_send_error_rsp
844ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
845ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      This function sends an error response.
846ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
847ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          void
848ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
849ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
850f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub PawlowskitGATT_STATUS gatt_send_error_rsp(tGATT_TCB& tcb, uint8_t err_code,
851911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                                 uint8_t op_code, uint16_t handle, bool deq) {
852911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_STATUS status;
853911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  BT_HDR* p_buf;
8545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8558e89469b5e223a48e1915f16862e81a3f4581259Myles Watson  tGATT_SR_MSG msg;
8568e89469b5e223a48e1915f16862e81a3f4581259Myles Watson  msg.error.cmd_code = op_code;
8578e89469b5e223a48e1915f16862e81a3f4581259Myles Watson  msg.error.reason = err_code;
8588e89469b5e223a48e1915f16862e81a3f4581259Myles Watson  msg.error.handle = handle;
8595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8608e89469b5e223a48e1915f16862e81a3f4581259Myles Watson  p_buf = attp_build_sr_msg(tcb, GATT_RSP_ERROR, &msg);
861911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_buf != NULL) {
862f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    status = attp_send_sr_msg(tcb, p_buf);
863911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else
864911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    status = GATT_INSUF_RESOURCE;
8655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
866f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  if (deq) gatt_dequeue_sr_cmd(tcb);
8675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
868911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return status;
8695738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
8705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
8715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
872ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
873ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_add_sdp_record
874ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
875ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      This function add a SDP record for a GATT primary service
876ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
877ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          0 if error else sdp handle for the record.
878ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
879ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
880911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonuint32_t gatt_add_sdp_record(tBT_UUID* p_uuid, uint16_t start_hdl,
881911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                             uint16_t end_hdl) {
882911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tSDP_PROTOCOL_ELEM proto_elem_list[2];
883911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint32_t sdp_handle;
884911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint16_t list = UUID_SERVCLASS_PUBLIC_BROWSE_GROUP;
885911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t buff[60];
886911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t* p = buff;
8875738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
888d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__
889d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski          << StringPrintf(" s_hdl=0x%x  s_hdl=0x%x", start_hdl, end_hdl);
8905738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
891911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  sdp_handle = SDP_CreateRecord();
892911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (sdp_handle == 0) return 0;
8935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
894911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  switch (p_uuid->len) {
895911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    case LEN_UUID_16:
896911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      SDP_AddServiceClassIdList(sdp_handle, 1, &p_uuid->uu.uuid16);
897911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
8985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
899911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    case LEN_UUID_32:
900911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      UINT8_TO_BE_STREAM(p, (UUID_DESC_TYPE << 3) | SIZE_FOUR_BYTES);
901911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      UINT32_TO_BE_STREAM(p, p_uuid->uu.uuid32);
902911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      SDP_AddAttribute(sdp_handle, ATTR_ID_SERVICE_CLASS_ID_LIST,
903911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                       DATA_ELE_SEQ_DESC_TYPE, (uint32_t)(p - buff), buff);
904911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
905911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
906911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    case LEN_UUID_128:
907911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      UINT8_TO_BE_STREAM(p, (UUID_DESC_TYPE << 3) | SIZE_SIXTEEN_BYTES);
908911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      ARRAY_TO_BE_STREAM_REVERSE(p, p_uuid->uu.uuid128, LEN_UUID_128);
909911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      SDP_AddAttribute(sdp_handle, ATTR_ID_SERVICE_CLASS_ID_LIST,
910911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                       DATA_ELE_SEQ_DESC_TYPE, (uint32_t)(p - buff), buff);
911911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
912911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
913911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    default:
914d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski      LOG(ERROR) << "inavlid UUID len=" << +p_uuid->len;
915911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      SDP_DeleteRecord(sdp_handle);
916911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      return 0;
917911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
918911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
9195738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
920911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /*** Fill out the protocol element sequence for SDP ***/
921911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  proto_elem_list[0].protocol_uuid = UUID_PROTOCOL_L2CAP;
922911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  proto_elem_list[0].num_params = 1;
923911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  proto_elem_list[0].params[0] = BT_PSM_ATT;
924911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  proto_elem_list[1].protocol_uuid = UUID_PROTOCOL_ATT;
925911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  proto_elem_list[1].num_params = 2;
926911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  proto_elem_list[1].params[0] = start_hdl;
927911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  proto_elem_list[1].params[1] = end_hdl;
9285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
929911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  SDP_AddProtocolList(sdp_handle, 2, proto_elem_list);
930911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
931911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* Make the service browseable */
932911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  SDP_AddUuidSequence(sdp_handle, ATTR_ID_BROWSE_GROUP_LIST, 1, &list);
933911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
934911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return (sdp_handle);
935911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson}
936911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
937bdd2f5001ffc7c53f0e38c2a98e393b1855f9ce6Myles Watson#if GATT_CONFORMANCE_TESTING == TRUE
9385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
939ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
940ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_set_err_rsp
941ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
942ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      This function is called to set the test confirm value
943ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
944ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          void
945ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
946ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
947911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_set_err_rsp(bool enable, uint8_t req_op_code, uint8_t err_status) {
948d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__ << StringPrintf(" enable=%d op_code=%d, err_status=%d",
949d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski                                      enable, req_op_code, err_status);
950911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  gatt_cb.enable_err_rsp = enable;
951911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  gatt_cb.req_op_code = req_op_code;
952911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  gatt_cb.err_status = err_status;
9535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
954911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson#endif
9555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
957ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
958ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_get_regcb
959ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
960ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      The function returns the registration control block.
961ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
962ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          pointer to the registration control block or NULL
963ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
964ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
965911d1ae03efec2d54c3b1b605589d790d1745488Myles WatsontGATT_REG* gatt_get_regcb(tGATT_IF gatt_if) {
966911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t ii = (uint8_t)gatt_if;
967911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_REG* p_reg = NULL;
9685738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
969911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (ii < 1 || ii > GATT_MAX_APPS) {
970d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski    LOG(WARNING) << "gatt_if out of range = " << +ii;
971911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    return NULL;
972911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
9735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
974911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  // Index for cl_rcb is always 1 less than gatt_if.
975911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  p_reg = &gatt_cb.cl_rcb[ii - 1];
976accf8811ddb623ea50b23b4dd9609661b6bf4718Steve Gu
977911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (!p_reg->in_use) {
978d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski    LOG(WARNING) << "gatt_if found but not in use.";
979911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    return NULL;
980911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
981accf8811ddb623ea50b23b4dd9609661b6bf4718Steve Gu
982911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return p_reg;
9835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
9845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
9855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
986ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
987ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_is_clcb_allocated
988ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
989ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      The function check clcb for conn_id is allocated or not
990ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
991ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns           True already allocated
992ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
993ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
9945738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
995911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonbool gatt_is_clcb_allocated(uint16_t conn_id) {
996911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t i = 0;
997911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  bool is_allocated = false;
9985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
999911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  for (i = 0; i < GATT_CL_MAX_LCB; i++) {
1000911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (gatt_cb.clcb[i].in_use && (gatt_cb.clcb[i].conn_id == conn_id)) {
1001911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      is_allocated = true;
1002911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
10035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1004911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
10055738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1006911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return is_allocated;
10075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
10085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1010ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1011ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_clcb_alloc
1012ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1013ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      The function allocates a GATT  connection link control block
1014ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
10159ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Returns          NULL if not found. Otherwise pointer to the connection link
10169ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson *                  block.
1017ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1018ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1019911d1ae03efec2d54c3b1b605589d790d1745488Myles WatsontGATT_CLCB* gatt_clcb_alloc(uint16_t conn_id) {
1020911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t i = 0;
1021911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_CLCB* p_clcb = NULL;
1022911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_IF gatt_if = GATT_GET_GATT_IF(conn_id);
1023911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t tcb_idx = GATT_GET_TCB_IDX(conn_id);
1024911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_TCB* p_tcb = gatt_get_tcb_by_idx(tcb_idx);
1025911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_REG* p_reg = gatt_get_regcb(gatt_if);
1026911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
1027911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  for (i = 0; i < GATT_CL_MAX_LCB; i++) {
1028911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (!gatt_cb.clcb[i].in_use) {
1029911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_clcb = &gatt_cb.clcb[i];
1030911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
1031911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_clcb->in_use = true;
1032911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_clcb->conn_id = conn_id;
1033911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_clcb->p_reg = p_reg;
1034911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_clcb->p_tcb = p_tcb;
1035911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
10365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1037911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
10383f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski
1039911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return p_clcb;
10405738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
10415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1043ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1044ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_clcb_dealloc
1045ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
10469ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Description      The function de-allocates a GATT connection link control
10479ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson *                  block
1048ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1049ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns         None
1050ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1051ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1052911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_clcb_dealloc(tGATT_CLCB* p_clcb) {
1053911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_clcb && p_clcb->in_use) {
1054911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    alarm_free(p_clcb->gatt_rsp_timer_ent);
1055911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    memset(p_clcb, 0, sizeof(tGATT_CLCB));
1056911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
10575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
10585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1060ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1061ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_find_tcb_by_cid
1062ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1063ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      The function searches for an empty entry
1064ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *                   in registration info table for GATT client
1065ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1066ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns           NULL if not found. Otherwise pointer to the rcb.
1067ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1068ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1069911d1ae03efec2d54c3b1b605589d790d1745488Myles WatsontGATT_TCB* gatt_find_tcb_by_cid(uint16_t lcid) {
1070911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint16_t xx = 0;
1071911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_TCB* p_tcb = NULL;
10725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1073911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  for (xx = 0; xx < GATT_MAX_PHY_CHANNEL; xx++) {
1074911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (gatt_cb.tcb[xx].in_use && gatt_cb.tcb[xx].att_lcid == lcid) {
1075911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      p_tcb = &gatt_cb.tcb[xx];
1076911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      break;
10775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1078911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
1079911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return p_tcb;
10805738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
10815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
10825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1083ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1084ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_num_clcb_by_bd_addr
1085ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1086ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      The function searches all LCB with macthing bd address
1087ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1088ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          total number of clcb found.
1089ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1090ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
10919e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskiuint8_t gatt_num_clcb_by_bd_addr(const RawAddress& bda) {
1092911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t i, num = 0;
10935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1094911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  for (i = 0; i < GATT_CL_MAX_LCB; i++) {
1095c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski    if (gatt_cb.clcb[i].in_use && gatt_cb.clcb[i].p_tcb->peer_bda == bda) num++;
1096911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
1097911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return num;
10985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
10995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1100f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowskivoid gatt_sr_copy_prep_cnt_to_cback_cnt(tGATT_TCB& tcb) {
1101f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  for (uint8_t i = 0; i < GATT_MAX_APPS; i++) {
1102f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    if (tcb.prep_cnt[i]) {
1103f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski      tcb.sr_cmd.cback_cnt[i] = 1;
11045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1105911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
11065738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
11075738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
11085738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1109ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1110ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_sr_is_cback_cnt_zero
1111ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1112ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      The function searches all LCB with macthing bd address
1113ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1114ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          True if thetotal application callback count is zero
1115ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1116ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1117f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowskibool gatt_sr_is_cback_cnt_zero(tGATT_TCB& tcb) {
1118f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  for (uint8_t i = 0; i < GATT_MAX_APPS; i++) {
1119f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    if (tcb.sr_cmd.cback_cnt[i]) {
1120f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski      return false;
11215738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1122911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
1123f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  return true;
11245738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
11255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
11265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1127ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1128ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_sr_is_prep_cnt_zero
1129ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1130ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Check the prepare write request count is zero or not
1131ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1132ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          True no prepare write request
1133ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1134ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1135f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowskibool gatt_sr_is_prep_cnt_zero(tGATT_TCB& tcb) {
1136f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  for (uint8_t i = 0; i < GATT_MAX_APPS; i++) {
1137f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    if (tcb.prep_cnt[i]) {
1138f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski      return false;
11395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1140911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
1141f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  return true;
11425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
11435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
11445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1145ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1146ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_sr_reset_cback_cnt
1147ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1148ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Reset the application callback count to zero
1149ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1150ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns         None
1151ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1152ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1153f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowskivoid gatt_sr_reset_cback_cnt(tGATT_TCB& tcb) {
1154f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  for (uint8_t i = 0; i < GATT_MAX_APPS; i++) {
1155f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    tcb.sr_cmd.cback_cnt[i] = 0;
1156911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
11575738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
11585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
11595738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1160ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1161ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_sr_reset_prep_cnt
1162ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1163ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description     Reset the prep write count to zero
1164ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1165ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns        None
1166ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1167ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1168f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowskivoid gatt_sr_reset_prep_cnt(tGATT_TCB& tcb) {
1169f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  for (uint8_t i = 0; i < GATT_MAX_APPS; i++) {
1170f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    tcb.prep_cnt[i] = 0;
1171911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
11725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
11735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
11745738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1175ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1176ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_sr_update_cback_cnt
1177ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1178ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description    Update the teh applicaiton callback count
1179ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1180ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns           None
1181ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1182ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1183f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowskivoid gatt_sr_update_cback_cnt(tGATT_TCB& tcb, tGATT_IF gatt_if, bool is_inc,
1184911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                              bool is_reset_first) {
1185911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t idx = ((uint8_t)gatt_if) - 1;
11865738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1187f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  if (is_reset_first) {
1188f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    gatt_sr_reset_cback_cnt(tcb);
1189f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  }
1190f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  if (is_inc) {
1191f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    tcb.sr_cmd.cback_cnt[idx]++;
1192f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  } else {
1193f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    if (tcb.sr_cmd.cback_cnt[idx]) {
1194f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski      tcb.sr_cmd.cback_cnt[idx]--;
11955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1196911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
11975738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
11985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
11995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1200ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1201ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_sr_update_prep_cnt
1202ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1203ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description    Update the teh prepare write request count
1204ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1205ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns           None
1206ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1207ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1208f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowskivoid gatt_sr_update_prep_cnt(tGATT_TCB& tcb, tGATT_IF gatt_if, bool is_inc,
1209911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                             bool is_reset_first) {
1210911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t idx = ((uint8_t)gatt_if) - 1;
12115738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1212d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << StringPrintf(
1213d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski      "%s tcb idx=%d gatt_if=%d is_inc=%d is_reset_first=%d", __func__,
1214d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski      tcb.tcb_idx, gatt_if, is_inc, is_reset_first);
12155738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1216f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  if (is_reset_first) {
1217f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    gatt_sr_reset_prep_cnt(tcb);
1218f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  }
1219f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  if (is_inc) {
1220f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    tcb.prep_cnt[idx]++;
1221f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski  } else {
1222f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski    if (tcb.prep_cnt[idx]) {
1223f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski      tcb.prep_cnt[idx]--;
1224911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    }
1225911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
12265738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
12275738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1228ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1229ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_cancel_open
1230ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1231ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Cancel open request
1232ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1233ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns         Boolean
1234ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1235ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
12369e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskibool gatt_cancel_open(tGATT_IF gatt_if, const RawAddress& bda) {
1237911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_TCB* p_tcb = NULL;
1238911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  bool status = true;
12395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1240911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  p_tcb = gatt_find_tcb_by_addr(bda, BT_TRANSPORT_LE);
12418fe58875ce67c6e1099e7ba2339dcd2b979491b0Ganesh Ganapathi Batta
1242911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_tcb) {
1243911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (gatt_get_ch_state(p_tcb) == GATT_CH_OPEN) {
1244d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski      LOG(ERROR) << __func__ << ": link connected Too late to cancel";
1245911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      status = false;
1246911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    } else {
1247911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      gatt_update_app_use_link_flag(gatt_if, p_tcb, false, false);
12483dda89880b66b0f04f684d138e7c3dc9a0e61597Jakub Pawlowski      if (p_tcb->app_hold_link.empty()) {
1249911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        gatt_disconnect(p_tcb);
1250911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      }
12515738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1252911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
12535738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1254911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return status;
12555738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
12565738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1257d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski/** Enqueue this command */
1258e4f42abab339b3329aec07502199e11d3d8b3d80Jakub Pawlowskivoid gatt_cmd_enq(tGATT_TCB& tcb, tGATT_CLCB* p_clcb, bool to_send,
1259911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                  uint8_t op_code, BT_HDR* p_buf) {
1260d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski  tGATT_CMD_Q cmd;
1261d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski  cmd.to_send = to_send; /* waiting to be sent */
1262d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski  cmd.op_code = op_code;
1263d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski  cmd.p_cmd = p_buf;
1264e4f42abab339b3329aec07502199e11d3d8b3d80Jakub Pawlowski  cmd.p_clcb = p_clcb;
12655738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1266911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (!to_send) {
1267d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski    // TODO: WTF why do we clear the queue here ?!
1268d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski    tcb.cl_cmd_q = std::queue<tGATT_CMD_Q>();
1269911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
12705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1271d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski  tcb.cl_cmd_q.push(cmd);
12725738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
12735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1274d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski/** dequeue the command in the client CCB command queue */
1275f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub PawlowskitGATT_CLCB* gatt_cmd_dequeue(tGATT_TCB& tcb, uint8_t* p_op_code) {
1276d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski  if (tcb.cl_cmd_q.empty()) return nullptr;
12775738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1278d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski  tGATT_CMD_Q cmd = tcb.cl_cmd_q.front();
1279e4f42abab339b3329aec07502199e11d3d8b3d80Jakub Pawlowski  tGATT_CLCB* p_clcb = cmd.p_clcb;
1280d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski  *p_op_code = cmd.op_code;
1281d1a9313471ed5290ca560305978c3107020272c2Jakub Pawlowski  tcb.cl_cmd_q.pop();
12825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1283911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return p_clcb;
12845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
12855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
12868463560c803bcf879fe1511239e5d12b15582c2eJakub Pawlowski/** Send out the ATT message for write */
1287e4f42abab339b3329aec07502199e11d3d8b3d80Jakub Pawlowskiuint8_t gatt_send_write_msg(tGATT_TCB& tcb, tGATT_CLCB* p_clcb, uint8_t op_code,
1288f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski                            uint16_t handle, uint16_t len, uint16_t offset,
1289f4c0292c63085cd4d0f5c001974b6503aeaf8ed3Jakub Pawlowski                            uint8_t* p_data) {
1290911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_CL_MSG msg;
1291911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  msg.attr_value.handle = handle;
1292911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  msg.attr_value.len = len;
1293911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  msg.attr_value.offset = offset;
1294911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  memcpy(msg.attr_value.value, p_data, len);
12955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1296911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* write by handle */
1297e4f42abab339b3329aec07502199e11d3d8b3d80Jakub Pawlowski  return attp_send_cl_msg(tcb, p_clcb, op_code, &msg);
12985738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
12995738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
13005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1301ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1302ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_end_operation
1303ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1304ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      This function ends a discovery, send callback and finalize
1305ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *                  some control value.
1306ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1307ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          16 bits uuid.
1308ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1309ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1310911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_end_operation(tGATT_CLCB* p_clcb, tGATT_STATUS status, void* p_data) {
1311911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_CL_COMPLETE cb_data;
1312911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_CMPL_CBACK* p_cmpl_cb =
1313911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      (p_clcb->p_reg) ? p_clcb->p_reg->app_cb.p_cmpl_cb : NULL;
1314911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t op = p_clcb->operation, disc_type = GATT_DISC_MAX;
1315911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_DISC_CMPL_CB* p_disc_cmpl_cb =
1316911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      (p_clcb->p_reg) ? p_clcb->p_reg->app_cb.p_disc_cmpl_cb : NULL;
1317911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint16_t conn_id;
1318911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t operation;
1319911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
1320d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__ << StringPrintf(" status=%d op=%d subtype=%d", status,
1321d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski                                      p_clcb->operation, p_clcb->op_subtype);
1322911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  memset(&cb_data.att_value, 0, sizeof(tGATT_VALUE));
1323911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
1324911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_cmpl_cb != NULL && p_clcb->operation != 0) {
1325911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (p_clcb->operation == GATTC_OPTYPE_READ) {
1326911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      cb_data.att_value.handle = p_clcb->s_handle;
1327911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      cb_data.att_value.len = p_clcb->counter;
1328911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
1329911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      if (p_data && p_clcb->counter)
1330911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        memcpy(cb_data.att_value.value, p_data, cb_data.att_value.len);
1331911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    }
1332911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
1333911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (p_clcb->operation == GATTC_OPTYPE_WRITE) {
1334911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      memset(&cb_data.att_value, 0, sizeof(tGATT_VALUE));
1335911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      cb_data.handle = cb_data.att_value.handle = p_clcb->s_handle;
1336911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      if (p_clcb->op_subtype == GATT_WRITE_PREPARE) {
1337911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        if (p_data) {
1338911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson          cb_data.att_value = *((tGATT_VALUE*)p_data);
1339911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        } else {
1340d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski          VLOG(1) << "Rcv Prepare write rsp but no data";
13415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project        }
1342911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      }
1343911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    }
13445738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1345911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (p_clcb->operation == GATTC_OPTYPE_CONFIG)
1346911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      cb_data.mtu = p_clcb->p_tcb->payload_size;
13475738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1348911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY) {
1349911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      disc_type = p_clcb->op_subtype;
13505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1351911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
13525738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1353911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  osi_free_and_reset((void**)&p_clcb->p_attr_buf);
13545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1355911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  operation = p_clcb->operation;
1356911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  conn_id = p_clcb->conn_id;
1357911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  alarm_cancel(p_clcb->gatt_rsp_timer_ent);
13585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1359911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  gatt_clcb_dealloc(p_clcb);
13605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1361911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_disc_cmpl_cb && (op == GATTC_OPTYPE_DISCOVERY))
1362911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    (*p_disc_cmpl_cb)(conn_id, disc_type, status);
1363911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  else if (p_cmpl_cb && op)
1364911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    (*p_cmpl_cb)(conn_id, op, status, &cb_data);
1365911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  else
1366d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski    LOG(WARNING) << __func__
1367d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski                 << StringPrintf(
1368d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski                        ": not sent out op=%d p_disc_cmpl_cb:%p p_cmpl_cb:%p",
1369d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski                        operation, p_disc_cmpl_cb, p_cmpl_cb);
13705738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
13715738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
13723f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski/** This function cleans up the control blocks when L2CAP channel disconnect */
13739e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskivoid gatt_cleanup_upon_disc(const RawAddress& bda, uint16_t reason,
1374911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson                            tBT_TRANSPORT transport) {
1375d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__;
1376911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
13773f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  tGATT_TCB* p_tcb = gatt_find_tcb_by_addr(bda, transport);
13783f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  if (!p_tcb) return;
1379911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
13803f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  gatt_set_ch_state(p_tcb, GATT_CH_CLOSE);
13813f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  for (uint8_t i = 0; i < GATT_CL_MAX_LCB; i++) {
13823f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski    tGATT_CLCB* p_clcb = &gatt_cb.clcb[i];
13833f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski    if (!p_clcb->in_use || p_clcb->p_tcb != p_tcb) continue;
1384911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
13853f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski    alarm_cancel(p_clcb->gatt_rsp_timer_ent);
1386d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski    VLOG(1) << "found p_clcb conn_id=" << +p_clcb->conn_id;
13873f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski    if (p_clcb->operation == GATTC_OPTYPE_NONE) {
13883f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski      gatt_clcb_dealloc(p_clcb);
13893f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski      continue;
1390911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    }
1391911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
13923f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski    gatt_end_operation(p_clcb, GATT_ERROR, NULL);
13933f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  }
13943f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski
13953f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  alarm_free(p_tcb->ind_ack_timer);
13963f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  p_tcb->ind_ack_timer = NULL;
13973f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  alarm_free(p_tcb->conf_timer);
13983f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  p_tcb->conf_timer = NULL;
13993f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  gatt_free_pending_ind(p_tcb);
14003f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  fixed_queue_free(p_tcb->sr_cmd.multi_rsp_q, NULL);
14013f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  p_tcb->sr_cmd.multi_rsp_q = NULL;
14023f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski
14033f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  for (uint8_t i = 0; i < GATT_MAX_APPS; i++) {
14043f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski    tGATT_REG* p_reg = &gatt_cb.cl_rcb[i];
14053f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski    if (p_reg->in_use && p_reg->app_cb.p_conn_cb) {
14063f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski      uint16_t conn_id = GATT_CREATE_CONN_ID(p_tcb->tcb_idx, p_reg->gatt_if);
1407d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski      VLOG(1) << StringPrintf("found p_reg tcb_idx=%d gatt_if=%d  conn_id=0x%x",
1408d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski                              p_tcb->tcb_idx, p_reg->gatt_if, conn_id);
14093f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski      (*p_reg->app_cb.p_conn_cb)(p_reg->gatt_if, bda, conn_id, false, reason,
14103f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski                                 transport);
1411911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    }
1412911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
14133f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski
14143f177e0addc35bb39b6688d0059592b161a6bac1Jakub Pawlowski  *p_tcb = tGATT_TCB();
1415d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__ << ": exit";
14165738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
14175738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1418ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1419ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_dbg_req_op_name
1420ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1421ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Get op code description name, for debug information.
1422ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1423ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          uint8_t *: name of the operation.
1424ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1425ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1426911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonuint8_t* gatt_dbg_op_name(uint8_t op_code) {
1427911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  uint8_t pseduo_op_code_idx = op_code & (~GATT_WRITE_CMD_MASK);
14285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1429911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (op_code == GATT_CMD_WRITE) {
1430911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    pseduo_op_code_idx = 0x14; /* just an index to op_code_name */
1431911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
14325738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1433911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (op_code == GATT_SIGN_CMD_WRITE) {
1434911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    pseduo_op_code_idx = 0x15; /* just an index to op_code_name */
1435911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
14365738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1437911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (pseduo_op_code_idx <= GATT_OP_CODE_MAX)
1438911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    return (uint8_t*)op_code_name[pseduo_op_code_idx];
1439911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  else
1440911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    return (uint8_t*)"Op Code Exceed Max";
14415738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
14425738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
14435738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1444ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1445ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_dbg_display_uuid
1446ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1447ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      Disaplay the UUID
1448ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1449ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          None
1450ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1451ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1452911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_dbg_display_uuid(tBT_UUID bt_uuid) {
1453911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  char str_buf[50];
14545738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1455911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (bt_uuid.len == LEN_UUID_16) {
1456911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    snprintf(str_buf, sizeof(str_buf), "0x%04x", bt_uuid.uu.uuid16);
1457911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else if (bt_uuid.len == LEN_UUID_32) {
1458911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    snprintf(str_buf, sizeof(str_buf), "0x%08x",
1459911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson             (unsigned int)bt_uuid.uu.uuid32);
1460911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else if (bt_uuid.len == LEN_UUID_128) {
1461911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    int x = snprintf(
1462911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        str_buf, sizeof(str_buf), "0x%02x%02x%02x%02x%02x%02x%02x%02x",
1463911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        bt_uuid.uu.uuid128[15], bt_uuid.uu.uuid128[14], bt_uuid.uu.uuid128[13],
1464911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        bt_uuid.uu.uuid128[12], bt_uuid.uu.uuid128[11], bt_uuid.uu.uuid128[10],
1465911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        bt_uuid.uu.uuid128[9], bt_uuid.uu.uuid128[8]);
1466911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    snprintf(
1467911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        &str_buf[x], sizeof(str_buf) - x, "%02x%02x%02x%02x%02x%02x%02x%02x",
1468911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        bt_uuid.uu.uuid128[7], bt_uuid.uu.uuid128[6], bt_uuid.uu.uuid128[5],
1469911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        bt_uuid.uu.uuid128[4], bt_uuid.uu.uuid128[3], bt_uuid.uu.uuid128[2],
1470911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson        bt_uuid.uu.uuid128[1], bt_uuid.uu.uuid128[0]);
1471911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else
1472911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    strlcpy(str_buf, "Unknown UUID 0", sizeof(str_buf));
14735738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1474d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << StringPrintf("UUID=[%s]", str_buf);
14755738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
14765738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
14777cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski/** Returns true if this is one of the background devices for the application,
14787cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski * false otherwise */
1479911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonbool gatt_is_bg_dev_for_app(tGATT_BG_CONN_DEV* p_dev, tGATT_IF gatt_if) {
14807cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  return p_dev->gatt_if.count(gatt_if);
14815738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
14825738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
14837cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski/** background connection device from the list. Returns pointer to the device
14847cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski * record, or nullptr if not found */
14859e030fde05352ec4385d7baf6cc2af89e95e039cJakub PawlowskitGATT_BG_CONN_DEV* gatt_find_bg_dev(const RawAddress& remote_bda) {
14867cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  for (tGATT_BG_CONN_DEV& dev : gatt_cb.bgconn_dev) {
1487c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski    if (dev.remote_bda == remote_bda) {
14887cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski      return &dev;
14895738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1490911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
14917cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  return nullptr;
14925738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
14935738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1494c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowskistd::list<tGATT_BG_CONN_DEV>::iterator gatt_find_bg_dev_it(
14959e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowski    const RawAddress& remote_bda) {
14967cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  auto& list = gatt_cb.bgconn_dev;
14977cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  for (auto it = list.begin(); it != list.end(); it++) {
1498c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski    if (it->remote_bda == remote_bda) {
14997cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski      return it;
15005738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1501911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
15027cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  return list.end();
15035738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
15045738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
15057cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski/** Add a device from the background connection list.  Returns true if device
15067cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski * added to the list, or already in list, false otherwise */
15079e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskibool gatt_add_bg_dev_list(tGATT_REG* p_reg, const RawAddress& bd_addr) {
1508911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_IF gatt_if = p_reg->gatt_if;
15095738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
15107cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  tGATT_BG_CONN_DEV* p_dev = gatt_find_bg_dev(bd_addr);
1511911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_dev) {
15127cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski    // device already in the whitelist, just add interested app to the list
15137cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski    if (!p_dev->gatt_if.insert(gatt_if).second) {
1514d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski      LOG(ERROR) << "device already in iniator white list";
1515ead3cde4bac0c3e32cd31f149093f004eef8ceebGanesh Ganapathi Batta    }
15167cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski
15177cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski    return true;
1518911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
15197cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  // the device is not in the whitelist
15205738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
15217cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  if (!BTM_BleUpdateBgConnDev(true, bd_addr)) return false;
15227cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski
15237cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  gatt_cb.bgconn_dev.emplace_back();
15247cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  tGATT_BG_CONN_DEV& dev = gatt_cb.bgconn_dev.back();
1525c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowski  dev.remote_bda = bd_addr;
15267cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  dev.gatt_if.insert(gatt_if);
15277cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  return true;
15285738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
15295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
15307cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski/** Remove the application interface for the specified background device */
15319e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskibool gatt_remove_bg_dev_for_app(tGATT_IF gatt_if, const RawAddress& bd_addr) {
1532911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_TCB* p_tcb = gatt_find_tcb_by_addr(bd_addr, BT_TRANSPORT_LE);
1533911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  bool status;
15345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1535911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_tcb) gatt_update_app_use_link_flag(gatt_if, p_tcb, false, false);
1536911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  status = gatt_update_auto_connect_dev(gatt_if, false, bd_addr);
1537911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return status;
15385738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
15395738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
15407cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski/** Removes all registrations for background connection for given device.
15417cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski * Returns true if anything was removed, false otherwise */
15429e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskiuint8_t gatt_clear_bg_dev_for_addr(const RawAddress& bd_addr) {
15437cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  auto dev_it = gatt_find_bg_dev_it(bd_addr);
15447cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  if (dev_it == gatt_cb.bgconn_dev.end()) return false;
15455738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
15467cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  CHECK(BTM_BleUpdateBgConnDev(false, dev_it->remote_bda));
15477cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  gatt_cb.bgconn_dev.erase(dev_it);
15487cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  return true;
15495738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
15505738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
15517cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski/** Remove device from the background connection device list or listening to
15527cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski * advertising list.  Returns true if device was on the list and was succesfully
15537cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski * removed */
15549e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowskibool gatt_remove_bg_dev_from_list(tGATT_REG* p_reg, const RawAddress& bd_addr) {
1555911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_IF gatt_if = p_reg->gatt_if;
15567cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  auto dev_it = gatt_find_bg_dev_it(bd_addr);
15577cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  if (dev_it == gatt_cb.bgconn_dev.end()) return false;
15585738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
15597cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  if (!dev_it->gatt_if.erase(gatt_if)) return false;
15605738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
15617cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  if (!dev_it->gatt_if.empty()) return true;
1562911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson
15637cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  // no more apps interested - remove from whitelist and delete record
15647cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  CHECK(BTM_BleUpdateBgConnDev(false, dev_it->remote_bda));
15657cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  gatt_cb.bgconn_dev.erase(dev_it);
15667cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski  return true;
15675738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
15687cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski/** deregister all related back ground connetion device. */
1569911d1ae03efec2d54c3b1b605589d790d1745488Myles Watsonvoid gatt_deregister_bgdev_list(tGATT_IF gatt_if) {
1570bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski  auto it = gatt_cb.bgconn_dev.begin();
1571bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski  auto end = gatt_cb.bgconn_dev.end();
1572911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* update the BG conn device list */
1573bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski  while (it != end) {
15747cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowski    it->gatt_if.erase(gatt_if);
1575bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski    if (it->gatt_if.size()) {
1576bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski      it++;
1577bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski      continue;
15785738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1579bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski
1580bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski    BTM_BleUpdateBgConnDev(false, it->remote_bda);
1581bb95a1d62243dc3f4ce7c208d68f50cb57713eabJakub Pawlowski    it = gatt_cb.bgconn_dev.erase(it);
1582911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
15835738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
15845738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
15855738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1586ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1587ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_reset_bgdev_list
1588ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1589ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Description      reset bg device list
1590ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1591ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Returns          pointer to the device record
1592ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1593ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
15947cfd8391f6db2d387ea556ca2b7be0a7e4791e5dJakub Pawlowskivoid gatt_reset_bgdev_list(void) { gatt_cb.bgconn_dev.clear(); }
15955738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project/*******************************************************************************
1596ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1597ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Function         gatt_update_auto_connect_dev
1598ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
15999ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Description      This function add or remove a device for background
16009ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson *                  connection procedure.
1601ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1602ee96a3c60fca590d38025925c072d264e06493c4Myles Watson * Parameters       gatt_if: Application ID.
1603ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *                  add: add peer device
1604ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *                  bd_addr: peer device address.
1605ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
16069ca07091a1f07ea201cee0504dab6a1d7073d429Myles Watson * Returns          true if connection started; false otherwise.
1607ee96a3c60fca590d38025925c072d264e06493c4Myles Watson *
1608ee96a3c60fca590d38025925c072d264e06493c4Myles Watson ******************************************************************************/
1609c2276b06572ab6fc1f900fbb1f41087e77d47e2aJakub Pawlowskibool gatt_update_auto_connect_dev(tGATT_IF gatt_if, bool add,
16109e030fde05352ec4385d7baf6cc2af89e95e039cJakub Pawlowski                                  const RawAddress& bd_addr) {
1611911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  bool ret = false;
1612911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_REG* p_reg;
1613911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  tGATT_TCB* p_tcb = gatt_find_tcb_by_addr(bd_addr, BT_TRANSPORT_LE);
16145738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1615d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski  VLOG(1) << __func__;
1616911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  /* Make sure app is registered */
1617911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  p_reg = gatt_get_regcb(gatt_if);
1618911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (p_reg == NULL) {
1619d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski    LOG(ERROR) << __func__ << " gatt_if is not registered " << +gatt_if;
1620d8be0e590aa1efe1c33a8acfea0d7e14fd1a8030Jakub Pawlowski    return false;
1621911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
16225738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1623911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  if (add) {
1624911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    ret = gatt_add_bg_dev_list(p_reg, bd_addr);
16255738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project
1626911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    if (ret && p_tcb != NULL) {
1627911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      /* if a connected device, update the link holding number */
1628911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson      gatt_update_app_use_link_flag(gatt_if, p_tcb, true, true);
16295738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project    }
1630911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  } else {
1631911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson    ret = gatt_remove_bg_dev_from_list(p_reg, bd_addr);
1632911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  }
1633911d1ae03efec2d54c3b1b605589d790d1745488Myles Watson  return ret;
16345738f83aeb59361a0a2eda2460113f6dc919427The Android Open Source Project}
1635