Skip to content

Commit

Permalink
use a mock rng in tests
Browse files Browse the repository at this point in the history
  • Loading branch information
diegomrsantos committed Apr 18, 2024
1 parent b30b265 commit ffe80dc
Show file tree
Hide file tree
Showing 42 changed files with 378 additions and 221 deletions.
12 changes: 6 additions & 6 deletions libp2p/builders.nim
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ import
protocols/connectivity/[autonat/server, relay/relay, relay/client, relay/rtransport],
connmanager, upgrademngrs/muxedupgrade, observedaddrmanager,
nameresolving/nameresolver,
errors, utility
errors, utility, utils/random/securerng

export
switch, peerid, peerinfo, connection, multiaddress, crypto, errors
Expand All @@ -44,7 +44,7 @@ type
secureManagers: seq[SecureProtocol]
muxers: seq[MuxerProvider]
transports: seq[TransportProvider]
rng: ref HmacDrbgContext
rng: Rng
maxConnections: int
maxIn: int
sendSignedPeerRecord: bool
Expand Down Expand Up @@ -149,7 +149,7 @@ proc withTransport*(b: SwitchBuilder, prov: TransportProvider): SwitchBuilder {.
proc withTcpTransport*(b: SwitchBuilder, flags: set[ServerFlags] = {}): SwitchBuilder {.public.} =
b.withTransport(proc(upgr: Upgrade): Transport = TcpTransport.new(flags, upgr))

proc withRng*(b: SwitchBuilder, rng: ref HmacDrbgContext): SwitchBuilder {.public.} =
proc withRng*(b: SwitchBuilder, rng: Rng): SwitchBuilder {.public.} =
b.rng = rng
b

Expand Down Expand Up @@ -215,7 +215,7 @@ proc build*(b: SwitchBuilder): Switch
if b.rng == nil: # newRng could fail
raise newException(Defect, "Cannot initialize RNG")

let pkRes = PrivateKey.random(b.rng[])
let pkRes = PrivateKey.random(b.rng)
let
seckey = b.privKey.get(otherwise = pkRes.expect("Expected default Private Key"))

Expand Down Expand Up @@ -253,7 +253,7 @@ proc build*(b: SwitchBuilder): Switch
b.secureManagers &= SecureProtocol.Noise

if isNil(b.rng):
b.rng = newRng()
b.rng = SecureRng.new()

let peerStore = block:
b.peerStoreCapacity.withValue(capacity):
Expand Down Expand Up @@ -297,7 +297,7 @@ proc newStandardSwitch*(
SecureProtocol.Noise,
],
transportFlags: set[ServerFlags] = {},
rng = newRng(),
rng: Rng = SecureRng.new(),
inTimeout: Duration = 5.minutes,
outTimeout: Duration = 5.minutes,
maxConnections = MaxConnections,
Expand Down
8 changes: 4 additions & 4 deletions libp2p/crypto/crypto.nim
Original file line number Diff line number Diff line change
Expand Up @@ -188,7 +188,7 @@ proc shuffle*[T](
swap(x[i], x[y])

proc random*(T: typedesc[PrivateKey], scheme: PKScheme,
rng: var HmacDrbgContext,
rng: Rng,
bits = RsaDefaultKeySize): CryptoResult[PrivateKey] =
## Generate random private key for scheme ``scheme``.
##
Expand Down Expand Up @@ -220,7 +220,7 @@ proc random*(T: typedesc[PrivateKey], scheme: PKScheme,
else:
err(SchemeError)

proc random*(T: typedesc[PrivateKey], rng: var HmacDrbgContext,
proc random*(T: typedesc[PrivateKey], rng: Rng,
bits = RsaDefaultKeySize): CryptoResult[PrivateKey] =
## Generate random private key using default public-key cryptography scheme.
##
Expand All @@ -244,7 +244,7 @@ proc random*(T: typedesc[PrivateKey], rng: var HmacDrbgContext,
err(SchemeError)

proc random*(T: typedesc[KeyPair], scheme: PKScheme,
rng: var HmacDrbgContext,
rng: Rng,
bits = RsaDefaultKeySize): CryptoResult[KeyPair] =
## Generate random key pair for scheme ``scheme``.
##
Expand Down Expand Up @@ -284,7 +284,7 @@ proc random*(T: typedesc[KeyPair], scheme: PKScheme,
else:
err(SchemeError)

proc random*(T: typedesc[KeyPair], rng: var HmacDrbgContext,
proc random*(T: typedesc[KeyPair], rng: Rng,
bits = RsaDefaultKeySize): CryptoResult[KeyPair] =
## Generate random private pair of keys using default public-key cryptography
## scheme.
Expand Down
8 changes: 5 additions & 3 deletions libp2p/crypto/curve25519.nim
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,9 @@
import bearssl/[ec, rand]
import stew/results
from stew/assign2 import assign

import ../utils/random/rng

export results

const
Expand Down Expand Up @@ -79,11 +82,10 @@ proc mulgen(_: type[Curve25519], dst: var Curve25519Key, point: Curve25519Key) =
proc public*(private: Curve25519Key): Curve25519Key =
Curve25519.mulgen(result, private)

proc random*(_: type[Curve25519Key], rng: var HmacDrbgContext): Curve25519Key =
proc random*(_: type[Curve25519Key], rng: Rng): Curve25519Key =
var res: Curve25519Key
let defaultBrEc = ecGetDefault()
let len = ecKeygen(
addr rng.vtable, defaultBrEc, nil, addr res[0], EC_curve25519)
let len = ecKeygen(addr rng.vtable, defaultBrEc, nil, addr res[0], EC_curve25519)
# Per bearssl documentation, the keygen only fails if the curve is
# unrecognised -
doAssert len == Curve25519KeySize, "Could not generate curve"
Expand Down
11 changes: 6 additions & 5 deletions libp2p/crypto/ecnist.nim
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import minasn1
export minasn1.Asn1Error
import stew/[results, ctops]

import ../utils/random/rng
import ../utility

export results
Expand Down Expand Up @@ -233,15 +234,15 @@ proc clear*[T: EcPKI|EcKeyPair](pki: var T) =

proc random*(
T: typedesc[EcPrivateKey], kind: EcCurveKind,
rng: var HmacDrbgContext): EcResult[EcPrivateKey] =
rng: Rng): EcResult[EcPrivateKey] =
## Generate new random EC private key using BearSSL's HMAC-SHA256-DRBG
## algorithm.
##
## ``kind`` elliptic curve kind of your choice (secp256r1, secp384r1 or
## secp521r1).
var ecimp = ecGetDefault()
var res = new EcPrivateKey
if ecKeygen(addr rng.vtable, ecimp,
if ecKeygen(rng.vtable, ecimp,
addr res.key, addr res.buffer[0],
safeConvert[cint](kind)) == 0:
err(EcKeyGenError)
Expand All @@ -267,7 +268,7 @@ proc getPublicKey*(seckey: EcPrivateKey): EcResult[EcPublicKey] =

proc random*(
T: typedesc[EcKeyPair], kind: EcCurveKind,
rng: var HmacDrbgContext): EcResult[T] =
rng: Rng): EcResult[T] =
## Generate new random EC private and public keypair using BearSSL's
## HMAC-SHA256-DRBG algorithm.
##
Expand Down Expand Up @@ -999,7 +1000,7 @@ type ECDHEScheme* = EcCurveKind

proc ephemeral*(
scheme: ECDHEScheme,
rng: var HmacDrbgContext): EcResult[EcKeyPair] =
rng: Rng): EcResult[EcKeyPair] =
## Generate ephemeral keys used to perform ECDHE.
var keypair: EcKeyPair
if scheme == Secp256r1:
Expand All @@ -1011,7 +1012,7 @@ proc ephemeral*(
ok(keypair)

proc ephemeral*(
scheme: string, rng: var HmacDrbgContext): EcResult[EcKeyPair] =
scheme: string, rng: Rng): EcResult[EcKeyPair] =
## Generate ephemeral keys used to perform ECDHE using string encoding.
##
## Currently supported encoding strings are P-256, P-384, P-521, if encoding
Expand Down
11 changes: 6 additions & 5 deletions libp2p/crypto/ed25519/ed25519.nim
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,9 @@ import nimcrypto/utils as ncrutils
import stew/[results, ctops]

import ../../utility
import ../../utils/random/rng

export results
export results, rng

# This workaround needed because of some bugs in Nim Static[T].
export hash, sha2, rand
Expand Down Expand Up @@ -1648,14 +1649,14 @@ proc checkScalar*(scalar: openArray[byte]): uint32 =
c = -1
result = NEQ(z, 0'u32) and LT0(c)

proc random*(t: typedesc[EdPrivateKey], rng: var HmacDrbgContext): EdPrivateKey =
proc random*(t: typedesc[EdPrivateKey], rng: Rng): EdPrivateKey =
## Generate new random ED25519 private key using the given random number generator
var
point: GeP3
pk: array[EdPublicKeySize, byte]
res: EdPrivateKey

hmacDrbgGenerate(rng, res.data.toOpenArray(0, 31))
rng.generate(res.data.toOpenArray(0, 31))

var hh = sha512.digest(res.data.toOpenArray(0, 31))
hh.data[0] = hh.data[0] and 0xF8'u8
Expand All @@ -1667,14 +1668,14 @@ proc random*(t: typedesc[EdPrivateKey], rng: var HmacDrbgContext): EdPrivateKey

res

proc random*(t: typedesc[EdKeyPair], rng: var HmacDrbgContext): EdKeyPair =
proc random*(t: typedesc[EdKeyPair], rng: Rng): EdKeyPair =
## Generate new random ED25519 private and public keypair using OS specific
## CSPRNG.
var
point: GeP3
res: EdKeyPair

hmacDrbgGenerate(rng, res.seckey.data.toOpenArray(0, 31))
rng.generate(res.seckey.data.toOpenArray(0, 31))

var hh = sha512.digest(res.seckey.data.toOpenArray(0, 31))
hh.data[0] = hh.data[0] and 0xF8'u8
Expand Down
5 changes: 3 additions & 2 deletions libp2p/crypto/rsa.nim
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import minasn1
import stew/[results, ctops]
# We use `ncrutils` for constant-time hexadecimal encoding/decoding procedures.
import nimcrypto/utils as ncrutils
import ../utils/random/rng

export Asn1Error, results

Expand Down Expand Up @@ -115,7 +116,7 @@ template trimZeroes(b: seq[byte], pt, ptlen: untyped) =
pt = cast[ptr byte](cast[uint](pt) + 1)
ptlen -= 1

proc random*[T: RsaKP](t: typedesc[T], rng: var HmacDrbgContext,
proc random*[T: RsaKP](t: typedesc[T], rng: Rng,
bits = DefaultKeySize,
pubexp = DefaultPublicExponent): RsaResult[T] =
## Generate new random RSA private key using BearSSL's HMAC-SHA256-DRBG
Expand All @@ -139,7 +140,7 @@ proc random*[T: RsaKP](t: typedesc[T], rng: var HmacDrbgContext,

var keygen = rsaKeygenGetDefault()

if keygen(addr rng.vtable,
if keygen(rng.vtable,
addr res.seck, addr res.buffer[sko],
addr res.pubk, addr res.buffer[pko],
cuint(bits), pubexp) == 0:
Expand Down
12 changes: 6 additions & 6 deletions libp2p/crypto/secp.nim
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@ import
stew/[byteutils, results],
nimcrypto/[hash, sha2]

import ../utils/random/rng

export sha2, results, rand

const
Expand All @@ -32,18 +34,16 @@ type
SkSignature* = distinct secp256k1.SkSignature
SkKeyPair* = distinct secp256k1.SkKeyPair

proc random*(t: typedesc[SkPrivateKey], rng: var HmacDrbgContext): SkPrivateKey =
proc random*(t: typedesc[SkPrivateKey], rng: rng.Rng): SkPrivateKey =
#TODO is there a better way?
var rngPtr = addr rng
proc callRng(data: var openArray[byte]) =
hmacDrbgGenerate(rngPtr[], data)
rng.generate(data)

SkPrivateKey(SkSecretKey.random(callRng))

proc random*(t: typedesc[SkKeyPair], rng: var HmacDrbgContext): SkKeyPair =
let rngPtr = addr rng
proc random*(t: typedesc[SkKeyPair], rng: rng.Rng): SkKeyPair =
proc callRng(data: var openArray[byte]) =
hmacDrbgGenerate(rngPtr[], data)
rng.generate(data)

SkKeyPair(secp256k1.SkKeyPair.random(callRng))

Expand Down
5 changes: 3 additions & 2 deletions libp2p/peerid.nim
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import
utility,
./crypto/crypto, ./multicodec, ./multihash, ./vbuffer,
./protobuf/minprotobuf
import utils/random/securerng

export results, utility

Expand Down Expand Up @@ -178,9 +179,9 @@ func init*(t: typedesc[PeerId], seckey: PrivateKey): Result[PeerId, cstring] =
## Create new peer id from private key ``seckey``.
PeerId.init(? seckey.getPublicKey().orError(cstring("invalid private key")))

proc random*(t: typedesc[PeerId], rng = newRng()): Result[PeerId, cstring] =
proc random*(t: typedesc[PeerId], rng: Rng = SecureRng.new()): Result[PeerId, cstring] =
## Create new peer id with random public key.
let randomKey = PrivateKey.random(Secp256k1, rng[])[]
let randomKey = PrivateKey.random(Secp256k1, rng)[]
PeerId.init(randomKey).orError(cstring("failed to generate random key"))

func match*(pid: PeerId, pubkey: PublicKey): bool =
Expand Down
5 changes: 3 additions & 2 deletions libp2p/protocols/connectivity/autonat/service.nim
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ import ../../../wire
import client
from core import NetworkReachability, AutonatUnreachableError
import ../../../utils/heartbeat
import ../../../utils/random/rng
import ../../../crypto/crypto

export core.NetworkReachability
Expand All @@ -35,7 +36,7 @@ type
answers: Deque[NetworkReachability]
autonatClient: AutonatClient
statusAndConfidenceHandler: StatusAndConfidenceHandler
rng: ref HmacDrbgContext
rng: Rng
scheduleInterval: Opt[Duration]
askNewConnectedPeers: bool
numPeersToAsk: int
Expand All @@ -49,7 +50,7 @@ type
proc new*(
T: typedesc[AutonatService],
autonatClient: AutonatClient,
rng: ref HmacDrbgContext,
rng: Rng,
scheduleInterval: Opt[Duration] = Opt.none(Duration),
askNewConnectedPeers = true,
numPeersToAsk: int = 5,
Expand Down
11 changes: 6 additions & 5 deletions libp2p/protocols/secure/noise.nim
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ import ../../peerinfo
import ../../protobuf/minprotobuf
import ../../utility
import ../../errors
import ../../utils/random/rng

import secure,
../../crypto/[crypto, chacha20poly1305, curve25519, hkdf]
Expand Down Expand Up @@ -78,7 +79,7 @@ type
rs: Curve25519Key

Noise* = ref object of Secure
rng: ref HmacDrbgContext
rng: Rng
localPrivateKey: PrivateKey
localPublicKey: seq[byte]
noiseKeys: KeyPair
Expand Down Expand Up @@ -106,7 +107,7 @@ func shortLog*(conn: NoiseConnection): auto =

chronicles.formatIt(NoiseConnection): shortLog(it)

proc genKeyPair(rng: var HmacDrbgContext): KeyPair =
proc genKeyPair(rng: Rng): KeyPair =
result.privateKey = Curve25519Key.random(rng)
result.publicKey = result.privateKey.public()

Expand Down Expand Up @@ -235,7 +236,7 @@ template write_e: untyped =
trace "noise write e"
# Sets e (which must be empty) to GENERATE_KEYPAIR().
# Appends e.public_key to the buffer. Calls MixHash(e.public_key).
hs.e = genKeyPair(p.rng[])
hs.e = genKeyPair(p.rng)
msg.add hs.e.publicKey
hs.ss.mixHash(hs.e.publicKey)

Expand Down Expand Up @@ -645,7 +646,7 @@ method init*(p: Noise) {.gcsafe.} =

proc new*(
T: typedesc[Noise],
rng: ref HmacDrbgContext,
rng: Rng,
privateKey: PrivateKey,
outgoing: bool = true,
commonPrologue: seq[byte] = @[]): T =
Expand All @@ -658,7 +659,7 @@ proc new*(
outgoing: outgoing,
localPrivateKey: privateKey,
localPublicKey: pkBytes,
noiseKeys: genKeyPair(rng[]),
noiseKeys: genKeyPair(rng),
commonPrologue: commonPrologue,
)

Expand Down
7 changes: 4 additions & 3 deletions libp2p/services/autorelayservice.nim
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,8 @@

import chronos, chronicles, times, tables, sequtils
import ../switch,
../protocols/connectivity/relay/[client, utils]
../protocols/connectivity/relay/[client, utils],
../utils/random/rng

logScope:
topics = "libp2p autorelay"
Expand All @@ -30,7 +31,7 @@ type
peerAvailable: AsyncEvent
onReservation: OnReservationHandler
addressMapper: AddressMapper
rng: ref HmacDrbgContext
rng: Rng

proc isRunning*(self: AutoRelayService): bool =
return self.running
Expand Down Expand Up @@ -139,7 +140,7 @@ proc new*(T: typedesc[AutoRelayService],
numRelays: int,
client: RelayClient,
onReservation: OnReservationHandler,
rng: ref HmacDrbgContext): T =
rng: Rng): T =
T(numRelays: numRelays,
client: client,
onReservation: onReservation,
Expand Down
Loading

0 comments on commit ffe80dc

Please sign in to comment.