1.1 Create src/swarm/ module skeleton (mod.rs, settings.rs with
SwarmSettings for overlay + role configuration), export it from the
darkfi crate, and verify make compiles with make clippy clean.
2. SubnetId derivation (D2, spec: swarm-overlay)
2.1 Implement SubnetDescriptor (app_name, magic_bytes,
version_constraint, optional secret) with canonical serialization and
BLAKE3 SubnetId derivation; verify unit tests pass: identical
descriptors yield equal ids, any field divergence yields different ids,
secret-bearing ids are the same length and format as public ones.
2.2 Add a pinned-descriptor constructor from an existing
{app_name, magic_bytes, version} network triple; verify a golden-value
unit test fixes the darkirc triple's id so all deployments agree.
3.1 Plumb a features list from net::Settings into the
VersionMessage handshake (currently hardcoded to vec![] in
protocol_version.rs); verify a version-exchange test round-trips the
feature and that the diff contains no other src/net changes (flag this
diff explicitly in the change notes for review).
3.2 Verify existing net behavior is unchanged:
cargo test -p darkfi --release --all-features net passes and
make clippy is clean.
4. Overlay wire messages (D4)
4.1 Define SubnetAd, GetSubnets, Subnets, GetSubnetAddrs,
SubnetAddrs via impl_p2p_message! with MAX_BYTES estimates and
metering configurations in the existing style; verify serialization
roundtrip and size-estimate unit tests pass.
5. Advertisement store (D3, spec: swarm-overlay)
5.1 Implement the ad store: per-subnet and total entry caps, TTL
expiry, shareable-scheme filtering, disk persistence, and no recording of
querier data; verify unit tests pass for TTL expiry, cap enforcement,
restart persistence, and non-shareable-scheme rejection.
5.2 Implement the ad refinery task: rate-limited liveness checks of
advertised addresses with drop/downgrade on failure; verify an integration
test shows a dead advertised address is dropped before TTL expiry and
checks are not issued in a simultaneous burst.
6. ProtocolSwarm: gossip and queries (D4, D8)
6.1 Implement ProtocolSwarm gossip handling: validate SubnetAd
(one subnet, shareable schemes), insert into the ad store, relay
unmodified with no provenance or hop fields; register via
ProtocolRegistry on the overlay's outbound and inbound sessions; verify
a test asserts relayed ads are unchanged and non-shareable addresses are
dropped rather than relayed.
6.2 Implement GetSubnets/GetSubnetAddrs query handling answered
from local state for every connected peer; verify a test shows a
persistent and a transient node with identical local state answer with
the same message types and semantics.
6.3 Implement the jittered ad re-gossip cadence with no
event-triggered emission; verify tests show no ad is sent on subnet
start, listener startup, or new overlay connection, and that the cadence
tick does emit.
7. Swarm lifecycle and roles (D1, D5, D6, D8)
7.1 Implement Swarm owning the overlay P2p plus the subnet
registry, with persistent and transient constructors (persistent:
swarm-store handshake feature via task 3.1, high inbound; transient:
zero inbound, minimal outbound, optional overlay hostlist cache and
nothing else on disk); verify a transient integration test writes only
the overlay hostlist cache and emits no ads.
7.2 Implement join(descriptor): overlay resolution, greylist
seeding of resolved addrs, subnet P2p spawn with SubnetId-namespaced
datastore/hostlist paths, app protocol registration before start; verify
a descriptor-only join succeeds against a local overlay seed with no
subnet seed configuration, and unknown subnets fail in bounded time.
7.3 Implement serve(): per-subnet opt-in requiring that subnet's
inbound addrs, advertising only those addrs on the 6.3 cadence; verify
tests show served-subnet ads carry only that subnet's addresses and
join-only mode never emits an ad.
7.4 Implement leave(): stop and deregister the subnet P2p with no
departure message and state retained for rejoin; verify tests assert no
overlay message is emitted on leave and rejoin resumes from the persisted
hostlist.
7.5 Verify runtime lifecycle tests pass: late subnet spawn does not
disturb running subnets or the overlay, and concurrent teardown of
several subnets terminates cleanly.
7.6 Implement transient cache-first bootstrap: the overlay hostlist
cache is persisted between sessions and dialed before configured seeds,
with cache contents limited to overlay peer addresses; verify an
integration test where a second session connects through cached peers
with all seeds unreachable, and a test asserting the cache contains no
subnet identifiers or query records.
8. Multi-node integration tests (spec scenarios)
8.1 Cold-start chain test over local transports: overlay seed →
persistent node → transient node discovers and joins a subnet with no
per-subnet seeds anywhere; verify the transient node connects into the
subnet and leaves no trace in any hostlist or ad store.
8.2 Abuse tests: an ad flood exceeds store caps and triggers
metering/ban penalties, and poisoned (unreachable) addrs are dropped by
refinement; verify both behaviors in one integration test.
8.3 Linkability structure test: one node serving two subnets through
distinct addresses emits ads that share no field linking them; verify by
structural inspection of all emitted messages in a two-subnet test.
9.1 Add the [overlay] config section with parsing, overlay-only
mode, and mixed overlay + legacy per-network operation; verify config
parsing unit tests (overlay-only, mixed, malformed) and a mixed-config
integration test where both the overlay seed and legacy nets run.
9.2 Wire the durable ad store and refinery into lilith; verify a
restart test shows persisted ads survive a stop/start cycle within TTL
bounds and no querier data is stored.
9.3 Retarget lilith's RPC: listener health, participating subnet ids,
ad store stats, with no per-querier data; verify a JSON-RPC test asserts
the reported fields and the absence of query-source information.
10. Pilot adoption, docs, gates
10.1 darkirc pilot behind a config flag: pinned descriptor via 2.2,
Swarm-based networking with static-seed fallback preserved; verify
tests exercise both the overlay path and the fallback path.
10.2 Write deployment guidance: onion-per-subnet recommendation,
shared-endpoint linkability hazard (required by the no-cross-subnet
linkability spec requirement), and transient battery-vs-mixing
recommendation to hold the overlay connection for the app session.
10.3 Full gates green: make, make clippy, make test, and
make fmt all complete without errors.
10.4 Invoke @anon-security-review on the full diff and record the
verdict on the change; a FAIL is blocking — resolve findings or escalate
before marking the change ready to apply.