mirror of
https://github.com/bluekitchen/btstack.git
synced 2025-01-25 18:35:17 +00:00
add gatt_client_read_value_of_characteristics_by_uuid16/128
This commit is contained in:
parent
b0beacba68
commit
3f4e6e214e
@ -253,17 +253,29 @@ static void att_find_by_type_value_request(uint16_t request_type, uint16_t attri
|
||||
}
|
||||
|
||||
// precondition: can_send_packet_now == TRUE
|
||||
static void att_read_by_type_or_group_request(uint16_t request_type, uint16_t attribute_group_type, uint16_t peripheral_handle, uint16_t start_handle, uint16_t end_handle){
|
||||
static void att_read_by_type_or_group_request_for_uuid16(uint16_t request_type, uint16_t uuid16, uint16_t peripheral_handle, uint16_t start_handle, uint16_t end_handle){
|
||||
l2cap_reserve_packet_buffer();
|
||||
uint8_t * request = l2cap_get_outgoing_buffer();
|
||||
request[0] = request_type;
|
||||
bt_store_16(request, 1, start_handle);
|
||||
bt_store_16(request, 3, end_handle);
|
||||
bt_store_16(request, 5, attribute_group_type);
|
||||
bt_store_16(request, 5, uuid16);
|
||||
|
||||
l2cap_send_prepared_connectionless(peripheral_handle, L2CAP_CID_ATTRIBUTE_PROTOCOL, 7);
|
||||
}
|
||||
|
||||
// precondition: can_send_packet_now == TRUE
|
||||
static void att_read_by_type_or_group_request_for_uuid128(uint16_t request_type, uint8_t * uuid128, uint16_t peripheral_handle, uint16_t start_handle, uint16_t end_handle){
|
||||
l2cap_reserve_packet_buffer();
|
||||
uint8_t * request = l2cap_get_outgoing_buffer();
|
||||
request[0] = request_type;
|
||||
bt_store_16(request, 1, start_handle);
|
||||
bt_store_16(request, 3, end_handle);
|
||||
swap128(uuid128, &request[5]);
|
||||
|
||||
l2cap_send_prepared_connectionless(peripheral_handle, L2CAP_CID_ATTRIBUTE_PROTOCOL, 21);
|
||||
}
|
||||
|
||||
// precondition: can_send_packet_now == TRUE
|
||||
static void att_read_request(uint16_t request_type, uint16_t peripheral_handle, uint16_t attribute_handle){
|
||||
l2cap_reserve_packet_buffer();
|
||||
@ -351,7 +363,7 @@ static uint16_t write_blob_length(gatt_client_t * peripheral){
|
||||
}
|
||||
|
||||
static void send_gatt_services_request(gatt_client_t *peripheral){
|
||||
att_read_by_type_or_group_request(ATT_READ_BY_GROUP_TYPE_REQUEST, GATT_PRIMARY_SERVICE_UUID, peripheral->handle, peripheral->start_group_handle, peripheral->end_group_handle);
|
||||
att_read_by_type_or_group_request_for_uuid16(ATT_READ_BY_GROUP_TYPE_REQUEST, GATT_PRIMARY_SERVICE_UUID, peripheral->handle, peripheral->start_group_handle, peripheral->end_group_handle);
|
||||
}
|
||||
|
||||
static void send_gatt_by_uuid_request(gatt_client_t *peripheral, uint16_t attribute_group_type){
|
||||
@ -375,11 +387,11 @@ static void send_gatt_included_service_uuid_request(gatt_client_t *peripheral){
|
||||
}
|
||||
|
||||
static void send_gatt_included_service_request(gatt_client_t *peripheral){
|
||||
att_read_by_type_or_group_request(ATT_READ_BY_TYPE_REQUEST, GATT_INCLUDE_SERVICE_UUID, peripheral->handle, peripheral->start_group_handle, peripheral->end_group_handle);
|
||||
att_read_by_type_or_group_request_for_uuid16(ATT_READ_BY_TYPE_REQUEST, GATT_INCLUDE_SERVICE_UUID, peripheral->handle, peripheral->start_group_handle, peripheral->end_group_handle);
|
||||
}
|
||||
|
||||
static void send_gatt_characteristic_request(gatt_client_t *peripheral){
|
||||
att_read_by_type_or_group_request(ATT_READ_BY_TYPE_REQUEST, GATT_CHARACTERISTICS_UUID, peripheral->handle, peripheral->start_group_handle, peripheral->end_group_handle);
|
||||
att_read_by_type_or_group_request_for_uuid16(ATT_READ_BY_TYPE_REQUEST, GATT_CHARACTERISTICS_UUID, peripheral->handle, peripheral->start_group_handle, peripheral->end_group_handle);
|
||||
}
|
||||
|
||||
static void send_gatt_characteristic_descriptor_request(gatt_client_t *peripheral){
|
||||
@ -390,6 +402,14 @@ static void send_gatt_read_characteristic_value_request(gatt_client_t *periphera
|
||||
att_read_request(ATT_READ_REQUEST, peripheral->handle, peripheral->attribute_handle);
|
||||
}
|
||||
|
||||
static void send_gatt_read_by_type_request(gatt_client_t * peripheral){
|
||||
if (peripheral->uuid16){
|
||||
att_read_by_type_or_group_request_for_uuid16(ATT_READ_BY_TYPE_REQUEST, peripheral->uuid16, peripheral->handle, peripheral->start_group_handle, peripheral->end_group_handle);
|
||||
} else {
|
||||
att_read_by_type_or_group_request_for_uuid128(ATT_READ_BY_TYPE_REQUEST, peripheral->uuid128, peripheral->handle, peripheral->start_group_handle, peripheral->end_group_handle);
|
||||
}
|
||||
}
|
||||
|
||||
static void send_gatt_read_blob_request(gatt_client_t *peripheral){
|
||||
att_read_blob_request(ATT_READ_BLOB_REQUEST, peripheral->handle, peripheral->attribute_handle, peripheral->attribute_offset);
|
||||
}
|
||||
@ -415,7 +435,7 @@ static void send_gatt_cancel_prepared_write_request(gatt_client_t * peripheral){
|
||||
}
|
||||
|
||||
static void send_gatt_read_client_characteristic_configuration_request(gatt_client_t * peripheral){
|
||||
att_read_by_type_or_group_request(ATT_READ_BY_TYPE_REQUEST, GATT_CLIENT_CHARACTERISTICS_CONFIGURATION, peripheral->handle, peripheral->start_group_handle, peripheral->end_group_handle);
|
||||
att_read_by_type_or_group_request_for_uuid16(ATT_READ_BY_TYPE_REQUEST, GATT_CLIENT_CHARACTERISTICS_CONFIGURATION, peripheral->handle, peripheral->start_group_handle, peripheral->end_group_handle);
|
||||
}
|
||||
|
||||
static void send_gatt_read_characteristic_descriptor_request(gatt_client_t * peripheral){
|
||||
@ -547,7 +567,6 @@ static void report_gatt_characteristics(gatt_client_t * peripheral, uint8_t * pa
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void report_gatt_included_service(gatt_client_t * peripheral, uint8_t *uuid128, uint16_t uuid16){
|
||||
le_service_t service;
|
||||
service.uuid16 = uuid16;
|
||||
@ -668,6 +687,10 @@ static inline void trigger_next_characteristic_descriptor_query(gatt_client_t *
|
||||
trigger_next_query(peripheral, last_result_handle, P_W2_SEND_ALL_CHARACTERISTIC_DESCRIPTORS_QUERY);
|
||||
}
|
||||
|
||||
static inline void trigger_next_read_by_type_query(gatt_client_t * peripheral, uint16_t last_result_handle){
|
||||
trigger_next_query(peripheral, last_result_handle, P_W2_SEND_READ_BY_TYPE_REQUEST);
|
||||
}
|
||||
|
||||
static inline void trigger_next_prepare_write_query(gatt_client_t * peripheral, gatt_client_state_t next_query_state, gatt_client_state_t done_state){
|
||||
peripheral->attribute_offset += write_blob_length(peripheral);
|
||||
uint16_t next_blob_length = write_blob_length(peripheral);
|
||||
@ -692,6 +715,7 @@ static inline void trigger_next_blob_query(gatt_client_t * peripheral, gatt_clie
|
||||
peripheral->gatt_client_state = next_query_state;
|
||||
}
|
||||
|
||||
|
||||
static int is_value_valid(gatt_client_t *peripheral, uint8_t *packet, uint16_t size){
|
||||
uint16_t attribute_handle = READ_BT_16(packet, 1);
|
||||
uint16_t value_offset = READ_BT_16(packet, 3);
|
||||
@ -791,6 +815,11 @@ static void gatt_client_run(void){
|
||||
send_gatt_read_blob_request(peripheral);
|
||||
return;
|
||||
|
||||
case P_W2_SEND_READ_BY_TYPE_REQUEST:
|
||||
peripheral->gatt_client_state = P_W4_READ_BY_TYPE_RESPONSE;
|
||||
send_gatt_read_by_type_request(peripheral);
|
||||
break;
|
||||
|
||||
case P_W2_SEND_WRITE_CHARACTERISTIC_VALUE:
|
||||
peripheral->gatt_client_state = P_W4_WRITE_CHARACTERISTIC_VALUE_RESULT;
|
||||
send_gatt_write_attribute_value_request(peripheral);
|
||||
@ -1006,6 +1035,18 @@ static void gatt_client_att_packet_handler(uint8_t packet_type, uint16_t handle,
|
||||
peripheral->client_characteristic_configuration_handle = READ_BT_16(packet, 2);
|
||||
peripheral->gatt_client_state = P_W2_WRITE_CLIENT_CHARACTERISTIC_CONFIGURATION;
|
||||
break;
|
||||
case P_W4_READ_BY_TYPE_RESPONSE: {
|
||||
uint16_t pair_size = packet[1];
|
||||
uint16_t offset;
|
||||
uint16_t last_result_handle = 0;
|
||||
for (offset = 2; offset < size ; offset += pair_size){
|
||||
uint16_t value_handle = READ_BT_16(packet, offset);
|
||||
report_gatt_characteristic_value(peripheral, value_handle, &packet[offset+2], pair_size-2);
|
||||
last_result_handle = value_handle;
|
||||
}
|
||||
trigger_next_read_by_type_query(peripheral, last_result_handle);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
@ -1180,6 +1221,14 @@ static void gatt_client_att_packet_handler(uint8_t packet_type, uint16_t handle,
|
||||
gatt_client_handle_transaction_complete(peripheral);
|
||||
emit_gatt_complete_event(peripheral, 0);
|
||||
break;
|
||||
case P_W4_READ_BY_TYPE_RESPONSE:
|
||||
gatt_client_handle_transaction_complete(peripheral);
|
||||
if (peripheral->start_group_handle == peripheral->query_start_handle){
|
||||
emit_gatt_complete_event(peripheral, ATT_ERROR_ATTRIBUTE_NOT_FOUND);
|
||||
} else {
|
||||
emit_gatt_complete_event(peripheral, 0);
|
||||
}
|
||||
break;
|
||||
default:
|
||||
gatt_client_report_error_if_pending(peripheral, packet[4]);
|
||||
break;
|
||||
@ -1388,6 +1437,43 @@ le_command_status_t gatt_client_read_value_of_characteristic_using_value_handle(
|
||||
return BLE_PERIPHERAL_OK;
|
||||
}
|
||||
|
||||
le_command_status_t gatt_client_read_value_of_characteristics_by_uuid16(uint16_t gatt_client_id, uint16_t con_handle, uint16_t start_handle, uint16_t end_handle, uint16_t uuid16){
|
||||
gatt_client_t * peripheral = provide_context_for_conn_handle_and_start_timer(con_handle);
|
||||
|
||||
if (!peripheral) return (le_command_status_t) BTSTACK_MEMORY_ALLOC_FAILED;
|
||||
if (!is_ready(peripheral)) return BLE_PERIPHERAL_IN_WRONG_STATE;
|
||||
|
||||
peripheral->subclient_id = gatt_client_id;
|
||||
peripheral->start_group_handle = start_handle;
|
||||
peripheral->end_group_handle = end_handle;
|
||||
peripheral->query_start_handle = start_handle;
|
||||
peripheral->query_end_handle = end_handle;
|
||||
peripheral->uuid16 = uuid16;
|
||||
sdp_normalize_uuid((uint8_t*) &(peripheral->uuid128), uuid16);
|
||||
peripheral->gatt_client_state = P_W2_SEND_READ_BY_TYPE_REQUEST;
|
||||
gatt_client_run();
|
||||
return BLE_PERIPHERAL_OK;
|
||||
}
|
||||
|
||||
le_command_status_t gatt_client_read_value_of_characteristics_by_uuid128(uint16_t gatt_client_id, uint16_t con_handle, uint16_t start_handle, uint16_t end_handle, uint8_t * uuid128){
|
||||
gatt_client_t * peripheral = provide_context_for_conn_handle_and_start_timer(con_handle);
|
||||
|
||||
if (!peripheral) return (le_command_status_t) BTSTACK_MEMORY_ALLOC_FAILED;
|
||||
if (!is_ready(peripheral)) return BLE_PERIPHERAL_IN_WRONG_STATE;
|
||||
|
||||
peripheral->subclient_id = gatt_client_id;
|
||||
peripheral->start_group_handle = start_handle;
|
||||
peripheral->end_group_handle = end_handle;
|
||||
peripheral->query_start_handle = start_handle;
|
||||
peripheral->query_end_handle = end_handle;
|
||||
peripheral->uuid16 = 0;
|
||||
memcpy(peripheral->uuid128, uuid128, 16);
|
||||
peripheral->gatt_client_state = P_W2_SEND_READ_BY_TYPE_REQUEST;
|
||||
gatt_client_run();
|
||||
return BLE_PERIPHERAL_OK;
|
||||
}
|
||||
|
||||
|
||||
le_command_status_t gatt_client_read_value_of_characteristic(uint16_t gatt_client_id, uint16_t handle, le_characteristic_t *characteristic){
|
||||
return gatt_client_read_value_of_characteristic_using_value_handle(gatt_client_id, handle, characteristic->value_handle);
|
||||
}
|
||||
|
@ -77,6 +77,9 @@ typedef enum {
|
||||
|
||||
P_W2_SEND_READ_BLOB_QUERY,
|
||||
P_W4_READ_BLOB_RESULT,
|
||||
|
||||
P_W2_SEND_READ_BY_TYPE_REQUEST,
|
||||
P_W4_READ_BY_TYPE_RESPONSE,
|
||||
|
||||
P_W2_SEND_WRITE_CHARACTERISTIC_VALUE,
|
||||
P_W4_WRITE_CHARACTERISTIC_VALUE_RESULT,
|
||||
@ -299,6 +302,12 @@ le_command_status_t gatt_client_discover_characteristic_descriptors(uint16_t gat
|
||||
le_command_status_t gatt_client_read_value_of_characteristic(uint16_t gatt_client_id, uint16_t con_handle, le_characteristic_t *characteristic);
|
||||
le_command_status_t gatt_client_read_value_of_characteristic_using_value_handle(uint16_t gatt_client_id, uint16_t con_handle, uint16_t characteristic_value_handle);
|
||||
|
||||
/**
|
||||
* @brief Reads the characteric value of all characteristics with the uuid. For each found, an le_characteristic_value_event_t with type set to GATT_CHARACTERISTIC_VALUE_QUERY_RESULT will be generated and passed to the registered callback. The gatt_complete_event_t with type set to GATT_QUERY_COMPLETE, marks the end of read.
|
||||
*/
|
||||
le_command_status_t gatt_client_read_value_of_characteristics_by_uuid16(uint16_t gatt_client_id, uint16_t con_handle, uint16_t start_handle, uint16_t end_handle, uint16_t uuid16);
|
||||
le_command_status_t gatt_client_read_value_of_characteristics_by_uuid128(uint16_t gatt_client_id, uint16_t con_handle, uint16_t start_handle, uint16_t end_handle, uint8_t * uuid128);
|
||||
|
||||
/**
|
||||
* @brief Reads the long characteristic value using the characteristic's value handle. The value will be returned in several blobs. For each blob, an le_characteristic_value_event_t with type set to GATT_CHARACTERISTIC_VALUE_QUERY_RESULT and updated value offset will be generated and passed to the registered callback. The gatt_complete_event_t with type set to GATT_QUERY_COMPLETE, mark the end of read.
|
||||
*/
|
||||
|
Loading…
x
Reference in New Issue
Block a user