1 /* 2 * Copyright (C) 2014 BlueKitchen GmbH 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 3. Neither the name of the copyright holders nor the names of 14 * contributors may be used to endorse or promote products derived 15 * from this software without specific prior written permission. 16 * 4. Any redistribution, use, or modification is done solely for 17 * personal benefit and not for any commercial purpose or for 18 * monetary gain. 19 * 20 * THIS SOFTWARE IS PROVIDED BY BLUEKITCHEN GMBH AND CONTRIBUTORS 21 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 22 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 23 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL BLUEKITCHEN 24 * GMBH OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 25 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 26 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS 27 * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 28 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 29 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF 30 * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 31 * SUCH DAMAGE. 32 * 33 * Please inquire about commercial licensing options at 34 * [email protected] 35 * 36 */ 37 38 #define BTSTACK_FILE__ "gatt_client.c" 39 40 #include <stdint.h> 41 #include <string.h> 42 #include <stddef.h> 43 44 #include "btstack_config.h" 45 46 #include "ble/att_dispatch.h" 47 #include "ble/att_db.h" 48 #include "ble/gatt_client.h" 49 #include "ble/le_device_db.h" 50 #include "ble/sm.h" 51 #include "bluetooth_psm.h" 52 #include "btstack_debug.h" 53 #include "btstack_event.h" 54 #include "btstack_memory.h" 55 #include "btstack_run_loop.h" 56 #include "btstack_util.h" 57 #include "hci.h" 58 #include "hci_dump.h" 59 #include "hci_event_builder.h" 60 #include "l2cap.h" 61 #include "classic/sdp_client.h" 62 #include "bluetooth_gatt.h" 63 #include "bluetooth_sdp.h" 64 #include "classic/sdp_util.h" 65 66 #if defined(ENABLE_GATT_OVER_EATT) && !defined(ENABLE_L2CAP_ENHANCED_CREDIT_BASED_FLOW_CONTROL_MODE) 67 #error "GATT Over EATT requires support for L2CAP Enhanced CoC. Please enable ENABLE_L2CAP_ENHANCED_CREDIT_BASED_FLOW_CONTROL_MODE" 68 #endif 69 70 // L2CAP Test Spec p35 defines a minimum of 100 ms, but PTS might indicate an error if we sent after 100 ms 71 #define GATT_CLIENT_COLLISION_BACKOFF_MS 150 72 73 static btstack_linked_list_t gatt_client_connections; 74 static btstack_linked_list_t gatt_client_value_listeners; 75 static btstack_linked_list_t gatt_client_service_value_listeners; 76 #ifdef ENABLE_GATT_CLIENT_SERVICE_CHANGED 77 static btstack_linked_list_t gatt_client_service_changed_handler; 78 #endif 79 static btstack_packet_callback_registration_t hci_event_callback_registration; 80 static btstack_packet_callback_registration_t sm_event_callback_registration; 81 static btstack_context_callback_registration_t gatt_client_deferred_event_emit; 82 83 // GATT Client Configuration 84 static bool gatt_client_mtu_exchange_enabled; 85 static gap_security_level_t gatt_client_required_security_level; 86 87 static void gatt_client_att_packet_handler(uint8_t packet_type, uint16_t handle, uint8_t *packet, uint16_t size); 88 static void gatt_client_event_packet_handler(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size); 89 static void gatt_client_report_error_if_pending(gatt_client_t *gatt_client, uint8_t att_error_code); 90 91 #ifdef ENABLE_LE_SIGNED_WRITE 92 static void att_signed_write_handle_cmac_result(uint8_t hash[8]); 93 #endif 94 95 #ifdef ENABLE_GATT_OVER_CLASSIC 96 static gatt_client_t * gatt_client_get_context_for_l2cap_cid(uint16_t l2cap_cid); 97 static void gatt_client_classic_handle_connected(gatt_client_t * gatt_client, uint8_t status); 98 static void gatt_client_classic_handle_disconnected(gatt_client_t * gatt_client); 99 static void gatt_client_classic_retry(btstack_timer_source_t * ts); 100 #endif 101 102 #ifdef ENABLE_GATT_OVER_EATT 103 static bool gatt_client_le_enhanced_handle_can_send_query(gatt_client_t * gatt_client); 104 static void gatt_client_le_enhanced_retry(btstack_timer_source_t * ts); 105 #endif 106 107 void gatt_client_init(void){ 108 gatt_client_connections = NULL; 109 gatt_client_value_listeners = NULL; 110 gatt_client_service_value_listeners = NULL; 111 #ifdef ENABLE_GATT_CLIENT_SERVICE_CHANGED 112 gatt_client_service_changed_handler = NULL; 113 #endif 114 // default configuration 115 gatt_client_mtu_exchange_enabled = true; 116 gatt_client_required_security_level = LEVEL_0; 117 118 // register for HCI Events 119 hci_event_callback_registration.callback = &gatt_client_event_packet_handler; 120 hci_add_event_handler(&hci_event_callback_registration); 121 122 // register for SM Events 123 sm_event_callback_registration.callback = &gatt_client_event_packet_handler; 124 sm_add_event_handler(&sm_event_callback_registration); 125 126 // and ATT Client PDUs 127 att_dispatch_register_client(gatt_client_att_packet_handler); 128 } 129 130 void gatt_client_set_required_security_level(gap_security_level_t level){ 131 gatt_client_required_security_level = level; 132 } 133 134 static gatt_client_t * gatt_client_for_timer(btstack_timer_source_t * ts){ 135 btstack_linked_list_iterator_t it; 136 btstack_linked_list_iterator_init(&it, &gatt_client_connections); 137 while (btstack_linked_list_iterator_has_next(&it)){ 138 gatt_client_t * gatt_client = (gatt_client_t *) btstack_linked_list_iterator_next(&it); 139 if (&gatt_client->gc_timeout == ts) { 140 return gatt_client; 141 } 142 } 143 return NULL; 144 } 145 146 static void gatt_client_timeout_handler(btstack_timer_source_t * timer){ 147 gatt_client_t * gatt_client = gatt_client_for_timer(timer); 148 if (gatt_client == NULL) return; 149 log_info("GATT client timeout handle, handle 0x%02x", gatt_client->con_handle); 150 gatt_client_report_error_if_pending(gatt_client, ATT_ERROR_TIMEOUT); 151 } 152 153 static void gatt_client_timeout_start(gatt_client_t * gatt_client){ 154 log_debug("GATT client timeout start, handle 0x%02x", gatt_client->con_handle); 155 btstack_run_loop_remove_timer(&gatt_client->gc_timeout); 156 btstack_run_loop_set_timer_handler(&gatt_client->gc_timeout, gatt_client_timeout_handler); 157 btstack_run_loop_set_timer(&gatt_client->gc_timeout, 30000); // 30 seconds sm timeout 158 btstack_run_loop_add_timer(&gatt_client->gc_timeout); 159 } 160 161 static void gatt_client_timeout_stop(gatt_client_t * gatt_client){ 162 log_debug("GATT client timeout stop, handle 0x%02x", gatt_client->con_handle); 163 btstack_run_loop_remove_timer(&gatt_client->gc_timeout); 164 } 165 166 static gap_security_level_t gatt_client_le_security_level_for_connection(hci_con_handle_t con_handle){ 167 uint8_t encryption_key_size = gap_encryption_key_size(con_handle); 168 if (encryption_key_size == 0) return LEVEL_0; 169 170 bool authenticated = gap_authenticated(con_handle); 171 if (!authenticated) return LEVEL_2; 172 173 return encryption_key_size == 16 ? LEVEL_4 : LEVEL_3; 174 } 175 176 static gatt_client_t * gatt_client_get_context_for_handle(uint16_t handle){ 177 btstack_linked_item_t *it; 178 for (it = (btstack_linked_item_t *) gatt_client_connections; it != NULL; it = it->next){ 179 gatt_client_t * gatt_client = (gatt_client_t *) it; 180 if (gatt_client->con_handle == handle){ 181 return gatt_client; 182 } 183 } 184 return NULL; 185 } 186 187 188 // @return gatt_client context 189 // returns existing one, or tries to setup new one 190 static uint8_t gatt_client_provide_context_for_handle(hci_con_handle_t con_handle, gatt_client_t ** out_gatt_client){ 191 gatt_client_t * gatt_client = gatt_client_get_context_for_handle(con_handle); 192 193 if (gatt_client != NULL){ 194 *out_gatt_client = gatt_client; 195 return ERROR_CODE_SUCCESS; 196 } 197 198 // bail if no such hci connection 199 hci_connection_t * hci_connection = hci_connection_for_handle(con_handle); 200 if (hci_connection == NULL){ 201 log_error("No connection for handle 0x%04x", con_handle); 202 *out_gatt_client = NULL; 203 return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER; 204 } 205 206 gatt_client = btstack_memory_gatt_client_get(); 207 if (gatt_client == NULL){ 208 *out_gatt_client = NULL; 209 return ERROR_CODE_MEMORY_CAPACITY_EXCEEDED; 210 } 211 // init state 212 gatt_client->bearer_type = ATT_BEARER_UNENHANCED_LE; 213 gatt_client->con_handle = con_handle; 214 gatt_client->mtu = ATT_DEFAULT_MTU; 215 gatt_client->security_level = gatt_client_le_security_level_for_connection(con_handle); 216 if (gatt_client_mtu_exchange_enabled){ 217 gatt_client->mtu_state = SEND_MTU_EXCHANGE; 218 } else { 219 gatt_client->mtu_state = MTU_AUTO_EXCHANGE_DISABLED; 220 } 221 gatt_client->state = P_READY; 222 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_DISCOVER_W2_SEND; 223 #ifdef ENABLE_GATT_OVER_EATT 224 gatt_client->eatt_state = GATT_CLIENT_EATT_IDLE; 225 #endif 226 btstack_linked_list_add(&gatt_client_connections, (btstack_linked_item_t*)gatt_client); 227 228 // get unenhanced att bearer state 229 if (hci_connection->att_connection.mtu_exchanged){ 230 gatt_client->mtu = hci_connection->att_connection.mtu; 231 gatt_client->mtu_state = MTU_EXCHANGED; 232 } 233 *out_gatt_client = gatt_client; 234 return ERROR_CODE_SUCCESS; 235 } 236 237 static bool is_ready(gatt_client_t * gatt_client){ 238 return gatt_client->state == P_READY; 239 } 240 241 static uint8_t gatt_client_provide_context_for_request(hci_con_handle_t con_handle, gatt_client_t ** out_gatt_client){ 242 gatt_client_t * gatt_client = NULL; 243 uint8_t status = gatt_client_provide_context_for_handle(con_handle, &gatt_client); 244 if (status != ERROR_CODE_SUCCESS){ 245 return status; 246 } 247 248 #ifdef ENABLE_GATT_OVER_EATT 249 if (gatt_client->eatt_state == GATT_CLIENT_EATT_READY){ 250 btstack_linked_list_iterator_t it; 251 gatt_client_t * eatt_client = NULL; 252 // find free eatt client 253 btstack_linked_list_iterator_init(&it, &gatt_client->eatt_clients); 254 while (btstack_linked_list_iterator_has_next(&it)){ 255 gatt_client_t * client = (gatt_client_t *) btstack_linked_list_iterator_next(&it); 256 if (client->state == P_READY){ 257 eatt_client = client; 258 break; 259 } 260 } 261 if (eatt_client == NULL){ 262 return ERROR_CODE_COMMAND_DISALLOWED; 263 } 264 gatt_client = eatt_client; 265 } 266 #endif 267 268 if (is_ready(gatt_client) == false){ 269 return GATT_CLIENT_IN_WRONG_STATE; 270 } 271 272 gatt_client_timeout_start(gatt_client); 273 274 *out_gatt_client = gatt_client; 275 276 return status; 277 } 278 279 int gatt_client_is_ready(hci_con_handle_t con_handle){ 280 gatt_client_t * gatt_client; 281 uint8_t status = gatt_client_provide_context_for_handle(con_handle, &gatt_client); 282 if (status != ERROR_CODE_SUCCESS){ 283 return 0; 284 } 285 return is_ready(gatt_client) ? 1 : 0; 286 } 287 288 void gatt_client_mtu_enable_auto_negotiation(uint8_t enabled){ 289 gatt_client_mtu_exchange_enabled = enabled != 0; 290 } 291 292 uint8_t gatt_client_get_mtu(hci_con_handle_t con_handle, uint16_t * mtu){ 293 gatt_client_t * gatt_client; 294 uint8_t status = gatt_client_provide_context_for_handle(con_handle, &gatt_client); 295 if (status != ERROR_CODE_SUCCESS){ 296 *mtu = 0; 297 return status; 298 } 299 300 if ((gatt_client->mtu_state == MTU_EXCHANGED) || (gatt_client->mtu_state == MTU_AUTO_EXCHANGE_DISABLED)){ 301 *mtu = gatt_client->mtu; 302 return ERROR_CODE_SUCCESS; 303 } 304 *mtu = ATT_DEFAULT_MTU; 305 return GATT_CLIENT_IN_WRONG_STATE; 306 } 307 308 static uint8_t *gatt_client_reserve_request_buffer(gatt_client_t *gatt_client) { 309 switch (gatt_client->bearer_type){ 310 #ifdef ENABLE_GATT_OVER_CLASSIC 311 case ATT_BEARER_UNENHANCED_CLASSIC: 312 #endif 313 case ATT_BEARER_UNENHANCED_LE: 314 l2cap_reserve_packet_buffer(); 315 return l2cap_get_outgoing_buffer(); 316 #ifdef ENABLE_GATT_OVER_EATT 317 case ATT_BEARER_ENHANCED_LE: 318 return gatt_client->eatt_storage_buffer; 319 #endif 320 default: 321 btstack_unreachable(); 322 break; 323 } 324 return NULL; 325 } 326 327 // precondition: can_send_packet_now == TRUE 328 static uint8_t gatt_client_send(gatt_client_t * gatt_client, uint16_t len){ 329 switch (gatt_client->bearer_type){ 330 case ATT_BEARER_UNENHANCED_LE: 331 return l2cap_send_prepared_connectionless(gatt_client->con_handle, L2CAP_CID_ATTRIBUTE_PROTOCOL, len); 332 #ifdef ENABLE_GATT_OVER_CLASSIC 333 case ATT_BEARER_UNENHANCED_CLASSIC: 334 return l2cap_send_prepared(gatt_client->l2cap_cid, len); 335 #endif 336 #ifdef ENABLE_GATT_OVER_EATT 337 case ATT_BEARER_ENHANCED_LE: 338 return l2cap_send(gatt_client->l2cap_cid, gatt_client->eatt_storage_buffer, len); 339 #endif 340 default: 341 btstack_unreachable(); 342 return ERROR_CODE_HARDWARE_FAILURE; 343 } 344 } 345 346 // precondition: can_send_packet_now == TRUE 347 static uint8_t att_confirmation(gatt_client_t * gatt_client) { 348 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 349 350 request[0] = ATT_HANDLE_VALUE_CONFIRMATION; 351 352 return gatt_client_send(gatt_client, 1); 353 } 354 355 // precondition: can_send_packet_now == TRUE 356 static uint8_t att_find_information_request(gatt_client_t *gatt_client, uint8_t request_type, uint16_t start_handle, 357 uint16_t end_handle) { 358 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 359 360 request[0] = request_type; 361 little_endian_store_16(request, 1, start_handle); 362 little_endian_store_16(request, 3, end_handle); 363 364 return gatt_client_send(gatt_client, 5); 365 } 366 367 // precondition: can_send_packet_now == TRUE 368 static uint8_t 369 att_find_by_type_value_request(gatt_client_t *gatt_client, uint8_t request_type, uint16_t attribute_group_type, 370 uint16_t start_handle, uint16_t end_handle, uint8_t *value, uint16_t value_size) { 371 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 372 request[0] = request_type; 373 374 little_endian_store_16(request, 1, start_handle); 375 little_endian_store_16(request, 3, end_handle); 376 little_endian_store_16(request, 5, attribute_group_type); 377 (void)memcpy(&request[7], value, value_size); 378 379 return gatt_client_send(gatt_client, 7u + value_size); 380 } 381 382 // precondition: can_send_packet_now == TRUE 383 static uint8_t 384 att_read_by_type_or_group_request_for_uuid16(gatt_client_t *gatt_client, uint8_t request_type, uint16_t uuid16, 385 uint16_t start_handle, uint16_t end_handle) { 386 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 387 388 request[0] = request_type; 389 little_endian_store_16(request, 1, start_handle); 390 little_endian_store_16(request, 3, end_handle); 391 little_endian_store_16(request, 5, uuid16); 392 393 return gatt_client_send(gatt_client, 7); 394 } 395 396 // precondition: can_send_packet_now == TRUE 397 static uint8_t 398 att_read_by_type_or_group_request_for_uuid128(gatt_client_t *gatt_client, uint8_t request_type, const uint8_t *uuid128, 399 uint16_t start_handle, uint16_t end_handle) { 400 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 401 402 request[0] = request_type; 403 little_endian_store_16(request, 1, start_handle); 404 little_endian_store_16(request, 3, end_handle); 405 reverse_128(uuid128, &request[5]); 406 407 return gatt_client_send(gatt_client, 21); 408 } 409 410 // precondition: can_send_packet_now == TRUE 411 static uint8_t att_read_request(gatt_client_t *gatt_client, uint8_t request_type, uint16_t attribute_handle) { 412 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 413 414 request[0] = request_type; 415 little_endian_store_16(request, 1, attribute_handle); 416 417 return gatt_client_send(gatt_client, 3); 418 } 419 420 // precondition: can_send_packet_now == TRUE 421 static uint8_t att_read_blob_request(gatt_client_t *gatt_client, uint8_t request_type, uint16_t attribute_handle, 422 uint16_t value_offset) { 423 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 424 425 request[0] = request_type; 426 little_endian_store_16(request, 1, attribute_handle); 427 little_endian_store_16(request, 3, value_offset); 428 429 return gatt_client_send(gatt_client, 5); 430 } 431 432 static uint8_t 433 att_read_multiple_request_with_opcode(gatt_client_t *gatt_client, uint16_t num_value_handles, uint16_t *value_handles, uint8_t opcode) { 434 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 435 436 request[0] = opcode; 437 uint16_t i; 438 uint16_t offset = 1; 439 for (i=0;i<num_value_handles;i++){ 440 little_endian_store_16(request, offset, value_handles[i]); 441 offset += 2; 442 } 443 444 return gatt_client_send(gatt_client, offset); 445 } 446 447 static uint8_t 448 att_read_multiple_request(gatt_client_t *gatt_client, uint16_t num_value_handles, uint16_t *value_handles) { 449 return att_read_multiple_request_with_opcode(gatt_client, num_value_handles, value_handles, ATT_READ_MULTIPLE_REQUEST); 450 } 451 452 #ifdef ENABLE_GATT_OVER_EATT 453 static uint8_t 454 att_read_multiple_variable_request(gatt_client_t *gatt_client, uint16_t num_value_handles, uint16_t *value_handles) { 455 return att_read_multiple_request_with_opcode(gatt_client, num_value_handles, value_handles, ATT_READ_MULTIPLE_VARIABLE_REQ); 456 } 457 #endif 458 459 #ifdef ENABLE_LE_SIGNED_WRITE 460 // precondition: can_send_packet_now == TRUE 461 static uint8_t att_signed_write_request(gatt_client_t *gatt_client, uint16_t request_type, uint16_t attribute_handle, 462 uint16_t value_length, uint8_t *value, uint32_t sign_counter, uint8_t sgn[8]) { 463 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 464 465 request[0] = request_type; 466 little_endian_store_16(request, 1, attribute_handle); 467 (void)memcpy(&request[3], value, value_length); 468 little_endian_store_32(request, 3 + value_length, sign_counter); 469 reverse_64(sgn, &request[3 + value_length + 4]); 470 471 return gatt_client_send(gatt_client, 3 + value_length + 12); 472 } 473 #endif 474 475 // precondition: can_send_packet_now == TRUE 476 static uint8_t 477 att_write_request(gatt_client_t *gatt_client, uint8_t request_type, uint16_t attribute_handle, uint16_t value_length, 478 uint8_t *value) { 479 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 480 481 request[0] = request_type; 482 little_endian_store_16(request, 1, attribute_handle); 483 (void)memcpy(&request[3], value, value_length); 484 485 return gatt_client_send(gatt_client, 3u + value_length); 486 } 487 488 // precondition: can_send_packet_now == TRUE 489 static uint8_t att_execute_write_request(gatt_client_t *gatt_client, uint8_t request_type, uint8_t execute_write) { 490 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 491 492 request[0] = request_type; 493 request[1] = execute_write; 494 495 return gatt_client_send(gatt_client, 2); 496 } 497 498 // precondition: can_send_packet_now == TRUE 499 static uint8_t att_prepare_write_request(gatt_client_t *gatt_client, uint8_t request_type, uint16_t attribute_handle, 500 uint16_t value_offset, uint16_t blob_length, uint8_t *value) { 501 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 502 503 request[0] = request_type; 504 little_endian_store_16(request, 1, attribute_handle); 505 little_endian_store_16(request, 3, value_offset); 506 (void)memcpy(&request[5], &value[value_offset], blob_length); 507 508 return gatt_client_send(gatt_client, 5u + blob_length); 509 } 510 511 static uint8_t att_exchange_mtu_request(gatt_client_t *gatt_client) { 512 uint8_t *request = gatt_client_reserve_request_buffer(gatt_client); 513 514 request[0] = ATT_EXCHANGE_MTU_REQUEST; 515 uint16_t mtu = l2cap_max_le_mtu(); 516 little_endian_store_16(request, 1, mtu); 517 518 return gatt_client_send(gatt_client, 3); 519 } 520 521 static uint16_t write_blob_length(gatt_client_t * gatt_client){ 522 uint16_t max_blob_length = gatt_client->mtu - 5u; 523 if (gatt_client->attribute_offset >= gatt_client->attribute_length) { 524 return 0; 525 } 526 uint16_t rest_length = gatt_client->attribute_length - gatt_client->attribute_offset; 527 if (max_blob_length > rest_length){ 528 return rest_length; 529 } 530 return max_blob_length; 531 } 532 533 static void send_gatt_services_request(gatt_client_t *gatt_client){ 534 att_read_by_type_or_group_request_for_uuid16(gatt_client, ATT_READ_BY_GROUP_TYPE_REQUEST, 535 gatt_client->uuid16, gatt_client->start_group_handle, 536 gatt_client->end_group_handle); 537 } 538 539 static void send_gatt_by_uuid_request(gatt_client_t *gatt_client, uint16_t attribute_group_type){ 540 if (gatt_client->uuid16 != 0u){ 541 uint8_t uuid16[2]; 542 little_endian_store_16(uuid16, 0, gatt_client->uuid16); 543 att_find_by_type_value_request(gatt_client, ATT_FIND_BY_TYPE_VALUE_REQUEST, attribute_group_type, 544 gatt_client->start_group_handle, gatt_client->end_group_handle, uuid16, 2); 545 return; 546 } 547 uint8_t uuid128[16]; 548 reverse_128(gatt_client->uuid128, uuid128); 549 att_find_by_type_value_request(gatt_client, ATT_FIND_BY_TYPE_VALUE_REQUEST, attribute_group_type, 550 gatt_client->start_group_handle, gatt_client->end_group_handle, uuid128, 16); 551 } 552 553 static void send_gatt_services_by_uuid_request(gatt_client_t *gatt_client){ 554 send_gatt_by_uuid_request(gatt_client, GATT_PRIMARY_SERVICE_UUID); 555 } 556 557 static void send_gatt_included_service_uuid_request(gatt_client_t *gatt_client){ 558 att_read_request(gatt_client, ATT_READ_REQUEST, gatt_client->query_start_handle); 559 } 560 561 static void send_gatt_included_service_request(gatt_client_t *gatt_client){ 562 att_read_by_type_or_group_request_for_uuid16(gatt_client, ATT_READ_BY_TYPE_REQUEST, 563 GATT_INCLUDE_SERVICE_UUID, gatt_client->start_group_handle, 564 gatt_client->end_group_handle); 565 } 566 567 static void send_gatt_characteristic_request(gatt_client_t *gatt_client){ 568 att_read_by_type_or_group_request_for_uuid16(gatt_client, ATT_READ_BY_TYPE_REQUEST, 569 GATT_CHARACTERISTICS_UUID, gatt_client->start_group_handle, 570 gatt_client->end_group_handle); 571 } 572 573 static void send_gatt_characteristic_descriptor_request(gatt_client_t *gatt_client){ 574 att_find_information_request(gatt_client, ATT_FIND_INFORMATION_REQUEST, gatt_client->start_group_handle, 575 gatt_client->end_group_handle); 576 } 577 578 static void send_gatt_read_characteristic_value_request(gatt_client_t *gatt_client){ 579 att_read_request(gatt_client, ATT_READ_REQUEST, gatt_client->attribute_handle); 580 } 581 582 static void send_gatt_read_by_type_request(gatt_client_t * gatt_client){ 583 if (gatt_client->uuid16 != 0u){ 584 att_read_by_type_or_group_request_for_uuid16(gatt_client, ATT_READ_BY_TYPE_REQUEST, 585 gatt_client->uuid16, gatt_client->start_group_handle, 586 gatt_client->end_group_handle); 587 } else { 588 att_read_by_type_or_group_request_for_uuid128(gatt_client, ATT_READ_BY_TYPE_REQUEST, 589 gatt_client->uuid128, gatt_client->start_group_handle, 590 gatt_client->end_group_handle); 591 } 592 } 593 594 static void send_gatt_read_blob_request(gatt_client_t *gatt_client){ 595 if (gatt_client->attribute_offset == 0){ 596 att_read_request(gatt_client, ATT_READ_REQUEST, gatt_client->attribute_handle); 597 } else { 598 att_read_blob_request(gatt_client, ATT_READ_BLOB_REQUEST, gatt_client->attribute_handle, 599 gatt_client->attribute_offset); 600 } 601 } 602 603 static void send_gatt_read_multiple_request(gatt_client_t * gatt_client){ 604 att_read_multiple_request(gatt_client, gatt_client->read_multiple_handle_count, gatt_client->read_multiple_handles); 605 } 606 607 #ifdef ENABLE_GATT_OVER_EATT 608 static void send_gatt_read_multiple_variable_request(gatt_client_t * gatt_client){ 609 att_read_multiple_variable_request(gatt_client, gatt_client->read_multiple_handle_count, gatt_client->read_multiple_handles); 610 } 611 #endif 612 613 static void send_gatt_write_attribute_value_request(gatt_client_t * gatt_client){ 614 att_write_request(gatt_client, ATT_WRITE_REQUEST, gatt_client->attribute_handle, gatt_client->attribute_length, 615 gatt_client->attribute_value); 616 } 617 618 static void send_gatt_write_client_characteristic_configuration_request(gatt_client_t * gatt_client){ 619 att_write_request(gatt_client, ATT_WRITE_REQUEST, gatt_client->client_characteristic_configuration_handle, 2, 620 gatt_client->client_characteristic_configuration_value); 621 } 622 623 static void send_gatt_prepare_write_request(gatt_client_t * gatt_client){ 624 att_prepare_write_request(gatt_client, ATT_PREPARE_WRITE_REQUEST, gatt_client->attribute_handle, 625 gatt_client->attribute_offset, write_blob_length(gatt_client), 626 gatt_client->attribute_value); 627 } 628 629 static void send_gatt_execute_write_request(gatt_client_t * gatt_client){ 630 att_execute_write_request(gatt_client, ATT_EXECUTE_WRITE_REQUEST, 1); 631 } 632 633 static void send_gatt_cancel_prepared_write_request(gatt_client_t * gatt_client){ 634 att_execute_write_request(gatt_client, ATT_EXECUTE_WRITE_REQUEST, 0); 635 } 636 637 #ifndef ENABLE_GATT_FIND_INFORMATION_FOR_CCC_DISCOVERY 638 static void send_gatt_read_client_characteristic_configuration_request(gatt_client_t * gatt_client){ 639 att_read_by_type_or_group_request_for_uuid16(gatt_client, ATT_READ_BY_TYPE_REQUEST, 640 GATT_CLIENT_CHARACTERISTICS_CONFIGURATION, 641 gatt_client->start_group_handle, gatt_client->end_group_handle); 642 } 643 #endif 644 645 static void send_gatt_read_characteristic_descriptor_request(gatt_client_t * gatt_client){ 646 att_read_request(gatt_client, ATT_READ_REQUEST, gatt_client->attribute_handle); 647 } 648 649 #ifdef ENABLE_LE_SIGNED_WRITE 650 static void send_gatt_signed_write_request(gatt_client_t * gatt_client, uint32_t sign_counter){ 651 att_signed_write_request(gatt_client, ATT_SIGNED_WRITE_COMMAND, gatt_client->attribute_handle, 652 gatt_client->attribute_length, gatt_client->attribute_value, sign_counter, 653 gatt_client->cmac); 654 } 655 #endif 656 657 static uint16_t get_last_result_handle_from_service_list(uint8_t * packet, uint16_t size){ 658 if (size < 2) return 0xffff; 659 uint8_t attr_length = packet[1]; 660 if ((2 + attr_length) > size) return 0xffff; 661 return little_endian_read_16(packet, size - attr_length + 2u); 662 } 663 664 static uint16_t get_last_result_handle_from_characteristics_list(uint8_t * packet, uint16_t size){ 665 if (size < 2) return 0xffff; 666 uint8_t attr_length = packet[1]; 667 if ((2 + attr_length) > size) return 0xffff; 668 return little_endian_read_16(packet, size - attr_length + 3u); 669 } 670 671 static uint16_t get_last_result_handle_from_included_services_list(uint8_t * packet, uint16_t size){ 672 if (size < 2) return 0xffff; 673 uint8_t attr_length = packet[1]; 674 if ((2 + attr_length) > size) return 0xffff; 675 return little_endian_read_16(packet, size - attr_length); 676 } 677 678 #ifdef ENABLE_GATT_CLIENT_SERVICE_CHANGED 679 static void gatt_client_service_emit_event(gatt_client_t * gatt_client, uint8_t * event, uint16_t size){ 680 btstack_linked_list_iterator_t it; 681 btstack_linked_list_iterator_init(&it, &gatt_client_service_changed_handler); 682 while (btstack_linked_list_iterator_has_next(&it)) { 683 btstack_packet_callback_registration_t *callback = (btstack_packet_callback_registration_t *) btstack_linked_list_iterator_next(&it); 684 (*callback->callback)(HCI_EVENT_PACKET, (uint16_t) gatt_client->con_handle, event, size); 685 } 686 } 687 688 static void 689 gatt_client_service_emit_database_hash(gatt_client_t *gatt_client, const uint8_t *value, uint16_t value_len) { 690 if (value_len == 16){ 691 uint8_t event[21]; 692 hci_event_builder_context_t context; 693 hci_event_builder_init(&context, event, sizeof(event), HCI_EVENT_GATTSERVICE_META, GATTSERVICE_SUBEVENT_GATT_DATABASE_HASH); 694 hci_event_builder_add_con_handle(&context, gatt_client->con_handle); 695 hci_event_builder_add_bytes(&context, value, 16); 696 gatt_client_service_emit_event(gatt_client, event, hci_event_builder_get_length(&context)); 697 } 698 } 699 700 static void 701 gatt_client_service_emit_service_changed(gatt_client_t *gatt_client, const uint8_t *value, uint16_t value_len) { 702 if (value_len == 4){ 703 uint8_t event[9]; 704 hci_event_builder_context_t context; 705 hci_event_builder_init(&context, event, sizeof(event), HCI_EVENT_GATTSERVICE_META, GATTSERVICE_SUBEVENT_GATT_SERVICE_CHANGED); 706 hci_event_builder_add_con_handle(&context, gatt_client->con_handle); 707 hci_event_builder_add_bytes(&context, value, 4); 708 gatt_client_service_emit_event(gatt_client, event, hci_event_builder_get_length(&context)); 709 } 710 } 711 712 static void gatt_client_service_packet_handler(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size){ 713 UNUSED(channel); // ok: handling own l2cap events 714 UNUSED(size); // ok: there is no channel 715 716 hci_con_handle_t con_handle; 717 gatt_client_t *gatt_client; 718 gatt_client_service_t service; 719 gatt_client_characteristic_t characteristic; 720 switch (packet_type) { 721 case HCI_EVENT_PACKET: 722 switch (hci_event_packet_get_type(packet)) { 723 case GATT_EVENT_SERVICE_QUERY_RESULT: 724 con_handle = gatt_event_service_query_result_get_handle(packet); 725 gatt_client = gatt_client_get_context_for_handle(con_handle); 726 btstack_assert(gatt_client != NULL); 727 btstack_assert(gatt_client->gatt_service_state == GATT_CLIENT_SERVICE_DISCOVER_W4_DONE); 728 gatt_event_service_query_result_get_service(packet, &service); 729 gatt_client->gatt_service_start_group_handle = service.start_group_handle; 730 gatt_client->gatt_service_end_group_handle = service.end_group_handle; 731 break; 732 case GATT_EVENT_CHARACTERISTIC_QUERY_RESULT: 733 con_handle = gatt_event_characteristic_query_result_get_handle(packet); 734 gatt_client = gatt_client_get_context_for_handle(con_handle); 735 btstack_assert(gatt_client != NULL); 736 btstack_assert(gatt_client->gatt_service_state == GATT_CLIENT_SERVICE_DISCOVER_CHARACTERISTICS_W4_DONE); 737 gatt_event_characteristic_query_result_get_characteristic(packet, &characteristic); 738 switch (characteristic.uuid16){ 739 case ORG_BLUETOOTH_CHARACTERISTIC_GATT_SERVICE_CHANGED: 740 gatt_client->gatt_service_changed_value_handle = characteristic.value_handle; 741 gatt_client->gatt_service_changed_end_handle = characteristic.end_handle; 742 break; 743 case ORG_BLUETOOTH_CHARACTERISTIC_DATABASE_HASH: 744 gatt_client->gatt_service_database_hash_value_handle = characteristic.value_handle; 745 gatt_client->gatt_service_database_hash_end_handle = characteristic.end_handle; 746 break; 747 default: 748 break; 749 } 750 break; 751 case GATT_EVENT_CHARACTERISTIC_VALUE_QUERY_RESULT: 752 con_handle = gatt_event_characteristic_value_query_result_get_handle(packet); 753 gatt_client = gatt_client_get_context_for_handle(con_handle); 754 btstack_assert(gatt_client != NULL); 755 btstack_assert(gatt_client->gatt_service_state == GATT_CLIENT_SERVICE_DATABASE_HASH_READ_W4_DONE); 756 gatt_client_service_emit_database_hash(gatt_client, 757 gatt_event_characteristic_value_query_result_get_value(packet), 758 gatt_event_characteristic_value_query_result_get_value_length(packet)); 759 break; 760 case GATT_EVENT_QUERY_COMPLETE: 761 con_handle = gatt_event_query_complete_get_handle(packet); 762 gatt_client = gatt_client_get_context_for_handle(con_handle); 763 btstack_assert(gatt_client != NULL); 764 switch (gatt_client->gatt_service_state) { 765 case GATT_CLIENT_SERVICE_DISCOVER_W4_DONE: 766 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_DISCOVER_CHARACTERISTICS_W2_SEND; 767 break; 768 case GATT_CLIENT_SERVICE_DISCOVER_CHARACTERISTICS_W4_DONE: 769 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_SERVICE_CHANGED_WRITE_CCCD_W2_SEND; 770 break; 771 case GATT_CLIENT_SERVICE_SERVICE_CHANGED_WRITE_CCCD_W4_DONE: 772 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_DATABASE_HASH_READ_W2_SEND; 773 break; 774 case GATT_CLIENT_SERVICE_DATABASE_HASH_READ_W4_DONE: 775 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_DATABASE_HASH_WRITE_CCCD_W2_SEND; 776 break; 777 case GATT_CLIENT_SERVICE_DATABASE_HASH_WRITE_CCCD_W4_DONE: 778 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_DONE; 779 break; 780 default: 781 btstack_unreachable(); 782 break; 783 } 784 break; 785 default: 786 break; 787 } 788 break; 789 default: 790 break; 791 } 792 } 793 #endif 794 795 static void gatt_client_notify_can_send_query(gatt_client_t * gatt_client){ 796 797 #ifdef ENABLE_GATT_OVER_EATT 798 // if eatt is ready, notify all clients that can send a query 799 if (gatt_client->eatt_state == GATT_CLIENT_EATT_READY){ 800 btstack_linked_list_iterator_t it; 801 btstack_linked_list_iterator_init(&it, &gatt_client->eatt_clients); 802 while (btstack_linked_list_iterator_has_next(&it)){ 803 gatt_client_t * client = (gatt_client_t *) btstack_linked_list_iterator_next(&it); 804 if (client->state == P_READY){ 805 // call callback 806 btstack_context_callback_registration_t * callback = (btstack_context_callback_registration_t *) btstack_linked_list_pop(&gatt_client->query_requests); 807 if (callback == NULL) { 808 return; 809 } 810 (*callback->callback)(callback->context); 811 } 812 } 813 return; 814 } 815 #endif 816 817 while (gatt_client->state == P_READY){ 818 bool query_sent = false; 819 UNUSED(query_sent); 820 821 #ifdef ENABLE_GATT_CLIENT_SERVICE_CHANGED 822 uint8_t status = ERROR_CODE_SUCCESS; 823 gatt_client_service_t gatt_service; 824 gatt_client_characteristic_t characteristic; 825 switch (gatt_client->gatt_service_state){ 826 case GATT_CLIENT_SERVICE_DISCOVER_W2_SEND: 827 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_DISCOVER_W4_DONE; 828 status = gatt_client_discover_primary_services_by_uuid16(&gatt_client_service_packet_handler, 829 gatt_client->con_handle, 830 ORG_BLUETOOTH_SERVICE_GENERIC_ATTRIBUTE); 831 query_sent = true; 832 break; 833 case GATT_CLIENT_SERVICE_DISCOVER_CHARACTERISTICS_W2_SEND: 834 if (gatt_client->gatt_service_start_group_handle != 0){ 835 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_DISCOVER_CHARACTERISTICS_W4_DONE; 836 gatt_service.start_group_handle = gatt_client->gatt_service_start_group_handle; 837 gatt_service.end_group_handle = gatt_client->gatt_service_end_group_handle; 838 status = gatt_client_discover_characteristics_for_service(&gatt_client_service_packet_handler, gatt_client->con_handle, &gatt_service); 839 query_sent = true; 840 break; 841 } 842 843 /* fall through */ 844 845 case GATT_CLIENT_SERVICE_SERVICE_CHANGED_WRITE_CCCD_W2_SEND: 846 if (gatt_client->gatt_service_changed_value_handle != 0){ 847 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_SERVICE_CHANGED_WRITE_CCCD_W4_DONE; 848 characteristic.value_handle = gatt_client->gatt_service_changed_value_handle; 849 characteristic.end_handle = gatt_client->gatt_service_changed_end_handle; 850 // we assume good case. We cannot do much otherwise 851 characteristic.properties = ATT_PROPERTY_INDICATE; 852 status = gatt_client_write_client_characteristic_configuration(&gatt_client_service_packet_handler, 853 gatt_client->con_handle, &characteristic, 854 GATT_CLIENT_CHARACTERISTICS_CONFIGURATION_INDICATION); 855 query_sent = true; 856 break; 857 } 858 859 /* fall through */ 860 861 case GATT_CLIENT_SERVICE_DATABASE_HASH_READ_W2_SEND: 862 if (gatt_client->gatt_service_database_hash_value_handle != 0){ 863 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_DATABASE_HASH_READ_W4_DONE; 864 status = gatt_client_read_value_of_characteristics_by_uuid16(&gatt_client_service_packet_handler, 865 gatt_client->con_handle, 866 0x0001, 0xffff, ORG_BLUETOOTH_CHARACTERISTIC_DATABASE_HASH); 867 query_sent = true; 868 break; 869 } 870 871 /* fall through */ 872 873 case GATT_CLIENT_SERVICE_DATABASE_HASH_WRITE_CCCD_W2_SEND: 874 if (gatt_client->gatt_service_database_hash_value_handle != 0) { 875 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_DATABASE_HASH_WRITE_CCCD_W4_DONE; 876 characteristic.value_handle = gatt_client->gatt_service_database_hash_value_handle; 877 characteristic.end_handle = gatt_client->gatt_service_database_hash_end_handle; 878 // we assume good case. We cannot do much otherwise 879 characteristic.properties = ATT_PROPERTY_INDICATE; 880 status = gatt_client_write_client_characteristic_configuration(&gatt_client_service_packet_handler, 881 gatt_client->con_handle, 882 &characteristic, 883 GATT_CLIENT_CHARACTERISTICS_CONFIGURATION_INDICATION); 884 query_sent = true; 885 break; 886 } 887 888 // DONE 889 gatt_client->gatt_service_state = GATT_CLIENT_SERVICE_DONE; 890 break; 891 default: 892 break; 893 } 894 btstack_assert(status == ERROR_CODE_SUCCESS); 895 UNUSED(status); 896 if (query_sent){ 897 continue; 898 } 899 #endif 900 901 #ifdef ENABLE_GATT_OVER_EATT 902 query_sent = gatt_client_le_enhanced_handle_can_send_query(gatt_client); 903 if (query_sent){ 904 continue; 905 } 906 #endif 907 btstack_context_callback_registration_t * callback = (btstack_context_callback_registration_t *) btstack_linked_list_pop(&gatt_client->query_requests); 908 if (callback == NULL) { 909 return; 910 } 911 (*callback->callback)(callback->context); 912 } 913 } 914 915 // test if notification/indication should be delivered to application (BLESA) 916 static bool gatt_client_accept_server_message(gatt_client_t *gatt_client) { 917 // ignore messages until re-encryption is complete 918 if (gap_reconnect_security_setup_active(gatt_client->con_handle)) return false; 919 920 // after that ignore if bonded but not encrypted 921 return !gap_bonded(gatt_client->con_handle) || (gap_encryption_key_size(gatt_client->con_handle) > 0); 922 } 923 924 static void emit_event_new(btstack_packet_handler_t callback, uint8_t * packet, uint16_t size){ 925 if (!callback) return; 926 hci_dump_btstack_event(packet, size); 927 (*callback)(HCI_EVENT_PACKET, 0, packet, size); 928 } 929 930 static void emit_gatt_complete_event(gatt_client_t * gatt_client, uint8_t att_status){ 931 // @format H122 932 uint8_t packet[9]; 933 hci_event_builder_context_t context; 934 hci_event_builder_init(&context, packet, sizeof(packet), GATT_EVENT_QUERY_COMPLETE, 0); 935 hci_event_builder_add_con_handle(&context, gatt_client->con_handle); 936 hci_event_builder_add_16(&context, gatt_client->service_id); 937 hci_event_builder_add_16(&context, gatt_client->connection_id); 938 hci_event_builder_add_08(&context, att_status); 939 emit_event_new(gatt_client->callback, packet, hci_event_builder_get_length(&context)); 940 } 941 942 static void emit_gatt_service_query_result_event(gatt_client_t * gatt_client, uint16_t start_group_handle, uint16_t end_group_handle, const uint8_t * uuid128){ 943 // @format H22X 944 uint8_t packet[28]; 945 hci_event_builder_context_t context; 946 hci_event_builder_init(&context, packet, sizeof(packet), GATT_EVENT_SERVICE_QUERY_RESULT, 0); 947 hci_event_builder_add_con_handle(&context, gatt_client->con_handle); 948 hci_event_builder_add_16(&context, gatt_client->service_id); 949 hci_event_builder_add_16(&context, gatt_client->connection_id); 950 hci_event_builder_add_16(&context, start_group_handle); 951 hci_event_builder_add_16(&context, end_group_handle); 952 hci_event_builder_add_128(&context, uuid128); 953 emit_event_new(gatt_client->callback, packet, hci_event_builder_get_length(&context)); 954 } 955 956 static void emit_gatt_included_service_query_result_event(gatt_client_t * gatt_client, uint16_t include_handle, uint16_t start_group_handle, uint16_t end_group_handle, const uint8_t * uuid128){ 957 // @format H22X 958 uint8_t packet[30]; 959 hci_event_builder_context_t context; 960 hci_event_builder_init(&context, packet, sizeof(packet), GATT_EVENT_INCLUDED_SERVICE_QUERY_RESULT, 0); 961 hci_event_builder_add_con_handle(&context, gatt_client->con_handle); 962 hci_event_builder_add_16(&context, gatt_client->service_id); 963 hci_event_builder_add_16(&context, gatt_client->connection_id); 964 hci_event_builder_add_16(&context, include_handle); 965 hci_event_builder_add_16(&context, start_group_handle); 966 hci_event_builder_add_16(&context, end_group_handle); 967 hci_event_builder_add_128(&context, uuid128); 968 emit_event_new(gatt_client->callback, packet, hci_event_builder_get_length(&context)); 969 } 970 971 static void emit_gatt_characteristic_query_result_event(gatt_client_t * gatt_client, uint16_t start_handle, uint16_t value_handle, uint16_t end_handle, 972 uint16_t properties, const uint8_t * uuid128){ 973 // @format H22Y 974 uint8_t packet[32]; 975 hci_event_builder_context_t context; 976 hci_event_builder_init(&context, packet, sizeof(packet), GATT_EVENT_CHARACTERISTIC_QUERY_RESULT, 0); 977 hci_event_builder_add_con_handle(&context, gatt_client->con_handle); 978 hci_event_builder_add_16(&context, gatt_client->service_id); 979 hci_event_builder_add_16(&context, gatt_client->connection_id); 980 hci_event_builder_add_16(&context, start_handle); 981 hci_event_builder_add_16(&context, value_handle); 982 hci_event_builder_add_16(&context, end_handle); 983 hci_event_builder_add_16(&context, properties); 984 hci_event_builder_add_128(&context, uuid128); 985 emit_event_new(gatt_client->callback, packet, hci_event_builder_get_length(&context)); 986 } 987 988 static void emit_gatt_all_characteristic_descriptors_result_event( 989 gatt_client_t * gatt_client, uint16_t descriptor_handle, const uint8_t * uuid128){ 990 // @format H22Z 991 uint8_t packet[26]; 992 hci_event_builder_context_t context; 993 hci_event_builder_init(&context, packet, sizeof(packet), GATT_EVENT_ALL_CHARACTERISTIC_DESCRIPTORS_QUERY_RESULT, 0); 994 hci_event_builder_add_con_handle(&context, gatt_client->con_handle); 995 hci_event_builder_add_16(&context, gatt_client->service_id); 996 hci_event_builder_add_16(&context, gatt_client->connection_id); 997 hci_event_builder_add_16(&context, descriptor_handle); 998 hci_event_builder_add_128(&context, uuid128); 999 emit_event_new(gatt_client->callback, packet, hci_event_builder_get_length(&context)); 1000 } 1001 1002 static void emit_gatt_mtu_exchanged_result_event(gatt_client_t * gatt_client, uint16_t new_mtu){ 1003 // @format H2 1004 uint8_t packet[6]; 1005 packet[0] = GATT_EVENT_MTU; 1006 packet[1] = sizeof(packet) - 2u; 1007 little_endian_store_16(packet, 2, gatt_client->con_handle); 1008 little_endian_store_16(packet, 4, new_mtu); 1009 att_dispatch_client_mtu_exchanged(gatt_client->con_handle, new_mtu); 1010 emit_event_new(gatt_client->callback, packet, sizeof(packet)); 1011 } 1012 1013 // helper 1014 static void gatt_client_handle_transaction_complete(gatt_client_t *gatt_client, uint8_t att_status) { 1015 gatt_client->state = P_READY; 1016 gatt_client_timeout_stop(gatt_client); 1017 emit_gatt_complete_event(gatt_client, att_status); 1018 gatt_client_notify_can_send_query(gatt_client); 1019 } 1020 1021 // @return packet pointer 1022 // @note assume that value is part of an l2cap buffer - overwrite HCI + L2CAP packet headers + 4 pre_buffer bytes 1023 #define CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE 12 1024 static uint8_t * 1025 setup_characteristic_value_packet(const gatt_client_t *gatt_client, uint8_t type, uint16_t attribute_handle, 1026 uint8_t *value, uint16_t length, uint16_t service_id, uint16_t connection_id) { 1027 #ifdef FUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION 1028 // copy value into test packet for testing 1029 static uint8_t packet[1000]; 1030 memcpy(&packet[CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE], value, length); 1031 #else 1032 // before the value inside the ATT PDU 1033 uint8_t * packet = value - CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE; 1034 #endif 1035 packet[0] = type; 1036 packet[1] = CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE - 2 + length; 1037 little_endian_store_16(packet, 2, gatt_client->con_handle); 1038 little_endian_store_16(packet, 4, service_id); 1039 little_endian_store_16(packet, 6, connection_id); 1040 little_endian_store_16(packet, 8, attribute_handle); 1041 little_endian_store_16(packet, 10, length); 1042 return packet; 1043 } 1044 1045 // @return packet pointer 1046 // @note assume that value is part of an l2cap buffer - overwrite HCI + L2CAP packet headers + 6 pre_buffer bytes 1047 #define LONG_CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE 14 1048 1049 // L2CAP Header (4) + ACL Header (4) => 8 bytes 1050 #if !defined(HCI_INCOMING_PRE_BUFFER_SIZE) || ((HCI_INCOMING_PRE_BUFFER_SIZE < LONG_CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE - 8)) 1051 #error "Long Characteristic reads requires HCI_INCOMING_PRE_BUFFER_SIZE >= 6" 1052 #endif 1053 1054 static uint8_t * 1055 setup_long_characteristic_value_packet(const gatt_client_t *gatt_client, uint8_t type, uint16_t attribute_handle, 1056 uint16_t offset, uint8_t *value, uint16_t length) { 1057 #ifdef FUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION 1058 // avoid using pre ATT headers. 1059 // copy value into test packet for testing 1060 static uint8_t packet[1000]; 1061 memcpy(&packet[LONG_CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE], value, length); 1062 #else 1063 // before the value inside the ATT PDU 1064 uint8_t * packet = value - LONG_CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE; 1065 #endif 1066 packet[0] = type; 1067 packet[1] = LONG_CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE - 2 + length; 1068 little_endian_store_16(packet, 2, gatt_client->con_handle); 1069 little_endian_store_16(packet, 4, gatt_client->service_id); 1070 little_endian_store_16(packet, 6, gatt_client->connection_id); 1071 little_endian_store_16(packet, 8, attribute_handle); 1072 little_endian_store_16(packet, 10, offset); 1073 little_endian_store_16(packet, 12, length); 1074 return packet; 1075 } 1076 1077 #if (LONG_CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE > CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE) 1078 #define REPORT_PREBUFFER_HEADER LONG_CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE 1079 #else 1080 #define REPORT_PREBUFFER_HEADER CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE 1081 #endif 1082 1083 /// 1084 static void report_gatt_services(gatt_client_t * gatt_client, uint8_t * packet, uint16_t size){ 1085 if (size < 2) return; 1086 uint8_t attr_length = packet[1]; 1087 uint8_t uuid_length = attr_length - 4u; 1088 1089 int i; 1090 for (i = 2; (i+attr_length) <= size; i += attr_length){ 1091 uint16_t start_group_handle = little_endian_read_16(packet,i); 1092 uint16_t end_group_handle = little_endian_read_16(packet,i+2); 1093 uint8_t uuid128[16]; 1094 uint16_t uuid16 = 0; 1095 1096 if (uuid_length == 2u){ 1097 uuid16 = little_endian_read_16(packet, i+4); 1098 uuid_add_bluetooth_prefix((uint8_t*) &uuid128, uuid16); 1099 } else if (uuid_length == 16u) { 1100 reverse_128(&packet[i+4], uuid128); 1101 } else { 1102 return; 1103 } 1104 emit_gatt_service_query_result_event(gatt_client, start_group_handle, end_group_handle, uuid128); 1105 } 1106 } 1107 1108 static void report_gatt_characteristic_start_found(gatt_client_t * gatt_client, uint16_t start_handle, uint8_t properties, uint16_t value_handle, uint8_t * uuid, uint16_t uuid_length){ 1109 uint8_t uuid128[16]; 1110 uint16_t uuid16 = 0; 1111 if (uuid_length == 2u){ 1112 uuid16 = little_endian_read_16(uuid, 0); 1113 uuid_add_bluetooth_prefix((uint8_t*) uuid128, uuid16); 1114 } else if (uuid_length == 16u){ 1115 reverse_128(uuid, uuid128); 1116 } else { 1117 return; 1118 } 1119 1120 if (gatt_client->filter_with_uuid && (memcmp(gatt_client->uuid128, uuid128, 16) != 0)) return; 1121 1122 gatt_client->characteristic_properties = properties; 1123 gatt_client->characteristic_start_handle = start_handle; 1124 gatt_client->attribute_handle = value_handle; 1125 1126 if (gatt_client->filter_with_uuid) return; 1127 1128 gatt_client->uuid16 = uuid16; 1129 (void)memcpy(gatt_client->uuid128, uuid128, 16); 1130 } 1131 1132 static void report_gatt_characteristic_end_found(gatt_client_t * gatt_client, uint16_t end_handle){ 1133 // TODO: stop searching if filter and uuid found 1134 1135 if (!gatt_client->characteristic_start_handle) return; 1136 1137 emit_gatt_characteristic_query_result_event(gatt_client, gatt_client->characteristic_start_handle, gatt_client->attribute_handle, 1138 end_handle, gatt_client->characteristic_properties, gatt_client->uuid128); 1139 1140 gatt_client->characteristic_start_handle = 0; 1141 } 1142 1143 1144 static void report_gatt_characteristics(gatt_client_t * gatt_client, uint8_t * packet, uint16_t size){ 1145 if (size < 2u) return; 1146 uint8_t attr_length = packet[1]; 1147 if ((attr_length != 7u) && (attr_length != 21u)) return; 1148 uint8_t uuid_length = attr_length - 5u; 1149 int i; 1150 for (i = 2u; (i + attr_length) <= size; i += attr_length){ 1151 uint16_t start_handle = little_endian_read_16(packet, i); 1152 uint8_t properties = packet[i+2]; 1153 uint16_t value_handle = little_endian_read_16(packet, i+3); 1154 report_gatt_characteristic_end_found(gatt_client, start_handle - 1u); 1155 report_gatt_characteristic_start_found(gatt_client, start_handle, properties, value_handle, &packet[i + 5], 1156 uuid_length); 1157 } 1158 } 1159 1160 static void report_gatt_included_service_uuid16(gatt_client_t * gatt_client, uint16_t include_handle, uint16_t uuid16){ 1161 uint8_t normalized_uuid128[16]; 1162 uuid_add_bluetooth_prefix(normalized_uuid128, uuid16); 1163 emit_gatt_included_service_query_result_event(gatt_client, include_handle, gatt_client->query_start_handle, 1164 gatt_client->query_end_handle, normalized_uuid128); 1165 } 1166 1167 static void report_gatt_included_service_uuid128(gatt_client_t * gatt_client, uint16_t include_handle, const uint8_t * uuid128){ 1168 emit_gatt_included_service_query_result_event(gatt_client, include_handle, gatt_client->query_start_handle, 1169 gatt_client->query_end_handle, uuid128); 1170 } 1171 1172 static void report_gatt_characteristic_value_change(gatt_client_t *gatt_client, uint8_t event_type, uint16_t value_handle, uint8_t *value, int length) { 1173 uint8_t * packet; 1174 1175 // Single Characteristic listener, setup packet with service + connection id = 0 1176 packet = setup_characteristic_value_packet(gatt_client, event_type, value_handle, value, length, 0, 0); 1177 btstack_linked_list_iterator_t it; 1178 btstack_linked_list_iterator_init(&it, &gatt_client_value_listeners); 1179 while (btstack_linked_list_iterator_has_next(&it)) { 1180 gatt_client_notification_t *notification = (gatt_client_notification_t *) btstack_linked_list_iterator_next(&it); 1181 if ((notification->con_handle != GATT_CLIENT_ANY_CONNECTION) && (notification->con_handle != gatt_client->con_handle)) continue; 1182 if ((notification->attribute_handle != GATT_CLIENT_ANY_VALUE_HANDLE) && (notification->attribute_handle != value_handle)) continue; 1183 1184 (*notification->callback)(HCI_EVENT_PACKET, 0, packet, CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE + length); 1185 } 1186 1187 // Service characteristics 1188 btstack_linked_list_iterator_init(&it, &gatt_client_service_value_listeners); 1189 while (btstack_linked_list_iterator_has_next(&it)){ 1190 const gatt_client_service_notification_t * notification = (gatt_client_service_notification_t*) btstack_linked_list_iterator_next(&it); 1191 if (notification->con_handle != gatt_client->con_handle) continue; 1192 if (notification->start_group_handle > value_handle) continue; 1193 if (notification->end_group_handle < value_handle) continue; 1194 // (re)setup value packet with service and connection id (to avoid patching event later) 1195 packet = setup_characteristic_value_packet(gatt_client, event_type, value_handle, value, length, notification->service_id, notification->connection_id); 1196 (*notification->callback)(HCI_EVENT_PACKET, 0, packet, CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE + length); 1197 } 1198 } 1199 1200 // @note assume that value is part of an l2cap buffer - overwrite parts of the HCI/L2CAP/ATT packet (4/4/3) bytes 1201 static void report_gatt_notification(gatt_client_t *gatt_client, uint16_t value_handle, uint8_t *value, int length) { 1202 if (!gatt_client_accept_server_message(gatt_client)) return; 1203 report_gatt_characteristic_value_change(gatt_client, GATT_EVENT_NOTIFICATION, value_handle, value, length); 1204 } 1205 1206 // @note assume that value is part of an l2cap buffer - overwrite parts of the HCI/L2CAP/ATT packet (4/4/3) bytes 1207 static void report_gatt_indication(gatt_client_t *gatt_client, uint16_t value_handle, uint8_t *value, int length) { 1208 if (!gatt_client_accept_server_message(gatt_client)) return; 1209 #ifdef ENABLE_GATT_CLIENT_SERVICE_CHANGED 1210 // Directly Handle GATT Service Changed and Database Hash indications 1211 if (value_handle == gatt_client->gatt_service_database_hash_value_handle){ 1212 gatt_client_service_emit_database_hash(gatt_client, value, length); 1213 } 1214 if (value_handle == gatt_client->gatt_service_changed_value_handle){ 1215 gatt_client_service_emit_service_changed(gatt_client, value, length); 1216 } 1217 #endif 1218 report_gatt_characteristic_value_change(gatt_client, GATT_EVENT_INDICATION, value_handle, value, length); 1219 } 1220 1221 // @note assume that value is part of an l2cap buffer - overwrite parts of the HCI/L2CAP/ATT packet (4/4/3) bytes 1222 static void report_gatt_characteristic_value(gatt_client_t * gatt_client, uint16_t attribute_handle, uint8_t * value, uint16_t length){ 1223 uint8_t * packet = setup_characteristic_value_packet( 1224 gatt_client, GATT_EVENT_CHARACTERISTIC_VALUE_QUERY_RESULT, attribute_handle, value, length, gatt_client->service_id, gatt_client->connection_id); 1225 emit_event_new(gatt_client->callback, packet, CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE + length); 1226 } 1227 1228 // @note assume that value is part of an l2cap buffer - overwrite parts of the HCI/L2CAP/ATT packet (4/4/3) bytes 1229 static void report_gatt_long_characteristic_value_blob(gatt_client_t * gatt_client, uint16_t attribute_handle, uint8_t * blob, uint16_t blob_length, int value_offset){ 1230 uint8_t * packet = setup_long_characteristic_value_packet(gatt_client, 1231 GATT_EVENT_LONG_CHARACTERISTIC_VALUE_QUERY_RESULT, 1232 attribute_handle, value_offset, 1233 blob, blob_length); 1234 emit_event_new(gatt_client->callback, packet, blob_length + LONG_CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE); 1235 } 1236 1237 static void report_gatt_characteristic_descriptor(gatt_client_t * gatt_client, uint16_t descriptor_handle, uint8_t *value, uint16_t value_length, uint16_t value_offset){ 1238 UNUSED(value_offset); 1239 uint8_t * packet = setup_characteristic_value_packet(gatt_client, GATT_EVENT_CHARACTERISTIC_DESCRIPTOR_QUERY_RESULT, 1240 descriptor_handle, value, 1241 value_length, gatt_client->service_id, gatt_client->connection_id); 1242 emit_event_new(gatt_client->callback, packet, value_length + 8u); 1243 } 1244 1245 static void report_gatt_long_characteristic_descriptor(gatt_client_t * gatt_client, uint16_t descriptor_handle, uint8_t *blob, uint16_t blob_length, uint16_t value_offset){ 1246 uint8_t * packet = setup_long_characteristic_value_packet(gatt_client, 1247 GATT_EVENT_LONG_CHARACTERISTIC_DESCRIPTOR_QUERY_RESULT, 1248 descriptor_handle, value_offset, 1249 blob, blob_length); 1250 emit_event_new(gatt_client->callback, packet, blob_length + LONG_CHARACTERISTIC_VALUE_EVENT_HEADER_SIZE); 1251 } 1252 1253 static void report_gatt_all_characteristic_descriptors(gatt_client_t * gatt_client, uint8_t * packet, uint16_t size, uint16_t pair_size){ 1254 int i; 1255 for (i = 0u; (i + pair_size) <= size; i += pair_size){ 1256 uint16_t descriptor_handle = little_endian_read_16(packet,i); 1257 uint8_t uuid128[16]; 1258 uint16_t uuid16 = 0; 1259 if (pair_size == 4u){ 1260 uuid16 = little_endian_read_16(packet,i+2); 1261 uuid_add_bluetooth_prefix(uuid128, uuid16); 1262 } else { 1263 reverse_128(&packet[i+2], uuid128); 1264 } 1265 emit_gatt_all_characteristic_descriptors_result_event(gatt_client, descriptor_handle, uuid128); 1266 } 1267 1268 } 1269 1270 static bool is_query_done(gatt_client_t * gatt_client, uint16_t last_result_handle){ 1271 return last_result_handle >= gatt_client->end_group_handle; 1272 } 1273 1274 static void trigger_next_query(gatt_client_t * gatt_client, uint16_t last_result_handle, gatt_client_state_t next_query_state){ 1275 if (is_query_done(gatt_client, last_result_handle)){ 1276 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 1277 return; 1278 } 1279 // next 1280 gatt_client->start_group_handle = last_result_handle + 1u; 1281 gatt_client->state = next_query_state; 1282 } 1283 1284 static void trigger_next_included_service_query(gatt_client_t * gatt_client, uint16_t last_result_handle){ 1285 trigger_next_query(gatt_client, last_result_handle, P_W2_SEND_INCLUDED_SERVICE_QUERY); 1286 } 1287 1288 static void trigger_next_service_query(gatt_client_t * gatt_client, uint16_t last_result_handle){ 1289 trigger_next_query(gatt_client, last_result_handle, P_W2_SEND_SERVICE_QUERY); 1290 } 1291 1292 static void trigger_next_service_by_uuid_query(gatt_client_t * gatt_client, uint16_t last_result_handle){ 1293 trigger_next_query(gatt_client, last_result_handle, P_W2_SEND_SERVICE_WITH_UUID_QUERY); 1294 } 1295 1296 static void trigger_next_characteristic_query(gatt_client_t * gatt_client, uint16_t last_result_handle){ 1297 if (is_query_done(gatt_client, last_result_handle)){ 1298 // report last characteristic 1299 report_gatt_characteristic_end_found(gatt_client, gatt_client->end_group_handle); 1300 } 1301 trigger_next_query(gatt_client, last_result_handle, P_W2_SEND_ALL_CHARACTERISTICS_OF_SERVICE_QUERY); 1302 } 1303 1304 static void trigger_next_characteristic_descriptor_query(gatt_client_t * gatt_client, uint16_t last_result_handle){ 1305 trigger_next_query(gatt_client, last_result_handle, P_W2_SEND_ALL_CHARACTERISTIC_DESCRIPTORS_QUERY); 1306 } 1307 1308 static void trigger_next_read_by_type_query(gatt_client_t * gatt_client, uint16_t last_result_handle){ 1309 trigger_next_query(gatt_client, last_result_handle, P_W2_SEND_READ_BY_TYPE_REQUEST); 1310 } 1311 1312 static void trigger_next_prepare_write_query(gatt_client_t * gatt_client, gatt_client_state_t next_query_state, gatt_client_state_t done_state){ 1313 gatt_client->attribute_offset += write_blob_length(gatt_client); 1314 uint16_t next_blob_length = write_blob_length(gatt_client); 1315 1316 if (next_blob_length == 0u){ 1317 gatt_client->state = done_state; 1318 return; 1319 } 1320 gatt_client->state = next_query_state; 1321 } 1322 1323 static void trigger_next_blob_query(gatt_client_t * gatt_client, gatt_client_state_t next_query_state, uint16_t received_blob_length){ 1324 1325 uint16_t max_blob_length = gatt_client->mtu - 1u; 1326 if (received_blob_length < max_blob_length){ 1327 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 1328 return; 1329 } 1330 1331 gatt_client->attribute_offset += received_blob_length; 1332 gatt_client->state = next_query_state; 1333 } 1334 1335 void gatt_client_listen_for_characteristic_value_updates(gatt_client_notification_t * notification, btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_characteristic_t * characteristic){ 1336 notification->callback = callback; 1337 notification->con_handle = con_handle; 1338 if (characteristic == NULL){ 1339 notification->attribute_handle = GATT_CLIENT_ANY_VALUE_HANDLE; 1340 } else { 1341 notification->attribute_handle = characteristic->value_handle; 1342 } 1343 btstack_linked_list_add(&gatt_client_value_listeners, (btstack_linked_item_t*) notification); 1344 } 1345 1346 void gatt_client_stop_listening_for_characteristic_value_updates(gatt_client_notification_t * notification){ 1347 btstack_linked_list_remove(&gatt_client_value_listeners, (btstack_linked_item_t*) notification); 1348 } 1349 1350 void gatt_client_listen_for_service_characteristic_value_updates(gatt_client_service_notification_t * notification, 1351 btstack_packet_handler_t callback, 1352 hci_con_handle_t con_handle, 1353 gatt_client_service_t * service, 1354 uint16_t service_id, 1355 uint16_t connection_id){ 1356 notification->callback = callback; 1357 notification->con_handle = con_handle; 1358 notification->start_group_handle = service->start_group_handle; 1359 notification->end_group_handle = service->end_group_handle; 1360 notification->service_id = service_id; 1361 notification->connection_id = connection_id; 1362 btstack_linked_list_add(&gatt_client_service_value_listeners, (btstack_linked_item_t*) notification); 1363 } 1364 1365 /** 1366 * @brief Stop listening to characteristic value updates for registered service with 1367 * the gatt_client_listen_for_characteristic_value_updates function. 1368 * @param notification struct used in gatt_client_listen_for_characteristic_value_updates 1369 */ 1370 void gatt_client_stop_listening_for_service_characteristic_value_updates(gatt_client_service_notification_t * notification){ 1371 btstack_linked_list_remove(&gatt_client_service_value_listeners, (btstack_linked_item_t*) notification); 1372 } 1373 1374 static bool is_value_valid(gatt_client_t *gatt_client, uint8_t *packet, uint16_t size){ 1375 uint16_t attribute_handle = little_endian_read_16(packet, 1); 1376 uint16_t value_offset = little_endian_read_16(packet, 3); 1377 1378 if (gatt_client->attribute_handle != attribute_handle) return false; 1379 if (gatt_client->attribute_offset != value_offset) return false; 1380 return memcmp(&gatt_client->attribute_value[gatt_client->attribute_offset], &packet[5], size - 5u) == 0u; 1381 } 1382 1383 #ifdef ENABLE_LE_SIGNED_WRITE 1384 static void gatt_client_run_for_client_start_signed_write(gatt_client_t *gatt_client) { 1385 sm_key_t csrk; 1386 le_device_db_local_csrk_get(gatt_client->le_device_index, csrk); 1387 uint32_t sign_counter = le_device_db_local_counter_get(gatt_client->le_device_index); 1388 gatt_client->state = P_W4_CMAC_RESULT; 1389 sm_cmac_signed_write_start(csrk, ATT_SIGNED_WRITE_COMMAND, gatt_client->attribute_handle, gatt_client->attribute_length, gatt_client->attribute_value, sign_counter, att_signed_write_handle_cmac_result); 1390 } 1391 #endif 1392 1393 // returns true if packet was sent 1394 static bool gatt_client_run_for_gatt_client(gatt_client_t * gatt_client){ 1395 1396 // wait until re-encryption is complete 1397 if (gap_reconnect_security_setup_active(gatt_client->con_handle)) return false; 1398 1399 // wait until re-encryption is complete 1400 if (gatt_client->reencryption_active) return false; 1401 1402 // wait until pairing complete (either reactive authentication or due to required security level) 1403 if (gatt_client->wait_for_authentication_complete) return false; 1404 1405 bool client_request_pending = gatt_client->state != P_READY; 1406 1407 // verify security level for Mandatory Authentication over LE 1408 bool check_security; 1409 switch (gatt_client->bearer_type){ 1410 case ATT_BEARER_UNENHANCED_LE: 1411 check_security = true; 1412 break; 1413 default: 1414 check_security = false; 1415 break; 1416 } 1417 if (client_request_pending && (gatt_client_required_security_level > gatt_client->security_level) && check_security){ 1418 log_info("Trigger pairing, current security level %u, required %u\n", gatt_client->security_level, gatt_client_required_security_level); 1419 gatt_client->wait_for_authentication_complete = true; 1420 // set att error code for pairing failure based on required level 1421 switch (gatt_client_required_security_level){ 1422 case LEVEL_4: 1423 case LEVEL_3: 1424 gatt_client->pending_error_code = ATT_ERROR_INSUFFICIENT_AUTHENTICATION; 1425 break; 1426 default: 1427 gatt_client->pending_error_code = ATT_ERROR_INSUFFICIENT_ENCRYPTION; 1428 break; 1429 } 1430 sm_request_pairing(gatt_client->con_handle); 1431 // sm probably just sent a pdu 1432 return true; 1433 } 1434 1435 switch (gatt_client->mtu_state) { 1436 case SEND_MTU_EXCHANGE: 1437 gatt_client->mtu_state = SENT_MTU_EXCHANGE; 1438 att_exchange_mtu_request(gatt_client); 1439 return true; 1440 case SENT_MTU_EXCHANGE: 1441 return false; 1442 default: 1443 break; 1444 } 1445 1446 if (gatt_client->send_confirmation){ 1447 gatt_client->send_confirmation = false; 1448 att_confirmation(gatt_client); 1449 return true; 1450 } 1451 1452 // check MTU for writes 1453 switch (gatt_client->state){ 1454 case P_W2_SEND_WRITE_CHARACTERISTIC_VALUE: 1455 case P_W2_SEND_WRITE_CHARACTERISTIC_DESCRIPTOR: 1456 if (gatt_client->attribute_length <= (gatt_client->mtu - 3u)) break; 1457 log_error("gatt_client_run: value len %u > MTU %u - 3\n", gatt_client->attribute_length,gatt_client->mtu); 1458 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_INVALID_ATTRIBUTE_VALUE_LENGTH); 1459 return false; 1460 default: 1461 break; 1462 } 1463 1464 bool packet_sent = true; 1465 bool done = true; 1466 switch (gatt_client->state){ 1467 case P_W2_SEND_SERVICE_QUERY: 1468 gatt_client->state = P_W4_SERVICE_QUERY_RESULT; 1469 send_gatt_services_request(gatt_client); 1470 break; 1471 1472 case P_W2_SEND_SERVICE_WITH_UUID_QUERY: 1473 gatt_client->state = P_W4_SERVICE_WITH_UUID_RESULT; 1474 send_gatt_services_by_uuid_request(gatt_client); 1475 break; 1476 1477 case P_W2_SEND_ALL_CHARACTERISTICS_OF_SERVICE_QUERY: 1478 gatt_client->state = P_W4_ALL_CHARACTERISTICS_OF_SERVICE_QUERY_RESULT; 1479 send_gatt_characteristic_request(gatt_client); 1480 break; 1481 1482 case P_W2_SEND_CHARACTERISTIC_WITH_UUID_QUERY: 1483 gatt_client->state = P_W4_CHARACTERISTIC_WITH_UUID_QUERY_RESULT; 1484 send_gatt_characteristic_request(gatt_client); 1485 break; 1486 1487 case P_W2_SEND_ALL_CHARACTERISTIC_DESCRIPTORS_QUERY: 1488 gatt_client->state = P_W4_CHARACTERISTIC_WITH_UUID_QUERY_RESULT; 1489 send_gatt_characteristic_descriptor_request(gatt_client); 1490 break; 1491 1492 case P_W2_SEND_INCLUDED_SERVICE_QUERY: 1493 gatt_client->state = P_W4_INCLUDED_SERVICE_QUERY_RESULT; 1494 send_gatt_included_service_request(gatt_client); 1495 break; 1496 1497 case P_W2_SEND_INCLUDED_SERVICE_WITH_UUID_QUERY: 1498 gatt_client->state = P_W4_INCLUDED_SERVICE_UUID_WITH_QUERY_RESULT; 1499 send_gatt_included_service_uuid_request(gatt_client); 1500 break; 1501 1502 case P_W2_SEND_READ_CHARACTERISTIC_VALUE_QUERY: 1503 gatt_client->state = P_W4_READ_CHARACTERISTIC_VALUE_RESULT; 1504 send_gatt_read_characteristic_value_request(gatt_client); 1505 break; 1506 1507 case P_W2_SEND_READ_BLOB_QUERY: 1508 gatt_client->state = P_W4_READ_BLOB_RESULT; 1509 send_gatt_read_blob_request(gatt_client); 1510 break; 1511 1512 case P_W2_SEND_READ_BY_TYPE_REQUEST: 1513 gatt_client->state = P_W4_READ_BY_TYPE_RESPONSE; 1514 send_gatt_read_by_type_request(gatt_client); 1515 break; 1516 1517 case P_W2_SEND_READ_MULTIPLE_REQUEST: 1518 gatt_client->state = P_W4_READ_MULTIPLE_RESPONSE; 1519 send_gatt_read_multiple_request(gatt_client); 1520 break; 1521 1522 #ifdef ENABLE_GATT_OVER_EATT 1523 case P_W2_SEND_READ_MULTIPLE_VARIABLE_REQUEST: 1524 gatt_client->state = P_W4_READ_MULTIPLE_VARIABLE_RESPONSE; 1525 send_gatt_read_multiple_variable_request(gatt_client); 1526 break; 1527 #endif 1528 1529 case P_W2_SEND_WRITE_CHARACTERISTIC_VALUE: 1530 gatt_client->state = P_W4_WRITE_CHARACTERISTIC_VALUE_RESULT; 1531 send_gatt_write_attribute_value_request(gatt_client); 1532 break; 1533 1534 case P_W2_PREPARE_WRITE: 1535 gatt_client->state = P_W4_PREPARE_WRITE_RESULT; 1536 send_gatt_prepare_write_request(gatt_client); 1537 break; 1538 1539 case P_W2_PREPARE_WRITE_SINGLE: 1540 gatt_client->state = P_W4_PREPARE_WRITE_SINGLE_RESULT; 1541 send_gatt_prepare_write_request(gatt_client); 1542 break; 1543 1544 case P_W2_PREPARE_RELIABLE_WRITE: 1545 gatt_client->state = P_W4_PREPARE_RELIABLE_WRITE_RESULT; 1546 send_gatt_prepare_write_request(gatt_client); 1547 break; 1548 1549 case P_W2_EXECUTE_PREPARED_WRITE: 1550 gatt_client->state = P_W4_EXECUTE_PREPARED_WRITE_RESULT; 1551 send_gatt_execute_write_request(gatt_client); 1552 break; 1553 1554 case P_W2_CANCEL_PREPARED_WRITE: 1555 gatt_client->state = P_W4_CANCEL_PREPARED_WRITE_RESULT; 1556 send_gatt_cancel_prepared_write_request(gatt_client); 1557 break; 1558 1559 case P_W2_CANCEL_PREPARED_WRITE_DATA_MISMATCH: 1560 gatt_client->state = P_W4_CANCEL_PREPARED_WRITE_DATA_MISMATCH_RESULT; 1561 send_gatt_cancel_prepared_write_request(gatt_client); 1562 break; 1563 1564 #ifdef ENABLE_GATT_FIND_INFORMATION_FOR_CCC_DISCOVERY 1565 case P_W2_SEND_FIND_CLIENT_CHARACTERISTIC_CONFIGURATION_QUERY: 1566 // use Find Information 1567 gatt_client->state = P_W4_FIND_CLIENT_CHARACTERISTIC_CONFIGURATION_QUERY_RESULT; 1568 send_gatt_characteristic_descriptor_request(gatt_client); 1569 #else 1570 case P_W2_SEND_READ_CLIENT_CHARACTERISTIC_CONFIGURATION_QUERY: 1571 // Use Read By Type 1572 gatt_client->state = P_W4_READ_CLIENT_CHARACTERISTIC_CONFIGURATION_QUERY_RESULT; 1573 send_gatt_read_client_characteristic_configuration_request(gatt_client); 1574 #endif 1575 break; 1576 1577 case P_W2_SEND_READ_CHARACTERISTIC_DESCRIPTOR_QUERY: 1578 gatt_client->state = P_W4_READ_CHARACTERISTIC_DESCRIPTOR_RESULT; 1579 send_gatt_read_characteristic_descriptor_request(gatt_client); 1580 break; 1581 1582 case P_W2_SEND_READ_BLOB_CHARACTERISTIC_DESCRIPTOR_QUERY: 1583 gatt_client->state = P_W4_READ_BLOB_CHARACTERISTIC_DESCRIPTOR_RESULT; 1584 send_gatt_read_blob_request(gatt_client); 1585 break; 1586 1587 case P_W2_SEND_WRITE_CHARACTERISTIC_DESCRIPTOR: 1588 gatt_client->state = P_W4_WRITE_CHARACTERISTIC_DESCRIPTOR_RESULT; 1589 send_gatt_write_attribute_value_request(gatt_client); 1590 break; 1591 1592 case P_W2_WRITE_CLIENT_CHARACTERISTIC_CONFIGURATION: 1593 gatt_client->state = P_W4_CLIENT_CHARACTERISTIC_CONFIGURATION_RESULT; 1594 send_gatt_write_client_characteristic_configuration_request(gatt_client); 1595 break; 1596 1597 case P_W2_PREPARE_WRITE_CHARACTERISTIC_DESCRIPTOR: 1598 gatt_client->state = P_W4_PREPARE_WRITE_CHARACTERISTIC_DESCRIPTOR_RESULT; 1599 send_gatt_prepare_write_request(gatt_client); 1600 break; 1601 1602 case P_W2_EXECUTE_PREPARED_WRITE_CHARACTERISTIC_DESCRIPTOR: 1603 gatt_client->state = P_W4_EXECUTE_PREPARED_WRITE_CHARACTERISTIC_DESCRIPTOR_RESULT; 1604 send_gatt_execute_write_request(gatt_client); 1605 break; 1606 1607 #ifdef ENABLE_LE_SIGNED_WRITE 1608 case P_W4_IDENTITY_RESOLVING: 1609 log_info("P_W4_IDENTITY_RESOLVING - state %x", sm_identity_resolving_state(gatt_client->con_handle)); 1610 switch (sm_identity_resolving_state(gatt_client->con_handle)){ 1611 case IRK_LOOKUP_SUCCEEDED: 1612 gatt_client->le_device_index = sm_le_device_index(gatt_client->con_handle); 1613 gatt_client->state = P_W4_CMAC_READY; 1614 if (sm_cmac_ready()){ 1615 gatt_client_run_for_client_start_signed_write(gatt_client); 1616 } 1617 break; 1618 case IRK_LOOKUP_FAILED: 1619 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_BONDING_INFORMATION_MISSING); 1620 break; 1621 default: 1622 break; 1623 } 1624 packet_sent = false; 1625 break; 1626 1627 case P_W4_CMAC_READY: 1628 if (sm_cmac_ready()){ 1629 gatt_client_run_for_client_start_signed_write(gatt_client); 1630 } 1631 packet_sent = false; 1632 break; 1633 1634 case P_W2_SEND_SIGNED_WRITE: { 1635 gatt_client->state = P_W4_SEND_SIGNED_WRITE_DONE; 1636 // bump local signing counter 1637 uint32_t sign_counter = le_device_db_local_counter_get(gatt_client->le_device_index); 1638 le_device_db_local_counter_set(gatt_client->le_device_index, sign_counter + 1); 1639 // send signed write command 1640 send_gatt_signed_write_request(gatt_client, sign_counter); 1641 // finally, notifiy client that write is complete 1642 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 1643 break; 1644 } 1645 #endif 1646 default: 1647 done = false; 1648 break; 1649 } 1650 1651 if (done){ 1652 return packet_sent; 1653 } 1654 1655 // write without response callback 1656 btstack_context_callback_registration_t * callback = 1657 (btstack_context_callback_registration_t *) btstack_linked_list_pop(&gatt_client->write_without_response_requests); 1658 if (callback != NULL){ 1659 (*callback->callback)(callback->context); 1660 return true; 1661 } 1662 1663 // requested can send now old 1664 if (gatt_client->write_without_response_callback != NULL){ 1665 btstack_packet_handler_t packet_handler = gatt_client->write_without_response_callback; 1666 gatt_client->write_without_response_callback = NULL; 1667 uint8_t event[4]; 1668 event[0] = GATT_EVENT_CAN_WRITE_WITHOUT_RESPONSE; 1669 event[1] = sizeof(event) - 2u; 1670 little_endian_store_16(event, 2, gatt_client->con_handle); 1671 packet_handler(HCI_EVENT_PACKET, gatt_client->con_handle, event, sizeof(event)); 1672 return true; // to trigger requeueing (even if higher layer didn't sent) 1673 } 1674 1675 return false; 1676 } 1677 1678 static void gatt_client_run(void){ 1679 btstack_linked_item_t *it; 1680 bool packet_sent; 1681 #ifdef ENABLE_GATT_OVER_EATT 1682 btstack_linked_list_iterator_t it_eatt; 1683 #endif 1684 for (it = (btstack_linked_item_t *) gatt_client_connections; it != NULL; it = it->next){ 1685 gatt_client_t * gatt_client = (gatt_client_t *) it; 1686 switch (gatt_client->bearer_type){ 1687 case ATT_BEARER_UNENHANCED_LE: 1688 #ifdef ENABLE_GATT_OVER_EATT 1689 btstack_linked_list_iterator_init(&it_eatt, &gatt_client->eatt_clients); 1690 while (btstack_linked_list_iterator_has_next(&it_eatt)) { 1691 gatt_client_t * eatt_client = (gatt_client_t *) btstack_linked_list_iterator_next(&it_eatt); 1692 if (eatt_client->state != P_READY){ 1693 if (att_dispatch_client_can_send_now(gatt_client->con_handle)){ 1694 gatt_client_run_for_gatt_client(eatt_client); 1695 } 1696 } 1697 } 1698 #endif 1699 if (!att_dispatch_client_can_send_now(gatt_client->con_handle)) { 1700 att_dispatch_client_request_can_send_now_event(gatt_client->con_handle); 1701 return; 1702 } 1703 packet_sent = gatt_client_run_for_gatt_client(gatt_client); 1704 if (packet_sent){ 1705 // request new permission 1706 att_dispatch_client_request_can_send_now_event(gatt_client->con_handle); 1707 // requeue client for fairness and exit 1708 // note: iterator has become invalid 1709 btstack_linked_list_remove(&gatt_client_connections, (btstack_linked_item_t *) gatt_client); 1710 btstack_linked_list_add_tail(&gatt_client_connections, (btstack_linked_item_t *) gatt_client); 1711 return; 1712 } 1713 break; 1714 #ifdef ENABLE_GATT_OVER_CLASSIC 1715 case ATT_BEARER_UNENHANCED_CLASSIC: 1716 if (gatt_client->con_handle == HCI_CON_HANDLE_INVALID) { 1717 continue; 1718 } 1719 1720 // handle GATT over BR/EDR 1721 if (att_dispatch_client_can_send_now(gatt_client->con_handle) == false) { 1722 att_dispatch_client_request_can_send_now_event(gatt_client->con_handle); 1723 return; 1724 } 1725 packet_sent = gatt_client_run_for_gatt_client(gatt_client); 1726 if (packet_sent){ 1727 // request new permission 1728 att_dispatch_client_request_can_send_now_event(gatt_client->con_handle); 1729 // requeue client for fairness and exit 1730 // note: iterator has become invalid 1731 btstack_linked_list_remove(&gatt_client_connections, (btstack_linked_item_t *) gatt_client); 1732 btstack_linked_list_add_tail(&gatt_client_connections, (btstack_linked_item_t *) gatt_client); 1733 return; 1734 } 1735 break; 1736 #endif 1737 default: 1738 btstack_unreachable(); 1739 break; 1740 } 1741 1742 1743 } 1744 } 1745 1746 // emit complete event, used to avoid emitting event from API call 1747 static void gatt_client_emit_events(void * context){ 1748 UNUSED(context); 1749 btstack_linked_item_t *it; 1750 for (it = (btstack_linked_item_t *) gatt_client_connections; it != NULL; it = it->next) { 1751 gatt_client_t *gatt_client = (gatt_client_t *) it; 1752 if (gatt_client->state == P_W2_EMIT_QUERY_COMPLETE_EVENT){ 1753 gatt_client->state = P_READY; 1754 emit_gatt_complete_event(gatt_client, ATT_ERROR_SUCCESS); 1755 } 1756 } 1757 } 1758 1759 static void gatt_client_report_error_if_pending(gatt_client_t *gatt_client, uint8_t att_error_code) { 1760 if (is_ready(gatt_client)) return; 1761 gatt_client_handle_transaction_complete(gatt_client, att_error_code); 1762 } 1763 1764 static void gatt_client_handle_reencryption_complete(const uint8_t * packet){ 1765 hci_con_handle_t con_handle = sm_event_reencryption_complete_get_handle(packet); 1766 gatt_client_t * gatt_client = gatt_client_get_context_for_handle(con_handle); 1767 if (gatt_client == NULL) return; 1768 1769 // update security level 1770 gatt_client->security_level = gatt_client_le_security_level_for_connection(con_handle); 1771 1772 gatt_client->reencryption_result = sm_event_reencryption_complete_get_status(packet); 1773 gatt_client->reencryption_active = false; 1774 gatt_client->wait_for_authentication_complete = false; 1775 1776 if (gatt_client->state == P_READY) return; 1777 1778 switch (sm_event_reencryption_complete_get_status(packet)){ 1779 case ERROR_CODE_SUCCESS: 1780 log_info("re-encryption success, retry operation"); 1781 break; 1782 case ERROR_CODE_AUTHENTICATION_FAILURE: 1783 case ERROR_CODE_PIN_OR_KEY_MISSING: 1784 #if defined(ENABLE_GATT_CLIENT_PAIRING) && !defined(ENABLE_LE_PROACTIVE_AUTHENTICATION) 1785 if (gatt_client_required_security_level == LEVEL_0) { 1786 // re-encryption failed for reactive authentication with pairing and we have a pending client request 1787 // => try to resolve it by deleting bonding information if we started pairing before 1788 // delete bonding information 1789 int le_device_db_index = sm_le_device_index(gatt_client->con_handle); 1790 btstack_assert(le_device_db_index >= 0); 1791 log_info("reactive auth with pairing: delete bonding and start pairing"); 1792 #ifdef ENABLE_LE_PRIVACY_ADDRESS_RESOLUTION 1793 hci_remove_le_device_db_entry_from_resolving_list((uint16_t) le_device_db_index); 1794 #endif 1795 le_device_db_remove(le_device_db_index); 1796 // trigger pairing again 1797 sm_request_pairing(gatt_client->con_handle); 1798 break; 1799 } 1800 #endif 1801 // report bonding information missing 1802 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_BONDING_INFORMATION_MISSING); 1803 break; 1804 default: 1805 // report bonding information missing 1806 gatt_client_handle_transaction_complete(gatt_client, gatt_client->pending_error_code); 1807 break; 1808 } 1809 } 1810 1811 static void gatt_client_handle_disconnection_complete(const uint8_t * packet){ 1812 log_info("GATT Client: HCI_EVENT_DISCONNECTION_COMPLETE"); 1813 hci_con_handle_t con_handle = little_endian_read_16(packet,3); 1814 gatt_client_t * gatt_client = gatt_client_get_context_for_handle(con_handle); 1815 if (gatt_client == NULL) return; 1816 1817 gatt_client_report_error_if_pending(gatt_client, ATT_ERROR_HCI_DISCONNECT_RECEIVED); 1818 gatt_client_timeout_stop(gatt_client); 1819 btstack_linked_list_remove(&gatt_client_connections, (btstack_linked_item_t *) gatt_client); 1820 btstack_memory_gatt_client_free(gatt_client); 1821 } 1822 1823 static void gatt_client_event_packet_handler(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size){ 1824 UNUSED(channel); // ok: handling own l2cap events 1825 UNUSED(size); // ok: there is no channel 1826 1827 if (packet_type != HCI_EVENT_PACKET) return; 1828 1829 hci_con_handle_t con_handle; 1830 gatt_client_t * gatt_client; 1831 switch (hci_event_packet_get_type(packet)) { 1832 case HCI_EVENT_DISCONNECTION_COMPLETE: 1833 gatt_client_handle_disconnection_complete(packet); 1834 break; 1835 1836 // Pairing complete (with/without bonding=storing of pairing information) 1837 case SM_EVENT_PAIRING_COMPLETE: 1838 con_handle = sm_event_pairing_complete_get_handle(packet); 1839 gatt_client = gatt_client_get_context_for_handle(con_handle); 1840 if (gatt_client == NULL) break; 1841 1842 // update security level 1843 gatt_client->security_level = gatt_client_le_security_level_for_connection(con_handle); 1844 1845 if (gatt_client->wait_for_authentication_complete){ 1846 gatt_client->wait_for_authentication_complete = false; 1847 if (sm_event_pairing_complete_get_status(packet) != ERROR_CODE_SUCCESS){ 1848 log_info("pairing failed, report previous error 0x%x", gatt_client->pending_error_code); 1849 gatt_client_report_error_if_pending(gatt_client, gatt_client->pending_error_code); 1850 } else { 1851 log_info("pairing success, retry operation"); 1852 } 1853 } 1854 break; 1855 1856 #ifdef ENABLE_LE_SIGNED_WRITE 1857 // Identity Resolving completed (no code, gatt_client_run will continue) 1858 case SM_EVENT_IDENTITY_RESOLVING_SUCCEEDED: 1859 case SM_EVENT_IDENTITY_RESOLVING_FAILED: 1860 break; 1861 #endif 1862 1863 // re-encryption started 1864 case SM_EVENT_REENCRYPTION_STARTED: 1865 con_handle = sm_event_reencryption_complete_get_handle(packet); 1866 gatt_client = gatt_client_get_context_for_handle(con_handle); 1867 if (gatt_client == NULL) break; 1868 1869 gatt_client->reencryption_active = true; 1870 gatt_client->reencryption_result = ERROR_CODE_SUCCESS; 1871 break; 1872 1873 // re-encryption complete 1874 case SM_EVENT_REENCRYPTION_COMPLETE: 1875 gatt_client_handle_reencryption_complete(packet); 1876 break; 1877 default: 1878 break; 1879 } 1880 1881 gatt_client_run(); 1882 } 1883 1884 static void gatt_client_handle_att_read_response(gatt_client_t *gatt_client, uint8_t *packet, uint16_t size) { 1885 switch (gatt_client->state) { 1886 case P_W4_INCLUDED_SERVICE_UUID_WITH_QUERY_RESULT: 1887 if (size >= 17) { 1888 uint8_t uuid128[16]; 1889 reverse_128(&packet[1], uuid128); 1890 report_gatt_included_service_uuid128(gatt_client, gatt_client->start_group_handle, uuid128); 1891 } 1892 trigger_next_included_service_query(gatt_client, gatt_client->start_group_handle); 1893 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 1894 break; 1895 1896 case P_W4_READ_CHARACTERISTIC_VALUE_RESULT: 1897 report_gatt_characteristic_value(gatt_client, gatt_client->attribute_handle, &packet[1], size - 1u); 1898 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 1899 break; 1900 1901 case P_W4_READ_CHARACTERISTIC_DESCRIPTOR_RESULT: 1902 report_gatt_characteristic_descriptor(gatt_client, gatt_client->attribute_handle, &packet[1], 1903 size - 1u, 0u); 1904 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 1905 break; 1906 1907 // Use ATT_READ_REQUEST for first blob of Read Long Characteristic 1908 case P_W4_READ_BLOB_RESULT: 1909 report_gatt_long_characteristic_value_blob(gatt_client, gatt_client->attribute_handle, &packet[1], 1910 size - 1u, gatt_client->attribute_offset); 1911 trigger_next_blob_query(gatt_client, P_W2_SEND_READ_BLOB_QUERY, size - 1u); 1912 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 1913 break; 1914 1915 // Use ATT_READ_REQUEST for first blob of Read Long Characteristic Descriptor 1916 case P_W4_READ_BLOB_CHARACTERISTIC_DESCRIPTOR_RESULT: 1917 report_gatt_long_characteristic_descriptor(gatt_client, gatt_client->attribute_handle, &packet[1], 1918 size - 1u, gatt_client->attribute_offset); 1919 trigger_next_blob_query(gatt_client, P_W2_SEND_READ_BLOB_CHARACTERISTIC_DESCRIPTOR_QUERY, 1920 size - 1u); 1921 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 1922 break; 1923 1924 default: 1925 break; 1926 } 1927 } 1928 1929 static void gatt_client_handle_att_read_by_type_response(gatt_client_t *gatt_client, uint8_t *packet, uint16_t size) { 1930 switch (gatt_client->state) { 1931 case P_W4_ALL_CHARACTERISTICS_OF_SERVICE_QUERY_RESULT: 1932 report_gatt_characteristics(gatt_client, packet, size); 1933 trigger_next_characteristic_query(gatt_client, 1934 get_last_result_handle_from_characteristics_list(packet, size)); 1935 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done, or by ATT_ERROR 1936 break; 1937 case P_W4_CHARACTERISTIC_WITH_UUID_QUERY_RESULT: 1938 report_gatt_characteristics(gatt_client, packet, size); 1939 trigger_next_characteristic_query(gatt_client, 1940 get_last_result_handle_from_characteristics_list(packet, size)); 1941 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done, or by ATT_ERROR 1942 break; 1943 case P_W4_INCLUDED_SERVICE_QUERY_RESULT: { 1944 if (size < 2u) break; 1945 uint16_t uuid16 = 0; 1946 uint16_t pair_size = packet[1]; 1947 1948 if (pair_size == 6u) { 1949 if (size < 8u) break; 1950 // UUIDs not available, query first included service 1951 gatt_client->start_group_handle = little_endian_read_16(packet, 2); // ready for next query 1952 gatt_client->query_start_handle = little_endian_read_16(packet, 4); 1953 gatt_client->query_end_handle = little_endian_read_16(packet, 6); 1954 gatt_client->state = P_W2_SEND_INCLUDED_SERVICE_WITH_UUID_QUERY; 1955 break; 1956 } 1957 1958 if (pair_size != 8u) break; 1959 1960 // UUIDs included, report all of them 1961 uint16_t offset; 1962 for (offset = 2u; (offset + 8u) <= size; offset += pair_size) { 1963 uint16_t include_handle = little_endian_read_16(packet, offset); 1964 gatt_client->query_start_handle = little_endian_read_16(packet, offset + 2u); 1965 gatt_client->query_end_handle = little_endian_read_16(packet, offset + 4u); 1966 uuid16 = little_endian_read_16(packet, offset + 6u); 1967 report_gatt_included_service_uuid16(gatt_client, include_handle, uuid16); 1968 } 1969 1970 trigger_next_included_service_query(gatt_client, 1971 get_last_result_handle_from_included_services_list(packet, 1972 size)); 1973 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 1974 break; 1975 } 1976 #ifndef ENABLE_GATT_FIND_INFORMATION_FOR_CCC_DISCOVERY 1977 case P_W4_READ_CLIENT_CHARACTERISTIC_CONFIGURATION_QUERY_RESULT: 1978 gatt_client->client_characteristic_configuration_handle = little_endian_read_16(packet, 2); 1979 gatt_client->state = P_W2_WRITE_CLIENT_CHARACTERISTIC_CONFIGURATION; 1980 break; 1981 #endif 1982 case P_W4_READ_BY_TYPE_RESPONSE: { 1983 uint16_t pair_size = packet[1]; 1984 // set last result handle to last valid handle, only used if pair_size invalid 1985 uint16_t last_result_handle = 0xffff; 1986 if (pair_size > 2) { 1987 uint16_t offset; 1988 for (offset = 2; offset < size; offset += pair_size) { 1989 uint16_t value_handle = little_endian_read_16(packet, offset); 1990 report_gatt_characteristic_value(gatt_client, value_handle, &packet[offset + 2u], 1991 pair_size - 2u); 1992 last_result_handle = value_handle; 1993 } 1994 } 1995 trigger_next_read_by_type_query(gatt_client, last_result_handle); 1996 break; 1997 } 1998 default: 1999 break; 2000 } 2001 } 2002 2003 static void gatt_client_handle_att_write_response(gatt_client_t *gatt_client) { 2004 switch (gatt_client->state) { 2005 case P_W4_WRITE_CHARACTERISTIC_VALUE_RESULT: 2006 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 2007 break; 2008 case P_W4_CLIENT_CHARACTERISTIC_CONFIGURATION_RESULT: 2009 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 2010 break; 2011 case P_W4_WRITE_CHARACTERISTIC_DESCRIPTOR_RESULT: 2012 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 2013 break; 2014 default: 2015 break; 2016 } 2017 } 2018 2019 static void gatt_client_handle_att_response(gatt_client_t * gatt_client, uint8_t * packet, uint16_t size) { 2020 uint8_t att_status; 2021 switch (packet[0]) { 2022 case ATT_EXCHANGE_MTU_RESPONSE: { 2023 if (size < 3u) break; 2024 bool update_gatt_server_att_mtu = false; 2025 uint16_t remote_rx_mtu = little_endian_read_16(packet, 1); 2026 uint16_t local_rx_mtu = l2cap_max_le_mtu(); 2027 switch (gatt_client->bearer_type){ 2028 case ATT_BEARER_UNENHANCED_LE: 2029 update_gatt_server_att_mtu = true; 2030 break; 2031 #ifdef ENABLE_GATT_OVER_CLASSIC 2032 case ATT_BEARER_UNENHANCED_CLASSIC: 2033 local_rx_mtu = gatt_client->mtu; 2034 break; 2035 #endif 2036 default: 2037 btstack_unreachable(); 2038 break; 2039 } 2040 2041 uint16_t mtu = (remote_rx_mtu < local_rx_mtu) ? remote_rx_mtu : local_rx_mtu; 2042 2043 // set gatt client mtu 2044 gatt_client->mtu = mtu; 2045 gatt_client->mtu_state = MTU_EXCHANGED; 2046 2047 if (update_gatt_server_att_mtu){ 2048 // set per connection mtu state - for fixed channel 2049 hci_connection_t *hci_connection = hci_connection_for_handle(gatt_client->con_handle); 2050 hci_connection->att_connection.mtu = gatt_client->mtu; 2051 hci_connection->att_connection.mtu_exchanged = true; 2052 } 2053 emit_gatt_mtu_exchanged_result_event(gatt_client, gatt_client->mtu); 2054 break; 2055 } 2056 case ATT_READ_BY_GROUP_TYPE_RESPONSE: 2057 switch (gatt_client->state) { 2058 case P_W4_SERVICE_QUERY_RESULT: 2059 report_gatt_services(gatt_client, packet, size); 2060 trigger_next_service_query(gatt_client, get_last_result_handle_from_service_list(packet, size)); 2061 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 2062 break; 2063 default: 2064 break; 2065 } 2066 break; 2067 case ATT_HANDLE_VALUE_NOTIFICATION: 2068 if (size < 3u) return; 2069 report_gatt_notification(gatt_client, little_endian_read_16(packet, 1u), &packet[3], size - 3u); 2070 return; 2071 #ifdef ENABLE_GATT_OVER_EATT 2072 case ATT_MULTIPLE_HANDLE_VALUE_NTF: 2073 if (size >= 5u) { 2074 uint16_t offset = 1; 2075 while (true){ 2076 uint16_t value_handle = little_endian_read_16(packet, offset); 2077 offset += 2; 2078 uint16_t value_length = little_endian_read_16(packet, offset); 2079 offset += 2; 2080 if ((offset + value_length) > size) break; 2081 report_gatt_notification(gatt_client, value_handle, &packet[offset], value_length); 2082 offset += value_length; 2083 } 2084 } 2085 return; 2086 #endif 2087 case ATT_HANDLE_VALUE_INDICATION: 2088 if (size < 3u) break; 2089 report_gatt_indication(gatt_client, little_endian_read_16(packet, 1u), &packet[3], size - 3u); 2090 gatt_client->send_confirmation = true; 2091 break; 2092 case ATT_READ_BY_TYPE_RESPONSE: 2093 gatt_client_handle_att_read_by_type_response(gatt_client, packet, size); 2094 break; 2095 case ATT_READ_RESPONSE: 2096 gatt_client_handle_att_read_response(gatt_client, packet, size); 2097 break; 2098 case ATT_FIND_BY_TYPE_VALUE_RESPONSE: { 2099 uint8_t pair_size = 4; 2100 int i; 2101 uint16_t start_group_handle; 2102 uint16_t end_group_handle = 0xffff; // asserts GATT_EVENT_QUERY_COMPLETE is emitted if no results 2103 for (i = 1u; (i + pair_size) <= size; i += pair_size) { 2104 start_group_handle = little_endian_read_16(packet, i); 2105 end_group_handle = little_endian_read_16(packet, i + 2); 2106 emit_gatt_service_query_result_event(gatt_client, start_group_handle, end_group_handle, 2107 gatt_client->uuid128); 2108 } 2109 trigger_next_service_by_uuid_query(gatt_client, end_group_handle); 2110 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 2111 break; 2112 } 2113 case ATT_FIND_INFORMATION_REPLY: { 2114 if (size < 2u) break; 2115 2116 uint8_t pair_size = 4; 2117 if (packet[1u] == 2u) { 2118 pair_size = 18; 2119 } 2120 uint16_t offset = 2; 2121 2122 if (size < (pair_size + offset)) break; 2123 uint16_t last_descriptor_handle = little_endian_read_16(packet, size - pair_size); 2124 2125 #ifdef ENABLE_GATT_FIND_INFORMATION_FOR_CCC_DISCOVERY 2126 log_info("ENABLE_GATT_FIND_INFORMATION_FOR_CCC_DISCOVERY, state %x", gatt_client->state); 2127 if (gatt_client->state == P_W4_FIND_CLIENT_CHARACTERISTIC_CONFIGURATION_QUERY_RESULT){ 2128 // iterate over descriptors looking for CCC 2129 if (pair_size == 4){ 2130 while ((offset + 4) <= size){ 2131 uint16_t uuid16 = little_endian_read_16(packet, offset + 2); 2132 if (uuid16 == GATT_CLIENT_CHARACTERISTICS_CONFIGURATION){ 2133 gatt_client->client_characteristic_configuration_handle = little_endian_read_16(packet, offset); 2134 gatt_client->state = P_W2_WRITE_CLIENT_CHARACTERISTIC_CONFIGURATION; 2135 log_info("CCC found %x", gatt_client->client_characteristic_configuration_handle); 2136 break; 2137 } 2138 offset += pair_size; 2139 } 2140 } 2141 if (is_query_done(gatt_client, last_descriptor_handle)){ 2142 2143 } else { 2144 // next 2145 gatt_client->start_group_handle = last_descriptor_handle + 1; 2146 gatt_client->state = P_W2_SEND_FIND_CLIENT_CHARACTERISTIC_CONFIGURATION_QUERY; 2147 } 2148 break; 2149 } 2150 #endif 2151 report_gatt_all_characteristic_descriptors(gatt_client, &packet[2], size - 2u, pair_size); 2152 trigger_next_characteristic_descriptor_query(gatt_client, last_descriptor_handle); 2153 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 2154 break; 2155 } 2156 2157 case ATT_WRITE_RESPONSE: 2158 gatt_client_handle_att_write_response(gatt_client); 2159 break; 2160 2161 case ATT_READ_BLOB_RESPONSE: { 2162 uint16_t received_blob_length = size - 1u; 2163 switch (gatt_client->state) { 2164 case P_W4_READ_BLOB_RESULT: 2165 report_gatt_long_characteristic_value_blob(gatt_client, gatt_client->attribute_handle, &packet[1], 2166 received_blob_length, gatt_client->attribute_offset); 2167 trigger_next_blob_query(gatt_client, P_W2_SEND_READ_BLOB_QUERY, received_blob_length); 2168 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 2169 break; 2170 case P_W4_READ_BLOB_CHARACTERISTIC_DESCRIPTOR_RESULT: 2171 report_gatt_long_characteristic_descriptor(gatt_client, gatt_client->attribute_handle, 2172 &packet[1], received_blob_length, 2173 gatt_client->attribute_offset); 2174 trigger_next_blob_query(gatt_client, P_W2_SEND_READ_BLOB_CHARACTERISTIC_DESCRIPTOR_QUERY, 2175 received_blob_length); 2176 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 2177 break; 2178 default: 2179 break; 2180 } 2181 break; 2182 } 2183 case ATT_PREPARE_WRITE_RESPONSE: 2184 switch (gatt_client->state) { 2185 case P_W4_PREPARE_WRITE_SINGLE_RESULT: 2186 if (is_value_valid(gatt_client, packet, size)) { 2187 att_status = ATT_ERROR_SUCCESS; 2188 } else { 2189 att_status = ATT_ERROR_DATA_MISMATCH; 2190 } 2191 gatt_client_handle_transaction_complete(gatt_client, att_status); 2192 break; 2193 2194 case P_W4_PREPARE_WRITE_RESULT: { 2195 gatt_client->attribute_offset = little_endian_read_16(packet, 3); 2196 trigger_next_prepare_write_query(gatt_client, P_W2_PREPARE_WRITE, P_W2_EXECUTE_PREPARED_WRITE); 2197 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 2198 break; 2199 } 2200 case P_W4_PREPARE_WRITE_CHARACTERISTIC_DESCRIPTOR_RESULT: { 2201 gatt_client->attribute_offset = little_endian_read_16(packet, 3); 2202 trigger_next_prepare_write_query(gatt_client, P_W2_PREPARE_WRITE_CHARACTERISTIC_DESCRIPTOR, 2203 P_W2_EXECUTE_PREPARED_WRITE_CHARACTERISTIC_DESCRIPTOR); 2204 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 2205 break; 2206 } 2207 case P_W4_PREPARE_RELIABLE_WRITE_RESULT: { 2208 if (is_value_valid(gatt_client, packet, size)) { 2209 gatt_client->attribute_offset = little_endian_read_16(packet, 3); 2210 trigger_next_prepare_write_query(gatt_client, P_W2_PREPARE_RELIABLE_WRITE, 2211 P_W2_EXECUTE_PREPARED_WRITE); 2212 // GATT_EVENT_QUERY_COMPLETE is emitted by trigger_next_xxx when done 2213 break; 2214 } 2215 gatt_client->state = P_W2_CANCEL_PREPARED_WRITE_DATA_MISMATCH; 2216 break; 2217 } 2218 default: 2219 break; 2220 } 2221 break; 2222 2223 case ATT_EXECUTE_WRITE_RESPONSE: 2224 switch (gatt_client->state) { 2225 case P_W4_EXECUTE_PREPARED_WRITE_RESULT: 2226 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 2227 break; 2228 case P_W4_CANCEL_PREPARED_WRITE_RESULT: 2229 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 2230 break; 2231 case P_W4_CANCEL_PREPARED_WRITE_DATA_MISMATCH_RESULT: 2232 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_DATA_MISMATCH); 2233 break; 2234 case P_W4_EXECUTE_PREPARED_WRITE_CHARACTERISTIC_DESCRIPTOR_RESULT: 2235 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 2236 break; 2237 default: 2238 break; 2239 2240 } 2241 break; 2242 2243 case ATT_READ_MULTIPLE_RESPONSE: 2244 switch (gatt_client->state) { 2245 case P_W4_READ_MULTIPLE_RESPONSE: 2246 report_gatt_characteristic_value(gatt_client, 0u, &packet[1], size - 1u); 2247 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 2248 break; 2249 default: 2250 break; 2251 } 2252 break; 2253 2254 #ifdef ENABLE_GATT_OVER_EATT 2255 case ATT_READ_MULTIPLE_VARIABLE_RSP: 2256 switch (gatt_client->state) { 2257 case P_W4_READ_MULTIPLE_VARIABLE_RESPONSE: 2258 report_gatt_characteristic_value(gatt_client, 0u, &packet[1], size - 1u); 2259 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 2260 break; 2261 default: 2262 break; 2263 } 2264 break; 2265 #endif 2266 2267 case ATT_ERROR_RESPONSE: 2268 if (size < 5u) return; 2269 att_status = packet[4]; 2270 switch (att_status) { 2271 case ATT_ERROR_ATTRIBUTE_NOT_FOUND: { 2272 switch (gatt_client->state) { 2273 case P_W4_SERVICE_QUERY_RESULT: 2274 case P_W4_SERVICE_WITH_UUID_RESULT: 2275 case P_W4_INCLUDED_SERVICE_QUERY_RESULT: 2276 case P_W4_ALL_CHARACTERISTIC_DESCRIPTORS_QUERY_RESULT: 2277 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 2278 break; 2279 case P_W4_ALL_CHARACTERISTICS_OF_SERVICE_QUERY_RESULT: 2280 case P_W4_CHARACTERISTIC_WITH_UUID_QUERY_RESULT: 2281 report_gatt_characteristic_end_found(gatt_client, gatt_client->end_group_handle); 2282 gatt_client_handle_transaction_complete(gatt_client, ATT_ERROR_SUCCESS); 2283 break; 2284 case P_W4_READ_BY_TYPE_RESPONSE: 2285 if (gatt_client->start_group_handle == gatt_client->query_start_handle) { 2286 att_status = ATT_ERROR_ATTRIBUTE_NOT_FOUND; 2287 } else { 2288 att_status = ATT_ERROR_SUCCESS; 2289 } 2290 gatt_client_handle_transaction_complete(gatt_client, att_status); 2291 break; 2292 default: 2293 gatt_client_report_error_if_pending(gatt_client, att_status); 2294 break; 2295 } 2296 break; 2297 } 2298 2299 #ifdef ENABLE_GATT_CLIENT_PAIRING 2300 2301 case ATT_ERROR_INSUFFICIENT_AUTHENTICATION: 2302 case ATT_ERROR_INSUFFICIENT_ENCRYPTION_KEY_SIZE: 2303 case ATT_ERROR_INSUFFICIENT_ENCRYPTION: { 2304 2305 // security too low 2306 if (gatt_client->security_counter > 0) { 2307 gatt_client_report_error_if_pending(gatt_client, att_status); 2308 break; 2309 } 2310 // start security 2311 gatt_client->security_counter++; 2312 2313 // setup action 2314 int retry = 1; 2315 switch (gatt_client->state){ 2316 case P_W4_READ_CHARACTERISTIC_VALUE_RESULT: 2317 gatt_client->state = P_W2_SEND_READ_CHARACTERISTIC_VALUE_QUERY ; 2318 break; 2319 case P_W4_READ_BLOB_RESULT: 2320 gatt_client->state = P_W2_SEND_READ_BLOB_QUERY; 2321 break; 2322 case P_W4_READ_BY_TYPE_RESPONSE: 2323 gatt_client->state = P_W2_SEND_READ_BY_TYPE_REQUEST; 2324 break; 2325 case P_W4_READ_MULTIPLE_RESPONSE: 2326 gatt_client->state = P_W2_SEND_READ_MULTIPLE_REQUEST; 2327 break; 2328 case P_W4_READ_MULTIPLE_VARIABLE_RESPONSE: 2329 gatt_client->state = P_W2_SEND_READ_MULTIPLE_VARIABLE_REQUEST; 2330 break; 2331 case P_W4_WRITE_CHARACTERISTIC_VALUE_RESULT: 2332 gatt_client->state = P_W2_SEND_WRITE_CHARACTERISTIC_VALUE; 2333 break; 2334 case P_W4_PREPARE_WRITE_RESULT: 2335 gatt_client->state = P_W2_PREPARE_WRITE; 2336 break; 2337 case P_W4_PREPARE_WRITE_SINGLE_RESULT: 2338 gatt_client->state = P_W2_PREPARE_WRITE_SINGLE; 2339 break; 2340 case P_W4_PREPARE_RELIABLE_WRITE_RESULT: 2341 gatt_client->state = P_W2_PREPARE_RELIABLE_WRITE; 2342 break; 2343 case P_W4_EXECUTE_PREPARED_WRITE_RESULT: 2344 gatt_client->state = P_W2_EXECUTE_PREPARED_WRITE; 2345 break; 2346 case P_W4_CANCEL_PREPARED_WRITE_RESULT: 2347 gatt_client->state = P_W2_CANCEL_PREPARED_WRITE; 2348 break; 2349 case P_W4_CANCEL_PREPARED_WRITE_DATA_MISMATCH_RESULT: 2350 gatt_client->state = P_W2_CANCEL_PREPARED_WRITE_DATA_MISMATCH; 2351 break; 2352 case P_W4_READ_CHARACTERISTIC_DESCRIPTOR_RESULT: 2353 gatt_client->state = P_W2_SEND_READ_CHARACTERISTIC_DESCRIPTOR_QUERY; 2354 break; 2355 case P_W4_READ_BLOB_CHARACTERISTIC_DESCRIPTOR_RESULT: 2356 gatt_client->state = P_W2_SEND_READ_BLOB_CHARACTERISTIC_DESCRIPTOR_QUERY; 2357 break; 2358 case P_W4_WRITE_CHARACTERISTIC_DESCRIPTOR_RESULT: 2359 gatt_client->state = P_W2_SEND_WRITE_CHARACTERISTIC_DESCRIPTOR; 2360 break; 2361 case P_W4_CLIENT_CHARACTERISTIC_CONFIGURATION_RESULT: 2362 gatt_client->state = P_W2_WRITE_CLIENT_CHARACTERISTIC_CONFIGURATION; 2363 break; 2364 case P_W4_PREPARE_WRITE_CHARACTERISTIC_DESCRIPTOR_RESULT: 2365 gatt_client->state = P_W2_PREPARE_WRITE_CHARACTERISTIC_DESCRIPTOR; 2366 break; 2367 case P_W4_EXECUTE_PREPARED_WRITE_CHARACTERISTIC_DESCRIPTOR_RESULT: 2368 gatt_client->state = P_W2_EXECUTE_PREPARED_WRITE_CHARACTERISTIC_DESCRIPTOR; 2369 break; 2370 #ifdef ENABLE_LE_SIGNED_WRITE 2371 case P_W4_SEND_SIGNED_WRITE_DONE: 2372 gatt_client->state = P_W2_SEND_SIGNED_WRITE; 2373 break; 2374 #endif 2375 default: 2376 log_info("retry not supported for state %x", gatt_client->state); 2377 retry = 0; 2378 break; 2379 } 2380 2381 if (!retry) { 2382 gatt_client_report_error_if_pending(gatt_client, att_status); 2383 break; 2384 } 2385 2386 log_info("security error, start pairing"); 2387 2388 // start pairing for higher security level 2389 gatt_client->wait_for_authentication_complete = true; 2390 gatt_client->pending_error_code = att_status; 2391 sm_request_pairing(gatt_client->con_handle); 2392 break; 2393 } 2394 #endif 2395 2396 // nothing we can do about that 2397 case ATT_ERROR_INSUFFICIENT_AUTHORIZATION: 2398 default: 2399 gatt_client_report_error_if_pending(gatt_client, att_status); 2400 break; 2401 } 2402 break; 2403 2404 default: 2405 log_info("ATT Handler, unhandled response type 0x%02x", packet[0]); 2406 break; 2407 } 2408 } 2409 2410 static void gatt_client_att_packet_handler(uint8_t packet_type, uint16_t handle, uint8_t *packet, uint16_t size) { 2411 gatt_client_t *gatt_client; 2412 #ifdef ENABLE_GATT_OVER_CLASSIC 2413 uint8_t status; 2414 hci_connection_t * hci_connection; 2415 hci_con_handle_t con_handle; 2416 #endif 2417 2418 if (size < 1u) return; 2419 switch (packet_type){ 2420 case HCI_EVENT_PACKET: 2421 switch (hci_event_packet_get_type(packet)) { 2422 #ifdef ENABLE_GATT_OVER_CLASSIC 2423 case L2CAP_EVENT_CHANNEL_OPENED: 2424 status = l2cap_event_channel_opened_get_status(packet); 2425 gatt_client = gatt_client_get_context_for_l2cap_cid(l2cap_event_channel_opened_get_local_cid(packet)); 2426 if (gatt_client != NULL){ 2427 con_handle = l2cap_event_channel_opened_get_handle(packet); 2428 hci_connection = hci_connection_for_handle(con_handle); 2429 if (status == L2CAP_CONNECTION_RESPONSE_RESULT_REFUSED_RESOURCES){ 2430 if ((hci_connection != NULL) && hci_connection->att_server.incoming_connection_request) { 2431 log_info("Collision, retry in 100ms"); 2432 gatt_client->state = P_W2_L2CAP_CONNECT; 2433 // set timer for retry 2434 btstack_run_loop_set_timer(&gatt_client->gc_timeout, GATT_CLIENT_COLLISION_BACKOFF_MS); 2435 btstack_run_loop_set_timer_handler(&gatt_client->gc_timeout, gatt_client_classic_retry); 2436 btstack_run_loop_add_timer(&gatt_client->gc_timeout); 2437 break; 2438 } 2439 } 2440 // if status != 0, gatt_client will be discarded 2441 gatt_client->state = P_READY; 2442 gatt_client->con_handle = l2cap_event_channel_opened_get_handle(packet); 2443 gatt_client->mtu = l2cap_event_channel_opened_get_remote_mtu(packet); 2444 gatt_client_classic_handle_connected(gatt_client, status); 2445 } 2446 break; 2447 case L2CAP_EVENT_CHANNEL_CLOSED: 2448 gatt_client = gatt_client_get_context_for_l2cap_cid(l2cap_event_channel_closed_get_local_cid(packet)); 2449 if (gatt_client != NULL){ 2450 // discard gatt client object 2451 gatt_client_classic_handle_disconnected(gatt_client); 2452 } 2453 break; 2454 #endif 2455 case L2CAP_EVENT_CAN_SEND_NOW: 2456 gatt_client_run(); 2457 break; 2458 // att_server has negotiated the mtu for this connection, cache if context exists 2459 case ATT_EVENT_MTU_EXCHANGE_COMPLETE: 2460 if (size < 6u) break; 2461 gatt_client = gatt_client_get_context_for_handle(handle); 2462 if (gatt_client != NULL) { 2463 gatt_client->mtu = little_endian_read_16(packet, 4); 2464 } 2465 break; 2466 default: 2467 break; 2468 } 2469 break; 2470 2471 case ATT_DATA_PACKET: 2472 // special cases: notifications & indications motivate creating context 2473 switch (packet[0]) { 2474 case ATT_HANDLE_VALUE_NOTIFICATION: 2475 case ATT_HANDLE_VALUE_INDICATION: 2476 gatt_client_provide_context_for_handle(handle, &gatt_client); 2477 break; 2478 default: 2479 gatt_client = gatt_client_get_context_for_handle(handle); 2480 break; 2481 } 2482 2483 if (gatt_client != NULL) { 2484 gatt_client_handle_att_response(gatt_client, packet, size); 2485 gatt_client_run(); 2486 } 2487 break; 2488 2489 #ifdef ENABLE_GATT_OVER_CLASSIC 2490 case L2CAP_DATA_PACKET: 2491 gatt_client = gatt_client_get_context_for_l2cap_cid(handle); 2492 if (gatt_client != NULL){ 2493 gatt_client_handle_att_response(gatt_client, packet, size); 2494 gatt_client_run(); 2495 } 2496 break; 2497 #endif 2498 2499 default: 2500 break; 2501 } 2502 } 2503 2504 #ifdef ENABLE_LE_SIGNED_WRITE 2505 static void att_signed_write_handle_cmac_result(uint8_t hash[8]){ 2506 btstack_linked_list_iterator_t it; 2507 btstack_linked_list_iterator_init(&it, &gatt_client_connections); 2508 while (btstack_linked_list_iterator_has_next(&it)){ 2509 gatt_client_t * gatt_client = (gatt_client_t *) btstack_linked_list_iterator_next(&it); 2510 if (gatt_client->state == P_W4_CMAC_RESULT){ 2511 // store result 2512 (void)memcpy(gatt_client->cmac, hash, 8); 2513 // reverse_64(hash, gatt_client->cmac); 2514 gatt_client->state = P_W2_SEND_SIGNED_WRITE; 2515 gatt_client_run(); 2516 return; 2517 } 2518 } 2519 } 2520 2521 uint8_t gatt_client_signed_write_without_response(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t value_handle, uint16_t message_len, uint8_t * message){ 2522 gatt_client_t * gatt_client; 2523 uint8_t status = gatt_client_provide_context_for_handle(con_handle, &gatt_client); 2524 if (status != ERROR_CODE_SUCCESS){ 2525 return status; 2526 } 2527 if (is_ready(gatt_client) == 0){ 2528 return GATT_CLIENT_IN_WRONG_STATE; 2529 } 2530 2531 gatt_client->callback = callback; 2532 gatt_client->attribute_handle = value_handle; 2533 gatt_client->attribute_length = message_len; 2534 gatt_client->attribute_value = message; 2535 gatt_client->state = P_W4_IDENTITY_RESOLVING; 2536 gatt_client_run(); 2537 return ERROR_CODE_SUCCESS; 2538 } 2539 #endif 2540 2541 uint8_t gatt_client_discover_primary_services(btstack_packet_handler_t callback, hci_con_handle_t con_handle){ 2542 gatt_client_t * gatt_client; 2543 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2544 if (status != ERROR_CODE_SUCCESS){ 2545 return status; 2546 } 2547 2548 gatt_client->callback = callback; 2549 gatt_client->start_group_handle = 0x0001; 2550 gatt_client->end_group_handle = 0xffff; 2551 gatt_client->state = P_W2_SEND_SERVICE_QUERY; 2552 gatt_client->uuid16 = GATT_PRIMARY_SERVICE_UUID; 2553 gatt_client_run(); 2554 return ERROR_CODE_SUCCESS; 2555 } 2556 2557 uint8_t gatt_client_discover_secondary_services(btstack_packet_handler_t callback, hci_con_handle_t con_handle){ 2558 gatt_client_t * gatt_client; 2559 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2560 if (status != ERROR_CODE_SUCCESS){ 2561 return status; 2562 } 2563 2564 gatt_client->callback = callback; 2565 gatt_client->start_group_handle = 0x0001; 2566 gatt_client->end_group_handle = 0xffff; 2567 gatt_client->state = P_W2_SEND_SERVICE_QUERY; 2568 gatt_client->uuid16 = GATT_SECONDARY_SERVICE_UUID; 2569 gatt_client_run(); 2570 return ERROR_CODE_SUCCESS; 2571 } 2572 2573 uint8_t gatt_client_discover_primary_services_by_uuid16_with_context(btstack_packet_handler_t callback, hci_con_handle_t con_handle, 2574 uint16_t uuid16, uint16_t service_id, uint16_t connection_id){ 2575 gatt_client_t * gatt_client; 2576 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2577 if (status != ERROR_CODE_SUCCESS){ 2578 return status; 2579 } 2580 2581 gatt_client->callback = callback; 2582 gatt_client->service_id = service_id; 2583 gatt_client->connection_id = connection_id; 2584 gatt_client->start_group_handle = 0x0001; 2585 gatt_client->end_group_handle = 0xffff; 2586 gatt_client->state = P_W2_SEND_SERVICE_WITH_UUID_QUERY; 2587 gatt_client->uuid16 = uuid16; 2588 uuid_add_bluetooth_prefix((uint8_t*) &(gatt_client->uuid128), gatt_client->uuid16); 2589 gatt_client_run(); 2590 return ERROR_CODE_SUCCESS; 2591 } 2592 2593 uint8_t gatt_client_discover_primary_services_by_uuid16(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t uuid16){ 2594 return gatt_client_discover_primary_services_by_uuid16_with_context(callback, con_handle, uuid16, 0, 0); 2595 } 2596 2597 uint8_t gatt_client_discover_primary_services_by_uuid128(btstack_packet_handler_t callback, hci_con_handle_t con_handle, const uint8_t * uuid128){ 2598 gatt_client_t * gatt_client; 2599 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2600 if (status != ERROR_CODE_SUCCESS){ 2601 return status; 2602 } 2603 2604 gatt_client->callback = callback; 2605 gatt_client->start_group_handle = 0x0001; 2606 gatt_client->end_group_handle = 0xffff; 2607 gatt_client->uuid16 = 0; 2608 (void)memcpy(gatt_client->uuid128, uuid128, 16); 2609 gatt_client->state = P_W2_SEND_SERVICE_WITH_UUID_QUERY; 2610 gatt_client_run(); 2611 return ERROR_CODE_SUCCESS; 2612 } 2613 2614 uint8_t gatt_client_discover_characteristics_for_service_with_context(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_service_t * service, 2615 uint16_t service_id, uint16_t connection_id){ 2616 gatt_client_t * gatt_client; 2617 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2618 if (status != ERROR_CODE_SUCCESS){ 2619 return status; 2620 } 2621 2622 gatt_client->callback = callback; 2623 gatt_client->service_id = service_id; 2624 gatt_client->connection_id = connection_id; 2625 gatt_client->start_group_handle = service->start_group_handle; 2626 gatt_client->end_group_handle = service->end_group_handle; 2627 gatt_client->filter_with_uuid = false; 2628 gatt_client->characteristic_start_handle = 0; 2629 gatt_client->state = P_W2_SEND_ALL_CHARACTERISTICS_OF_SERVICE_QUERY; 2630 gatt_client_run(); 2631 return ERROR_CODE_SUCCESS; 2632 } 2633 2634 uint8_t gatt_client_discover_characteristics_for_service(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_service_t * service){ 2635 return gatt_client_discover_characteristics_for_service_with_context(callback, con_handle, service, 0, 0); 2636 } 2637 2638 uint8_t gatt_client_find_included_services_for_service_with_context(btstack_packet_handler_t callback, hci_con_handle_t con_handle, 2639 gatt_client_service_t * service, uint16_t service_id, uint16_t connection_id){ 2640 gatt_client_t * gatt_client; 2641 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2642 if (status != ERROR_CODE_SUCCESS){ 2643 return status; 2644 } 2645 2646 gatt_client->callback = callback; 2647 gatt_client->service_id = service_id; 2648 gatt_client->connection_id = connection_id; 2649 gatt_client->start_group_handle = service->start_group_handle; 2650 gatt_client->end_group_handle = service->end_group_handle; 2651 gatt_client->state = P_W2_SEND_INCLUDED_SERVICE_QUERY; 2652 2653 gatt_client_run(); 2654 return ERROR_CODE_SUCCESS; 2655 } 2656 2657 uint8_t gatt_client_find_included_services_for_service(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_service_t * service) { 2658 return gatt_client_find_included_services_for_service_with_context(callback, con_handle, service, 0, 0); 2659 } 2660 2661 uint8_t gatt_client_discover_characteristics_for_handle_range_by_uuid16(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t start_handle, uint16_t end_handle, uint16_t uuid16){ 2662 gatt_client_t * gatt_client; 2663 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2664 if (status != ERROR_CODE_SUCCESS){ 2665 return status; 2666 } 2667 2668 gatt_client->callback = callback; 2669 gatt_client->start_group_handle = start_handle; 2670 gatt_client->end_group_handle = end_handle; 2671 gatt_client->filter_with_uuid = true; 2672 gatt_client->uuid16 = uuid16; 2673 uuid_add_bluetooth_prefix((uint8_t*) &(gatt_client->uuid128), uuid16); 2674 gatt_client->characteristic_start_handle = 0; 2675 gatt_client->state = P_W2_SEND_CHARACTERISTIC_WITH_UUID_QUERY; 2676 gatt_client_run(); 2677 return ERROR_CODE_SUCCESS; 2678 } 2679 2680 uint8_t gatt_client_discover_characteristics_for_handle_range_by_uuid128(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t start_handle, uint16_t end_handle, const uint8_t * uuid128){ 2681 gatt_client_t * gatt_client; 2682 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2683 if (status != ERROR_CODE_SUCCESS){ 2684 return status; 2685 } 2686 2687 gatt_client->callback = callback; 2688 gatt_client->start_group_handle = start_handle; 2689 gatt_client->end_group_handle = end_handle; 2690 gatt_client->filter_with_uuid = true; 2691 gatt_client->uuid16 = 0; 2692 (void)memcpy(gatt_client->uuid128, uuid128, 16); 2693 gatt_client->characteristic_start_handle = 0; 2694 gatt_client->state = P_W2_SEND_CHARACTERISTIC_WITH_UUID_QUERY; 2695 gatt_client_run(); 2696 return ERROR_CODE_SUCCESS; 2697 } 2698 2699 2700 uint8_t gatt_client_discover_characteristics_for_service_by_uuid16(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_service_t * service, uint16_t uuid16){ 2701 return gatt_client_discover_characteristics_for_handle_range_by_uuid16(callback, con_handle, service->start_group_handle, service->end_group_handle, uuid16); 2702 } 2703 2704 uint8_t gatt_client_discover_characteristics_for_service_by_uuid128(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_service_t * service, const uint8_t * uuid128){ 2705 return gatt_client_discover_characteristics_for_handle_range_by_uuid128(callback, con_handle, service->start_group_handle, service->end_group_handle, uuid128); 2706 } 2707 2708 uint8_t gatt_client_discover_characteristic_descriptors_with_context(btstack_packet_handler_t callback, hci_con_handle_t con_handle, 2709 gatt_client_characteristic_t * characteristic, uint16_t service_id, uint16_t connection_id){ 2710 gatt_client_t * gatt_client; 2711 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2712 if (status != ERROR_CODE_SUCCESS){ 2713 return status; 2714 } 2715 2716 gatt_client->service_id = service_id; 2717 gatt_client->connection_id = connection_id; 2718 2719 // check if there is space for characteristics descriptors 2720 if (characteristic->end_handle > characteristic->value_handle){ 2721 gatt_client->callback = callback; 2722 gatt_client->start_group_handle = characteristic->value_handle + 1u; 2723 gatt_client->end_group_handle = characteristic->end_handle; 2724 gatt_client->state = P_W2_SEND_ALL_CHARACTERISTIC_DESCRIPTORS_QUERY; 2725 gatt_client_run(); 2726 } else { 2727 // schedule gatt complete event on next run loop iteration otherwise 2728 gatt_client->state = P_W2_EMIT_QUERY_COMPLETE_EVENT; 2729 gatt_client_deferred_event_emit.callback = gatt_client_emit_events; 2730 btstack_run_loop_execute_on_main_thread(&gatt_client_deferred_event_emit); 2731 } 2732 return ERROR_CODE_SUCCESS; 2733 } 2734 2735 uint8_t gatt_client_discover_characteristic_descriptors(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_characteristic_t * characteristic){ 2736 return gatt_client_discover_characteristic_descriptors_with_context(callback, con_handle, characteristic, 0, 0); 2737 } 2738 2739 uint8_t gatt_client_read_value_of_characteristic_using_value_handle_with_context(btstack_packet_handler_t callback, 2740 hci_con_handle_t con_handle, 2741 uint16_t value_handle, 2742 uint16_t service_id, 2743 uint16_t connection_id) { 2744 gatt_client_t * gatt_client; 2745 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2746 if (status != ERROR_CODE_SUCCESS){ 2747 return status; 2748 } 2749 2750 gatt_client->callback = callback; 2751 gatt_client->service_id = service_id; 2752 gatt_client->connection_id = connection_id; 2753 gatt_client->attribute_handle = value_handle; 2754 gatt_client->attribute_offset = 0; 2755 gatt_client->state = P_W2_SEND_READ_CHARACTERISTIC_VALUE_QUERY; 2756 gatt_client_run(); 2757 return ERROR_CODE_SUCCESS; 2758 } 2759 2760 uint8_t gatt_client_read_value_of_characteristic_using_value_handle(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t value_handle){ 2761 return gatt_client_read_value_of_characteristic_using_value_handle_with_context(callback, con_handle, value_handle, 0, 0); 2762 2763 } 2764 2765 uint8_t gatt_client_read_value_of_characteristics_by_uuid16(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t start_handle, uint16_t end_handle, uint16_t uuid16){ 2766 gatt_client_t * gatt_client; 2767 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2768 if (status != ERROR_CODE_SUCCESS){ 2769 return status; 2770 } 2771 2772 gatt_client->callback = callback; 2773 gatt_client->start_group_handle = start_handle; 2774 gatt_client->end_group_handle = end_handle; 2775 gatt_client->query_start_handle = start_handle; 2776 gatt_client->query_end_handle = end_handle; 2777 gatt_client->uuid16 = uuid16; 2778 uuid_add_bluetooth_prefix((uint8_t*) &(gatt_client->uuid128), uuid16); 2779 gatt_client->state = P_W2_SEND_READ_BY_TYPE_REQUEST; 2780 gatt_client_run(); 2781 return ERROR_CODE_SUCCESS; 2782 } 2783 2784 uint8_t gatt_client_read_value_of_characteristics_by_uuid128(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t start_handle, uint16_t end_handle, const uint8_t * uuid128){ 2785 gatt_client_t * gatt_client; 2786 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2787 if (status != ERROR_CODE_SUCCESS){ 2788 return status; 2789 } 2790 2791 gatt_client->callback = callback; 2792 gatt_client->start_group_handle = start_handle; 2793 gatt_client->end_group_handle = end_handle; 2794 gatt_client->query_start_handle = start_handle; 2795 gatt_client->query_end_handle = end_handle; 2796 gatt_client->uuid16 = 0; 2797 (void)memcpy(gatt_client->uuid128, uuid128, 16); 2798 gatt_client->state = P_W2_SEND_READ_BY_TYPE_REQUEST; 2799 gatt_client_run(); 2800 return ERROR_CODE_SUCCESS; 2801 } 2802 2803 2804 uint8_t gatt_client_read_value_of_characteristic(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_characteristic_t * characteristic){ 2805 return gatt_client_read_value_of_characteristic_using_value_handle(callback, con_handle, characteristic->value_handle); 2806 } 2807 2808 uint8_t gatt_client_read_long_value_of_characteristic_using_value_handle_with_offset(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t value_handle, uint16_t offset){ 2809 gatt_client_t * gatt_client; 2810 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2811 if (status != ERROR_CODE_SUCCESS){ 2812 return status; 2813 } 2814 2815 gatt_client->callback = callback; 2816 gatt_client->attribute_handle = value_handle; 2817 gatt_client->attribute_offset = offset; 2818 gatt_client->state = P_W2_SEND_READ_BLOB_QUERY; 2819 gatt_client_run(); 2820 return ERROR_CODE_SUCCESS; 2821 } 2822 uint8_t gatt_client_read_long_value_of_characteristic_using_value_handle_with_context(btstack_packet_handler_t callback, 2823 hci_con_handle_t con_handle, uint16_t value_handle, 2824 uint16_t service_id, uint16_t connection_id){ 2825 // TODO: move into gatt_client_read_long_value_of_characteristic_using_value_handle_with_offset once 2826 // gatt_client_read_long_value_of_characteristic_using_value_handle_with_offset_and_context exists 2827 gatt_client_t * gatt_client; 2828 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2829 if (status != ERROR_CODE_SUCCESS){ 2830 return status; 2831 } 2832 gatt_client->service_id = service_id; 2833 gatt_client->connection_id = connection_id; 2834 return gatt_client_read_long_value_of_characteristic_using_value_handle_with_offset(callback, con_handle, value_handle, 0); 2835 } 2836 2837 uint8_t gatt_client_read_long_value_of_characteristic_using_value_handle(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t value_handle){ 2838 return gatt_client_read_long_value_of_characteristic_using_value_handle_with_context(callback, con_handle, value_handle, 0, 0); 2839 } 2840 2841 uint8_t gatt_client_read_long_value_of_characteristic(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_characteristic_t * characteristic){ 2842 return gatt_client_read_long_value_of_characteristic_using_value_handle(callback, con_handle, characteristic->value_handle); 2843 } 2844 2845 static uint8_t gatt_client_read_multiple_characteristic_values_with_state(btstack_packet_handler_t callback, hci_con_handle_t con_handle, int num_value_handles, uint16_t * value_handles, gatt_client_state_t state){ 2846 gatt_client_t * gatt_client; 2847 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2848 if (status != ERROR_CODE_SUCCESS){ 2849 return status; 2850 } 2851 2852 #ifdef ENABLE_GATT_OVER_EATT 2853 if (state == P_W2_SEND_READ_MULTIPLE_VARIABLE_REQUEST){ 2854 if (gatt_client->bearer_type != ATT_BEARER_ENHANCED_LE){ 2855 return ERROR_CODE_COMMAND_DISALLOWED; 2856 } 2857 } 2858 #endif 2859 2860 gatt_client->callback = callback; 2861 gatt_client->read_multiple_handle_count = num_value_handles; 2862 gatt_client->read_multiple_handles = value_handles; 2863 gatt_client->state = state; 2864 gatt_client_run(); 2865 return ERROR_CODE_SUCCESS; 2866 } 2867 2868 uint8_t gatt_client_read_multiple_characteristic_values(btstack_packet_handler_t callback, hci_con_handle_t con_handle, int num_value_handles, uint16_t * value_handles){ 2869 return gatt_client_read_multiple_characteristic_values_with_state(callback, con_handle, num_value_handles, value_handles, P_W2_SEND_READ_MULTIPLE_REQUEST); 2870 } 2871 2872 #ifdef ENABLE_GATT_OVER_EATT 2873 uint8_t gatt_client_read_multiple_variable_characteristic_values(btstack_packet_handler_t callback, hci_con_handle_t con_handle, int num_value_handles, uint16_t * value_handles){ 2874 return gatt_client_read_multiple_characteristic_values_with_state(callback, con_handle, num_value_handles, value_handles, P_W2_SEND_READ_MULTIPLE_VARIABLE_REQUEST); 2875 } 2876 #endif 2877 2878 uint8_t gatt_client_write_value_of_characteristic_without_response(hci_con_handle_t con_handle, uint16_t value_handle, uint16_t value_length, uint8_t * value){ 2879 gatt_client_t * gatt_client; 2880 uint8_t status = gatt_client_provide_context_for_handle(con_handle, &gatt_client); 2881 if (status != ERROR_CODE_SUCCESS){ 2882 return status; 2883 } 2884 2885 if (value_length > (gatt_client->mtu - 3u)) return GATT_CLIENT_VALUE_TOO_LONG; 2886 if (!att_dispatch_client_can_send_now(gatt_client->con_handle)) return GATT_CLIENT_BUSY; 2887 2888 return att_write_request(gatt_client, ATT_WRITE_COMMAND, value_handle, value_length, value); 2889 } 2890 uint8_t gatt_client_write_value_of_characteristic_with_context(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t value_handle, 2891 uint16_t value_length, uint8_t * value, uint16_t service_id, uint16_t connection_id){ 2892 gatt_client_t * gatt_client; 2893 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2894 if (status != ERROR_CODE_SUCCESS){ 2895 return status; 2896 } 2897 2898 gatt_client->callback = callback; 2899 gatt_client->service_id = service_id; 2900 gatt_client->connection_id = connection_id; 2901 gatt_client->attribute_handle = value_handle; 2902 gatt_client->attribute_length = value_length; 2903 gatt_client->attribute_value = value; 2904 gatt_client->state = P_W2_SEND_WRITE_CHARACTERISTIC_VALUE; 2905 gatt_client_run(); 2906 return ERROR_CODE_SUCCESS; 2907 } 2908 uint8_t gatt_client_write_value_of_characteristic(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t value_handle, uint16_t value_length, uint8_t * value) { 2909 return gatt_client_write_value_of_characteristic_with_context(callback, con_handle, value_handle, value_length, value, 0, 0); 2910 } 2911 2912 uint8_t gatt_client_write_long_value_of_characteristic_with_offset(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t value_handle, uint16_t offset, uint16_t value_length, uint8_t * value){ 2913 gatt_client_t * gatt_client; 2914 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2915 if (status != ERROR_CODE_SUCCESS){ 2916 return status; 2917 } 2918 2919 gatt_client->callback = callback; 2920 gatt_client->attribute_handle = value_handle; 2921 gatt_client->attribute_length = value_length; 2922 gatt_client->attribute_offset = offset; 2923 gatt_client->attribute_value = value; 2924 gatt_client->state = P_W2_PREPARE_WRITE; 2925 gatt_client_run(); 2926 return ERROR_CODE_SUCCESS; 2927 } 2928 2929 uint8_t gatt_client_write_long_value_of_characteristic_with_context(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t value_handle, uint16_t value_length, uint8_t * value, uint16_t service_id, uint16_t connection_id){ 2930 // TODO: move into gatt_client_write_long_value_of_characteristic_with_offset once gatt_client_write_long_value_of_characteristic_with_offset_with_context exists 2931 gatt_client_t * gatt_client; 2932 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2933 if (status != ERROR_CODE_SUCCESS){ 2934 return status; 2935 } 2936 gatt_client->service_id = service_id; 2937 gatt_client->connection_id = connection_id; 2938 return gatt_client_write_long_value_of_characteristic_with_offset(callback, con_handle, value_handle, 0, value_length, value); 2939 } 2940 2941 uint8_t gatt_client_write_long_value_of_characteristic(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t value_handle, uint16_t value_length, uint8_t * value){ 2942 return gatt_client_write_long_value_of_characteristic_with_context(callback, con_handle, value_handle, value_length, value, 0, 0); 2943 } 2944 2945 uint8_t gatt_client_reliable_write_long_value_of_characteristic(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t value_handle, uint16_t value_length, uint8_t * value){ 2946 gatt_client_t * gatt_client; 2947 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2948 if (status != ERROR_CODE_SUCCESS){ 2949 return status; 2950 } 2951 2952 gatt_client->callback = callback; 2953 gatt_client->attribute_handle = value_handle; 2954 gatt_client->attribute_length = value_length; 2955 gatt_client->attribute_offset = 0; 2956 gatt_client->attribute_value = value; 2957 gatt_client->state = P_W2_PREPARE_RELIABLE_WRITE; 2958 gatt_client_run(); 2959 return ERROR_CODE_SUCCESS; 2960 } 2961 2962 uint8_t gatt_client_write_client_characteristic_configuration_with_context(btstack_packet_handler_t callback, hci_con_handle_t con_handle, 2963 gatt_client_characteristic_t * characteristic, uint16_t configuration, uint16_t service_id, uint16_t connection_id){ 2964 gatt_client_t * gatt_client; 2965 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 2966 if (status != ERROR_CODE_SUCCESS){ 2967 return status; 2968 } 2969 2970 if (configuration > 3){ 2971 return ERROR_CODE_UNSUPPORTED_FEATURE_OR_PARAMETER_VALUE; 2972 } 2973 2974 if ( (configuration & GATT_CLIENT_CHARACTERISTICS_CONFIGURATION_NOTIFICATION) && 2975 ((characteristic->properties & ATT_PROPERTY_NOTIFY) == 0u)) { 2976 log_info("gatt_client_write_client_characteristic_configuration: GATT_CLIENT_CHARACTERISTIC_NOTIFICATION_NOT_SUPPORTED"); 2977 return GATT_CLIENT_CHARACTERISTIC_NOTIFICATION_NOT_SUPPORTED; 2978 } else if ( (configuration & GATT_CLIENT_CHARACTERISTICS_CONFIGURATION_INDICATION) && 2979 ((characteristic->properties & ATT_PROPERTY_INDICATE) == 0u)){ 2980 log_info("gatt_client_write_client_characteristic_configuration: GATT_CLIENT_CHARACTERISTIC_INDICATION_NOT_SUPPORTED"); 2981 return GATT_CLIENT_CHARACTERISTIC_INDICATION_NOT_SUPPORTED; 2982 } 2983 2984 gatt_client->callback = callback; 2985 gatt_client->service_id = service_id; 2986 gatt_client->connection_id = connection_id; 2987 gatt_client->start_group_handle = characteristic->value_handle; 2988 gatt_client->end_group_handle = characteristic->end_handle; 2989 little_endian_store_16(gatt_client->client_characteristic_configuration_value, 0, configuration); 2990 2991 #ifdef ENABLE_GATT_FIND_INFORMATION_FOR_CCC_DISCOVERY 2992 gatt_client->state = P_W2_SEND_FIND_CLIENT_CHARACTERISTIC_CONFIGURATION_QUERY; 2993 #else 2994 gatt_client->state = P_W2_SEND_READ_CLIENT_CHARACTERISTIC_CONFIGURATION_QUERY; 2995 #endif 2996 gatt_client_run(); 2997 return ERROR_CODE_SUCCESS; 2998 } 2999 3000 uint8_t gatt_client_write_client_characteristic_configuration(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_characteristic_t * characteristic, uint16_t configuration){ 3001 return gatt_client_write_client_characteristic_configuration_with_context(callback, con_handle, characteristic, configuration, 0, 0); 3002 } 3003 3004 uint8_t gatt_client_read_characteristic_descriptor_using_descriptor_handle(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t descriptor_handle){ 3005 gatt_client_t * gatt_client; 3006 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 3007 if (status != ERROR_CODE_SUCCESS){ 3008 return status; 3009 } 3010 3011 gatt_client->callback = callback; 3012 gatt_client->attribute_handle = descriptor_handle; 3013 3014 gatt_client->state = P_W2_SEND_READ_CHARACTERISTIC_DESCRIPTOR_QUERY; 3015 gatt_client_run(); 3016 return ERROR_CODE_SUCCESS; 3017 } 3018 3019 uint8_t gatt_client_read_characteristic_descriptor(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_characteristic_descriptor_t * descriptor){ 3020 return gatt_client_read_characteristic_descriptor_using_descriptor_handle(callback, con_handle, descriptor->handle); 3021 } 3022 3023 uint8_t gatt_client_read_long_characteristic_descriptor_using_descriptor_handle_with_offset(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t descriptor_handle, uint16_t offset){ 3024 gatt_client_t * gatt_client; 3025 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 3026 if (status != ERROR_CODE_SUCCESS){ 3027 return status; 3028 } 3029 3030 gatt_client->callback = callback; 3031 gatt_client->attribute_handle = descriptor_handle; 3032 gatt_client->attribute_offset = offset; 3033 gatt_client->state = P_W2_SEND_READ_BLOB_CHARACTERISTIC_DESCRIPTOR_QUERY; 3034 gatt_client_run(); 3035 return ERROR_CODE_SUCCESS; 3036 } 3037 3038 uint8_t gatt_client_read_long_characteristic_descriptor_using_descriptor_handle(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t descriptor_handle){ 3039 return gatt_client_read_long_characteristic_descriptor_using_descriptor_handle_with_offset(callback, con_handle, descriptor_handle, 0); 3040 } 3041 3042 uint8_t gatt_client_read_long_characteristic_descriptor(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_characteristic_descriptor_t * descriptor){ 3043 return gatt_client_read_long_characteristic_descriptor_using_descriptor_handle(callback, con_handle, descriptor->handle); 3044 } 3045 3046 uint8_t gatt_client_write_characteristic_descriptor_using_descriptor_handle(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t descriptor_handle, uint16_t value_length, uint8_t * value){ 3047 gatt_client_t * gatt_client; 3048 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 3049 if (status != ERROR_CODE_SUCCESS){ 3050 return status; 3051 } 3052 3053 gatt_client->callback = callback; 3054 gatt_client->attribute_handle = descriptor_handle; 3055 gatt_client->attribute_length = value_length; 3056 gatt_client->attribute_offset = 0; 3057 gatt_client->attribute_value = value; 3058 gatt_client->state = P_W2_SEND_WRITE_CHARACTERISTIC_DESCRIPTOR; 3059 gatt_client_run(); 3060 return ERROR_CODE_SUCCESS; 3061 } 3062 3063 uint8_t gatt_client_write_characteristic_descriptor(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_characteristic_descriptor_t * descriptor, uint16_t value_length, uint8_t * value){ 3064 return gatt_client_write_characteristic_descriptor_using_descriptor_handle(callback, con_handle, descriptor->handle, value_length, value); 3065 } 3066 3067 uint8_t gatt_client_write_long_characteristic_descriptor_using_descriptor_handle_with_offset(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t descriptor_handle, uint16_t offset, uint16_t value_length, uint8_t * value){ 3068 gatt_client_t * gatt_client; 3069 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 3070 if (status != ERROR_CODE_SUCCESS){ 3071 return status; 3072 } 3073 3074 gatt_client->callback = callback; 3075 gatt_client->attribute_handle = descriptor_handle; 3076 gatt_client->attribute_length = value_length; 3077 gatt_client->attribute_offset = offset; 3078 gatt_client->attribute_value = value; 3079 gatt_client->state = P_W2_PREPARE_WRITE_CHARACTERISTIC_DESCRIPTOR; 3080 gatt_client_run(); 3081 return ERROR_CODE_SUCCESS; 3082 } 3083 3084 uint8_t gatt_client_write_long_characteristic_descriptor_using_descriptor_handle(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t descriptor_handle, uint16_t value_length, uint8_t * value){ 3085 return gatt_client_write_long_characteristic_descriptor_using_descriptor_handle_with_offset(callback, con_handle, descriptor_handle, 0, value_length, value); 3086 } 3087 3088 uint8_t gatt_client_write_long_characteristic_descriptor(btstack_packet_handler_t callback, hci_con_handle_t con_handle, gatt_client_characteristic_descriptor_t * descriptor, uint16_t value_length, uint8_t * value){ 3089 return gatt_client_write_long_characteristic_descriptor_using_descriptor_handle(callback, con_handle, descriptor->handle, value_length, value); 3090 } 3091 3092 /** 3093 * @brief -> gatt complete event 3094 */ 3095 uint8_t gatt_client_prepare_write(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint16_t attribute_handle, uint16_t offset, uint16_t value_length, uint8_t * value){ 3096 gatt_client_t * gatt_client; 3097 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 3098 if (status != ERROR_CODE_SUCCESS){ 3099 return status; 3100 } 3101 3102 gatt_client->callback = callback; 3103 gatt_client->attribute_handle = attribute_handle; 3104 gatt_client->attribute_length = value_length; 3105 gatt_client->attribute_offset = offset; 3106 gatt_client->attribute_value = value; 3107 gatt_client->state = P_W2_PREPARE_WRITE_SINGLE; 3108 gatt_client_run(); 3109 return ERROR_CODE_SUCCESS; 3110 } 3111 3112 /** 3113 * @brief -> gatt complete event 3114 */ 3115 uint8_t gatt_client_execute_write(btstack_packet_handler_t callback, hci_con_handle_t con_handle){ 3116 gatt_client_t * gatt_client; 3117 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 3118 if (status != ERROR_CODE_SUCCESS){ 3119 return status; 3120 } 3121 3122 gatt_client->callback = callback; 3123 gatt_client->state = P_W2_EXECUTE_PREPARED_WRITE; 3124 gatt_client_run(); 3125 return ERROR_CODE_SUCCESS; 3126 } 3127 3128 /** 3129 * @brief -> gatt complete event 3130 */ 3131 uint8_t gatt_client_cancel_write(btstack_packet_handler_t callback, hci_con_handle_t con_handle){ 3132 gatt_client_t * gatt_client; 3133 uint8_t status = gatt_client_provide_context_for_request(con_handle, &gatt_client); 3134 if (status != ERROR_CODE_SUCCESS){ 3135 return status; 3136 } 3137 3138 gatt_client->callback = callback; 3139 gatt_client->state = P_W2_CANCEL_PREPARED_WRITE; 3140 gatt_client_run(); 3141 return ERROR_CODE_SUCCESS; 3142 } 3143 3144 void gatt_client_deserialize_service(const uint8_t *packet, int offset, gatt_client_service_t * service){ 3145 service->start_group_handle = little_endian_read_16(packet, offset); 3146 service->end_group_handle = little_endian_read_16(packet, offset + 2); 3147 reverse_128(&packet[offset + 4], service->uuid128); 3148 if (uuid_has_bluetooth_prefix(service->uuid128)){ 3149 service->uuid16 = big_endian_read_32(service->uuid128, 0); 3150 } else { 3151 service->uuid16 = 0; 3152 } 3153 } 3154 3155 void gatt_client_deserialize_characteristic(const uint8_t * packet, int offset, gatt_client_characteristic_t * characteristic){ 3156 characteristic->start_handle = little_endian_read_16(packet, offset); 3157 characteristic->value_handle = little_endian_read_16(packet, offset + 2); 3158 characteristic->end_handle = little_endian_read_16(packet, offset + 4); 3159 characteristic->properties = little_endian_read_16(packet, offset + 6); 3160 reverse_128(&packet[offset+8], characteristic->uuid128); 3161 if (uuid_has_bluetooth_prefix(characteristic->uuid128)){ 3162 characteristic->uuid16 = big_endian_read_32(characteristic->uuid128, 0); 3163 } else { 3164 characteristic->uuid16 = 0; 3165 } 3166 } 3167 3168 void gatt_client_deserialize_characteristic_descriptor(const uint8_t * packet, int offset, gatt_client_characteristic_descriptor_t * descriptor){ 3169 descriptor->handle = little_endian_read_16(packet, offset); 3170 reverse_128(&packet[offset+2], descriptor->uuid128); 3171 if (uuid_has_bluetooth_prefix(descriptor->uuid128)){ 3172 descriptor->uuid16 = big_endian_read_32(descriptor->uuid128, 0); 3173 } else { 3174 descriptor->uuid16 = 0; 3175 } 3176 } 3177 3178 void gatt_client_send_mtu_negotiation(btstack_packet_handler_t callback, hci_con_handle_t con_handle){ 3179 gatt_client_t * gatt_client; 3180 uint8_t status = gatt_client_provide_context_for_handle(con_handle, &gatt_client); 3181 if (status != ERROR_CODE_SUCCESS){ 3182 return; 3183 } 3184 if (gatt_client->mtu_state == MTU_AUTO_EXCHANGE_DISABLED){ 3185 gatt_client->callback = callback; 3186 gatt_client->mtu_state = SEND_MTU_EXCHANGE; 3187 gatt_client_run(); 3188 } 3189 } 3190 3191 uint8_t gatt_client_request_to_write_without_response(btstack_context_callback_registration_t * callback_registration, hci_con_handle_t con_handle){ 3192 gatt_client_t * gatt_client; 3193 uint8_t status = gatt_client_provide_context_for_handle(con_handle, &gatt_client); 3194 if (status != ERROR_CODE_SUCCESS){ 3195 return status; 3196 } 3197 bool added = btstack_linked_list_add_tail(&gatt_client->write_without_response_requests, (btstack_linked_item_t*) callback_registration); 3198 if (added == false){ 3199 return ERROR_CODE_COMMAND_DISALLOWED; 3200 } else { 3201 att_dispatch_client_request_can_send_now_event(gatt_client->con_handle); 3202 return ERROR_CODE_SUCCESS; 3203 } 3204 } 3205 3206 uint8_t gatt_client_request_to_send_gatt_query(btstack_context_callback_registration_t * callback_registration, hci_con_handle_t con_handle){ 3207 gatt_client_t * gatt_client; 3208 uint8_t status = gatt_client_provide_context_for_handle(con_handle, &gatt_client); 3209 if (status != ERROR_CODE_SUCCESS){ 3210 return status; 3211 } 3212 bool added = btstack_linked_list_add_tail(&gatt_client->query_requests, (btstack_linked_item_t*) callback_registration); 3213 if (added == false){ 3214 return ERROR_CODE_COMMAND_DISALLOWED; 3215 } else { 3216 gatt_client_notify_can_send_query(gatt_client); 3217 return ERROR_CODE_SUCCESS; 3218 } 3219 } 3220 3221 uint8_t gatt_client_remove_gatt_query(btstack_context_callback_registration_t * callback_registration, hci_con_handle_t con_handle){ 3222 gatt_client_t * gatt_client; 3223 uint8_t status = gatt_client_provide_context_for_handle(con_handle, &gatt_client); 3224 if (status != ERROR_CODE_SUCCESS){ 3225 return status; 3226 } 3227 (void)btstack_linked_list_remove(&gatt_client->query_requests, (btstack_linked_item_t*) callback_registration); 3228 return ERROR_CODE_SUCCESS; 3229 } 3230 3231 uint8_t gatt_client_request_can_write_without_response_event(btstack_packet_handler_t callback, hci_con_handle_t con_handle){ 3232 gatt_client_t * gatt_client; 3233 uint8_t status = gatt_client_provide_context_for_handle(con_handle, &gatt_client); 3234 if (status != ERROR_CODE_SUCCESS){ 3235 return status; 3236 } 3237 if (gatt_client->write_without_response_callback != NULL){ 3238 return GATT_CLIENT_IN_WRONG_STATE; 3239 } 3240 gatt_client->write_without_response_callback = callback; 3241 att_dispatch_client_request_can_send_now_event(gatt_client->con_handle); 3242 return ERROR_CODE_SUCCESS; 3243 } 3244 3245 uint8_t gatt_client_att_status_to_error_code(uint8_t att_error_code){ 3246 switch (att_error_code){ 3247 case ATT_ERROR_SUCCESS: 3248 return ERROR_CODE_SUCCESS; 3249 case ATT_ERROR_INVALID_ATTRIBUTE_VALUE_LENGTH: 3250 return ERROR_CODE_PARAMETER_OUT_OF_MANDATORY_RANGE; 3251 default: 3252 log_info("ATT ERROR 0x%02x mapped to ERROR_CODE_UNSPECIFIED_ERROR", att_error_code); 3253 return ERROR_CODE_UNSPECIFIED_ERROR; 3254 } 3255 } 3256 3257 #ifdef ENABLE_GATT_CLIENT_SERVICE_CHANGED 3258 void gatt_client_add_service_changed_handler(btstack_packet_callback_registration_t * callback) { 3259 btstack_linked_list_add_tail(&gatt_client_service_changed_handler, (btstack_linked_item_t*) callback); 3260 } 3261 3262 void gatt_client_remove_service_changed_handler(btstack_packet_callback_registration_t * callback){ 3263 btstack_linked_list_remove(&gatt_client_service_changed_handler, (btstack_linked_item_t*) callback); 3264 } 3265 #endif 3266 3267 #if defined(ENABLE_GATT_OVER_CLASSIC) || defined(ENABLE_GATT_OVER_EATT) 3268 3269 #include "hci_event.h" 3270 3271 static const hci_event_t gatt_client_connected = { 3272 GATT_EVENT_CONNECTED, 0, "11BH" 3273 }; 3274 3275 static const hci_event_t gatt_client_disconnected = { 3276 GATT_EVENT_DISCONNECTED, 0, "H" 3277 }; 3278 3279 static void 3280 gatt_client_emit_connected(btstack_packet_handler_t callback, uint8_t status, bd_addr_type_t addr_type, bd_addr_t addr, 3281 hci_con_handle_t con_handle) { 3282 uint8_t buffer[20]; 3283 uint16_t len = hci_event_create_from_template_and_arguments(buffer, sizeof(buffer), &gatt_client_connected, status, addr, con_handle); 3284 (*callback)(HCI_EVENT_PACKET, 0, buffer, len); 3285 } 3286 3287 #endif 3288 3289 #ifdef ENABLE_GATT_OVER_CLASSIC 3290 3291 #include "bluetooth_psm.h" 3292 3293 // single active SDP query 3294 static gatt_client_t * gatt_client_classic_active_sdp_query; 3295 3296 // macos protocol descriptor list requires 16 bytes 3297 static uint8_t gatt_client_classic_sdp_buffer[32]; 3298 3299 3300 static gatt_client_t * gatt_client_get_context_for_classic_addr(bd_addr_t addr){ 3301 btstack_linked_item_t *it; 3302 for (it = (btstack_linked_item_t *) gatt_client_connections; it != NULL; it = it->next){ 3303 gatt_client_t * gatt_client = (gatt_client_t *) it; 3304 if (memcmp(gatt_client->addr, addr, 6) == 0){ 3305 return gatt_client; 3306 } 3307 } 3308 return NULL; 3309 } 3310 3311 static gatt_client_t * gatt_client_get_context_for_l2cap_cid(uint16_t l2cap_cid){ 3312 btstack_linked_item_t *it; 3313 for (it = (btstack_linked_item_t *) gatt_client_connections; it != NULL; it = it->next){ 3314 gatt_client_t * gatt_client = (gatt_client_t *) it; 3315 if (gatt_client->l2cap_cid == l2cap_cid){ 3316 return gatt_client; 3317 } 3318 } 3319 return NULL; 3320 } 3321 3322 static void gatt_client_classic_handle_connected(gatt_client_t * gatt_client, uint8_t status){ 3323 // cache peer information 3324 bd_addr_t addr; 3325 // cppcheck-suppress uninitvar ; addr is reported as uninitialized although it's the destination of the memcpy 3326 memcpy(addr, gatt_client->addr, 6); 3327 bd_addr_type_t addr_type = gatt_client->addr_type; 3328 gatt_client->addr_type = BD_ADDR_TYPE_ACL; 3329 hci_con_handle_t con_handle = gatt_client->con_handle; 3330 btstack_packet_handler_t callback = gatt_client->callback; 3331 3332 if (status != ERROR_CODE_SUCCESS){ 3333 btstack_linked_list_remove(&gatt_client_connections, (btstack_linked_item_t *) gatt_client); 3334 btstack_memory_gatt_client_free(gatt_client); 3335 } 3336 3337 gatt_client_emit_connected(callback, status, addr_type, addr, con_handle); 3338 } 3339 3340 static void gatt_client_classic_retry(btstack_timer_source_t * ts){ 3341 gatt_client_t * gatt_client = gatt_client_for_timer(ts); 3342 if (gatt_client != NULL){ 3343 gatt_client->state = P_W4_L2CAP_CONNECTION; 3344 att_dispatch_classic_connect(gatt_client->addr, gatt_client->l2cap_psm, &gatt_client->l2cap_cid); 3345 } 3346 } 3347 3348 static void gatt_client_classic_handle_disconnected(gatt_client_t * gatt_client){ 3349 3350 gatt_client_report_error_if_pending(gatt_client, ATT_ERROR_HCI_DISCONNECT_RECEIVED); 3351 gatt_client_timeout_stop(gatt_client); 3352 3353 hci_con_handle_t con_handle = gatt_client->con_handle; 3354 btstack_packet_handler_t callback = gatt_client->callback; 3355 btstack_linked_list_remove(&gatt_client_connections, (btstack_linked_item_t *) gatt_client); 3356 btstack_memory_gatt_client_free(gatt_client); 3357 3358 uint8_t buffer[20]; 3359 uint16_t len = hci_event_create_from_template_and_arguments(buffer, sizeof(buffer), &gatt_client_disconnected, con_handle); 3360 (*callback)(HCI_EVENT_PACKET, 0, buffer, len); 3361 } 3362 3363 static void gatt_client_handle_sdp_client_query_attribute_value(gatt_client_t * connection, uint8_t *packet){ 3364 des_iterator_t des_list_it; 3365 des_iterator_t prot_it; 3366 3367 if (sdp_event_query_attribute_byte_get_attribute_length(packet) <= sizeof(gatt_client_classic_sdp_buffer)) { 3368 gatt_client_classic_sdp_buffer[sdp_event_query_attribute_byte_get_data_offset(packet)] = sdp_event_query_attribute_byte_get_data(packet); 3369 if ((uint16_t)(sdp_event_query_attribute_byte_get_data_offset(packet)+1) == sdp_event_query_attribute_byte_get_attribute_length(packet)) { 3370 switch(sdp_event_query_attribute_byte_get_attribute_id(packet)) { 3371 case BLUETOOTH_ATTRIBUTE_PROTOCOL_DESCRIPTOR_LIST: 3372 for (des_iterator_init(&des_list_it, gatt_client_classic_sdp_buffer); des_iterator_has_more(&des_list_it); des_iterator_next(&des_list_it)) { 3373 uint8_t *des_element; 3374 uint8_t *element; 3375 uint32_t uuid; 3376 3377 if (des_iterator_get_type(&des_list_it) != DE_DES) continue; 3378 3379 des_element = des_iterator_get_element(&des_list_it); 3380 des_iterator_init(&prot_it, des_element); 3381 element = des_iterator_get_element(&prot_it); 3382 3383 if (de_get_element_type(element) != DE_UUID) continue; 3384 3385 uuid = de_get_uuid32(element); 3386 des_iterator_next(&prot_it); 3387 // we assume that the even if there are both roles supported, remote device uses the same psm and avdtp version for both 3388 switch (uuid){ 3389 case BLUETOOTH_PROTOCOL_L2CAP: 3390 if (!des_iterator_has_more(&prot_it)) continue; 3391 de_element_get_uint16(des_iterator_get_element(&prot_it), &connection->l2cap_psm); 3392 break; 3393 default: 3394 break; 3395 } 3396 } 3397 break; 3398 3399 default: 3400 break; 3401 } 3402 } 3403 } 3404 } 3405 3406 static void gatt_client_classic_sdp_handler(uint8_t packet_type, uint16_t handle, uint8_t *packet, uint16_t size){ 3407 gatt_client_t * gatt_client = gatt_client_classic_active_sdp_query; 3408 btstack_assert(gatt_client != NULL); 3409 uint8_t status; 3410 3411 // TODO: handle sdp events, get l2cap psm 3412 switch (hci_event_packet_get_type(packet)){ 3413 case SDP_EVENT_QUERY_ATTRIBUTE_VALUE: 3414 gatt_client_handle_sdp_client_query_attribute_value(gatt_client, packet); 3415 // TODO: 3416 return; 3417 case SDP_EVENT_QUERY_COMPLETE: 3418 status = sdp_event_query_complete_get_status(packet); 3419 gatt_client_classic_active_sdp_query = NULL; 3420 log_info("l2cap psm: %0x, status %02x", gatt_client->l2cap_psm, status); 3421 if (status != ERROR_CODE_SUCCESS) break; 3422 if (gatt_client->l2cap_psm == 0) { 3423 status = SDP_SERVICE_NOT_FOUND; 3424 break; 3425 } 3426 break; 3427 default: 3428 btstack_assert(false); 3429 return; 3430 } 3431 3432 // done 3433 if (status == ERROR_CODE_SUCCESS){ 3434 gatt_client->state = P_W4_L2CAP_CONNECTION; 3435 status = att_dispatch_classic_connect(gatt_client->addr, gatt_client->l2cap_psm, &gatt_client->l2cap_cid); 3436 } 3437 if (status != ERROR_CODE_SUCCESS) { 3438 gatt_client_classic_handle_connected(gatt_client, status); 3439 } 3440 } 3441 3442 static void gatt_client_classic_sdp_start(void * context){ 3443 gatt_client_classic_active_sdp_query = (gatt_client_t *) context; 3444 gatt_client_classic_active_sdp_query->state = P_W4_SDP_QUERY; 3445 sdp_client_query_uuid16(gatt_client_classic_sdp_handler, gatt_client_classic_active_sdp_query->addr, ORG_BLUETOOTH_SERVICE_GENERIC_ATTRIBUTE); 3446 } 3447 3448 static void gatt_client_classic_emit_connected(void * context){ 3449 gatt_client_t * gatt_client = (gatt_client_t *) context; 3450 gatt_client->state = P_READY; 3451 gatt_client_emit_connected(gatt_client->callback, ERROR_CODE_SUCCESS, gatt_client->addr_type, gatt_client->addr, gatt_client->con_handle); 3452 } 3453 3454 uint8_t gatt_client_classic_connect(btstack_packet_handler_t callback, bd_addr_t addr){ 3455 gatt_client_t * gatt_client = gatt_client_get_context_for_classic_addr(addr); 3456 if (gatt_client != NULL){ 3457 return ERROR_CODE_ACL_CONNECTION_ALREADY_EXISTS; 3458 } 3459 gatt_client = btstack_memory_gatt_client_get(); 3460 if (gatt_client == NULL){ 3461 return ERROR_CODE_MEMORY_CAPACITY_EXCEEDED; 3462 } 3463 // init state 3464 gatt_client->bearer_type = ATT_BEARER_UNENHANCED_CLASSIC; 3465 gatt_client->con_handle = HCI_CON_HANDLE_INVALID; 3466 memcpy(gatt_client->addr, addr, 6); 3467 gatt_client->addr_type = BD_ADDR_TYPE_ACL; 3468 gatt_client->mtu = ATT_DEFAULT_MTU; 3469 gatt_client->security_level = LEVEL_0; 3470 gatt_client->mtu_state = MTU_AUTO_EXCHANGE_DISABLED; 3471 gatt_client->callback = callback; 3472 #ifdef ENABLE_GATT_OVER_EATT 3473 gatt_client->eatt_state = GATT_CLIENT_EATT_IDLE; 3474 #endif 3475 btstack_linked_list_add(&gatt_client_connections, (btstack_linked_item_t*)gatt_client); 3476 3477 // schedule emitted event if already connected, otherwise 3478 bool already_connected = false; 3479 hci_connection_t * hci_connection = hci_connection_for_bd_addr_and_type(addr, BD_ADDR_TYPE_ACL); 3480 if (hci_connection != NULL){ 3481 if (hci_connection->att_server.l2cap_cid != 0){ 3482 already_connected = true; 3483 } 3484 } 3485 gatt_client->callback_request.context = gatt_client; 3486 if (already_connected){ 3487 gatt_client->con_handle = hci_connection->con_handle; 3488 gatt_client->callback_request.callback = &gatt_client_classic_emit_connected; 3489 gatt_client->state = P_W2_EMIT_CONNECTED; 3490 btstack_run_loop_execute_on_main_thread(&gatt_client->callback_request); 3491 } else { 3492 gatt_client->callback_request.callback = &gatt_client_classic_sdp_start; 3493 gatt_client->state = P_W2_SDP_QUERY; 3494 sdp_client_register_query_callback(&gatt_client->callback_request); 3495 } 3496 return ERROR_CODE_SUCCESS; 3497 } 3498 3499 uint8_t gatt_client_classic_disconnect(btstack_packet_handler_t callback, hci_con_handle_t con_handle){ 3500 gatt_client_t * gatt_client = gatt_client_get_context_for_handle(con_handle); 3501 if (gatt_client == NULL){ 3502 return ERROR_CODE_UNKNOWN_CONNECTION_IDENTIFIER; 3503 } 3504 gatt_client->callback = callback; 3505 return l2cap_disconnect(gatt_client->l2cap_cid); 3506 } 3507 #endif 3508 3509 #ifdef ENABLE_GATT_OVER_EATT 3510 3511 #define MAX_NR_EATT_CHANNELS 5 3512 3513 static void gatt_client_le_enhanced_packet_handler(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size); 3514 3515 static uint8_t gatt_client_le_enhanced_num_eatt_clients_in_state(gatt_client_t * gatt_client, gatt_client_state_t state){ 3516 uint8_t num_clients = 0; 3517 btstack_linked_list_iterator_t it; 3518 btstack_linked_list_iterator_init(&it, &gatt_client->eatt_clients); 3519 while (btstack_linked_list_iterator_has_next(&it)){ 3520 gatt_client_t * eatt_client = (gatt_client_t *) btstack_linked_list_iterator_next(&it); 3521 if (eatt_client->state == state){ 3522 num_clients++; 3523 } 3524 } 3525 return num_clients; 3526 } 3527 3528 static void gatt_client_eatt_finalize(gatt_client_t * gatt_client) { 3529 // free eatt clients 3530 btstack_linked_list_iterator_t it; 3531 btstack_linked_list_iterator_init(&it, &gatt_client_connections); 3532 while (btstack_linked_list_iterator_has_next(&it)) { 3533 gatt_client_t *eatt_client = (gatt_client_t *) btstack_linked_list_iterator_next(&it); 3534 btstack_linked_list_iterator_remove(&it); 3535 btstack_memory_gatt_client_free(eatt_client); 3536 } 3537 } 3538 3539 // all channels connected 3540 static void gatt_client_le_enhanced_handle_connected(gatt_client_t * gatt_client, uint8_t status) { 3541 if (status == ERROR_CODE_SUCCESS){ 3542 uint8_t num_ready = gatt_client_le_enhanced_num_eatt_clients_in_state(gatt_client, P_READY); 3543 if (num_ready > 0){ 3544 gatt_client->eatt_state = GATT_CLIENT_EATT_READY; 3545 // free unused channels 3546 btstack_linked_list_iterator_t it; 3547 btstack_linked_list_iterator_init(&it, &gatt_client_connections); 3548 while (btstack_linked_list_iterator_has_next(&it)) { 3549 gatt_client_t *eatt_client = (gatt_client_t *) btstack_linked_list_iterator_next(&it); 3550 if (eatt_client->state == P_L2CAP_CLOSED){ 3551 btstack_linked_list_iterator_remove(&it); 3552 btstack_memory_gatt_client_free(eatt_client); 3553 } 3554 } 3555 } else { 3556 hci_connection_t * hci_connection = hci_connection_for_handle(gatt_client->con_handle); 3557 btstack_assert(hci_connection != NULL); 3558 if (hci_connection->att_server.incoming_connection_request){ 3559 hci_connection->att_server.incoming_connection_request = false; 3560 log_info("Collision, retry in 100ms"); 3561 gatt_client->state = P_W2_L2CAP_CONNECT; 3562 // set timer for retry 3563 btstack_run_loop_set_timer(&gatt_client->gc_timeout, GATT_CLIENT_COLLISION_BACKOFF_MS); 3564 btstack_run_loop_set_timer_handler(&gatt_client->gc_timeout, gatt_client_le_enhanced_retry); 3565 btstack_run_loop_add_timer(&gatt_client->gc_timeout); 3566 return; 3567 } else { 3568 gatt_client->eatt_state = GATT_CLIENT_EATT_IDLE; 3569 status = ERROR_CODE_CONNECTION_REJECTED_DUE_TO_LIMITED_RESOURCES; 3570 } 3571 } 3572 } else { 3573 gatt_client_eatt_finalize(gatt_client); 3574 gatt_client->eatt_state = GATT_CLIENT_EATT_IDLE; 3575 } 3576 3577 gatt_client_emit_connected(gatt_client->callback, status, gatt_client->addr_type, gatt_client->addr, gatt_client->con_handle); 3578 } 3579 3580 // single channel disconnected 3581 static void gatt_client_le_enhanced_handle_ecbm_disconnected(gatt_client_t * gatt_client, gatt_client_t * eatt_client) { 3582 3583 // report error 3584 gatt_client_report_error_if_pending(eatt_client, ATT_ERROR_HCI_DISCONNECT_RECEIVED); 3585 3586 // free memory 3587 btstack_linked_list_remove(&gatt_client->eatt_clients, (btstack_linked_item_t *) eatt_client); 3588 btstack_memory_gatt_client_free(eatt_client); 3589 3590 // last channel 3591 if (btstack_linked_list_empty(&gatt_client->eatt_clients)){ 3592 hci_connection_t * hci_connection = hci_connection_for_handle(gatt_client->con_handle); 3593 hci_connection->att_server.eatt_outgoing_active = false; 3594 3595 if (gatt_client->eatt_state == GATT_CLIENT_EATT_READY) { 3596 // report disconnected if last channel closed 3597 uint8_t buffer[20]; 3598 uint16_t len = hci_event_create_from_template_and_arguments(buffer, sizeof(buffer), &gatt_client_disconnected, gatt_client->con_handle); 3599 (*gatt_client->callback)(HCI_EVENT_PACKET, 0, buffer, len); 3600 } 3601 } 3602 } 3603 3604 static gatt_client_t * gatt_client_le_enhanced_get_context_for_l2cap_cid(uint16_t l2cap_cid, gatt_client_t ** out_eatt_client){ 3605 btstack_linked_list_iterator_t it; 3606 btstack_linked_list_iterator_init(&it, &gatt_client_connections); 3607 while (btstack_linked_list_iterator_has_next(&it)) { 3608 gatt_client_t * gatt_client = (gatt_client_t *) btstack_linked_list_iterator_next(&it); 3609 btstack_linked_list_iterator_t it2; 3610 btstack_linked_list_iterator_init(&it2, &gatt_client->eatt_clients); 3611 while (btstack_linked_list_iterator_has_next(&it2)) { 3612 gatt_client_t * eatt_client = (gatt_client_t *) btstack_linked_list_iterator_next(&it2); 3613 if (eatt_client->l2cap_cid == l2cap_cid){ 3614 *out_eatt_client = eatt_client; 3615 return gatt_client; 3616 } 3617 } 3618 } 3619 return NULL; 3620 } 3621 3622 static void gatt_client_le_enhanced_setup_l2cap_channel(gatt_client_t * gatt_client){ 3623 uint8_t num_channels = gatt_client->eatt_num_clients; 3624 3625 // setup channels 3626 uint16_t buffer_size_per_client = gatt_client->eatt_storage_size / num_channels; 3627 uint16_t max_mtu = (buffer_size_per_client - REPORT_PREBUFFER_HEADER) / 2; 3628 uint8_t * receive_buffers[MAX_NR_EATT_CHANNELS]; 3629 uint16_t new_cids[MAX_NR_EATT_CHANNELS]; 3630 memset(gatt_client->eatt_storage_buffer, 0, gatt_client->eatt_storage_size); 3631 uint8_t i; 3632 for (i=0;i<gatt_client->eatt_num_clients; i++){ 3633 receive_buffers[i] = &gatt_client->eatt_storage_buffer[REPORT_PREBUFFER_HEADER]; 3634 gatt_client->eatt_storage_buffer += REPORT_PREBUFFER_HEADER + max_mtu; 3635 } 3636 3637 log_info("%u EATT clients with receive buffer size %u", gatt_client->eatt_num_clients, buffer_size_per_client); 3638 3639 uint8_t status = l2cap_ecbm_create_channels(&gatt_client_le_enhanced_packet_handler, 3640 gatt_client->con_handle, 3641 gatt_client->security_level, 3642 BLUETOOTH_PSM_EATT, num_channels, 3643 L2CAP_LE_AUTOMATIC_CREDITS, 3644 buffer_size_per_client, 3645 receive_buffers, 3646 new_cids); 3647 3648 if (status == ERROR_CODE_SUCCESS){ 3649 i = 0; 3650 btstack_linked_list_iterator_t it; 3651 btstack_linked_list_iterator_init(&it, &gatt_client->eatt_clients); 3652 while (btstack_linked_list_iterator_has_next(&it)) { 3653 gatt_client_t *new_eatt_client = (gatt_client_t *) btstack_linked_list_iterator_next(&it); 3654 3655 // init state with new cid and transmit buffer 3656 new_eatt_client->bearer_type = ATT_BEARER_ENHANCED_LE; 3657 new_eatt_client->con_handle = gatt_client->con_handle; 3658 new_eatt_client->mtu = 64; 3659 new_eatt_client->security_level = LEVEL_0; 3660 new_eatt_client->mtu_state = MTU_AUTO_EXCHANGE_DISABLED; 3661 new_eatt_client->state = P_W4_L2CAP_CONNECTION; 3662 new_eatt_client->l2cap_cid = new_cids[i]; 3663 new_eatt_client->eatt_storage_buffer = gatt_client->eatt_storage_buffer; 3664 gatt_client->eatt_storage_buffer += max_mtu; 3665 i++; 3666 } 3667 gatt_client->eatt_state = GATT_CLIENT_EATT_L2CAP_SETUP; 3668 } else { 3669 gatt_client_le_enhanced_handle_connected(gatt_client, status); 3670 } 3671 } 3672 3673 static void gatt_client_le_enhanced_retry(btstack_timer_source_t * ts){ 3674 gatt_client_t * gatt_client = gatt_client_for_timer(ts); 3675 if (gatt_client != NULL){ 3676 gatt_client->state = P_W4_L2CAP_CONNECTION; 3677 gatt_client_le_enhanced_setup_l2cap_channel(gatt_client); 3678 } 3679 } 3680 3681 static void gatt_client_le_enhanced_packet_handler(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size) { 3682 gatt_client_t *gatt_client; 3683 gatt_client_t *eatt_client; 3684 hci_con_handle_t con_handle; 3685 uint16_t l2cap_cid; 3686 uint8_t status; 3687 gatt_client_characteristic_t characteristic; 3688 gatt_client_service_t service; 3689 switch (packet_type) { 3690 case HCI_EVENT_PACKET: 3691 switch (hci_event_packet_get_type(packet)) { 3692 case GATT_EVENT_SERVICE_QUERY_RESULT: 3693 con_handle = gatt_event_service_query_result_get_handle(packet); 3694 gatt_client = gatt_client_get_context_for_handle(con_handle); 3695 btstack_assert(gatt_client != NULL); 3696 btstack_assert(gatt_client->eatt_state == GATT_CLIENT_EATT_DISCOVER_GATT_SERVICE_W4_DONE); 3697 gatt_event_service_query_result_get_service(packet, &service); 3698 gatt_client->gatt_service_start_group_handle = service.start_group_handle; 3699 gatt_client->gatt_service_end_group_handle = service.end_group_handle; 3700 break; 3701 case GATT_EVENT_CHARACTERISTIC_VALUE_QUERY_RESULT: 3702 con_handle = gatt_event_characteristic_value_query_result_get_handle(packet); 3703 gatt_client = gatt_client_get_context_for_handle(con_handle); 3704 btstack_assert(gatt_client != NULL); 3705 btstack_assert(gatt_client->eatt_state == GATT_CLIENT_EATT_READ_SERVER_SUPPORTED_FEATURES_W4_DONE); 3706 if (gatt_event_characteristic_value_query_result_get_value_length(packet) >= 1) { 3707 gatt_client->gatt_server_supported_features = gatt_event_characteristic_value_query_result_get_value(packet)[0]; 3708 } 3709 break; 3710 case GATT_EVENT_CHARACTERISTIC_QUERY_RESULT: 3711 con_handle = gatt_event_characteristic_query_result_get_handle(packet); 3712 gatt_client = gatt_client_get_context_for_handle(con_handle); 3713 btstack_assert(gatt_client != NULL); 3714 btstack_assert(gatt_client->eatt_state == GATT_CLIENT_EATT_FIND_CLIENT_SUPPORTED_FEATURES_W4_DONE); 3715 gatt_event_characteristic_query_result_get_characteristic(packet, &characteristic); 3716 gatt_client->gatt_client_supported_features_handle = characteristic.value_handle; 3717 break; 3718 case GATT_EVENT_QUERY_COMPLETE: 3719 con_handle = gatt_event_query_complete_get_handle(packet); 3720 gatt_client = gatt_client_get_context_for_handle(con_handle); 3721 btstack_assert(gatt_client != NULL); 3722 switch (gatt_client->eatt_state){ 3723 case GATT_CLIENT_EATT_DISCOVER_GATT_SERVICE_W4_DONE: 3724 if (gatt_client->gatt_service_start_group_handle == 0){ 3725 gatt_client_le_enhanced_handle_connected(gatt_client, ERROR_CODE_UNSUPPORTED_FEATURE_OR_PARAMETER_VALUE); 3726 } else { 3727 gatt_client->eatt_state = GATT_CLIENT_EATT_READ_SERVER_SUPPORTED_FEATURES_W2_SEND; 3728 } 3729 break; 3730 case GATT_CLIENT_EATT_READ_SERVER_SUPPORTED_FEATURES_W4_DONE: 3731 if ((gatt_client->gatt_server_supported_features & 1) == 0) { 3732 gatt_client_le_enhanced_handle_connected(gatt_client, ERROR_CODE_UNSUPPORTED_FEATURE_OR_PARAMETER_VALUE); 3733 } else { 3734 gatt_client->eatt_state = GATT_CLIENT_EATT_FIND_CLIENT_SUPPORTED_FEATURES_W2_SEND; 3735 } 3736 break; 3737 case GATT_CLIENT_EATT_FIND_CLIENT_SUPPORTED_FEATURES_W4_DONE: 3738 if (gatt_client->gatt_client_supported_features_handle == 0){ 3739 gatt_client_le_enhanced_handle_connected(gatt_client, ERROR_CODE_UNSUPPORTED_FEATURE_OR_PARAMETER_VALUE); 3740 } else { 3741 gatt_client->eatt_state = GATT_CLIENT_EATT_WRITE_ClIENT_SUPPORTED_FEATURES_W2_SEND; 3742 } 3743 break; 3744 case GATT_CLIENT_EATT_WRITE_ClIENT_SUPPORTED_FEATURES_W4_DONE: 3745 gatt_client_le_enhanced_setup_l2cap_channel(gatt_client); 3746 break; 3747 default: 3748 break; 3749 } 3750 break; 3751 case L2CAP_EVENT_ECBM_CHANNEL_OPENED: 3752 l2cap_cid = l2cap_event_ecbm_channel_opened_get_local_cid(packet); 3753 gatt_client = gatt_client_le_enhanced_get_context_for_l2cap_cid(l2cap_cid, &eatt_client); 3754 3755 btstack_assert(gatt_client != NULL); 3756 btstack_assert(eatt_client != NULL); 3757 btstack_assert(eatt_client->state == P_W4_L2CAP_CONNECTION); 3758 3759 status = l2cap_event_channel_opened_get_status(packet); 3760 if (status == ERROR_CODE_SUCCESS){ 3761 eatt_client->state = P_READY; 3762 eatt_client->mtu = l2cap_event_channel_opened_get_remote_mtu(packet); 3763 } else { 3764 eatt_client->state = P_L2CAP_CLOSED; 3765 } 3766 // connected if opened event for all channels received 3767 if (gatt_client_le_enhanced_num_eatt_clients_in_state(gatt_client, P_W4_L2CAP_CONNECTION) == 0){ 3768 gatt_client_le_enhanced_handle_connected(gatt_client, ERROR_CODE_SUCCESS); 3769 } 3770 break; 3771 case L2CAP_EVENT_CHANNEL_CLOSED: 3772 l2cap_cid = l2cap_event_channel_closed_get_local_cid(packet); 3773 gatt_client = gatt_client_le_enhanced_get_context_for_l2cap_cid(l2cap_cid, &eatt_client); 3774 btstack_assert(gatt_client != NULL); 3775 btstack_assert(eatt_client != NULL); 3776 gatt_client_le_enhanced_handle_ecbm_disconnected(gatt_client, eatt_client); 3777 break; 3778 default: 3779 break; 3780 } 3781 break; 3782 case L2CAP_DATA_PACKET: 3783 gatt_client = gatt_client_le_enhanced_get_context_for_l2cap_cid(channel, &eatt_client); 3784 btstack_assert(gatt_client != NULL); 3785 btstack_assert(eatt_client != NULL); 3786 gatt_client_handle_att_response(eatt_client, packet, size); 3787 gatt_client_run(); 3788 break; 3789 default: 3790 break; 3791 } 3792 } 3793 3794 static bool gatt_client_le_enhanced_handle_can_send_query(gatt_client_t * gatt_client){ 3795 uint8_t status = ERROR_CODE_SUCCESS; 3796 uint8_t gatt_client_supported_features = 0x06; // eatt + multiple value notifications 3797 switch (gatt_client->eatt_state){ 3798 case GATT_CLIENT_EATT_DISCOVER_GATT_SERVICE_W2_SEND: 3799 gatt_client->gatt_service_start_group_handle = 0; 3800 gatt_client->eatt_state = GATT_CLIENT_EATT_DISCOVER_GATT_SERVICE_W4_DONE; 3801 status = gatt_client_discover_primary_services_by_uuid16(&gatt_client_le_enhanced_packet_handler, 3802 gatt_client->con_handle, 3803 ORG_BLUETOOTH_SERVICE_GENERIC_ATTRIBUTE); 3804 break; 3805 case GATT_CLIENT_EATT_READ_SERVER_SUPPORTED_FEATURES_W2_SEND: 3806 gatt_client->gatt_server_supported_features = 0; 3807 gatt_client->eatt_state = GATT_CLIENT_EATT_READ_SERVER_SUPPORTED_FEATURES_W4_DONE; 3808 status = gatt_client_read_value_of_characteristics_by_uuid16(&gatt_client_le_enhanced_packet_handler, 3809 gatt_client->con_handle, 3810 gatt_client->gatt_service_start_group_handle, 3811 gatt_client->gatt_service_end_group_handle, 3812 ORG_BLUETOOTH_CHARACTERISTIC_SERVER_SUPPORTED_FEATURES); 3813 return true; 3814 case GATT_CLIENT_EATT_FIND_CLIENT_SUPPORTED_FEATURES_W2_SEND: 3815 gatt_client->gatt_client_supported_features_handle = 0; 3816 gatt_client->eatt_state = GATT_CLIENT_EATT_FIND_CLIENT_SUPPORTED_FEATURES_W4_DONE; 3817 status = gatt_client_discover_characteristics_for_handle_range_by_uuid16(&gatt_client_le_enhanced_packet_handler, 3818 gatt_client->con_handle, 3819 gatt_client->gatt_service_start_group_handle, 3820 gatt_client->gatt_service_end_group_handle, 3821 ORG_BLUETOOTH_CHARACTERISTIC_CLIENT_SUPPORTED_FEATURES); 3822 return true; 3823 case GATT_CLIENT_EATT_WRITE_ClIENT_SUPPORTED_FEATURES_W2_SEND: 3824 gatt_client->eatt_state = GATT_CLIENT_EATT_WRITE_ClIENT_SUPPORTED_FEATURES_W4_DONE; 3825 status = gatt_client_write_value_of_characteristic(&gatt_client_le_enhanced_packet_handler, gatt_client->con_handle, 3826 gatt_client->gatt_client_supported_features_handle, 1, 3827 &gatt_client_supported_features); 3828 return true; 3829 default: 3830 break; 3831 } 3832 btstack_assert(status == ERROR_CODE_SUCCESS); 3833 UNUSED(status); 3834 return false; 3835 } 3836 3837 uint8_t gatt_client_le_enhanced_connect(btstack_packet_handler_t callback, hci_con_handle_t con_handle, uint8_t num_channels, uint8_t * storage_buffer, uint16_t storage_size) { 3838 gatt_client_t * gatt_client; 3839 uint8_t status = gatt_client_provide_context_for_handle(con_handle, &gatt_client); 3840 if (status != ERROR_CODE_SUCCESS){ 3841 return status; 3842 } 3843 3844 if (gatt_client->eatt_state != GATT_CLIENT_EATT_IDLE){ 3845 return ERROR_CODE_COMMAND_DISALLOWED; 3846 } 3847 3848 // need one buffer for sending and one for receiving. Receiving includes pre-buffer for reports 3849 uint16_t buffer_size_per_client = storage_size / num_channels; 3850 uint16_t max_mtu = (buffer_size_per_client - REPORT_PREBUFFER_HEADER) / 2; 3851 if (max_mtu < 64) { 3852 return ERROR_CODE_INVALID_HCI_COMMAND_PARAMETERS; 3853 } 3854 3855 if ((num_channels == 0) || (num_channels > MAX_NR_EATT_CHANNELS)){ 3856 return ERROR_CODE_INVALID_HCI_COMMAND_PARAMETERS; 3857 } 3858 3859 // create max num_channel eatt clients 3860 uint8_t i; 3861 btstack_linked_list_t eatt_clients = NULL; 3862 for (i=0;i<num_channels;i++) { 3863 gatt_client_t * new_gatt_client = btstack_memory_gatt_client_get(); 3864 if (new_gatt_client == NULL) { 3865 break; 3866 } 3867 btstack_linked_list_add(&eatt_clients, (btstack_linked_item_t*)new_gatt_client); 3868 } 3869 3870 if (i != num_channels){ 3871 while (true){ 3872 gatt_client = (gatt_client_t *) btstack_linked_list_pop(&eatt_clients); 3873 if (gatt_client == NULL) { 3874 break; 3875 } 3876 btstack_memory_gatt_client_free(gatt_client); 3877 } 3878 return ERROR_CODE_MEMORY_CAPACITY_EXCEEDED; 3879 } 3880 3881 hci_connection_t * hci_connection = hci_connection_for_handle(con_handle); 3882 hci_connection->att_server.eatt_outgoing_active = true; 3883 3884 gatt_client->callback = callback; 3885 gatt_client->eatt_num_clients = num_channels; 3886 gatt_client->eatt_storage_buffer = storage_buffer; 3887 gatt_client->eatt_storage_size = storage_size; 3888 gatt_client->eatt_clients = eatt_clients; 3889 gatt_client->eatt_state = GATT_CLIENT_EATT_DISCOVER_GATT_SERVICE_W2_SEND; 3890 gatt_client_notify_can_send_query(gatt_client); 3891 3892 return ERROR_CODE_SUCCESS; 3893 } 3894 3895 #endif 3896 3897 #ifdef FUZZING_BUILD_MODE_UNSAFE_FOR_PRODUCTION 3898 void gatt_client_att_packet_handler_fuzz(uint8_t packet_type, uint16_t handle, uint8_t *packet, uint16_t size){ 3899 gatt_client_att_packet_handler(packet_type, handle, packet, size); 3900 } 3901 3902 uint8_t gatt_client_get_client(hci_con_handle_t con_handle, gatt_client_t ** out_gatt_client){ 3903 uint8_t status = gatt_client_provide_context_for_handle(con_handle, out_gatt_client); 3904 return status; 3905 } 3906 #endif 3907