1
0
mirror of https://github.com/esphome/esphome.git synced 2025-09-24 14:12:24 +01:00

[bluetooth_proxy] Send native 16/32-bit UUIDs instead of always converting to 128-bit

This commit is contained in:
J. Nick Koston
2025-07-30 21:24:40 -10:00
parent 71557c9f58
commit 37911e84f2
8 changed files with 143 additions and 19 deletions

View File

@@ -1482,21 +1482,42 @@ message BluetoothGATTGetServicesRequest {
}
message BluetoothGATTDescriptor {
repeated uint64 uuid = 1 [(fixed_array_size) = 2];
repeated uint64 uuid = 1 [(fixed_array_size) = 2, (fixed_array_skip_zero) = true];
uint32 handle = 2;
// New fields for efficient UUID (v1.12+)
// Only one of uuid, uuid16, or uuid32 will be set.
// uuid16/uuid32 are only used for 16/32-bit UUIDs with v1.12+ clients.
// 128-bit UUIDs always use the uuid field for backwards compatibility.
uint32 uuid16 = 3; // 16-bit UUID
uint32 uuid32 = 4; // 32-bit UUID
}
message BluetoothGATTCharacteristic {
repeated uint64 uuid = 1 [(fixed_array_size) = 2];
repeated uint64 uuid = 1 [(fixed_array_size) = 2, (fixed_array_skip_zero) = true];
uint32 handle = 2;
uint32 properties = 3;
repeated BluetoothGATTDescriptor descriptors = 4;
// New fields for efficient UUID (v1.12+)
// Only one of uuid, uuid16, or uuid32 will be set.
// uuid16/uuid32 are only used for 16/32-bit UUIDs with v1.12+ clients.
// 128-bit UUIDs always use the uuid field for backwards compatibility.
uint32 uuid16 = 5; // 16-bit UUID
uint32 uuid32 = 6; // 32-bit UUID
}
message BluetoothGATTService {
repeated uint64 uuid = 1 [(fixed_array_size) = 2];
repeated uint64 uuid = 1 [(fixed_array_size) = 2, (fixed_array_skip_zero) = true];
uint32 handle = 2;
repeated BluetoothGATTCharacteristic characteristics = 3;
// New fields for efficient UUID (v1.12+)
// Only one of uuid, uuid16, or uuid32 will be set.
// uuid16/uuid32 are only used for 16/32-bit UUIDs with v1.12+ clients.
// 128-bit UUIDs always use the uuid field for backwards compatibility.
uint32 uuid16 = 4; // 16-bit UUID
uint32 uuid32 = 5; // 32-bit UUID
}
message BluetoothGATTGetServicesResponse {

View File

@@ -1363,7 +1363,7 @@ bool APIConnection::send_hello_response(const HelloRequest &msg) {
HelloResponse resp;
resp.api_version_major = 1;
resp.api_version_minor = 11;
resp.api_version_minor = 12;
// Temporary string for concatenation - will be valid during send_message call
std::string server_info = App.get_name() + " (esphome v" ESPHOME_VERSION ")";
resp.set_server_info(StringRef(server_info));

View File

@@ -28,6 +28,7 @@ extend google.protobuf.FieldOptions {
optional string field_ifdef = 1042;
optional uint32 fixed_array_size = 50007;
optional bool no_zero_copy = 50008 [default=false];
optional bool fixed_array_skip_zero = 50009 [default=false];
// container_pointer: Zero-copy optimization for repeated fields.
//

View File

@@ -1888,44 +1888,68 @@ bool BluetoothGATTGetServicesRequest::decode_varint(uint32_t field_id, ProtoVarI
return true;
}
void BluetoothGATTDescriptor::encode(ProtoWriteBuffer buffer) const {
buffer.encode_uint64(1, this->uuid[0], true);
buffer.encode_uint64(1, this->uuid[1], true);
if (!(this->uuid[0] == 0 && this->uuid[1] == 0)) {
buffer.encode_uint64(1, this->uuid[0], true);
buffer.encode_uint64(1, this->uuid[1], true);
}
buffer.encode_uint32(2, this->handle);
buffer.encode_uint32(3, this->uuid16);
buffer.encode_uint32(4, this->uuid32);
}
void BluetoothGATTDescriptor::calculate_size(ProtoSize &size) const {
size.add_uint64_force(1, this->uuid[0]);
size.add_uint64_force(1, this->uuid[1]);
if (!(this->uuid[0] == 0 && this->uuid[1] == 0)) {
size.add_uint64_force(1, this->uuid[0]);
size.add_uint64_force(1, this->uuid[1]);
}
size.add_uint32(1, this->handle);
size.add_uint32(1, this->uuid16);
size.add_uint32(1, this->uuid32);
}
void BluetoothGATTCharacteristic::encode(ProtoWriteBuffer buffer) const {
buffer.encode_uint64(1, this->uuid[0], true);
buffer.encode_uint64(1, this->uuid[1], true);
if (!(this->uuid[0] == 0 && this->uuid[1] == 0)) {
buffer.encode_uint64(1, this->uuid[0], true);
buffer.encode_uint64(1, this->uuid[1], true);
}
buffer.encode_uint32(2, this->handle);
buffer.encode_uint32(3, this->properties);
for (auto &it : this->descriptors) {
buffer.encode_message(4, it, true);
}
buffer.encode_uint32(5, this->uuid16);
buffer.encode_uint32(6, this->uuid32);
}
void BluetoothGATTCharacteristic::calculate_size(ProtoSize &size) const {
size.add_uint64_force(1, this->uuid[0]);
size.add_uint64_force(1, this->uuid[1]);
if (!(this->uuid[0] == 0 && this->uuid[1] == 0)) {
size.add_uint64_force(1, this->uuid[0]);
size.add_uint64_force(1, this->uuid[1]);
}
size.add_uint32(1, this->handle);
size.add_uint32(1, this->properties);
size.add_repeated_message(1, this->descriptors);
size.add_uint32(1, this->uuid16);
size.add_uint32(1, this->uuid32);
}
void BluetoothGATTService::encode(ProtoWriteBuffer buffer) const {
buffer.encode_uint64(1, this->uuid[0], true);
buffer.encode_uint64(1, this->uuid[1], true);
if (!(this->uuid[0] == 0 && this->uuid[1] == 0)) {
buffer.encode_uint64(1, this->uuid[0], true);
buffer.encode_uint64(1, this->uuid[1], true);
}
buffer.encode_uint32(2, this->handle);
for (auto &it : this->characteristics) {
buffer.encode_message(3, it, true);
}
buffer.encode_uint32(4, this->uuid16);
buffer.encode_uint32(5, this->uuid32);
}
void BluetoothGATTService::calculate_size(ProtoSize &size) const {
size.add_uint64_force(1, this->uuid[0]);
size.add_uint64_force(1, this->uuid[1]);
if (!(this->uuid[0] == 0 && this->uuid[1] == 0)) {
size.add_uint64_force(1, this->uuid[0]);
size.add_uint64_force(1, this->uuid[1]);
}
size.add_uint32(1, this->handle);
size.add_repeated_message(1, this->characteristics);
size.add_uint32(1, this->uuid16);
size.add_uint32(1, this->uuid32);
}
void BluetoothGATTGetServicesResponse::encode(ProtoWriteBuffer buffer) const {
buffer.encode_uint64(1, this->address);

View File

@@ -1857,6 +1857,8 @@ class BluetoothGATTDescriptor : public ProtoMessage {
public:
std::array<uint64_t, 2> uuid{};
uint32_t handle{0};
uint32_t uuid16{0};
uint32_t uuid32{0};
void encode(ProtoWriteBuffer buffer) const override;
void calculate_size(ProtoSize &size) const override;
#ifdef HAS_PROTO_MESSAGE_DUMP
@@ -1871,6 +1873,8 @@ class BluetoothGATTCharacteristic : public ProtoMessage {
uint32_t handle{0};
uint32_t properties{0};
std::vector<BluetoothGATTDescriptor> descriptors{};
uint32_t uuid16{0};
uint32_t uuid32{0};
void encode(ProtoWriteBuffer buffer) const override;
void calculate_size(ProtoSize &size) const override;
#ifdef HAS_PROTO_MESSAGE_DUMP
@@ -1884,6 +1888,8 @@ class BluetoothGATTService : public ProtoMessage {
std::array<uint64_t, 2> uuid{};
uint32_t handle{0};
std::vector<BluetoothGATTCharacteristic> characteristics{};
uint32_t uuid16{0};
uint32_t uuid32{0};
void encode(ProtoWriteBuffer buffer) const override;
void calculate_size(ProtoSize &size) const override;
#ifdef HAS_PROTO_MESSAGE_DUMP

View File

@@ -1561,6 +1561,8 @@ void BluetoothGATTDescriptor::dump_to(std::string &out) const {
dump_field(out, "uuid", it, 4);
}
dump_field(out, "handle", this->handle);
dump_field(out, "uuid16", this->uuid16);
dump_field(out, "uuid32", this->uuid32);
}
void BluetoothGATTCharacteristic::dump_to(std::string &out) const {
MessageDumpHelper helper(out, "BluetoothGATTCharacteristic");
@@ -1574,6 +1576,8 @@ void BluetoothGATTCharacteristic::dump_to(std::string &out) const {
it.dump_to(out);
out.append("\n");
}
dump_field(out, "uuid16", this->uuid16);
dump_field(out, "uuid32", this->uuid32);
}
void BluetoothGATTService::dump_to(std::string &out) const {
MessageDumpHelper helper(out, "BluetoothGATTService");
@@ -1586,6 +1590,8 @@ void BluetoothGATTService::dump_to(std::string &out) const {
it.dump_to(out);
out.append("\n");
}
dump_field(out, "uuid16", this->uuid16);
dump_field(out, "uuid32", this->uuid32);
}
void BluetoothGATTGetServicesResponse::dump_to(std::string &out) const {
MessageDumpHelper helper(out, "BluetoothGATTGetServicesResponse");