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