verify: tshark HSMS dissector validation (independent third codec)

Wireshark's built-in HSMS dissector — written by network-protocol
authors who don't know us, didn't talk to us, and don't share
implementation details with secsgem-py — is a third independent codec
for our framing.  If they parse our pcap without warnings, our HSMS
framing is wire-correct independently of both our internal tests and
the secsgem-py interop path.

interop/tshark_validate.sh:
- Boots secs_server on 127.0.0.1:5099 (away from the demo port)
- Captures the loopback wire traffic with tcpdump
- Runs secs_client through ~24 transactions plus Separate.req +
  TCP FIN
- Parses the pcap with tshark -V using the HSMS dissector
- Asserts: no "Malformed Packet", no "Dissector bug", at least one
  HSMS frame, expected tokens present (Select.req/rsp, Separate.req,
  Data message), reports histogram (count by control type + distinct
  S/F pairs)

Result against the demo: 69 HSMS frames dissected, 49 distinct
S/F pairs (S01F01..S16F28), all clean.

Dockerfile gains tshark + tcpdump.  .gitea/workflows/ci.yml gains a
`tshark-dissector` job that runs this validator as part of every
push to main.  README proof table grows to 6 commands.

VERIFICATION.md §1a documents a follow-up: round-trip the KAT
fixtures through secsgem-py to corroborate that the format codes
we used match an independent implementation.  Strengthens the KAT
proof from "internally consistent" to "confirmed by a second
implementer who read the spec without talking to us."

Plan: VERIFICATION.md §2.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
2026-06-09 16:02:38 +02:00
parent a79973ed4c
commit 5baf3f4dc7
5 changed files with 207 additions and 0 deletions
+31
View File
@@ -86,6 +86,37 @@ the proof).
prove higher-level message structure (S1F3 body has these fields in
this order) — that's covered by `test_messages.cpp`.
**Honest disclosure about authority.** SEMI does NOT publish official
test vectors for E5 (unlike NIST, which ships `.rsp` files for every
crypto standard). The hex bytes in `test_e5_kat.cpp` are constructed
by us from the encoding rules described in the spec. They prove our
encoder is internally consistent with *our reading* of the rules — if
we somehow got a format code wrong, the KAT would happily match our
buggy codec. The mitigation is the secsgem-py interop and the
secs4j cross-validation in §3: those use independent decoders, so
disagreement on a format code surfaces there. KAT + interop combined
is a strong proof; KAT alone is a regression test.
### 1a. KAT corroboration via secsgem-py
To close the "we might have gotten the format codes wrong" loophole,
a follow-up step is to round-trip every KAT fixture through
secsgem-py's decoder and assert it returns the same value. Concrete
plan:
1. Export the KAT fixtures to a JSON file
(`tests/data/e5_kat.json`) listing each `(name, canonical_hex,
sml_repr)`.
2. Add `interop/kat_corroborate.py` that reads the JSON, feeds each
canonical hex to `secsgem.secs.functions.SecsStreamFunction`'s
decoder, and asserts the parsed structure matches the `sml_repr`.
3. Wire into CI as a separate job after the C++ tests pass.
Effort: ~2 hours. Lifts the KATs from "our format codes are
internally consistent" to "our format codes are confirmed by an
independent Python implementation that read the spec without
talking to us."
---
## 2. tshark / Wireshark HSMS dissector