fix(mqtt): size the status buffer for real field maxima
The worst-case test added with the connection-health fields did not model production maxima -- it used a 28-byte model and a 24-byte firmware string, while MQTTBridge permits _origin[32], _device_id[65], _board_model[64], _firmware_version[64] and derives a 63-byte client version. isValidName() rejects [ ] / \ : , ? * but permits '"', so a 31-character node name of quotes is legal and every quote escapes to two bytes. Measured at those real maxima: without connection-health fields 762 bytes with connection-health fields 851 bytes buffer 768 bytes So the 768-byte buffer already had only six bytes of headroom before this work, and the four new fields overflow it. Overflow is silent: serializeComplete() returns 0 and clears the buffer, and the bridge publishes only a positive length, so a device would simply stop publishing status with no error anywhere -- the same blindness the connection-health fields exist to remove. Raises STATUS_JSON_BUFFER_SIZE to 1024 and corrects the test to use the actual maxima. Status serializes into the shared 2048-byte publish scratch buffer, so this costs no extra RAM; only the PSRAM-allocation-failed stack fallback grows by 256 bytes. A static_assert keeps the status ceiling within the shared buffer. Found by adversarial review of the preceding commit.
This commit is contained in:
1 parent
f7ed2f176d
commit
383339eccc
2 files changed
+34
-15
No files matched your search
@@ -366,9 +366,15 @@ private:
|
||||
// internal heap. On non-PSRAM: inline in the class object so the allocation doesn't
|
||||
// interleave with large TLS buffers at startup.
|
||||
static const size_t PUBLISH_JSON_BUFFER_SIZE = 2048;
|
||||
// Status keeps its own smaller ceiling: raising it would change which oversized
|
||||
// status documents get published instead of dropped.
|
||||
static const size_t STATUS_JSON_BUFFER_SIZE = 768;
|
||||
// Status keeps its own smaller ceiling: raising it changes which oversized status
|
||||
// documents get published instead of dropped. 768 left only 6 bytes spare at the real
|
||||
// field maxima (_origin[32] of quotes, which isValidName permits and JSON doubles, plus
|
||||
// _device_id[65], _board_model[64], _firmware_version[64] and a 63-byte client version):
|
||||
// measured 762/768 before the connection-health fields existed. Overflow is silent —
|
||||
// serializeComplete() returns 0 and the bridge publishes only len>0, so status stops
|
||||
// entirely. Raised to 1024, which costs no extra RAM here because status serializes into
|
||||
// the shared scratch buffer. See the worst-case test in test_mqtt_payload_builder.
|
||||
static const size_t STATUS_JSON_BUFFER_SIZE = 1024;
|
||||
static_assert(STATUS_JSON_BUFFER_SIZE <= PUBLISH_JSON_BUFFER_SIZE,
|
||||
"status payloads serialize into the shared publish buffer");
|
||||
#if defined(BOARD_HAS_PSRAM)
|
||||
|
||||
Reference in new issue
Block a user