diff --git a/cmd/node/config/enableEpochs.toml b/cmd/node/config/enableEpochs.toml index dd6e20d3589..5da22947810 100644 --- a/cmd/node/config/enableEpochs.toml +++ b/cmd/node/config/enableEpochs.toml @@ -64,6 +64,12 @@ # GovernanceEnableEpoch represents the epoch when governance is enabled GovernanceEnableEpoch = 5 + # GovernanceDisableProposeEnableEpoch represents the epoch when governance disable proposal is enabled + GovernanceDisableProposeEnableEpoch = 6 + + # GovernanceFixesEnableEpoch represents the epoch when governance fixes are enabled + GovernanceFixesEnableEpoch = 7 + # DelegationManagerEnableEpoch represents the epoch when the delegation manager is enabled # epoch should not be 0 DelegationManagerEnableEpoch = 1 diff --git a/common/constants.go b/common/constants.go index c2d76f0072a..cacc0f99d7f 100644 --- a/common/constants.go +++ b/common/constants.go @@ -913,6 +913,8 @@ const ( ESDTFlag core.EnableEpochFlag = "ESDTFlag" ESDTFlagInSpecificEpochOnly core.EnableEpochFlag = "ESDTFlagInSpecificEpochOnly" GovernanceFlag core.EnableEpochFlag = "GovernanceFlag" + GovernanceDisableProposeFlag core.EnableEpochFlag = "GovernanceDisableProposeFlag" + GovernanceFixesFlag core.EnableEpochFlag = "GovernanceFixesFlag" GovernanceFlagInSpecificEpochOnly core.EnableEpochFlag = "GovernanceFlagInSpecificEpochOnly" DelegationManagerFlag core.EnableEpochFlag = "DelegationManagerFlag" DelegationSmartContractFlag core.EnableEpochFlag = "DelegationSmartContractFlag" diff --git a/common/enablers/enableEpochsHandler.go b/common/enablers/enableEpochsHandler.go index 197cab8fff8..7e19773707b 100644 --- a/common/enablers/enableEpochsHandler.go +++ b/common/enablers/enableEpochsHandler.go @@ -185,6 +185,18 @@ func (handler *enableEpochsHandler) createAllFlagsMap() { }, activationEpoch: handler.enableEpochsConfig.GovernanceEnableEpoch, }, + common.GovernanceDisableProposeFlag: { + isActiveInEpoch: func(epoch uint32) bool { + return epoch >= handler.enableEpochsConfig.GovernanceDisableProposeEnableEpoch + }, + activationEpoch: handler.enableEpochsConfig.GovernanceDisableProposeEnableEpoch, + }, + common.GovernanceFixesFlag: { + isActiveInEpoch: func(epoch uint32) bool { + return epoch >= handler.enableEpochsConfig.GovernanceFixesEnableEpoch + }, + activationEpoch: handler.enableEpochsConfig.GovernanceFixesEnableEpoch, + }, common.DelegationManagerFlag: { isActiveInEpoch: func(epoch uint32) bool { return epoch >= handler.enableEpochsConfig.DelegationManagerEnableEpoch diff --git a/common/enablers/enableEpochsHandler_test.go b/common/enablers/enableEpochsHandler_test.go index 30949150e49..4b35120441b 100644 --- a/common/enablers/enableEpochsHandler_test.go +++ b/common/enablers/enableEpochsHandler_test.go @@ -37,6 +37,8 @@ func createEnableEpochsConfig() config.EnableEpochs { DoubleKeyProtectionEnableEpoch: 19, ESDTEnableEpoch: 20, GovernanceEnableEpoch: 21, + GovernanceDisableProposeEnableEpoch: 22, + GovernanceFixesEnableEpoch: 23, DelegationManagerEnableEpoch: 22, DelegationSmartContractEnableEpoch: 23, CorrectLastUnjailedEnableEpoch: 24, @@ -213,6 +215,8 @@ func TestEnableEpochsHandler_IsFlagEnabled(t *testing.T) { require.False(t, handler.IsFlagEnabled(common.ESDTFlagInSpecificEpochOnly)) // == require.True(t, handler.IsFlagEnabled(common.GovernanceFlag)) require.False(t, handler.IsFlagEnabled(common.GovernanceFlagInSpecificEpochOnly)) // == + require.True(t, handler.IsFlagEnabled(common.GovernanceDisableProposeFlag)) // == + require.True(t, handler.IsFlagEnabled(common.GovernanceFixesFlag)) // == require.True(t, handler.IsFlagEnabled(common.DelegationManagerFlag)) require.True(t, handler.IsFlagEnabled(common.DelegationSmartContractFlag)) require.False(t, handler.IsFlagEnabled(common.DelegationSmartContractFlagInSpecificEpochOnly)) // == @@ -326,6 +330,8 @@ func TestEnableEpochsHandler_GetActivationEpoch(t *testing.T) { require.Equal(t, cfg.DoubleKeyProtectionEnableEpoch, handler.GetActivationEpoch(common.DoubleKeyProtectionFlag)) require.Equal(t, cfg.ESDTEnableEpoch, handler.GetActivationEpoch(common.ESDTFlag)) require.Equal(t, cfg.GovernanceEnableEpoch, handler.GetActivationEpoch(common.GovernanceFlag)) + require.Equal(t, cfg.GovernanceDisableProposeEnableEpoch, handler.GetActivationEpoch(common.GovernanceDisableProposeFlag)) + require.Equal(t, cfg.GovernanceFixesEnableEpoch, handler.GetActivationEpoch(common.GovernanceFixesFlag)) require.Equal(t, cfg.DelegationManagerEnableEpoch, handler.GetActivationEpoch(common.DelegationManagerFlag)) require.Equal(t, cfg.DelegationSmartContractEnableEpoch, handler.GetActivationEpoch(common.DelegationSmartContractFlag)) require.Equal(t, cfg.CorrectLastUnjailedEnableEpoch, handler.GetActivationEpoch(common.CorrectLastUnJailedFlag)) diff --git a/config/epochConfig.go b/config/epochConfig.go index 854f80063be..92730e246a9 100644 --- a/config/epochConfig.go +++ b/config/epochConfig.go @@ -32,6 +32,8 @@ type EnableEpochs struct { DoubleKeyProtectionEnableEpoch uint32 ESDTEnableEpoch uint32 GovernanceEnableEpoch uint32 + GovernanceDisableProposeEnableEpoch uint32 + GovernanceFixesEnableEpoch uint32 DelegationManagerEnableEpoch uint32 DelegationSmartContractEnableEpoch uint32 CorrectLastUnjailedEnableEpoch uint32 diff --git a/config/tomlConfig_test.go b/config/tomlConfig_test.go index a6e9f5c2086..7d7b0912625 100644 --- a/config/tomlConfig_test.go +++ b/config/tomlConfig_test.go @@ -619,6 +619,12 @@ func TestEnableEpochConfig(t *testing.T) { # GovernanceEnableEpoch represents the epoch when governance is enabled GovernanceEnableEpoch = 21 + # GovernanceDisableProposeEnableEpoch represents the epoch when governance disable proposal is enabled + GovernanceDisableProposeEnableEpoch = 22 + + # GovernanceFixesEnableEpoch represents the epoch when governance fixes are enabled + GovernanceFixesEnableEpoch = 23 + # DelegationManagerEnableEpoch represents the epoch when the delegation manager is enabled # epoch should not be 0 DelegationManagerEnableEpoch = 22 @@ -883,6 +889,8 @@ func TestEnableEpochConfig(t *testing.T) { DoubleKeyProtectionEnableEpoch: 19, ESDTEnableEpoch: 20, GovernanceEnableEpoch: 21, + GovernanceDisableProposeEnableEpoch: 22, + GovernanceFixesEnableEpoch: 23, DelegationManagerEnableEpoch: 22, DelegationSmartContractEnableEpoch: 23, CorrectLastUnjailedEnableEpoch: 24, diff --git a/genesis/process/shardGenesisBlockCreator.go b/genesis/process/shardGenesisBlockCreator.go index 9fef8f05569..ec3cf7f8d6b 100644 --- a/genesis/process/shardGenesisBlockCreator.go +++ b/genesis/process/shardGenesisBlockCreator.go @@ -88,6 +88,8 @@ func createGenesisConfig() config.EnableEpochs { DoubleKeyProtectionEnableEpoch: 0, ESDTEnableEpoch: unreachableEpoch, GovernanceEnableEpoch: unreachableEpoch, + GovernanceDisableProposeEnableEpoch: unreachableEpoch, + GovernanceFixesEnableEpoch: unreachableEpoch, DelegationManagerEnableEpoch: unreachableEpoch, DelegationSmartContractEnableEpoch: unreachableEpoch, CorrectLastUnjailedEnableEpoch: unreachableEpoch, diff --git a/integrationTests/testProcessorNode.go b/integrationTests/testProcessorNode.go index 5b59fedb896..c72d6360cd5 100644 --- a/integrationTests/testProcessorNode.go +++ b/integrationTests/testProcessorNode.go @@ -3172,6 +3172,8 @@ func CreateEnableEpochsConfig() config.EnableEpochs { DoubleKeyProtectionEnableEpoch: 0, ESDTEnableEpoch: UnreachableEpoch, GovernanceEnableEpoch: UnreachableEpoch, + GovernanceDisableProposeEnableEpoch: UnreachableEpoch, + GovernanceFixesEnableEpoch: UnreachableEpoch, DelegationManagerEnableEpoch: UnreachableEpoch, DelegationSmartContractEnableEpoch: UnreachableEpoch, CorrectLastUnjailedEnableEpoch: UnreachableEpoch, diff --git a/node/nodeRunner.go b/node/nodeRunner.go index 71cdc1b1beb..a4af2192f2d 100644 --- a/node/nodeRunner.go +++ b/node/nodeRunner.go @@ -158,6 +158,8 @@ func printEnableEpochs(configs *config.Configs) { log.Debug(readEpochFor("double key protection"), "epoch", enableEpochs.DoubleKeyProtectionEnableEpoch) log.Debug(readEpochFor("esdt"), "epoch", enableEpochs.ESDTEnableEpoch) log.Debug(readEpochFor("governance"), "epoch", enableEpochs.GovernanceEnableEpoch) + log.Debug(readEpochFor("governance disable proposal"), "epoch", enableEpochs.GovernanceDisableProposeEnableEpoch) + log.Debug(readEpochFor("governance fixes"), "epoch", enableEpochs.GovernanceFixesEnableEpoch) log.Debug(readEpochFor("delegation manager"), "epoch", enableEpochs.DelegationManagerEnableEpoch) log.Debug(readEpochFor("delegation smart contract"), "epoch", enableEpochs.DelegationSmartContractEnableEpoch) log.Debug(readEpochFor("correct last unjailed"), "epoch", enableEpochs.CorrectLastUnjailedEnableEpoch) diff --git a/vm/systemSmartContracts/governance.go b/vm/systemSmartContracts/governance.go index 042df1bc204..f23e5babc77 100644 --- a/vm/systemSmartContracts/governance.go +++ b/vm/systemSmartContracts/governance.go @@ -1,4 +1,4 @@ -//go:generate protoc -I=. -I=$GOPATH/src -I=$GOPATH/src/github.com/gogo/protobuf/protobuf --gogoslick_out=. governance.proto +//go:generate protoc -I=. -I=$GOPATH/src -I=$GOPATH/src/github.com/gogo/protobuf/protobuf --gogoslick_out=. governance.proto package systemSmartContracts import ( @@ -155,8 +155,6 @@ func (g *governanceContract) Execute(args *vmcommon.ContractCallInput) vmcommon. return g.viewVotingPower(args) case "viewConfig": return g.viewConfig(args) - case "viewUserVoteHistory": - return g.viewUserVoteHistory(args) case "viewDelegatedVoteInfo": return g.viewDelegatedVoteInfo(args) case "viewProposal": @@ -284,6 +282,10 @@ func (g *governanceContract) changeConfig(args *vmcommon.ContractCallInput) vmco // proposal creates a new proposal from passed arguments func (g *governanceContract) proposal(args *vmcommon.ContractCallInput) vmcommon.ReturnCode { + if g.enableEpochsHandler.IsFlagEnabled(common.GovernanceDisableProposeFlag) && !g.enableEpochsHandler.IsFlagEnabled(common.GovernanceFixesFlag) { + g.eei.AddReturnMessage("proposing is disabled") + return vmcommon.UserError + } err := g.eei.UseGas(g.gasCost.MetaChainSystemSCsCost.Proposal) if err != nil { g.eei.AddReturnMessage("not enough gas") @@ -398,7 +400,8 @@ func (g *governanceContract) vote(args *vmcommon.ContractCallInput) vmcommon.Ret string(args.Arguments[1]), totalVotingPower, totalStake, - true) + true, + nil) if err != nil { g.eei.AddReturnMessage(err.Error()) return vmcommon.UserError @@ -465,7 +468,8 @@ func (g *governanceContract) delegateVote(args *vmcommon.ContractCallInput) vmco string(args.Arguments[1]), votePower, userStake, - false) + false, + args.CallerAddr) if err != nil { g.eei.AddReturnMessage(err.Error()) return vmcommon.UserError @@ -524,9 +528,11 @@ func (g *governanceContract) addUserVote( totalVotingPower *big.Int, totalStake *big.Int, direct bool, + scAddress []byte, ) error { nonce := big.NewInt(0).SetBytes(nonceAsBytes) - err := g.updateUserVoteList(address, nonce.Uint64(), direct) + //TODO: remove extra struct & methods for V2 if no V1 proposal exists + err := g.updateUserVoteListV2(address, nonce.Uint64(), direct, scAddress) if err != nil { return err } @@ -545,25 +551,57 @@ func (g *governanceContract) addUserVote( return g.saveGeneralProposal(proposal.CommitHash, proposal) } -func (g *governanceContract) updateUserVoteList(address []byte, nonce uint64, direct bool) error { - userVoteList, err := g.getUserVotes(address) +func (g *governanceContract) updateUserVoteListV1(address []byte, nonce uint64, direct bool) error { + userVoteList, err := g.getUserVotesV1(address) if err != nil { return err } + err = g.updateUserVotesV1(userVoteList, nonce, direct) + if err != nil { + return err + } + + return g.saveUserVotesV1(address, userVoteList) +} + +func (g *governanceContract) updateUserVoteListV2(address []byte, nonce uint64, direct bool, scAddress []byte) error { + if !g.enableEpochsHandler.IsFlagEnabled(common.GovernanceFixesFlag) { + return g.updateUserVoteListV1(address, nonce, direct) + } + userVoteList, err := g.getUserVotesV2(address) + if err != nil { + return err + } + + err = g.updateUserVotesV2(userVoteList, nonce, direct, scAddress) + if err != nil { + return err + } + + return g.saveUserVotesV2(address, userVoteList) +} + +func (g *governanceContract) updateUserVotesV1(userVoteList *OngoingVotedList, nonce uint64, direct bool) error { + var err error if direct { userVoteList.Direct, err = addNewNonce(userVoteList.Direct, nonce) - if err != nil { - return err - } - } else { - userVoteList.Delegated, err = addNewNonce(userVoteList.Delegated, nonce) - if err != nil { - return err - } + return err + } + + userVoteList.Delegated, err = addNewNonce(userVoteList.Delegated, nonce) + return err +} + +func (g *governanceContract) updateUserVotesV2(userVoteList *OngoingVotedListV2, nonce uint64, direct bool, scAddress []byte) error { + var err error + if direct { + userVoteList.Direct, err = addNewNonce(userVoteList.Direct, nonce) + return err } - return g.saveUserVotes(address, userVoteList) + userVoteList.DelegatedWithAddress, err = addNewNonceV2(userVoteList.DelegatedWithAddress, scAddress, nonce) + return err } func addNewNonce(nonceList []uint64, newNonce uint64) ([]uint64, error) { @@ -577,6 +615,20 @@ func addNewNonce(nonceList []uint64, newNonce uint64) ([]uint64, error) { return nonceList, nil } +func addNewNonceV2(nonceList []*DelegatedWithAddress, newDelegatedAddress []byte, newNonce uint64) ([]*DelegatedWithAddress, error) { + for _, delegatedStruct := range nonceList { + if newNonce == delegatedStruct.Nonce && bytes.Equal(delegatedStruct.DelegatedAddress, newDelegatedAddress) { + return nil, vm.ErrDoubleVote + } + } + + nonceList = append(nonceList, &DelegatedWithAddress{ + Nonce: newNonce, + DelegatedAddress: newDelegatedAddress, + }) + return nonceList, nil +} + func (g *governanceContract) getMinValueToVote() (*big.Int, error) { delegationManagement, err := getDelegationManagement(g.eei, g.marshalizer, g.delegationMgrSCAddress) if err != nil { @@ -756,41 +808,6 @@ func (g *governanceContract) viewConfig(args *vmcommon.ContractCallInput) vmcomm return vmcommon.Ok } -func (g *governanceContract) viewUserVoteHistory(args *vmcommon.ContractCallInput) vmcommon.ReturnCode { - err := g.checkViewFuncArguments(args, 1) - if err != nil { - g.eei.AddReturnMessage(err.Error()) - return vmcommon.UserError - } - - userVotes, err := g.getUserVotes(args.Arguments[0]) - if err != nil { - g.eei.AddReturnMessage(err.Error()) - return vmcommon.UserError - } - - g.finishWithIntValue(len(userVotes.Delegated)) // first we send the number of delegated nonces and afterward the nonces - for _, val := range userVotes.Delegated { - g.finishWithIntValue(int(val)) - } - - g.finishWithIntValue(len(userVotes.Direct)) // then we send the number of direct nonces and afterward the nonces - for _, val := range userVotes.Direct { - g.finishWithIntValue(int(val)) - } - - return vmcommon.Ok -} - -func (g *governanceContract) finishWithIntValue(value int) { - if value == 0 { - g.eei.Finish([]byte{0}) - return - } - - g.eei.Finish(big.NewInt(int64(value)).Bytes()) -} - func (g *governanceContract) viewProposal(args *vmcommon.ContractCallInput) vmcommon.ReturnCode { err := g.checkViewFuncArguments(args, 1) if err != nil { @@ -1010,7 +1027,17 @@ func (g *governanceContract) getTotalStake(validatorAddress []byte) (*big.Int, e return validatorData.TotalStakeValue, nil } -func (g *governanceContract) saveUserVotes(address []byte, votedList *OngoingVotedList) error { +func (g *governanceContract) saveUserVotesV1(address []byte, votedList *OngoingVotedList) error { + marshaledData, err := g.marshalizer.Marshal(votedList) + if err != nil { + return err + } + g.eei.SetStorage(address, marshaledData) + + return nil +} + +func (g *governanceContract) saveUserVotesV2(address []byte, votedList *OngoingVotedListV2) error { marshaledData, err := g.marshalizer.Marshal(votedList) if err != nil { return err @@ -1020,7 +1047,7 @@ func (g *governanceContract) saveUserVotes(address []byte, votedList *OngoingVot return nil } -func (g *governanceContract) getUserVotes(address []byte) (*OngoingVotedList, error) { +func (g *governanceContract) getUserVotesV1(address []byte) (*OngoingVotedList, error) { onGoingList := &OngoingVotedList{ Direct: make([]uint64, 0), Delegated: make([]uint64, 0), @@ -1038,6 +1065,25 @@ func (g *governanceContract) getUserVotes(address []byte) (*OngoingVotedList, er return onGoingList, nil } +// getUserVotesV2 returns the ongoing voted list for a user +// if the user has v1 ongoing list, it will be converted to v2, dropping Delegate field +func (g *governanceContract) getUserVotesV2(address []byte) (*OngoingVotedListV2, error) { + onGoingListV2 := &OngoingVotedListV2{ + Direct: make([]uint64, 0), + DelegatedWithAddress: make([]*DelegatedWithAddress, 0), + } + marshaledData := g.eei.GetStorage(address) + if len(marshaledData) == 0 { + return onGoingListV2, nil + } + + err := g.marshalizer.Unmarshal(onGoingListV2, marshaledData) + if err != nil { + return nil, err + } + return onGoingListV2, nil +} + func (g *governanceContract) getDelegatedContractInfo(scAddress []byte, reference []byte) (*DelegatedSCVoteInfo, error) { scVoteInfo := &DelegatedSCVoteInfo{ TotalPower: big.NewInt(0), diff --git a/vm/systemSmartContracts/governance.pb.go b/vm/systemSmartContracts/governance.pb.go index 49e8acfc63e..a884dfb6009 100644 --- a/vm/systemSmartContracts/governance.pb.go +++ b/vm/systemSmartContracts/governance.pb.go @@ -389,6 +389,100 @@ func (m *OngoingVotedList) GetDelegated() []uint64 { return nil } +type OngoingVotedListV2 struct { + Direct []uint64 `protobuf:"varint,1,rep,packed,name=Direct,proto3" json:"Direct"` + DelegatedWithAddress []*DelegatedWithAddress `protobuf:"bytes,2,rep,name=DelegatedWithAddress,proto3" json:"DelegatedWithAddress"` +} + +func (m *OngoingVotedListV2) Reset() { *m = OngoingVotedListV2{} } +func (*OngoingVotedListV2) ProtoMessage() {} +func (*OngoingVotedListV2) Descriptor() ([]byte, []int) { + return fileDescriptor_e18a03da5266c714, []int{4} +} +func (m *OngoingVotedListV2) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *OngoingVotedListV2) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil +} +func (m *OngoingVotedListV2) XXX_Merge(src proto.Message) { + xxx_messageInfo_OngoingVotedListV2.Merge(m, src) +} +func (m *OngoingVotedListV2) XXX_Size() int { + return m.Size() +} +func (m *OngoingVotedListV2) XXX_DiscardUnknown() { + xxx_messageInfo_OngoingVotedListV2.DiscardUnknown(m) +} + +var xxx_messageInfo_OngoingVotedListV2 proto.InternalMessageInfo + +func (m *OngoingVotedListV2) GetDirect() []uint64 { + if m != nil { + return m.Direct + } + return nil +} + +func (m *OngoingVotedListV2) GetDelegatedWithAddress() []*DelegatedWithAddress { + if m != nil { + return m.DelegatedWithAddress + } + return nil +} + +type DelegatedWithAddress struct { + Nonce uint64 `protobuf:"varint,1,opt,name=Nonce,proto3" json:"Nonce,omitempty"` + DelegatedAddress []byte `protobuf:"bytes,2,opt,name=DelegatedAddress,proto3" json:"DelegatedAddress"` +} + +func (m *DelegatedWithAddress) Reset() { *m = DelegatedWithAddress{} } +func (*DelegatedWithAddress) ProtoMessage() {} +func (*DelegatedWithAddress) Descriptor() ([]byte, []int) { + return fileDescriptor_e18a03da5266c714, []int{5} +} +func (m *DelegatedWithAddress) XXX_Unmarshal(b []byte) error { + return m.Unmarshal(b) +} +func (m *DelegatedWithAddress) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) { + b = b[:cap(b)] + n, err := m.MarshalToSizedBuffer(b) + if err != nil { + return nil, err + } + return b[:n], nil +} +func (m *DelegatedWithAddress) XXX_Merge(src proto.Message) { + xxx_messageInfo_DelegatedWithAddress.Merge(m, src) +} +func (m *DelegatedWithAddress) XXX_Size() int { + return m.Size() +} +func (m *DelegatedWithAddress) XXX_DiscardUnknown() { + xxx_messageInfo_DelegatedWithAddress.DiscardUnknown(m) +} + +var xxx_messageInfo_DelegatedWithAddress proto.InternalMessageInfo + +func (m *DelegatedWithAddress) GetNonce() uint64 { + if m != nil { + return m.Nonce + } + return 0 +} + +func (m *DelegatedWithAddress) GetDelegatedAddress() []byte { + if m != nil { + return m.DelegatedAddress + } + return nil +} + type DelegatedSCVoteInfo struct { TotalPower *math_big.Int `protobuf:"bytes,1,opt,name=TotalPower,proto3,casttypewith=math/big.Int;github.com/multiversx/mx-chain-core-go/data.BigIntCaster" json:"TotalPower"` UsedPower *math_big.Int `protobuf:"bytes,2,opt,name=UsedPower,proto3,casttypewith=math/big.Int;github.com/multiversx/mx-chain-core-go/data.BigIntCaster" json:"UsedPower"` @@ -399,7 +493,7 @@ type DelegatedSCVoteInfo struct { func (m *DelegatedSCVoteInfo) Reset() { *m = DelegatedSCVoteInfo{} } func (*DelegatedSCVoteInfo) ProtoMessage() {} func (*DelegatedSCVoteInfo) Descriptor() ([]byte, []int) { - return fileDescriptor_e18a03da5266c714, []int{4} + return fileDescriptor_e18a03da5266c714, []int{6} } func (m *DelegatedSCVoteInfo) XXX_Unmarshal(b []byte) error { return m.Unmarshal(b) @@ -458,70 +552,76 @@ func init() { proto.RegisterType((*GovernanceConfig)(nil), "proto.GovernanceConfig") proto.RegisterType((*GovernanceConfigV2)(nil), "proto.GovernanceConfigV2") proto.RegisterType((*OngoingVotedList)(nil), "proto.OngoingVotedList") + proto.RegisterType((*OngoingVotedListV2)(nil), "proto.OngoingVotedListV2") + proto.RegisterType((*DelegatedWithAddress)(nil), "proto.DelegatedWithAddress") proto.RegisterType((*DelegatedSCVoteInfo)(nil), "proto.DelegatedSCVoteInfo") } func init() { proto.RegisterFile("governance.proto", fileDescriptor_e18a03da5266c714) } var fileDescriptor_e18a03da5266c714 = []byte{ - // 902 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x56, 0x4f, 0x6f, 0x23, 0x35, - 0x14, 0xcf, 0xe4, 0x5f, 0x5b, 0x37, 0xdd, 0x9d, 0x35, 0x8b, 0x34, 0xe2, 0x30, 0xae, 0x72, 0x8a, - 0x40, 0x4d, 0x24, 0x40, 0x5a, 0x09, 0x2e, 0xec, 0x64, 0xcb, 0x52, 0xa9, 0x9b, 0xed, 0x4e, 0x4b, - 0x60, 0x11, 0x12, 0x72, 0x66, 0xdc, 0xc9, 0x88, 0x8c, 0x5d, 0x8d, 0x9d, 0xfd, 0x83, 0x84, 0xc4, - 0x89, 0x2b, 0x7c, 0x0c, 0xc4, 0x27, 0xe1, 0xd8, 0x63, 0x4f, 0x03, 0x4d, 0x2f, 0x60, 0x71, 0x58, - 0x89, 0x2f, 0x80, 0xec, 0x49, 0xe6, 0x4f, 0x72, 0xaa, 0x18, 0x71, 0xb2, 0xdf, 0xef, 0xd9, 0xbf, - 0xdf, 0xbc, 0x37, 0xcf, 0x7e, 0x06, 0x66, 0xc0, 0x5e, 0x90, 0x98, 0x62, 0xea, 0x91, 0xfe, 0x45, - 0xcc, 0x04, 0x83, 0x2d, 0x3d, 0xbc, 0x73, 0x10, 0x84, 0x62, 0x3a, 0x9f, 0xf4, 0x3d, 0x16, 0x0d, - 0x02, 0x16, 0xb0, 0x81, 0x86, 0x27, 0xf3, 0x73, 0x6d, 0x69, 0x43, 0xcf, 0xd2, 0x5d, 0xdd, 0xbf, - 0xb7, 0xc0, 0xdd, 0xc7, 0x84, 0x92, 0x18, 0xcf, 0x4e, 0x62, 0x76, 0xc1, 0x38, 0x9e, 0x41, 0x04, - 0x5a, 0x23, 0x46, 0x3d, 0x62, 0x19, 0xfb, 0x46, 0xaf, 0xe9, 0xec, 0xc8, 0x04, 0xa5, 0x80, 0x9b, - 0x0e, 0xb0, 0x0f, 0xc0, 0x90, 0x45, 0x51, 0x28, 0x3e, 0xc3, 0x7c, 0x6a, 0xd5, 0xf7, 0x8d, 0x5e, - 0xc7, 0xb9, 0x23, 0x13, 0x54, 0x40, 0xdd, 0xc2, 0x1c, 0x7e, 0x04, 0xee, 0x9c, 0x0a, 0x1c, 0x8b, - 0x31, 0x13, 0xe4, 0xf0, 0x82, 0x79, 0x53, 0xab, 0xa1, 0x99, 0xa1, 0x4c, 0xd0, 0x9a, 0xc7, 0x5d, - 0xb3, 0xe1, 0x87, 0xa0, 0x73, 0x48, 0xfd, 0x7c, 0x67, 0x53, 0xef, 0x34, 0x65, 0x82, 0x4a, 0xb8, - 0x5b, 0xb2, 0xe0, 0x04, 0x34, 0x9e, 0x13, 0x6e, 0xb5, 0xf4, 0xa7, 0x9d, 0xc8, 0x04, 0x29, 0xf3, - 0xd7, 0xdf, 0xd1, 0x61, 0x84, 0xc5, 0x74, 0x30, 0x09, 0x83, 0xfe, 0x11, 0x15, 0x1f, 0x17, 0x52, - 0x15, 0xcd, 0x67, 0x22, 0x7c, 0x41, 0x62, 0xfe, 0x6a, 0x10, 0xbd, 0x3a, 0xf0, 0xa6, 0x38, 0xa4, - 0x07, 0x1e, 0x8b, 0xc9, 0x41, 0xc0, 0x06, 0x3e, 0x16, 0xb8, 0xef, 0x84, 0xc1, 0x11, 0x15, 0x43, - 0xcc, 0x05, 0x89, 0x5d, 0xc5, 0x06, 0xbf, 0x01, 0xf5, 0x11, 0xb3, 0xda, 0x5a, 0xe2, 0xa9, 0x4c, - 0x50, 0x7d, 0xc4, 0xaa, 0x53, 0xa8, 0x8f, 0x18, 0x24, 0xa0, 0x39, 0x26, 0x82, 0x59, 0x5b, 0x5a, - 0xe2, 0x99, 0x4c, 0x90, 0xb6, 0xab, 0x13, 0xd1, 0x74, 0x90, 0x82, 0xad, 0x87, 0x13, 0x2e, 0x70, - 0x48, 0xad, 0x6d, 0xad, 0x74, 0x26, 0x13, 0xb4, 0x82, 0xaa, 0x13, 0x5b, 0x31, 0xc2, 0xef, 0xc0, - 0xee, 0xb3, 0x39, 0x8b, 0xe7, 0xd1, 0xa9, 0xc0, 0xdf, 0x12, 0x6b, 0x47, 0x6b, 0x7e, 0x29, 0x13, - 0x54, 0x84, 0xab, 0xd3, 0x2d, 0xb2, 0xc2, 0x2e, 0x68, 0x9f, 0x60, 0xce, 0x89, 0x6f, 0x81, 0x7d, - 0xa3, 0xb7, 0xed, 0x00, 0x99, 0xa0, 0x25, 0xe2, 0x2e, 0x47, 0xb5, 0x66, 0x38, 0x63, 0x6a, 0xcd, - 0x6e, 0xbe, 0x26, 0x45, 0xdc, 0xe5, 0x08, 0x1f, 0x80, 0xbd, 0x23, 0xce, 0xe7, 0x24, 0x7e, 0xe8, - 0xfb, 0x31, 0xe1, 0xdc, 0xea, 0xe8, 0x28, 0xee, 0xc9, 0x04, 0x95, 0x1d, 0x6e, 0xd9, 0x84, 0xdf, - 0x83, 0xce, 0xea, 0x9c, 0x0d, 0x19, 0x17, 0xd6, 0x9e, 0xde, 0xf7, 0x5c, 0x95, 0x73, 0x11, 0xaf, - 0x2e, 0xfc, 0x12, 0x6d, 0xf7, 0xaf, 0x3a, 0x30, 0x1f, 0x67, 0x37, 0xc7, 0x90, 0xd1, 0xf3, 0x30, - 0x80, 0x3d, 0xb0, 0x3d, 0x9a, 0x47, 0x23, 0xe6, 0x13, 0xae, 0x8f, 0x7c, 0xc3, 0xe9, 0xc8, 0x04, - 0x65, 0x98, 0x9b, 0xcd, 0xe0, 0x7b, 0x60, 0xe7, 0x49, 0x48, 0xd3, 0x84, 0xea, 0x73, 0xdf, 0x72, - 0xf6, 0x64, 0x82, 0x72, 0xd0, 0xcd, 0xa7, 0xf0, 0x13, 0x60, 0x3e, 0x09, 0xa9, 0x4a, 0xea, 0xd9, - 0x34, 0x26, 0x7c, 0xca, 0x66, 0xbe, 0x3e, 0xf7, 0x2d, 0xe7, 0xbe, 0x4c, 0xd0, 0x86, 0xcf, 0xdd, - 0x40, 0x96, 0x0c, 0xaa, 0x48, 0x73, 0x86, 0x66, 0x89, 0xa1, 0xe4, 0x73, 0x37, 0x10, 0x55, 0x6b, - 0xab, 0xf8, 0x3f, 0x25, 0x64, 0x79, 0x1f, 0xe8, 0x5a, 0x2b, 0xc0, 0x15, 0xd6, 0x5a, 0x81, 0xb5, - 0xfb, 0x53, 0x13, 0xc0, 0xf5, 0x5c, 0x8f, 0xdf, 0x2f, 0xe7, 0x50, 0xa5, 0xbb, 0x7e, 0xcb, 0x1c, - 0xd6, 0xf5, 0x9e, 0xff, 0x92, 0xc3, 0x46, 0x89, 0xe1, 0x96, 0x39, 0x6c, 0xfe, 0x8f, 0x39, 0x84, - 0x3f, 0x1a, 0xe0, 0xee, 0x31, 0xe3, 0x62, 0xf3, 0x27, 0x7e, 0x2d, 0x13, 0xb4, 0xee, 0xaa, 0xee, - 0x23, 0xd6, 0x99, 0xe1, 0x10, 0xdc, 0x3b, 0xc6, 0x39, 0x94, 0xf6, 0xc7, 0xb6, 0xee, 0x45, 0x6f, - 0xcb, 0x04, 0x6d, 0x3a, 0xdd, 0x4d, 0xa8, 0xeb, 0x01, 0xf3, 0x29, 0x0d, 0x58, 0x48, 0x03, 0xd5, - 0xa9, 0xfc, 0xe3, 0x90, 0x0b, 0x75, 0xdb, 0x3c, 0x0a, 0x63, 0xe2, 0x09, 0xcb, 0xd8, 0x6f, 0xf4, - 0x9a, 0xe9, 0x6d, 0x93, 0x22, 0xee, 0x72, 0x54, 0x25, 0xf3, 0x88, 0xcc, 0x48, 0x80, 0x05, 0x51, - 0xbf, 0x5f, 0x2d, 0xd3, 0x25, 0x93, 0x81, 0x6e, 0x3e, 0xed, 0xfe, 0xd3, 0x00, 0x6f, 0x65, 0xd6, - 0xe9, 0x50, 0x29, 0x1d, 0xd1, 0x73, 0x06, 0x5f, 0x02, 0x70, 0xc6, 0x04, 0x9e, 0x9d, 0xb0, 0x97, - 0x24, 0xd6, 0x85, 0xd7, 0x71, 0xbe, 0x50, 0x4d, 0x3b, 0x47, 0xab, 0xcb, 0x5f, 0x81, 0x14, 0x0a, - 0xb0, 0xf3, 0x39, 0x27, 0x7e, 0xaa, 0x9b, 0x3e, 0x16, 0xc6, 0xea, 0xeb, 0x33, 0xb0, 0x3a, 0xd9, - 0x9c, 0x33, 0x0b, 0x37, 0x6d, 0x32, 0x8d, 0xb5, 0x70, 0x2b, 0xee, 0x31, 0x05, 0xd2, 0x55, 0xb8, - 0xa9, 0x6e, 0xb3, 0x1c, 0x6e, 0xc5, 0xb2, 0x39, 0xe7, 0xbb, 0x0f, 0xc0, 0x9e, 0xfa, 0xd3, 0x63, - 0x3c, 0x9b, 0x93, 0xb3, 0xd7, 0x17, 0x04, 0x6e, 0xe9, 0x17, 0x90, 0x59, 0x83, 0x6d, 0xf5, 0x4c, - 0x31, 0x0d, 0xb8, 0x9d, 0xbe, 0x26, 0xcc, 0x3a, 0xdc, 0xcd, 0x1a, 0xbe, 0xd9, 0x70, 0x46, 0x97, - 0xd7, 0x76, 0xed, 0xea, 0xda, 0xae, 0xbd, 0xb9, 0xb6, 0x8d, 0x1f, 0x16, 0xb6, 0xf1, 0xcb, 0xc2, - 0x36, 0x7e, 0x5b, 0xd8, 0xc6, 0xe5, 0xc2, 0x36, 0xae, 0x16, 0xb6, 0xf1, 0xc7, 0xc2, 0x36, 0xfe, - 0x5c, 0xd8, 0xb5, 0x37, 0x0b, 0xdb, 0xf8, 0xf9, 0xc6, 0xae, 0x5d, 0xde, 0xd8, 0xb5, 0xab, 0x1b, - 0xbb, 0xf6, 0xd5, 0x7d, 0xfe, 0x9a, 0x0b, 0x12, 0x9d, 0x46, 0x38, 0x16, 0x43, 0x46, 0x45, 0x8c, - 0x3d, 0xc1, 0x27, 0x6d, 0xfd, 0xae, 0xfc, 0xe0, 0xdf, 0x00, 0x00, 0x00, 0xff, 0xff, 0x67, 0xcd, - 0x78, 0x44, 0xa1, 0x0a, 0x00, 0x00, + // 971 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x56, 0x4f, 0x6f, 0xe3, 0x44, + 0x14, 0x8f, 0xf3, 0xaf, 0xed, 0x34, 0xdd, 0xf5, 0x0e, 0x45, 0xb2, 0x40, 0xf2, 0x54, 0x39, 0x45, + 0xa0, 0x26, 0x52, 0x41, 0x5a, 0x09, 0x2e, 0xbb, 0xce, 0x96, 0xa5, 0x52, 0x37, 0xdb, 0x75, 0x4b, + 0x96, 0x45, 0x48, 0x68, 0x62, 0x4f, 0x1d, 0x8b, 0x78, 0xa6, 0xf2, 0x4c, 0xf6, 0x0f, 0x12, 0x12, + 0x27, 0xae, 0xf0, 0x1d, 0xb8, 0x20, 0x3e, 0x09, 0xc7, 0x1e, 0x7b, 0x32, 0x34, 0xbd, 0x80, 0xc5, + 0x61, 0x25, 0xbe, 0x00, 0x9a, 0x71, 0xe2, 0x3f, 0x49, 0x0e, 0xac, 0xb0, 0x38, 0xcd, 0xbc, 0xdf, + 0x9b, 0xf9, 0xfd, 0xfc, 0x9e, 0xdf, 0xcc, 0x3c, 0xa0, 0x7b, 0xec, 0x39, 0x09, 0x29, 0xa6, 0x0e, + 0xe9, 0x5e, 0x84, 0x4c, 0x30, 0xd8, 0x50, 0xc3, 0x3b, 0xfb, 0x9e, 0x2f, 0xc6, 0xd3, 0x51, 0xd7, + 0x61, 0x41, 0xcf, 0x63, 0x1e, 0xeb, 0x29, 0x78, 0x34, 0x3d, 0x57, 0x96, 0x32, 0xd4, 0x2c, 0xd9, + 0xd5, 0xfe, 0x6b, 0x03, 0xdc, 0x7e, 0x48, 0x28, 0x09, 0xf1, 0xe4, 0x24, 0x64, 0x17, 0x8c, 0xe3, + 0x09, 0x44, 0xa0, 0x31, 0x60, 0xd4, 0x21, 0x86, 0xb6, 0xa7, 0x75, 0xea, 0xd6, 0x56, 0x1c, 0xa1, + 0x04, 0xb0, 0x93, 0x01, 0x76, 0x01, 0xe8, 0xb3, 0x20, 0xf0, 0xc5, 0xa7, 0x98, 0x8f, 0x8d, 0xea, + 0x9e, 0xd6, 0x69, 0x59, 0xb7, 0xe2, 0x08, 0xe5, 0x50, 0x3b, 0x37, 0x87, 0x1f, 0x81, 0x5b, 0xa7, + 0x02, 0x87, 0x62, 0xc8, 0x04, 0x39, 0xbc, 0x60, 0xce, 0xd8, 0xa8, 0x29, 0x66, 0x18, 0x47, 0x68, + 0xc9, 0x63, 0x2f, 0xd9, 0xf0, 0x43, 0xd0, 0x3a, 0xa4, 0x6e, 0xb6, 0xb3, 0xae, 0x76, 0xea, 0x71, + 0x84, 0x0a, 0xb8, 0x5d, 0xb0, 0xe0, 0x08, 0xd4, 0x9e, 0x11, 0x6e, 0x34, 0xd4, 0xa7, 0x9d, 0xc4, + 0x11, 0x92, 0xe6, 0x2f, 0xbf, 0xa1, 0xc3, 0x00, 0x8b, 0x71, 0x6f, 0xe4, 0x7b, 0xdd, 0x23, 0x2a, + 0x3e, 0xce, 0xa5, 0x2a, 0x98, 0x4e, 0x84, 0xff, 0x9c, 0x84, 0xfc, 0x65, 0x2f, 0x78, 0xb9, 0xef, + 0x8c, 0xb1, 0x4f, 0xf7, 0x1d, 0x16, 0x92, 0x7d, 0x8f, 0xf5, 0x5c, 0x2c, 0x70, 0xd7, 0xf2, 0xbd, + 0x23, 0x2a, 0xfa, 0x98, 0x0b, 0x12, 0xda, 0x92, 0x0d, 0x7e, 0x05, 0xaa, 0x03, 0x66, 0x34, 0x95, + 0xc4, 0xe3, 0x38, 0x42, 0xd5, 0x01, 0x2b, 0x4f, 0xa1, 0x3a, 0x60, 0x90, 0x80, 0xfa, 0x90, 0x08, + 0x66, 0x6c, 0x28, 0x89, 0x27, 0x71, 0x84, 0x94, 0x5d, 0x9e, 0x88, 0xa2, 0x83, 0x14, 0x6c, 0xdc, + 0x1f, 0x71, 0x81, 0x7d, 0x6a, 0x6c, 0x2a, 0xa5, 0xb3, 0x38, 0x42, 0x0b, 0xa8, 0x3c, 0xb1, 0x05, + 0x23, 0xfc, 0x06, 0x6c, 0x3f, 0x99, 0xb2, 0x70, 0x1a, 0x9c, 0x0a, 0xfc, 0x35, 0x31, 0xb6, 0x94, + 0xe6, 0xe7, 0x71, 0x84, 0xf2, 0x70, 0x79, 0xba, 0x79, 0x56, 0xd8, 0x06, 0xcd, 0x13, 0xcc, 0x39, + 0x71, 0x0d, 0xb0, 0xa7, 0x75, 0x36, 0x2d, 0x10, 0x47, 0x68, 0x8e, 0xd8, 0xf3, 0x51, 0xae, 0xe9, + 0x4f, 0x98, 0x5c, 0xb3, 0x9d, 0xad, 0x49, 0x10, 0x7b, 0x3e, 0xc2, 0xbb, 0x60, 0xe7, 0x88, 0xf3, + 0x29, 0x09, 0xef, 0xbb, 0x6e, 0x48, 0x38, 0x37, 0x5a, 0x2a, 0x8a, 0x3b, 0x71, 0x84, 0x8a, 0x0e, + 0xbb, 0x68, 0xc2, 0x6f, 0x41, 0x6b, 0x71, 0xce, 0xfa, 0x8c, 0x0b, 0x63, 0x47, 0xed, 0x7b, 0x26, + 0xcb, 0x39, 0x8f, 0x97, 0x17, 0x7e, 0x81, 0xb6, 0xfd, 0x67, 0x15, 0xe8, 0x0f, 0xd3, 0x9b, 0xa3, + 0xcf, 0xe8, 0xb9, 0xef, 0xc1, 0x0e, 0xd8, 0x1c, 0x4c, 0x83, 0x01, 0x73, 0x09, 0x57, 0x47, 0xbe, + 0x66, 0xb5, 0xe2, 0x08, 0xa5, 0x98, 0x9d, 0xce, 0xe0, 0xfb, 0x60, 0xeb, 0x91, 0x4f, 0x93, 0x84, + 0xaa, 0x73, 0xdf, 0xb0, 0x76, 0xe2, 0x08, 0x65, 0xa0, 0x9d, 0x4d, 0xe1, 0x3d, 0xa0, 0x3f, 0xf2, + 0xa9, 0x4c, 0xea, 0xd9, 0x38, 0x24, 0x7c, 0xcc, 0x26, 0xae, 0x3a, 0xf7, 0x0d, 0x6b, 0x37, 0x8e, + 0xd0, 0x8a, 0xcf, 0x5e, 0x41, 0xe6, 0x0c, 0xb2, 0x48, 0x33, 0x86, 0x7a, 0x81, 0xa1, 0xe0, 0xb3, + 0x57, 0x10, 0x59, 0x6b, 0x8b, 0xf8, 0x3f, 0x21, 0x64, 0x7e, 0x1f, 0xa8, 0x5a, 0xcb, 0xc1, 0x25, + 0xd6, 0x5a, 0x8e, 0xb5, 0xfd, 0x43, 0x1d, 0xc0, 0xe5, 0x5c, 0x0f, 0x0f, 0x8a, 0x39, 0x94, 0xe9, + 0xae, 0xbe, 0x61, 0x0e, 0xab, 0x6a, 0xcf, 0x7f, 0xc9, 0x61, 0xad, 0xc0, 0xf0, 0x86, 0x39, 0xac, + 0xff, 0x8f, 0x39, 0x84, 0xdf, 0x6b, 0xe0, 0xf6, 0x31, 0xe3, 0x62, 0xf5, 0x27, 0x7e, 0x19, 0x47, + 0x68, 0xd9, 0x55, 0xde, 0x47, 0x2c, 0x33, 0xc3, 0x3e, 0xb8, 0x73, 0x8c, 0x33, 0x28, 0x79, 0x1f, + 0x9b, 0xea, 0x2d, 0x7a, 0x3b, 0x8e, 0xd0, 0xaa, 0xd3, 0x5e, 0x85, 0xda, 0x0e, 0xd0, 0x1f, 0x53, + 0x8f, 0xf9, 0xd4, 0x93, 0x2f, 0x95, 0x7b, 0xec, 0x73, 0x21, 0x6f, 0x9b, 0x07, 0x7e, 0x48, 0x1c, + 0x61, 0x68, 0x7b, 0xb5, 0x4e, 0x3d, 0xb9, 0x6d, 0x12, 0xc4, 0x9e, 0x8f, 0xb2, 0x64, 0x1e, 0x90, + 0x09, 0xf1, 0xb0, 0x20, 0xf2, 0xf7, 0xcb, 0x65, 0xaa, 0x64, 0x52, 0xd0, 0xce, 0xa6, 0xed, 0x9f, + 0x34, 0x00, 0x97, 0x55, 0x86, 0x07, 0xff, 0x4a, 0xc7, 0x07, 0xbb, 0x29, 0xcf, 0x53, 0x5f, 0x8c, + 0x17, 0x97, 0x9b, 0x94, 0xdc, 0x3e, 0x78, 0x37, 0x69, 0x19, 0xba, 0xeb, 0x96, 0x58, 0x46, 0x1c, + 0xa1, 0xb5, 0x9b, 0xed, 0xb5, 0x68, 0x9b, 0xae, 0x97, 0x82, 0xbb, 0x85, 0xde, 0x63, 0xd1, 0x70, + 0xdc, 0x03, 0x7a, 0xba, 0x3a, 0xfb, 0x28, 0x59, 0x06, 0xaa, 0x88, 0x97, 0x7d, 0xf6, 0x0a, 0xd2, + 0xfe, 0xbb, 0x06, 0xde, 0x4a, 0xc1, 0xd3, 0xbe, 0xcc, 0xcc, 0x11, 0x3d, 0x67, 0xf0, 0x05, 0x00, + 0x67, 0x4c, 0xe0, 0xc9, 0x09, 0x7b, 0x41, 0x42, 0x25, 0xda, 0xb2, 0x9e, 0xca, 0x56, 0x26, 0x43, + 0xcb, 0xab, 0xaa, 0x1c, 0x29, 0x14, 0x60, 0xeb, 0x33, 0x4e, 0xdc, 0x44, 0x37, 0x89, 0x65, 0x28, + 0xff, 0x69, 0x0a, 0x96, 0x27, 0x9b, 0x71, 0xa6, 0xe1, 0x26, 0x4f, 0x6f, 0x6d, 0x29, 0xdc, 0x92, + 0x5f, 0xde, 0x1c, 0xe9, 0x22, 0xdc, 0x44, 0xb7, 0x5e, 0x0c, 0xb7, 0x64, 0xd9, 0x8c, 0xf3, 0xbd, + 0xbb, 0x60, 0x47, 0xfe, 0xe9, 0x21, 0x9e, 0x4c, 0xc9, 0xd9, 0xab, 0x0b, 0x02, 0x37, 0x54, 0x5f, + 0xa8, 0x57, 0x60, 0x53, 0x36, 0x6f, 0xba, 0x06, 0x37, 0x93, 0x1e, 0x4b, 0xaf, 0xc2, 0xed, 0xb4, + 0x0d, 0xd2, 0x6b, 0xd6, 0xe0, 0xf2, 0xda, 0xac, 0x5c, 0x5d, 0x9b, 0x95, 0xd7, 0xd7, 0xa6, 0xf6, + 0xdd, 0xcc, 0xd4, 0x7e, 0x9e, 0x99, 0xda, 0xaf, 0x33, 0x53, 0xbb, 0x9c, 0x99, 0xda, 0xd5, 0xcc, + 0xd4, 0x7e, 0x9f, 0x99, 0xda, 0x1f, 0x33, 0xb3, 0xf2, 0x7a, 0x66, 0x6a, 0x3f, 0xde, 0x98, 0x95, + 0xcb, 0x1b, 0xb3, 0x72, 0x75, 0x63, 0x56, 0xbe, 0xd8, 0xe5, 0xaf, 0xb8, 0x20, 0xc1, 0x69, 0x80, + 0x43, 0xd1, 0x67, 0x54, 0x84, 0xd8, 0x11, 0x7c, 0xd4, 0x54, 0x47, 0xe7, 0x83, 0x7f, 0x02, 0x00, + 0x00, 0xff, 0xff, 0x1c, 0x53, 0x09, 0x81, 0xb7, 0x0b, 0x00, 0x00, } func (x VoteValueType) String() string { @@ -730,6 +830,70 @@ func (this *OngoingVotedList) Equal(that interface{}) bool { } return true } +func (this *OngoingVotedListV2) Equal(that interface{}) bool { + if that == nil { + return this == nil + } + + that1, ok := that.(*OngoingVotedListV2) + if !ok { + that2, ok := that.(OngoingVotedListV2) + if ok { + that1 = &that2 + } else { + return false + } + } + if that1 == nil { + return this == nil + } else if this == nil { + return false + } + if len(this.Direct) != len(that1.Direct) { + return false + } + for i := range this.Direct { + if this.Direct[i] != that1.Direct[i] { + return false + } + } + if len(this.DelegatedWithAddress) != len(that1.DelegatedWithAddress) { + return false + } + for i := range this.DelegatedWithAddress { + if !this.DelegatedWithAddress[i].Equal(that1.DelegatedWithAddress[i]) { + return false + } + } + return true +} +func (this *DelegatedWithAddress) Equal(that interface{}) bool { + if that == nil { + return this == nil + } + + that1, ok := that.(*DelegatedWithAddress) + if !ok { + that2, ok := that.(DelegatedWithAddress) + if ok { + that1 = &that2 + } else { + return false + } + } + if that1 == nil { + return this == nil + } else if this == nil { + return false + } + if this.Nonce != that1.Nonce { + return false + } + if !bytes.Equal(this.DelegatedAddress, that1.DelegatedAddress) { + return false + } + return true +} func (this *DelegatedSCVoteInfo) Equal(that interface{}) bool { if that == nil { return this == nil @@ -837,6 +1001,30 @@ func (this *OngoingVotedList) GoString() string { s = append(s, "}") return strings.Join(s, "") } +func (this *OngoingVotedListV2) GoString() string { + if this == nil { + return "nil" + } + s := make([]string, 0, 6) + s = append(s, "&systemSmartContracts.OngoingVotedListV2{") + s = append(s, "Direct: "+fmt.Sprintf("%#v", this.Direct)+",\n") + if this.DelegatedWithAddress != nil { + s = append(s, "DelegatedWithAddress: "+fmt.Sprintf("%#v", this.DelegatedWithAddress)+",\n") + } + s = append(s, "}") + return strings.Join(s, "") +} +func (this *DelegatedWithAddress) GoString() string { + if this == nil { + return "nil" + } + s := make([]string, 0, 6) + s = append(s, "&systemSmartContracts.DelegatedWithAddress{") + s = append(s, "Nonce: "+fmt.Sprintf("%#v", this.Nonce)+",\n") + s = append(s, "DelegatedAddress: "+fmt.Sprintf("%#v", this.DelegatedAddress)+",\n") + s = append(s, "}") + return strings.Join(s, "") +} func (this *DelegatedSCVoteInfo) GoString() string { if this == nil { return "nil" @@ -1177,6 +1365,96 @@ func (m *OngoingVotedList) MarshalToSizedBuffer(dAtA []byte) (int, error) { return len(dAtA) - i, nil } +func (m *OngoingVotedListV2) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *OngoingVotedListV2) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *OngoingVotedListV2) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.DelegatedWithAddress) > 0 { + for iNdEx := len(m.DelegatedWithAddress) - 1; iNdEx >= 0; iNdEx-- { + { + size, err := m.DelegatedWithAddress[iNdEx].MarshalToSizedBuffer(dAtA[:i]) + if err != nil { + return 0, err + } + i -= size + i = encodeVarintGovernance(dAtA, i, uint64(size)) + } + i-- + dAtA[i] = 0x12 + } + } + if len(m.Direct) > 0 { + dAtA6 := make([]byte, len(m.Direct)*10) + var j5 int + for _, num := range m.Direct { + for num >= 1<<7 { + dAtA6[j5] = uint8(uint64(num)&0x7f | 0x80) + num >>= 7 + j5++ + } + dAtA6[j5] = uint8(num) + j5++ + } + i -= j5 + copy(dAtA[i:], dAtA6[:j5]) + i = encodeVarintGovernance(dAtA, i, uint64(j5)) + i-- + dAtA[i] = 0xa + } + return len(dAtA) - i, nil +} + +func (m *DelegatedWithAddress) Marshal() (dAtA []byte, err error) { + size := m.Size() + dAtA = make([]byte, size) + n, err := m.MarshalToSizedBuffer(dAtA[:size]) + if err != nil { + return nil, err + } + return dAtA[:n], nil +} + +func (m *DelegatedWithAddress) MarshalTo(dAtA []byte) (int, error) { + size := m.Size() + return m.MarshalToSizedBuffer(dAtA[:size]) +} + +func (m *DelegatedWithAddress) MarshalToSizedBuffer(dAtA []byte) (int, error) { + i := len(dAtA) + _ = i + var l int + _ = l + if len(m.DelegatedAddress) > 0 { + i -= len(m.DelegatedAddress) + copy(dAtA[i:], m.DelegatedAddress) + i = encodeVarintGovernance(dAtA, i, uint64(len(m.DelegatedAddress))) + i-- + dAtA[i] = 0x12 + } + if m.Nonce != 0 { + i = encodeVarintGovernance(dAtA, i, uint64(m.Nonce)) + i-- + dAtA[i] = 0x8 + } + return len(dAtA) - i, nil +} + func (m *DelegatedSCVoteInfo) Marshal() (dAtA []byte, err error) { size := m.Size() dAtA = make([]byte, size) @@ -1397,6 +1675,44 @@ func (m *OngoingVotedList) Size() (n int) { return n } +func (m *OngoingVotedListV2) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if len(m.Direct) > 0 { + l = 0 + for _, e := range m.Direct { + l += sovGovernance(uint64(e)) + } + n += 1 + sovGovernance(uint64(l)) + l + } + if len(m.DelegatedWithAddress) > 0 { + for _, e := range m.DelegatedWithAddress { + l = e.Size() + n += 1 + l + sovGovernance(uint64(l)) + } + } + return n +} + +func (m *DelegatedWithAddress) Size() (n int) { + if m == nil { + return 0 + } + var l int + _ = l + if m.Nonce != 0 { + n += 1 + sovGovernance(uint64(m.Nonce)) + } + l = len(m.DelegatedAddress) + if l > 0 { + n += 1 + l + sovGovernance(uint64(l)) + } + return n +} + func (m *DelegatedSCVoteInfo) Size() (n int) { if m == nil { return 0 @@ -1494,6 +1810,33 @@ func (this *OngoingVotedList) String() string { }, "") return s } +func (this *OngoingVotedListV2) String() string { + if this == nil { + return "nil" + } + repeatedStringForDelegatedWithAddress := "[]*DelegatedWithAddress{" + for _, f := range this.DelegatedWithAddress { + repeatedStringForDelegatedWithAddress += strings.Replace(f.String(), "DelegatedWithAddress", "DelegatedWithAddress", 1) + "," + } + repeatedStringForDelegatedWithAddress += "}" + s := strings.Join([]string{`&OngoingVotedListV2{`, + `Direct:` + fmt.Sprintf("%v", this.Direct) + `,`, + `DelegatedWithAddress:` + repeatedStringForDelegatedWithAddress + `,`, + `}`, + }, "") + return s +} +func (this *DelegatedWithAddress) String() string { + if this == nil { + return "nil" + } + s := strings.Join([]string{`&DelegatedWithAddress{`, + `Nonce:` + fmt.Sprintf("%v", this.Nonce) + `,`, + `DelegatedAddress:` + fmt.Sprintf("%v", this.DelegatedAddress) + `,`, + `}`, + }, "") + return s +} func (this *DelegatedSCVoteInfo) String() string { if this == nil { return "nil" @@ -2514,6 +2857,275 @@ func (m *OngoingVotedList) Unmarshal(dAtA []byte) error { } return nil } +func (m *OngoingVotedListV2) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGovernance + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: OngoingVotedListV2: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: OngoingVotedListV2: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType == 0 { + var v uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGovernance + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + v |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + m.Direct = append(m.Direct, v) + } else if wireType == 2 { + var packedLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGovernance + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + packedLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if packedLen < 0 { + return ErrInvalidLengthGovernance + } + postIndex := iNdEx + packedLen + if postIndex < 0 { + return ErrInvalidLengthGovernance + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + var elementCount int + var count int + for _, integer := range dAtA[iNdEx:postIndex] { + if integer < 128 { + count++ + } + } + elementCount = count + if elementCount != 0 && len(m.Direct) == 0 { + m.Direct = make([]uint64, 0, elementCount) + } + for iNdEx < postIndex { + var v uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGovernance + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + v |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + m.Direct = append(m.Direct, v) + } + } else { + return fmt.Errorf("proto: wrong wireType = %d for field Direct", wireType) + } + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field DelegatedWithAddress", wireType) + } + var msglen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGovernance + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + msglen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if msglen < 0 { + return ErrInvalidLengthGovernance + } + postIndex := iNdEx + msglen + if postIndex < 0 { + return ErrInvalidLengthGovernance + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.DelegatedWithAddress = append(m.DelegatedWithAddress, &DelegatedWithAddress{}) + if err := m.DelegatedWithAddress[len(m.DelegatedWithAddress)-1].Unmarshal(dAtA[iNdEx:postIndex]); err != nil { + return err + } + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipGovernance(dAtA[iNdEx:]) + if err != nil { + return err + } + if skippy < 0 { + return ErrInvalidLengthGovernance + } + if (iNdEx + skippy) < 0 { + return ErrInvalidLengthGovernance + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} +func (m *DelegatedWithAddress) Unmarshal(dAtA []byte) error { + l := len(dAtA) + iNdEx := 0 + for iNdEx < l { + preIndex := iNdEx + var wire uint64 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGovernance + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + wire |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + fieldNum := int32(wire >> 3) + wireType := int(wire & 0x7) + if wireType == 4 { + return fmt.Errorf("proto: DelegatedWithAddress: wiretype end group for non-group") + } + if fieldNum <= 0 { + return fmt.Errorf("proto: DelegatedWithAddress: illegal tag %d (wire type %d)", fieldNum, wire) + } + switch fieldNum { + case 1: + if wireType != 0 { + return fmt.Errorf("proto: wrong wireType = %d for field Nonce", wireType) + } + m.Nonce = 0 + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGovernance + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + m.Nonce |= uint64(b&0x7F) << shift + if b < 0x80 { + break + } + } + case 2: + if wireType != 2 { + return fmt.Errorf("proto: wrong wireType = %d for field DelegatedAddress", wireType) + } + var byteLen int + for shift := uint(0); ; shift += 7 { + if shift >= 64 { + return ErrIntOverflowGovernance + } + if iNdEx >= l { + return io.ErrUnexpectedEOF + } + b := dAtA[iNdEx] + iNdEx++ + byteLen |= int(b&0x7F) << shift + if b < 0x80 { + break + } + } + if byteLen < 0 { + return ErrInvalidLengthGovernance + } + postIndex := iNdEx + byteLen + if postIndex < 0 { + return ErrInvalidLengthGovernance + } + if postIndex > l { + return io.ErrUnexpectedEOF + } + m.DelegatedAddress = append(m.DelegatedAddress[:0], dAtA[iNdEx:postIndex]...) + if m.DelegatedAddress == nil { + m.DelegatedAddress = []byte{} + } + iNdEx = postIndex + default: + iNdEx = preIndex + skippy, err := skipGovernance(dAtA[iNdEx:]) + if err != nil { + return err + } + if skippy < 0 { + return ErrInvalidLengthGovernance + } + if (iNdEx + skippy) < 0 { + return ErrInvalidLengthGovernance + } + if (iNdEx + skippy) > l { + return io.ErrUnexpectedEOF + } + iNdEx += skippy + } + } + + if iNdEx > l { + return io.ErrUnexpectedEOF + } + return nil +} func (m *DelegatedSCVoteInfo) Unmarshal(dAtA []byte) error { l := len(dAtA) iNdEx := 0 diff --git a/vm/systemSmartContracts/governance.proto b/vm/systemSmartContracts/governance.proto index 019a0755eae..ba245d0f7d4 100644 --- a/vm/systemSmartContracts/governance.proto +++ b/vm/systemSmartContracts/governance.proto @@ -52,6 +52,16 @@ message OngoingVotedList { repeated uint64 Delegated = 2 [(gogoproto.jsontag) = "Delegated"]; } +message OngoingVotedListV2 { + repeated uint64 Direct = 1 [(gogoproto.jsontag) = "Direct"]; + repeated DelegatedWithAddress DelegatedWithAddress = 2 [(gogoproto.jsontag) = "DelegatedWithAddress"]; +} + +message DelegatedWithAddress { + uint64 Nonce = 1; + bytes DelegatedAddress = 2 [(gogoproto.jsontag) = "DelegatedAddress"]; +} + message DelegatedSCVoteInfo { bytes TotalPower = 1 [(gogoproto.jsontag) = "TotalPower", (gogoproto.casttypewith) = "math/big.Int;github.com/multiversx/mx-chain-core-go/data.BigIntCaster"]; bytes UsedPower = 2 [(gogoproto.jsontag) = "UsedPower", (gogoproto.casttypewith) = "math/big.Int;github.com/multiversx/mx-chain-core-go/data.BigIntCaster"]; diff --git a/vm/systemSmartContracts/governance_test.go b/vm/systemSmartContracts/governance_test.go index e451d090f70..00c19b79903 100644 --- a/vm/systemSmartContracts/governance_test.go +++ b/vm/systemSmartContracts/governance_test.go @@ -270,6 +270,19 @@ func TestGovernanceContract_ExecuteInit(t *testing.T) { require.Equal(t, vmcommon.Ok, retCode) } +func TestGovernanceContract_ExecuteSendESDT(t *testing.T) { + t.Parallel() + + gsc, _, eei := createGovernanceBlockChainHookStubContextHandler() + + callerAddr := []byte("addr1") + callInput := createVMInput(big.NewInt(0), "vote", callerAddr, vm.GovernanceSCAddress, nil) + callInput.ESDTTransfers = []*vmcommon.ESDTTransfer{{ESDTValue: big.NewInt(10), ESDTTokenName: []byte("tokenName"), ESDTTokenType: 0, ESDTTokenNonce: 0}} + retCode := gsc.Execute(callInput) + require.Equal(t, vmcommon.UserError, retCode) + require.True(t, strings.Contains(eei.GetReturnMessage(), "cannot transfer ESDT to system SCs")) +} + func TestGovernanceContract_ExecuteInitV2InvalidCaller(t *testing.T) { t.Parallel() @@ -827,6 +840,104 @@ func TestGovernanceContract_VoteTwice(t *testing.T) { require.Equal(t, eei.GetReturnMessage(), "double vote is not allowed") } +func TestGovernanceContract_VoteTwiceV2(t *testing.T) { + t.Parallel() + + gsc, blockchainHook, eei := createGovernanceBlockChainHookStubContextHandler() + gsc.enableEpochsHandler = enableEpochsHandlerMock.NewEnableEpochsHandlerStub(common.GovernanceFlag, common.GovernanceDisableProposeFlag, common.GovernanceFixesFlag) + blockchainHook.CurrentEpochCalled = func() uint32 { + return 12 + } + + callerAddress := bytes.Repeat([]byte{2}, 32) + proposalIdentifier := []byte("aaaaaaaaa") + generalProposal := &GeneralProposal{ + ProposalCost: gsc.baseProposalCost, + CommitHash: proposalIdentifier, + StartVoteEpoch: 10, + EndVoteEpoch: 15, + Yes: big.NewInt(0), + No: big.NewInt(0), + Veto: big.NewInt(0), + Abstain: big.NewInt(0), + QuorumStake: big.NewInt(0), + } + + voteArgs := [][]byte{ + []byte("1"), + []byte("yes"), + } + + gsc.eei.SetStorage(append([]byte(noncePrefix), voteArgs[0]...), proposalIdentifier) + _ = gsc.saveGeneralProposal(proposalIdentifier, generalProposal) + + callInput := createVMInput(big.NewInt(0), "vote", callerAddress, vm.GovernanceSCAddress, voteArgs) + retCode := gsc.Execute(callInput) + require.Equal(t, vmcommon.Ok, retCode) + + voteArgs[1] = []byte("no") + retCode = gsc.Execute(callInput) + require.Equal(t, vmcommon.UserError, retCode) + require.Equal(t, eei.GetReturnMessage(), "double vote is not allowed") +} + +func TestGovernanceContract_VoteAfterGovernanceFixesActivationWithOngoingListV1(t *testing.T) { + t.Parallel() + + gsc, blockchainHook, _ := createGovernanceBlockChainHookStubContextHandler() + blockchainHook.CurrentEpochCalled = func() uint32 { + return 12 + } + + delegatedAddress := bytes.Repeat([]byte{2}, 32) + proposalIdentifier := []byte("aaaaaaaaa") + generalProposal := &GeneralProposal{ + ProposalCost: gsc.baseProposalCost, + CommitHash: proposalIdentifier, + StartVoteEpoch: 10, + EndVoteEpoch: 15, + Yes: big.NewInt(0), + No: big.NewInt(0), + Veto: big.NewInt(0), + Abstain: big.NewInt(0), + QuorumStake: big.NewInt(0), + } + + voteArgs := [][]byte{ + []byte("1"), + []byte("yes"), + } + delegateVoteArgs := [][]byte{ + []byte("1"), + []byte("yes"), + delegatedAddress, + big.NewInt(30).Bytes(), + } + + gsc.eei.SetStorage(append([]byte(noncePrefix), delegateVoteArgs[0]...), proposalIdentifier) + _ = gsc.saveGeneralProposal(proposalIdentifier, generalProposal) + + callInput := createVMInput(big.NewInt(0), "delegateVote", vm.ESDTSCAddress, vm.GovernanceSCAddress, delegateVoteArgs) + addStakeAndDelegationForAddress(gsc, callInput.CallerAddr) + retCode := gsc.Execute(callInput) + require.Equal(t, vmcommon.Ok, retCode) + + callInput = createVMInput(big.NewInt(0), "vote", delegatedAddress, vm.GovernanceSCAddress, voteArgs) + retCode = gsc.Execute(callInput) + require.Equal(t, vmcommon.Ok, retCode) + + delegateVoteArgs[0] = []byte("2") + generalProposal.CommitHash = []byte("bbbbbbbbb") + + gsc.eei.SetStorage(append([]byte(noncePrefix), delegateVoteArgs[0]...), proposalIdentifier) + _ = gsc.saveGeneralProposal(proposalIdentifier, generalProposal) + callInput = createVMInput(big.NewInt(0), "delegateVote", vm.ESDTSCAddress, vm.GovernanceSCAddress, delegateVoteArgs) + + gsc.enableEpochsHandler = enableEpochsHandlerMock.NewEnableEpochsHandlerStub(common.GovernanceFlag, common.GovernanceDisableProposeFlag, common.GovernanceFixesFlag) + retCode = gsc.Execute(callInput) + require.Equal(t, vmcommon.Ok, retCode) +} + func TestGovernanceContract_DelegateVoteUserErrors(t *testing.T) { t.Parallel() @@ -934,6 +1045,83 @@ func TestGovernanceContract_DelegateVoteMoreErrors(t *testing.T) { retCode = gsc.Execute(callInput) require.Equal(t, vmcommon.UserError, retCode) require.True(t, strings.Contains(eei.GetReturnMessage(), "double vote is not allowed")) + + addStakeAndDelegationForAddress(gsc, vm.FirstDelegationSCAddress) + callInput.CallerAddr = vm.FirstDelegationSCAddress + retCode = gsc.Execute(callInput) + require.Equal(t, vmcommon.UserError, retCode) + require.True(t, strings.Contains(eei.GetReturnMessage(), "double vote is not allowed")) +} + +func TestGovernanceContract_ProposalDuringDisableFlag(t *testing.T) { + t.Parallel() + + gsc, _, eei := createGovernanceBlockChainHookStubContextHandler() + gsc.enableEpochsHandler = enableEpochsHandlerMock.NewEnableEpochsHandlerStub(common.GovernanceFlag, common.GovernanceDisableProposeFlag) + proposalIdentifier := bytes.Repeat([]byte("a"), commitHashLength) + + callInputArgs := [][]byte{ + proposalIdentifier, + []byte("50"), + []byte("55"), + } + callInput := createVMInput(big.NewInt(500), "proposal", vm.GovernanceSCAddress, []byte("addr1"), callInputArgs) + retCode := gsc.Execute(callInput) + + require.True(t, strings.Contains(eei.GetReturnMessage(), "proposing is disabled")) + require.Equal(t, vmcommon.UserError, retCode) + + gsc.enableEpochsHandler = enableEpochsHandlerMock.NewEnableEpochsHandlerStub(common.GovernanceFlag, common.GovernanceDisableProposeFlag, common.GovernanceFixesFlag) + retCode = gsc.Execute(callInput) + require.Equal(t, vmcommon.Ok, retCode) +} + +func TestGovernanceContract_DelegateVoteMultiple(t *testing.T) { + t.Parallel() + + gsc, blockchainHook, eei := createGovernanceBlockChainHookStubContextHandler() + gsc.enableEpochsHandler = enableEpochsHandlerMock.NewEnableEpochsHandlerStub(common.GovernanceFlag, common.GovernanceFixesFlag) + blockchainHook.CurrentEpochCalled = func() uint32 { + return 12 + } + + voter := bytes.Repeat([]byte{2}, 32) + proposalIdentifier := []byte("aaaaaaaaa") + generalProposal := &GeneralProposal{ + ProposalCost: gsc.baseProposalCost, + CommitHash: proposalIdentifier, + StartVoteEpoch: 10, + EndVoteEpoch: 15, + Yes: big.NewInt(0), + No: big.NewInt(0), + Veto: big.NewInt(0), + Abstain: big.NewInt(0), + QuorumStake: big.NewInt(0), + } + + voteArgs := [][]byte{ + []byte("1"), + []byte("yes"), + voter, + big.NewInt(12).Bytes(), + } + + gsc.eei.SetStorage(append([]byte(noncePrefix), voteArgs[0]...), proposalIdentifier) + _ = gsc.saveGeneralProposal(proposalIdentifier, generalProposal) + + addStakeAndDelegationForAddress(gsc, vm.ESDTSCAddress) + addStakeAndDelegationForAddress(gsc, vm.FirstDelegationSCAddress) + callInput := createVMInput(big.NewInt(0), "delegateVote", vm.ESDTSCAddress, vm.GovernanceSCAddress, voteArgs) + retCode := gsc.Execute(callInput) + require.Equal(t, vmcommon.Ok, retCode) + + retCode = gsc.Execute(callInput) + require.Equal(t, vmcommon.UserError, retCode) + require.True(t, strings.Contains(eei.GetReturnMessage(), "double vote is not allowed")) + + callInput.CallerAddr = vm.FirstDelegationSCAddress + retCode = gsc.Execute(callInput) + require.Equal(t, vmcommon.Ok, retCode) } func TestGovernanceContract_CloseProposal(t *testing.T) { @@ -1448,68 +1636,6 @@ func TestGovernanceContract_ViewConfig(t *testing.T) { require.Equal(t, vmcommon.Ok, retCode) } -func TestGovernanceContract_ViewUserHistory(t *testing.T) { - t.Parallel() - - callerAddress := []byte("address") - args := createMockGovernanceArgs() - returnMessage := "" - finishedMessages := make([][]byte, 0) - mockEEI := &mock.SystemEIStub{ - GetStorageFromAddressCalled: func(_ []byte, _ []byte) []byte { - return []byte("invalid data") - }, - AddReturnMessageCalled: func(msg string) { - returnMessage = msg - }, - FinishCalled: func(value []byte) { - finishedMessages = append(finishedMessages, value) - }, - } - args.Eei = mockEEI - - gsc, _ := NewGovernanceContract(args) - callInputArgs := [][]byte{ - callerAddress, - } - callInput := createVMInput(zero, "viewUserVoteHistory", callerAddress, vm.GovernanceSCAddress, callInputArgs) - retCode := gsc.Execute(callInput) - require.Equal(t, vmcommon.UserError, retCode) - require.Equal(t, returnMessage, vm.ErrInvalidCaller.Error()) - - callInput.CallerAddr = callInput.RecipientAddr - callInput.Arguments = [][]byte{callerAddress} - retCode = gsc.Execute(callInput) - require.Equal(t, vmcommon.Ok, retCode) - expectedMessaged := [][]byte{ - {0}, // 0 delegated values - {0}, // 0 direct values - } - assert.Equal(t, expectedMessaged, finishedMessages) - - mockEEI.GetStorageCalled = func(key []byte) []byte { - proposalBytes, _ := args.Marshalizer.Marshal(&OngoingVotedList{ - Delegated: []uint64{1, 2}, - Direct: []uint64{3, 4, 5}, - }) - return proposalBytes - } - - finishedMessages = make([][]byte, 0) - retCode = gsc.Execute(callInput) - require.Equal(t, vmcommon.Ok, retCode) - expectedMessaged = [][]byte{ - {2}, // 2 delegated values - {1}, - {2}, - {3}, // 3 direct values - {3}, - {4}, - {5}, - } - assert.Equal(t, expectedMessaged, finishedMessages) -} - func TestGovernanceContract_ViewProposal(t *testing.T) { t.Parallel()