Skip to content

Commit 9fb81d6

Browse files
DavidCozensclaude
andcommitted
feat: raise the message cap to fit the grown record
Three SD-ELEMENTs put the record at 245 bytes, but sequenceId and sysUpTime are both 32-bit counters: at full width the same record is 261 bytes, past the 256-byte cap and into truncation. The cap doubles to 512. Flash +11,980 B (+8 on the previous stage) RAM +9,440 B (+2,304) Log stack +704 B (+256) Service +992 B (+256) The cap is the largest single demand the formatter makes of whichever task calls it, so both stacks rise by exactly the difference — 568 to 824 on the log task, 788 to 1,044 on the service task. Both seams were sized at 2 KiB when the send moved, so they absorb it and no RAM moves with them. The RAM that does move accounts for itself exactly. The ring is eight records at the cap plus a two-byte length prefix each, so it grows 2,048. The store keeps one record buffer of cap plus integrity trailer plus framing, so it grows 256. That is the whole 2,304. The store is otherwise unaffected. SOLIDSYSLOG_FILE_DEFAULT_BLOCK_SIZE must hold one worst-case record — cap plus integrity trailer plus five framing bytes, 549 here — and at 8192 it has room to spare. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
1 parent 57262b5 commit 9fb81d6

5 files changed

Lines changed: 46 additions & 31 deletions

File tree

README.md

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,16 +10,18 @@ It builds on a baseline that simulates the sort of device you might be adding th
1010
measures itself: see [docs/baseline.md](docs/baseline.md) for what the baseline is, how the
1111
figures are made, and how to run it.
1212

13-
## This stage — Origin
13+
## This stage — Larger cap
1414

15-
The record carries an `origin` SD-ELEMENT naming the software, its version and the vendor's IANA
16-
enterprise number, so it identifies its sender instead of leaving the collector to infer that from
17-
the source address — which matters once the store replays records hours after the event. The `ip`
18-
PARAM is left out: the address the collector sees is still the one that reached it.
15+
The message cap doubles to 512 bytes. Three SD-ELEMENTs had already taken a short record close to
16+
the old ceiling, and the two counters it carries are 32-bit — at full width the same record would
17+
cross it and start truncating.
18+
19+
The cost is almost all RAM, because the cap sizes three things at once: the ring, the store's
20+
record buffer, and the deepest single demand the formatter makes of whichever task calls it.
1921

2022
<!-- STAGE-COST:START (generated by scripts/gen-cost-table.py — do not edit by hand) -->
2123

22-
**Cost above baseline: Flash +11,972 B, RAM +7,136 B.**
24+
**Cost above baseline: Flash +11,980 B, RAM +9,440 B.**
2325

2426
<!-- STAGE-COST:END -->
2527

@@ -45,6 +47,7 @@ committed as [`run-report.md`](run-report.md), and rewritten by every stage.
4547
| Time quality | a timestamp the collector knows how far to trust, and an uptime that tells a reboot from a counter wrap | +7,612 | +5,880 |
4648
| File store | records that survive a failed send, spooled to disk with a checksum at rest | +11,576 | +7,092 |
4749
| Origin | the device named in the record itself, not inferred from the source address | +11,972 | +7,136 |
50+
| Larger cap | headroom for the grown record, so full-width counters cannot push it into truncation | +11,980 | +9,440 |
4851

4952
*Deltas are bytes above the baseline, which is itself Flash 350,308 B, RAM 111,192 B.*
5053

app/config/solid_syslog_tunables.h

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4,12 +4,10 @@
44
#ifndef SOLID_SYSLOG_TUNABLES_H
55
#define SOLID_SYSLOG_TUNABLES_H
66

7-
/* The longest record this device will emit. The library defaults to 2048, the
8-
* size RFC 5424 section 6.1 says a receiver should accept; over UDP, RFC 5426
9-
* section 3.2 guarantees only that 480 will be accepted. This device's records are
10-
* far shorter, so 256 stays well inside every guarantee and anything longer is
11-
* truncated rather than dropped. */
12-
#define SOLIDSYSLOG_MAX_MESSAGE_SIZE 256U
7+
/* The longest record this device will emit; anything longer is truncated rather
8+
* than dropped. Sized to this device's worst-case record, and within what RFC 5424
9+
* section 6.1 asks a receiver to accept. */
10+
#define SOLIDSYSLOG_MAX_MESSAGE_SIZE 512U
1311

1412
/* One sender, so one destination address. The default of 3 suits a device
1513
* running UDP, plain TCP and TLS at once. */

measurements/cap-rise.csv

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
# cap-rise figures (bytes) — captured by scripts/run.sh (CAPTURE=1).
2+
# The device reads measurements/Baseline.csv as its frozen baseline and reports current-minus-Baseline.
3+
flash_text,361648
4+
flash_data,640
5+
static_bss,119992
6+
heap_used,4440
7+
mbedtls_peak,21332
8+
mbedtls_free,11436
9+
lwip_mem_free,7576
10+
lwip_pbufs_free,14
11+
stack_log,824
12+
stack_service,1044
13+
stack_harness,2848

measurements/stages.tsv

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,3 +22,4 @@ tcp TCP records the network retransmits instead of dropping, and a send that fai
2222
time-quality Time quality a timestamp the collector knows how far to trust, and an uptime that tells a reboot from a counter wrap
2323
file-store File store records that survive a failed send, spooled to disk with a checksum at rest
2424
origin Origin the device named in the record itself, not inferred from the source address
25+
cap-rise Larger cap headroom for the grown record, so full-width counters cannot push it into truncation

run-report.md

Lines changed: 19 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# solid-syslog-example — run (origin)
1+
# solid-syslog-example — run (cap-rise)
22

33
## Device (self-measured)
44

@@ -10,16 +10,16 @@
1010
[device] first record logged: yes
1111
[report] --- SolidSyslog cost above baseline (simulated existing application) ---
1212
[report] key,current,baseline,used_above_baseline
13-
[report] flash_text,361640,349992,11648
13+
[report] flash_text,361648,349992,11656
1414
[report] flash_data,640,316,324
15-
[report] static_bss,117688,110876,6812
15+
[report] static_bss,119992,110876,9116
1616
[report] heap_used,4440,4440,0
17-
[report] mbedtls_peak,21336,21332,4
18-
[report] mbedtls_free,11432,11436,-4
17+
[report] mbedtls_peak,21332,21332,0
18+
[report] mbedtls_free,11436,11436,0
1919
[report] lwip_mem_free,7576,7576,0
20-
[report] lwip_pbufs_free,13,14,-1
21-
[report] stack_log,568,120,448
22-
[report] stack_service,788,52,736
20+
[report] lwip_pbufs_free,14,14,0
21+
[report] stack_log,824,120,704
22+
[report] stack_service,1044,52,992
2323
[report] stack_harness,2848,2840,8
2424
[report] --- end ---
2525
[device] ready
@@ -29,7 +29,7 @@
2929

3030
```text
3131
text data bss dec hex filename
32-
361632 648 117688 479968 752e0 /w/build/baseline-cross/baseline.elf
32+
361640 648 119992 482280 75be8 /w/build/baseline-cross/baseline.elf
3333
```
3434

3535
## Listeners (proved before the device ran)
@@ -47,23 +47,23 @@
4747
## Collector (syslog-ng) received
4848

4949
```text
50-
wire <134>1 2026-07-29T08:21:38.360000Z 10.0.2.15 solid-syslog-example - BOOT [meta sequenceId="1" sysUpTime="236"][timeQuality tzKnown="1" isSynced="0"][origin software="solid-syslog-example" swVersion="0.1.0" enterpriseId="32473"] device started
51-
parsed PRIORITY=134 TIMESTAMP=2026-07-29T08:21:38+00:00 HOSTNAME=10.0.2.15 APP_NAME=solid-syslog-example PROCID= MSGID=BOOT STRUCTURED_DATA=[meta sequenceId="1" sysUpTime="236"][timeQuality tzKnown="1" isSynced="0"][origin software="solid-syslog-example" swVersion="0.1.0" enterpriseId="32473"] MSG=device started
50+
wire <134>1 2026-07-29T08:25:48.280000Z 10.0.2.15 solid-syslog-example - BOOT [meta sequenceId="1" sysUpTime="228"][timeQuality tzKnown="1" isSynced="0"][origin software="solid-syslog-example" swVersion="0.1.0" enterpriseId="32473"] device started
51+
parsed PRIORITY=134 TIMESTAMP=2026-07-29T08:25:48+00:00 HOSTNAME=10.0.2.15 APP_NAME=solid-syslog-example PROCID= MSGID=BOOT STRUCTURED_DATA=[meta sequenceId="1" sysUpTime="228"][timeQuality tzKnown="1" isSynced="0"][origin software="solid-syslog-example" swVersion="0.1.0" enterpriseId="32473"] MSG=device started
5252
```
5353

54-
## Self-check (vs measurements/origin.csv)
54+
## Self-check (vs measurements/cap-rise.csv)
5555

5656
```text
57-
OK flash_text: 361640 (expected 361640, Δ0)
57+
OK flash_text: 361648 (expected 361648, Δ0)
5858
OK flash_data: 640 (expected 640, Δ0)
59-
OK static_bss: 117688 (expected 117688, Δ0)
59+
OK static_bss: 119992 (expected 119992, Δ0)
6060
OK heap_used: 4440 (expected 4440, Δ0)
61-
OK mbedtls_peak: 21336 (expected 21336, Δ0)
62-
OK mbedtls_free: 11432 (expected 11432, Δ0)
61+
OK mbedtls_peak: 21332 (expected 21332, Δ0)
62+
OK mbedtls_free: 11436 (expected 11436, Δ0)
6363
OK lwip_mem_free: 7576 (expected 7576, Δ0)
64-
OK lwip_pbufs_free: 13 (expected 13, Δ0)
65-
OK stack_log: 568 (expected 568, Δ0)
66-
OK stack_service: 788 (expected 788, Δ0)
64+
OK lwip_pbufs_free: 14 (expected 14, Δ0)
65+
OK stack_log: 824 (expected 824, Δ0)
66+
OK stack_service: 1044 (expected 1044, Δ0)
6767
OK stack_harness: 2848 (expected 2848, Δ0)
6868
```
6969

0 commit comments

Comments
 (0)