Skip to content

Commit

Permalink
fix(rln): nullifierlog vulnerability (#2855)
Browse files Browse the repository at this point in the history
  • Loading branch information
alrevuelta authored Jun 28, 2024
1 parent 7b97c80 commit dad054d
Showing 1 changed file with 18 additions and 13 deletions.
31 changes: 18 additions & 13 deletions waku/waku_rln_relay/rln_relay.nim
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,7 @@ proc updateLog*(
try:
# check if an identical record exists
if rlnPeer.nullifierLog[epoch].hasKeyOrPut(proofMetadata.nullifier, proofMetadata):
# the above condition could be `discarded` but it is kept for clarity, that slashing will
# the above condition could be `discarded` but it is kept for clarity, that slashing will
# be implemented here
# TODO: slashing logic
return ok()
Expand Down Expand Up @@ -279,8 +279,10 @@ proc validateMessageAndUpdateLog*(
if proofMetadataRes.isErr():
return MessageValidationResult.Invalid

# insert the message to the log (never errors)
discard rlnPeer.updateLog(msgProof.epoch, proofMetadataRes.get())
# insert the message to the log (never errors) only if the
# message is valid.
if isValidMessage == MessageValidationResult.Valid:
discard rlnPeer.updateLog(msgProof.epoch, proofMetadataRes.get())

return isValidMessage

Expand Down Expand Up @@ -308,22 +310,25 @@ proc appendRLNProof*(
let proof = rlnPeer.groupManager.generateProof(input, epoch, nonce).valueOr:
return err("could not generate rln-v2 proof: " & $error)


msg.proof = proof.encode().buffer
return ok()

proc clearNullifierLog*(rlnPeer: WakuRlnRelay) =
# clear the first MaxEpochGap epochs of the nullifer log
# if more than MaxEpochGap epochs are in the log
# note: the epochs are ordered ascendingly
if rlnPeer.nullifierLog.len().uint <= rlnPeer.rlnMaxEpochGap:
return

let countToClear = rlnPeer.nullifierLog.len().uint - rlnPeer.rlnMaxEpochGap
trace "clearing epochs from the nullifier log", count = countToClear
let epochsToClear = rlnPeer.nullifierLog.keys().toSeq()[0 ..< countToClear]
for epoch in epochsToClear:
rlnPeer.nullifierLog.del(epoch)
let currentEpoch = fromEpoch(rlnPeer.getCurrentEpoch())

var epochsToRemove: seq[Epoch] = @[]
for epoch in rlnPeer.nullifierLog.keys():
let epochInt = fromEpoch(epoch)

# clean all epochs that are +- rlnMaxEpochGap from the current epoch
if (currentEpoch+rlnPeer.rlnMaxEpochGap) <= epochInt or epochInt <= (currentEpoch-rlnPeer.rlnMaxEpochGap):
epochsToRemove.add(epoch)

for epochRemove in epochsToRemove:
trace "clearing epochs from the nullifier log", currentEpoch = currentEpoch, cleanedEpoch = fromEpoch(epochRemove)
rlnPeer.nullifierLog.del(epochRemove)

proc generateRlnValidator*(
wakuRlnRelay: WakuRLNRelay, spamHandler = none(SpamHandler)
Expand Down

0 comments on commit dad054d

Please sign in to comment.