Files
fips/src/proto/lookup/tests/util.rs
T
Johnathan Corgan e3e03f6a5d proto: rename the mesh discovery subsystem module from discovery to lookup
Rename src/proto/discovery to src/proto/lookup and bring the module's naming
onto the lookup stem, matching its concept: a mesh lookup of a node's
coordinates from its pubkey, sent into the mesh as a bloom-filter-guided
multicast request that returns a unicast response with the coordinates.

- the module directory and its declaration (proto::discovery -> proto::lookup)
- exported types: DiscoveryAction -> LookupAction, DiscoveryBackoff ->
  LookupBackoff, DiscoveryForwardRateLimiter -> LookupForwardRateLimiter,
  MAX_RECENT_DISCOVERY_REQUESTS -> MAX_RECENT_LOOKUP_REQUESTS, and the Discovery
  state struct -> Lookup
- internal terminology: doc comments, the "overlay-lookup" phrasing, the
  empty_discovery/suppressing_discovery test helpers, and the disc
  parameter/variable all take the lookup names
- the already-lookup-named wire types (LookupRequest/LookupResponse) are unchanged

Behavior-neutral: no wire bytes or decision logic change. Two references are
intentionally kept as "discovery": the still-named node::handlers::discovery
shell module and the node.discovery.* config keys, which belong to the broader
disambiguation of the shell, config, and metric surfaces still to come.
2026-07-08 21:54:24 +00:00

99 lines
3.3 KiB
Rust

//! Shared test helpers for the lookup subsystem unit tests.
use sha2::Digest;
use crate::proto::lookup::{
Lookup, LookupAction, LookupBackoff, LookupForwardRateLimiter, LookupRequest, LookupResponse,
RoutingView,
};
use crate::testutil::make_node_addr;
use crate::{NodeAddr, TreeCoordinate};
/// Mock routing view: each entry is `(addr, is_tree, may_reach)`.
pub(super) struct MockRoutingView {
pub(super) peers: Vec<(NodeAddr, bool, bool)>,
}
impl RoutingView for MockRoutingView {
fn is_tree_peer(&self, addr: &NodeAddr) -> bool {
self.peers
.iter()
.find(|(a, _, _)| a == addr)
.map(|(_, is_tree, _)| *is_tree)
.unwrap_or(false)
}
fn peers_reaching(&self, _target: &NodeAddr) -> Vec<NodeAddr> {
self.peers
.iter()
.filter(|(_, _, may_reach)| *may_reach)
.map(|(a, _, _)| *a)
.collect()
}
}
pub(super) fn make_request(ttl: u8) -> LookupRequest {
let target = make_node_addr(0xAA);
let origin = make_node_addr(0xBB);
let origin_coords = TreeCoordinate::root(origin);
LookupRequest::new(1, target, origin, origin_coords, ttl, 0)
}
/// Build a request with an explicit request_id and target.
pub(super) fn make_request_id(request_id: u64, target: NodeAddr, ttl: u8) -> LookupRequest {
let origin = make_node_addr(0xBB);
let origin_coords = TreeCoordinate::root(origin);
LookupRequest::new(request_id, target, origin, origin_coords, ttl, 0)
}
pub(super) fn make_coords(ids: &[u8]) -> TreeCoordinate {
TreeCoordinate::from_addrs(ids.iter().map(|&v| make_node_addr(v)).collect()).unwrap()
}
pub(super) fn action_peers(actions: &[LookupAction]) -> Vec<NodeAddr> {
actions
.iter()
.map(|action| match action {
LookupAction::SendLink { peer, .. } => *peer,
_ => panic!("expected SendLink, got a different action variant"),
})
.collect()
}
pub(super) fn empty_lookup() -> Lookup {
Lookup::new(
LookupBackoff::default(),
LookupForwardRateLimiter::default(),
)
}
/// A Lookup whose backoff is armed (non-zero base/cap) so that a single
/// recorded failure suppresses the target — the default backoff is inert.
pub(super) fn suppressing_lookup() -> Lookup {
Lookup::new(
LookupBackoff::with_params(30, 300),
LookupForwardRateLimiter::default(),
)
}
/// Build a `LookupResponse` carrying a valid schnorr proof over its own
/// `proof_bytes`, factoring out the secp/sha256/sign_schnorr setup shared by
/// the wire response roundtrip tests. `path_mtu` is the default `u16::MAX`.
pub(super) fn signed_response(
request_id: u64,
target: &NodeAddr,
coords: &TreeCoordinate,
) -> LookupResponse {
use secp256k1::Secp256k1;
let secp = Secp256k1::new();
let mut secret_bytes = [0u8; 32];
rand::Rng::fill_bytes(&mut rand::rng(), &mut secret_bytes);
let secret_key = secp256k1::SecretKey::from_slice(&secret_bytes)
.expect("32 random bytes is a valid secret key");
let keypair = secp256k1::Keypair::from_secret_key(&secp, &secret_key);
let proof_data = LookupResponse::proof_bytes(request_id, target, coords);
let digest: [u8; 32] = sha2::Sha256::digest(&proof_data).into();
let sig = secp.sign_schnorr(&digest, &keypair);
LookupResponse::new(request_id, *target, coords.clone(), sig)
}