From d174c4eed8f7abff978c856c7dc400b428f7800f Mon Sep 17 00:00:00 2001 From: Raul Jordan Date: Fri, 15 Feb 2019 13:49:37 -0600 Subject: [PATCH] Update Validity Conditions to Match Spec (#1611) * validity conditions to match master * update tests across repo --- beacon-chain/blockchain/service.go | 5 ++-- beacon-chain/blockchain/service_test.go | 15 +++-------- beacon-chain/core/blocks/block.go | 8 ------ .../core/blocks/validity_conditions.go | 27 ++++++++++--------- .../core/blocks/validity_conditions_test.go | 18 ++++++++----- 5 files changed, 31 insertions(+), 42 deletions(-) diff --git a/beacon-chain/blockchain/service.go b/beacon-chain/blockchain/service.go index 8fd38b0d2c10..ed98c23c7200 100644 --- a/beacon-chain/blockchain/service.go +++ b/beacon-chain/blockchain/service.go @@ -5,7 +5,6 @@ package blockchain import ( "context" - "errors" "fmt" "time" @@ -265,8 +264,8 @@ func (c *ChainService) ReceiveBlock(block *pb.BeaconBlock, beaconState *pb.Beaco return nil, fmt.Errorf("could not tree hash incoming block: %v", err) } - if block.Slot == 0 { - return nil, errors.New("cannot process a genesis block: received block with slot 0") + if block.Slot == params.BeaconConfig().GenesisSlot { + return nil, fmt.Errorf("cannot process a genesis block: received block with slot %d", params.BeaconConfig().GenesisSlot) } // Save blocks with higher slot numbers in cache. diff --git a/beacon-chain/blockchain/service_test.go b/beacon-chain/blockchain/service_test.go index 5e18ad52fdd2..d3a4c6a11c71 100644 --- a/beacon-chain/blockchain/service_test.go +++ b/beacon-chain/blockchain/service_test.go @@ -322,7 +322,7 @@ func TestRunningChainServiceFaultyPOWChain(t *testing.T) { chainService.cancel() exitRoutine <- true - testutil.AssertLogsContain(t, hook, "unable to retrieve POW chain reference block failed") + testutil.AssertLogsContain(t, hook, "unable to retrieve POW chain reference block") } func setupGenesisState(t *testing.T, cs *ChainService, beaconState *pb.BeaconState) ([32]byte, *pb.BeaconState) { @@ -666,15 +666,6 @@ func TestIsBlockReadyForProcessing(t *testing.T) { t.Fatalf("unable to get root of canonical head: %v", err) } - block2 := &pb.BeaconBlock{ - ParentRootHash32: parentRoot[:], - Slot: 10, - } - - if err := chainService.isBlockReadyForProcessing(block2, beaconState); err == nil { - t.Fatal("block processing succeeded despite block slot being invalid") - } - beaconState.LatestEth1Data = &pb.Eth1Data{ DepositRootHash32: []byte{2}, BlockHash32: []byte{3}, @@ -684,7 +675,7 @@ func TestIsBlockReadyForProcessing(t *testing.T) { currentSlot := uint64(1) attestationSlot := uint64(0) - block3 := &pb.BeaconBlock{ + block2 := &pb.BeaconBlock{ Slot: currentSlot, StateRootHash32: stateRoot[:], ParentRootHash32: parentRoot[:], @@ -706,7 +697,7 @@ func TestIsBlockReadyForProcessing(t *testing.T) { chainService.enablePOWChain = true - if err := chainService.isBlockReadyForProcessing(block3, beaconState); err != nil { + if err := chainService.isBlockReadyForProcessing(block2, beaconState); err != nil { t.Fatalf("block processing failed despite being a valid block: %v", err) } } diff --git a/beacon-chain/core/blocks/block.go b/beacon-chain/core/blocks/block.go index 0784d2f6a977..6972a1e6f3df 100644 --- a/beacon-chain/core/blocks/block.go +++ b/beacon-chain/core/blocks/block.go @@ -7,7 +7,6 @@ import ( "bytes" "encoding/binary" "fmt" - "time" "github.com/prysmaticlabs/prysm/beacon-chain/utils" pb "github.com/prysmaticlabs/prysm/proto/beacon/p2p/v1" @@ -41,13 +40,6 @@ func NewGenesisBlock(stateRoot []byte) *pb.BeaconBlock { return block } -// IsSlotValid compares the slot to the system clock to determine if the block is valid. -func IsSlotValid(slot uint64, genesisTime time.Time) bool { - slotDuration := time.Duration(slot*params.BeaconConfig().SlotDuration) * time.Second - validTimeThreshold := genesisTime.Add(slotDuration) - return clock.Now().After(validTimeThreshold) -} - // BlockRoot returns the block root stored in the BeaconState for a given slot. // It returns an error if the requested block root is not within the BeaconState. // Spec pseudocode definition: diff --git a/beacon-chain/core/blocks/validity_conditions.go b/beacon-chain/core/blocks/validity_conditions.go index 4a7547946645..69b87f9c6c0a 100644 --- a/beacon-chain/core/blocks/validity_conditions.go +++ b/beacon-chain/core/blocks/validity_conditions.go @@ -8,6 +8,8 @@ import ( "fmt" "time" + "github.com/prysmaticlabs/prysm/shared/params" + "github.com/ethereum/go-ethereum/common" gethTypes "github.com/ethereum/go-ethereum/core/types" pb "github.com/prysmaticlabs/prysm/proto/beacon/p2p/v1" @@ -38,35 +40,34 @@ func IsValidBlock( return fmt.Errorf("unprocessed parent block as it is not saved in the db: %#x", parentRoot) } - // Pre-Processing Condition 2: - // The state is updated up to block.slot -1. - - if state.Slot != block.Slot-1 { - return fmt.Errorf( - "block slot is not valid %d as it is supposed to be %d", block.Slot, state.Slot+1) - } - if enablePOWChain { - h := common.BytesToHash(state.LatestEth1Data.DepositRootHash32) + h := common.BytesToHash(state.LatestEth1Data.BlockHash32) powBlock, err := GetPOWBlock(ctx, h) if err != nil { - return fmt.Errorf("unable to retrieve POW chain reference block %v", err) + return fmt.Errorf("unable to retrieve POW chain reference block: %v", err) } - // Pre-Processing Condition 3: + // Pre-Processing Condition 2: // The block pointed to by the state in state.processed_pow_receipt_root has // been processed in the ETH 1.0 chain. if powBlock == nil { - return fmt.Errorf("proof-of-Work chain reference in state does not exist %#x", state.LatestEth1Data.DepositRootHash32) + return fmt.Errorf("proof-of-Work chain reference in state does not exist: %#x", state.LatestEth1Data.BlockHash32) } } // Pre-Processing Condition 4: // The node's local time is greater than or equal to - // state.genesis_time + block.slot * SLOT_DURATION. + // state.genesis_time + (block.slot-GENESIS_SLOT)* SLOT_DURATION. if !IsSlotValid(block.Slot, genesisTime) { return fmt.Errorf("slot of block is too high: %d", block.Slot) } return nil } + +// IsSlotValid compares the slot to the system clock to determine if the block is valid. +func IsSlotValid(slot uint64, genesisTime time.Time) bool { + slotDuration := time.Duration((slot-params.BeaconConfig().GenesisSlot)*params.BeaconConfig().SlotDuration) * time.Second + validTimeThreshold := genesisTime.Add(slotDuration) + return clock.Now().After(validTimeThreshold) +} diff --git a/beacon-chain/core/blocks/validity_conditions_test.go b/beacon-chain/core/blocks/validity_conditions_test.go index 04ef3d578e4c..3a0c3fe2ff32 100644 --- a/beacon-chain/core/blocks/validity_conditions_test.go +++ b/beacon-chain/core/blocks/validity_conditions_test.go @@ -5,6 +5,8 @@ import ( "testing" "time" + "github.com/prysmaticlabs/prysm/shared/params" + "github.com/ethereum/go-ethereum/common" gethTypes "github.com/ethereum/go-ethereum/core/types" pb "github.com/prysmaticlabs/prysm/proto/beacon/p2p/v1" @@ -42,10 +44,10 @@ func TestBadBlock(t *testing.T) { db := &mockDB{} powClient := &mockPOWClient{} - beaconState.Slot = 3 + beaconState.Slot = params.BeaconConfig().GenesisSlot + 3 block := &pb.BeaconBlock{ - Slot: 4, + Slot: params.BeaconConfig().GenesisSlot + 4, } genesisTime := time.Unix(0, 0) @@ -57,15 +59,19 @@ func TestBadBlock(t *testing.T) { t.Fatal("block is valid despite not having a parent") } - block.Slot = 3 + block.Slot = params.BeaconConfig().GenesisSlot + 3 db.hasBlock = true + beaconState.LatestEth1Data = &pb.Eth1Data{ + DepositRootHash32: []byte{2}, + BlockHash32: []byte{3}, + } if err := IsValidBlock(ctx, beaconState, block, true, db.HasBlock, powClient.BlockByHash, genesisTime); err == nil { t.Fatalf("block is valid despite having an invalid slot %d", block.Slot) } - block.Slot = 4 + block.Slot = params.BeaconConfig().GenesisSlot + 4 powClient.blockExists = false beaconState.LatestEth1Data = &pb.Eth1Data{ DepositRootHash32: []byte{2}, @@ -94,11 +100,11 @@ func TestValidBlock(t *testing.T) { db := &mockDB{} powClient := &mockPOWClient{} - beaconState.Slot = 3 + beaconState.Slot = params.BeaconConfig().GenesisSlot + 3 db.hasBlock = true block := &pb.BeaconBlock{ - Slot: 4, + Slot: params.BeaconConfig().GenesisSlot + 4, } genesisTime := time.Unix(0, 0)