diff --git a/config/example/ir.yaml b/config/example/ir.yaml index b4fd01cb57e..109d2b1c670 100644 --- a/config/example/ir.yaml +++ b/config/example/ir.yaml @@ -77,6 +77,9 @@ morph: ping: # Optional settings of pinging mechanism interval: 30s # Optional time period between pings. Defaults to 30s. Must not be negative timeout: 90s # Optional time period to wait for pong. Defaults to 1m. Must not be negative + set_roles_in_genesis: true # Optional flag for designating P2PNotary and NeoFSAlphabet roles to all + # genesis block validators. The validators depend on 'committee' and, if set, 'validators_history'. + # Must be 'true' or 'false'. network_settings: # NeoFS network settings managed in the Netmap contract epoch_duration: 240 # Time interval (approximate) between two adjacent NeoFS epochs measured in Sidechain blocks. diff --git a/pkg/innerring/config.go b/pkg/innerring/config.go index 134a0fd18a1..f9c531da9c9 100644 --- a/pkg/innerring/config.go +++ b/pkg/innerring/config.go @@ -209,6 +209,11 @@ func parseBlockchainConfig(v *viper.Viper, _logger *zap.Logger) (c blockchain.Co } } + c.SetRolesInGenesis, err = parseConfigBool(v, rootSection+".set_roles_in_genesis", "flag to set roles for the committee in the genesis block") + if err != nil && !errors.Is(err, errMissingConfig) { + return c, err + } + c.Logger = _logger return c, nil diff --git a/pkg/innerring/config_test.go b/pkg/innerring/config_test.go index 4be437fe65b..c728c2912f0 100644 --- a/pkg/innerring/config_test.go +++ b/pkg/innerring/config_test.go @@ -66,6 +66,7 @@ const validBlockchainConfigOptions = ` ping: interval: 44s timeout: 55s + set_roles_in_genesis: true ` func _newConfigFromYAML(tb testing.TB, yaml1, yaml2 string) *viper.Viper { @@ -196,6 +197,7 @@ func TestParseBlockchainConfig(t *testing.T) { 2: 2, 10: 2, }, + SetRolesInGenesis: true, }, c) }) @@ -275,6 +277,11 @@ func TestParseBlockchainConfig(t *testing.T) { {kvF("p2p.peers.max", math.MaxInt32+1)}, {kvF("p2p.peers.attempts", -1)}, {kvF("p2p.peers.attempts", math.MaxInt32+1)}, + {kvF("set_roles_in_genesis", "not a boolean")}, + {kvF("set_roles_in_genesis", 1)}, + {kvF("set_roles_in_genesis", "True")}, + {kvF("set_roles_in_genesis", "False")}, + {kvF("set_roles_in_genesis", "not a boolean")}, } { var reportMsg []string diff --git a/pkg/innerring/internal/blockchain/blockchain.go b/pkg/innerring/internal/blockchain/blockchain.go index 40e79f0ec59..c3175668f03 100644 --- a/pkg/innerring/internal/blockchain/blockchain.go +++ b/pkg/innerring/internal/blockchain/blockchain.go @@ -12,6 +12,7 @@ import ( "github.com/nspcc-dev/neo-go/pkg/config/netmode" "github.com/nspcc-dev/neo-go/pkg/consensus" "github.com/nspcc-dev/neo-go/pkg/core" + "github.com/nspcc-dev/neo-go/pkg/core/native/noderoles" "github.com/nspcc-dev/neo-go/pkg/core/storage" "github.com/nspcc-dev/neo-go/pkg/core/storage/dbconfig" "github.com/nspcc-dev/neo-go/pkg/core/transaction" @@ -239,6 +240,13 @@ type Config struct { // must not exceed Committee length. Value for zero key (genesis height) is // required. ValidatorsHistory map[uint32]uint32 + + // Whether to designate [noderoles.P2PNotary] and [noderoles.NeoFSAlphabet] + // roles to the Committee (keep an eye on ValidatorsHistory) for genesis block + // in the RoleManagement contract. + // + // Optional: by default, roles are unset. + SetRolesInGenesis bool } // New returns new Blockchain configured by the specified Config. New panics if @@ -336,13 +344,26 @@ func New(cfg Config) (res *Blockchain, err error) { cfgBaseProto.P2PSigExtensions = true cfgBaseProto.MaxTraceableBlocks = cfg.TraceableChainLength cfgBaseProto.Hardforks = cfg.HardForks + var genesisValidatorsCount uint32 if cfg.ValidatorsHistory != nil { cfgBaseProto.ValidatorsHistory = make(map[uint32]uint32, len(cfg.ValidatorsHistory)) for height, num := range cfg.ValidatorsHistory { cfgBaseProto.ValidatorsHistory[height] = num } + + // value checked above in function + genesisValidatorsCount = cfg.ValidatorsHistory[0] } else { cfgBaseProto.ValidatorsCount = uint32(len(standByCommittee)) + genesisValidatorsCount = cfgBaseProto.ValidatorsCount + } + + if cfg.SetRolesInGenesis { + cfgBaseProto.Genesis.Roles = map[noderoles.Role]keys.PublicKeys{ + // Notary service is always enabled, see below + noderoles.P2PNotary: cfg.Committee[:genesisValidatorsCount], + noderoles.NeoFSAlphabet: cfg.Committee[:genesisValidatorsCount], + } } cfgBaseApp := &cfgBase.ApplicationConfiguration