Update Validity Conditions to Match Spec (#1611)

* validity conditions to match master

* update tests across repo
This commit is contained in:
Raul Jordan 2019-02-15 13:49:37 -06:00 committed by GitHub
parent c8a170dbad
commit d174c4eed8
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 31 additions and 42 deletions

View File

@ -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.

View File

@ -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)
}
}

View File

@ -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:

View File

@ -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)
}

View File

@ -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)