From e009728858272c44a80c4e77c4aec63eb538b11f Mon Sep 17 00:00:00 2001 From: Jacek Sieka Date: Thu, 24 Mar 2022 15:37:37 +0100 Subject: [PATCH] work around Nim assignment bug that breaks state pruning (#3545) See https://github.com/nim-lang/Nim/issues/19613 --- .../consensus_object_pools/blockchain_dag.nim | 4 ++- tests/test_blockchain_dag.nim | 30 +++++++++++++++++++ 2 files changed, 33 insertions(+), 1 deletion(-) diff --git a/beacon_chain/consensus_object_pools/blockchain_dag.nim b/beacon_chain/consensus_object_pools/blockchain_dag.nim index a2689986e..6c186b88e 100644 --- a/beacon_chain/consensus_object_pools/blockchain_dag.nim +++ b/beacon_chain/consensus_object_pools/blockchain_dag.nim @@ -1499,7 +1499,9 @@ proc pruneStateCachesDAG*(dag: ChainDAGRef) = if not isFinalizedStateSnapshot(cur.get().slot) and cur.get().slot != dag.tail.slot: dag.delState(cur.get()) - cur = dag.parentOrSlot(cur.get()) + # TODO https://github.com/nim-lang/Nim/issues/19613 + let tmp = cur.get() + cur = dag.parentOrSlot(tmp) let statePruneTick = Moment.now() diff --git a/tests/test_blockchain_dag.nim b/tests/test_blockchain_dag.nim index a530d3041..3af755cee 100644 --- a/tests/test_blockchain_dag.nim +++ b/tests/test_blockchain_dag.nim @@ -415,6 +415,34 @@ suite "chain DAG finalization tests" & preset(): check: dag.db.immutableValidators.len() == getStateField(dag.headState, validators).len() + block: + var cur = dag.head.bid + while true: + let parent = dag.parent(cur) + if cur.slot > 0: + check: + parent.isSome and parent.get().slot < cur.slot + cur = parent.get() + else: + check: + parent.isErr() + break + check: cur.slot == 0 + + block: + var cur = dag.head.bid.atSlot() + while true: + let parent = dag.parentOrSlot(cur) + if cur.slot > 0: + check: + parent.isSome and (parent.get().slot < cur.slot or parent.get().bid != cur.bid) + cur = parent.get() + else: + check: + parent.isErr() + break + check: cur.slot == 0 + let finalER = dag.getEpochRef( dag.finalizedHead.blck, dag.finalizedHead.slot.epoch, false) @@ -458,9 +486,11 @@ suite "chain DAG finalization tests" & preset(): let finalizedCheckpoint = dag.stateCheckpoint(dag.finalizedHead.toBlockSlotId().get()) headCheckpoint = dag.stateCheckpoint(dag.head.bid.atSlot()) + prunedCheckpoint = dag.stateCheckpoint(dag.parent(dag.finalizedHead.blck.bid).get().atSlot()) check: db.getStateRoot(headCheckpoint.bid.root, headCheckpoint.slot).isSome db.getStateRoot(finalizedCheckpoint.bid.root, finalizedCheckpoint.slot).isSome + db.getStateRoot(prunedCheckpoint.bid.root, prunedCheckpoint.slot).isNone let validatorMonitor2 = newClone(ValidatorMonitor.init())