Skip to content

Commit

Permalink
Revert removal of legacy P-chain block parsing (#2866)
Browse files Browse the repository at this point in the history
  • Loading branch information
StephenButtolph authored Mar 24, 2024
1 parent 27bea09 commit 9833b45
Show file tree
Hide file tree
Showing 2 changed files with 144 additions and 1 deletion.
34 changes: 33 additions & 1 deletion vms/platformvm/state/state.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ import (
"github.com/ava-labs/avalanchego/database/versiondb"
"github.com/ava-labs/avalanchego/ids"
"github.com/ava-labs/avalanchego/snow"
"github.com/ava-labs/avalanchego/snow/choices"
"github.com/ava-labs/avalanchego/snow/uptime"
"github.com/ava-labs/avalanchego/snow/validators"
"github.com/ava-labs/avalanchego/utils"
Expand Down Expand Up @@ -178,6 +179,16 @@ type State interface {
Close() error
}

// Prior to https://github.com/ava-labs/avalanchego/pull/1719, blocks were
// stored as a map from blkID to stateBlk. Nodes synced prior to this PR may
// still have blocks partially stored using this legacy format.
//
// TODO: Remove after v1.12.x is activated
type stateBlk struct {
Bytes []byte `serialize:"true"`
Status choices.Status `serialize:"true"`
}

/*
* VMDB
* |-. validators
Expand Down Expand Up @@ -1789,7 +1800,7 @@ func (s *state) GetStatelessBlock(blockID ids.ID) (block.Block, error) {
return nil, err
}

blk, err := block.Parse(block.GenesisCodec, blkBytes)
blk, _, err := parseStoredBlock(blkBytes)
if err != nil {
return nil, err
}
Expand Down Expand Up @@ -2260,3 +2271,24 @@ func (s *state) writeMetadata() error {
}
return nil
}

// Returns the block and whether it is a [stateBlk].
// Invariant: blkBytes is safe to parse with blocks.GenesisCodec
//
// TODO: Remove after v1.12.x is activated
func parseStoredBlock(blkBytes []byte) (block.Block, bool, error) {
// Attempt to parse as blocks.Block
blk, err := block.Parse(block.GenesisCodec, blkBytes)
if err == nil {
return blk, false, nil
}

// Fallback to [stateBlk]
blkState := stateBlk{}
if _, err := block.GenesisCodec.Unmarshal(blkBytes, &blkState); err != nil {
return nil, false, err
}

blk, err = block.Parse(block.GenesisCodec, blkState.Bytes)
return blk, true, err
}
111 changes: 111 additions & 0 deletions vms/platformvm/state/state_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ import (
"github.com/ava-labs/avalanchego/database/memdb"
"github.com/ava-labs/avalanchego/ids"
"github.com/ava-labs/avalanchego/snow"
"github.com/ava-labs/avalanchego/snow/choices"
"github.com/ava-labs/avalanchego/snow/validators"
"github.com/ava-labs/avalanchego/utils/constants"
"github.com/ava-labs/avalanchego/utils/crypto/bls"
Expand Down Expand Up @@ -1293,6 +1294,116 @@ func requireEqualPublicKeysValidatorSet(
}
}

func TestParsedStateBlock(t *testing.T) {
require := require.New(t)

var blks []block.Block

{
blk, err := block.NewApricotAbortBlock(ids.GenerateTestID(), 1000)
require.NoError(err)
blks = append(blks, blk)
}

{
blk, err := block.NewApricotAtomicBlock(ids.GenerateTestID(), 1000, &txs.Tx{
Unsigned: &txs.AdvanceTimeTx{
Time: 1000,
},
})
require.NoError(err)
blks = append(blks, blk)
}

{
blk, err := block.NewApricotCommitBlock(ids.GenerateTestID(), 1000)
require.NoError(err)
blks = append(blks, blk)
}

{
tx := &txs.Tx{
Unsigned: &txs.RewardValidatorTx{
TxID: ids.GenerateTestID(),
},
}
require.NoError(tx.Initialize(txs.Codec))
blk, err := block.NewApricotProposalBlock(ids.GenerateTestID(), 1000, tx)
require.NoError(err)
blks = append(blks, blk)
}

{
tx := &txs.Tx{
Unsigned: &txs.RewardValidatorTx{
TxID: ids.GenerateTestID(),
},
}
require.NoError(tx.Initialize(txs.Codec))
blk, err := block.NewApricotStandardBlock(ids.GenerateTestID(), 1000, []*txs.Tx{tx})
require.NoError(err)
blks = append(blks, blk)
}

{
blk, err := block.NewBanffAbortBlock(time.Now(), ids.GenerateTestID(), 1000)
require.NoError(err)
blks = append(blks, blk)
}

{
blk, err := block.NewBanffCommitBlock(time.Now(), ids.GenerateTestID(), 1000)
require.NoError(err)
blks = append(blks, blk)
}

{
tx := &txs.Tx{
Unsigned: &txs.RewardValidatorTx{
TxID: ids.GenerateTestID(),
},
}
require.NoError(tx.Initialize(txs.Codec))

blk, err := block.NewBanffProposalBlock(time.Now(), ids.GenerateTestID(), 1000, tx, []*txs.Tx{})
require.NoError(err)
blks = append(blks, blk)
}

{
tx := &txs.Tx{
Unsigned: &txs.RewardValidatorTx{
TxID: ids.GenerateTestID(),
},
}
require.NoError(tx.Initialize(txs.Codec))

blk, err := block.NewBanffStandardBlock(time.Now(), ids.GenerateTestID(), 1000, []*txs.Tx{tx})
require.NoError(err)
blks = append(blks, blk)
}

for _, blk := range blks {
stBlk := stateBlk{
Bytes: blk.Bytes(),
Status: choices.Accepted,
}

stBlkBytes, err := block.GenesisCodec.Marshal(block.CodecVersion, &stBlk)
require.NoError(err)

gotBlk, isStateBlk, err := parseStoredBlock(stBlkBytes)
require.NoError(err)
require.True(isStateBlk)
require.Equal(blk.ID(), gotBlk.ID())

gotBlk, isStateBlk, err = parseStoredBlock(blk.Bytes())
require.NoError(err)
require.False(isStateBlk)
require.Equal(blk.ID(), gotBlk.ID())
}
}

func TestStateSubnetOwner(t *testing.T) {
require := require.New(t)

Expand Down

0 comments on commit 9833b45

Please sign in to comment.