Jump to content

GATT Profile Data in Bluetooth Low Energy

Revision as of 2025-05-10T06:32:26 by Kai (talk | contribs)

This article explains the binary structure of the GATT attributes data array that many Bluetooth Low Energy application frameworks, like BTstack, expect as setup input.

GATT characteristic attribute (descriptor) types

Characteristic declaration

Let's have a look at an ATT attribute that declares a GATT characteristic. Here is the binary sequence (in hex representation) generated for an attribute that declares a GATT characteristic with attribute UUID B0B0F155-B0B0-B0B0-B0B0-B0B000000101 and permissions READ | DYNAMIC

0x1b, 0x00, 0x02, 0x00, 0x08, 0x00, 0x03, 0x28, 0x02, 0x09, 0x00, 0x01, 0x01, 0x00, 0x00, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0x55, 0xf1, 0xb0, 0xb0

The bytes are grouped from left to right according to this scheme:

  • 2 bytes for the length of this attribute definition: 0x001b (= 27 bytes)
  • 2 bytes for the access permission of this attribute: 0x0002 (= read-only)
  • 2 bytes for the attribute handle: 0x0008
  • 2 bytes for the attribute type: 0x2803 (short 16-bit UUID that indicates a characteristic declaration)
  • 1 byte for the access permissions of the declared characteristic: 0x02 (= read-only)
  • 2 bytes for the attribute handle of the characteristic value: 0x0009
  • 16 bytes for the 128-bit UUID of the characteristic: 0xb0b0f155b0b0b0b0b0b0b0b000000101

where the bytes in each group are in reverse order!

For the official specification of the Bluetooth 5.4 GATT characteristic declaration refer to section 3.3.1 in the in the Bluetooth 5.4 Core Specification. That section also lists the characteristics permissions (or properties):

Properties Value Description
Broadcast 0x01 If set, permits broadcasts of the Characteristic Value using Server Characteristic Configuration Descriptor. If set, the Server Characteristic Configuration Descriptor shall exist.
Read 0x02 If set, permits reads of the Characteristic Value using procedures defined in Section 4.8
Write Without Response 0x04 If set, permit writes of the Characteristic Value without response using procedures defined in Section 4.9.1.
Write 0x08 If set, permits writes of the Characteristic Value with response using procedures defined in Section 4.9.3 or Section 4.9.4.
Notify 0x10 If set, permits notifications of a Characteristic Value without acknowledgment using the procedure defined in Section 4.10. If set, the Client Characteristic Configuration Descriptor shall exist.
Indicate 0x20 If set, permits indications of a Characteristic Value with acknowledgment using the procedure defined in Section 4.11. If set, the Client Characteristic Configuration Descriptor shall exist.
Authenticated Signed Writes 0x40 If set, permits signed writes to the Characteristic Value using the procedure defined in Section 4.9.2.
Extended Properties 0x80 If set, additional characteristic properties are defined in the Characteristic Extended Properties Descriptor defined in Section 3.3.3.1. If set, the Characteristic Extended Properties Descriptor shall exist.

Characteristic value

0x16, 0x00, 0x02, 0x03, 0x09, 0x00, 0x01, 0x01, 0x00, 0x00, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0xb0, 0x55, 0xf1, 0xb0, 0xb0

The bytes are grouped from left to right as follows:

  • 2 bytes for the length of the attribute: 0x0016 (= 22 bytes)
  • 2 bytes for the permissions (properties) of the attribute: 0x0302 (= read-only, dynamic, 128-bit UUID)
  • 2 bytes for the handle of the attribute: 0x0009
  • 16 bytes for the UUID of the characteristic that the value is associated with: 0xb0b0f155b0b0b0b0b0b0b0b000000101

Characteristic Client Configuration

The client configuration attribute of a GATT characteristic allows the GATT client to change the notify (or indicate) behavior for value write operations. Let us examine the sections of this example attribute:

0x0a, 0x00, 0x0e, 0x01, 0x0e, 0x00, 0x02, 0x29, 0x00, 0x00

From left to right, there are

  • 2 bytes for the length of the attribute: 0x000a (= 10 bytes)
  • 2 bytes for the permissions of this attribute: 0x010e (indicates read | write | write_without_response, dynamic)
  • 2 bytes for the handle of this attribute: 0x000e
  • 2 bytes for the short 16-bit UUID of this attribute: 0x2902 (the UUID for client characteristic configuration)
  • 2 bytes that indicate whether notification or indication messages are enabled: 0x0000 (both type of messages are disabled)

For the last two bytes, the following options are possible, depending on the requests from the GATT client to enable or disable notification or indication messages (when the value of the associated characteristic changes):

bit 0 the least significant bit indicates whether sending notifications is enabled (1) or disabled (0)
bit 1 the next significant bit indicates whether sending indications is enabled (1) or not (0)

All other bits are reserved for use in future changes to the GATT protocol.

User description

Here is an example binary sequence for a GATT user description attribute.

0x08, 0x00, 0x0a, 0x01, 0x0a, 0x00, 0x01, 0x29

Let's break down the byte grouping from left to right:

  • 2 bytes for the length of this attribute: 0x0008 (= 8 bytes)
  • 2 bytes for permissions: 0x010a (= read, write, dynamic)
  • 2 bytes for the handle of this attribute
  • 2 bytes for the 16-bit short UUID that indicates a user description attribute: 0x2901

where the order of the bytes in each group needs to be reversed before analyzing.

The attribute declaration does not include the user description text itself. User description text is always "dynamic", meaning that it is served to the client on demand on the basis of the attribute handle. In BTstack, the implementation of the read callback is responsible for returning the UTF-8 bytes for the text string corresponding the attribute handle.

Cookies help us deliver our services. By using our services, you agree to our use of cookies.