diff --git a/src/main/java/org/qortal/controller/Synchronizer.java b/src/main/java/org/qortal/controller/Synchronizer.java index 97d70027..f8ea0ec0 100644 --- a/src/main/java/org/qortal/controller/Synchronizer.java +++ b/src/main/java/org/qortal/controller/Synchronizer.java @@ -343,7 +343,7 @@ public class Synchronizer { } // Ignore this peer if it holds an invalid block - if (this.containsInvalidBlock(peer.getCommonBlockData().getBlockSummariesAfterCommonBlock())) { + if (this.containsInvalidBlockSummary(peer.getCommonBlockData().getBlockSummariesAfterCommonBlock())) { LOGGER.debug("Ignoring peer %s because it holds an invalid block", peer); peers.remove(peer); } @@ -503,7 +503,7 @@ public class Synchronizer { } invalidBlockSignatures.add(signature); } - private boolean containsInvalidBlock(List blockSummaries) { + private boolean containsInvalidBlockSummary(List blockSummaries) { if (blockSummaries == null || invalidBlockSignatures == null) { return false; } @@ -519,6 +519,21 @@ public class Synchronizer { } return false; } + private boolean containsInvalidBlockSignature(List blockSignatures) { + if (blockSignatures == null || invalidBlockSignatures == null) { + return false; + } + + // Loop through supplied block signatures and check each one against our known invalid blocks + for (byte[] signature : blockSignatures) { + for (byte[] invalidSignature : invalidBlockSignatures) { + if (Arrays.equals(signature, invalidSignature)) { + return true; + } + } + } + return false; + } /** @@ -920,6 +935,12 @@ public class Synchronizer { break; } + // Catch a block with an invalid signature before orphaning, so that we retain our existing valid candidate + if (this.containsInvalidBlockSignature(peerBlockSignatures)) { + LOGGER.info(String.format("Peer %s sent invalid block signature: %.8s", peer, Base58.encode(latestPeerSignature))); + return SynchronizationResult.INVALID_DATA; + } + byte[] nextPeerSignature = peerBlockSignatures.get(0); int nextHeight = height + 1;