Skip to content

Commit

Permalink
feat: standardized error responses for payload validation (#7939)
Browse files Browse the repository at this point in the history
Co-authored-by: Alexey Osipov <[email protected]>
Co-authored-by: Ben Adams <[email protected]>
  • Loading branch information
3 people authored Jan 14, 2025
1 parent ed1fe3b commit 6364cdb
Show file tree
Hide file tree
Showing 3 changed files with 41 additions and 35 deletions.
54 changes: 30 additions & 24 deletions src/Nethermind/Nethermind.Consensus/Messages/BlockErrorMessages.cs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@

using Nethermind.Core;
using Nethermind.Core.Crypto;
using Nethermind.Int256;

namespace Nethermind.Consensus.Messages;
public static class BlockErrorMessages
Expand All @@ -13,8 +14,8 @@ public static string ExceededUncleLimit(int maxUncleCount) =>
public const string InsufficientMaxFeePerBlobGas =
"InsufficientMaxFeePerBlobGas: Not enough to cover blob gas fee.";

public const string InvalidLogsBloom =
"InvalidLogsBloom: Logs bloom in header does not match.";
public static string InvalidLogsBloom(Bloom expected, Bloom actual) =>
$"InvalidLogsBloom: Logs bloom in header does not match. Expected {expected}, got {actual}";

public static string InvalidTxRoot(Core.Crypto.Hash256 expected, Core.Crypto.Hash256 actual) =>
$"InvalidTxRoot: Expected {expected}, got {actual}";
Expand All @@ -34,20 +35,20 @@ public static string InvalidWithdrawalsRoot(Core.Crypto.Hash256 expected, Core.C
public const string WithdrawalsNotEnabled =
"WithdrawalsNotEnabled: Block body cannot have withdrawals.";

public const string InvalidReceiptsRoot =
"InvalidReceiptsRoot: Receipts root in header does not match.";
public static string InvalidReceiptsRoot(Hash256 expected, Hash256 actual) =>
$"InvalidReceiptsRoot: Receipts root in header does not match. Expected {expected}, got {actual}";

public const string InvalidStateRoot =
"InvalidStateRoot: State root in header does not match.";
public static string InvalidStateRoot(Hash256 expected, Core.Crypto.Hash256 actual) =>
$"InvalidStateRoot: State root in header does not match. Expected {expected}, got {actual}";

public const string InvalidParentBeaconBlockRoot =
"InvalidParentBeaconBlockRoot: Beacon block root in header does not match.";
public static string InvalidParentBeaconBlockRoot(Hash256 expected, Hash256 actual) =>
$"InvalidParentBeaconBlockRoot: Beacon block root in header does not match. Expected {expected}, got {actual}";

public const string BlobGasPriceOverflow =
"BlobGasPriceOverflow: Overflow in excess blob gas.";

public const string InvalidHeaderHash =
"InvalidHeaderHash: Header hash does not match.";
public static string InvalidHeaderHash(Hash256 expected, Hash256 actual) =>
$"InvalidHeaderHash: Header hash does not match. Expected {expected}, got {actual}";

public const string InvalidExtraData =
"InvalidExtraData: Extra data in header is not valid.";
Expand All @@ -73,8 +74,8 @@ public static string InvalidWithdrawalsRoot(Core.Crypto.Hash256 expected, Core.C
public const string InvalidBlockNumber =
"InvalidBlockNumber: Block number does not match the parent.";

public const string InvalidBaseFeePerGas =
"InvalidBaseFeePerGas: Does not match calculated.";
public static string InvalidBaseFeePerGas(UInt256? expected, UInt256 actual) =>
$"InvalidBaseFeePerGas: Does not match calculated. Expected {expected}, got {actual}";

public const string NotAllowedBlobGasUsed =
"NotAllowedBlobGasUsed: Cannot be set.";
Expand All @@ -91,19 +92,17 @@ public static string InvalidWithdrawalsRoot(Core.Crypto.Hash256 expected, Core.C
public static string InvalidTxInBlock(int i) =>
$"InvalidTxInBlock: Tx at index {i} in body.";

public const string HeaderGasUsedMismatch =
"HeaderGasUsedMismatch: Gas used in header does not match calculated.";
public static string HeaderGasUsedMismatch(long expected, long actual) =>
$"HeaderGasUsedMismatch: Gas used in header does not match calculated. Expected {expected}, got {actual}";

//Block's blob gas used in header is above the limit.
public static readonly string BlobGasUsedAboveBlockLimit =
$"BlockBlobGasExceeded: A block cannot have more than {Eip4844Constants.MaxBlobGasPerBlock} blob gas.";

//Block's excess blob gas in header is incorrect.
public const string IncorrectExcessBlobGas =
"HeaderExcessBlobGasMismatch: Excess blob gas in header does not match calculated.";
public static string IncorrectExcessBlobGas(ulong? expected, ulong? actual) =>
$"HeaderExcessBlobGasMismatch: Excess blob gas in header does not match calculated. Expected {expected}, got {actual}";

public const string HeaderBlobGasMismatch =
"HeaderBlobGasMismatch: Blob gas in header does not match calculated.";
public static string HeaderBlobGasMismatch(ulong? expected, ulong? actual) =>
$"HeaderBlobGasMismatch: Blob gas in header does not match calculated. Expected {expected}, got {actual}";

public const string InvalidTimestamp =
"InvalidTimestamp: Timestamp in header cannot be lower than ancestor.";
Expand All @@ -117,8 +116,15 @@ public static string InvalidTxInBlock(int i) =>
public const string NegativeGasUsed =
"NegativeGasUsed: Cannot be negative.";

public static string MissingRequests => "MissingRequests: Requests cannot be null in block when EIP-6110 or EIP-7002 are activated.";
public static string RequestsNotEnabled => "RequestsNotEnabled: Requests must be null in block when EIP-6110 and EIP-7002 are not activated.";
public static string InvalidRequestsHash(Hash256? expected, Hash256? actual) => $"InvalidRequestsHash: Requests hash hash mismatch in block: expected {expected}, got {actual}";
public static string InvalidRequestsOrder => "InvalidRequestsOrder: Requests are not in the correct order in block.";
public const string MissingRequests =
"MissingRequests: Requests cannot be null in block when EIP-6110 or EIP-7002 are activated.";

public const string RequestsNotEnabled =
"RequestsNotEnabled: Requests must be null in block when EIP-6110 and EIP-7002 are not activated.";

public static string InvalidRequestsHash(Hash256? expected, Hash256? actual) =>
$"InvalidRequestsHash: Requests hash hash mismatch in block: expected {expected}, got {actual}";

public const string InvalidRequestsOrder =
"InvalidRequestsOrder: Requests are not in the correct order in block.";
}
16 changes: 8 additions & 8 deletions src/Nethermind/Nethermind.Consensus/Validators/BlockValidator.cs
Original file line number Diff line number Diff line change
Expand Up @@ -173,43 +173,43 @@ public bool ValidateProcessedBlock(Block processedBlock, TxReceipt[] receipts, B
if (processedBlock.Header.GasUsed != suggestedBlock.Header.GasUsed)
{
if (_logger.IsWarn) _logger.Warn($"- gas used: expected {suggestedBlock.Header.GasUsed}, got {processedBlock.Header.GasUsed} (diff: {processedBlock.Header.GasUsed - suggestedBlock.Header.GasUsed})");
error ??= BlockErrorMessages.HeaderGasUsedMismatch;
error ??= BlockErrorMessages.HeaderGasUsedMismatch(suggestedBlock.Header.GasUsed, processedBlock.Header.GasUsed);
}

if (processedBlock.Header.Bloom != suggestedBlock.Header.Bloom)
{
if (_logger.IsWarn) _logger.Warn($"- bloom: expected {suggestedBlock.Header.Bloom}, got {processedBlock.Header.Bloom}");
error ??= BlockErrorMessages.InvalidLogsBloom;
error ??= BlockErrorMessages.InvalidLogsBloom(suggestedBlock.Header.Bloom, processedBlock.Header.Bloom);
}

if (processedBlock.Header.ReceiptsRoot != suggestedBlock.Header.ReceiptsRoot)
{
if (_logger.IsWarn) _logger.Warn($"- receipts root: expected {suggestedBlock.Header.ReceiptsRoot}, got {processedBlock.Header.ReceiptsRoot}");
error ??= BlockErrorMessages.InvalidReceiptsRoot;
error ??= BlockErrorMessages.InvalidReceiptsRoot(suggestedBlock.Header.ReceiptsRoot, processedBlock.Header.ReceiptsRoot);
}

if (processedBlock.Header.StateRoot != suggestedBlock.Header.StateRoot)
{
if (_logger.IsWarn) _logger.Warn($"- state root: expected {suggestedBlock.Header.StateRoot}, got {processedBlock.Header.StateRoot}");
error ??= BlockErrorMessages.InvalidStateRoot;
error ??= BlockErrorMessages.InvalidStateRoot(suggestedBlock.Header.StateRoot, processedBlock.Header.StateRoot);
}

if (processedBlock.Header.BlobGasUsed != suggestedBlock.Header.BlobGasUsed)
{
if (_logger.IsWarn) _logger.Warn($"- blob gas used: expected {suggestedBlock.Header.BlobGasUsed}, got {processedBlock.Header.BlobGasUsed}");
error ??= BlockErrorMessages.HeaderBlobGasMismatch;
error ??= BlockErrorMessages.HeaderBlobGasMismatch(suggestedBlock.Header.BlobGasUsed, processedBlock.Header.BlobGasUsed);
}

if (processedBlock.Header.ExcessBlobGas != suggestedBlock.Header.ExcessBlobGas)
{
if (_logger.IsWarn) _logger.Warn($"- excess blob gas: expected {suggestedBlock.Header.ExcessBlobGas}, got {processedBlock.Header.ExcessBlobGas}");
error ??= BlockErrorMessages.IncorrectExcessBlobGas;
error ??= BlockErrorMessages.IncorrectExcessBlobGas(suggestedBlock.Header.ExcessBlobGas, processedBlock.Header.ExcessBlobGas);
}

if (processedBlock.Header.ParentBeaconBlockRoot != suggestedBlock.Header.ParentBeaconBlockRoot)
{
if (_logger.IsWarn) _logger.Warn($"- parent beacon block root : expected {suggestedBlock.Header.ParentBeaconBlockRoot}, got {processedBlock.Header.ParentBeaconBlockRoot}");
error ??= BlockErrorMessages.InvalidParentBeaconBlockRoot;
error ??= BlockErrorMessages.InvalidParentBeaconBlockRoot(suggestedBlock.Header.ParentBeaconBlockRoot, processedBlock.Header.ParentBeaconBlockRoot);
}

if (processedBlock.Header.RequestsHash != suggestedBlock.Header.RequestsHash)
Expand Down Expand Up @@ -346,7 +346,7 @@ protected virtual bool ValidateEip4844Fields(Block block, IReleaseSpec spec, out

if (blobGasUsed != block.Header.BlobGasUsed)
{
error = BlockErrorMessages.HeaderBlobGasMismatch;
error = BlockErrorMessages.HeaderBlobGasMismatch(blobGasUsed, block.Header.BlobGasUsed);
if (_logger.IsDebug) _logger.Debug($"{Invalid(block)} {nameof(BlockHeader.BlobGasUsed)} declared in the block header does not match actual blob gas used: {block.Header.BlobGasUsed} != {blobGasUsed}.");
return false;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ private bool ValidateHash(BlockHeader header, ref string? error)
if (!hashAsExpected)
{
if (_logger.IsWarn) _logger.Warn($"Invalid block header ({header.Hash}) - invalid block hash");
error = BlockErrorMessages.InvalidHeaderHash;
error = BlockErrorMessages.InvalidHeaderHash(header.Hash, header.CalculateHash());
return false;
}

Expand Down Expand Up @@ -127,7 +127,7 @@ protected virtual bool Validate1559(BlockHeader header, BlockHeader parent, IRel
if (expectedBaseFee != header.BaseFeePerGas)
{
if (_logger.IsWarn) _logger.Warn($"Invalid block header ({header.ToString(BlockHeader.Format.Short)}) incorrect base fee. Expected base fee: {expectedBaseFee}, Current base fee: {header.BaseFeePerGas} ");
error = BlockErrorMessages.InvalidBaseFeePerGas;
error = BlockErrorMessages.InvalidBaseFeePerGas(expectedBaseFee, header.BaseFeePerGas);
return false;
}
}
Expand Down Expand Up @@ -357,7 +357,7 @@ protected virtual bool ValidateBlobGasFields(BlockHeader header, BlockHeader par
if (header.ExcessBlobGas != expectedExcessBlobGas)
{
if (_logger.IsWarn) _logger.Warn($"ExcessBlobGas field is incorrect: {header.ExcessBlobGas}, should be {expectedExcessBlobGas}.");
error = BlockErrorMessages.IncorrectExcessBlobGas;
error = BlockErrorMessages.IncorrectExcessBlobGas(expectedExcessBlobGas, header.ExcessBlobGas);
return false;
}
}
Expand Down

0 comments on commit 6364cdb

Please sign in to comment.