-
Notifications
You must be signed in to change notification settings - Fork 0
Packet Format and Topics
Defined in src/CdpPacket.h. Fixed 27-byte header, up to 229 bytes of data (PACKET_LENGTH = 256, HEADER_LENGTH = 27, MAX_DATA_LENGTH = 229):
|0 |8 |16 |20|21|22|23 |27 255|
+--------+--------+----+--+--+--+----+----------------------------------------+
| SDUID | DDUID |MUID|T |DT|HC|DCRC| DATA |
+--------+--------+----+--+--+--+----+----------------------------------------+
| Field | Offset | Length | Meaning |
|---|---|---|---|
| SDUID | 0 | 8 | Source device unique ID |
| DDUID | 8 | 8 | Destination device unique ID (or BROADCAST_DUID/PAPADUCK_DUID) |
| MUID | 16 | 4 | Message unique ID (assigned by the bloom filter for dedup) |
| Topic | 20 | 1 | Application/protocol topic (see below) |
| Duck type | 21 | 1 | Sender's DuckType
|
| Hop count | 22 | 1 | Incremented on each relay, capped at MAX_HOPS = 6
|
| Data CRC | 23 | 4 | CRC32 of the data section |
| Data | 27 | ≤229 | Payload (application data or protocol-internal, depending on topic) |
PAPADUCK_DUID is all-zero bytes; BROADCAST_DUID is all-0xFF bytes.
enum reservedTopic {
unused = 0x00,
ping = 0x01,
pong = 0x02,
ack = 0x04,
cmd = 0x05,
rreq = 0x06,
rrep = 0x07,
max_reserved = 0x0F
};rreq/rrep drive route discovery (see Routing and Mesh). Any sendData() call with topic < max_reserved is rejected — application code must use topics values instead.
enum topics {
status = 0x10,
cpm = 0x11,
sensor = 0x13,
alert = 0x14,
health = 0x15,
dcmd = 0x16,
encrypted_cmd = 0x1B,
sealed_uplink = 0x1C,
identity_announce = 0x1D,
encrypted_data = 0x1E,
group_broadcast = 0x1F,
gps = 0xEA,
mq7 = 0xEF,
gp2y = 0xFA,
bmp280 = 0xFB,
dht11 = 0xFC,
pir = 0xFD,
bmp180 = 0xFE,
max_topics = 0xFF
};The five encryption-related topics (0x1B–0x1F) are documented in detail in Security and Encryption. In every case, the leading application topic byte inside the data section is sent in the clear (but bound into the AEAD's additional authenticated data), so relays and observers can distinguish which encryption mode was used without being able to decrypt the payload or see what it actually contains.
src/payloads/duck_payloads.proto defines the structured payloads carried inside sensor/gps/alert/health/status topics; src/payloads/DuckPayloads.h provides matching encode/decode helpers built on nanopb.
| Message | Topic | Purpose |
|---|---|---|
GpsReading |
gps |
Fix status, source (device/phone), lat/lng (as *_e7 fixed-point), altitude, speed, heading, satellite count, battery % |
SosAlert |
alert |
Origin (device/phone), optional GPS fix, battery % |
HealthStatus |
health |
Counter, free memory |
MTalk |
(custom, MamaDuck-to-MamaDuck chat) | Kind (message/ack), message ID, text |
StatusMsg / StatusReport
|
status |
Wraps either an SosAlert or a StatusMsg (phone/device-composed text) in one envelope |
OpText |
(custom, operator/mesh text topics) | Free text |
Each encode function (encodeGps, encodeSos, encodeHealth, encodeMTalk, encodeStatusReportSos, encodeStatusReportMsg, encodeOpText) prepends a one-byte format marker (kLegacyText = 0x00 or kProtobuf = 0x01) so a receiver can tell whether a payload is the newer protobuf encoding or the legacy plain-text format, via isProtobuf().
Payloads are always protobuf-encoded before any encryption is applied (see Security and Encryption) — encryption treats the already-serialized bytes as one opaque blob, never the other way around.