From c6d562538914f28fd4e0c1163b3f9eb453e9f800 Mon Sep 17 00:00:00 2001 From: Hristiyan Mitov Date: Fri, 7 Feb 2025 14:43:46 +0200 Subject: [PATCH 1/5] feat: Implement Finalize stage in Play-Grandpa-Round. --- .../grandpa/round/FinalizeStage.java | 35 ++++++++++++++++++- .../limechain/grandpa/round/GrandpaRound.java | 2 +- 2 files changed, 35 insertions(+), 2 deletions(-) diff --git a/src/main/java/com/limechain/grandpa/round/FinalizeStage.java b/src/main/java/com/limechain/grandpa/round/FinalizeStage.java index 50bc3d7d..19acece4 100644 --- a/src/main/java/com/limechain/grandpa/round/FinalizeStage.java +++ b/src/main/java/com/limechain/grandpa/round/FinalizeStage.java @@ -1,13 +1,46 @@ package com.limechain.grandpa.round; +import com.limechain.network.protocol.warp.dto.BlockHeader; +import lombok.extern.java.Log; + +@Log public class FinalizeStage implements StageState { @Override public void start(GrandpaRound round) { + + log.fine(String.format("Round %d entered the Finalize stage.", round.getRoundNumber())); + + if (isRoundReadyToEnd(round)) { + end(round); + return; + } + + Runnable onFinalizeHandler = () -> { + if (isRoundReadyToEnd(round)) { + end(round); + } + }; + round.setOnFinalizeHandler(onFinalizeHandler); } @Override public void end(GrandpaRound round) { + log.info(String.format("Round %d met finalization conditions and will be finalized.", round.getRoundNumber())); + round.setOnFinalizeHandler(null); + round.attemptToFinalizeAt(); + log.fine(String.format("Round %d exits Finalize stage.", round.getRoundNumber())); + + round.end(); } -} + private boolean isRoundReadyToEnd(GrandpaRound round) { + BlockHeader finalized = round.getFinalizedBlock(); + BlockHeader prevBestFinalCandidate = round.getPrevBestFinalCandidate(); + + if (finalized == null || prevBestFinalCandidate == null) { + return false; + } + return finalized.getBlockNumber().compareTo(prevBestFinalCandidate.getBlockNumber()) >= 0; + } +} diff --git a/src/main/java/com/limechain/grandpa/round/GrandpaRound.java b/src/main/java/com/limechain/grandpa/round/GrandpaRound.java index a71df068..41b327af 100644 --- a/src/main/java/com/limechain/grandpa/round/GrandpaRound.java +++ b/src/main/java/com/limechain/grandpa/round/GrandpaRound.java @@ -182,7 +182,7 @@ public BlockHeader getBestFinalCandidate() { return Optional.ofNullable(finalizeEstimate).orElse(lastFinalizedBlock); } - private void attemptToFinalizeAt() { + public void attemptToFinalizeAt() { BlockState blockState = stateManager.getBlockState(); BigInteger lastFinalizedBlockNumber = blockState.getHighestFinalizedNumber(); From 20fe0219a5a634da99fdfa1213f21fa1d6a4246c Mon Sep 17 00:00:00 2001 From: Hristiyan Mitov Date: Fri, 7 Feb 2025 14:53:33 +0200 Subject: [PATCH 2/5] Renamed isRoundReadyToEnd method to isRoundReadyToFinalized --- .../java/com/limechain/grandpa/round/FinalizeStage.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/com/limechain/grandpa/round/FinalizeStage.java b/src/main/java/com/limechain/grandpa/round/FinalizeStage.java index 19acece4..1f2f98e2 100644 --- a/src/main/java/com/limechain/grandpa/round/FinalizeStage.java +++ b/src/main/java/com/limechain/grandpa/round/FinalizeStage.java @@ -11,13 +11,13 @@ public void start(GrandpaRound round) { log.fine(String.format("Round %d entered the Finalize stage.", round.getRoundNumber())); - if (isRoundReadyToEnd(round)) { + if (isRoundReadyToFinalized(round)) { end(round); return; } Runnable onFinalizeHandler = () -> { - if (isRoundReadyToEnd(round)) { + if (isRoundReadyToFinalized(round)) { end(round); } }; @@ -34,7 +34,7 @@ public void end(GrandpaRound round) { round.end(); } - private boolean isRoundReadyToEnd(GrandpaRound round) { + private boolean isRoundReadyToFinalized(GrandpaRound round) { BlockHeader finalized = round.getFinalizedBlock(); BlockHeader prevBestFinalCandidate = round.getPrevBestFinalCandidate(); From 3f10834cd090108ae67278486d4776754d966760 Mon Sep 17 00:00:00 2001 From: Hristiyan Mitov Date: Fri, 7 Feb 2025 14:54:24 +0200 Subject: [PATCH 3/5] Renamed isRoundReadyToEnd method to isRoundReadyToFinalized --- .../java/com/limechain/grandpa/round/FinalizeStage.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/com/limechain/grandpa/round/FinalizeStage.java b/src/main/java/com/limechain/grandpa/round/FinalizeStage.java index 1f2f98e2..76148329 100644 --- a/src/main/java/com/limechain/grandpa/round/FinalizeStage.java +++ b/src/main/java/com/limechain/grandpa/round/FinalizeStage.java @@ -11,13 +11,13 @@ public void start(GrandpaRound round) { log.fine(String.format("Round %d entered the Finalize stage.", round.getRoundNumber())); - if (isRoundReadyToFinalized(round)) { + if (isRoundReadyToBeFinalized(round)) { end(round); return; } Runnable onFinalizeHandler = () -> { - if (isRoundReadyToFinalized(round)) { + if (isRoundReadyToBeFinalized(round)) { end(round); } }; @@ -34,7 +34,7 @@ public void end(GrandpaRound round) { round.end(); } - private boolean isRoundReadyToFinalized(GrandpaRound round) { + private boolean isRoundReadyToBeFinalized(GrandpaRound round) { BlockHeader finalized = round.getFinalizedBlock(); BlockHeader prevBestFinalCandidate = round.getPrevBestFinalCandidate(); From 816ca38dde3c1c43be91d46ef920e1f4c4d3d8c1 Mon Sep 17 00:00:00 2001 From: Hristiyan Mitov Date: Fri, 7 Feb 2025 15:13:11 +0200 Subject: [PATCH 4/5] fixed comment --- .../limechain/grandpa/round/FinalizeStage.java | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/src/main/java/com/limechain/grandpa/round/FinalizeStage.java b/src/main/java/com/limechain/grandpa/round/FinalizeStage.java index 76148329..9acc81a9 100644 --- a/src/main/java/com/limechain/grandpa/round/FinalizeStage.java +++ b/src/main/java/com/limechain/grandpa/round/FinalizeStage.java @@ -1,5 +1,6 @@ package com.limechain.grandpa.round; +import com.limechain.exception.grandpa.GrandpaGenericException; import com.limechain.network.protocol.warp.dto.BlockHeader; import lombok.extern.java.Log; @@ -35,12 +36,16 @@ public void end(GrandpaRound round) { } private boolean isRoundReadyToBeFinalized(GrandpaRound round) { - BlockHeader finalized = round.getFinalizedBlock(); - BlockHeader prevBestFinalCandidate = round.getPrevBestFinalCandidate(); - - if (finalized == null || prevBestFinalCandidate == null) { + BlockHeader finalized; + try { + finalized = round.getFinalizedBlock(); + } catch (GrandpaGenericException e) { return false; } - return finalized.getBlockNumber().compareTo(prevBestFinalCandidate.getBlockNumber()) >= 0; + + BlockHeader prevBestFinalCandidate = round.getPrevBestFinalCandidate(); + + return prevBestFinalCandidate != null + && finalized.getBlockNumber().compareTo(prevBestFinalCandidate.getBlockNumber()) >= 0; } } From f5828fb013b20598058fd48e2cda527e249074b4 Mon Sep 17 00:00:00 2001 From: Hristiyan Mitov Date: Fri, 7 Feb 2025 16:24:09 +0200 Subject: [PATCH 5/5] Made runnable inline and added logger when finalizedBlock not found. --- .../java/com/limechain/grandpa/round/FinalizeStage.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/java/com/limechain/grandpa/round/FinalizeStage.java b/src/main/java/com/limechain/grandpa/round/FinalizeStage.java index 9acc81a9..fcae06dd 100644 --- a/src/main/java/com/limechain/grandpa/round/FinalizeStage.java +++ b/src/main/java/com/limechain/grandpa/round/FinalizeStage.java @@ -17,12 +17,11 @@ public void start(GrandpaRound round) { return; } - Runnable onFinalizeHandler = () -> { + round.setOnFinalizeHandler(() -> { if (isRoundReadyToBeFinalized(round)) { end(round); } - }; - round.setOnFinalizeHandler(onFinalizeHandler); + }); } @Override @@ -40,6 +39,7 @@ private boolean isRoundReadyToBeFinalized(GrandpaRound round) { try { finalized = round.getFinalizedBlock(); } catch (GrandpaGenericException e) { + log.warning("Finalized block not found, round cannot be finalized."); return false; }