Repository navigation
test(protocols): edge-case round trips for every layer family (#1202) - #1454
Conversation
53b9d24 to
d0bbf31
Compare
|
Coverage: 89.56% (unit tier, Python 3.14,
Per-file detail: the |
|
Verdict: NEEDS CHANGES at Blocking: Verified:
Nits:
|
Four unit-tier modules and a shared harness build minimum and maximum lengths, reserved bits, zero-length values, padding variants and unassigned codes for link, internet, transport and application protocols. Each packet must parse back to itself and rebuild from its info; one-short and half-length cuts must be refused in-library or round-trip too; make() must be stable through a re-parse. KNOWN_FAILURES groups what still fails by root cause, pinned by status and failure fragment, and is asserted in both directions: #1455 (L2TPv2/OSPF length trailer), #1456 (RPL compression under IPv6), #1457 (truncated RPL address vectors), #1458 (zero-filled short reads), #1451 (its IPv6 extension-header case) and #1459 (HIP fixed bits rejected).
d0bbf31 to
9106d4c
Compare
|
Verdict: GOOD TO GO at
Merge order: #1460 (#1455) and #1462 (#1459) will each make their gap entry here stale. Whichever lands second has to delete that entry. |
…fixed #1454 merged before the three fixes, so its stale-entry check now fails on main: #1455 (L2TPv2/OSPF trailer), #1456/#1457 (RPL) and #1459 (HIP fixed bits) all come back OK. Drop those entries. The HIP fixed-bit cuts and two RPL in-IPv6 cut55 cases now parse but zero-fill, so they move under the #1451/#1458 short-read gaps. All four edge modules pass.
…ured (#1458, #1451) When the data ended inside a field, Schema.unpack read the missing octets as zeros and recorded nothing, so from_data(info) wrote that field, and every field after it, at full width: Ethernet(bytes(12) + b'\x08') rebuilt as 14 octets, and a Routing header with 23 of 24 octets as 24. - Schema.unpack records the first field it reads short, and how many octets it got, as __short_read__; Schema.pack writes back only those, and Schema.to_dict/from_dict carry the record like __remainder__. - keep_short_read/replay_short_read carry the record through info: the Link, Internet, Transport and Application bases add it after a parse and cut a from_data rebuild back to it. It is an ordinary info key, so Info.to_dict carries it and from_data(info.to_dict()) replays it too; only a truncated header has it. - The #1454 edge tables drop the #1451/#1458 rows this closes; five SCTP last-chunk pad rows remain, under #1455. Decoded values are unchanged: a truncated number still reads as zero-filled.
…ured (#1458, #1451) When the data ended inside a field, Schema.unpack read the missing octets as zeros and recorded nothing, so from_data(info) wrote that field, and every field after it, at full width: Ethernet(bytes(12) + b'\x08') rebuilt as 14 octets, and a Routing header with 23 of 24 octets as 24. - Schema.unpack records the first field it reads short, and how many octets it got, as __short_read__; Schema.pack writes back only those, and Schema.to_dict/from_dict carry the record like __remainder__. - keep_short_read/replay_short_read carry the record through info: the Link, Internet, Transport and Application bases add it after a parse and cut a from_data rebuild back to it. It is an ordinary info key, so Info.to_dict carries it and from_data(info.to_dict()) replays it too; only a truncated header has it. - The #1454 edge tables drop the #1451/#1458 rows this closes, and the harness its two now-unused defect strings; five SCTP last-chunk pad rows remain, under #1474. Decoded values are unchanged: a truncated number still reads as zero-filled.
Searched for similar pull requests
Followed the coding style — not run as
make; pylint (Makefile flags), isort and mypy on the five new files are clean except pylint duplicate-code on the four-line class bodiesmake testpasses, and a test case covers the change — the four new modules (pytest), bothprotocolsordering legs,tests/project,test_tier_guard,test_docstring_contractChangelog entry — N/A — centralised in docs(changelog): shared 1.5.0 changelog — long-lived, merges last (#610, #616, #617, #618, #620) #657
test— tests onlyRefs #1202: the protocol edge-case slice. Unit tier, no fixture reads;
tests/protocols/_edge_roundtrip.pyis the shared harness.link/test_link_edge_roundtrip_unit.py(Ethernet, 802.1Q/ad, ARP/RARP, L2TPv2, OSPF)internet/test_internet_edge_roundtrip_unit.py(IPv4, IPX, IPv6 + every ext header, HIP, MH, AH, ESP)transport/test_transport_edge_roundtrip_unit.py(TCP, UDP, SCTP)application/test_application_edge_roundtrip_unit.py(FTP, HTTP/1, HTTP/2)Each case must parse to itself and rebuild from
info. Its one-short and half-length cuts must either be refused with an in-library error or round-trip.make()must be stable through a re-parse.KNOWN_FAILURESis grouped by root cause and checked in both directions: #1455 (L2TPv2/OSPF drop octets past their length), #1456 (RPL compression lost inside IPv6), #1457 (truncated RPL address list), #1458 (a header cut inside a fixed-width field is zero-filled, every family), #1451 (its IPv6 extension-header case) and #1459 (HIP rejects packets whose fixed bits it must ignore). Each entry is pinned by status and a failure fragment. The #1443 and #1446 cases pass onmainand are ordinary cases.