import type { PairedDevice } from "./sync-types"; export const MESH_WAITER_RETRY_DELAY_MS = 2_000; export const MESH_WAITER_MAX_RETRY_DELAY_MS = 30_000; export function isRouteCapableMeshPeer(device: PairedDevice): boolean { // PB-26-006: fail closed on an unknown/absent trustSource — sibling trust // gates reject it, so routing must not treat it as direct/vouched. // // PB-26-213: the rendezvous secret is intentionally NOT part of this check. // The public registry carries no reusable secrets; the secret resolves from // the encrypted pair-secret record (or trusted session) at dial time, and // peers without one are skipped there. const trusted = device.trustSource === "direct" || device.trustSource === "vouched"; return ( trusted && (device.deviceType === "extension" || device.deviceType === "android" || device.deviceType === "ios") && typeof device.longTermPublicKeyHex === "string" && /^[0-9a-f]{64}$/.test(device.longTermPublicKeyHex) ); } /** Lower public key dials; higher public key waits. */ export function weDialMeshPeer( ourLongTermPublicKeyHex: string, peerLongTermPublicKeyHex: string, ): boolean { if ( !/^[0-9a-f]{64}$/.test(ourLongTermPublicKeyHex) || !/^[0-9a-f]{64}$/.test(peerLongTermPublicKeyHex) || ourLongTermPublicKeyHex === peerLongTermPublicKeyHex ) { return false; } return ourLongTermPublicKeyHex < peerLongTermPublicKeyHex; } export function selectDialTargets( devices: PairedDevice[], ourLongTermPublicKeyHex: string, ): PairedDevice[] { return devices.filter( (device) => isRouteCapableMeshPeer(device) && weDialMeshPeer( ourLongTermPublicKeyHex, device.longTermPublicKeyHex!, ), ); } export function nextMeshWaiterRetryDelay( current: number, succeeded: boolean, ): number { return succeeded ? MESH_WAITER_RETRY_DELAY_MS : Math.min(current * 2, MESH_WAITER_MAX_RETRY_DELAY_MS); }