Command Packets (CMD_TO_STRAP)
Commands sent to the device via the CMD_TO_STRAP characteristic follow a consistent structure.
Most commands use this 12-byte format:
aa 08 00 a8 23 | XX | YY | ZZ | CC CC CC CC
Header | PC | Cat| Val| Checksum
| Field | Bytes | Description |
|---|
| Header | 5 | Fixed header: aa0800a823 |
| Packet # | 1 | Packet counter (not validated by device) |
| Category | 1 | Command category (see below) |
| Value | 1 | Command value (usually 0x00 for off, 0x01 for on) |
| Checksum | 4 | CRC-32 variant (little-endian) |
Command Categories
The category byte determines the type of command:
| Category | Purpose | Example Value |
|---|
0x03 | Start/stop activity and recording | 0x00 / 0x01 |
0x0e | Enable/disable broadcast heart rate | 0x00 / 0x01 |
0x14 | Unknown (always sent with value 0x00) | 0x00 |
0x16 | Trigger data retrieval | 0x00 |
0x1d | Reboot device | 0x00 |
0x23 | Sync operations | varies |
0x24 | Get string from device | varies |
0x43 | Unknown | varies |
0x45 | Unknown | varies |
0x4c | Get device name | varies |
0x73 | Query device (returns notification on CMD_FROM_STRAP) | 0x01 |
0x74 | Query device with optional string data | 0x01 |
0x75 | Unknown | varies |
0x76 | Unknown | varies |
Example Commands
Broadcast Heart Rate
aa0800a823 07 0e 00 c7e40f08 # Off
aa0800a823 08 0e 01 6c935474 # On
aa0800a823 09 0e 00 cdc99102 # Off
Activity Control
aa0800a823 8c 03 01 7d5ec627 # Start activity
aa0800a823 8d 03 00 dc040351 # Stop activity
aa0800a823 90 03 01 6904fa32 # Start recording
aa0800a823 91 03 00 c85e3f44 # Stop recording
Health Monitor
aa0800a823 05 03 00 e44e25be # Health Monitor off
aa0800a823 06 03 01 2bc064cb # Health Monitor on
Data Retrieval
aa0800a823 0e 16 00 1147c585 # Retrieve data (triggers DATA_FROM_STRAP notifications)
Device Control
aa0800a823 d4 1d 00 3c2e2fe6 # Reboot device
aa0800a823 91 45 01 dd861b95 # Alarm off
The packet counter (6th byte) is not validated by the device. You can use any value or keep it constant.
Alarm Packets
Alarm commands use an extended format with 24 bytes:
aa 10 00 57 23 | XX | YY YY | UU UU UU UU | 00 00 00 00 | CC CC CC CC
Header | PC | Flags | Unix Time | Padding | Checksum
| Field | Bytes | Description |
|---|
| Header | 5 | Fixed header: aa10005723 |
| Packet # | 1 | Packet counter |
| Flags | 2 | Alarm type flags (usually 4201) |
| Unix Time | 4 | Alarm time as Unix timestamp (little-endian) |
| Padding | 4 | Zero padding |
| Checksum | 4 | CRC-32 variant (little-endian) |
Alarm Examples
aa10005723 6d 4201 d0366566 00000000 f62deb81 # 7:00 Exact time
aa10005723 6e 4201 0c376566 00000000 1023ccef # 7:01 Exact time
aa10005723 6f 4201 207d6566 00000000 fea1e060 # 12:00 Exact time
aa10005723 70 4201 50116566 00000000 f226a8bd # 4:20 Exact time
aa10005723 81 4201 f07e6666 00000000 7037c2a4 # Peak 06:20
aa10005723 82 4201 f07e6666 00000000 7151203d # Perform 06:20
aa10005723 83 4201 f07e6666 00000000 b18eaefc # In the Green 06:20
Setting an Alarm in Python
import struct
import time
from crc_module import my_crc # See Checksum/CRC section
# Set alarm for 10 seconds from now
unix_time = int(time.time()) + 10
unix_hex = struct.pack('<I', unix_time).hex()
# Build packet (without checksum)
packet_data = f"aa10005723704201{unix_hex}00000000"
# Calculate checksum
checksum_int = my_crc(bytearray.fromhex(packet_data))[0]
checksum_hex = struct.pack('<I', checksum_int).hex()
# Complete packet
packet = f"{packet_data}{checksum_hex}"
# Send via gatttool
import subprocess
subprocess.run([
'sudo', 'gatttool', '-i', 'hci0', '-t', 'random',
'-b', 'XX:XX:XX:XX:XX:XX',
'--char-write', '-a', '0x0010', '-n', packet
])
Data Packets (DATA_FROM_STRAP)
The device sends real-time and historical data via DATA_FROM_STRAP notifications.
Real-Time Health Data (24 bytes)
Received every second during activities or when Health Monitor is active:
aa 18 00 ff 28 02 | UU UU UU UU | SS SS | HR | RR | RR Data (9 bytes) | CC CC CC CC
Header | Unix Time | ?? | HR | RR | RR Data | Checksum
| Field | Bytes | Description |
|---|
| Header | 6 | Fixed: aa1800ff2802 |
| Unix | 4 | Timestamp (little-endian) |
| Unknown | 2 | Purpose unknown |
| HR | 1 | Heart rate (BPM) |
| RR | 1 | Respiratory rate flag/count |
| RR Data | 9 | Respiratory rate data |
| Checksum | 4 | CRC-32 variant |
Example:
Header Unix ?? HR RR RR data Checksum
aa1800ff2802 ad896566 f065 42 01 67060000000000000101 3ba00d4d
aa1800ff2802 ae896566 f860 43 00 00000000000000000101 5025f793
aa1800ff2802 af896566 085c 42 00 00000000000000000101 add7df13
aa1800ff2802 b0896566 1057 42 00 00000000000000000101 24b22179
Sync Data Request (28 bytes)
Received at end of sync process indicating batch number to request:
aa 1c 00 ab 31 | PC | 02 | UU UU UU UU | ?? ?? ?? ?? ?? ?? | BB BB BB BB | 04 00 00 00 00 00 00 | CC CC CC CC
Header | PC | ?? | Unix Time | Unknown | Batch N | Unknown | Checksum
Example:
unix don't care batch N checksum
aa1c00ab31 18 02 f65c7066 804043000000 2e470100 04000000000000 7f873cf3
aa1c00ab31 19 02 fb5c7066 704143000000 2e470100 04000000000000 f277ceb0
To request the next batch, send:
aa10005723 {PC} 1701 {batch_N} 00000000 {checksum}
Historical Data (96 bytes)
Large packets received during sync operations containing historical health metrics.
First 31 bytes:
Header Time? Unix? Something HR RR RR data
aa5c00f02f0c 07 8bb7 0900 c8326966 e03c8054cc01 58 01 b902000000000000
aa5c00f02f0c 07 8cb7 0900 c9326966 f0378054cc01 58 01 b502000000000000
aa5c00f02f0c 07 8db7 0900 ca326966 f8328054cc01 58 02 b802b90200000000
Remaining 65 bytes contain additional sensor data (format still being researched).
Erase Device Command
Special format for device erasure:
aa10005723 cf 19 fefefefefefefefe 00 2f8744f6
aa10005723 d2 19 fefefefefefefefe 00 e30e2693
aa10005723 d3 19 fefefefefefefefe 00 23d1a852
This command will erase all data on the device.
Text Command Packets (72 bytes)
Rare packets that contain text strings:
aa 48 00 f3 23 | NN NN 78 01 | Text String (32 bytes) | 32 00... | CC CC CC CC
Header | Number | Null-terminated string | Padding | Checksum
Decoded examples:
aa4800f323 47224 general_ab_test 0625af8c
aa4800f323 47480 sigproc_10_sec_dp 458e3fdb
aa4800f323 47736 sigproc_pdaf 9334bc6a
aa4800f323 47992 enable_r19_packets 5db99544
Purpose unknown; sent sporadically by the app.