From 9445480b15e3816a497dcdacd9b00c6141c82419 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Fri, 20 Mar 2026 12:30:09 -0400 Subject: [PATCH 01/19] init discovery integration --- waku/discovery/waku_kademlia.nim | 312 ++++++++++--------------------- waku/factory/node_factory.nim | 69 ++++--- 2 files changed, 130 insertions(+), 251 deletions(-) diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index 94b63a321..16feb2964 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -1,6 +1,6 @@ {.push raises: [].} -import std/[options, sequtils] +import std/[options, sequtils, sugar] import chronos, chronicles, @@ -8,111 +8,23 @@ import stew/byteutils, libp2p/[peerid, multiaddress, switch], libp2p/extended_peer_record, - libp2p/crypto/curve25519, libp2p/protocols/[kademlia, kad_disco], libp2p/protocols/kademlia_discovery/types as kad_types, - libp2p/protocols/mix/mix_protocol + libp2p/protocols/service_discovery/types import waku/waku_core, waku/node/peer_manager logScope: - topics = "waku extended kademlia discovery" + topics = "waku kademlia discovery" -const - DefaultExtendedKademliaDiscoveryInterval* = chronos.seconds(5) - ExtendedKademliaDiscoveryStartupDelay* = chronos.seconds(5) +const DefaultKademliaDiscoveryInterval* = chronos.seconds(10) -type - MixNodePoolSizeProvider* = proc(): int {.gcsafe, raises: [].} - NodeStartedProvider* = proc(): bool {.gcsafe, raises: [].} +type WakuKademlia* = ref object + protocol*: KademliaDiscovery + peerManager: PeerManager + intervalFut: Future[void] - ExtendedKademliaDiscoveryParams* = object - bootstrapNodes*: seq[(PeerId, seq[MultiAddress])] - mixPubKey*: Option[Curve25519Key] - advertiseMix*: bool = false - - WakuKademlia* = ref object - protocol*: KademliaDiscovery - peerManager: PeerManager - discoveryLoop: Future[void] - running*: bool - getMixNodePoolSize: MixNodePoolSizeProvider - isNodeStarted: NodeStartedProvider - -proc new*( - T: type WakuKademlia, - switch: Switch, - params: ExtendedKademliaDiscoveryParams, - peerManager: PeerManager, - getMixNodePoolSize: MixNodePoolSizeProvider = nil, - isNodeStarted: NodeStartedProvider = nil, -): Result[T, string] = - if params.bootstrapNodes.len == 0: - info "creating kademlia discovery as seed node (no bootstrap nodes)" - - let kademlia = KademliaDiscovery.new( - switch, - bootstrapNodes = params.bootstrapNodes, - config = KadDHTConfig.new( - validator = kad_types.ExtEntryValidator(), selector = kad_types.ExtEntrySelector() - ), - codec = ExtendedKademliaDiscoveryCodec, - ) - - try: - switch.mount(kademlia) - except CatchableError: - return err("failed to mount kademlia discovery: " & getCurrentExceptionMsg()) - - # Register services BEFORE starting kademlia so they are included in the - # initial self-signed peer record published to the DHT - if params.advertiseMix: - if params.mixPubKey.isSome(): - let alreadyAdvertising = kademlia.startAdvertising( - ServiceInfo(id: MixProtocolID, data: @(params.mixPubKey.get())) - ) - if alreadyAdvertising: - warn "mix service was already being advertised" - debug "extended kademlia advertising mix service", - keyHex = byteutils.toHex(params.mixPubKey.get()), - bootstrapNodes = params.bootstrapNodes.len - else: - warn "mix advertising enabled but no key provided" - - info "kademlia discovery created", - bootstrapNodes = params.bootstrapNodes.len, advertiseMix = params.advertiseMix - - return ok( - WakuKademlia( - protocol: kademlia, - peerManager: peerManager, - running: false, - getMixNodePoolSize: getMixNodePoolSize, - isNodeStarted: isNodeStarted, - ) - ) - -proc extractMixPubKey(service: ServiceInfo): Option[Curve25519Key] = - if service.id != MixProtocolID: - trace "service is not mix protocol", - serviceId = service.id, mixProtocolId = MixProtocolID - return none(Curve25519Key) - - if service.data.len != Curve25519KeySize: - warn "invalid mix pub key length from kademlia record", - expected = Curve25519KeySize, - actual = service.data.len, - dataHex = byteutils.toHex(service.data) - return none(Curve25519Key) - - debug "found mix protocol service", - dataLen = service.data.len, expectedLen = Curve25519KeySize - - let key = intoCurve25519Key(service.data) - debug "successfully extracted mix pub key", keyHex = byteutils.toHex(key) - return some(key) - -proc remotePeerInfoFrom(record: ExtendedPeerRecord): Option[RemotePeerInfo] = +proc toRemotePeerInfo(record: ExtendedPeerRecord): Option[RemotePeerInfo] = debug "processing kademlia record", peerId = record.peerId, numAddresses = record.addresses.len, @@ -130,151 +42,119 @@ proc remotePeerInfoFrom(record: ExtendedPeerRecord): Option[RemotePeerInfo] = let protocols = record.services.mapIt(it.id) - var mixPubKey = none(Curve25519Key) - for service in record.services: - debug "checking service", - peerId = record.peerId, serviceId = service.id, dataLen = service.data.len - mixPubKey = extractMixPubKey(service) - if mixPubKey.isSome(): - debug "extracted mix public key from service", peerId = record.peerId - break - - if record.services.len > 0 and mixPubKey.isNone(): - debug "record has services but no valid mix key", - peerId = record.peerId, services = record.services.mapIt(it.id) - return none(RemotePeerInfo) return some( RemotePeerInfo.init( - record.peerId, - addrs = addrs, - protocols = protocols, - origin = PeerOrigin.Kademlia, - mixPubKey = mixPubKey, + record.peerId, addrs = addrs, protocols = protocols, origin = PeerOrigin.Kademlia ) ) -proc lookupMixPeers*( - wk: WakuKademlia -): Future[Result[int, string]] {.async: (raises: []).} = - ## Lookup mix peers via kademlia and add them to the peer store. - ## Returns the number of mix peers found and added. - if wk.protocol.isNil(): - return err("cannot lookup mix peers: kademlia not mounted") - - let mixService = ServiceInfo(id: MixProtocolID, data: @[]) - var records: seq[ExtendedPeerRecord] - try: - records = await wk.protocol.lookup(mixService) - except CatchableError: - return err("mix peer lookup failed: " & getCurrentExceptionMsg()) - - debug "mix peer lookup returned records", numRecords = records.len - - var added = 0 - for record in records: - let peerOpt = remotePeerInfoFrom(record) - if peerOpt.isNone(): - continue - - let peerInfo = peerOpt.get() - if peerInfo.mixPubKey.isNone(): - continue - - wk.peerManager.addPeer(peerInfo, PeerOrigin.Kademlia) - info "mix peer added via kademlia lookup", - peerId = $peerInfo.peerId, mixPubKey = byteutils.toHex(peerInfo.mixPubKey.get()) - added.inc() - - info "mix peer lookup complete", found = added - return ok(added) - proc runDiscoveryLoop( - wk: WakuKademlia, interval: Duration, minMixPeers: int -) {.async: (raises: []).} = - info "extended kademlia discovery loop started", interval = interval + wk: WakuKademlia, interval: Duration +) {.async: (raises: [CancelledError]).} = + info "kademlia discovery loop started", interval = interval - try: - while true: - # Wait for node to be started - if not wk.isNodeStarted.isNil() and not wk.isNodeStarted(): - await sleepAsync(ExtendedKademliaDiscoveryStartupDelay) + while true: + await sleepAsync(interval) + + let res = catch: + await wk.protocol.randomRecords() + let records = res.valueOr: + error "kademlia discovery lookup failed", error = res.error.msg + continue + + for record in records: + let peerInfo = toRemotePeerInfo(record).valueOr: continue - var records: seq[ExtendedPeerRecord] - try: - records = await wk.protocol.randomRecords() - except CatchableError as e: - warn "extended kademlia discovery failed", error = e.msg - await sleepAsync(interval) - continue + wk.peerManager.addPeer(peerInfo, PeerOrigin.Kademlia) - debug "received random records from kademlia", numRecords = records.len + debug "peer added via kademlia discovery", + peerId = $peerInfo.peerId, + addresses = peerInfo.addrs.mapIt($it), + protocols = peerInfo.protocols - var added = 0 - for record in records: - let peerOpt = remotePeerInfoFrom(record) - if peerOpt.isNone(): - continue + #TODO peer added metric - let peerInfo = peerOpt.get() - wk.peerManager.addPeer(peerInfo, PeerOrigin.Kademlia) - debug "peer added via extended kademlia discovery", - peerId = $peerInfo.peerId, - addresses = peerInfo.addrs.mapIt($it), - protocols = peerInfo.protocols, - hasMixPubKey = peerInfo.mixPubKey.isSome() - added.inc() +proc lookup*( + self: WakuKademlia, codec: string +): Future[seq[RemotePeerInfo]] {.async: (raises: []).} = + let serviceId = hashServiceId(codec) - if added > 0: - info "added peers from extended kademlia discovery", count = added + let catchRes = catch: + await self.protocol.lookup(serviceId) + let lookupRes = catchRes.valueOr: + error "kademlia discovery lookup failed", error = catchRes.error.msg + return - # Targeted mix peer lookup when pool is low - if minMixPeers > 0 and not wk.getMixNodePoolSize.isNil() and - wk.getMixNodePoolSize() < minMixPeers: - debug "mix node pool below threshold, performing targeted lookup", - currentPoolSize = wk.getMixNodePoolSize(), threshold = minMixPeers - let found = (await wk.lookupMixPeers()).valueOr: - warn "targeted mix peer lookup failed", error = error - 0 - if found > 0: - info "found mix peers via targeted kademlia lookup", count = found + let ads = lookupRes.valueOr: + error "kademlia discovery lookup failed", error + return - await sleepAsync(interval) - except CancelledError as e: - debug "extended kademlia discovery loop cancelled", error = e.msg - except CatchableError as e: - error "extended kademlia discovery loop failed", error = e.msg + var peerInfos = newSeqOfCap[RemotePeerInfo](ads.len) + for ad in ads: + let peerInfo = toRemotePeerInfo(ad.data).valueOr: + continue + + self.peerManager.addPeer(peerInfo, PeerOrigin.Kademlia) + + debug "peer added via kademlia discovery", + peerId = $peerInfo.peerId, + addresses = peerInfo.addrs.mapIt($it), + protocols = peerInfo.protocols + + #TODO peer added metric + + peerInfos.add(peerInfo) + + return peerInfos + +proc new*( + T: type WakuKademlia, + switch: Switch, + peerManager: PeerManager, + bootstrapNodes: seq[(PeerId, seq[MultiAddress])], + providedServices: var seq[ServiceInfo], +): T = + if bootstrapNodes.len == 0: + info "creating kademlia discovery as seed node (no bootstrap nodes)" + + let kademlia = KademliaDiscovery.new( + switch, + bootstrapNodes = bootstrapNodes, + config = KadDHTConfig.new( + validator = kad_types.ExtEntryValidator(), selector = kad_types.ExtEntrySelector() + ), + services = providedServices, + ) + + info "kademlia service discovery created", bootstrapNodes = bootstrapNodes.len + + return WakuKademlia(protocol: kademlia, peerManager: peerManager) proc start*( - wk: WakuKademlia, - interval: Duration = DefaultExtendedKademliaDiscoveryInterval, - minMixPeers: int = 0, -): Future[Result[void, string]] {.async: (raises: []).} = - if wk.running: - return err("already running") + self: WakuKademlia, interval: Duration = DefaultKademliaDiscoveryInterval +) {.async: (raises: [CancelledError]).} = + if self.protocol.started: + warn "Starting kad-disco twice" + return - try: - await wk.protocol.start() - except CatchableError as e: - return err("failed to start kademlia discovery: " & e.msg) + await self.protocol.start() - wk.discoveryLoop = wk.runDiscoveryLoop(interval, minMixPeers) + self.intervalFut = self.runDiscoveryLoop(interval) info "kademlia discovery started" - return ok() -proc stop*(wk: WakuKademlia) {.async: (raises: []).} = - if not wk.running: +proc stop*(self: WakuKademlia) {.async: (raises: []).} = + if not self.protocol.started: return info "Stopping kademlia discovery" - wk.running = false + if not self.intervalFut.isNil(): + self.intervalFut.cancelSoon() + self.intervalFut = nil - if not wk.discoveryLoop.isNil(): - await wk.discoveryLoop.cancelAndWait() - wk.discoveryLoop = nil + if not self.protocol.isNil(): + await self.protocol.stop() - if not wk.protocol.isNil(): - await wk.protocol.stop() info "Successfully stopped kademlia discovery" diff --git a/waku/factory/node_factory.nim b/waku/factory/node_factory.nim index 52b719b8f..0dc4c8f89 100644 --- a/waku/factory/node_factory.nim +++ b/waku/factory/node_factory.nim @@ -1,5 +1,5 @@ import - std/[options, sequtils], + std/[options, sequtils, sugar], chronicles, chronos, libp2p/peerid, @@ -7,7 +7,9 @@ import libp2p/protocols/connectivity/relay/relay, libp2p/nameresolving/dnsresolver, libp2p/crypto/crypto, - libp2p/crypto/curve25519 + libp2p/crypto/curve25519, + libp2p/extended_peer_record, + libp2p/protocols/mix/mix_protocol import ./internal_config, @@ -121,10 +123,11 @@ proc initNode( builder.withRateLimit(conf.rateLimit) builder.withCircuitRelay(relay) - let node = ?builder.build().mapErr( - proc(err: string): string = - "failed to create waku node instance: " & err - ) + let node = + ?builder.build().mapErr( + proc(err: string): string = + "failed to create waku node instance: " & err + ) ok(node) @@ -159,38 +162,18 @@ proc setupProtocols( error "Unrecoverable error occurred", error = msg quit(QuitFailure) + var providedServices: seq[ServiceInfo] + #mount mix if conf.mixConf.isSome(): let mixConf = conf.mixConf.get() + + let mixService = ServiceInfo(id: MixProtocolID, data: @(mixConf.mixKey)) + providedServices.add(mixService) + (await node.mountMix(conf.clusterId, mixConf.mixKey, mixConf.mixnodes)).isOkOr: return err("failed to mount waku mix protocol: " & $error) - # Setup extended kademlia discovery - if conf.kademliaDiscoveryConf.isSome(): - let mixPubKey = - if conf.mixConf.isSome(): - some(conf.mixConf.get().mixPubKey) - else: - none(Curve25519Key) - - node.wakuKademlia = WakuKademlia.new( - node.switch, - ExtendedKademliaDiscoveryParams( - bootstrapNodes: conf.kademliaDiscoveryConf.get().bootstrapNodes, - mixPubKey: mixPubKey, - advertiseMix: conf.mixConf.isSome(), - ), - node.peerManager, - getMixNodePoolSize = proc(): int {.gcsafe, raises: [].} = - if node.wakuMix.isNil(): - 0 - else: - node.getMixNodePoolSize(), - isNodeStarted = proc(): bool {.gcsafe, raises: [].} = - node.started, - ).valueOr: - return err("failed to setup kademlia discovery: " & error) - if conf.storeServiceConf.isSome(): let storeServiceConf = conf.storeServiceConf.get() @@ -399,6 +382,21 @@ proc setupProtocols( if conf.peerExchangeDiscovery: await node.mountPeerExchangeClient() + if conf.kademliaDiscoveryConf.isSome(): + let kademlia = WakuKademlia.new( + node.switch, + node.peerManager, + conf.kademliaDiscoveryConf.get().bootstrapNodes, + providedServices, + ) + + let catchRes = catch: + node.switch.mount(kademlia.protocol) + if catchRes.isErr(): + return err("failed to mount kademlia discovery: " & catchRes.error.msg) + + node.wakuKademlia = kademlia + return ok() ## Start node @@ -451,9 +449,10 @@ proc startNode*( node.peerManager.start() if not node.wakuKademlia.isNil(): - let minMixPeers = if conf.mixConf.isSome(): 4 else: 0 - (await node.wakuKademlia.start(minMixPeers = minMixPeers)).isOkOr: - return err("failed to start kademlia discovery: " & error) + let catchRes = catch: + await node.wakuKademlia.start() + if catchRes.isErr(): + return err("failed to start kademlia discovery: " & catchRes.error.msg) return ok() From f070992723ac9aad4d90b42c8ed22fcd11a0e912 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Mon, 23 Mar 2026 08:44:53 -0400 Subject: [PATCH 02/19] add service for all protos --- waku/factory/node_factory.nim | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/waku/factory/node_factory.nim b/waku/factory/node_factory.nim index 0dc4c8f89..8f4bba310 100644 --- a/waku/factory/node_factory.nim +++ b/waku/factory/node_factory.nim @@ -197,6 +197,9 @@ proc setupProtocols( except CatchableError: return err("failed to mount waku store protocol: " & getCurrentExceptionMsg()) + let storeService = ServiceInfo(id: WakuStoreCodec, data: @[]) + providedServices.add(storeService) + if storeServiceConf.storeSyncConf.isSome(): let confStoreSync = storeServiceConf.storeSyncConf.get() @@ -209,6 +212,11 @@ proc setupProtocols( ).isOkOr: return err("failed to mount waku store sync protocol: " & $error) + let reconciliationService = ServiceInfo(id: WakuReconciliationCodec, data: @[]) + let transferService = ServiceInfo(id: WakuTransferCodec, data: @[]) + providedServices.add(reconciliationService) + providedServices.add(transferService) + if conf.remoteStoreNode.isSome(): let storeNode = parsePeerInfo(conf.remoteStoreNode.get()).valueOr: return err("failed to set node waku store-sync peer: " & error) @@ -292,10 +300,16 @@ proc setupProtocols( protectedShard = shardKey.shard, publicKey = shardKey.key node.wakuRelay.addSignedShardsValidator(subscribedProtectedShards, conf.clusterId) + let relayService = ServiceInfo(id: WakuRelayCodec, data: @[]) + providedServices.add(relayService) + if conf.rendezvous: await node.mountRendezvous(conf.clusterId, shards) await node.mountRendezvousClient(conf.clusterId) + let rendezvousService = ServiceInfo(id: WakuRendezVousCodec, data: @[]) + providedServices.add(rendezvousService) + # Keepalive mounted on all nodes try: await mountLibp2pPing(node) @@ -332,6 +346,9 @@ proc setupProtocols( except CatchableError: return err("failed to mount waku lightpush protocol: " & getCurrentExceptionMsg()) + let lightpushService = ServiceInfo(id: WakuLightPushCodec, data: @[]) + providedServices.add(lightpushService) + mountLightPushClient(node) mountLegacyLightPushClient(node) if conf.remoteLightPushNode.isSome(): @@ -354,6 +371,9 @@ proc setupProtocols( except CatchableError: return err("failed to mount waku filter protocol: " & getCurrentExceptionMsg()) + let filterService = ServiceInfo(id: WakuFilterPushCodec, data: @[]) + providedServices.add(filterService) + await node.mountFilterClient() if conf.remoteFilterNode.isSome(): let filterNode = parsePeerInfo(conf.remoteFilterNode.get()).valueOr: @@ -374,6 +394,9 @@ proc setupProtocols( return err("failed to mount waku peer-exchange protocol: " & getCurrentExceptionMsg()) + let peerXchangeService = ServiceInfo(id: WakuPeerExchangeCodec, data: @[]) + providedServices.add(peerXchangeService) + if conf.remotePeerExchangeNode.isSome(): let peerExchangeNode = parsePeerInfo(conf.remotePeerExchangeNode.get()).valueOr: return err("failed to set node waku peer-exchange peer: " & error) From 8bed6241b05fe57f2162d56a029b854e7109cd57 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Mon, 23 Mar 2026 13:28:45 -0400 Subject: [PATCH 03/19] Mix usage of service discovery --- tools/confutils/cli_args.nim | 42 +---- waku/discovery/waku_kademlia.nim | 70 +++++---- .../factory/conf_builder/mix_conf_builder.nim | 12 +- waku/factory/node_factory.nim | 15 +- waku/factory/waku_conf.nim | 1 - waku/node/waku_node.nim | 15 +- waku/waku_mix/protocol.nim | 145 +++++++++++------- 7 files changed, 150 insertions(+), 150 deletions(-) diff --git a/tools/confutils/cli_args.nim b/tools/confutils/cli_args.nim index d63b5880c..543f324d9 100644 --- a/tools/confutils/cli_args.nim +++ b/tools/confutils/cli_args.nim @@ -266,7 +266,8 @@ type WakuNodeConf* = object ## Circuit-relay config isRelayClient* {. - desc: """Set the node as a relay-client. + desc: + """Set the node as a relay-client. Set it to true for nodes that run behind a NAT or firewall and hence would have reachability issues.""", defaultValue: false, @@ -636,12 +637,6 @@ with the drawback of consuming some more bandwidth.""", name: "mixkey" .}: Option[string] - mixnodes* {. - desc: - "Multiaddress and mix-key of mix node to be statically specified in format multiaddr:mixPubKey. Argument may be repeated.", - name: "mixnode" - .}: seq[MixNodePubInfo] - # Kademlia Discovery config enableKadDiscovery* {. desc: @@ -735,22 +730,6 @@ proc isNumber(x: string): bool = except ValueError: result = false -proc parseCmdArg*(T: type MixNodePubInfo, p: string): T = - let elements = p.split(":") - if elements.len != 2: - raise newException( - ValueError, "Invalid format for mix node expected multiaddr:mixPublicKey" - ) - let multiaddr = MultiAddress.init(elements[0]).valueOr: - raise newException(ValueError, "Invalid multiaddress format") - if not multiaddr.contains(multiCodec("ip4")).get(): - raise newException( - ValueError, "Invalid format for ip address, expected a ipv4 multiaddress" - ) - return MixNodePubInfo( - multiaddr: elements[0], pubKey: intoCurve25519Key(ncrutils.fromHex(elements[1])) - ) - proc parseCmdArg*(T: type ProtectedShard, p: string): T = let elements = p.split(":") if elements.len != 2: @@ -834,22 +813,6 @@ proc readValue*( except CatchableError: raise newException(SerializationError, getCurrentExceptionMsg()) -proc readValue*( - r: var TomlReader, value: var MixNodePubInfo -) {.raises: [SerializationError].} = - try: - value = parseCmdArg(MixNodePubInfo, r.readValue(string)) - except CatchableError: - raise newException(SerializationError, getCurrentExceptionMsg()) - -proc readValue*( - r: var EnvvarReader, value: var MixNodePubInfo -) {.raises: [SerializationError].} = - try: - value = parseCmdArg(MixNodePubInfo, r.readValue(string)) - except CatchableError: - raise newException(SerializationError, getCurrentExceptionMsg()) - proc readValue*( r: var TomlReader, value: var ProtectedShard ) {.raises: [SerializationError].} = @@ -1067,7 +1030,6 @@ proc toWakuConf*(n: WakuNodeConf): ConfResult[WakuConf] = b.storeServiceConf.storeSyncConf.withRelayJitterSec(n.storeSyncRelayJitter) b.mixConf.withEnabled(n.mix) - b.mixConf.withMixNodes(n.mixnodes) b.withMix(n.mix) if n.mixkey.isSome(): b.mixConf.withMixKey(n.mixkey.get()) diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index 16feb2964..88076dbb2 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -1,11 +1,13 @@ {.push raises: [].} -import std/[options, sequtils, sugar] +import std/[options, sequtils] import chronos, chronicles, results, - stew/byteutils, + libp2p/crypto/curve25519, + libp2p/crypto/crypto, + libp2p/protocols/mix/mix_protocol, libp2p/[peerid, multiaddress, switch], libp2p/extended_peer_record, libp2p/protocols/[kademlia, kad_disco], @@ -15,14 +17,14 @@ import import waku/waku_core, waku/node/peer_manager logScope: - topics = "waku kademlia discovery" + topics = "waku kademlia" const DefaultKademliaDiscoveryInterval* = chronos.seconds(10) type WakuKademlia* = ref object protocol*: KademliaDiscovery peerManager: PeerManager - intervalFut: Future[void] + walkIntervalFut: Future[void] proc toRemotePeerInfo(record: ExtendedPeerRecord): Option[RemotePeerInfo] = debug "processing kademlia record", @@ -42,22 +44,37 @@ proc toRemotePeerInfo(record: ExtendedPeerRecord): Option[RemotePeerInfo] = let protocols = record.services.mapIt(it.id) + var mixPubKey = none(Curve25519Key) + for service in record.services: + if service.id != MixProtocolID: + continue + + if service.data.len != Curve25519KeySize: + continue + + mixPubKey = some(intoCurve25519Key(service.data)) + break + return some( RemotePeerInfo.init( - record.peerId, addrs = addrs, protocols = protocols, origin = PeerOrigin.Kademlia + record.peerId, + addrs = addrs, + protocols = protocols, + origin = PeerOrigin.Kademlia, + mixPubKey = mixPubKey, ) ) proc runDiscoveryLoop( - wk: WakuKademlia, interval: Duration + self: WakuKademlia, interval: Duration ) {.async: (raises: [CancelledError]).} = - info "kademlia discovery loop started", interval = interval + debug "kademlia discovery loop started", interval = interval while true: await sleepAsync(interval) let res = catch: - await wk.protocol.randomRecords() + await self.protocol.randomRecords() let records = res.valueOr: error "kademlia discovery lookup failed", error = res.error.msg continue @@ -66,15 +83,13 @@ proc runDiscoveryLoop( let peerInfo = toRemotePeerInfo(record).valueOr: continue - wk.peerManager.addPeer(peerInfo, PeerOrigin.Kademlia) + self.peerManager.addPeer(peerInfo, PeerOrigin.Kademlia) - debug "peer added via kademlia discovery", + debug "peer added via random walk", peerId = $peerInfo.peerId, addresses = peerInfo.addrs.mapIt($it), protocols = peerInfo.protocols - #TODO peer added metric - proc lookup*( self: WakuKademlia, codec: string ): Future[seq[RemotePeerInfo]] {.async: (raises: []).} = @@ -97,13 +112,12 @@ proc lookup*( self.peerManager.addPeer(peerInfo, PeerOrigin.Kademlia) - debug "peer added via kademlia discovery", + debug "peer added via service discovery", + service = codec, peerId = $peerInfo.peerId, addresses = peerInfo.addrs.mapIt($it), protocols = peerInfo.protocols - #TODO peer added metric - peerInfos.add(peerInfo) return peerInfos @@ -116,7 +130,7 @@ proc new*( providedServices: var seq[ServiceInfo], ): T = if bootstrapNodes.len == 0: - info "creating kademlia discovery as seed node (no bootstrap nodes)" + debug "creating kademlia discovery as seed node (no bootstrap nodes)" let kademlia = KademliaDiscovery.new( switch, @@ -127,34 +141,34 @@ proc new*( services = providedServices, ) - info "kademlia service discovery created", bootstrapNodes = bootstrapNodes.len - return WakuKademlia(protocol: kademlia, peerManager: peerManager) proc start*( self: WakuKademlia, interval: Duration = DefaultKademliaDiscoveryInterval -) {.async: (raises: [CancelledError]).} = +) {.async.} = if self.protocol.started: - warn "Starting kad-disco twice" + warn "Starting waku kad twice" return + info "Starting Waku Kademlia" + await self.protocol.start() - self.intervalFut = self.runDiscoveryLoop(interval) + self.walkIntervalFut = self.runDiscoveryLoop(interval) - info "kademlia discovery started" + info "Waku Kademlia Started" -proc stop*(self: WakuKademlia) {.async: (raises: []).} = +proc stop*(self: WakuKademlia) {.async.} = if not self.protocol.started: return - info "Stopping kademlia discovery" + info "Stopping Waku Kademlia" - if not self.intervalFut.isNil(): - self.intervalFut.cancelSoon() - self.intervalFut = nil + if not self.walkIntervalFut.isNil(): + self.walkIntervalFut.cancelSoon() + self.walkIntervalFut = nil if not self.protocol.isNil(): await self.protocol.stop() - info "Successfully stopped kademlia discovery" + info "Successfully stopped Waku Kademlia" diff --git a/waku/factory/conf_builder/mix_conf_builder.nim b/waku/factory/conf_builder/mix_conf_builder.nim index 145ccb76e..8a4f5b5f1 100644 --- a/waku/factory/conf_builder/mix_conf_builder.nim +++ b/waku/factory/conf_builder/mix_conf_builder.nim @@ -11,7 +11,6 @@ logScope: type MixConfBuilder* = object enabled: Option[bool] mixKey: Option[string] - mixNodes: seq[MixNodePubInfo] proc init*(T: type MixConfBuilder): MixConfBuilder = MixConfBuilder() @@ -22,9 +21,6 @@ proc withEnabled*(b: var MixConfBuilder, enabled: bool) = proc withMixKey*(b: var MixConfBuilder, mixKey: string) = b.mixKey = some(mixKey) -proc withMixNodes*(b: var MixConfBuilder, mixNodes: seq[MixNodePubInfo]) = - b.mixNodes = mixNodes - proc build*(b: MixConfBuilder): Result[Option[MixConf], string] = if not b.enabled.get(false): return ok(none[MixConf]()) @@ -32,12 +28,8 @@ proc build*(b: MixConfBuilder): Result[Option[MixConf], string] = if b.mixKey.isSome(): let mixPrivKey = intoCurve25519Key(ncrutils.fromHex(b.mixKey.get())) let mixPubKey = public(mixPrivKey) - return ok( - some(MixConf(mixKey: mixPrivKey, mixPubKey: mixPubKey, mixNodes: b.mixNodes)) - ) + return ok(some(MixConf(mixKey: mixPrivKey, mixPubKey: mixPubKey))) else: let (mixPrivKey, mixPubKey) = generateKeyPair().valueOr: return err("Generate key pair error: " & $error) - return ok( - some(MixConf(mixKey: mixPrivKey, mixPubKey: mixPubKey, mixNodes: b.mixNodes)) - ) + return ok(some(MixConf(mixKey: mixPrivKey, mixPubKey: mixPubKey))) diff --git a/waku/factory/node_factory.nim b/waku/factory/node_factory.nim index 8f4bba310..95a1e240b 100644 --- a/waku/factory/node_factory.nim +++ b/waku/factory/node_factory.nim @@ -32,6 +32,7 @@ import ../waku_filter_v2, ../waku_peer_exchange, ../discovery/waku_kademlia, + ../waku_mix/protocol, ../node/peer_manager, ../node/peer_manager/peer_store/waku_peer_storage, ../node/peer_manager/peer_store/migrations as peer_store_sqlite_migrations, @@ -168,10 +169,10 @@ proc setupProtocols( if conf.mixConf.isSome(): let mixConf = conf.mixConf.get() - let mixService = ServiceInfo(id: MixProtocolID, data: @(mixConf.mixKey)) + let mixService = ServiceInfo(id: MixProtocolID, data: @(mixConf.mixPubKey)) providedServices.add(mixService) - (await node.mountMix(conf.clusterId, mixConf.mixKey, mixConf.mixnodes)).isOkOr: + (await node.mountMix(mixConf.mixKey)).isOkOr: return err("failed to mount waku mix protocol: " & $error) if conf.storeServiceConf.isSome(): @@ -420,6 +421,10 @@ proc setupProtocols( node.wakuKademlia = kademlia + # Connect kademlia to mix for peer discovery + if not node.wakuMix.isNil() and not node.wakuKademlia.isNil(): + node.wakuMix.setKademlia(node.wakuKademlia) + return ok() ## Start node @@ -471,12 +476,6 @@ proc startNode*( if conf.relay: node.peerManager.start() - if not node.wakuKademlia.isNil(): - let catchRes = catch: - await node.wakuKademlia.start() - if catchRes.isErr(): - return err("failed to start kademlia discovery: " & catchRes.error.msg) - return ok() proc setupNode*( diff --git a/waku/factory/waku_conf.nim b/waku/factory/waku_conf.nim index 4934faccc..f199d1e55 100644 --- a/waku/factory/waku_conf.nim +++ b/waku/factory/waku_conf.nim @@ -50,7 +50,6 @@ type StoreSyncConf* {.requiresInit.} = object type MixConf* = ref object mixKey*: Curve25519Key mixPubKey*: Curve25519Key - mixnodes*: seq[MixNodePubInfo] type KademliaDiscoveryConf* = object bootstrapNodes*: seq[(PeerId, seq[MultiAddress])] diff --git a/waku/node/waku_node.nim b/waku/node/waku_node.nim index 45080d9d0..defbe404b 100644 --- a/waku/node/waku_node.nim +++ b/waku/node/waku_node.nim @@ -297,10 +297,7 @@ proc getMixNodePoolSize*(node: WakuNode): int = return node.wakuMix.poolSize() proc mountMix*( - node: WakuNode, - clusterId: uint16, - mixPrivKey: Curve25519Key, - mixnodes: seq[MixNodePubInfo], + node: WakuNode, mixPrivKey: Curve25519Key ): Future[Result[void, string]] {.async.} = info "mounting mix protocol", nodeId = node.info #TODO log the config used @@ -312,10 +309,13 @@ proc mountMix*( info "local addr", localaddr = localaddrStr node.wakuMix = WakuMix.new( - localaddrStr, node.peerManager, clusterId, mixPrivKey, mixnodes + mixPrivKey = mixPrivKey, + nodeAddr = localaddrStr, + switch = node.switch, + wakuKademlia = node.wakuKademlia, ).valueOr: error "Waku Mix protocol initialization failed", err = error - return + return err("Waku Mix protocol initialization failed: " & error) #TODO: should we do the below only for exit node? Also, what if multiple protocols use mix? node.wakuMix.registerDestReadBehavior(WakuLightPushCodec, readLp(int(-1))) let catchRes = catch: @@ -638,6 +638,9 @@ proc stop*(node: WakuNode) {.async.} = if not node.wakuRendezvousClient.isNil(): await node.wakuRendezvousClient.stopWait() + if not node.wakuKademlia.isNil(): + await node.wakuKademlia.stop() + node.started = false proc isReady*(node: WakuNode): Future[bool] {.async: (raises: [Exception]).} = diff --git a/waku/waku_mix/protocol.nim b/waku/waku_mix/protocol.nim index ac8b69eaf..8ee25073f 100644 --- a/waku/waku_mix/protocol.nim +++ b/waku/waku_mix/protocol.nim @@ -10,98 +10,129 @@ import libp2p/protocols/mix/mix_protocol, libp2p/protocols/mix/mix_metrics, libp2p/protocols/mix/delay_strategy, - libp2p/[multiaddress, peerid], + libp2p/[multiaddress, peerid, switch], + libp2p/extended_peer_record, eth/common/keys import waku/node/peer_manager, waku/waku_core, waku/waku_enr, - waku/node/peer_manager/waku_peer_store + waku/node/peer_manager/waku_peer_store, + waku/discovery/waku_kademlia logScope: topics = "waku mix" -const minMixPoolSize = 4 +const + MinimumMixPoolSize = 4 + DefaultMixPoolMaintenanceInterval = chronos.seconds(10) -type - WakuMix* = ref object of MixProtocol - peerManager*: PeerManager - clusterId: uint16 - pubKey*: Curve25519Key +type WakuMix* = ref object of MixProtocol + pubKey*: Curve25519Key + targetMixPoolSize: int + currentMixPoolSize: int + maintenanceInterval: Duration + maintenanceIntervalFut: Future[void] + wakuKademlia: WakuKademlia - WakuMixResult*[T] = Result[T, string] +proc poolSize*(self: WakuMix): int = + if self.nodePool.isNil(): + 0 + else: + self.nodePool.len() - MixNodePubInfo* = object - multiAddr*: string - pubKey*: Curve25519Key +proc mixPoolMaintenance( + self: WakuMix, interval: Duration +) {.async: (raises: [CancelledError]).} = + debug "mix pool maintenance loop started", interval = interval -proc processBootNodes( - bootnodes: seq[MixNodePubInfo], peermgr: PeerManager, mix: WakuMix -) = - var count = 0 - for node in bootnodes: - let pInfo = parsePeerInfo(node.multiAddr).valueOr: - error "Failed to get peer id from multiaddress: ", - error = error, multiAddr = $node.multiAddr - continue - let peerId = pInfo.peerId - var peerPubKey: crypto.PublicKey - if not peerId.extractPublicKey(peerPubKey): - warn "Failed to extract public key from peerId, skipping node", peerId = peerId + while true: + await sleepAsync(interval) + + self.currentMixPoolSize = self.poolSize() + mix_pool_size.set(self.currentMixPoolSize.int64) + + if self.currentMixPoolSize >= self.targetMixPoolSize: continue - if peerPubKey.scheme != PKScheme.Secp256k1: - warn "Peer public key is not Secp256k1, skipping node", - peerId = peerId, scheme = peerPubKey.scheme + # Skip discovery if kademlia not available + if self.wakuKademlia.isNil(): + debug "kademlia not available for mix peer discovery" continue - let multiAddr = MultiAddress.init(node.multiAddr).valueOr: - error "Failed to parse multiaddress", multiAddr = node.multiAddr, error = error - continue + trace "mix node pool below threshold, performing targeted lookup", + currentPoolSize = self.currentMixPoolSize, threshold = self.targetMixPoolSize - let mixPubInfo = MixPubInfo.init(peerId, multiAddr, node.pubKey, peerPubKey.skkey) - mix.nodePool.add(mixPubInfo) - count.inc() + let mixPeers = await self.wakuKademlia.lookup(MixProtocolID) - peermgr.addPeer( - RemotePeerInfo.init(peerId, @[multiAddr], mixPubKey = some(node.pubKey)) - ) - mix_pool_size.set(count) - info "using mix bootstrap nodes ", count = count + trace "mix peer discovery completed", discoveredPeers = mixPeers.len proc new*( T: typedesc[WakuMix], - nodeAddr: string, - peermgr: PeerManager, - clusterId: uint16, mixPrivKey: Curve25519Key, - bootnodes: seq[MixNodePubInfo], -): WakuMixResult[T] = + nodeAddr: string, + switch: Switch, + targetMixPoolSize: int = MinimumMixPoolSize, + maintenanceInterval: Duration = DefaultMixPoolMaintenanceInterval, + wakuKademlia: WakuKademlia = nil, +): Result[T, string] = let mixPubKey = public(mixPrivKey) - info "mixPubKey", mixPubKey = mixPubKey + + debug "Mix Public Key", mixPubKey = mixPubKey + let nodeMultiAddr = MultiAddress.init(nodeAddr).valueOr: return err("failed to parse mix node address: " & $nodeAddr & ", error: " & error) + let localMixNodeInfo = initMixNodeInfo( - peermgr.switch.peerInfo.peerId, nodeMultiAddr, mixPubKey, mixPrivKey, - peermgr.switch.peerInfo.publicKey.skkey, peermgr.switch.peerInfo.privateKey.skkey, + switch.peerInfo.peerId, nodeMultiAddr, mixPubKey, mixPrivKey, + switch.peerInfo.publicKey.skkey, switch.peerInfo.privateKey.skkey, ) - var m = WakuMix(peerManager: peermgr, clusterId: clusterId, pubKey: mixPubKey) - procCall MixProtocol(m).init( + let mix = WakuMix( + pubKey: mixPubKey, + targetMixPoolSize: targetMixPoolSize, + currentMixPoolSize: 0, + maintenanceInterval: maintenanceInterval, + maintenanceIntervalFut: nil, + wakuKademlia: wakuKademlia, + ) + + procCall MixProtocol(mix).init( localMixNodeInfo, - peermgr.switch, + switch, delayStrategy = ExponentialDelayStrategy.new(meanDelayMs = 50, rng = crypto.newRng()), ) - processBootNodes(bootnodes, peermgr, m) + return ok(mix) - if m.nodePool.len < minMixPoolSize: - warn "publishing with mix won't work until atleast 3 mix nodes in node pool" - return ok(m) +proc setKademlia*(self: WakuMix, wakuKademlia: WakuKademlia) = + self.wakuKademlia = wakuKademlia -proc poolSize*(mix: WakuMix): int = - mix.nodePool.len +method start*(self: WakuMix) {.async.} = + if self.started: + warn "Starting Waku Mix twice" + return -# Mix Protocol + info "Starting Waku Mix" + + await procCall start(MixProtocol(self)) + + self.maintenanceIntervalFut = self.mixPoolMaintenance(self.maintenanceInterval) + + info "Waku Mix Started" + +method stop*(self: WakuMix) {.async.} = + if not self.started: + return + + info "Stopping Waku Mix" + + if not self.maintenanceIntervalFut.isNil(): + self.maintenanceIntervalFut.cancelSoon() + self.maintenanceIntervalFut = nil + + await procCall stop(MixProtocol(self)) + + info "Successfully stopped Waku Mix" From b0b72e98af378c5fab7c8545f49684ee09e2488a Mon Sep 17 00:00:00 2001 From: SionoiS Date: Thu, 26 Mar 2026 07:37:45 -0400 Subject: [PATCH 04/19] kad loop interval conf std/options fixes - add Option[T] valueOr/withValue no longer provided by libp2p - add missing std/options imports no longer re-exported by libp2p --- config.nims | 3 +++ tests/test_wakunode.nim | 2 +- tests/waku_relay/test_wakunode_relay.nim | 2 +- tests/waku_store/test_wakunode_store.nim | 2 +- waku/common/option_shim.nim | 26 ++++++++++++++++++++++++ waku/discovery/waku_kademlia.nim | 12 ++++++----- waku/node/waku_node.nim | 3 --- 7 files changed, 39 insertions(+), 11 deletions(-) create mode 100644 waku/common/option_shim.nim diff --git a/config.nims b/config.nims index 0f6052c9b..0a61a086d 100644 --- a/config.nims +++ b/config.nims @@ -90,6 +90,9 @@ if not defined(macosx) and not defined(android): nimStackTraceOverride switch("import", "libbacktrace") +# Shim to provide valueOr and withValue for Option[T] +switch("import", "waku/common/option_shim") + --define: nimOldCaseObjects # https://github.com/status-im/nim-confutils/issues/9 diff --git a/tests/test_wakunode.nim b/tests/test_wakunode.nim index a7f1084fb..39452890d 100644 --- a/tests/test_wakunode.nim +++ b/tests/test_wakunode.nim @@ -1,7 +1,7 @@ {.used.} import - std/[sequtils, strutils, net], + std/[options, sequtils, strutils, net], stew/byteutils, testutils/unittests, chronicles, diff --git a/tests/waku_relay/test_wakunode_relay.nim b/tests/waku_relay/test_wakunode_relay.nim index a687119bd..ebfeef22c 100644 --- a/tests/waku_relay/test_wakunode_relay.nim +++ b/tests/waku_relay/test_wakunode_relay.nim @@ -1,7 +1,7 @@ {.used.} import - std/[os, strutils, sequtils, sysrand, math], + std/[options, os, strutils, sequtils, sysrand, math], stew/byteutils, testutils/unittests, chronos, diff --git a/tests/waku_store/test_wakunode_store.nim b/tests/waku_store/test_wakunode_store.nim index fa73cd16d..b7732aa65 100644 --- a/tests/waku_store/test_wakunode_store.nim +++ b/tests/waku_store/test_wakunode_store.nim @@ -1,7 +1,7 @@ {.used.} import - std/sequtils, + std/[options, sequtils], testutils/unittests, chronicles, chronos, diff --git a/waku/common/option_shim.nim b/waku/common/option_shim.nim new file mode 100644 index 000000000..6827cd856 --- /dev/null +++ b/waku/common/option_shim.nim @@ -0,0 +1,26 @@ +# Shim to provide valueOr and withValue for Option[T] + +{.push raises: [].} + +import std/options + +template valueOr*[T](self: Option[T], def: untyped): T = + let s = self + if s.isSome(): + s.get() + else: + def + +template withValue*[T](self: Option[T], value, body: untyped) = + let s = self + if s.isSome(): + let value {.inject.} = s.get() + body + +template withValue*[T](self: Option[T], value, body, elseStmt: untyped) = + let s = self + if s.isSome(): + let value {.inject.} = s.get() + body + else: + elseStmt diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index 88076dbb2..26f987439 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -24,6 +24,7 @@ const DefaultKademliaDiscoveryInterval* = chronos.seconds(10) type WakuKademlia* = ref object protocol*: KademliaDiscovery peerManager: PeerManager + loopInterval: Duration walkIntervalFut: Future[void] proc toRemotePeerInfo(record: ExtendedPeerRecord): Option[RemotePeerInfo] = @@ -128,6 +129,7 @@ proc new*( peerManager: PeerManager, bootstrapNodes: seq[(PeerId, seq[MultiAddress])], providedServices: var seq[ServiceInfo], + loopInterval: Duration = DefaultKademliaDiscoveryInterval, ): T = if bootstrapNodes.len == 0: debug "creating kademlia discovery as seed node (no bootstrap nodes)" @@ -141,11 +143,11 @@ proc new*( services = providedServices, ) - return WakuKademlia(protocol: kademlia, peerManager: peerManager) + return WakuKademlia( + protocol: kademlia, peerManager: peerManager, loopInterval: loopInterval + ) -proc start*( - self: WakuKademlia, interval: Duration = DefaultKademliaDiscoveryInterval -) {.async.} = +proc start*(self: WakuKademlia) {.async.} = if self.protocol.started: warn "Starting waku kad twice" return @@ -154,7 +156,7 @@ proc start*( await self.protocol.start() - self.walkIntervalFut = self.runDiscoveryLoop(interval) + self.walkIntervalFut = self.runDiscoveryLoop(self.loopInterval) info "Waku Kademlia Started" diff --git a/waku/node/waku_node.nim b/waku/node/waku_node.nim index defbe404b..03b2f05fb 100644 --- a/waku/node/waku_node.nim +++ b/waku/node/waku_node.nim @@ -638,9 +638,6 @@ proc stop*(node: WakuNode) {.async.} = if not node.wakuRendezvousClient.isNil(): await node.wakuRendezvousClient.stopWait() - if not node.wakuKademlia.isNil(): - await node.wakuKademlia.stop() - node.started = false proc isReady*(node: WakuNode): Future[bool] {.async: (raises: [Exception]).} = From 05635bcd4d2cf9f726143c758ddaaf6b6f1b61a5 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Wed, 1 Apr 2026 12:14:19 -0400 Subject: [PATCH 05/19] chat2mix update --- apps/chat2mix/chat2mix.nim | 65 ++++++++++++++----------------- apps/chat2mix/config_chat2mix.nim | 23 ----------- 2 files changed, 30 insertions(+), 58 deletions(-) diff --git a/apps/chat2mix/chat2mix.nim b/apps/chat2mix/chat2mix.nim index 8b786d7b6..374f670b8 100644 --- a/apps/chat2mix/chat2mix.nim +++ b/apps/chat2mix/chat2mix.nim @@ -31,6 +31,7 @@ import nameresolving/dnsresolver, protocols/mix/curve25519, protocols/mix/mix_protocol, + extended_peer_record, ] # define DNS resolution import waku/[ @@ -48,6 +49,7 @@ import waku_store/common, waku_filter_v2/client, common/logging, + waku_mix, ], ./config_chat2mix @@ -57,7 +59,8 @@ import ../../waku/waku_rln_relay logScope: topics = "chat2 mix" -const Help = """ +const Help = + """ Commands: /[?|help|connect|nick|exit] help: Prints this help connect: dials a remote peer @@ -428,16 +431,16 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = builder.withRecord(record) builder - .withNetworkConfigurationDetails( - conf.listenAddress, - Port(uint16(conf.tcpPort) + conf.portsShift), - extIp, - extTcpPort, - wsBindPort = Port(uint16(conf.websocketPort) + conf.portsShift), - wsEnabled = conf.websocketSupport, - wssEnabled = conf.websocketSecureSupport, - ) - .tryGet() + .withNetworkConfigurationDetails( + conf.listenAddress, + Port(uint16(conf.tcpPort) + conf.portsShift), + extIp, + extTcpPort, + wsBindPort = Port(uint16(conf.websocketPort) + conf.portsShift), + wsEnabled = conf.websocketSupport, + wssEnabled = conf.websocketSecureSupport, + ) + .tryGet() builder.build().tryGet() node.mountAutoSharding(conf.clusterId, conf.numShardsInNetwork).isOkOr: @@ -447,15 +450,20 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = error "failed to mount waku metadata protocol: ", err = error quit(QuitFailure) + var providedServices: seq[ServiceInfo] = @[] + let (mixPrivKey, mixPubKey) = generateKeyPair().valueOr: error "failed to generate mix key pair", error = error return - (await node.mountMix(conf.clusterId, mixPrivKey, conf.mixnodes)).isOkOr: + let mixService = ServiceInfo(id: MixProtocolID, data: @(mixPubKey)) + providedServices.add(mixService) + + (await node.mountMix(mixPrivKey)).isOkOr: error "failed to mount waku mix protocol: ", error = $error quit(QuitFailure) - # Setup extended kademlia discovery if bootstrap nodes are provided + # Setup kademlia discovery if bootstrap nodes are provided if conf.kadBootstrapNodes.len > 0: var kadBootstrapPeers: seq[(PeerId, seq[MultiAddress])] for nodeStr in conf.kadBootstrapNodes: @@ -466,23 +474,8 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = if kadBootstrapPeers.len > 0: node.wakuKademlia = WakuKademlia.new( - node.switch, - ExtendedKademliaDiscoveryParams( - bootstrapNodes: kadBootstrapPeers, - mixPubKey: some(mixPubKey), - advertiseMix: false, - ), - node.peerManager, - getMixNodePoolSize = proc(): int {.gcsafe, raises: [].} = - if node.wakuMix.isNil(): - 0 - else: - node.getMixNodePoolSize(), - isNodeStarted = proc(): bool {.gcsafe, raises: [].} = - node.started, - ).valueOr: - error "failed to setup kademlia discovery", error = error - quit(QuitFailure) + node.switch, node.peerManager, kadBootstrapPeers, providedServices + ) #await node.mountRendezvousClient(conf.clusterId) @@ -490,9 +483,11 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = node.peerManager.start() if not node.wakuKademlia.isNil(): - (await node.wakuKademlia.start(minMixPeers = MinMixNodePoolSize)).isOkOr: - error "failed to start kademlia discovery", error = error - quit(QuitFailure) + await node.wakuKademlia.start() + + # Wire mix protocol with kademlia for peer discovery + if not node.wakuMix.isNil() and not node.wakuKademlia.isNil(): + node.wakuMix.setKademlia(node.wakuKademlia) await node.mountLibp2pPing() #await node.mountPeerExchangeClient() @@ -645,8 +640,8 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = currentpoolSize = node.getMixNodePoolSize() echo "ready to publish messages now" - # Once min mixnodes are discovered loop as per default setting - node.startPeerExchangeLoop() + # Peer exchange disabled - using Kademlia discovery only + # node.startPeerExchangeLoop() if conf.metricsLogging: startMetricsLog() diff --git a/apps/chat2mix/config_chat2mix.nim b/apps/chat2mix/config_chat2mix.nim index 4e5a32e6d..dc43469e4 100644 --- a/apps/chat2mix/config_chat2mix.nim +++ b/apps/chat2mix/config_chat2mix.nim @@ -85,12 +85,6 @@ type defaultValue: @[] .}: seq[string] - mixnodes* {. - desc: - "Multiaddress and mix-key of mix node to be statically specified in format multiaddr:mixPubKey. Argument may be repeated.", - name: "mixnode" - .}: seq[MixNodePubInfo] - keepAlive* {. desc: "Enable keep-alive for idle connections: true|false", defaultValue: false, @@ -236,23 +230,6 @@ type name: "kad-bootstrap-node" .}: seq[string] -proc parseCmdArg*(T: type MixNodePubInfo, p: string): T = - let elements = p.split(":") - if elements.len != 2: - raise newException( - ValueError, "Invalid format for mix node expected multiaddr:mixPublicKey" - ) - let multiaddr = MultiAddress.init(elements[0]).valueOr: - raise newException(ValueError, "Invalid multiaddress format") - if not multiaddr.contains(multiCodec("ip4")).get(): - raise newException( - ValueError, "Invalid format for ip address, expected a ipv4 multiaddress" - ) - - return MixNodePubInfo( - multiaddr: elements[0], pubKey: intoCurve25519Key(ncrutils.fromHex(elements[1])) - ) - # NOTE: Keys are different in nim-libp2p proc parseCmdArg*(T: type crypto.PrivateKey, p: string): T = try: From 94e881eb02d88ce2d490501bebd7e1f8876223b4 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Mon, 13 Apr 2026 09:56:58 -0400 Subject: [PATCH 06/19] disable XPR publish & provide only one service --- waku/discovery/waku_kademlia.nim | 4 +++- waku/factory/node_factory.nim | 41 ++++++++++++++++++-------------- 2 files changed, 26 insertions(+), 19 deletions(-) diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index 26f987439..edebcddff 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -19,7 +19,7 @@ import waku/waku_core, waku/node/peer_manager logScope: topics = "waku kademlia" -const DefaultKademliaDiscoveryInterval* = chronos.seconds(10) +const DefaultKademliaDiscoveryInterval* = chronos.seconds(60) type WakuKademlia* = ref object protocol*: KademliaDiscovery @@ -130,6 +130,7 @@ proc new*( bootstrapNodes: seq[(PeerId, seq[MultiAddress])], providedServices: var seq[ServiceInfo], loopInterval: Duration = DefaultKademliaDiscoveryInterval, + xprPublishing: bool = false, ): T = if bootstrapNodes.len == 0: debug "creating kademlia discovery as seed node (no bootstrap nodes)" @@ -141,6 +142,7 @@ proc new*( validator = kad_types.ExtEntryValidator(), selector = kad_types.ExtEntrySelector() ), services = providedServices, + xprPublishing = xprPublishing, ) return WakuKademlia( diff --git a/waku/factory/node_factory.nim b/waku/factory/node_factory.nim index 95a1e240b..58eee4f29 100644 --- a/waku/factory/node_factory.nim +++ b/waku/factory/node_factory.nim @@ -165,12 +165,17 @@ proc setupProtocols( var providedServices: seq[ServiceInfo] + # For testing lets use only one service + + let deliveryService = ServiceInfo(id: "delivery", data: @[]) + providedServices.add(deliveryService) + #mount mix if conf.mixConf.isSome(): let mixConf = conf.mixConf.get() - let mixService = ServiceInfo(id: MixProtocolID, data: @(mixConf.mixPubKey)) - providedServices.add(mixService) + #let mixService = ServiceInfo(id: MixProtocolID, data: @(mixConf.mixPubKey)) + #providedServices.add(mixService) (await node.mountMix(mixConf.mixKey)).isOkOr: return err("failed to mount waku mix protocol: " & $error) @@ -198,8 +203,8 @@ proc setupProtocols( except CatchableError: return err("failed to mount waku store protocol: " & getCurrentExceptionMsg()) - let storeService = ServiceInfo(id: WakuStoreCodec, data: @[]) - providedServices.add(storeService) + #let storeService = ServiceInfo(id: WakuStoreCodec, data: @[]) + #providedServices.add(storeService) if storeServiceConf.storeSyncConf.isSome(): let confStoreSync = storeServiceConf.storeSyncConf.get() @@ -213,10 +218,10 @@ proc setupProtocols( ).isOkOr: return err("failed to mount waku store sync protocol: " & $error) - let reconciliationService = ServiceInfo(id: WakuReconciliationCodec, data: @[]) - let transferService = ServiceInfo(id: WakuTransferCodec, data: @[]) - providedServices.add(reconciliationService) - providedServices.add(transferService) + #let reconciliationService = ServiceInfo(id: WakuReconciliationCodec, data: @[]) + #let transferService = ServiceInfo(id: WakuTransferCodec, data: @[]) + #providedServices.add(reconciliationService) + #providedServices.add(transferService) if conf.remoteStoreNode.isSome(): let storeNode = parsePeerInfo(conf.remoteStoreNode.get()).valueOr: @@ -301,15 +306,15 @@ proc setupProtocols( protectedShard = shardKey.shard, publicKey = shardKey.key node.wakuRelay.addSignedShardsValidator(subscribedProtectedShards, conf.clusterId) - let relayService = ServiceInfo(id: WakuRelayCodec, data: @[]) - providedServices.add(relayService) + #let relayService = ServiceInfo(id: WakuRelayCodec, data: @[]) + #providedServices.add(relayService) if conf.rendezvous: await node.mountRendezvous(conf.clusterId, shards) await node.mountRendezvousClient(conf.clusterId) - let rendezvousService = ServiceInfo(id: WakuRendezVousCodec, data: @[]) - providedServices.add(rendezvousService) + #let rendezvousService = ServiceInfo(id: WakuRendezVousCodec, data: @[]) + #providedServices.add(rendezvousService) # Keepalive mounted on all nodes try: @@ -347,8 +352,8 @@ proc setupProtocols( except CatchableError: return err("failed to mount waku lightpush protocol: " & getCurrentExceptionMsg()) - let lightpushService = ServiceInfo(id: WakuLightPushCodec, data: @[]) - providedServices.add(lightpushService) + #let lightpushService = ServiceInfo(id: WakuLightPushCodec, data: @[]) + #providedServices.add(lightpushService) mountLightPushClient(node) mountLegacyLightPushClient(node) @@ -372,8 +377,8 @@ proc setupProtocols( except CatchableError: return err("failed to mount waku filter protocol: " & getCurrentExceptionMsg()) - let filterService = ServiceInfo(id: WakuFilterPushCodec, data: @[]) - providedServices.add(filterService) + #let filterService = ServiceInfo(id: WakuFilterPushCodec, data: @[]) + #providedServices.add(filterService) await node.mountFilterClient() if conf.remoteFilterNode.isSome(): @@ -395,8 +400,8 @@ proc setupProtocols( return err("failed to mount waku peer-exchange protocol: " & getCurrentExceptionMsg()) - let peerXchangeService = ServiceInfo(id: WakuPeerExchangeCodec, data: @[]) - providedServices.add(peerXchangeService) + #let peerXchangeService = ServiceInfo(id: WakuPeerExchangeCodec, data: @[]) + #providedServices.add(peerXchangeService) if conf.remotePeerExchangeNode.isSome(): let peerExchangeNode = parsePeerInfo(conf.remotePeerExchangeNode.get()).valueOr: From 7eeb0f3d1064d9d297ada9ed83350e3eb94ab16b Mon Sep 17 00:00:00 2001 From: SionoiS Date: Tue, 14 Apr 2026 08:15:27 -0400 Subject: [PATCH 07/19] enable hole punching --- waku/node/waku_switch.nim | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/waku/node/waku_switch.nim b/waku/node/waku_switch.nim index d1af77662..62797a8d8 100644 --- a/waku/node/waku_switch.nim +++ b/waku/node/waku_switch.nim @@ -9,7 +9,10 @@ import libp2p/crypto/crypto, libp2p/protocols/pubsub/gossipsub, libp2p/protocols/rendezvous, - libp2p/protocols/connectivity/relay/relay, + libp2p/protocols/connectivity/relay/[client, relay], + libp2p/protocols/connectivity/autonat/[client, service], + libp2p/services/hpservice, + libp2p/services/autorelayservice, libp2p/nameresolving/nameresolver, libp2p/builders, libp2p/switch, @@ -75,7 +78,13 @@ proc newWakuSwitch*( peerStoreCapacity = none(int), # defaults to 1.25 maxConnections rendezvous: RendezVous = nil, circuitRelay: Relay, + maxNumRelays: int = 5, ): Switch {.raises: [Defect, IOError, LPError].} = + let + autonatService = AutonatService.new(AutonatClient(), rng) + autoRelayService = AutoRelayService.new(maxNumRelays, RelayClient.new(), nil, rng) + hpService: Service = HPService.new(autonatService, autoRelayService) + var b = SwitchBuilder .new() .withRng(rng) @@ -90,7 +99,7 @@ proc newWakuSwitch*( .withNameResolver(nameResolver) .withSignedPeerRecord(sendSignedPeerRecord) .withCircuitRelay(circuitRelay) - .withAutonat() + .withServices(@[hpService]) if peerStoreCapacity.isSome(): b = b.withPeerStore(peerStoreCapacity.get()) From 19ea5fad91e7465354d99fa20f5736a4ee00ea45 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Tue, 14 Apr 2026 09:14:23 -0400 Subject: [PATCH 08/19] update libp2p & related fixes --- waku/waku_mix/protocol.nim | 4 ++-- waku/waku_rendezvous/client.nim | 3 +-- waku/waku_rendezvous/protocol.nim | 1 - 3 files changed, 3 insertions(+), 5 deletions(-) diff --git a/waku/waku_mix/protocol.nim b/waku/waku_mix/protocol.nim index 8ee25073f..0e0d483e3 100644 --- a/waku/waku_mix/protocol.nim +++ b/waku/waku_mix/protocol.nim @@ -10,6 +10,7 @@ import libp2p/protocols/mix/mix_protocol, libp2p/protocols/mix/mix_metrics, libp2p/protocols/mix/delay_strategy, + libp2p/protocols/mix/delay, libp2p/[multiaddress, peerid, switch], libp2p/extended_peer_record, eth/common/keys @@ -101,8 +102,7 @@ proc new*( procCall MixProtocol(mix).init( localMixNodeInfo, switch, - delayStrategy = - ExponentialDelayStrategy.new(meanDelayMs = 50, rng = crypto.newRng()), + delayStrategy = ExponentialDelayStrategy.new(rng = crypto.newRng()), ) return ok(mix) diff --git a/waku/waku_rendezvous/client.nim b/waku/waku_rendezvous/client.nim index 09e789774..62c0de848 100644 --- a/waku/waku_rendezvous/client.nim +++ b/waku/waku_rendezvous/client.nim @@ -7,8 +7,7 @@ import chronicles, libp2p/protocols/rendezvous, libp2p/crypto/curve25519, - libp2p/switch, - libp2p/utils/semaphore + libp2p/switch import metrics except collect diff --git a/waku/waku_rendezvous/protocol.nim b/waku/waku_rendezvous/protocol.nim index 89433f533..0e9b0aa76 100644 --- a/waku/waku_rendezvous/protocol.nim +++ b/waku/waku_rendezvous/protocol.nim @@ -8,7 +8,6 @@ import stew/byteutils, libp2p/protocols/rendezvous, libp2p/protocols/rendezvous/protobuf, - libp2p/utils/semaphore, libp2p/utils/offsettedseq, libp2p/crypto/curve25519, libp2p/switch, From ab995c0a8e5a9b1cc781d15e9ae09a2aa57200e5 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Fri, 17 Apr 2026 08:53:26 -0400 Subject: [PATCH 09/19] add service lookup & refactor --- waku/discovery/waku_kademlia.nim | 99 ++++++++++++++++++-------------- waku/factory/node_factory.nim | 3 +- waku/node/waku_node.nim | 4 ++ 3 files changed, 60 insertions(+), 46 deletions(-) diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index edebcddff..3ea24a31f 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -25,7 +25,8 @@ type WakuKademlia* = ref object protocol*: KademliaDiscovery peerManager: PeerManager loopInterval: Duration - walkIntervalFut: Future[void] + periodicWalkFut: Future[void] + periodicLookupFut: Future[void] proc toRemotePeerInfo(record: ExtendedPeerRecord): Option[RemotePeerInfo] = debug "processing kademlia record", @@ -66,30 +67,30 @@ proc toRemotePeerInfo(record: ExtendedPeerRecord): Option[RemotePeerInfo] = ) ) -proc runDiscoveryLoop( - self: WakuKademlia, interval: Duration -) {.async: (raises: [CancelledError]).} = - debug "kademlia discovery loop started", interval = interval +proc randomWalk*( + self: WakuKademlia +): Future[seq[RemotePeerInfo]] {.async: (raises: []).} = + let res = catch: + await self.protocol.randomRecords() + let records = res.valueOr: + error "kademlia discovery lookup failed", error = res.error.msg + return - while true: - await sleepAsync(interval) - - let res = catch: - await self.protocol.randomRecords() - let records = res.valueOr: - error "kademlia discovery lookup failed", error = res.error.msg + var peerInfos = newSeqOfCap[RemotePeerInfo](records.len) + for record in records: + let peerInfo = toRemotePeerInfo(record).valueOr: continue - for record in records: - let peerInfo = toRemotePeerInfo(record).valueOr: - continue + self.peerManager.addPeer(peerInfo, PeerOrigin.Kademlia) - self.peerManager.addPeer(peerInfo, PeerOrigin.Kademlia) + debug "peer added via random walk", + peerId = $peerInfo.peerId, + addresses = peerInfo.addrs.mapIt($it), + protocols = peerInfo.protocols - debug "peer added via random walk", - peerId = $peerInfo.peerId, - addresses = peerInfo.addrs.mapIt($it), - protocols = peerInfo.protocols + peerInfos.add(peerInfo) + + return peerInfos proc lookup*( self: WakuKademlia, codec: string @@ -123,6 +124,28 @@ proc lookup*( return peerInfos +proc periodicRandomWalk( + self: WakuKademlia, interval: Duration +) {.async: (raises: [CancelledError]).} = + debug "periodic random walk started", interval = interval + + while true: + await sleepAsync(interval) + + discard await self.randomWalk() + +proc periodicLookup( + self: WakuKademlia, interval: Duration +) {.async: (raises: [CancelledError]).} = + debug "periodic service lookup started", interval = interval + + while true: + await sleepAsync(interval) + + # For testing lets use only one hard-coded service + # Same as the advertised one + discard await self.lookup("delivery") + proc new*( T: type WakuKademlia, switch: Switch, @@ -149,30 +172,18 @@ proc new*( protocol: kademlia, peerManager: peerManager, loopInterval: loopInterval ) -proc start*(self: WakuKademlia) {.async.} = - if self.protocol.started: - warn "Starting waku kad twice" - return +proc start*(self: WakuKademlia) = + if self.periodicWalkFut.isNil(): + self.periodicWalkFut = self.periodicRandomWalk(self.loopInterval) - info "Starting Waku Kademlia" + if self.periodicLookupFut.isNil(): + self.periodicLookupFut = self.periodicLookup(self.loopInterval) - await self.protocol.start() +proc stop*(self: WakuKademlia) = + if not self.periodicWalkFut.isNil(): + self.periodicWalkFut.cancelSoon() + self.periodicWalkFut = nil - self.walkIntervalFut = self.runDiscoveryLoop(self.loopInterval) - - info "Waku Kademlia Started" - -proc stop*(self: WakuKademlia) {.async.} = - if not self.protocol.started: - return - - info "Stopping Waku Kademlia" - - if not self.walkIntervalFut.isNil(): - self.walkIntervalFut.cancelSoon() - self.walkIntervalFut = nil - - if not self.protocol.isNil(): - await self.protocol.stop() - - info "Successfully stopped Waku Kademlia" + if not self.periodicLookupFut.isNil(): + self.periodicLookupFut.cancelSoon() + self.periodicLookupFut = nil diff --git a/waku/factory/node_factory.nim b/waku/factory/node_factory.nim index 58eee4f29..dce6322f1 100644 --- a/waku/factory/node_factory.nim +++ b/waku/factory/node_factory.nim @@ -165,8 +165,7 @@ proc setupProtocols( var providedServices: seq[ServiceInfo] - # For testing lets use only one service - + # For testing lets use only one hard-coded service let deliveryService = ServiceInfo(id: "delivery", data: @[]) providedServices.add(deliveryService) diff --git a/waku/node/waku_node.nim b/waku/node/waku_node.nim index 03b2f05fb..a1d243eec 100644 --- a/waku/node/waku_node.nim +++ b/waku/node/waku_node.nim @@ -573,6 +573,8 @@ proc start*(node: WakuNode) {.async.} = if not node.wakuRendezvousClient.isNil(): await node.wakuRendezvousClient.start() + node.wakuKademlia.start() + ## The switch uses this mapper to update peer info addrs ## with announced addrs after start let addressMapper = proc( @@ -616,6 +618,8 @@ proc stop*(node: WakuNode) {.async.} = node.peerManager.stop() + node.wakuKademlia.stop() + if not node.wakuRlnRelay.isNil(): try: await node.wakuRlnRelay.stop() ## this can raise an exception From c8acdbbb3e65926bdb1d69b4b065e9ed4a23df4b Mon Sep 17 00:00:00 2001 From: SionoiS Date: Fri, 17 Apr 2026 10:06:19 -0400 Subject: [PATCH 10/19] remove randomwalk --- waku/discovery/waku_kademlia.nim | 14 +++++++------- waku/node/waku_node.nim | 8 +++++--- 2 files changed, 12 insertions(+), 10 deletions(-) diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index 3ea24a31f..5798a11f3 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -25,7 +25,7 @@ type WakuKademlia* = ref object protocol*: KademliaDiscovery peerManager: PeerManager loopInterval: Duration - periodicWalkFut: Future[void] + #periodicWalkFut: Future[void] periodicLookupFut: Future[void] proc toRemotePeerInfo(record: ExtendedPeerRecord): Option[RemotePeerInfo] = @@ -67,7 +67,7 @@ proc toRemotePeerInfo(record: ExtendedPeerRecord): Option[RemotePeerInfo] = ) ) -proc randomWalk*( +#[ proc randomWalk*( self: WakuKademlia ): Future[seq[RemotePeerInfo]] {.async: (raises: []).} = let res = catch: @@ -90,7 +90,7 @@ proc randomWalk*( peerInfos.add(peerInfo) - return peerInfos + return peerInfos ]# proc lookup*( self: WakuKademlia, codec: string @@ -124,7 +124,7 @@ proc lookup*( return peerInfos -proc periodicRandomWalk( +#[ proc periodicRandomWalk( self: WakuKademlia, interval: Duration ) {.async: (raises: [CancelledError]).} = debug "periodic random walk started", interval = interval @@ -132,7 +132,7 @@ proc periodicRandomWalk( while true: await sleepAsync(interval) - discard await self.randomWalk() + discard await self.randomWalk() ]# proc periodicLookup( self: WakuKademlia, interval: Duration @@ -173,8 +173,8 @@ proc new*( ) proc start*(self: WakuKademlia) = - if self.periodicWalkFut.isNil(): - self.periodicWalkFut = self.periodicRandomWalk(self.loopInterval) + #if self.periodicWalkFut.isNil(): + #self.periodicWalkFut = self.periodicRandomWalk(self.loopInterval) if self.periodicLookupFut.isNil(): self.periodicLookupFut = self.periodicLookup(self.loopInterval) diff --git a/waku/node/waku_node.nim b/waku/node/waku_node.nim index a1d243eec..85166a4cc 100644 --- a/waku/node/waku_node.nim +++ b/waku/node/waku_node.nim @@ -573,7 +573,8 @@ proc start*(node: WakuNode) {.async.} = if not node.wakuRendezvousClient.isNil(): await node.wakuRendezvousClient.start() - node.wakuKademlia.start() + if not node.wakuKademlia.isNil(): + node.wakuKademlia.start() ## The switch uses this mapper to update peer info addrs ## with announced addrs after start @@ -618,8 +619,6 @@ proc stop*(node: WakuNode) {.async.} = node.peerManager.stop() - node.wakuKademlia.stop() - if not node.wakuRlnRelay.isNil(): try: await node.wakuRlnRelay.stop() ## this can raise an exception @@ -642,6 +641,9 @@ proc stop*(node: WakuNode) {.async.} = if not node.wakuRendezvousClient.isNil(): await node.wakuRendezvousClient.stopWait() + if not node.wakuKademlia.isNil(): + node.wakuKademlia.stop() + node.started = false proc isReady*(node: WakuNode): Future[bool] {.async: (raises: [Exception]).} = From e4e3502aa7874da3bc1bcd1cd2427e229fc4ce98 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Tue, 21 Apr 2026 10:02:14 -0400 Subject: [PATCH 11/19] fix random walk removal --- waku/discovery/waku_kademlia.nim | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index 5798a11f3..f0a9fe252 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -173,16 +173,16 @@ proc new*( ) proc start*(self: WakuKademlia) = - #if self.periodicWalkFut.isNil(): - #self.periodicWalkFut = self.periodicRandomWalk(self.loopInterval) + #[ if self.periodicWalkFut.isNil(): + self.periodicWalkFut = self.periodicRandomWalk(self.loopInterval) ]# if self.periodicLookupFut.isNil(): self.periodicLookupFut = self.periodicLookup(self.loopInterval) proc stop*(self: WakuKademlia) = - if not self.periodicWalkFut.isNil(): + #[ if not self.periodicWalkFut.isNil(): self.periodicWalkFut.cancelSoon() - self.periodicWalkFut = nil + self.periodicWalkFut = nil ]# if not self.periodicLookupFut.isNil(): self.periodicLookupFut.cancelSoon() From e5740c2f127ca37d96497e997f91d8bde10959ba Mon Sep 17 00:00:00 2001 From: SionoiS Date: Thu, 23 Apr 2026 08:52:25 -0400 Subject: [PATCH 12/19] update libp2p & add addr filtering --- waku/discovery/waku_kademlia.nim | 12 +++++------- waku/node/waku_switch.nim | 4 +++- waku/waku_mix/protocol.nim | 6 +----- 3 files changed, 9 insertions(+), 13 deletions(-) diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index f0a9fe252..c80c9a8d7 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -10,8 +10,7 @@ import libp2p/protocols/mix/mix_protocol, libp2p/[peerid, multiaddress, switch], libp2p/extended_peer_record, - libp2p/protocols/[kademlia, kad_disco], - libp2p/protocols/kademlia_discovery/types as kad_types, + libp2p/protocols/[kademlia, service_discovery], libp2p/protocols/service_discovery/types import waku/waku_core, waku/node/peer_manager @@ -22,7 +21,7 @@ logScope: const DefaultKademliaDiscoveryInterval* = chronos.seconds(60) type WakuKademlia* = ref object - protocol*: KademliaDiscovery + protocol*: ServiceDiscovery peerManager: PeerManager loopInterval: Duration #periodicWalkFut: Future[void] @@ -158,12 +157,11 @@ proc new*( if bootstrapNodes.len == 0: debug "creating kademlia discovery as seed node (no bootstrap nodes)" - let kademlia = KademliaDiscovery.new( + let kademlia = ServiceDiscovery.new( switch, bootstrapNodes = bootstrapNodes, - config = KadDHTConfig.new( - validator = kad_types.ExtEntryValidator(), selector = kad_types.ExtEntrySelector() - ), + config = + KadDHTConfig.new(validator = ExtEntryValidator(), selector = ExtEntrySelector()), services = providedServices, xprPublishing = xprPublishing, ) diff --git a/waku/node/waku_switch.nim b/waku/node/waku_switch.nim index 62797a8d8..18bd03a57 100644 --- a/waku/node/waku_switch.nim +++ b/waku/node/waku_switch.nim @@ -16,7 +16,8 @@ import libp2p/nameresolving/nameresolver, libp2p/builders, libp2p/switch, - libp2p/transports/[transport, tcptransport, wstransport] + libp2p/transports/[transport, tcptransport, wstransport], + libp2p/peeraddrpolicy # override nim-libp2p default value (which is also 1) const MaxConnectionsPerPeer* = 1 @@ -100,6 +101,7 @@ proc newWakuSwitch*( .withSignedPeerRecord(sendSignedPeerRecord) .withCircuitRelay(circuitRelay) .withServices(@[hpService]) + .withAddressPolicy(noPrivateAddressPolicy) if peerStoreCapacity.isSome(): b = b.withPeerStore(peerStoreCapacity.get()) diff --git a/waku/waku_mix/protocol.nim b/waku/waku_mix/protocol.nim index 0e0d483e3..fb6b7ef6d 100644 --- a/waku/waku_mix/protocol.nim +++ b/waku/waku_mix/protocol.nim @@ -99,11 +99,7 @@ proc new*( wakuKademlia: wakuKademlia, ) - procCall MixProtocol(mix).init( - localMixNodeInfo, - switch, - delayStrategy = ExponentialDelayStrategy.new(rng = crypto.newRng()), - ) + procCall MixProtocol(mix).init(localMixNodeInfo, switch) return ok(mix) From e0d5c2e331f4843971181c750812130a6093a87c Mon Sep 17 00:00:00 2001 From: SionoiS Date: Thu, 23 Apr 2026 10:54:14 -0400 Subject: [PATCH 13/19] remove addr policy & hole punch service --- waku/discovery/waku_kademlia.nim | 4 +++- waku/node/waku_switch.nim | 6 +++--- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index c80c9a8d7..ae56ba0fa 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -143,7 +143,9 @@ proc periodicLookup( # For testing lets use only one hard-coded service # Same as the advertised one - discard await self.lookup("delivery") + let peers = await self.lookup("delivery") + + debug "lookup complete", peer_found = peers.len proc new*( T: type WakuKademlia, diff --git a/waku/node/waku_switch.nim b/waku/node/waku_switch.nim index 18bd03a57..5d4536a35 100644 --- a/waku/node/waku_switch.nim +++ b/waku/node/waku_switch.nim @@ -99,9 +99,9 @@ proc newWakuSwitch*( .withTcpTransport(transportFlags) .withNameResolver(nameResolver) .withSignedPeerRecord(sendSignedPeerRecord) - .withCircuitRelay(circuitRelay) - .withServices(@[hpService]) - .withAddressPolicy(noPrivateAddressPolicy) + #.withAddressPolicy(publicRoutableAddressPolicy) + #.withCircuitRelay(circuitRelay) + #.withServices(@[hpService]) if peerStoreCapacity.isSome(): b = b.withPeerStore(peerStoreCapacity.get()) From fdff21ce0f113a049774ad5cc31f9c6874e06ded Mon Sep 17 00:00:00 2001 From: SionoiS Date: Tue, 28 Apr 2026 10:30:59 -0400 Subject: [PATCH 14/19] update libp2p & fixes --- waku.nimble | 2 +- waku/factory/builder.nim | 5 +++-- waku/node/peer_manager/peer_manager.nim | 1 + waku/node/waku_node.nim | 3 --- waku/node/waku_switch.nim | 10 +++++----- 5 files changed, 10 insertions(+), 11 deletions(-) diff --git a/waku.nimble b/waku.nimble index 591307c23..7642c50ee 100644 --- a/waku.nimble +++ b/waku.nimble @@ -27,7 +27,7 @@ requires "nim >= 2.2.4", "toml_serialization", "faststreams", # Networking & P2P - "https://github.com/vacp2p/nim-libp2p.git#ff8d51857b4b79a68468e7bcc27b2026cca02996", + "https://github.com/vacp2p/nim-libp2p.git#9b6fedca059f3c054582407be9268e2999c7d05d", "eth", "nat_traversal", "dnsdisc", diff --git a/waku/factory/builder.nim b/waku/factory/builder.nim index 87b0db492..5bd343223 100644 --- a/waku/factory/builder.nim +++ b/waku/factory/builder.nim @@ -14,6 +14,7 @@ import ../discovery/waku_discv5, ../waku_node, ../node/peer_manager, + ../node/waku_switch, ../common/rate_limit/setting, ../common/utils/parse_size_units, ../common/broker/broker_context @@ -189,7 +190,7 @@ proc build*(builder: WakuNodeBuilder): Result[WakuNode, string] = wsAddress = builder.netConfig.get().wsHostAddress, transportFlags = {ServerFlags.ReuseAddr, ServerFlags.TcpNoDelay}, rng = rng, - maxConnections = builder.switchMaxConnections.get(builders.MaxConnections), + maxConnections = builder.switchMaxConnections.get(MaxConnections), wssEnabled = builder.netConfig.get().wssEnabled, secureKeyPath = builder.switchSslSecureKey.get(""), secureCertPath = builder.switchSslSecureCert.get(""), @@ -209,7 +210,7 @@ proc build*(builder: WakuNodeBuilder): Result[WakuNode, string] = maxServicePeers = some(builder.maxServicePeers), colocationLimit = builder.colocationLimit, shardedPeerManagement = builder.shardAware, - maxConnections = builder.switchMaxConnections.get(builders.MaxConnections), + maxConnections = builder.switchMaxConnections.get(MaxConnections), ) var node: WakuNode diff --git a/waku/node/peer_manager/peer_manager.nim b/waku/node/peer_manager/peer_manager.nim index e3eb8d75b..d8bd6e70b 100644 --- a/waku/node/peer_manager/peer_manager.nim +++ b/waku/node/peer_manager/peer_manager.nim @@ -23,6 +23,7 @@ import common/utils/parse_size_units, common/broker/broker_context, node/health_monitor/online_monitor, + node/waku_switch, ], ./peer_store/peer_storage, ./waku_peer_store diff --git a/waku/node/waku_node.nim b/waku/node/waku_node.nim index 85166a4cc..e15153785 100644 --- a/waku/node/waku_node.nim +++ b/waku/node/waku_node.nim @@ -635,9 +635,6 @@ proc stop*(node: WakuNode) {.async.} = not node.wakuPeerExchangeClient.pxLoopHandle.isNil(): await node.wakuPeerExchangeClient.pxLoopHandle.cancelAndWait() - if not node.wakuKademlia.isNil(): - await node.wakuKademlia.stop() - if not node.wakuRendezvousClient.isNil(): await node.wakuRendezvousClient.stopWait() diff --git a/waku/node/waku_switch.nim b/waku/node/waku_switch.nim index 5d4536a35..941c20807 100644 --- a/waku/node/waku_switch.nim +++ b/waku/node/waku_switch.nim @@ -19,7 +19,8 @@ import libp2p/transports/[transport, tcptransport, wstransport], libp2p/peeraddrpolicy -# override nim-libp2p default value (which is also 1) +# override nim-libp2p default values (which are also 50 & 1) +const MaxConnections* = 50 const MaxConnectionsPerPeer* = 1 proc withWsTransport*(b: SwitchBuilder): SwitchBuilder = @@ -67,8 +68,8 @@ proc newWakuSwitch*( inTimeout: Duration = 5.minutes, outTimeout: Duration = 5.minutes, maxConnections = MaxConnections, - maxIn = -1, - maxOut = -1, + maxIn = int.high, + maxOut = int.high, maxConnsPerPeer = MaxConnectionsPerPeer, nameResolver: NameResolver = nil, sendSignedPeerRecord = false, @@ -90,8 +91,7 @@ proc newWakuSwitch*( .new() .withRng(rng) .withMaxConnections(maxConnections) - .withMaxIn(maxIn) - .withMaxOut(maxOut) + .withMaxInOut(maxIn, maxOut) .withMaxConnsPerPeer(maxConnsPerPeer) .withYamux() .withMplex(inTimeout, outTimeout) From 36a4715ca394734e4539449ff827ea7a4c1cd0e4 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Thu, 30 Apr 2026 16:18:09 -0400 Subject: [PATCH 15/19] chat2disco --- apps/chat2disco/chat2disco.nim | 509 ++++++++++++++++++++++++++ apps/chat2disco/config_chat2disco.nim | 202 ++++++++++ apps/chat2disco/nim.cfg | 4 + waku.nimble | 6 + waku/discovery/waku_kademlia.nim | 29 +- 5 files changed, 745 insertions(+), 5 deletions(-) create mode 100644 apps/chat2disco/chat2disco.nim create mode 100644 apps/chat2disco/config_chat2disco.nim create mode 100644 apps/chat2disco/nim.cfg diff --git a/apps/chat2disco/chat2disco.nim b/apps/chat2disco/chat2disco.nim new file mode 100644 index 000000000..26e572590 --- /dev/null +++ b/apps/chat2disco/chat2disco.nim @@ -0,0 +1,509 @@ +## chat2disco is an example of usage of Waku v2 with Kademlia service discovery. +## Users create named chat rooms; the app derives a service ID from the room name, +## advertises via Kademlia, and discovers/connects to other peers with the same service. + +when not (compileOption("threads")): + {.fatal: "Please, compile this program with the --threads:on option!".} + +{.push raises: [].} + +import std/[strformat, strutils, times, options, random, sequtils, tables] +import + confutils, + chronicles, + chronos, + eth/keys, + bearssl, + stew/byteutils, + results, + metrics, + metrics/chronos_httpserver +import + libp2p/[ + switch, + crypto/crypto, + stream/connection, + multiaddress, + peerinfo, + peerid, + protobuf/minprotobuf, + nameresolving/dnsresolver, + extended_peer_record, + ] +import + waku/[ + waku_core, + waku_enr, + discovery/waku_dnsdisc, + discovery/waku_kademlia, + waku_node, + node/waku_metrics, + node/peer_manager, + factory/builder, + common/utils/nat, + waku_relay, + waku_store/common, + ], + ./config_chat2disco + +import libp2p/protocols/pubsub/rpc/messages, libp2p/protocols/pubsub/pubsub +import libp2p/protocols/service_discovery/types + +logScope: + topics = "chat2disco" + +const Help = """ + Commands: /[?|help|create|rooms|switch|nick|exit] + help: Prints this help + create : Create/join a chat room via service discovery + rooms: List joined rooms + switch : Switch active room for sending messages + nick: change nickname + exit: exits chat session +""" + +type + ChatRoom = object + serviceId*: string + contentTopic*: string + discovered*: seq[RemotePeerInfo] + + Chat = ref object + node: WakuNode + transp: StreamTransport + subscribed: bool + started: bool + nick: string + prompt: bool + rooms: Table[string, ChatRoom] + currentRoom: string + + PrivateKey* = crypto.PrivateKey + Topic* = waku_core.PubsubTopic + +##################### +## chat2 protobufs ## +##################### + +type + SelectResult*[T] = Result[T, string] + + Chat2Message* = object + timestamp*: int64 + nick*: string + payload*: seq[byte] + +proc init*(T: type Chat2Message, buffer: seq[byte]): ProtoResult[T] = + var msg = Chat2Message() + let pb = initProtoBuffer(buffer) + + var timestamp: uint64 + discard ?pb.getField(1, timestamp) + msg.timestamp = int64(timestamp) + + discard ?pb.getField(2, msg.nick) + discard ?pb.getField(3, msg.payload) + + ok(msg) + +proc encode*(message: Chat2Message): ProtoBuffer = + var serialised = initProtoBuffer() + + serialised.write(1, uint64(message.timestamp)) + serialised.write(2, message.nick) + serialised.write(3, message.payload) + + return serialised + +proc toString*(message: Chat2Message): string = + let time = message.timestamp.fromUnix().local().format("'<'MMM' 'dd,' 'HH:mm'>'") + return time & " " & message.nick & ": " & string.fromBytes(message.payload) + +##################### + +proc showChatPrompt(c: Chat) = + if not c.prompt: + try: + stdout.write(">> ") + stdout.flushFile() + c.prompt = true + except IOError: + discard + +proc getChatLine(payload: seq[byte]): string = + let pb = Chat2Message.init(payload).valueOr: + return string.fromBytes(payload) + return $pb + +proc readNick(transp: StreamTransport): Future[string] {.async.} = + stdout.write("Choose a nickname >> ") + stdout.flushFile() + return await transp.readLine() + +proc startMetricsServer( + serverIp: IpAddress, serverPort: Port +): Result[MetricsHttpServerRef, string] = + info "Starting metrics HTTP server", serverIp = $serverIp, serverPort = $serverPort + + let server = MetricsHttpServerRef.new($serverIp, serverPort).valueOr: + return err("metrics HTTP server start failed: " & $error) + + try: + waitFor server.start() + except CatchableError: + return err("metrics HTTP server start failed: " & getCurrentExceptionMsg()) + + info "Metrics HTTP server started", serverIp = $serverIp, serverPort = $serverPort + ok(server) + +proc publish(c: Chat, line: string) = + let time = getTime().toUnix() + let chat2pb = + Chat2Message(timestamp: time, nick: c.nick, payload: line.toBytes()).encode() + + let room = + try: + c.rooms[c.currentRoom] + except KeyError: + error "current room not found in rooms table", room = c.currentRoom + return + + var message = WakuMessage( + payload: chat2pb.buffer, + contentTopic: room.contentTopic, + version: 0, + timestamp: getNanosecondTime(time), + ) + + try: + (waitFor c.node.publish(some(DefaultPubsubTopic), message)).isOkOr: + error "failed to publish message", error = error + except CatchableError: + error "caught error publishing message: ", error = getCurrentExceptionMsg() + +# TODO This should read or be subscribe handler subscribe +proc readAndPrint(c: Chat) {.async.} = + while true: + await sleepAsync(100.millis) + +# TODO Implement +proc writeAndPrint(c: Chat) {.async.} = + while true: + showChatPrompt(c) + + let line = await c.transp.readLine() + if line.startsWith("/help") or line.startsWith("/?") or not c.started: + echo Help + continue + elif line.startsWith("/create"): + let roomName = line[7 ..^ 1].strip() + if roomName.len == 0: + echo "Usage: /create " + continue + + if roomName in c.rooms: + echo &"Already in room '{roomName}'. Use /switch {roomName} to make it active." + continue + + let serviceIdStr = "/waku/chat-room/" & roomName & "/1.0.0" + let contentTopic = "/chat2disco/1/" & roomName & "/proto" + + let serviceInfo = ServiceInfo(id: serviceIdStr, data: @[]) + + if not c.node.wakuKademlia.isNil(): + c.node.wakuKademlia.advertiseService(serviceInfo) + echo &"Advertising service: {serviceIdStr}" + + let peers = await c.node.wakuKademlia.lookup(serviceIdStr) + echo &"Discovered {peers.len} peer(s) for room '{roomName}'" + + if peers.len > 0: + await c.node.connectToNodes(peers) + echo "Connected to discovered peers" + + c.rooms[roomName] = ChatRoom( + serviceId: serviceIdStr, contentTopic: contentTopic, discovered: peers + ) + else: + echo "Warning: Kademlia not available. Room created locally only." + c.rooms[roomName] = + ChatRoom(serviceId: serviceIdStr, contentTopic: contentTopic, discovered: @[]) + + c.currentRoom = roomName + echo &"Created/joined room '{roomName}'. Content topic: {contentTopic}" + elif line.startsWith("/rooms"): + if c.rooms.len == 0: + echo "No rooms joined yet. Use /create to create one." + else: + echo "Joined rooms:" + for name, room in c.rooms: + let marker = if name == c.currentRoom: " *" else: "" + echo &" {name} ({room.discovered.len} peers){marker}" + elif line.startsWith("/switch"): + let roomName = line[7 ..^ 1].strip() + if roomName.len == 0: + echo "Usage: /switch " + continue + + if roomName notin c.rooms: + echo &"Room '{roomName}' not found. Use /create {roomName} to create it." + continue + + c.currentRoom = roomName + echo &"Switched to room '{roomName}'" + elif line.startsWith("/nick"): + c.nick = await readNick(c.transp) + echo "You are now known as " & c.nick + elif line.startsWith("/exit"): + echo "quitting..." + + try: + await c.node.stop() + except: + echo "exception happened when stopping: " & getCurrentExceptionMsg() + + quit(QuitSuccess) + else: + if c.started: + if c.rooms.len == 0: + echo "No room active. Use /create first." + else: + c.publish(line) + else: + try: + if line.startsWith("/") and "p2p" in line: + await c.node.connectToNodes(@[line]) + except: + echo &"unable to dial remote peer {line}" + echo getCurrentExceptionMsg() + +proc readWriteLoop(c: Chat) {.async.} = + asyncSpawn c.writeAndPrint() + asyncSpawn c.readAndPrint() + +proc readInput(wfd: AsyncFD) {.thread, raises: [Defect, CatchableError].} = + let transp = fromPipe(wfd) + + while true: + let line = stdin.readLine() + discard waitFor transp.write(line & "\r\n") + +{.pop.} +proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = + let + transp = fromPipe(rfd) + conf = Chat2DiscoConf.load() + nodekey = + if conf.nodekey.isSome(): + conf.nodekey.get() + else: + PrivateKey.random(Secp256k1, rng[]).tryGet() + + # set log level + if conf.logLevel != LogLevel.NONE: + setLogLevel(conf.logLevel) + + let (extIp, extTcpPort, extUdpPort) = setupNat( + conf.nat, + clientId, + Port(uint16(conf.tcpPort) + conf.portsShift), + Port(uint16(conf.udpPort) + conf.portsShift), + ).valueOr: + raise newException(ValueError, "setupNat error " & error) + + var enrBuilder = EnrBuilder.init(nodeKey) + + let record = enrBuilder.build().valueOr: + error "failed to create enr record", error = error + quit(QuitFailure) + + let node = block: + var builder = WakuNodeBuilder.init() + builder.withNodeKey(nodeKey) + builder.withRecord(record) + + builder + .withNetworkConfigurationDetails( + conf.listenAddress, + Port(uint16(conf.tcpPort) + conf.portsShift), + extIp, + extTcpPort, + wsBindPort = Port(uint16(conf.websocketPort) + conf.portsShift), + wsEnabled = conf.websocketSupport, + wssEnabled = conf.websocketSecureSupport, + ) + .tryGet() + builder.build().tryGet() + + if conf.relay: + (await node.mountRelay()).isOkOr: + echo "failed to mount relay: " & error + return + + await node.mountLibp2pPing() + + # Setup kademlia discovery if bootstrap nodes are provided + var providedServices: seq[ServiceInfo] = @[] + + if conf.kadBootstrapNodes.len > 0: + var kadBootstrapPeers: seq[(PeerId, seq[MultiAddress])] + for nodeStr in conf.kadBootstrapNodes: + let (peerId, ma) = parseFullAddress(nodeStr).valueOr: + error "Failed to parse kademlia bootstrap node", node = nodeStr, error = error + continue + kadBootstrapPeers.add((peerId, @[ma])) + + if kadBootstrapPeers.len > 0: + node.wakuKademlia = WakuKademlia.new( + node.switch, node.peerManager, kadBootstrapPeers, providedServices + ) + else: + # Create as seed node (no bootstrap) so we can still advertise services + node.wakuKademlia = + WakuKademlia.new(node.switch, node.peerManager, @[], providedServices) + + await node.start() + + if not node.wakuKademlia.isNil(): + node.wakuKademlia.start() + + let nick = await readNick(transp) + echo "Welcome, " & nick & "!" + + var chat = Chat( + node: node, + transp: transp, + subscribed: true, + started: true, + nick: nick, + prompt: false, + ) + + if conf.staticnodes.len > 0: + echo "Connecting to static peers..." + await node.connectToNodes(conf.staticnodes) + + var dnsDiscoveryUrl = none(string) + + if conf.fleet != Fleet.none: + echo "Connecting to " & $conf.fleet & " fleet using DNS discovery..." + + if conf.fleet == Fleet.test: + dnsDiscoveryUrl = some( + "enrtree://AOGYWMBYOUIMOENHXCHILPKY3ZRFEULMFI4DOM442QSZ73TT2A7VI@test.waku.nodes.status.im" + ) + else: + dnsDiscoveryUrl = some( + "enrtree://AIRVQ5DDA4FFWLRBCHJWUWOO6X6S4ZTZ5B667LQ6AJU6PEYDLRD5O@sandbox.waku.nodes.status.im" + ) + elif conf.dnsDiscoveryUrl != "": + info "Discovering nodes using Waku DNS discovery", url = conf.dnsDiscoveryUrl + dnsDiscoveryUrl = some(conf.dnsDiscoveryUrl) + + var discoveredNodes: seq[RemotePeerInfo] + + if dnsDiscoveryUrl.isSome: + var nameServers: seq[TransportAddress] + for ip in conf.dnsAddrsNameServers: + nameServers.add(initTAddress(ip, Port(53))) + + let dnsResolver = DnsResolver.new(nameServers) + + proc resolver(domain: string): Future[string] {.async, gcsafe.} = + trace "resolving", domain = domain + let resolved = await dnsResolver.resolveTxt(domain) + return resolved[0] + + let wakuDnsDiscovery = WakuDnsDiscovery.init(dnsDiscoveryUrl.get(), resolver) + if wakuDnsDiscovery.isOk: + let discoveredPeers = await wakuDnsDiscovery.get().findPeers() + if discoveredPeers.isOk: + info "Connecting to discovered peers" + discoveredNodes = discoveredPeers.get() + echo "Discovered and connecting to " & $discoveredNodes + waitFor chat.node.connectToNodes(discoveredNodes) + else: + warn "Failed to find peers via DNS discovery", error = discoveredPeers.error + else: + warn "Failed to init Waku DNS discovery", error = wakuDnsDiscovery.error + + let peerInfo = node.switch.peerInfo + let listenStr = $peerInfo.addrs[0] & "/p2p/" & $peerInfo.peerId + echo &"Listening on\n {listenStr}" + + if (conf.storenode != "") or (conf.store == true): + await node.mountStore() + + var storenode: Option[RemotePeerInfo] + + if conf.storenode != "": + let peerInfo = parsePeerInfo(conf.storenode) + if peerInfo.isOk(): + storenode = some(peerInfo.value) + else: + error "Incorrect conf.storenode", error = peerInfo.error + elif discoveredNodes.len > 0: + echo "Store enabled, but no store nodes configured. Choosing one at random from discovered peers" + storenode = some(discoveredNodes[rand(0 .. len(discoveredNodes) - 1)]) + + if storenode.isSome(): + echo "Connecting to storenode: " & $(storenode.get()) + + node.mountStoreClient() + node.peerManager.addServicePeer(storenode.get(), WakuStoreCodec) + + # Subscribe to relay topic + if conf.relay: + proc handler(topic: PubsubTopic, msg: WakuMessage): Future[void] {.async, gcsafe.} = + for roomName, room in chat.rooms: + if msg.contentTopic == room.contentTopic: + let chatLine = getChatLine(msg.payload) + let prefix = + if chat.rooms.len > 1: + "[" & roomName & "] " + else: + "" + try: + echo &"{prefix}{chatLine}" + except ValueError: + echo prefix & chatLine + chat.prompt = false + showChatPrompt(chat) + break + + node.subscribe( + (kind: PubsubSub, topic: DefaultPubsubTopic), WakuRelayHandler(handler) + ).isOkOr: + error "failed to subscribe to pubsub topic", + topic = DefaultPubsubTopic, error = error + + if conf.metricsLogging: + startMetricsLog() + + if conf.metricsServer: + let metricsServer = startMetricsServer( + conf.metricsServerAddress, Port(conf.metricsServerPort + conf.portsShift) + ) + + await chat.readWriteLoop() + + runForever() + +proc main(rng: ref HmacDrbgContext) {.async.} = + let (rfd, wfd) = createAsyncPipe() + if rfd == asyncInvalidPipe or wfd == asyncInvalidPipe: + raise newException(ValueError, "Could not initialize pipe!") + + var thread: Thread[AsyncFD] + thread.createThread(readInput, wfd) + try: + await processInput(rfd, rng) + except ConfigurationError as e: + raise e + +when isMainModule: + let rng = crypto.newRng() + try: + waitFor(main(rng)) + except CatchableError as e: + raise e diff --git a/apps/chat2disco/config_chat2disco.nim b/apps/chat2disco/config_chat2disco.nim new file mode 100644 index 000000000..c703641b7 --- /dev/null +++ b/apps/chat2disco/config_chat2disco.nim @@ -0,0 +1,202 @@ +import + chronicles, + chronos, + confutils, + confutils/defs, + confutils/std/net, + eth/keys, + libp2p/crypto/crypto, + libp2p/crypto/secp, + nimcrypto/utils, + std/strutils +import waku/waku_core + +const + defaultMetricsAddress* = parseIpAddress("127.0.0.1") + defaultDnsResolver1* = parseIpAddress("1.1.1.1") + defaultDnsResolver2* = parseIpAddress("1.0.0.1") + +type + Fleet* = enum + none + prod + test + + Chat2DiscoConf* = object ## General node config + logLevel* {. + desc: "Sets the log level.", defaultValue: LogLevel.INFO, name: "log-level" + .}: LogLevel + + nodekey* {.desc: "P2P node private key as 64 char hex string.", name: "nodekey".}: + Option[crypto.PrivateKey] + + listenAddress* {. + defaultValue: defaultListenAddress(config), + desc: "Listening address for the LibP2P traffic.", + name: "listen-address" + .}: IpAddress + + tcpPort* {.desc: "TCP listening port.", defaultValue: 60000, name: "tcp-port".}: + Port + + udpPort* {.desc: "UDP listening port.", defaultValue: 60000, name: "udp-port".}: + Port + + portsShift* {. + desc: "Add a shift to all port numbers.", defaultValue: 0, name: "ports-shift" + .}: uint16 + + nat* {. + desc: + "Specify method to use for determining public address. " & + "Must be one of: any, none, upnp, pmp, extip:.", + defaultValue: "any" + .}: string + + ## Relay config + relay* {. + desc: "Enable relay protocol: true|false", defaultValue: true, name: "relay" + .}: bool + + staticnodes* {. + desc: "Peer multiaddr to directly connect with. Argument may be repeated.", + name: "staticnode" + .}: seq[string] + + keepAlive* {. + desc: "Enable keep-alive for idle connections: true|false", + defaultValue: false, + name: "keep-alive" + .}: bool + + clusterId* {. + desc: + "Cluster id that the node is running in. Node in a different cluster id is disconnected.", + defaultValue: 0, + name: "cluster-id" + .}: uint16 + + shards* {. + desc: + "Shards index to subscribe to [0..NUM_SHARDS_IN_NETWORK-1]. Argument may be repeated.", + defaultValue: @[uint16(0)], + name: "shard" + .}: seq[uint16] + + ## Store config + store* {. + desc: "Enable store protocol: true|false", defaultValue: true, name: "store" + .}: bool + + storenode* {. + desc: "Peer multiaddr to query for storage.", defaultValue: "", name: "storenode" + .}: string + + ## Metrics config + metricsServer* {. + desc: "Enable the metrics server: true|false", + defaultValue: false, + name: "metrics-server" + .}: bool + + metricsServerAddress* {. + desc: "Listening address of the metrics server.", + defaultValue: defaultMetricsAddress, + name: "metrics-server-address" + .}: IpAddress + + metricsServerPort* {. + desc: "Listening HTTP port of the metrics server.", + defaultValue: 8008, + name: "metrics-server-port" + .}: uint16 + + metricsLogging* {. + desc: "Enable metrics logging: true|false", + defaultValue: true, + name: "metrics-logging" + .}: bool + + ## DNS discovery config + dnsDiscoveryUrl* {. + desc: "URL for DNS node list in format 'enrtree://@'", + defaultValue: "", + name: "dns-discovery-url" + .}: string + + dnsAddrsNameServers* {. + desc: + "DNS name server IPs to query for DNS multiaddrs resolution. Argument may be repeated.", + defaultValue: @[defaultDnsResolver1, defaultDnsResolver2], + name: "dns-addrs-name-server" + .}: seq[IpAddress] + + ## Chat2 configuration + fleet* {. + desc: + "Select the fleet to connect to. This sets the DNS discovery URL to the selected fleet.", + defaultValue: Fleet.prod, + name: "fleet" + .}: Fleet + + contentTopic* {. + desc: "Content topic for chat messages.", + defaultValue: "/chat2disco/1/default/proto", + name: "content-topic" + .}: string + + ## Websocket Configuration + websocketSupport* {. + desc: "Enable websocket: true|false", + defaultValue: false, + name: "websocket-support" + .}: bool + + websocketPort* {. + desc: "WebSocket listening port.", defaultValue: 8000, name: "websocket-port" + .}: Port + + websocketSecureSupport* {. + desc: "WebSocket Secure Support.", + defaultValue: false, + name: "websocket-secure-support" + .}: bool + + ## Kademlia Discovery config + kadBootstrapNodes* {. + desc: + "Peer multiaddr for kademlia discovery bootstrap node (must include /p2p/). Argument may be repeated.", + name: "kad-bootstrap-node" + .}: seq[string] + +# NOTE: Keys are different in nim-libp2p +proc parseCmdArg*(T: type crypto.PrivateKey, p: string): T = + try: + let key = SkPrivateKey.init(utils.fromHex(p)).tryGet() + result = crypto.PrivateKey(scheme: Secp256k1, skkey: key) + except CatchableError as e: + raise newException(ValueError, "Invalid private key") + +proc completeCmdArg*(T: type crypto.PrivateKey, val: string): seq[string] = + return @[] + +proc parseCmdArg*(T: type IpAddress, p: string): T = + try: + result = parseIpAddress(p) + except CatchableError as e: + raise newException(ValueError, "Invalid IP address") + +proc completeCmdArg*(T: type IpAddress, val: string): seq[string] = + return @[] + +proc parseCmdArg*(T: type Port, p: string): T = + try: + result = Port(parseInt(p)) + except CatchableError as e: + raise newException(ValueError, "Invalid Port number") + +proc completeCmdArg*(T: type Port, val: string): seq[string] = + return @[] + +func defaultListenAddress*(conf: Chat2DiscoConf): IpAddress = + (static parseIpAddress("0.0.0.0")) diff --git a/apps/chat2disco/nim.cfg b/apps/chat2disco/nim.cfg new file mode 100644 index 000000000..2231f2ebe --- /dev/null +++ b/apps/chat2disco/nim.cfg @@ -0,0 +1,4 @@ +-d:chronicles_line_numbers +-d:chronicles_runtime_filtering:on +-d:discv5_protocol_id:d5waku +path = "../.." diff --git a/waku.nimble b/waku.nimble index 7642c50ee..00be69426 100644 --- a/waku.nimble +++ b/waku.nimble @@ -432,6 +432,12 @@ task chat2mix, "Build example Waku chat mix usage": "-d:chronicles_sinks=textlines[file] -d:chronicles_log_level=TRACE " # -d:ssl - cause unlisted exception error in libp2p/utility... +task chat2disco, "Build example Waku chat with service discovery": + let name = "chat2disco" + buildBinary name, + "apps/chat2disco/", + "-d:chronicles_sinks=textlines[file] -d:chronicles_log_level=DEBUG " + task chat2bridge, "Build chat2bridge": let name = "chat2bridge" buildBinary name, "apps/chat2bridge/" diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index ae56ba0fa..d07632e7b 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -26,6 +26,7 @@ type WakuKademlia* = ref object loopInterval: Duration #periodicWalkFut: Future[void] periodicLookupFut: Future[void] + discoveredServices*: seq[string] proc toRemotePeerInfo(record: ExtendedPeerRecord): Option[RemotePeerInfo] = debug "processing kademlia record", @@ -123,6 +124,15 @@ proc lookup*( return peerInfos +proc registerLookupService*(self: WakuKademlia, serviceId: string) = + if serviceId notin self.discoveredServices: + self.protocol.startDiscovering(serviceId) + self.discoveredServices.add(serviceId) + +proc advertiseService*(self: WakuKademlia, service: ServiceInfo) = + self.protocol.addProvidedService(service) + self.registerLookupService(service.id) + #[ proc periodicRandomWalk( self: WakuKademlia, interval: Duration ) {.async: (raises: [CancelledError]).} = @@ -141,11 +151,13 @@ proc periodicLookup( while true: await sleepAsync(interval) - # For testing lets use only one hard-coded service - # Same as the advertised one - let peers = await self.lookup("delivery") + let services = self.discoveredServices + if services.len == 0: + continue - debug "lookup complete", peer_found = peers.len + for serviceId in services: + let peers = await self.lookup(serviceId) + debug "periodic lookup complete", service = serviceId, peerCount = peers.len proc new*( T: type WakuKademlia, @@ -168,8 +180,15 @@ proc new*( xprPublishing = xprPublishing, ) + var initialServices: seq[string] + for svc in providedServices: + initialServices.add(svc.id) + return WakuKademlia( - protocol: kademlia, peerManager: peerManager, loopInterval: loopInterval + protocol: kademlia, + peerManager: peerManager, + loopInterval: loopInterval, + discoveredServices: initialServices, ) proc start*(self: WakuKademlia) = From 8ef769e4fd4afa2e13287f76a73109cfbfd7c3a0 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Fri, 1 May 2026 09:40:41 -0400 Subject: [PATCH 16/19] makefile chat2disco update --- Makefile | 4 + apps/chat2disco/chat2disco.nim | 105 ++++---------------------- apps/chat2disco/config_chat2disco.nim | 42 ----------- config.nims | 2 +- waku.nimble | 6 +- waku/discovery/waku_kademlia.nim | 6 +- 6 files changed, 27 insertions(+), 138 deletions(-) diff --git a/Makefile b/Makefile index be9e14027..2740657ad 100644 --- a/Makefile +++ b/Makefile @@ -240,6 +240,10 @@ chat2mix: | $(NIMBLEDEPS_STAMP) build deps librln echo -e $(BUILD_MSG) "build/$@" && \ nimble chat2mix +chat2disco: | $(NIMBLEDEPS_STAMP) build deps librln + echo -e $(BUILD_MSG) "build/$@" && \ + nimble chat2disco + rln-db-inspector: | $(NIMBLEDEPS_STAMP) build deps librln echo -e $(BUILD_MSG) "build/$@" && \ nimble rln_db_inspector diff --git a/apps/chat2disco/chat2disco.nim b/apps/chat2disco/chat2disco.nim index 26e572590..be2f14cff 100644 --- a/apps/chat2disco/chat2disco.nim +++ b/apps/chat2disco/chat2disco.nim @@ -7,7 +7,7 @@ when not (compileOption("threads")): {.push raises: [].} -import std/[strformat, strutils, times, options, random, sequtils, tables] +import std/[strformat, strutils, times, options, sequtils, tables] import confutils, chronicles, @@ -27,14 +27,12 @@ import peerinfo, peerid, protobuf/minprotobuf, - nameresolving/dnsresolver, extended_peer_record, ] import waku/[ waku_core, waku_enr, - discovery/waku_dnsdisc, discovery/waku_kademlia, waku_node, node/waku_metrics, @@ -42,7 +40,6 @@ import factory/builder, common/utils/nat, waku_relay, - waku_store/common, ], ./config_chat2disco @@ -314,7 +311,7 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = var enrBuilder = EnrBuilder.init(nodeKey) let record = enrBuilder.build().valueOr: - error "failed to create enr record", error = error + error "failed to create enr record", error quit(QuitFailure) let node = block: @@ -337,36 +334,31 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = if conf.relay: (await node.mountRelay()).isOkOr: - echo "failed to mount relay: " & error - return + error "failed to mount relay", error + quit(QuitFailure) await node.mountLibp2pPing() - # Setup kademlia discovery if bootstrap nodes are provided - var providedServices: seq[ServiceInfo] = @[] - + var kadBootstrapPeers: seq[(PeerId, seq[MultiAddress])] = @[] if conf.kadBootstrapNodes.len > 0: - var kadBootstrapPeers: seq[(PeerId, seq[MultiAddress])] for nodeStr in conf.kadBootstrapNodes: let (peerId, ma) = parseFullAddress(nodeStr).valueOr: error "Failed to parse kademlia bootstrap node", node = nodeStr, error = error continue kadBootstrapPeers.add((peerId, @[ma])) - if kadBootstrapPeers.len > 0: - node.wakuKademlia = WakuKademlia.new( - node.switch, node.peerManager, kadBootstrapPeers, providedServices - ) - else: - # Create as seed node (no bootstrap) so we can still advertise services - node.wakuKademlia = - WakuKademlia.new(node.switch, node.peerManager, @[], providedServices) + node.wakuKademlia = WakuKademlia.new(node.switch, node.peerManager, kadBootstrapPeers) + let catchRes = catch: + node.switch.mount(node.wakuKademlia.protocol) + + if catchRes.isErr(): + error "failed to mount kademlia discovery", error = catchRes.error.msg + quit(QuitFailure) + + # node start include kademlia await node.start() - if not node.wakuKademlia.isNil(): - node.wakuKademlia.start() - let nick = await readNick(transp) echo "Welcome, " & nick & "!" @@ -379,79 +371,10 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = prompt: false, ) - if conf.staticnodes.len > 0: - echo "Connecting to static peers..." - await node.connectToNodes(conf.staticnodes) - - var dnsDiscoveryUrl = none(string) - - if conf.fleet != Fleet.none: - echo "Connecting to " & $conf.fleet & " fleet using DNS discovery..." - - if conf.fleet == Fleet.test: - dnsDiscoveryUrl = some( - "enrtree://AOGYWMBYOUIMOENHXCHILPKY3ZRFEULMFI4DOM442QSZ73TT2A7VI@test.waku.nodes.status.im" - ) - else: - dnsDiscoveryUrl = some( - "enrtree://AIRVQ5DDA4FFWLRBCHJWUWOO6X6S4ZTZ5B667LQ6AJU6PEYDLRD5O@sandbox.waku.nodes.status.im" - ) - elif conf.dnsDiscoveryUrl != "": - info "Discovering nodes using Waku DNS discovery", url = conf.dnsDiscoveryUrl - dnsDiscoveryUrl = some(conf.dnsDiscoveryUrl) - - var discoveredNodes: seq[RemotePeerInfo] - - if dnsDiscoveryUrl.isSome: - var nameServers: seq[TransportAddress] - for ip in conf.dnsAddrsNameServers: - nameServers.add(initTAddress(ip, Port(53))) - - let dnsResolver = DnsResolver.new(nameServers) - - proc resolver(domain: string): Future[string] {.async, gcsafe.} = - trace "resolving", domain = domain - let resolved = await dnsResolver.resolveTxt(domain) - return resolved[0] - - let wakuDnsDiscovery = WakuDnsDiscovery.init(dnsDiscoveryUrl.get(), resolver) - if wakuDnsDiscovery.isOk: - let discoveredPeers = await wakuDnsDiscovery.get().findPeers() - if discoveredPeers.isOk: - info "Connecting to discovered peers" - discoveredNodes = discoveredPeers.get() - echo "Discovered and connecting to " & $discoveredNodes - waitFor chat.node.connectToNodes(discoveredNodes) - else: - warn "Failed to find peers via DNS discovery", error = discoveredPeers.error - else: - warn "Failed to init Waku DNS discovery", error = wakuDnsDiscovery.error - let peerInfo = node.switch.peerInfo let listenStr = $peerInfo.addrs[0] & "/p2p/" & $peerInfo.peerId echo &"Listening on\n {listenStr}" - if (conf.storenode != "") or (conf.store == true): - await node.mountStore() - - var storenode: Option[RemotePeerInfo] - - if conf.storenode != "": - let peerInfo = parsePeerInfo(conf.storenode) - if peerInfo.isOk(): - storenode = some(peerInfo.value) - else: - error "Incorrect conf.storenode", error = peerInfo.error - elif discoveredNodes.len > 0: - echo "Store enabled, but no store nodes configured. Choosing one at random from discovered peers" - storenode = some(discoveredNodes[rand(0 .. len(discoveredNodes) - 1)]) - - if storenode.isSome(): - echo "Connecting to storenode: " & $(storenode.get()) - - node.mountStoreClient() - node.peerManager.addServicePeer(storenode.get(), WakuStoreCodec) - # Subscribe to relay topic if conf.relay: proc handler(topic: PubsubTopic, msg: WakuMessage): Future[void] {.async, gcsafe.} = diff --git a/apps/chat2disco/config_chat2disco.nim b/apps/chat2disco/config_chat2disco.nim index c703641b7..86b505bd8 100644 --- a/apps/chat2disco/config_chat2disco.nim +++ b/apps/chat2disco/config_chat2disco.nim @@ -13,15 +13,8 @@ import waku/waku_core const defaultMetricsAddress* = parseIpAddress("127.0.0.1") - defaultDnsResolver1* = parseIpAddress("1.1.1.1") - defaultDnsResolver2* = parseIpAddress("1.0.0.1") type - Fleet* = enum - none - prod - test - Chat2DiscoConf* = object ## General node config logLevel* {. desc: "Sets the log level.", defaultValue: LogLevel.INFO, name: "log-level" @@ -58,11 +51,6 @@ type desc: "Enable relay protocol: true|false", defaultValue: true, name: "relay" .}: bool - staticnodes* {. - desc: "Peer multiaddr to directly connect with. Argument may be repeated.", - name: "staticnode" - .}: seq[string] - keepAlive* {. desc: "Enable keep-alive for idle connections: true|false", defaultValue: false, @@ -83,15 +71,6 @@ type name: "shard" .}: seq[uint16] - ## Store config - store* {. - desc: "Enable store protocol: true|false", defaultValue: true, name: "store" - .}: bool - - storenode* {. - desc: "Peer multiaddr to query for storage.", defaultValue: "", name: "storenode" - .}: string - ## Metrics config metricsServer* {. desc: "Enable the metrics server: true|false", @@ -117,28 +96,7 @@ type name: "metrics-logging" .}: bool - ## DNS discovery config - dnsDiscoveryUrl* {. - desc: "URL for DNS node list in format 'enrtree://@'", - defaultValue: "", - name: "dns-discovery-url" - .}: string - - dnsAddrsNameServers* {. - desc: - "DNS name server IPs to query for DNS multiaddrs resolution. Argument may be repeated.", - defaultValue: @[defaultDnsResolver1, defaultDnsResolver2], - name: "dns-addrs-name-server" - .}: seq[IpAddress] - ## Chat2 configuration - fleet* {. - desc: - "Select the fleet to connect to. This sets the DNS discovery URL to the selected fleet.", - defaultValue: Fleet.prod, - name: "fleet" - .}: Fleet - contentTopic* {. desc: "Content topic for chat messages.", defaultValue: "/chat2disco/1/default/proto", diff --git a/config.nims b/config.nims index 0a61a086d..796716d3b 100644 --- a/config.nims +++ b/config.nims @@ -120,7 +120,7 @@ if defined(android): switch("passL", "--sysroot=" & sysRoot) switch("cincludes", sysRoot & "/usr/include/") # begin Nimble config (version 2) +--noNimblePath when withDir(thisDir(), system.fileExists("nimble.paths")): - --noNimblePath include "nimble.paths" # end Nimble config diff --git a/waku.nimble b/waku.nimble index 00be69426..bd9a442ed 100644 --- a/waku.nimble +++ b/waku.nimble @@ -433,10 +433,14 @@ task chat2mix, "Build example Waku chat mix usage": # -d:ssl - cause unlisted exception error in libp2p/utility... task chat2disco, "Build example Waku chat with service discovery": + # NOTE For debugging, set debug level. For chat usage we want minimal log + # output to STDOUT. Can be fixed by redirecting logs to file (e.g.) + #buildBinary name, "examples/", "-d:chronicles_log_level=WARN" + let name = "chat2disco" buildBinary name, "apps/chat2disco/", - "-d:chronicles_sinks=textlines[file] -d:chronicles_log_level=DEBUG " + "-d:chronicles_sinks=textlines -d:chronicles_log_level=DEBUG " task chat2bridge, "Build chat2bridge": let name = "chat2bridge" diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index d07632e7b..8c3caa026 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -126,7 +126,7 @@ proc lookup*( proc registerLookupService*(self: WakuKademlia, serviceId: string) = if serviceId notin self.discoveredServices: - self.protocol.startDiscovering(serviceId) + discard self.protocol.startDiscovering(serviceId) self.discoveredServices.add(serviceId) proc advertiseService*(self: WakuKademlia, service: ServiceInfo) = @@ -163,8 +163,8 @@ proc new*( T: type WakuKademlia, switch: Switch, peerManager: PeerManager, - bootstrapNodes: seq[(PeerId, seq[MultiAddress])], - providedServices: var seq[ServiceInfo], + bootstrapNodes: seq[(PeerId, seq[MultiAddress])] = @[], + providedServices: seq[ServiceInfo] = @[], loopInterval: Duration = DefaultKademliaDiscoveryInterval, xprPublishing: bool = false, ): T = From 648ddd194cd9629c62f75974d0b64edc1b021f58 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Mon, 4 May 2026 10:03:09 -0400 Subject: [PATCH 17/19] latest libp2p master & disable bootstrapping --- apps/chat2disco/chat2disco.nim | 8 +- apps/chat2disco/config_chat2disco.nim | 186 +++++++++++++------------- waku.nimble | 2 +- waku/discovery/waku_kademlia.nim | 10 +- waku/node/waku_switch.nim | 12 +- 5 files changed, 112 insertions(+), 106 deletions(-) diff --git a/apps/chat2disco/chat2disco.nim b/apps/chat2disco/chat2disco.nim index be2f14cff..dbe7b99cc 100644 --- a/apps/chat2disco/chat2disco.nim +++ b/apps/chat2disco/chat2disco.nim @@ -347,7 +347,13 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = continue kadBootstrapPeers.add((peerId, @[ma])) - node.wakuKademlia = WakuKademlia.new(node.switch, node.peerManager, kadBootstrapPeers) + node.wakuKademlia = WakuKademlia.new( + switch = node.switch, + peerManager = node.peerManager, + bootstrapNodes = kadBootstrapPeers, + xprPublishing = false, + disableBootstrapping = true, + ) let catchRes = catch: node.switch.mount(node.wakuKademlia.protocol) diff --git a/apps/chat2disco/config_chat2disco.nim b/apps/chat2disco/config_chat2disco.nim index 86b505bd8..c7c459133 100644 --- a/apps/chat2disco/config_chat2disco.nim +++ b/apps/chat2disco/config_chat2disco.nim @@ -11,121 +11,117 @@ import std/strutils import waku/waku_core -const - defaultMetricsAddress* = parseIpAddress("127.0.0.1") +const defaultMetricsAddress* = parseIpAddress("127.0.0.1") -type - Chat2DiscoConf* = object ## General node config - logLevel* {. - desc: "Sets the log level.", defaultValue: LogLevel.INFO, name: "log-level" - .}: LogLevel +type Chat2DiscoConf* = object ## General node config + logLevel* {. + desc: "Sets the log level.", defaultValue: LogLevel.INFO, name: "log-level" + .}: LogLevel - nodekey* {.desc: "P2P node private key as 64 char hex string.", name: "nodekey".}: - Option[crypto.PrivateKey] + nodekey* {.desc: "P2P node private key as 64 char hex string.", name: "nodekey".}: + Option[crypto.PrivateKey] - listenAddress* {. - defaultValue: defaultListenAddress(config), - desc: "Listening address for the LibP2P traffic.", - name: "listen-address" - .}: IpAddress + listenAddress* {. + defaultValue: defaultListenAddress(config), + desc: "Listening address for the LibP2P traffic.", + name: "listen-address" + .}: IpAddress - tcpPort* {.desc: "TCP listening port.", defaultValue: 60000, name: "tcp-port".}: - Port + tcpPort* {.desc: "TCP listening port.", defaultValue: 60000, name: "tcp-port".}: Port - udpPort* {.desc: "UDP listening port.", defaultValue: 60000, name: "udp-port".}: - Port + udpPort* {.desc: "UDP listening port.", defaultValue: 60000, name: "udp-port".}: Port - portsShift* {. - desc: "Add a shift to all port numbers.", defaultValue: 0, name: "ports-shift" - .}: uint16 + portsShift* {. + desc: "Add a shift to all port numbers.", defaultValue: 0, name: "ports-shift" + .}: uint16 - nat* {. - desc: - "Specify method to use for determining public address. " & - "Must be one of: any, none, upnp, pmp, extip:.", - defaultValue: "any" - .}: string + nat* {. + desc: + "Specify method to use for determining public address. " & + "Must be one of: any, none, upnp, pmp, extip:.", + defaultValue: "any" + .}: string - ## Relay config - relay* {. - desc: "Enable relay protocol: true|false", defaultValue: true, name: "relay" - .}: bool + ## Relay config + relay* {. + desc: "Enable relay protocol: true|false", defaultValue: true, name: "relay" + .}: bool - keepAlive* {. - desc: "Enable keep-alive for idle connections: true|false", - defaultValue: false, - name: "keep-alive" - .}: bool + keepAlive* {. + desc: "Enable keep-alive for idle connections: true|false", + defaultValue: false, + name: "keep-alive" + .}: bool - clusterId* {. - desc: - "Cluster id that the node is running in. Node in a different cluster id is disconnected.", - defaultValue: 0, - name: "cluster-id" - .}: uint16 + clusterId* {. + desc: + "Cluster id that the node is running in. Node in a different cluster id is disconnected.", + defaultValue: 0, + name: "cluster-id" + .}: uint16 - shards* {. - desc: - "Shards index to subscribe to [0..NUM_SHARDS_IN_NETWORK-1]. Argument may be repeated.", - defaultValue: @[uint16(0)], - name: "shard" - .}: seq[uint16] + shards* {. + desc: + "Shards index to subscribe to [0..NUM_SHARDS_IN_NETWORK-1]. Argument may be repeated.", + defaultValue: @[uint16(0)], + name: "shard" + .}: seq[uint16] - ## Metrics config - metricsServer* {. - desc: "Enable the metrics server: true|false", - defaultValue: false, - name: "metrics-server" - .}: bool + ## Metrics config + metricsServer* {. + desc: "Enable the metrics server: true|false", + defaultValue: false, + name: "metrics-server" + .}: bool - metricsServerAddress* {. - desc: "Listening address of the metrics server.", - defaultValue: defaultMetricsAddress, - name: "metrics-server-address" - .}: IpAddress + metricsServerAddress* {. + desc: "Listening address of the metrics server.", + defaultValue: defaultMetricsAddress, + name: "metrics-server-address" + .}: IpAddress - metricsServerPort* {. - desc: "Listening HTTP port of the metrics server.", - defaultValue: 8008, - name: "metrics-server-port" - .}: uint16 + metricsServerPort* {. + desc: "Listening HTTP port of the metrics server.", + defaultValue: 8008, + name: "metrics-server-port" + .}: uint16 - metricsLogging* {. - desc: "Enable metrics logging: true|false", - defaultValue: true, - name: "metrics-logging" - .}: bool + metricsLogging* {. + desc: "Enable metrics logging: true|false", + defaultValue: true, + name: "metrics-logging" + .}: bool - ## Chat2 configuration - contentTopic* {. - desc: "Content topic for chat messages.", - defaultValue: "/chat2disco/1/default/proto", - name: "content-topic" - .}: string + ## Chat2 configuration + contentTopic* {. + desc: "Content topic for chat messages.", + defaultValue: "/chat2disco/1/default/proto", + name: "content-topic" + .}: string - ## Websocket Configuration - websocketSupport* {. - desc: "Enable websocket: true|false", - defaultValue: false, - name: "websocket-support" - .}: bool + ## Websocket Configuration + websocketSupport* {. + desc: "Enable websocket: true|false", + defaultValue: false, + name: "websocket-support" + .}: bool - websocketPort* {. - desc: "WebSocket listening port.", defaultValue: 8000, name: "websocket-port" - .}: Port + websocketPort* {. + desc: "WebSocket listening port.", defaultValue: 8000, name: "websocket-port" + .}: Port - websocketSecureSupport* {. - desc: "WebSocket Secure Support.", - defaultValue: false, - name: "websocket-secure-support" - .}: bool + websocketSecureSupport* {. + desc: "WebSocket Secure Support.", + defaultValue: false, + name: "websocket-secure-support" + .}: bool - ## Kademlia Discovery config - kadBootstrapNodes* {. - desc: - "Peer multiaddr for kademlia discovery bootstrap node (must include /p2p/). Argument may be repeated.", - name: "kad-bootstrap-node" - .}: seq[string] + ## Kademlia Discovery config + kadBootstrapNodes* {. + desc: + "Peer multiaddr for kademlia discovery bootstrap node (must include /p2p/). Argument may be repeated.", + name: "kad-bootstrap-node" + .}: seq[string] # NOTE: Keys are different in nim-libp2p proc parseCmdArg*(T: type crypto.PrivateKey, p: string): T = diff --git a/waku.nimble b/waku.nimble index bd9a442ed..f18e8d1a3 100644 --- a/waku.nimble +++ b/waku.nimble @@ -27,7 +27,7 @@ requires "nim >= 2.2.4", "toml_serialization", "faststreams", # Networking & P2P - "https://github.com/vacp2p/nim-libp2p.git#9b6fedca059f3c054582407be9268e2999c7d05d", + "https://github.com/vacp2p/nim-libp2p.git#df777fc66cc100191dbefd3c222a4472b4d3b924", "eth", "nat_traversal", "dnsdisc", diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index 8c3caa026..d1e05182c 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -166,7 +166,8 @@ proc new*( bootstrapNodes: seq[(PeerId, seq[MultiAddress])] = @[], providedServices: seq[ServiceInfo] = @[], loopInterval: Duration = DefaultKademliaDiscoveryInterval, - xprPublishing: bool = false, + xprPublishing: bool = true, + disableBootstrapping: bool = false, ): T = if bootstrapNodes.len == 0: debug "creating kademlia discovery as seed node (no bootstrap nodes)" @@ -174,8 +175,11 @@ proc new*( let kademlia = ServiceDiscovery.new( switch, bootstrapNodes = bootstrapNodes, - config = - KadDHTConfig.new(validator = ExtEntryValidator(), selector = ExtEntrySelector()), + config = KadDHTConfig.new( + validator = ExtEntryValidator(), + selector = ExtEntrySelector(), + disableBootstrapping = disableBootstrapping, + ), services = providedServices, xprPublishing = xprPublishing, ) diff --git a/waku/node/waku_switch.nim b/waku/node/waku_switch.nim index 941c20807..e658bd0e4 100644 --- a/waku/node/waku_switch.nim +++ b/waku/node/waku_switch.nim @@ -23,11 +23,11 @@ import const MaxConnections* = 50 const MaxConnectionsPerPeer* = 1 -proc withWsTransport*(b: SwitchBuilder): SwitchBuilder = +#[ proc withWsTransport*(b: SwitchBuilder): SwitchBuilder = b.withTransport( proc(upgr: Upgrade, privateKey: crypto.PrivateKey): Transport = WsTransport.new(upgr) - ) + ) ]# proc getSecureKey(path: string): TLSPrivateKey {.raises: [Defect, IOError].} = trace "Key path is.", path = path @@ -47,7 +47,7 @@ proc getSecureCert(path: string): TLSCertificate {.raises: [Defect, IOError].} = except TLSStreamProtocolError as exc: info "exception raised from getSecureCert", err = exc.msg -proc withWssTransport*( +#[ proc withWssTransport*( b: SwitchBuilder, secureKeyPath: string, secureCertPath: string ): SwitchBuilder {.raises: [Defect, IOError].} = let key: TLSPrivateKey = getSecureKey(secureKeyPath) @@ -56,7 +56,7 @@ proc withWssTransport*( tlsPrivateKey = key, tlsCertificate = cert, {TLSFlags.NoVerifyHost, TLSFlags.NoVerifyServerName}, # THIS IS INSECURE, NO? - ) + ) ]# proc newWakuSwitch*( privKey = none(crypto.PrivateKey), @@ -115,10 +115,10 @@ proc newWakuSwitch*( if wsAddress.isSome(): b = b.withAddresses(@[wsAddress.get(), address]) - if wssEnabled: + #[ if wssEnabled: b = b.withWssTransport(secureKeyPath, secureCertPath) else: - b = b.withWsTransport() + b = b.withWsTransport() ]# else: b = b.withAddress(address) From f94efda2e3b0c992da4025651c6ddaddb2293159 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Mon, 4 May 2026 10:57:45 -0400 Subject: [PATCH 18/19] change disco param for local testing --- waku/discovery/waku_kademlia.nim | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index d1e05182c..f88430a40 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -29,12 +29,6 @@ type WakuKademlia* = ref object discoveredServices*: seq[string] proc toRemotePeerInfo(record: ExtendedPeerRecord): Option[RemotePeerInfo] = - debug "processing kademlia record", - peerId = record.peerId, - numAddresses = record.addresses.len, - numServices = record.services.len, - serviceIds = record.services.mapIt(it.id) - if record.addresses.len == 0: trace "kademlia record missing addresses", peerId = record.peerId return none(RemotePeerInfo) @@ -180,6 +174,9 @@ proc new*( selector = ExtEntrySelector(), disableBootstrapping = disableBootstrapping, ), + # change from defaults for local testing + discoConfig = + ServiceDiscoveryConfig.new(advertExpiry = 60.secs, ipSimCoefficient = 0.0), services = providedServices, xprPublishing = xprPublishing, ) From 5ec18fb4735a822c8f39e1ccb96415895bdb6281 Mon Sep 17 00:00:00 2001 From: SionoiS Date: Thu, 7 May 2026 14:43:12 -0400 Subject: [PATCH 19/19] update to latest libp2p --- apps/chat2/chat2.nim | 8 +- apps/chat2disco/chat2disco.nim | 8 +- apps/chat2mix/chat2mix.nim | 8 +- apps/networkmonitor/networkmonitor.nim | 2 +- apps/wakucanary/wakucanary.nim | 4 +- config.nims | 3 +- examples/filter_subscriber.nim | 4 +- .../lightpush_mix/lightpush_publisher_mix.nim | 8 +- examples/lightpush_publisher.nim | 4 +- examples/publisher.nim | 4 +- examples/subscriber.nim | 4 +- nimble.lock | 607 ------------------ tests/node/test_wakunode_filter.nim | 4 +- tests/node/test_wakunode_relay_rln.nim | 8 +- tests/test_helpers.nim | 12 +- tests/test_waku_dnsdisc.nim | 2 +- tests/test_waku_keystore.nim | 40 +- tests/test_waku_keystore_keyfile.nim | 20 +- tests/test_waku_noise.nim | 178 ++--- tests/test_waku_noise_sessions.nim | 38 +- tests/testlib/common.nim | 12 +- tests/testlib/wakucore.nim | 6 +- tests/waku_discv5/test_waku_discv5.nim | 10 +- tests/waku_rln_relay/utils_onchain.nim | 4 +- tests/wakunode_rest/test_rest_cors.nim | 2 +- tests/wakunode_rest/test_rest_debug.nim | 2 +- tests/wakunode_rest/test_rest_health.nim | 2 +- waku.nimble | 3 +- waku/api/types.nim | 4 +- waku/discovery/autonat_service.nim | 4 +- waku/discovery/waku_discv5.nim | 8 +- waku/discovery/waku_kademlia.nim | 3 +- waku/factory/builder.nim | 6 +- .../factory/conf_builder/mix_conf_builder.nim | 2 +- .../conf_builder/waku_conf_builder.nim | 6 +- waku/factory/node_factory.nim | 6 +- waku/factory/waku.nim | 4 +- waku/node/kernel_api/lightpush.nim | 2 +- waku/node/peer_manager/waku_peer_store.nim | 3 +- waku/node/waku_node.nim | 9 +- waku/node/waku_switch.nim | 4 +- waku/utils/requests.nim | 6 +- waku/waku_enr/capabilities.nim | 2 +- waku/waku_filter_v2/client.nim | 10 +- waku/waku_lightpush/client.nim | 6 +- waku/waku_lightpush/protocol.nim | 6 +- waku/waku_lightpush_legacy/client.nim | 6 +- waku/waku_lightpush_legacy/protocol.nim | 6 +- waku/waku_mix/protocol.nim | 12 +- waku/waku_noise/noise.nim | 6 +- .../waku_noise/noise_handshake_processing.nim | 6 +- waku/waku_noise/noise_utils.nim | 22 +- waku/waku_relay/protocol.nim | 3 +- waku/waku_rendezvous/client.nim | 8 +- waku/waku_rendezvous/protocol.nim | 12 +- waku/waku_store/client.nim | 6 +- waku/waku_store/protocol.nim | 5 +- 57 files changed, 294 insertions(+), 896 deletions(-) delete mode 100644 nimble.lock diff --git a/apps/chat2/chat2.nim b/apps/chat2/chat2.nim index e76c7be17..5da722e3a 100644 --- a/apps/chat2/chat2.nim +++ b/apps/chat2/chat2.nim @@ -12,7 +12,7 @@ import chronicles, chronos, eth/keys, - bearssl, + stew/[byteutils, results], metrics, metrics/chronos_httpserver @@ -301,7 +301,7 @@ proc readInput(wfd: AsyncFD) {.thread, raises: [Defect, CatchableError].} = {.pop.} # @TODO confutils.nim(775, 17) Error: can raise an unlisted exception: ref IOError -proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = +proc processInput(rfd: AsyncFD, rng: crypto.Rng) {.async.} = let transp = fromPipe(rfd) conf = Chat2Conf.load() @@ -309,7 +309,7 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = if conf.nodekey.isSome(): conf.nodekey.get() else: - PrivateKey.random(Secp256k1, rng[]).tryGet() + PrivateKey.random(Secp256k1, rng).tryGet() # set log level if conf.logLevel != LogLevel.NONE: @@ -564,7 +564,7 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = runForever() -proc main(rng: ref HmacDrbgContext) {.async.} = +proc main(rng: crypto.Rng) {.async.} = let (rfd, wfd) = createAsyncPipe() if rfd == asyncInvalidPipe or wfd == asyncInvalidPipe: raise newException(ValueError, "Could not initialize pipe!") diff --git a/apps/chat2disco/chat2disco.nim b/apps/chat2disco/chat2disco.nim index dbe7b99cc..3ac01eb1f 100644 --- a/apps/chat2disco/chat2disco.nim +++ b/apps/chat2disco/chat2disco.nim @@ -13,7 +13,7 @@ import chronicles, chronos, eth/keys, - bearssl, + stew/byteutils, results, metrics, @@ -286,7 +286,7 @@ proc readInput(wfd: AsyncFD) {.thread, raises: [Defect, CatchableError].} = discard waitFor transp.write(line & "\r\n") {.pop.} -proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = +proc processInput(rfd: AsyncFD, rng: crypto.Rng) {.async.} = let transp = fromPipe(rfd) conf = Chat2DiscoConf.load() @@ -294,7 +294,7 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = if conf.nodekey.isSome(): conf.nodekey.get() else: - PrivateKey.random(Secp256k1, rng[]).tryGet() + PrivateKey.random(Secp256k1, rng).tryGet() # set log level if conf.logLevel != LogLevel.NONE: @@ -418,7 +418,7 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = runForever() -proc main(rng: ref HmacDrbgContext) {.async.} = +proc main(rng: crypto.Rng) {.async.} = let (rfd, wfd) = createAsyncPipe() if rfd == asyncInvalidPipe or wfd == asyncInvalidPipe: raise newException(ValueError, "Could not initialize pipe!") diff --git a/apps/chat2mix/chat2mix.nim b/apps/chat2mix/chat2mix.nim index 374f670b8..10e15d4a5 100644 --- a/apps/chat2mix/chat2mix.nim +++ b/apps/chat2mix/chat2mix.nim @@ -12,7 +12,7 @@ import chronicles, chronos, eth/keys, - bearssl, + results, stew/[byteutils], metrics, @@ -391,7 +391,7 @@ proc maintainSubscription( {.pop.} # @TODO confutils.nim(775, 17) Error: can raise an unlisted exception: ref IOError -proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = +proc processInput(rfd: AsyncFD, rng: crypto.Rng) {.async.} = let transp = fromPipe(rfd) conf = Chat2Conf.load() @@ -399,7 +399,7 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = if conf.nodekey.isSome(): conf.nodekey.get() else: - PrivateKey.random(Secp256k1, rng[]).tryGet() + PrivateKey.random(Secp256k1, rng).tryGet() # set log level if conf.logLevel != LogLevel.NONE: @@ -655,7 +655,7 @@ proc processInput(rfd: AsyncFD, rng: ref HmacDrbgContext) {.async.} = runForever() -proc main(rng: ref HmacDrbgContext) {.async.} = +proc main(rng: crypto.Rng) {.async.} = let (rfd, wfd) = createAsyncPipe() if rfd == asyncInvalidPipe or wfd == asyncInvalidPipe: raise newException(ValueError, "Could not initialize pipe!") diff --git a/apps/networkmonitor/networkmonitor.nim b/apps/networkmonitor/networkmonitor.nim index 23607b118..5b37e80f4 100644 --- a/apps/networkmonitor/networkmonitor.nim +++ b/apps/networkmonitor/networkmonitor.nim @@ -423,7 +423,7 @@ proc initAndStartApp( let # some hardcoded parameters rng = keys.newRng() - key = crypto.PrivateKey.random(Secp256k1, rng[])[] + key = crypto.PrivateKey.random(Secp256k1, rng)[] nodeTcpPort = Port(60000) nodeUdpPort = Port(9000) flags = CapabilitiesBitfield.init( diff --git a/apps/wakucanary/wakucanary.nim b/apps/wakucanary/wakucanary.nim index e7b1ff9aa..96dfb19c4 100644 --- a/apps/wakucanary/wakucanary.nim +++ b/apps/wakucanary/wakucanary.nim @@ -159,7 +159,7 @@ proc pingNode( error "Failed to ping the peer", peer = peerInfo, err = msg return false -proc main(rng: ref HmacDrbgContext): Future[int] {.async.} = +proc main(rng: crypto.Rng): Future[int] {.async.} = let conf: WakuCanaryConf = WakuCanaryConf.load() # create dns resolver @@ -190,7 +190,7 @@ proc main(rng: ref HmacDrbgContext): Future[int] {.async.} = quit(QuitFailure) let - nodeKey = crypto.PrivateKey.random(Secp256k1, rng[])[] + nodeKey = crypto.PrivateKey.random(Secp256k1, rng)[] bindIp = parseIpAddress("0.0.0.0") wsBindPort = Port(conf.nodePort + WebSocketPortOffset) nodeTcpPort = Port(conf.nodePort) diff --git a/config.nims b/config.nims index 796716d3b..5346a8d8b 100644 --- a/config.nims +++ b/config.nims @@ -5,6 +5,8 @@ if defined(release): else: switch("nimcache", "nimcache/debug/$projectName") +switch("passL", getCurrentDir() / "librln_v0.9.0.a") + if defined(windows): switch("passL", "rln.lib") switch("define", "postgres=false") @@ -120,7 +122,6 @@ if defined(android): switch("passL", "--sysroot=" & sysRoot) switch("cincludes", sysRoot & "/usr/include/") # begin Nimble config (version 2) ---noNimblePath when withDir(thisDir(), system.fileExists("nimble.paths")): include "nimble.paths" # end Nimble config diff --git a/examples/filter_subscriber.nim b/examples/filter_subscriber.nim index 03a5de4eb..1b3ed6e17 100644 --- a/examples/filter_subscriber.nim +++ b/examples/filter_subscriber.nim @@ -43,13 +43,13 @@ proc messagePushHandler( contentTopic = message.contentTopic, timestamp = message.timestamp -proc setupAndSubscribe(rng: ref HmacDrbgContext) {.async.} = +proc setupAndSubscribe(rng: crypto.Rng) {.async.} = # use notice to filter all waku messaging setupLog(logging.LogLevel.NOTICE, logging.LogFormat.TEXT) notice "starting subscriber", wakuPort = wakuPort let - nodeKey = crypto.PrivateKey.random(Secp256k1, rng[])[] + nodeKey = crypto.PrivateKey.random(Secp256k1, rng)[] ip = parseIpAddress("0.0.0.0") flags = CapabilitiesBitfield.init(relay = true) diff --git a/examples/lightpush_mix/lightpush_publisher_mix.nim b/examples/lightpush_mix/lightpush_publisher_mix.nim index 104de8552..b9bc26c4f 100644 --- a/examples/lightpush_mix/lightpush_publisher_mix.nim +++ b/examples/lightpush_mix/lightpush_publisher_mix.nim @@ -7,8 +7,8 @@ import confutils, libp2p/crypto/crypto, libp2p/crypto/curve25519, - libp2p/protocols/mix, - libp2p/protocols/mix/curve25519, + libp2p_mix, + libp2p_mix/curve25519, libp2p/multiaddress, eth/keys, eth/p2p/discoveryv5/enr, @@ -48,13 +48,13 @@ proc splitPeerIdAndAddr(maddr: string): (string, string) = peerId = parts[1] return (address, peerId) -proc setupAndPublish(rng: ref HmacDrbgContext, conf: LightPushMixConf) {.async.} = +proc setupAndPublish(rng: crypto.Rng, conf: LightPushMixConf) {.async.} = # use notice to filter all waku messaging setupLog(logging.LogLevel.DEBUG, logging.LogFormat.TEXT) notice "starting publisher", wakuPort = conf.port let - nodeKey = crypto.PrivateKey.random(Secp256k1, rng[]).get() + nodeKey = crypto.PrivateKey.random(Secp256k1, rng).get() ip = parseIpAddress("0.0.0.0") flags = CapabilitiesBitfield.init(relay = true) diff --git a/examples/lightpush_publisher.nim b/examples/lightpush_publisher.nim index c7eacdd30..e55fcc9b1 100644 --- a/examples/lightpush_publisher.nim +++ b/examples/lightpush_publisher.nim @@ -35,13 +35,13 @@ const LightpushPubsubTopic = PubsubTopic("/waku/2/rs/1/0") LightpushContentTopic = ContentTopic("/examples/1/light-pubsub-example/proto") -proc setupAndPublish(rng: ref HmacDrbgContext) {.async.} = +proc setupAndPublish(rng: crypto.Rng) {.async.} = # use notice to filter all waku messaging setupLog(logging.LogLevel.NOTICE, logging.LogFormat.TEXT) notice "starting publisher", wakuPort = wakuPort let - nodeKey = crypto.PrivateKey.random(Secp256k1, rng[]).get() + nodeKey = crypto.PrivateKey.random(Secp256k1, rng).get() ip = parseIpAddress("0.0.0.0") flags = CapabilitiesBitfield.init(relay = true) diff --git a/examples/publisher.nim b/examples/publisher.nim index 6f5d34bc4..d3ee032a3 100644 --- a/examples/publisher.nim +++ b/examples/publisher.nim @@ -37,13 +37,13 @@ const bootstrapNode = const wakuPort = 60000 const discv5Port = 9000 -proc setupAndPublish(rng: ref HmacDrbgContext) {.async.} = +proc setupAndPublish(rng: crypto.Rng) {.async.} = # use notice to filter all waku messaging setupLog(logging.LogLevel.NOTICE, logging.LogFormat.TEXT) notice "starting publisher", wakuPort = wakuPort, discv5Port = discv5Port let - nodeKey = crypto.PrivateKey.random(Secp256k1, rng[]).get() + nodeKey = crypto.PrivateKey.random(Secp256k1, rng).get() ip = parseIpAddress("0.0.0.0") flags = CapabilitiesBitfield.init(relay = true) diff --git a/examples/subscriber.nim b/examples/subscriber.nim index ce64bb803..36bc4554c 100644 --- a/examples/subscriber.nim +++ b/examples/subscriber.nim @@ -35,13 +35,13 @@ const bootstrapNode = const wakuPort = 50000 const discv5Port = 8000 -proc setupAndSubscribe(rng: ref HmacDrbgContext) {.async.} = +proc setupAndSubscribe(rng: crypto.Rng) {.async.} = # use notice to filter all waku messaging setupLog(logging.LogLevel.NOTICE, logging.LogFormat.TEXT) notice "starting subscriber", wakuPort = wakuPort, discv5Port = discv5Port let - nodeKey = crypto.PrivateKey.random(Secp256k1, rng[])[] + nodeKey = crypto.PrivateKey.random(Secp256k1, rng)[] ip = parseIpAddress("0.0.0.0") flags = CapabilitiesBitfield.init(relay = true) diff --git a/nimble.lock b/nimble.lock deleted file mode 100644 index 7c76f7fa9..000000000 --- a/nimble.lock +++ /dev/null @@ -1,607 +0,0 @@ -{ - "version": 2, - "packages": { - "nim": { - "version": "2.2.4", - "vcsRevision": "911e0dbb1f76de61fa0215ab1bb85af5334cc9a8", - "url": "https://github.com/nim-lang/Nim.git", - "downloadMethod": "git", - "dependencies": [], - "checksums": { - "sha1": "68bb85cbfb1832ce4db43943911b046c3af3caab" - } - }, - "unittest2": { - "version": "0.2.5", - "vcsRevision": "26f2ef3ae0ec72a2a75bfe557e02e88f6a31c189", - "url": "https://github.com/status-im/nim-unittest2", - "downloadMethod": "git", - "dependencies": [ - "nim" - ], - "checksums": { - "sha1": "02bb3751ba9ddc3c17bfd89f2e41cb6bfb8fc0c9" - } - }, - "bearssl": { - "version": "0.2.8", - "vcsRevision": "22c6a76ce015bc07e011562bdcfc51d9446c1e82", - "url": "https://github.com/status-im/nim-bearssl", - "downloadMethod": "git", - "dependencies": [ - "nim", - "unittest2" - ], - "checksums": { - "sha1": "da4dd7ae96d536bdaf42dca9c85d7aed024b6a86" - } - }, - "bearssl_pkey_decoder": { - "version": "#21dd3710df9345ed2ad8bf8f882761e07863b8e0", - "vcsRevision": "21dd3710df9345ed2ad8bf8f882761e07863b8e0", - "url": "https://github.com/vacp2p/bearssl_pkey_decoder", - "downloadMethod": "git", - "dependencies": [ - "nim", - "bearssl" - ], - "checksums": { - "sha1": "21b42e2e6ddca6c875d3fc50f36a5115abf51714" - } - }, - "jwt": { - "version": "#18f8378de52b241f321c1f9ea905456e89b95c6f", - "vcsRevision": "18f8378de52b241f321c1f9ea905456e89b95c6f", - "url": "https://github.com/vacp2p/nim-jwt.git", - "downloadMethod": "git", - "dependencies": [ - "nim", - "bearssl", - "bearssl_pkey_decoder" - ], - "checksums": { - "sha1": "bcfd6fc9c5e10a52b87117219b7ab5c98136bc8e" - } - }, - "testutils": { - "version": "0.8.1", - "vcsRevision": "6ce5e5e2301ccbc04b09d27ff78741ff4d352b4d", - "url": "https://github.com/status-im/nim-testutils", - "downloadMethod": "git", - "dependencies": [ - "nim", - "unittest2" - ], - "checksums": { - "sha1": "96a11cf8b84fa9bd12d4a553afa1cc4b7f9df4e3" - } - }, - "db_connector": { - "version": "0.1.0", - "vcsRevision": "29450a2063970712422e1ab857695c12d80112a6", - "url": "https://github.com/nim-lang/db_connector", - "downloadMethod": "git", - "dependencies": [ - "nim" - ], - "checksums": { - "sha1": "4f2e67d0e4b61af9ac5575509305660b473f01a4" - } - }, - "results": { - "version": "0.5.1", - "vcsRevision": "df8113dda4c2d74d460a8fa98252b0b771bf1f27", - "url": "https://github.com/arnetheduck/nim-results", - "downloadMethod": "git", - "dependencies": [ - "nim" - ], - "checksums": { - "sha1": "a9c011f74bc9ed5c91103917b9f382b12e82a9e7" - } - }, - "nat_traversal": { - "version": "0.0.1", - "vcsRevision": "860e18c37667b5dd005b94c63264560c35d88004", - "url": "https://github.com/status-im/nim-nat-traversal", - "downloadMethod": "git", - "dependencies": [ - "nim", - "results" - ], - "checksums": { - "sha1": "1a376d3e710590ef2c48748a546369755f0a7c97" - } - }, - "stew": { - "version": "0.5.0", - "vcsRevision": "4382b18f04b3c43c8409bfcd6b62063773b2bbaa", - "url": "https://github.com/status-im/nim-stew", - "downloadMethod": "git", - "dependencies": [ - "nim", - "results", - "unittest2" - ], - "checksums": { - "sha1": "db22942939773ab7d5a0f2b2668c237240c67dd6" - } - }, - "zlib": { - "version": "0.1.0", - "vcsRevision": "e680f269fb01af2c34a2ba879ff281795a5258fe", - "url": "https://github.com/status-im/nim-zlib", - "downloadMethod": "git", - "dependencies": [ - "nim", - "stew", - "results" - ], - "checksums": { - "sha1": "bbde4f5a97a84b450fef7d107461e5f35cf2b47f" - } - }, - "httputils": { - "version": "0.4.1", - "vcsRevision": "f142cb2e8bd812dd002a6493b6082827bb248592", - "url": "https://github.com/status-im/nim-http-utils", - "downloadMethod": "git", - "dependencies": [ - "nim", - "stew", - "results", - "unittest2" - ], - "checksums": { - "sha1": "016774ab31c3afff9a423f7d80584905ee59c570" - } - }, - "chronos": { - "version": "4.2.2", - "vcsRevision": "45f43a9ad8bd8bcf5903b42f365c1c879bd54240", - "url": "https://github.com/status-im/nim-chronos", - "downloadMethod": "git", - "dependencies": [ - "nim", - "results", - "stew", - "bearssl", - "httputils", - "unittest2" - ], - "checksums": { - "sha1": "3a4c9477df8cef20a04e4f1b54a2d74fdfc2a3d0" - } - }, - "metrics": { - "version": "0.2.1", - "vcsRevision": "a1296caf3ebb5f30f51a5feae7749a30df2824c2", - "url": "https://github.com/status-im/nim-metrics", - "downloadMethod": "git", - "dependencies": [ - "nim", - "chronos", - "results", - "stew" - ], - "checksums": { - "sha1": "84bb09873d7677c06046f391c7b473cd2fcff8a2" - } - }, - "faststreams": { - "version": "0.5.0", - "vcsRevision": "ce27581a3e881f782f482cb66dc5b07a02bd615e", - "url": "https://github.com/status-im/nim-faststreams", - "downloadMethod": "git", - "dependencies": [ - "nim", - "stew", - "unittest2" - ], - "checksums": { - "sha1": "ee61e507b805ae1df7ec936f03f2d101b0d72383" - } - }, - "snappy": { - "version": "0.1.0", - "vcsRevision": "00bfcef94f8ef6981df5d5b994897f6695badfb2", - "url": "https://github.com/status-im/nim-snappy", - "downloadMethod": "git", - "dependencies": [ - "nim", - "faststreams", - "unittest2", - "results", - "stew" - ], - "checksums": { - "sha1": "e572d60d6a3178c5b1cde2400c51ad771812cd3d" - } - }, - "serialization": { - "version": "0.5.2", - "vcsRevision": "b0f2fa32960ea532a184394b0f27be37bd80248b", - "url": "https://github.com/status-im/nim-serialization", - "downloadMethod": "git", - "dependencies": [ - "nim", - "faststreams", - "unittest2", - "stew" - ], - "checksums": { - "sha1": "fa35c1bb76a0a02a2379fe86eaae0957c7527cb8" - } - }, - "toml_serialization": { - "version": "0.2.18", - "vcsRevision": "b5b387e6fb2a7cc75d54a269b07cc6218361bd46", - "url": "https://github.com/status-im/nim-toml-serialization", - "downloadMethod": "git", - "dependencies": [ - "nim", - "faststreams", - "serialization", - "stew" - ], - "checksums": { - "sha1": "76ae1c2af5dd092849b41750ff29217980dc9ca3" - } - }, - "confutils": { - "version": "0.1.0", - "vcsRevision": "7728f6bd81a1eedcfe277d02ea85fdb805bcc05a", - "url": "https://github.com/status-im/nim-confutils", - "downloadMethod": "git", - "dependencies": [ - "nim", - "stew", - "serialization", - "results" - ], - "checksums": { - "sha1": "8bc8c30b107fdba73b677e5f257c6c42ae1cdc8e" - } - }, - "json_serialization": { - "version": "0.4.4", - "vcsRevision": "c343b0e243d9e17e2c40f3a8a24340f7c4a71d44", - "url": "https://github.com/status-im/nim-json-serialization", - "downloadMethod": "git", - "dependencies": [ - "nim", - "faststreams", - "serialization", - "stew", - "results" - ], - "checksums": { - "sha1": "8b3115354104858a0ac9019356fb29720529c2bd" - } - }, - "chronicles": { - "version": "0.12.2", - "vcsRevision": "27ec507429a4eb81edc20f28292ee8ec420be05b", - "url": "https://github.com/status-im/nim-chronicles", - "downloadMethod": "git", - "dependencies": [ - "nim", - "faststreams", - "serialization", - "json_serialization", - "testutils" - ], - "checksums": { - "sha1": "02febb20d088120b2836d3306cfa21f434f88f65" - } - }, - "presto": { - "version": "0.1.1", - "vcsRevision": "d66043dd7ede146442e6c39720c76a20bde5225f", - "url": "https://github.com/status-im/nim-presto", - "downloadMethod": "git", - "dependencies": [ - "nim", - "chronos", - "chronicles", - "metrics", - "results", - "stew" - ], - "checksums": { - "sha1": "8df97c45683abe2337bdff43b844c4fbcc124ca2" - } - }, - "stint": { - "version": "0.8.2", - "vcsRevision": "470b7892561b5179ab20bd389a69217d6213fe58", - "url": "https://github.com/status-im/nim-stint", - "downloadMethod": "git", - "dependencies": [ - "nim", - "stew", - "unittest2" - ], - "checksums": { - "sha1": "d8f871fd617e7857192d4609fe003b48942a8ae5" - } - }, - "minilru": { - "version": "0.1.0", - "vcsRevision": "6dd93feb60f4cded3c05e7af7209cf63fb677893", - "url": "https://github.com/status-im/nim-minilru", - "downloadMethod": "git", - "dependencies": [ - "nim", - "results", - "unittest2" - ], - "checksums": { - "sha1": "0be03a5da29fdd4409ea74a60fd0ccce882601b4" - } - }, - "sqlite3_abi": { - "version": "3.53.0.0", - "vcsRevision": "8240e8e2819dfce1b67fa2733135d01b5cc80ae0", - "url": "https://github.com/arnetheduck/nim-sqlite3-abi", - "downloadMethod": "git", - "dependencies": [ - "nim" - ], - "checksums": { - "sha1": "fb7a6e6f36fc4eb4dfa6634dbcbf5cd0dfd0ebf0" - } - }, - "dnsclient": { - "version": "0.3.4", - "vcsRevision": "23214235d4784d24aceed99bbfe153379ea557c8", - "url": "https://github.com/ba0f3/dnsclient.nim", - "downloadMethod": "git", - "dependencies": [ - "nim" - ], - "checksums": { - "sha1": "65262c7e533ff49d6aca5539da4bc6c6ce132f40" - } - }, - "unicodedb": { - "version": "0.13.2", - "vcsRevision": "66f2458710dc641dd4640368f9483c8a0ec70561", - "url": "https://github.com/nitely/nim-unicodedb", - "downloadMethod": "git", - "dependencies": [ - "nim" - ], - "checksums": { - "sha1": "739102d885d99bb4571b1955f5f12aee423c935b" - } - }, - "regex": { - "version": "0.26.3", - "vcsRevision": "4593305ed1e49731fc75af1dc572dd2559aad19c", - "url": "https://github.com/nitely/nim-regex", - "downloadMethod": "git", - "dependencies": [ - "nim", - "unicodedb" - ], - "checksums": { - "sha1": "4d24e7d7441137cd202e16f2359a5807ddbdc31f" - } - }, - "nimcrypto": { - "version": "0.6.4", - "vcsRevision": "721fb99ee099b632eb86dfad1f0d96ee87583774", - "url": "https://github.com/cheatfate/nimcrypto", - "downloadMethod": "git", - "dependencies": [ - "nim" - ], - "checksums": { - "sha1": "f9ab24fa940ed03d0fb09729a7303feb50b7eaec" - } - }, - "websock": { - "version": "0.3.0", - "vcsRevision": "c105d98e6522e0e2cbe3dfa11b07a273e9fd0e7b", - "url": "https://github.com/status-im/nim-websock", - "downloadMethod": "git", - "dependencies": [ - "nim", - "chronos", - "httputils", - "chronicles", - "stew", - "nimcrypto", - "bearssl", - "results", - "zlib" - ], - "checksums": { - "sha1": "1294a66520fa4541e261dec8a6a84f774fb8c0ac" - } - }, - "json_rpc": { - "version": "#43bbf499143eb45046c83ac9794c9e3280a2b8e7", - "vcsRevision": "43bbf499143eb45046c83ac9794c9e3280a2b8e7", - "url": "https://github.com/status-im/nim-json-rpc.git", - "downloadMethod": "git", - "dependencies": [ - "nim", - "stew", - "nimcrypto", - "stint", - "chronos", - "httputils", - "chronicles", - "websock", - "serialization", - "json_serialization", - "unittest2" - ], - "checksums": { - "sha1": "30ff6ead115b88c79862c5c7e37b1c9852eea59f" - } - }, - "lsquic": { - "version": "0.0.1", - "vcsRevision": "4fb03ee7bfb39aecb3316889fdcb60bec3d0936f", - "url": "https://github.com/vacp2p/nim-lsquic", - "downloadMethod": "git", - "dependencies": [ - "nim", - "zlib", - "stew", - "chronos", - "nimcrypto", - "unittest2", - "chronicles" - ], - "checksums": { - "sha1": "f465fa994346490d0924d162f53d9b5aec62f948" - } - }, - "secp256k1": { - "version": "0.6.0.3.2", - "vcsRevision": "d8f1288b7c72f00be5fc2c5ea72bf5cae1eafb15", - "url": "https://github.com/status-im/nim-secp256k1", - "downloadMethod": "git", - "dependencies": [ - "nim", - "stew", - "results", - "nimcrypto" - ], - "checksums": { - "sha1": "6618ef9de17121846a8c1d0317026b0ce8584e10" - } - }, - "eth": { - "version": "0.9.0", - "vcsRevision": "d9135e6c3c5d6d819afdfb566aa8d958756b73a8", - "url": "https://github.com/status-im/nim-eth", - "downloadMethod": "git", - "dependencies": [ - "nim", - "nimcrypto", - "stint", - "secp256k1", - "chronos", - "chronicles", - "stew", - "nat_traversal", - "metrics", - "sqlite3_abi", - "confutils", - "testutils", - "unittest2", - "results", - "minilru", - "snappy" - ], - "checksums": { - "sha1": "2e01b0cfff9523d110562af70d19948280f8013e" - } - }, - "web3": { - "version": "0.8.0", - "vcsRevision": "cdfe5601d2812a58e54faf53ee634452d01e5918", - "url": "https://github.com/status-im/nim-web3", - "downloadMethod": "git", - "dependencies": [ - "nim", - "chronicles", - "chronos", - "bearssl", - "eth", - "faststreams", - "json_rpc", - "serialization", - "json_serialization", - "nimcrypto", - "stew", - "stint", - "results" - ], - "checksums": { - "sha1": "26a112af032ef1536f97da2ca7364af618a11b80" - } - }, - "dnsdisc": { - "version": "0.1.0", - "vcsRevision": "38f2e0f52c0a8f032ef4530835e519d550706d9e", - "url": "https://github.com/status-im/nim-dnsdisc", - "downloadMethod": "git", - "dependencies": [ - "nim", - "bearssl", - "chronicles", - "chronos", - "eth", - "secp256k1", - "stew", - "testutils", - "unittest2", - "nimcrypto", - "results" - ], - "checksums": { - "sha1": "055b882a0f6b1d1e57a25a7af99d2e5ac6268154" - } - }, - "libp2p": { - "version": "#ff8d51857b4b79a68468e7bcc27b2026cca02996", - "vcsRevision": "ff8d51857b4b79a68468e7bcc27b2026cca02996", - "url": "https://github.com/vacp2p/nim-libp2p.git", - "downloadMethod": "git", - "dependencies": [ - "nim", - "nimcrypto", - "dnsclient", - "bearssl", - "chronicles", - "chronos", - "metrics", - "secp256k1", - "stew", - "websock", - "unittest2", - "results", - "serialization", - "lsquic", - "jwt" - ], - "checksums": { - "sha1": "fa2a7552c6ec860717b77ce34cf0b7afe4570234" - } - }, - "taskpools": { - "version": "0.1.0", - "vcsRevision": "9e8ccc754631ac55ac2fd495e167e74e86293edb", - "url": "https://github.com/status-im/nim-taskpools", - "downloadMethod": "git", - "dependencies": [ - "nim" - ], - "checksums": { - "sha1": "09e1b2fdad55b973724d61227971afc0df0b7a81" - } - }, - "ffi": { - "version": "0.1.3", - "vcsRevision": "06111de155253b34e47ed2aaed1d61d08d62cc1b", - "url": "https://github.com/logos-messaging/nim-ffi", - "downloadMethod": "git", - "dependencies": [ - "nim", - "chronos", - "chronicles", - "taskpools" - ], - "checksums": { - "sha1": "6f9d49375ea1dc71add55c72ac80a808f238e5b0" - } - } - }, - "tasks": {} -} diff --git a/tests/node/test_wakunode_filter.nim b/tests/node/test_wakunode_filter.nim index 2777b0124..2deaa8833 100644 --- a/tests/node/test_wakunode_filter.nim +++ b/tests/node/test_wakunode_filter.nim @@ -21,9 +21,9 @@ import ../testlib/[common, wakucore, wakunode, testasync, futures, testutils], ../waku_filter_v2/waku_filter_utils -proc generateRequestId(rng: ref HmacDrbgContext): string = +proc generateRequestId(rng: crypto.Rng): string = var bytes: array[10, byte] - hmacDrbgGenerate(rng[], bytes) + rng.generate(bytes) return toHex(bytes) proc createRequest( diff --git a/tests/node/test_wakunode_relay_rln.nim b/tests/node/test_wakunode_relay_rln.nim index c8ca9b43d..1169ce7b3 100644 --- a/tests/node/test_wakunode_relay_rln.nim +++ b/tests/node/test_wakunode_relay_rln.nim @@ -35,10 +35,10 @@ from ../../waku/waku_noise/noise_utils import randomSeqByte proc buildRandomIdentityCredentials(): IdentityCredential = # We generate a random identity credential (inter-value constrains are not enforced, otherwise we need to load e.g. zerokit RLN keygen) let - idTrapdoor = randomSeqByte(rng[], 32) - idNullifier = randomSeqByte(rng[], 32) - idSecretHash = randomSeqByte(rng[], 32) - idCommitment = randomSeqByte(rng[], 32) + idTrapdoor = randomSeqByte(rng, 32) + idNullifier = randomSeqByte(rng, 32) + idSecretHash = randomSeqByte(rng, 32) + idCommitment = randomSeqByte(rng, 32) IdentityCredential( idTrapdoor: idTrapdoor, diff --git a/tests/test_helpers.nim b/tests/test_helpers.nim index bd1d837b6..a2ec045ea 100644 --- a/tests/test_helpers.nim +++ b/tests/test_helpers.nim @@ -1,4 +1,4 @@ -import chronos, bearssl/rand, eth/[keys, p2p] +import chronos, eth/[keys, p2p] import libp2p/crypto/crypto @@ -9,10 +9,10 @@ proc localAddress*(port: int): Address = result = Address(udpPort: port, tcpPort: port, ip: parseIpAddress("127.0.0.1")) proc setupTestNode*( - rng: ref HmacDrbgContext, capabilities: varargs[ProtocolInfo, `protocolInfo`] + rng: crypto.Rng, capabilities: varargs[ProtocolInfo, `protocolInfo`] ): EthereumNode = let - keys1 = keys.KeyPair.random(rng[]) + keys1 = keys.KeyPair.random(rng) address = localAddress(nextPort) result = newEthereumNode( keys1, @@ -29,11 +29,11 @@ proc setupTestNode*( # Copied from here: https://github.com/status-im/nim-libp2p/blob/d522537b19a532bc4af94fcd146f779c1f23bad0/tests/helpers.nim#L28 type RngWrap = object - rng: ref rand.HmacDrbgContext + rng: Rng var rngVar: RngWrap -proc getRng(): ref rand.HmacDrbgContext = +proc getRng(): Rng = # TODO if `rngVar` is a threadvar like it should be, there are random and # spurious compile failures on mac - this is not gcsafe but for the # purpose of the tests, it's ok as long as we only use a single thread @@ -42,5 +42,5 @@ proc getRng(): ref rand.HmacDrbgContext = rngVar.rng = crypto.newRng() rngVar.rng -template rng*(): ref rand.HmacDrbgContext = +template rng*(): Rng = getRng() diff --git a/tests/test_waku_dnsdisc.nim b/tests/test_waku_dnsdisc.nim index 758bdb3ca..9c6dde7d6 100644 --- a/tests/test_waku_dnsdisc.nim +++ b/tests/test_waku_dnsdisc.nim @@ -52,7 +52,7 @@ suite "Waku DNS Discovery": ) .get() # No link entries - let treeKeys = keys.KeyPair.random(rng[]) + let treeKeys = keys.KeyPair.random(rng) # Sign tree check: diff --git a/tests/test_waku_keystore.nim b/tests/test_waku_keystore.nim index 8fd8ad297..83536b062 100644 --- a/tests/test_waku_keystore.nim +++ b/tests/test_waku_keystore.nim @@ -46,10 +46,10 @@ procSuite "Credentials test suite": # We generate a random identity credential (inter-value constrains are not enforced, otherwise we need to load e.g. zerokit RLN keygen) var - idTrapdoor = randomSeqByte(rng[], 32) - idNullifier = randomSeqByte(rng[], 32) - idSecretHash = randomSeqByte(rng[], 32) - idCommitment = randomSeqByte(rng[], 32) + idTrapdoor = randomSeqByte(rng, 32) + idNullifier = randomSeqByte(rng, 32) + idSecretHash = randomSeqByte(rng, 32) + idCommitment = randomSeqByte(rng, 32) var idCredential = IdentityCredential( idTrapdoor: idTrapdoor, @@ -85,10 +85,10 @@ procSuite "Credentials test suite": # We generate two random identity credentials (inter-value constrains are not enforced, otherwise we need to load e.g. zerokit RLN keygen) var - idTrapdoor = randomSeqByte(rng[], 32) - idNullifier = randomSeqByte(rng[], 32) - idSecretHash = randomSeqByte(rng[], 32) - idCommitment = randomSeqByte(rng[], 32) + idTrapdoor = randomSeqByte(rng, 32) + idNullifier = randomSeqByte(rng, 32) + idSecretHash = randomSeqByte(rng, 32) + idCommitment = randomSeqByte(rng, 32) idCredential = IdentityCredential( idTrapdoor: idTrapdoor, idNullifier: idNullifier, @@ -141,10 +141,10 @@ procSuite "Credentials test suite": # We generate random identity credentials (inter-value constrains are not enforced, otherwise we need to load e.g. zerokit RLN keygen) let - idTrapdoor = randomSeqByte(rng[], 32) - idNullifier = randomSeqByte(rng[], 32) - idSecretHash = randomSeqByte(rng[], 32) - idCommitment = randomSeqByte(rng[], 32) + idTrapdoor = randomSeqByte(rng, 32) + idNullifier = randomSeqByte(rng, 32) + idSecretHash = randomSeqByte(rng, 32) + idCommitment = randomSeqByte(rng, 32) idCredential = IdentityCredential( idTrapdoor: idTrapdoor, idNullifier: idNullifier, @@ -193,10 +193,10 @@ procSuite "Credentials test suite": # We generate random identity credentials (inter-value constrains are not enforced, otherwise we need to load e.g. zerokit RLN keygen) let - idTrapdoor = randomSeqByte(rng[], 32) - idNullifier = randomSeqByte(rng[], 32) - idSecretHash = randomSeqByte(rng[], 32) - idCommitment = randomSeqByte(rng[], 32) + idTrapdoor = randomSeqByte(rng, 32) + idNullifier = randomSeqByte(rng, 32) + idSecretHash = randomSeqByte(rng, 32) + idCommitment = randomSeqByte(rng, 32) idCredential = IdentityCredential( idTrapdoor: idTrapdoor, idNullifier: idNullifier, @@ -254,10 +254,10 @@ procSuite "Credentials test suite": # We generate random identity credentials (inter-value constrains are not enforced, otherwise we need to load e.g. zerokit RLN keygen) let - idTrapdoor = randomSeqByte(rng[], 32) - idNullifier = randomSeqByte(rng[], 32) - idSecretHash = randomSeqByte(rng[], 32) - idCommitment = randomSeqByte(rng[], 32) + idTrapdoor = randomSeqByte(rng, 32) + idNullifier = randomSeqByte(rng, 32) + idSecretHash = randomSeqByte(rng, 32) + idCommitment = randomSeqByte(rng, 32) idCredential = IdentityCredential( idTrapdoor: idTrapdoor, idNullifier: idNullifier, diff --git a/tests/test_waku_keystore_keyfile.nim b/tests/test_waku_keystore_keyfile.nim index afdb7e44b..cd187baf6 100644 --- a/tests/test_waku_keystore_keyfile.nim +++ b/tests/test_waku_keystore_keyfile.nim @@ -16,7 +16,7 @@ suite "KeyFile test suite": removeFile(filepath) # The secret - var secret = randomSeqByte(rng[], 300) + var secret = randomSeqByte(rng, 300) # We create a keyfile encrypting the secret with password let keyfile = createKeyFileJson(secret, password) @@ -42,9 +42,9 @@ suite "KeyFile test suite": test "Create/Save/Load multiple keyfiles in same file": # We set different passwords for different keyfiles that will be stored in same file - let password1 = string.fromBytes(randomSeqByte(rng[], 20)) + let password1 = string.fromBytes(randomSeqByte(rng, 20)) let password2 = "" - let password3 = string.fromBytes(randomSeqByte(rng[], 20)) + let password3 = string.fromBytes(randomSeqByte(rng, 20)) var keyfile: KfResult[JsonNode] let filepath = "./test.keyfile" @@ -53,40 +53,40 @@ suite "KeyFile test suite": # We generate 6 different secrets and we encrypt them using 3 different passwords, and we store the obtained keystore - let secret1 = randomSeqByte(rng[], 300) + let secret1 = randomSeqByte(rng, 300) keyfile = createKeyFileJson(secret1, password1) check: keyfile.isOk() saveKeyFile(filepath, keyfile.get()).isOk() - let secret2 = randomSeqByte(rng[], 300) + let secret2 = randomSeqByte(rng, 300) keyfile = createKeyFileJson(secret2, password2) check: keyfile.isOk() saveKeyFile(filepath, keyfile.get()).isOk() - let secret3 = randomSeqByte(rng[], 300) + let secret3 = randomSeqByte(rng, 300) keyfile = createKeyFileJson(secret3, password3) check: keyfile.isOk() saveKeyFile(filepath, keyfile.get()).isOk() # We encrypt secret4 with password3 - let secret4 = randomSeqByte(rng[], 300) + let secret4 = randomSeqByte(rng, 300) keyfile = createKeyFileJson(secret4, password3) check: keyfile.isOk() saveKeyFile(filepath, keyfile.get()).isOk() # We encrypt secret5 with password1 - let secret5 = randomSeqByte(rng[], 300) + let secret5 = randomSeqByte(rng, 300) keyfile = createKeyFileJson(secret5, password1) check: keyfile.isOk() saveKeyFile(filepath, keyfile.get()).isOk() # We encrypt secret6 with password1 - let secret6 = randomSeqByte(rng[], 300) + let secret6 = randomSeqByte(rng, 300) keyfile = createKeyFileJson(secret6, password1) check: keyfile.isOk() @@ -343,7 +343,7 @@ suite "KeyFile test suite (adapted from nim-eth keyfile tests)": test "Scrypt keyfiles": let - expectedSecret = randomSeqByte(rng[], 300) + expectedSecret = randomSeqByte(rng, 300) password = "miawmiawcat" # By default, keyfiles' encryption key is derived from password using PBKDF2. diff --git a/tests/test_waku_noise.nim b/tests/test_waku_noise.nim index 6566f9eed..6dbb3a2f9 100644 --- a/tests/test_waku_noise.nim +++ b/tests/test_waku_noise.nim @@ -27,7 +27,7 @@ procSuite "Waku Noise": let maxMessageLength = 3 * NoisePaddingBlockSize for messageLen in 0 .. maxMessageLength: let - message = randomSeqByte(rng[], messageLen) + message = randomSeqByte(rng, messageLen) padded = pkcs7_pad(message, NoisePaddingBlockSize) unpadded = pkcs7_unpad(padded, NoisePaddingBlockSize) @@ -37,11 +37,11 @@ procSuite "Waku Noise": message == unpadded test "ChaChaPoly Encryption/Decryption: random byte sequences": - let cipherState = randomChaChaPolyCipherState(rng[]) + let cipherState = randomChaChaPolyCipherState(rng) # We encrypt/decrypt random byte sequences let - plaintext: seq[byte] = randomSeqByte(rng[], rand(1 .. 128)) + plaintext: seq[byte] = randomSeqByte(rng, rand(1 .. 128)) ciphertext: ChaChaPolyCiphertext = encrypt(cipherState, plaintext) decryptedCiphertext: seq[byte] = decrypt(cipherState, ciphertext) @@ -49,7 +49,7 @@ procSuite "Waku Noise": plaintext == decryptedCiphertext test "ChaChaPoly Encryption/Decryption: random strings": - let cipherState = randomChaChaPolyCipherState(rng[]) + let cipherState = randomChaChaPolyCipherState(rng) # We encrypt/decrypt random strings var plaintext: string @@ -64,10 +64,10 @@ procSuite "Waku Noise": plaintext.toBytes() == decryptedCiphertext test "Noise public keys: encrypt and decrypt a public key": - let noisePublicKey: NoisePublicKey = genNoisePublicKey(rng[]) + let noisePublicKey: NoisePublicKey = genNoisePublicKey(rng) let - cs: ChaChaPolyCipherState = randomChaChaPolyCipherState(rng[]) + cs: ChaChaPolyCipherState = randomChaChaPolyCipherState(rng) encryptedPk: NoisePublicKey = encryptNoisePublicKey(cs, noisePublicKey) decryptedPk: NoisePublicKey = decryptNoisePublicKey(cs, encryptedPk) @@ -75,20 +75,20 @@ procSuite "Waku Noise": noisePublicKey == decryptedPk test "Noise public keys: decrypt an unencrypted public key": - let noisePublicKey: NoisePublicKey = genNoisePublicKey(rng[]) + let noisePublicKey: NoisePublicKey = genNoisePublicKey(rng) let - cs: ChaChaPolyCipherState = randomChaChaPolyCipherState(rng[]) + cs: ChaChaPolyCipherState = randomChaChaPolyCipherState(rng) decryptedPk: NoisePublicKey = decryptNoisePublicKey(cs, noisePublicKey) check: noisePublicKey == decryptedPk test "Noise public keys: encrypt an encrypted public key": - let noisePublicKey: NoisePublicKey = genNoisePublicKey(rng[]) + let noisePublicKey: NoisePublicKey = genNoisePublicKey(rng) let - cs: ChaChaPolyCipherState = randomChaChaPolyCipherState(rng[]) + cs: ChaChaPolyCipherState = randomChaChaPolyCipherState(rng) encryptedPk: NoisePublicKey = encryptNoisePublicKey(cs, noisePublicKey) encryptedPk2: NoisePublicKey = encryptNoisePublicKey(cs, encryptedPk) @@ -96,10 +96,10 @@ procSuite "Waku Noise": encryptedPk == encryptedPk2 test "Noise public keys: encrypt, decrypt and decrypt a public key": - let noisePublicKey: NoisePublicKey = genNoisePublicKey(rng[]) + let noisePublicKey: NoisePublicKey = genNoisePublicKey(rng) let - cs: ChaChaPolyCipherState = randomChaChaPolyCipherState(rng[]) + cs: ChaChaPolyCipherState = randomChaChaPolyCipherState(rng) encryptedPk: NoisePublicKey = encryptNoisePublicKey(cs, noisePublicKey) decryptedPk: NoisePublicKey = decryptNoisePublicKey(cs, encryptedPk) decryptedPk2: NoisePublicKey = decryptNoisePublicKey(cs, decryptedPk) @@ -109,7 +109,7 @@ procSuite "Waku Noise": test "Noise public keys: serialize and deserialize an unencrypted public key": let - noisePublicKey: NoisePublicKey = genNoisePublicKey(rng[]) + noisePublicKey: NoisePublicKey = genNoisePublicKey(rng) serializedNoisePublicKey: seq[byte] = serializeNoisePublicKey(noisePublicKey) deserializedNoisePublicKey: NoisePublicKey = intoNoisePublicKey(serializedNoisePublicKey) @@ -118,10 +118,10 @@ procSuite "Waku Noise": noisePublicKey == deserializedNoisePublicKey test "Noise public keys: encrypt, serialize, deserialize and decrypt a public key": - let noisePublicKey: NoisePublicKey = genNoisePublicKey(rng[]) + let noisePublicKey: NoisePublicKey = genNoisePublicKey(rng) let - cs: ChaChaPolyCipherState = randomChaChaPolyCipherState(rng[]) + cs: ChaChaPolyCipherState = randomChaChaPolyCipherState(rng) encryptedPk: NoisePublicKey = encryptNoisePublicKey(cs, noisePublicKey) serializedNoisePublicKey: seq[byte] = serializeNoisePublicKey(encryptedPk) deserializedNoisePublicKey: NoisePublicKey = @@ -134,7 +134,7 @@ procSuite "Waku Noise": test "PayloadV2: serialize/deserialize PayloadV2 to byte sequence": let - payload2: PayloadV2 = randomPayloadV2(rng[]) + payload2: PayloadV2 = randomPayloadV2(rng) serializedPayload = serializePayloadV2(payload2) check: @@ -149,7 +149,7 @@ procSuite "Waku Noise": test "PayloadV2: Encode/Decode a Waku Message (version 2) to a PayloadV2": # We encode to a WakuMessage a random PayloadV2 let - payload2 = randomPayloadV2(rng[]) + payload2 = randomPayloadV2(rng) msg = encodePayloadV2(payload2) check: @@ -173,8 +173,8 @@ procSuite "Waku Noise": test "Noise State Machine: Diffie-Hellman operation": #We generate random keypairs let - aliceKey = genKeyPair(rng[]) - bobKey = genKeyPair(rng[]) + aliceKey = genKeyPair(rng) + bobKey = genKeyPair(rng) # A Diffie-Hellman operation between Alice's private key and Bob's public key must be equal to # a Diffie-hellman operation between Alice's public key and Bob's private key @@ -188,10 +188,10 @@ procSuite "Waku Noise": test "Noise State Machine: Cipher State primitives": # We generate a random Cipher State, associated data ad and plaintext var - cipherState: CipherState = randomCipherState(rng[]) + cipherState: CipherState = randomCipherState(rng) nonce: uint64 = uint64(rand(0 .. int.high)) - ad: seq[byte] = randomSeqByte(rng[], rand(1 .. 128)) - plaintext: seq[byte] = randomSeqByte(rng[], rand(1 .. 128)) + ad: seq[byte] = randomSeqByte(rng, rand(1 .. 128)) + plaintext: seq[byte] = randomSeqByte(rng, rand(1 .. 128)) # We set the random nonce generated in the cipher state setNonce(cipherState, nonce) @@ -218,7 +218,7 @@ procSuite "Waku Noise": setCipherStateKey(cipherState, EmptyKey) nonce = getNonce(cipherState) - plaintext = randomSeqByte(rng[], rand(1 .. 128)) + plaintext = randomSeqByte(rng, rand(1 .. 128)) ciphertext = encryptWithAd(cipherState, ad, plaintext) check: @@ -230,7 +230,7 @@ procSuite "Waku Noise": nonce = getNonce(cipherState) # Note that we set ciphertext minimum length to 16 to not trigger checks on authentication tag length - ciphertext = randomSeqByte(rng[], rand(16 .. 128)) + ciphertext = randomSeqByte(rng, rand(16 .. 128)) plaintext = decryptWithAd(cipherState, ad, ciphertext) check: @@ -241,9 +241,9 @@ procSuite "Waku Noise": # Note that NonceMax is uint64.high - 1 = 2^64-1-1 and that nonce is increased after each encryption and decryption operation # We generate a test Cipher State with nonce set to MaxNonce - cipherState = randomCipherState(rng[]) + cipherState = randomCipherState(rng) setNonce(cipherState, NonceMax) - plaintext = randomSeqByte(rng[], rand(1 .. 128)) + plaintext = randomSeqByte(rng, rand(1 .. 128)) # We test if encryption fails with a NoiseNonceMaxError error. Any subsequent encryption call over the Cipher State should fail similarly and leave the nonce unchanged for _ in [1 .. 5]: @@ -257,9 +257,9 @@ procSuite "Waku Noise": # Since nonce is increased after decryption as well, we need to generate a proper ciphertext in order to test MaxNonceError error handling # We cannot call encryptWithAd to encrypt a plaintext using a nonce equal MaxNonce, since this will trigger a MaxNonceError. # To perform such test, we then need to encrypt a test plaintext using directly ChaChaPoly primitive - cipherState = randomCipherState(rng[]) + cipherState = randomCipherState(rng) setNonce(cipherState, NonceMax) - plaintext = randomSeqByte(rng[], rand(1 .. 128)) + plaintext = randomSeqByte(rng, rand(1 .. 128)) # We perform encryption using the Cipher State key, NonceMax and ad # By Noise specification the nonce is 8 bytes long out of the 12 bytes supported by ChaChaPoly, thus we copy the Little endian conversion of the nonce to a ChaChaPolyNonce @@ -308,7 +308,7 @@ procSuite "Waku Noise": ######################################## # We generate a random byte sequence and execute a mixHash over it - mixHash(symmetricState, randomSeqByte(rng[], rand(1 .. 128))) + mixHash(symmetricState, randomSeqByte(rng, rand(1 .. 128))) # mixHash changes only the handshake hash value of the Symmetric state check: @@ -324,7 +324,7 @@ procSuite "Waku Noise": ######################################## # We generate random input key material and we execute mixKey - var inputKeyMaterial = randomSeqByte(rng[], rand(1 .. 128)) + var inputKeyMaterial = randomSeqByte(rng, rand(1 .. 128)) mixKey(symmetricState, inputKeyMaterial) # mixKey changes the Symmetric State's chaining key and encryption key of the embedded Cipher State @@ -345,7 +345,7 @@ procSuite "Waku Noise": ######################################## # We generate random input key material and we execute mixKeyAndHash - inputKeyMaterial = randomSeqByte(rng[], rand(1 .. 128)) + inputKeyMaterial = randomSeqByte(rng, rand(1 .. 128)) mixKeyAndHash(symmetricState, inputKeyMaterial) # mixKeyAndHash executes a mixKey and a mixHash using the input key material @@ -368,7 +368,7 @@ procSuite "Waku Noise": var initialSymmetricState = symmetricState # We generate random plaintext and we execute encryptAndHash - var plaintext = randomChaChaPolyKey(rng[]) + var plaintext = randomChaChaPolyKey(rng) var nonce = getNonce(getCipherState(symmetricState)) var ciphertext = encryptAndHash(symmetricState, plaintext) @@ -421,11 +421,11 @@ procSuite "Waku Noise": let hsPattern = NoiseHandshakePatterns["XX"] # We initialize Alice's and Bob's Handshake State - let aliceStaticKey = genKeyPair(rng[]) + let aliceStaticKey = genKeyPair(rng) var aliceHS = initialize(hsPattern = hsPattern, staticKey = aliceStaticKey, initiator = true) - let bobStaticKey = genKeyPair(rng[]) + let bobStaticKey = genKeyPair(rng) var bobHS = initialize(hsPattern = hsPattern, staticKey = bobStaticKey) var @@ -440,15 +440,15 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # By being the handshake initiator, Alice writes a Waku2 payload v2 containing her handshake message # and the (encrypted) transport message aliceStep = - stepHandshake(rng[], aliceHS, transportMessage = sentTransportMessage).get() + stepHandshake(rng, aliceHS, transportMessage = sentTransportMessage).get() # Bob reads Alice's payloads, and returns the (decrypted) transport message Alice sent to him - bobStep = stepHandshake(rng[], bobHS, readPayloadV2 = aliceStep.payload2).get() + bobStep = stepHandshake(rng, bobHS, readPayloadV2 = aliceStep.payload2).get() check: bobStep.transportMessage == sentTransportMessage @@ -458,13 +458,13 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # At this step, Bob writes and returns a payload - bobStep = stepHandshake(rng[], bobHS, transportMessage = sentTransportMessage).get() + bobStep = stepHandshake(rng, bobHS, transportMessage = sentTransportMessage).get() # While Alice reads and returns the (decrypted) transport message - aliceStep = stepHandshake(rng[], aliceHS, readPayloadV2 = bobStep.payload2).get() + aliceStep = stepHandshake(rng, aliceHS, readPayloadV2 = bobStep.payload2).get() check: aliceStep.transportMessage == sentTransportMessage @@ -474,14 +474,14 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # Similarly as in first step, Alice writes a Waku2 payload containing the handshake message and the (encrypted) transport message aliceStep = - stepHandshake(rng[], aliceHS, transportMessage = sentTransportMessage).get() + stepHandshake(rng, aliceHS, transportMessage = sentTransportMessage).get() # Bob reads Alice's payloads, and returns the (decrypted) transport message Alice sent to him - bobStep = stepHandshake(rng[], bobHS, readPayloadV2 = aliceStep.payload2).get() + bobStep = stepHandshake(rng, bobHS, readPayloadV2 = aliceStep.payload2).get() check: bobStep.transportMessage == sentTransportMessage @@ -494,13 +494,13 @@ procSuite "Waku Noise": let prevBobHS = bobHS let bobStep1 = - stepHandshake(rng[], bobHS, transportMessage = sentTransportMessage).get() + stepHandshake(rng, bobHS, transportMessage = sentTransportMessage).get() let aliceStep1 = - stepHandshake(rng[], aliceHS, readPayloadV2 = bobStep1.payload2).get() + stepHandshake(rng, aliceHS, readPayloadV2 = bobStep1.payload2).get() let aliceStep2 = - stepHandshake(rng[], aliceHS, transportMessage = sentTransportMessage).get() + stepHandshake(rng, aliceHS, transportMessage = sentTransportMessage).get() let bobStep2 = - stepHandshake(rng[], bobHS, readPayloadV2 = aliceStep2.payload2).get() + stepHandshake(rng, bobHS, readPayloadV2 = aliceStep2.payload2).get() check: aliceStep1 == default(HandshakeStepResult) @@ -529,7 +529,7 @@ procSuite "Waku Noise": for _ in 0 .. 10: # Alice writes to Bob - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage(aliceHSResult, message, defaultMessageNametagBuffer) readMessage = readMessage(bobHSResult, payload2, defaultMessageNametagBuffer).get() @@ -538,7 +538,7 @@ procSuite "Waku Noise": message == readMessage # Bob writes to Alice - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage(bobHSResult, message, defaultMessageNametagBuffer) readMessage = readMessage(aliceHSResult, payload2, defaultMessageNametagBuffer).get() @@ -550,15 +550,15 @@ procSuite "Waku Noise": let hsPattern = NoiseHandshakePatterns["XXpsk0"] # We generate a random psk - let psk = randomSeqByte(rng[], 32) + let psk = randomSeqByte(rng, 32) # We initialize Alice's and Bob's Handshake State - let aliceStaticKey = genKeyPair(rng[]) + let aliceStaticKey = genKeyPair(rng) var aliceHS = initialize( hsPattern = hsPattern, staticKey = aliceStaticKey, psk = psk, initiator = true ) - let bobStaticKey = genKeyPair(rng[]) + let bobStaticKey = genKeyPair(rng) var bobHS = initialize(hsPattern = hsPattern, staticKey = bobStaticKey, psk = psk) var @@ -573,15 +573,15 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # By being the handshake initiator, Alice writes a Waku2 payload v2 containing her handshake message # and the (encrypted) transport message aliceStep = - stepHandshake(rng[], aliceHS, transportMessage = sentTransportMessage).get() + stepHandshake(rng, aliceHS, transportMessage = sentTransportMessage).get() # Bob reads Alice's payloads, and returns the (decrypted) transport message Alice sent to him - bobStep = stepHandshake(rng[], bobHS, readPayloadV2 = aliceStep.payload2).get() + bobStep = stepHandshake(rng, bobHS, readPayloadV2 = aliceStep.payload2).get() check: bobStep.transportMessage == sentTransportMessage @@ -591,13 +591,13 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # At this step, Bob writes and returns a payload - bobStep = stepHandshake(rng[], bobHS, transportMessage = sentTransportMessage).get() + bobStep = stepHandshake(rng, bobHS, transportMessage = sentTransportMessage).get() # While Alice reads and returns the (decrypted) transport message - aliceStep = stepHandshake(rng[], aliceHS, readPayloadV2 = bobStep.payload2).get() + aliceStep = stepHandshake(rng, aliceHS, readPayloadV2 = bobStep.payload2).get() check: aliceStep.transportMessage == sentTransportMessage @@ -607,14 +607,14 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # Similarly as in first step, Alice writes a Waku2 payload containing the handshake message and the (encrypted) transport message aliceStep = - stepHandshake(rng[], aliceHS, transportMessage = sentTransportMessage).get() + stepHandshake(rng, aliceHS, transportMessage = sentTransportMessage).get() # Bob reads Alice's payloads, and returns the (decrypted) transportMessage alice sent to him - bobStep = stepHandshake(rng[], bobHS, readPayloadV2 = aliceStep.payload2).get() + bobStep = stepHandshake(rng, bobHS, readPayloadV2 = aliceStep.payload2).get() check: bobStep.transportMessage == sentTransportMessage @@ -640,7 +640,7 @@ procSuite "Waku Noise": for _ in 0 .. 10: # Alice writes to Bob - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage(aliceHSResult, message, defaultMessageNametagBuffer) readMessage = readMessage(bobHSResult, payload2, defaultMessageNametagBuffer).get() @@ -649,7 +649,7 @@ procSuite "Waku Noise": message == readMessage # Bob writes to Alice - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage(bobHSResult, message, defaultMessageNametagBuffer) readMessage = readMessage(aliceHSResult, payload2, defaultMessageNametagBuffer).get() @@ -661,8 +661,8 @@ procSuite "Waku Noise": let hsPattern = NoiseHandshakePatterns["K1K1"] # We initialize Alice's and Bob's Handshake State - let aliceStaticKey = genKeyPair(rng[]) - let bobStaticKey = genKeyPair(rng[]) + let aliceStaticKey = genKeyPair(rng) + let bobStaticKey = genKeyPair(rng) # This handshake has the following pre-message pattern: # -> s @@ -696,15 +696,15 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # By being the handshake initiator, Alice writes a Waku2 payload v2 containing her handshake message # and the (encrypted) transport message aliceStep = - stepHandshake(rng[], aliceHS, transportMessage = sentTransportMessage).get() + stepHandshake(rng, aliceHS, transportMessage = sentTransportMessage).get() # Bob reads Alice's payloads, and returns the (decrypted) transport message Alice sent to him - bobStep = stepHandshake(rng[], bobHS, readPayloadV2 = aliceStep.payload2).get() + bobStep = stepHandshake(rng, bobHS, readPayloadV2 = aliceStep.payload2).get() check: bobStep.transportMessage == sentTransportMessage @@ -714,13 +714,13 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # At this step, Bob writes and returns a payload - bobStep = stepHandshake(rng[], bobHS, transportMessage = sentTransportMessage).get() + bobStep = stepHandshake(rng, bobHS, transportMessage = sentTransportMessage).get() # While Alice reads and returns the (decrypted) transport message - aliceStep = stepHandshake(rng[], aliceHS, readPayloadV2 = bobStep.payload2).get() + aliceStep = stepHandshake(rng, aliceHS, readPayloadV2 = bobStep.payload2).get() check: aliceStep.transportMessage == sentTransportMessage @@ -730,14 +730,14 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # Similarly as in first step, Alice writes a Waku2 payload containing the handshake_message and the (encrypted) transportMessage aliceStep = - stepHandshake(rng[], aliceHS, transportMessage = sentTransportMessage).get() + stepHandshake(rng, aliceHS, transportMessage = sentTransportMessage).get() # Bob reads Alice's payloads, and returns the (decrypted) transportMessage alice sent to him - bobStep = stepHandshake(rng[], bobHS, readPayloadV2 = aliceStep.payload2).get() + bobStep = stepHandshake(rng, bobHS, readPayloadV2 = aliceStep.payload2).get() check: bobStep.transportMessage == sentTransportMessage @@ -763,7 +763,7 @@ procSuite "Waku Noise": for _ in 0 .. 10: # Alice writes to Bob - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage(aliceHSResult, message, defaultMessageNametagBuffer) readMessage = readMessage(bobHSResult, payload2, defaultMessageNametagBuffer).get() @@ -772,7 +772,7 @@ procSuite "Waku Noise": message == readMessage # Bob writes to Alice - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage(bobHSResult, message, defaultMessageNametagBuffer) readMessage = readMessage(aliceHSResult, payload2, defaultMessageNametagBuffer).get() @@ -784,8 +784,8 @@ procSuite "Waku Noise": let hsPattern = NoiseHandshakePatterns["XK1"] # We initialize Alice's and Bob's Handshake State - let aliceStaticKey = genKeyPair(rng[]) - let bobStaticKey = genKeyPair(rng[]) + let aliceStaticKey = genKeyPair(rng) + let bobStaticKey = genKeyPair(rng) # This handshake has the following pre-message pattern: # <- s @@ -816,15 +816,15 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # By being the handshake initiator, Alice writes a Waku2 payload v2 containing her handshake message # and the (encrypted) transport message aliceStep = - stepHandshake(rng[], aliceHS, transportMessage = sentTransportMessage).get() + stepHandshake(rng, aliceHS, transportMessage = sentTransportMessage).get() # Bob reads Alice's payloads, and returns the (decrypted) transport message Alice sent to him - bobStep = stepHandshake(rng[], bobHS, readPayloadV2 = aliceStep.payload2).get() + bobStep = stepHandshake(rng, bobHS, readPayloadV2 = aliceStep.payload2).get() check: bobStep.transportMessage == sentTransportMessage @@ -834,13 +834,13 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # At this step, Bob writes and returns a payload - bobStep = stepHandshake(rng[], bobHS, transportMessage = sentTransportMessage).get() + bobStep = stepHandshake(rng, bobHS, transportMessage = sentTransportMessage).get() # While Alice reads and returns the (decrypted) transport message - aliceStep = stepHandshake(rng[], aliceHS, readPayloadV2 = bobStep.payload2).get() + aliceStep = stepHandshake(rng, aliceHS, readPayloadV2 = bobStep.payload2).get() check: aliceStep.transportMessage == sentTransportMessage @@ -850,14 +850,14 @@ procSuite "Waku Noise": ############### # We generate a random transport message - sentTransportMessage = randomSeqByte(rng[], 32) + sentTransportMessage = randomSeqByte(rng, 32) # Similarly as in first step, Alice writes a Waku2 payload containing the handshake message and the (encrypted) transport message aliceStep = - stepHandshake(rng[], aliceHS, transportMessage = sentTransportMessage).get() + stepHandshake(rng, aliceHS, transportMessage = sentTransportMessage).get() # Bob reads Alice's payloads, and returns the (decrypted) transport message Alice sent to him - bobStep = stepHandshake(rng[], bobHS, readPayloadV2 = aliceStep.payload2).get() + bobStep = stepHandshake(rng, bobHS, readPayloadV2 = aliceStep.payload2).get() check: bobStep.transportMessage == sentTransportMessage @@ -883,7 +883,7 @@ procSuite "Waku Noise": for _ in 0 .. 10: # Alice writes to Bob - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage(aliceHSResult, message, defaultMessageNametagBuffer) readMessage = readMessage(bobHSResult, payload2, defaultMessageNametagBuffer).get() @@ -892,7 +892,7 @@ procSuite "Waku Noise": message == readMessage # Bob writes to Alice - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage(bobHSResult, message, defaultMessageNametagBuffer) readMessage = readMessage(aliceHSResult, payload2, defaultMessageNametagBuffer).get() diff --git a/tests/test_waku_noise_sessions.nim b/tests/test_waku_noise_sessions.nim index 543653982..61eaa0038 100644 --- a/tests/test_waku_noise_sessions.nim +++ b/tests/test_waku_noise_sessions.nim @@ -25,22 +25,22 @@ procSuite "Waku Noise Sessions": let hsPattern = NoiseHandshakePatterns["WakuPairing"] # Alice static/ephemeral key initialization and commitment - let aliceStaticKey = genKeyPair(rng[]) - let aliceEphemeralKey = genKeyPair(rng[]) - let s = randomSeqByte(rng[], 32) + let aliceStaticKey = genKeyPair(rng) + let aliceEphemeralKey = genKeyPair(rng) + let s = randomSeqByte(rng, 32) let aliceCommittedStaticKey = commitPublicKey(getPublicKey(aliceStaticKey), s) # Bob static/ephemeral key initialization and commitment - let bobStaticKey = genKeyPair(rng[]) - let bobEphemeralKey = genKeyPair(rng[]) - let r = randomSeqByte(rng[], 32) + let bobStaticKey = genKeyPair(rng) + let bobEphemeralKey = genKeyPair(rng) + let r = randomSeqByte(rng, 32) let bobCommittedStaticKey = commitPublicKey(getPublicKey(bobStaticKey), r) # Content Topic information let applicationName = "waku-noise-sessions" let applicationVersion = "0.1" let shardId = "10" - let qrMessageNametag = randomSeqByte(rng[], MessageNametagLength) + let qrMessageNametag = randomSeqByte(rng, MessageNametagLength) # Out-of-band Communication @@ -133,7 +133,7 @@ procSuite "Waku Noise Sessions": # and the (encrypted) transport message # The message is sent with a messageNametag equal to the one received through the QR code aliceStep = stepHandshake( - rng[], + rng, aliceHS, transportMessage = sentTransportMessage, messageNametag = qrMessageNametag, @@ -168,7 +168,7 @@ procSuite "Waku Noise Sessions": # Bob reads Alice's payloads, and returns the (decrypted) transport message Alice sent to him # Note that Bob verifies if the received payloadv2 has the expected messageNametag set bobStep = stepHandshake( - rng[], bobHS, readPayloadV2 = readPayloadV2, messageNametag = qrMessageNametag + rng, bobHS, readPayloadV2 = readPayloadV2, messageNametag = qrMessageNametag ) .get() @@ -199,7 +199,7 @@ procSuite "Waku Noise Sessions": # At this step, Bob writes and returns a payload bobStep = stepHandshake( - rng[], + rng, bobHS, transportMessage = sentTransportMessage, messageNametag = bobMessageNametag, @@ -233,7 +233,7 @@ procSuite "Waku Noise Sessions": # While Alice reads and returns the (decrypted) transport message aliceStep = stepHandshake( - rng[], + rng, aliceHS, readPayloadV2 = readPayloadV2, messageNametag = aliceMessageNametag, @@ -265,7 +265,7 @@ procSuite "Waku Noise Sessions": # Similarly as in first step, Alice writes a Waku2 payload containing the handshake message and the (encrypted) transport message aliceStep = stepHandshake( - rng[], + rng, aliceHS, transportMessage = sentTransportMessage, messageNametag = aliceMessageNametag, @@ -299,7 +299,7 @@ procSuite "Waku Noise Sessions": # Bob reads Alice's payloads, and returns the (decrypted) transport message Alice sent to him bobStep = stepHandshake( - rng[], bobHS, readPayloadV2 = readPayloadV2, messageNametag = bobMessageNametag + rng, bobHS, readPayloadV2 = readPayloadV2, messageNametag = bobMessageNametag ) .get() @@ -333,7 +333,7 @@ procSuite "Waku Noise Sessions": # Note that we exchange more than the number of messages contained in the nametag buffer to test if they are filled correctly as the communication proceeds for i in 0 .. 10 * MessageNametagBufferSize: # Alice writes to Bob - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage( aliceHSResult, message, @@ -350,7 +350,7 @@ procSuite "Waku Noise Sessions": message == readMessage # Bob writes to Alice - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage( bobHSResult, message, @@ -368,13 +368,13 @@ procSuite "Waku Noise Sessions": # We test how nametag buffers help in detecting lost messages # Alice writes two messages to Bob, but only the second is received - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage( aliceHSResult, message, outboundMessageNametagBuffer = aliceHSResult.nametagsOutbound, ) - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage( aliceHSResult, message, @@ -390,7 +390,7 @@ procSuite "Waku Noise Sessions": # We adjust bob nametag buffer for next test (i.e. the missed message is correctly recovered) delete(bobHSResult.nametagsInbound, 2) - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage( bobHSResult, message, outboundMessageNametagBuffer = bobHSResult.nametagsOutbound ) @@ -405,7 +405,7 @@ procSuite "Waku Noise Sessions": message == readMessage # We test if a missing nametag is correctly detected - message = randomSeqByte(rng[], 32) + message = randomSeqByte(rng, 32) payload2 = writeMessage( aliceHSResult, message, diff --git a/tests/testlib/common.nim b/tests/testlib/common.nim index 216320692..78a3409db 100644 --- a/tests/testlib/common.nim +++ b/tests/testlib/common.nim @@ -1,4 +1,4 @@ -import std/[times, random], bearssl/rand, libp2p/crypto/crypto +import std/[times, random], libp2p/crypto/crypto ## Randomization @@ -11,14 +11,14 @@ proc randomize*() = ## RNG # Copied from here: https://github.com/status-im/nim-libp2p/blob/d522537b19a532bc4af94fcd146f779c1f23bad0/tests/helpers.nim#L28 -type Rng = object - rng: ref HmacDrbgContext +type RngState = object + rng: Rng # Typically having a module variable is considered bad design. This case should # be considered as an exception and it should be used only in the tests. -var rngVar: Rng +var rngVar: RngState -proc getRng(): ref HmacDrbgContext = +proc getRng(): Rng = # TODO: if `rngVar` is a threadvar like it should be, there are random and # spurious compile failures on mac - this is not gcsafe but for the # purpose of the tests, it's ok as long as we only use a single thread @@ -28,5 +28,5 @@ proc getRng(): ref HmacDrbgContext = rngVar.rng -template rng*(): ref HmacDrbgContext = +template rng*(): Rng = getRng() diff --git a/tests/testlib/wakucore.nim b/tests/testlib/wakucore.nim index 0c5b5199d..879ff8d32 100644 --- a/tests/testlib/wakucore.nim +++ b/tests/testlib/wakucore.nim @@ -22,13 +22,13 @@ proc ts*(offset = 0, origin = now()): Timestamp = # Switch proc generateEcdsaKey*(): libp2p_keys.PrivateKey = - libp2p_keys.PrivateKey.random(ECDSA, rng[]).get() + libp2p_keys.PrivateKey.random(ECDSA, rng).get() proc generateEcdsaKeyPair*(): libp2p_keys.KeyPair = - libp2p_keys.KeyPair.random(ECDSA, rng[]).get() + libp2p_keys.KeyPair.random(ECDSA, rng).get() proc generateSecp256k1Key*(): libp2p_keys.PrivateKey = - libp2p_keys.PrivateKey.random(Secp256k1, rng[]).get() + libp2p_keys.PrivateKey.random(Secp256k1, rng).get() proc ethSecp256k1Key*(hex: string): eth_keys.PrivateKey = eth_keys.PrivateKey.fromHex(hex).get() diff --git a/tests/waku_discv5/test_waku_discv5.nim b/tests/waku_discv5/test_waku_discv5.nim index 20a0c6965..cefeb4bd2 100644 --- a/tests/waku_discv5/test_waku_discv5.nim +++ b/tests/waku_discv5/test_waku_discv5.nim @@ -38,8 +38,8 @@ suite "Waku Discovery v5": let rng = eth_keys.newRng() - pk1 = eth_keys.PrivateKey.random(rng[]) - pk2 = eth_keys.PrivateKey.random(rng[]) + pk1 = eth_keys.PrivateKey.random(rng) + pk2 = eth_keys.PrivateKey.random(rng) suite "shardingPredicate": var @@ -423,7 +423,7 @@ suite "Waku Discovery v5": let myRng = libp2p_keys.newRng() var confBuilder = defaultTestWakuConfBuilder() - confBuilder.withNodeKey(libp2p_keys.PrivateKey.random(Secp256k1, myRng[])[]) + confBuilder.withNodeKey(libp2p_keys.PrivateKey.random(Secp256k1, myRng)) confBuilder.discv5Conf.withEnabled(true) confBuilder.discv5Conf.withUdpPort(9000.Port) let conf = confBuilder.build().valueOr: @@ -434,7 +434,7 @@ suite "Waku Discovery v5": (waitFor startWaku(addr waku0)).isOkOr: raiseAssert error - confBuilder.withNodeKey(crypto.PrivateKey.random(Secp256k1, myRng[])[]) + confBuilder.withNodeKey(crypto.PrivateKey.random(Secp256k1, myRng)) confBuilder.discv5Conf.withBootstrapNodes(@[waku0.node.enr.toURI()]) confBuilder.discv5Conf.withEnabled(true) confBuilder.discv5Conf.withUdpPort(9001.Port) @@ -454,7 +454,7 @@ suite "Waku Discovery v5": confBuilder.discv5Conf.withBootstrapNodes(@[waku1.node.enr.toURI()]) confBuilder.withP2pTcpPort(60003.Port) confBuilder.discv5Conf.withUdpPort(9003.Port) - confBuilder.withNodeKey(crypto.PrivateKey.random(Secp256k1, myRng[])[]) + confBuilder.withNodeKey(crypto.PrivateKey.random(Secp256k1, myRng)) let conf2 = confBuilder.build().valueOr: raiseAssert error diff --git a/tests/waku_rln_relay/utils_onchain.nim b/tests/waku_rln_relay/utils_onchain.nim index db07d3cd6..636790184 100644 --- a/tests/waku_rln_relay/utils_onchain.nim +++ b/tests/waku_rln_relay/utils_onchain.nim @@ -446,7 +446,7 @@ proc createEthAccount*( let gasPrice = Quantity(await web3.provider.eth_gasPrice()) web3.defaultAccount = accounts[0] - let pk = keys.PrivateKey.random(rng[]) + let pk = keys.PrivateKey.random(rng) let acc = Address(toCanonicalAddress(pk.toPublicKey())) var tx: TransactionArgs @@ -464,7 +464,7 @@ proc createEthAccount*( return (pk, acc) proc createEthAccount*(web3: Web3): (keys.PrivateKey, Address) = - let pk = keys.PrivateKey.random(rng[]) + let pk = keys.PrivateKey.random(rng) let acc = Address(toCanonicalAddress(pk.toPublicKey())) return (pk, acc) diff --git a/tests/wakunode_rest/test_rest_cors.nim b/tests/wakunode_rest/test_rest_cors.nim index 0393b0d72..1a965bbcb 100644 --- a/tests/wakunode_rest/test_rest_cors.nim +++ b/tests/wakunode_rest/test_rest_cors.nim @@ -22,7 +22,7 @@ type TestResponseTuple = tuple[status: int, data: string, headers: HttpTable] proc testWakuNode(): WakuNode = let - privkey = crypto.PrivateKey.random(Secp256k1, rng[]).tryGet() + privkey = crypto.PrivateKey.random(Secp256k1, rng).tryGet() bindIp = parseIpAddress("0.0.0.0") extIp = parseIpAddress("127.0.0.1") port = Port(0) diff --git a/tests/wakunode_rest/test_rest_debug.nim b/tests/wakunode_rest/test_rest_debug.nim index 4bd2e8c02..649c9b176 100644 --- a/tests/wakunode_rest/test_rest_debug.nim +++ b/tests/wakunode_rest/test_rest_debug.nim @@ -24,7 +24,7 @@ import proc testWakuNode(): WakuNode = let - privkey = crypto.PrivateKey.random(Secp256k1, rng[]).tryGet() + privkey = crypto.PrivateKey.random(Secp256k1, rng).tryGet() bindIp = parseIpAddress("0.0.0.0") extIp = parseIpAddress("127.0.0.1") port = Port(0) diff --git a/tests/wakunode_rest/test_rest_health.nim b/tests/wakunode_rest/test_rest_health.nim index 0bdb93123..08d0c518f 100644 --- a/tests/wakunode_rest/test_rest_health.nim +++ b/tests/wakunode_rest/test_rest_health.nim @@ -29,7 +29,7 @@ import proc testWakuNode(): WakuNode = let - privkey = crypto.PrivateKey.random(Secp256k1, rng[]).tryGet() + privkey = crypto.PrivateKey.random(Secp256k1, rng).tryGet() bindIp = parseIpAddress("0.0.0.0") extIp = parseIpAddress("127.0.0.1") port = Port(0) diff --git a/waku.nimble b/waku.nimble index f18e8d1a3..4e0991308 100644 --- a/waku.nimble +++ b/waku.nimble @@ -27,7 +27,7 @@ requires "nim >= 2.2.4", "toml_serialization", "faststreams", # Networking & P2P - "https://github.com/vacp2p/nim-libp2p.git#df777fc66cc100191dbefd3c222a4472b4d3b924", + "https://github.com/vacp2p/nim-libp2p.git#e41a3ab8ff143fa30e75357f81200545590f0ec6", "eth", "nat_traversal", "dnsdisc", @@ -60,6 +60,7 @@ requires "nim >= 2.2.4", # Packages not on nimble (use git URLs) requires "https://github.com/logos-messaging/nim-ffi" +requires "https://github.com/logos-co/nim-libp2p-mix" requires "https://github.com/vacp2p/nim-lsquic" requires "https://github.com/vacp2p/nim-jwt.git#057ec95eb5af0eea9c49bfe9025b3312c95dc5f2" diff --git a/waku/api/types.nim b/waku/api/types.nim index 9eae503c8..4b0348fad 100644 --- a/waku/api/types.nim +++ b/waku/api/types.nim @@ -1,6 +1,6 @@ {.push raises: [].} -import bearssl/rand, std/times, chronos +import std/times, chronos, libp2p/crypto/crypto import stew/byteutils import waku/utils/requests as request_utils import waku/waku_core/[topics/content_topic, message/message, time] @@ -19,7 +19,7 @@ type PartiallyConnected Connected -proc new*(T: typedesc[RequestId], rng: ref HmacDrbgContext): T = +proc new*(T: typedesc[RequestId], rng: crypto.Rng): T = ## Generate a new RequestId using the provided RNG. RequestId(request_utils.generateRequestId(rng)) diff --git a/waku/discovery/autonat_service.nim b/waku/discovery/autonat_service.nim index fb1f7dbc3..16d014708 100644 --- a/waku/discovery/autonat_service.nim +++ b/waku/discovery/autonat_service.nim @@ -1,13 +1,13 @@ import chronos, chronicles, - bearssl/rand, + libp2p/crypto/crypto, libp2p/protocols/connectivity/autonat/client, libp2p/protocols/connectivity/autonat/service const AutonatCheckInterval = Opt.some(chronos.seconds(30)) -proc getAutonatService*(rng: ref HmacDrbgContext): AutonatService = +proc getAutonatService*(rng: crypto.Rng): AutonatService = ## AutonatService request other peers to dial us back ## flagging us as Reachable or NotReachable. ## minConfidence is used as threshold to determine the state. diff --git a/waku/discovery/waku_discv5.nim b/waku/discovery/waku_discv5.nim index 0eb329fa4..de239508f 100644 --- a/waku/discovery/waku_discv5.nim +++ b/waku/discovery/waku_discv5.nim @@ -7,6 +7,8 @@ import chronicles, metrics, libp2p/multiaddress, + libp2p/crypto/crypto, + libp2p/crypto/rng, eth/keys as eth_keys, eth/p2p/discoveryv5/node, eth/p2p/discoveryv5/protocol @@ -80,7 +82,7 @@ proc shardingPredicate*( proc new*( T: type WakuDiscoveryV5, - rng: ref HmacDrbgContext, + rng: crypto.Rng, conf: WakuDiscoveryV5Config, record: Option[waku_enr.Record], peerManager: Option[PeerManager] = none(PeerManager), @@ -88,7 +90,7 @@ proc new*( newAsyncEventQueue[SubscriptionEvent](30), ): T = let protocol = newProtocol( - rng = rng, + rng = bearSslDrbgRef(rng), config = conf.discv5Config.get(protocol.defaultDiscoveryConfig), bindPort = conf.port, bindIp = conf.address, @@ -405,7 +407,7 @@ proc setupDiscoveryV5*( nodeTopicSubscriptionQueue: AsyncEventQueue[SubscriptionEvent], conf: Discv5Conf, dynamicBootstrapNodes: seq[RemotePeerInfo], - rng: ref HmacDrbgContext, + rng: crypto.Rng, key: crypto.PrivateKey, p2pListenAddress: IpAddress, portsShift: uint16, diff --git a/waku/discovery/waku_kademlia.nim b/waku/discovery/waku_kademlia.nim index f88430a40..a0488fb45 100644 --- a/waku/discovery/waku_kademlia.nim +++ b/waku/discovery/waku_kademlia.nim @@ -7,7 +7,7 @@ import results, libp2p/crypto/curve25519, libp2p/crypto/crypto, - libp2p/protocols/mix/mix_protocol, + libp2p_mix/mix_protocol, libp2p/[peerid, multiaddress, switch], libp2p/extended_peer_record, libp2p/protocols/[kademlia, service_discovery], @@ -174,6 +174,7 @@ proc new*( selector = ExtEntrySelector(), disableBootstrapping = disableBootstrapping, ), + rng = switch.rng, # change from defaults for local testing discoConfig = ServiceDiscoveryConfig.new(advertExpiry = 60.secs, ipSimCoefficient = 0.0), diff --git a/waku/factory/builder.nim b/waku/factory/builder.nim index 5bd343223..b333150ae 100644 --- a/waku/factory/builder.nim +++ b/waku/factory/builder.nim @@ -21,7 +21,7 @@ import type WakuNodeBuilder* = object # General - nodeRng: Option[ref crypto.HmacDrbgContext] + nodeRng: Option[crypto.Rng] nodeKey: Option[crypto.PrivateKey] netConfig: Option[NetConfig] record: Option[enr.Record] @@ -57,7 +57,7 @@ proc init*(T: type WakuNodeBuilder): WakuNodeBuilder = ## General -proc withRng*(builder: var WakuNodeBuilder, rng: ref crypto.HmacDrbgContext) = +proc withRng*(builder: var WakuNodeBuilder, rng: crypto.Rng) = builder.nodeRng = some(rng) proc withNodeKey*(builder: var WakuNodeBuilder, nodeKey: crypto.PrivateKey) = @@ -157,7 +157,7 @@ proc withSwitchConfiguration*( ## Build proc build*(builder: WakuNodeBuilder): Result[WakuNode, string] = - var rng: ref crypto.HmacDrbgContext + var rng: crypto.Rng if builder.nodeRng.isNone(): rng = crypto.newRng() else: diff --git a/waku/factory/conf_builder/mix_conf_builder.nim b/waku/factory/conf_builder/mix_conf_builder.nim index 8a4f5b5f1..b3198a309 100644 --- a/waku/factory/conf_builder/mix_conf_builder.nim +++ b/waku/factory/conf_builder/mix_conf_builder.nim @@ -1,5 +1,5 @@ import chronicles, std/options, results -import libp2p/crypto/crypto, libp2p/crypto/curve25519, libp2p/protocols/mix/curve25519 +import libp2p/crypto/crypto, libp2p/crypto/curve25519, libp2p_mix/curve25519 import ../waku_conf, waku/waku_mix logScope: diff --git a/waku/factory/conf_builder/waku_conf_builder.nim b/waku/factory/conf_builder/waku_conf_builder.nim index 78dbd9eb9..1e30b6e24 100644 --- a/waku/factory/conf_builder/waku_conf_builder.nim +++ b/waku/factory/conf_builder/waku_conf_builder.nim @@ -283,13 +283,13 @@ proc withStaticNodes*(builder: var WakuConfBuilder, staticNodes: seq[string]) = ## Building proc nodeKey( - builder: WakuConfBuilder, rng: ref HmacDrbgContext + builder: WakuConfBuilder, rng: crypto.Rng ): Result[crypto.PrivateKey, string] = if builder.nodeKey.isSome(): return ok(builder.nodeKey.get()) else: warn "missing node key, generating new set" - let nodeKey = crypto.PrivateKey.random(Secp256k1, rng[]).valueOr: + let nodeKey = crypto.PrivateKey.random(Secp256k1, rng).valueOr: error "Failed to generate key", error = error return err("Failed to generate key: " & $error) return ok(nodeKey) @@ -433,7 +433,7 @@ proc applyNetworkConf(builder: var WakuConfBuilder) = warn "Failed to process entry nodes from network conf", error = processed.error() proc build*( - builder: var WakuConfBuilder, rng: ref HmacDrbgContext = crypto.newRng() + builder: var WakuConfBuilder, rng: crypto.Rng = crypto.newRng() ): Result[WakuConf, string] = ## Return a WakuConf that contains all mandatory parameters ## Applies some sane defaults that are applicable across any usage diff --git a/waku/factory/node_factory.nim b/waku/factory/node_factory.nim index dce6322f1..c742e1c29 100644 --- a/waku/factory/node_factory.nim +++ b/waku/factory/node_factory.nim @@ -9,7 +9,7 @@ import libp2p/crypto/crypto, libp2p/crypto/curve25519, libp2p/extended_peer_record, - libp2p/protocols/mix/mix_protocol + libp2p_mix/mix_protocol import ./internal_config, @@ -57,7 +57,7 @@ proc setupPeerStorage(): Result[Option[WakuPeerStorage], string] = proc initNode( conf: WakuConf, netConfig: NetConfig, - rng: ref HmacDrbgContext, + rng: crypto.Rng, record: enr.Record, peerStore: Option[WakuPeerStorage], relay: Relay, @@ -483,7 +483,7 @@ proc startNode*( return ok() proc setupNode*( - wakuConf: WakuConf, rng: ref HmacDrbgContext = crypto.newRng(), relay: Relay + wakuConf: WakuConf, rng: crypto.Rng = crypto.newRng(), relay: Relay ): Future[Result[WakuNode, string]] {.async.} = let netConfig = ( await networkConfiguration( diff --git a/waku/factory/waku.nim b/waku/factory/waku.nim index 45e0edee0..66bb71fcb 100644 --- a/waku/factory/waku.nim +++ b/waku/factory/waku.nim @@ -59,7 +59,7 @@ const git_version* {.strdefine.} = "n/a" type Waku* = ref object stateInfo*: WakuStateInfo conf*: WakuConf - rng*: ref HmacDrbgContext + rng*: crypto.Rng key: crypto.PrivateKey @@ -81,7 +81,7 @@ type Waku* = ref object brokerCtx*: BrokerContext proc setupSwitchServices( - waku: Waku, conf: WakuConf, circuitRelay: Relay, rng: ref HmacDrbgContext + waku: Waku, conf: WakuConf, circuitRelay: Relay, rng: crypto.Rng ) = proc onReservation(addresses: seq[MultiAddress]) {.gcsafe, raises: [].} = info "circuit relay handler new reserve event", diff --git a/waku/node/kernel_api/lightpush.nim b/waku/node/kernel_api/lightpush.nim index ffe2afdac..b3ef68eba 100644 --- a/waku/node/kernel_api/lightpush.nim +++ b/waku/node/kernel_api/lightpush.nim @@ -17,7 +17,7 @@ import libp2p/transports/tcptransport, libp2p/transports/wstransport, libp2p/utility, - libp2p/protocols/mix + libp2p_mix import ../waku_node, diff --git a/waku/node/peer_manager/waku_peer_store.nim b/waku/node/peer_manager/waku_peer_store.nim index 93ac9ad2e..fbfd0041d 100644 --- a/waku/node/peer_manager/waku_peer_store.nim +++ b/waku/node/peer_manager/waku_peer_store.nim @@ -7,7 +7,8 @@ import eth/p2p/discoveryv5/enr, libp2p/builders, libp2p/peerstore, - libp2p/crypto/curve25519 + libp2p/crypto/curve25519, + libp2p_mix/pool import ../../waku_core, diff --git a/waku/node/waku_node.nim b/waku/node/waku_node.nim index e15153785..78f2949cc 100644 --- a/waku/node/waku_node.nim +++ b/waku/node/waku_node.nim @@ -8,7 +8,6 @@ import results, eth/keys, nimcrypto, - bearssl/rand, stew/byteutils, eth/p2p/discoveryv5/enr, libp2p/crypto/crypto, @@ -23,8 +22,8 @@ import libp2p/transports/wstransport, libp2p/utility, libp2p/utils/offsettedseq, - libp2p/protocols/mix, - libp2p/protocols/mix/mix_protocol + libp2p_mix, + libp2p_mix/mix_protocol import waku/[ @@ -126,7 +125,7 @@ type wakuAutoSharding*: Option[Sharding] enr*: enr.Record libp2pPing*: Ping - rng*: ref rand.HmacDrbgContext + rng*: crypto.Rng brokerCtx*: BrokerContext wakuRendezvous*: WakuRendezVous wakuRendezvousClient*: rendezvous_client.WakuRendezVousClient @@ -206,7 +205,7 @@ proc new*( peerManager: PeerManager, rateLimitSettings: ProtocolRateLimitSettings = DefaultProtocolRateLimit, # TODO: make this argument required after tests are updated - rng: ref HmacDrbgContext = crypto.newRng(), + rng: crypto.Rng = crypto.newRng(), ): T {.raises: [Defect, LPError, IOError, TLSStreamProtocolError].} = ## Creates a Waku Node instance. diff --git a/waku/node/waku_switch.nim b/waku/node/waku_switch.nim index e658bd0e4..dda378030 100644 --- a/waku/node/waku_switch.nim +++ b/waku/node/waku_switch.nim @@ -64,7 +64,7 @@ proc newWakuSwitch*( wsAddress = none(MultiAddress), secureManagers: openarray[SecureProtocol] = [SecureProtocol.Noise], transportFlags: set[ServerFlags] = {}, - rng: ref HmacDrbgContext, + rng: crypto.Rng, inTimeout: Duration = 5.minutes, outTimeout: Duration = 5.minutes, maxConnections = MaxConnections, @@ -78,7 +78,7 @@ proc newWakuSwitch*( secureCertPath: string = "", agentString = none(string), # defaults to nim-libp2p version peerStoreCapacity = none(int), # defaults to 1.25 maxConnections - rendezvous: RendezVous = nil, + rendezvous: RendezVousConfig = nil, circuitRelay: Relay, maxNumRelays: int = 5, ): Switch {.raises: [Defect, IOError, LPError].} = diff --git a/waku/utils/requests.nim b/waku/utils/requests.nim index d9afd2887..a7fd9a2a9 100644 --- a/waku/utils/requests.nim +++ b/waku/utils/requests.nim @@ -2,9 +2,9 @@ {.push raises: [].} -import bearssl/rand, stew/byteutils +import libp2p/crypto/crypto, stew/byteutils -proc generateRequestId*(rng: ref HmacDrbgContext): string = +proc generateRequestId*(rng: crypto.Rng): string = var bytes: array[10, byte] - hmacDrbgGenerate(rng[], bytes) + rng.generate(bytes) return byteutils.toHex(bytes) diff --git a/waku/waku_enr/capabilities.nim b/waku/waku_enr/capabilities.nim index 26899fbb4..6a5b5338f 100644 --- a/waku/waku_enr/capabilities.nim +++ b/waku/waku_enr/capabilities.nim @@ -3,7 +3,7 @@ import std/[options, bitops, sequtils, net, tables], results, eth/keys, libp2p/crypto/crypto import ../common/enr, ../waku_core/codecs -import libp2p/protocols/mix +import libp2p_mix const CapabilitiesEnrField* = "waku2" diff --git a/waku/waku_filter_v2/client.nim b/waku/waku_filter_v2/client.nim index 265bf5e7b..439cfd29e 100644 --- a/waku/waku_filter_v2/client.nim +++ b/waku/waku_filter_v2/client.nim @@ -7,7 +7,7 @@ import chronicles, chronos, libp2p/protocols/protocol, - bearssl/rand, + libp2p/crypto/crypto, stew/byteutils import waku/ @@ -22,13 +22,13 @@ logScope: type WakuFilterClient* = ref object of LPProtocol brokerCtx: BrokerContext - rng: ref HmacDrbgContext + rng: Rng peerManager: PeerManager pushHandlers: seq[FilterPushHandler] -func generateRequestId(rng: ref HmacDrbgContext): string = +func generateRequestId(rng: crypto.Rng): string = var bytes: array[10, byte] - hmacDrbgGenerate(rng[], bytes) + rng.generate(bytes) return byteutils.toHex(bytes) proc sendSubscribeRequest( @@ -210,7 +210,7 @@ proc initProtocolHandler(wfc: WakuFilterClient) = wfc.codec = WakuFilterPushCodec proc new*( - T: type WakuFilterClient, peerManager: PeerManager, rng: ref HmacDrbgContext + T: type WakuFilterClient, peerManager: PeerManager, rng: crypto.Rng ): T = let brokerCtx = globalBrokerContext() let wfc = WakuFilterClient( diff --git a/waku/waku_lightpush/client.nim b/waku/waku_lightpush/client.nim index fd12c49d2..e0c46d403 100644 --- a/waku/waku_lightpush/client.nim +++ b/waku/waku_lightpush/client.nim @@ -1,6 +1,6 @@ {.push raises: [].} -import std/options, results, chronicles, chronos, metrics, bearssl/rand, stew/byteutils +import std/options, results, chronicles, chronos, metrics, libp2p/crypto/crypto, stew/byteutils import libp2p/peerid, libp2p/stream/connection import ../waku_core/peers, @@ -16,11 +16,11 @@ logScope: topics = "waku lightpush client" type WakuLightPushClient* = ref object - rng*: ref rand.HmacDrbgContext + rng*: Rng peerManager*: PeerManager proc new*( - T: type WakuLightPushClient, peerManager: PeerManager, rng: ref rand.HmacDrbgContext + T: type WakuLightPushClient, peerManager: PeerManager, rng: crypto.Rng ): T = WakuLightPushClient(peerManager: peerManager, rng: rng) diff --git a/waku/waku_lightpush/protocol.nim b/waku/waku_lightpush/protocol.nim index 8336f4dfc..a8e8173e0 100644 --- a/waku/waku_lightpush/protocol.nim +++ b/waku/waku_lightpush/protocol.nim @@ -7,7 +7,7 @@ import chronicles, chronos, metrics, - bearssl/rand + libp2p/crypto/crypto import ../node/peer_manager/peer_manager, ../waku_core, @@ -22,7 +22,7 @@ logScope: topics = "waku lightpush" type WakuLightPush* = ref object of LPProtocol - rng*: ref rand.HmacDrbgContext + rng*: Rng peerManager*: PeerManager pushHandler*: PushMessageHandler requestRateLimiter*: RequestRateLimiter @@ -156,7 +156,7 @@ proc initProtocolHandler(wl: WakuLightPush) = proc new*( T: type WakuLightPush, peerManager: PeerManager, - rng: ref rand.HmacDrbgContext, + rng: crypto.Rng, pushHandler: PushMessageHandler, autoSharding: Option[Sharding], rateLimitSetting: Option[RateLimitSetting] = none[RateLimitSetting](), diff --git a/waku/waku_lightpush_legacy/client.nim b/waku/waku_lightpush_legacy/client.nim index ab489bec9..ce69bee60 100644 --- a/waku/waku_lightpush_legacy/client.nim +++ b/waku/waku_lightpush_legacy/client.nim @@ -1,6 +1,6 @@ {.push raises: [].} -import std/options, results, chronicles, chronos, metrics, bearssl/rand, stew/byteutils +import std/options, results, chronicles, chronos, metrics, libp2p/crypto/crypto, stew/byteutils import libp2p/peerid import ../waku_core/peers, @@ -17,12 +17,12 @@ logScope: type WakuLegacyLightPushClient* = ref object peerManager*: PeerManager - rng*: ref rand.HmacDrbgContext + rng*: Rng proc new*( T: type WakuLegacyLightPushClient, peerManager: PeerManager, - rng: ref rand.HmacDrbgContext, + rng: crypto.Rng, ): T = WakuLegacyLightPushClient(peerManager: peerManager, rng: rng) diff --git a/waku/waku_lightpush_legacy/protocol.nim b/waku/waku_lightpush_legacy/protocol.nim index f5ed60134..47fb9030b 100644 --- a/waku/waku_lightpush_legacy/protocol.nim +++ b/waku/waku_lightpush_legacy/protocol.nim @@ -1,6 +1,6 @@ {.push raises: [].} -import std/options, results, stew/byteutils, chronicles, chronos, metrics, bearssl/rand +import std/options, results, stew/byteutils, chronicles, chronos, metrics, libp2p/crypto/crypto import ../node/peer_manager/peer_manager, ../waku_core, @@ -14,7 +14,7 @@ logScope: topics = "waku lightpush legacy" type WakuLegacyLightPush* = ref object of LPProtocol - rng*: ref rand.HmacDrbgContext + rng*: Rng peerManager*: PeerManager pushHandler*: PushMessageHandler requestRateLimiter*: RequestRateLimiter @@ -116,7 +116,7 @@ proc initProtocolHandler(wl: WakuLegacyLightPush) = proc new*( T: type WakuLegacyLightPush, peerManager: PeerManager, - rng: ref rand.HmacDrbgContext, + rng: crypto.Rng, pushHandler: PushMessageHandler, rateLimitSetting: Option[RateLimitSetting] = none[RateLimitSetting](), ): T = diff --git a/waku/waku_mix/protocol.nim b/waku/waku_mix/protocol.nim index fb6b7ef6d..ddaa384c1 100644 --- a/waku/waku_mix/protocol.nim +++ b/waku/waku_mix/protocol.nim @@ -5,12 +5,12 @@ import chronicles, std/options, chronos, results, metrics import libp2p/crypto/curve25519, libp2p/crypto/crypto, - libp2p/protocols/mix, - libp2p/protocols/mix/mix_node, - libp2p/protocols/mix/mix_protocol, - libp2p/protocols/mix/mix_metrics, - libp2p/protocols/mix/delay_strategy, - libp2p/protocols/mix/delay, + libp2p_mix, + libp2p_mix/mix_node, + libp2p_mix/mix_protocol, + libp2p_mix/mix_metrics, + libp2p_mix/delay_strategy, + libp2p_mix/delay, libp2p/[multiaddress, peerid, switch], libp2p/extended_peer_record, eth/common/keys diff --git a/waku/waku_noise/noise.nim b/waku/waku_noise/noise.nim index 9c5dd76e7..c8a08468b 100644 --- a/waku/waku_noise/noise.nim +++ b/waku/waku_noise/noise.nim @@ -12,7 +12,7 @@ import std/[options, strutils] import stew/byteutils import chronos import chronicles -import bearssl/rand +import libp2p/crypto/crypto import stew/endians2 import nimcrypto/[sha2, hmac] @@ -168,9 +168,9 @@ proc setCipherStateKey*(cs: var CipherState, key: ChaChaPolyKey) = cs.k = key # Generates a random Symmetric Cipher State for test purposes -proc randomCipherState*(rng: var HmacDrbgContext, nonce: uint64 = 0): CipherState = +proc randomCipherState*(rng: crypto.Rng, nonce: uint64 = 0): CipherState = var randomCipherState: CipherState - hmacDrbgGenerate(rng, randomCipherState.k) + rng.generate(randomCipherState.k) setNonce(randomCipherState, nonce) return randomCipherState diff --git a/waku/waku_noise/noise_handshake_processing.nim b/waku/waku_noise/noise_handshake_processing.nim index 8b84bf958..5a2262e32 100644 --- a/waku/waku_noise/noise_handshake_processing.nim +++ b/waku/waku_noise/noise_handshake_processing.nim @@ -7,7 +7,7 @@ import std/[options, strutils, tables] import chronos import chronicles -import bearssl/rand +import libp2p/crypto/crypto import results import libp2p/crypto/[chacha20poly1305, curve25519] @@ -237,7 +237,7 @@ proc processMessagePatternPayload( # We process an input handshake message according to current handshake state and we return the next handshake step's handshake message proc processMessagePatternTokens( - rng: var rand.HmacDrbgContext, + rng: crypto.Rng, hs: var HandshakeState, inputHandshakeMessage: seq[NoisePublicKey] = @[], ): Result[seq[NoisePublicKey], cstring] {. @@ -480,7 +480,7 @@ proc initialize*( # If the user is writing the handshake message, the transport message (if not empty) and eventually a non-empty message nametag has to be passed to transportMessage and messageNametag and readPayloadV2 can be left to its default value # It the user is reading the handshake message, the read payload v2 has to be passed to readPayloadV2 and the transportMessage can be left to its default values. Decryption is skipped if the payloadv2 read doesn't have a message nametag equal to messageNametag (empty input nametags are converted to all-0 MessageNametagLength bytes arrays) proc stepHandshake*( - rng: var rand.HmacDrbgContext, + rng: crypto.Rng, hs: var HandshakeState, readPayloadV2: PayloadV2 = default(PayloadV2), transportMessage: seq[byte] = @[], diff --git a/waku/waku_noise/noise_utils.nim b/waku/waku_noise/noise_utils.nim index 177dc6557..e168f47ed 100644 --- a/waku/waku_noise/noise_utils.nim +++ b/waku/waku_noise/noise_utils.nim @@ -8,7 +8,7 @@ import std/[algorithm, base64, oids, options, strutils, tables, sequtils] import chronos import chronicles -import bearssl/rand +import libp2p/crypto/crypto import results import stew/[endians2, byteutils] import nimcrypto/sha2 @@ -28,9 +28,9 @@ logScope: ################################# # Generates random byte sequences of given size -proc randomSeqByte*(rng: var HmacDrbgContext, size: int): seq[byte] = +proc randomSeqByte*(rng: crypto.Rng, size: int): seq[byte] = var output = newSeq[byte](size.uint32) - hmacDrbgGenerate(rng, output) + rng.generate(output) return output # Pads a payload according to PKCS#7 as per RFC 5652 https://datatracker.ietf.org/doc/html/rfc5652#section-6.3 @@ -149,7 +149,7 @@ proc isDefault*[T](value: T): bool = ################################# # Generate random (public, private) Elliptic Curve key pairs -proc genKeyPair*(rng: var HmacDrbgContext): KeyPair = +proc genKeyPair*(rng: crypto.Rng): KeyPair = var keyPair: KeyPair keyPair.privateKey = EllipticCurveKey.random(rng) keyPair.publicKey = keyPair.privateKey.public() @@ -319,18 +319,18 @@ proc dh*(private: EllipticCurveKey, public: EllipticCurveKey): EllipticCurveKey ################################# # Generates a random ChaChaPolyKey for testing encryption/decryption -proc randomChaChaPolyKey*(rng: var HmacDrbgContext): ChaChaPolyKey = +proc randomChaChaPolyKey*(rng: crypto.Rng): ChaChaPolyKey = var key: ChaChaPolyKey - hmacDrbgGenerate(rng, key) + rng.generate(key) return key # Generates a random ChaChaPoly Cipher State for testing encryption/decryption -proc randomChaChaPolyCipherState*(rng: var HmacDrbgContext): ChaChaPolyCipherState = +proc randomChaChaPolyCipherState*(rng: crypto.Rng): ChaChaPolyCipherState = var randomCipherState: ChaChaPolyCipherState randomCipherState.k = randomChaChaPolyKey(rng) - hmacDrbgGenerate(rng, randomCipherState.nonce) + rng.generate(randomCipherState.nonce) randomCipherState.ad = newSeq[byte](32) - hmacDrbgGenerate(rng, randomCipherState.ad) + rng.generate(randomCipherState.ad) return randomCipherState ################################################################# @@ -351,7 +351,7 @@ proc toNoisePublicKey*(publicKey: EllipticCurveKey): NoisePublicKey = return noisePublicKey # Generates a random Noise public key -proc genNoisePublicKey*(rng: var HmacDrbgContext): NoisePublicKey = +proc genNoisePublicKey*(rng: crypto.Rng): NoisePublicKey = var noisePublicKey: NoisePublicKey # We generate a random key pair let keyPair: KeyPair = genKeyPair(rng) @@ -446,7 +446,7 @@ proc `==`*(p1, p2: PayloadV2): bool = (p1.transportMessage == p2.transportMessage) # Generates a random PayloadV2 -proc randomPayloadV2*(rng: var HmacDrbgContext): PayloadV2 = +proc randomPayloadV2*(rng: crypto.Rng): PayloadV2 = var payload2: PayloadV2 # We set a random messageNametag let randMessageNametag = randomSeqByte(rng, MessageNametagLength) diff --git a/waku/waku_relay/protocol.nim b/waku/waku_relay/protocol.nim index e7b2c99cb..e8377438e 100644 --- a/waku/waku_relay/protocol.nim +++ b/waku/waku_relay/protocol.nim @@ -366,7 +366,8 @@ proc new*( triggerSelf = true, msgIdProvider = defaultMessageIdProvider, maxMessageSize = maxMessageSize, - parameters = GossipsubParameters, + rng = switch.rng, + parameters = GossipSubParams.init(), ) w.brokerCtx = globalBrokerContext() diff --git a/waku/waku_rendezvous/client.nim b/waku/waku_rendezvous/client.nim index 62c0de848..bf43a4a71 100644 --- a/waku/waku_rendezvous/client.nim +++ b/waku/waku_rendezvous/client.nim @@ -106,10 +106,10 @@ proc new*( switch: switch, rng: rng, sema: newAsyncSemaphore(MaxSimultanesousAdvertisements), - minDuration: rendezvous.MinimumAcceptedDuration, - maxDuration: rendezvous.MaximumDuration, - minTTL: rendezvous.MinimumAcceptedDuration.seconds.uint64, - maxTTL: rendezvous.MaximumDuration.seconds.uint64, + config: RendezVousConfig.new( + minDuration = rendezvous.MinimumDuration, + maxDuration = rendezvous.MaximumDuration, + ), peers: @[], # Will be populated from selectPeer calls cookiesSaved: initTable[PeerId, Table[string, seq[byte]]](), peerRecordValidator: checkWakuPeerRecord, diff --git a/waku/waku_rendezvous/protocol.nim b/waku/waku_rendezvous/protocol.nim index 0e9b0aa76..9d5acb46d 100644 --- a/waku/waku_rendezvous/protocol.nim +++ b/waku/waku_rendezvous/protocol.nim @@ -50,7 +50,7 @@ proc advertise*( self: WakuRendezVous, namespace: string, peers: seq[PeerId], - ttl: timer.Duration = self.minDuration, + ttl: timer.Duration = rendezvous.MinimumDuration, ): Future[Result[void, string]] {.async: (raises: []).} = trace "advertising via waku rendezvous", namespace = namespace, ttl = ttl, peers = $peers, peerRecord = $self.getPeerRecord() @@ -153,14 +153,14 @@ proc new*( let rng = newRng() let wrv = T( rng: rng, - salt: string.fromBytes(generateBytes(rng[], 8)), + salt: string.fromBytes(generateBytes(rng, 8)), registered: initOffsettedSeq[RegisteredData](), expiredDT: Moment.now() - 1.days, sema: newAsyncSemaphore(SemaphoreDefaultSize), - minDuration: rendezvous.MinimumAcceptedDuration, - maxDuration: rendezvous.MaximumDuration, - minTTL: rendezvous.MinimumAcceptedDuration.seconds.uint64, - maxTTL: rendezvous.MaximumDuration.seconds.uint64, + config: RendezVousConfig.new( + minDuration = rendezvous.MinimumDuration, + maxDuration = rendezvous.MaximumDuration, + ), peerRecordValidator: checkWakuPeerRecord, ) diff --git a/waku/waku_store/client.nim b/waku/waku_store/client.nim index 5b261af47..857a5e0bf 100644 --- a/waku/waku_store/client.nim +++ b/waku/waku_store/client.nim @@ -6,7 +6,7 @@ import chronicles, chronos, metrics, - bearssl/rand + libp2p/crypto/crypto import ../node/peer_manager, ../utils/requests, ./protocol_metrics, ./common, ./rpc_codec @@ -20,11 +20,11 @@ const MaxQueryRetries = 5 # Maximum number of store peers to try before giving u type WakuStoreClient* = ref object peerManager: PeerManager - rng: ref rand.HmacDrbgContext + rng: Rng storeMsgMetricsPerShard*: Table[string, float64] proc new*( - T: type WakuStoreClient, peerManager: PeerManager, rng: ref rand.HmacDrbgContext + T: type WakuStoreClient, peerManager: PeerManager, rng: crypto.Rng ): T {.gcsafe.} = WakuStoreClient(peerManager: peerManager, rng: rng) diff --git a/waku/waku_store/protocol.nim b/waku/waku_store/protocol.nim index 891c6a93c..c40e3667a 100644 --- a/waku/waku_store/protocol.nim +++ b/waku/waku_store/protocol.nim @@ -8,7 +8,6 @@ import results, chronicles, chronos, - bearssl/rand, libp2p/crypto/crypto, libp2p/protocols/protocol, libp2p/protobuf/minprotobuf, @@ -30,7 +29,7 @@ type StoreQueryRequestHandler* = type WakuStore* = ref object of LPProtocol peerManager: PeerManager - rng: ref rand.HmacDrbgContext + rng: Rng requestHandler*: StoreQueryRequestHandler requestRateLimiter*: RequestRateLimiter @@ -154,7 +153,7 @@ proc initProtocolHandler(self: WakuStore) = proc new*( T: type WakuStore, peerManager: PeerManager, - rng: ref rand.HmacDrbgContext, + rng: crypto.Rng, requestHandler: StoreQueryRequestHandler, rateLimitSetting: Option[RateLimitSetting] = none[RateLimitSetting](), ): T =