1 /******************************************************************************
2 *
3 * Copyright 2003-2012 Broadcom Corporation
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 ******************************************************************************/
18
19 /******************************************************************************
20 *
21 * This file contains the GATT client utility function.
22 *
23 ******************************************************************************/
24
25 #include <cstdint>
26
27 #include "bt_target.h" // Must be first to define build configuration
28
29 #include "bta/gatt/bta_gatts_int.h"
30
31 /*******************************************************************************
32 *
33 * Function bta_gatts_alloc_srvc_cb
34 *
35 * Description allocate a service control block.
36 *
37 * Returns pointer to the control block, or otherwise NULL when failed.
38 *
39 ******************************************************************************/
bta_gatts_alloc_srvc_cb(tBTA_GATTS_CB * p_cb,uint8_t rcb_idx)40 uint8_t bta_gatts_alloc_srvc_cb(tBTA_GATTS_CB* p_cb, uint8_t rcb_idx) {
41 uint8_t i;
42
43 for (i = 0; i < BTA_GATTS_MAX_SRVC_NUM; i++) {
44 if (!p_cb->srvc_cb[i].in_use) {
45 p_cb->srvc_cb[i].in_use = true;
46 p_cb->srvc_cb[i].rcb_idx = rcb_idx;
47 return i;
48 }
49 }
50 return BTA_GATTS_INVALID_APP;
51 }
52
53 /*******************************************************************************
54 *
55 * Function bta_gatts_find_app_rcb_by_app_if
56 *
57 * Description find the index of the application control block by app ID.
58 *
59 * Returns pointer to the control block if success, otherwise NULL
60 *
61 ******************************************************************************/
bta_gatts_find_app_rcb_by_app_if(tGATT_IF server_if)62 tBTA_GATTS_RCB* bta_gatts_find_app_rcb_by_app_if(tGATT_IF server_if) {
63 uint8_t i;
64 tBTA_GATTS_RCB* p_reg;
65
66 for (i = 0, p_reg = bta_gatts_cb.rcb; i < BTA_GATTS_MAX_APP_NUM;
67 i++, p_reg++) {
68 if (p_reg->in_use && p_reg->gatt_if == server_if) return p_reg;
69 }
70 return NULL;
71 }
72
73 /*******************************************************************************
74 *
75 * Function bta_gatts_find_app_rcb_idx_by_app_if
76 *
77 * Description find the index of the application control block by app ID.
78 *
79 * Returns index of the control block, or BTA_GATTS_INVALID_APP if
80 * failed.
81 *
82 ******************************************************************************/
83
bta_gatts_find_app_rcb_idx_by_app_if(tBTA_GATTS_CB * p_cb,tGATT_IF server_if)84 uint8_t bta_gatts_find_app_rcb_idx_by_app_if(tBTA_GATTS_CB* p_cb,
85 tGATT_IF server_if) {
86 uint8_t i;
87
88 for (i = 0; i < BTA_GATTS_MAX_APP_NUM; i++) {
89 if (p_cb->rcb[i].in_use && p_cb->rcb[i].gatt_if == server_if) return i;
90 }
91 return BTA_GATTS_INVALID_APP;
92 }
93 /*******************************************************************************
94 *
95 * Function bta_gatts_find_srvc_cb_by_srvc_id
96 *
97 * Description find the service control block by service ID.
98 *
99 * Returns pointer to the rcb.
100 *
101 ******************************************************************************/
bta_gatts_find_srvc_cb_by_srvc_id(tBTA_GATTS_CB * p_cb,uint16_t service_id)102 tBTA_GATTS_SRVC_CB* bta_gatts_find_srvc_cb_by_srvc_id(tBTA_GATTS_CB* p_cb,
103 uint16_t service_id) {
104 uint8_t i;
105 VLOG(1) << __func__ << ": service_id=" << +service_id;
106 for (i = 0; i < BTA_GATTS_MAX_SRVC_NUM; i++) {
107 if (p_cb->srvc_cb[i].in_use && p_cb->srvc_cb[i].service_id == service_id) {
108 VLOG(1) << __func__ << ": found service cb index=" << +i;
109 return &p_cb->srvc_cb[i];
110 }
111 }
112 return NULL;
113 }
114 /*******************************************************************************
115 *
116 * Function bta_gatts_find_srvc_cb_by_attr_id
117 *
118 * Description find the service control block by attribute ID.
119 *
120 * Returns pointer to the rcb.
121 *
122 ******************************************************************************/
bta_gatts_find_srvc_cb_by_attr_id(tBTA_GATTS_CB * p_cb,uint16_t attr_id)123 tBTA_GATTS_SRVC_CB* bta_gatts_find_srvc_cb_by_attr_id(tBTA_GATTS_CB* p_cb,
124 uint16_t attr_id) {
125 uint8_t i;
126
127 for (i = 0; i < (BTA_GATTS_MAX_SRVC_NUM); i++) {
128 if (/* middle service */
129 (i < (BTA_GATTS_MAX_SRVC_NUM - 1) && p_cb->srvc_cb[i].in_use &&
130 p_cb->srvc_cb[i + 1].in_use &&
131 attr_id >= p_cb->srvc_cb[i].service_id &&
132 attr_id < p_cb->srvc_cb[i + 1].service_id) ||
133 /* last active service */
134 (i < (BTA_GATTS_MAX_SRVC_NUM - 1) && p_cb->srvc_cb[i].in_use &&
135 !p_cb->srvc_cb[i + 1].in_use &&
136 attr_id >= p_cb->srvc_cb[i].service_id) ||
137 /* last service incb */
138 (i == (BTA_GATTS_MAX_SRVC_NUM - 1) &&
139 attr_id >= p_cb->srvc_cb[i].service_id)) {
140 return &p_cb->srvc_cb[i];
141 }
142 }
143 return NULL;
144 }
145