heap_trace dumps — 2026-05-04, Rev A¶
Two passive heap_trace windows captured from the live Rev A device
(192.168.23.125, dataSource=1 / mempool+Kraken) via the
/api/diag/heap_trace/{start,stop} endpoints.
Firmware HEAD: 3a3efd9 (post-format-fixup, after the cert-bundle
mitigation in fe8d1d0 was already in place — so these dumps show the
residual leak that PSRAM-routing only displaces, not the original
internal-heap drift).
| File | Window | Records | cap | Notes |
|---|---|---|---|---|
window_90s.json |
90 s | 26 | 256 | Initial capture, kernel of the steady-state |
window_600s.json |
600 s | 107 | 256 | Long capture, ~4× more records |
Schema¶
{
"count": <number of leak records>,
"capacity": <heap_trace buffer slots, currently 256>,
"leaks": [
{
"sz": <bytes>,
"addr": "<heap address as hex string>",
"cc": <ccount cycle counter at alloc time>,
"pcs": ["<frame0>", "<frame1>", "<frame2>", "<frame3>"]
},
…
]
}
pcs[] is CONFIG_HEAP_TRACING_STACK_DEPTH=4 deep. Symbol resolution
for every distinct PC across both windows is in symbols.txt.
Cert-bundle signature (the upstream issue)¶
The dominant leak chain across both windows resolves to:
heap_caps_malloc_default heap_caps.c:120
calloc esp_libc/src/heap.c:46
mbedtls_calloc platform.c:50
esp_crt_copy_asn1 esp_crt_bundle.c:440 ← X.509 fragment alloc
esp_crt_copy_asn1 esp_crt_bundle.c:448 ← X.509 fragment alloc
esp_crt_ca_cb_callback esp_crt_bundle.c:489
x509_crt_verify_chain x509_crt.c:2578
Per-handshake fingerprint (size histogram of dominant chain in 90 s
window): 2 / 3 / 12 / 16 / 24 / 32 / 45 / 81 / 168 B. Same fragments
on every TLS reconnect.
Filed upstream at https://github.com/espressif/esp-idf/issues/18550.
Other PC chains visible in the dumps¶
The 600 s window also surfaces leaks from esp_http_client_init,
esp_http_client_set_url, http_header_*, mbedtls_ssl_set_hostname,
esp_transport_*, and pbuf_alloc. Those are transient allocations
that heap_trace correctly snapshots as live at trace-stop time — they
get freed when the corresponding HTTP/TCP session closes. They are
not the cert-bundle leak. The cert-bundle leak is distinguished by
the esp_crt_* frames in pcs[] and the per-handshake repetition of
the same byte sizes.
Reproducing¶
curl -X POST http://<rev-a-ip>/api/diag/heap_trace/start
sleep 600
curl -X POST http://<rev-a-ip>/api/diag/heap_trace/stop > window_600s.json
Endpoints are guarded by #if CONFIG_HEAP_TRACING_STANDALONE, which
ships in the Rev A build (see build-rev-a/sdkconfig). Resolve PCs
with xtensa-esp32s3-elf-addr2line -e build-rev-a/btclock_v4.elf -f -p.