Skip to content

Commit 98a7f44

Browse files
agnxshtersec
andauthored
fix: response checking from RequestManager for blobs (#6755)
* rewrite: response checking from RequestManager for blobs * clean whitespace * use a comparator and std instead * sort incoming blobs by index * fix list traversal --------- Co-authored-by: tersec <[email protected]>
1 parent 031d24f commit 98a7f44

File tree

2 files changed

+29
-13
lines changed

2 files changed

+29
-13
lines changed

beacon_chain/spec/helpers.nim

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
# Uncategorized helper functions from the spec
1111

1212
import
13+
std/sequtils,
1314
# Status libraries
1415
stew/[byteutils, endians2, objects],
1516
nimcrypto/sha2,
@@ -542,7 +543,6 @@ proc compute_execution_block_hash*(blck: ForkyBeaconBlock): Eth2Digest =
542543
rlpHash(blockToBlockHeader(blck)).to(Eth2Digest)
543544

544545
from std/math import exp, ln
545-
from std/sequtils import foldl
546546

547547
func ln_binomial(n, k: int): float64 =
548548
if k > n:

beacon_chain/sync/request_manager.nim

Lines changed: 28 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ import
1818
"."/sync_protocol, "."/sync_manager,
1919
../gossip_processing/block_processor
2020

21+
from std/algorithm import binarySearch, sort
2122
from ../beacon_clock import GetBeaconTimeFn
2223
export block_quarantine, sync_manager
2324

@@ -102,21 +103,32 @@ proc checkResponse(roots: openArray[Eth2Digest],
102103
checks.del(res)
103104
true
104105

106+
func cmpSidecarIdentifier(x: BlobIdentifier | DataColumnIdentifier,
107+
y: ref BlobSidecar | ref DataColumnSidecar): int =
108+
cmp(x.index, y.index)
109+
105110
proc checkResponse(idList: seq[BlobIdentifier],
106111
blobs: openArray[ref BlobSidecar]): bool =
107-
if len(blobs) > len(idList):
112+
if blobs.len > idList.len:
108113
return false
109-
for blob in blobs:
110-
let block_root = hash_tree_root(blob.signed_block_header.message)
111-
var found = false
112-
for id in idList:
113-
if id.block_root == block_root and id.index == blob.index:
114-
found = true
115-
break
116-
if not found:
114+
var i = 0
115+
while i < blobs.len:
116+
let
117+
block_root = hash_tree_root(blobs[i].signed_block_header.message)
118+
id = idList[i]
119+
120+
# Check if the blob response is a subset
121+
if binarySearch(idList, blobs[i], cmpSidecarIdentifier) == -1:
117122
return false
118-
blob[].verify_blob_sidecar_inclusion_proof().isOkOr:
123+
124+
# Verify block_root and index match
125+
if id.block_root != block_root or id.index != blobs[i].index:
119126
return false
127+
128+
# Verify inclusion proof
129+
blobs[i][].verify_blob_sidecar_inclusion_proof().isOkOr:
130+
return false
131+
inc i
120132
true
121133

122134
proc requestBlocksByRoot(rman: RequestManager, items: seq[Eth2Digest]) {.async: (raises: [CancelledError]).} =
@@ -190,6 +202,9 @@ proc requestBlocksByRoot(rman: RequestManager, items: seq[Eth2Digest]) {.async:
190202
if not(isNil(peer)):
191203
rman.network.peerPool.release(peer)
192204

205+
func cmpBlobIndexes(x, y: ref BlobSidecar): int =
206+
cmp(x.index, y.index)
207+
193208
proc fetchBlobsFromNetwork(self: RequestManager,
194209
idList: seq[BlobIdentifier])
195210
{.async: (raises: [CancelledError]).} =
@@ -203,8 +218,9 @@ proc fetchBlobsFromNetwork(self: RequestManager,
203218
let blobs = await blobSidecarsByRoot(peer, BlobIdentifierList idList)
204219

205220
if blobs.isOk:
206-
let ublobs = blobs.get()
207-
if not checkResponse(idList, ublobs.asSeq()):
221+
var ublobs = blobs.get().asSeq()
222+
ublobs.sort(cmpBlobIndexes)
223+
if not checkResponse(idList, ublobs):
208224
debug "Mismatched response to blobs by root",
209225
peer = peer, blobs = shortLog(idList), ublobs = len(ublobs)
210226
peer.updateScore(PeerScoreBadResponse)

0 commit comments

Comments
 (0)