Problem
_process_datagram_at_time short-circuits processing only when the incoming data equals self.data — a single-slot remembered "last packet." An attacker alternating between two byte-distinct payloads (A, B, A, B, …) bypasses the guard entirely on every packet, even when the actual semantic content is the same query. Combined with finding #1, this means an attacker who alternates just two TC-flagged payloads is also defeating duplicate suppression at the receive layer, and every packet flows through DNSIncoming(...) parse + the deferred-queue path.
Why This Matters
This converts what should be a per-source rate-limiter into a one-bit XOR puzzle. The CPU cost of parsing each packet (DNSIncoming._initial_parse, name decompression, NSEC bitmap decode, etc.) plus the O(N) deferred-queue dedup scan from finding #1 turns into a sustainable CPU/memory drain by one malicious LAN host.
Suggested Fix
Replace the single-slot self.data check with a small bounded recency window (e.g. a collections.deque of N most-recent packet digests, or a small LRU keyed on (addr, hash(data))), so alternating-payload attacks no longer slip through. Keep the window small (≤16) so legitimate burst traffic still passes.
Details
|
|
| Severity |
🟡 Medium |
| Category |
dos |
| Location |
src/zeroconf/_listener.py:113-129 |
| Effort |
⚡ Quick fix |
🤖 Created by Kōan from audit session
Problem
_process_datagram_at_timeshort-circuits processing only when the incomingdataequalsself.data— a single-slot remembered "last packet." An attacker alternating between two byte-distinct payloads (A, B, A, B, …) bypasses the guard entirely on every packet, even when the actual semantic content is the same query. Combined with finding #1, this means an attacker who alternates just two TC-flagged payloads is also defeating duplicate suppression at the receive layer, and every packet flows throughDNSIncoming(...)parse + the deferred-queue path.Why This Matters
This converts what should be a per-source rate-limiter into a one-bit XOR puzzle. The CPU cost of parsing each packet (
DNSIncoming._initial_parse, name decompression, NSEC bitmap decode, etc.) plus the O(N) deferred-queue dedup scan from finding #1 turns into a sustainable CPU/memory drain by one malicious LAN host.Suggested Fix
Replace the single-slot
self.datacheck with a small bounded recency window (e.g. acollections.dequeof N most-recent packet digests, or a small LRU keyed on(addr, hash(data))), so alternating-payload attacks no longer slip through. Keep the window small (≤16) so legitimate burst traffic still passes.Details
src/zeroconf/_listener.py:113-129🤖 Created by Kōan from audit session