github.com/klaytn/klaytn@v1.12.1/governance/default_test.go (about)

     1  // Copyright 2019 The klaytn Authors
     2  // This file is part of the klaytn library.
     3  //
     4  // The klaytn library is free software: you can redistribute it and/or modify
     5  // it under the terms of the GNU Lesser General Public License as published by
     6  // the Free Software Foundation, either version 3 of the License, or
     7  // (at your option) any later version.
     8  //
     9  // The klaytn library is distributed in the hope that it will be useful,
    10  // but WITHOUT ANY WARRANTY; without even the implied warranty of
    11  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
    12  // GNU Lesser General Public License for more details.
    13  //
    14  // You should have received a copy of the GNU Lesser General Public License
    15  // along with the klaytn library. If not, see <http://www.gnu.org/licenses/>.
    16  
    17  package governance
    18  
    19  import (
    20  	"encoding/json"
    21  	"fmt"
    22  	"math/big"
    23  	"reflect"
    24  	"testing"
    25  
    26  	gotest_assert "gotest.tools/assert"
    27  
    28  	"github.com/klaytn/klaytn/blockchain"
    29  	"github.com/klaytn/klaytn/blockchain/types"
    30  	"github.com/klaytn/klaytn/common"
    31  	"github.com/klaytn/klaytn/consensus/istanbul"
    32  	"github.com/klaytn/klaytn/consensus/istanbul/validator"
    33  	"github.com/klaytn/klaytn/params"
    34  	"github.com/klaytn/klaytn/rlp"
    35  	"github.com/klaytn/klaytn/storage/database"
    36  	"github.com/stretchr/testify/assert"
    37  )
    38  
    39  type voteValue struct {
    40  	k string
    41  	v interface{}
    42  	e bool
    43  }
    44  
    45  var tstData = []voteValue{
    46  	{k: "istanbul.epoch", v: uint64(30000), e: true},
    47  	{k: "istanbul.epoch", v: "bad", e: false},
    48  	{k: "istanbul.epoch", v: float64(30000.00), e: true},
    49  	{k: "istanbul.Epoch", v: float64(30000.10), e: false},
    50  	{k: "istanbul.epoch", v: true, e: false},
    51  	{k: "istanbul.committeesize", v: uint64(7), e: true},
    52  	{k: "istanbul.committeesize", v: float64(7.0), e: true},
    53  	{k: "istanbul.committeesize", v: float64(7.1), e: false},
    54  	{k: "istanbul.committeesize", v: "7", e: false},
    55  	{k: "istanbul.committeesize", v: true, e: false},
    56  	{k: "istanbul.committeesize", v: float64(-7), e: false},
    57  	{k: "istanbul.committeesize", v: uint64(0), e: false},
    58  	{k: "istanbul.policy", v: "roundrobin", e: false},
    59  	{k: "istanbul.policy", v: "RoundRobin", e: false},
    60  	{k: "istanbul.policy", v: "sticky", e: false},
    61  	{k: "istanbul.policy", v: "weightedrandom", e: false},
    62  	{k: "istanbul.policy", v: "WeightedRandom", e: false},
    63  	{k: "istanbul.policy", v: uint64(0), e: false},
    64  	{k: "istanbul.policy", v: uint64(1), e: false},
    65  	{k: "istanbul.policy", v: uint64(2), e: false},
    66  	{k: "istanbul.policy", v: float64(1.2), e: false},
    67  	{k: "istanbul.policy", v: float64(1.0), e: false},
    68  	{k: "istanbul.policy", v: true, e: false},
    69  	{k: "governance.governancemode", v: "none", e: true},
    70  	{k: "governance.governancemode", v: "single", e: true},
    71  	{k: "governance.governancemode", v: "ballot", e: true},
    72  	{k: "governance.governancemode", v: 0, e: false},
    73  	{k: "governance.governancemode", v: 1, e: false},
    74  	{k: "governance.governancemode", v: 2, e: false},
    75  	{k: "governance.governancemode", v: "unexpected", e: false},
    76  	{k: "governance.governingnode", v: "0x00000000000000000000", e: false},
    77  	{k: "governance.governingnode", v: "0x0000000000000000000000000000000000000000", e: true},
    78  	{k: "governance.governingnode", v: "0x000000000000000000000000000abcd000000000", e: true},
    79  	{k: "governance.governingnode", v: "000000000000000000000000000abcd000000000", e: true},
    80  	{k: "governance.governingnode", v: common.HexToAddress("000000000000000000000000000abcd000000000"), e: true},
    81  	{k: "governance.governingnode", v: "0x000000000000000000000000000xxxx000000000", e: false},
    82  	{k: "governance.governingnode", v: "address", e: false},
    83  	{k: "governance.governingnode", v: 0, e: false},
    84  	{k: "governance.governingnode", v: true, e: false},
    85  	{k: "governance.govparamcontract", v: "0x00000000000000000000", e: false},
    86  	{k: "governance.govparamcontract", v: "0x0000000000000000000000000000000000000000", e: true},
    87  	{k: "governance.govparamcontract", v: "0x000000000000000000000000000abcd000000000", e: true},
    88  	{k: "governance.govparamcontract", v: "000000000000000000000000000abcd000000000", e: true},
    89  	{k: "governance.govparamcontract", v: common.HexToAddress("000000000000000000000000000abcd000000000"), e: true},
    90  	{k: "governance.govparamcontract", v: "0x000000000000000000000000000xxxx000000000", e: false},
    91  	{k: "governance.govparamcontract", v: "address", e: false},
    92  	{k: "governance.govparamcontract", v: 0, e: false},
    93  	{k: "governance.govparamcontract", v: true, e: false},
    94  	{k: "governance.unitprice", v: float64(0.0), e: true},
    95  	{k: "governance.unitprice", v: float64(0.1), e: false},
    96  	{k: "governance.unitprice", v: uint64(25000000000), e: true},
    97  	{k: "governance.unitprice", v: float64(-10), e: false},
    98  	{k: "governance.unitprice", v: "25000000000", e: false},
    99  	{k: "governance.unitprice", v: true, e: false},
   100  	{k: "governance.deriveshaimpl", v: float64(0.0), e: true},
   101  	{k: "governance.deriveshaimpl", v: float64(0.1), e: false},
   102  	{k: "governance.deriveshaimpl", v: uint64(2), e: true},
   103  	{k: "governance.deriveshaimpl", v: float64(-1), e: false},
   104  	{k: "governance.deriveshaimpl", v: "2", e: false},
   105  	{k: "governance.deriveshaimpl", v: true, e: false},
   106  	{k: "reward.useginicoeff", v: false, e: true},
   107  	{k: "reward.useginicoeff", v: true, e: true},
   108  	{k: "reward.useginicoeff", v: "true", e: false},
   109  	{k: "reward.useginicoeff", v: 0, e: false},
   110  	{k: "reward.useginicoeff", v: 1, e: false},
   111  	{k: "reward.mintingamount", v: "9600000000000000000", e: true},
   112  	{k: "reward.mintingamount", v: "0", e: true},
   113  	{k: "reward.mintingamount", v: 96000, e: false},
   114  	{k: "reward.mintingamount", v: "many", e: false},
   115  	{k: "reward.mintingamount", v: true, e: false},
   116  	{k: "reward.ratio", v: "30/40/30", e: true},
   117  	{k: "reward.ratio", v: "10/10/80", e: true},
   118  	{k: "reward.ratio", v: "30/70", e: false},
   119  	{k: "reward.ratio", v: "30/40/31", e: false},
   120  	{k: "reward.ratio", v: "30/40/29", e: false},
   121  	{k: "reward.ratio", v: 30 / 40 / 30, e: false},
   122  	{k: "reward.ratio", v: "0/0/100", e: true},
   123  	{k: "reward.ratio", v: "0/100/0", e: true},
   124  	{k: "reward.ratio", v: "100/0/0", e: true},
   125  	{k: "reward.ratio", v: "0/0/0", e: false},
   126  	{k: "reward.ratio", v: "30.5/40/29.5", e: false},
   127  	{k: "reward.ratio", v: "30.5/40/30.5", e: false},
   128  	{k: "reward.kip82ratio", v: "20/80", e: true},
   129  	{k: "reward.kip82ratio", v: "10/90", e: true},
   130  	{k: "reward.kip82ratio", v: "30/80", e: false},
   131  	{k: "reward.kip82ratio", v: "30/30/40", e: false},
   132  	{k: "reward.kip82ratio", v: "49.5/50.5", e: false},
   133  	{k: "reward.kip82ratio", v: "50.5/50.5", e: false},
   134  	{k: "kip71.lowerboundbasefee", v: uint64(25000000000), e: true},
   135  	{k: "kip71.lowerboundbasefee", v: 25000000, e: false},
   136  	{k: "kip71.lowerboundbasefee", v: "250000000", e: false},
   137  	{k: "kip71.lowerboundbasefee", v: true, e: false},
   138  	{k: "kip71.lowerboundbasefee", v: "test", e: false},
   139  	{k: "kip71.upperboundbasefee", v: uint64(750000000000), e: true},
   140  	{k: "kip71.upperboundbasefee", v: 7500000, e: false},
   141  	{k: "kip71.upperboundbasefee", v: "750000", e: false},
   142  	{k: "kip71.upperboundbasefee", v: true, e: false},
   143  	{k: "kip71.upperboundbasefee", v: false, e: false},
   144  	{k: "kip71.gastarget", v: uint64(30000000), e: true},
   145  	{k: "kip71.gastarget", v: 3000, e: false},
   146  	{k: "kip71.gastarget", v: "30000", e: false},
   147  	{k: "kip71.gastarget", v: true, e: false},
   148  	{k: "kip71.gastarget", v: false, e: false},
   149  	{k: "kip71.maxblockgasusedforbasefee", v: uint64(84000000), e: true},
   150  	{k: "kip71.maxblockgasusedforbasefee", v: 840000, e: false},
   151  	{k: "kip71.maxblockgasusedforbasefee", v: true, e: false},
   152  	{k: "kip71.maxblockgasusedforbasefee", v: "84000", e: false},
   153  	{k: "kip71.maxblockgasusedforbasefee", v: 0, e: false},
   154  	{k: "kip71.basefeedenominator", v: uint64(64), e: true},
   155  	{k: "kip71.basefeedenominator", v: 64, e: false},
   156  	{k: "kip71.basefeedenominator", v: "64", e: false},
   157  	{k: "kip71.basefeedenominator", v: "sixtyfour", e: false},
   158  	{k: "kip71.basefeedenominator", v: true, e: false},
   159  	{k: "reward.deferredtxfee", v: true, e: true},
   160  	{k: "reward.deferredtxfee", v: false, e: true},
   161  	{k: "reward.deferredtxfee", v: 0, e: false},
   162  	{k: "reward.deferredtxfee", v: 1, e: false},
   163  	{k: "reward.deferredtxfee", v: "true", e: false},
   164  	{k: "reward.minimumstake", v: "2000000000000000000000000", e: true},
   165  	{k: "reward.minimumstake", v: 200000000000000, e: false},
   166  	{k: "reward.minimumstake", v: "-1", e: false},
   167  	{k: "reward.minimumstake", v: "0", e: true},
   168  	{k: "reward.minimumstake", v: 0, e: false},
   169  	{k: "reward.minimumstake", v: 1.1, e: false},
   170  	{k: "reward.stakingupdateinterval", v: uint64(20), e: false},
   171  	{k: "reward.stakingupdateinterval", v: float64(20.0), e: false},
   172  	{k: "reward.stakingupdateinterval", v: float64(20.2), e: false},
   173  	{k: "reward.stakingupdateinterval", v: "20", e: false},
   174  	{k: "reward.proposerupdateinterval", v: uint64(20), e: false},
   175  	{k: "reward.proposerupdateinterval", v: float64(20.0), e: false},
   176  	{k: "reward.proposerupdateinterval", v: float64(20.2), e: false},
   177  	{k: "reward.proposerupdateinterval", v: "20", e: false},
   178  	{k: "istanbul.timeout", v: uint64(10000), e: true},
   179  	{k: "istanbul.timeout", v: uint64(5000), e: true},
   180  	{k: "istanbul.timeout", v: float64(-1000), e: false},
   181  	{k: "istanbul.timeout", v: true, e: false},
   182  	{k: "istanbul.timeout", v: "10", e: false},
   183  	{k: "istanbul.timeout", v: 5.3, e: false},
   184  	{k: "governance.addvalidator", v: "0x639e5ebfc483716fbac9810b230ff6ad487f366c", e: true},
   185  	{k: "governance.addvalidator", v: " 0x639e5ebfc483716fbac9810b230ff6ad487f366c ", e: true},
   186  	{k: "governance.addvalidator", v: "0x639e5ebfc483716fbac9810b230ff6ad487f366c,0x828880c5f09cc1cc6a58715e3fe2b4c4cf3c5869", e: true},
   187  	{k: "governance.addvalidator", v: "0x639e5ebfc483716fbac9810b230ff6ad487f366c,0x828880c5f09cc1cc6a58715e3fe2b4c4cf3c58", e: false},
   188  	{k: "governance.addvalidator", v: "0x639e5ebfc483716fbac9810b230ff6ad487f366c,0x639e5ebfc483716fbac9810b230ff6ad487f366c", e: false},
   189  	{k: "governance.addvalidator", v: "0x639e5ebfc483716fbac9810b230ff6ad487f366c, 0x828880c5f09cc1cc6a58715e3fe2b4c4cf3c5869, ", e: false},
   190  	{k: "governance.addvalidator", v: "0x639e5ebfc483716fbac9810b230ff6ad487f366c,, 0x828880c5f09cc1cc6a58715e3fe2b4c4cf3c5869, ", e: false},
   191  	{k: "governance.addvalidator", v: "0x639e5ebfc483716fbac9810b230ff6ad487f366c, 0x828880c5f09cc1cc6a58715e3fe2b4c4cf3c5869 ", e: true},
   192  }
   193  
   194  var goodVotes = []voteValue{
   195  	{k: "istanbul.epoch", v: uint64(20000), e: true},
   196  	{k: "istanbul.committeesize", v: uint64(7), e: true},
   197  	{k: "governance.governancemode", v: "single", e: true},
   198  	{k: "governance.governingnode", v: common.HexToAddress("0x0000000000000000000000000000000000000000"), e: true},
   199  	{k: "governance.unitprice", v: uint64(25000000000), e: true},
   200  	{k: "governance.deriveshaimpl", v: uint64(0), e: true},
   201  	{k: "kip71.lowerboundbasefee", v: uint64(25000000000), e: true},
   202  	{k: "kip71.upperboundbasefee", v: uint64(750000000000), e: true},
   203  	{k: "kip71.gastarget", v: uint64(30000000), e: true},
   204  	{k: "kip71.maxblockgasusedforbasefee", v: uint64(84000000), e: true},
   205  	{k: "kip71.basefeedenominator", v: uint64(64), e: true},
   206  	{k: "reward.useginicoeff", v: false, e: true},
   207  	{k: "reward.mintingamount", v: "9600000000000000000", e: true},
   208  	{k: "reward.ratio", v: "10/10/80", e: true},
   209  	{k: "reward.kip82ratio", v: "20/80", e: true},
   210  	{k: "istanbul.timeout", v: uint64(5000), e: true},
   211  	{k: "governance.addvalidator", v: "0x639e5ebfc483716fbac9810b230ff6ad487f366c,0x828880c5f09cc1cc6a58715e3fe2b4c4cf3c5869", e: true},
   212  }
   213  
   214  func getTestConfig() *params.ChainConfig {
   215  	config := params.TestChainConfig.Copy()
   216  	config.Governance = params.GetDefaultGovernanceConfig()
   217  	config.Istanbul = params.GetDefaultIstanbulConfig()
   218  	return config
   219  }
   220  
   221  func getGovernance() *Governance {
   222  	dbm := database.NewDBManager(&database.DBConfig{DBType: database.MemoryDB})
   223  	config := getTestConfig()
   224  	return NewGovernanceInitialize(config, dbm)
   225  }
   226  
   227  func TestGetDefaultGovernanceConfig(t *testing.T) {
   228  	tstGovernance := params.GetDefaultGovernanceConfig()
   229  
   230  	want := []interface{}{
   231  		params.DefaultUseGiniCoeff,
   232  		params.DefaultRatio,
   233  		common.HexToAddress(params.DefaultGoverningNode),
   234  		params.DefaultGovernanceMode,
   235  		params.DefaultDeferredTxFee,
   236  	}
   237  
   238  	got := []interface{}{
   239  		tstGovernance.Reward.UseGiniCoeff,
   240  		tstGovernance.Reward.Ratio,
   241  		tstGovernance.GoverningNode,
   242  		tstGovernance.GovernanceMode,
   243  		tstGovernance.DeferredTxFee(),
   244  	}
   245  
   246  	if !reflect.DeepEqual(want, got) {
   247  		t.Fatalf("Want %v, got %v", want, got)
   248  	}
   249  
   250  	if tstGovernance.Reward.MintingAmount.Cmp(params.DefaultMintingAmount) != 0 {
   251  		t.Errorf("Default minting amount is not equal")
   252  	}
   253  }
   254  
   255  func TestGovernance_ValidateVote(t *testing.T) {
   256  	gov := getGovernance()
   257  
   258  	for _, val := range tstData {
   259  		vote := &GovernanceVote{
   260  			Key:   val.k,
   261  			Value: val.v,
   262  		}
   263  		_, ret := gov.ValidateVote(vote)
   264  		if ret != val.e {
   265  			if _, ok := GovernanceForbiddenKeyMap[val.k]; !ok && !ret {
   266  				t.Errorf("Want %v, got %v for %v and %v", val.e, ret, val.k, val.v)
   267  			}
   268  		}
   269  	}
   270  }
   271  
   272  func TestGovernance_AddVote(t *testing.T) {
   273  	gov := getGovernance()
   274  
   275  	for _, val := range tstData {
   276  		ret := gov.AddVote(val.k, val.v)
   277  		assert.Equal(t, val.e, ret, fmt.Sprintf("key %v, value %v", val.k, val.v))
   278  	}
   279  }
   280  
   281  func TestGovernance_RemoveVote(t *testing.T) {
   282  	gov := getGovernance()
   283  
   284  	for _, val := range goodVotes {
   285  		ret := gov.AddVote(val.k, val.v)
   286  		if ret != val.e {
   287  			t.Errorf("Want %v, got %v for %v and %v", val.e, ret, val.k, val.v)
   288  		}
   289  	}
   290  
   291  	// Length check. Because []votes has all valid votes, length of voteMap and votes should be equal
   292  	if countUncastedVote(gov.voteMap) != len(goodVotes) {
   293  		t.Errorf("Length of voteMap should be %d, but %d\n", len(goodVotes), gov.voteMap.Size())
   294  	}
   295  
   296  	// Remove unvoted vote. Length should still be same
   297  	gov.RemoveVote("istanbul.Epoch", uint64(10000), 0)
   298  	if countUncastedVote(gov.voteMap) != len(goodVotes) {
   299  		t.Errorf("Length of voteMap should be %d, but %d\n", len(goodVotes), gov.voteMap.Size())
   300  	}
   301  
   302  	// Remove vote with wrong key. Length should still be same
   303  	gov.RemoveVote("istanbul.EpochEpoch", uint64(10000), 0)
   304  	if countUncastedVote(gov.voteMap) != len(goodVotes) {
   305  		t.Errorf("Length of voteMap should be %d, but %d\n", len(goodVotes), gov.voteMap.Size())
   306  	}
   307  
   308  	// Removed a vote. Length should be len(goodVotes) -1
   309  	gov.RemoveVote("istanbul.epoch", uint64(20000), 0)
   310  	if countUncastedVote(gov.voteMap) != (len(goodVotes) - 1) {
   311  		t.Errorf("Length of voteMap should be %d, but %d\n", len(goodVotes)-1, gov.voteMap.Size())
   312  	}
   313  }
   314  
   315  func countUncastedVote(data VoteMap) int {
   316  	size := 0
   317  
   318  	for _, v := range data.Copy() {
   319  		if v.Casted == false {
   320  			size++
   321  		}
   322  	}
   323  	return size
   324  }
   325  
   326  func TestGovernance_ClearVotes(t *testing.T) {
   327  	gov := getGovernance()
   328  
   329  	for _, val := range tstData {
   330  		ret := gov.AddVote(val.k, val.v)
   331  		if ret != val.e {
   332  			t.Errorf("Want %v, got %v for %v and %v", val.e, ret, val.k, val.v)
   333  		}
   334  		avt := gov.adjustValueType(val.k, val.v)
   335  		gov.RemoveVote(val.k, avt, 0)
   336  	}
   337  	gov.ClearVotes(0)
   338  	if gov.voteMap.Size() != 0 {
   339  		t.Errorf("Want 0, got %v after clearing votes", gov.voteMap.Size())
   340  	}
   341  }
   342  
   343  func TestGovernance_GetEncodedVote(t *testing.T) {
   344  	gov := getGovernance()
   345  
   346  	for _, val := range goodVotes {
   347  		_ = gov.AddVote(val.k, val.v)
   348  	}
   349  
   350  	l := gov.voteMap.Size()
   351  	for i := 0; i < l; i++ {
   352  		voteData := gov.GetEncodedVote(common.HexToAddress("0x1234567890123456789012345678901234567890"), 1000)
   353  		v := new(GovernanceVote)
   354  		rlp.DecodeBytes(voteData, &v)
   355  
   356  		v, err := gov.ParseVoteValue(v)
   357  		assert.Equal(t, nil, err)
   358  		gotest_assert.DeepEqual(t, gov.voteMap.GetValue(v.Key).Value, v.Value)
   359  	}
   360  }
   361  
   362  func TestGovernance_ParseVoteValue(t *testing.T) {
   363  	gov := getGovernance()
   364  
   365  	addr := common.HexToAddress("0x1234567890123456789012345678901234567890")
   366  	for _, val := range goodVotes {
   367  		v := &GovernanceVote{
   368  			Key:       val.k,
   369  			Value:     gov.adjustValueType(val.k, val.v),
   370  			Validator: addr,
   371  		}
   372  
   373  		b, _ := rlp.EncodeToBytes(v)
   374  
   375  		d := new(GovernanceVote)
   376  		rlp.DecodeBytes(b, d)
   377  
   378  		d, err := gov.ParseVoteValue(d)
   379  		assert.Equal(t, nil, err)
   380  		gotest_assert.DeepEqual(t, v, d)
   381  	}
   382  }
   383  
   384  var testGovernanceMap = map[string]interface{}{
   385  	"governance.governancemode": "none",
   386  	"governance.governingnode":  common.HexToAddress("0x1234567890123456789012345678901234567890"),
   387  	"governance.unitprice":      uint64(25000000000),
   388  	"reward.ratio":              "30/40/30",
   389  	"reward.useginicoeff":       true,
   390  	"reward.deferredtxfee":      true,
   391  	"reward.minimumstake":       2000000,
   392  }
   393  
   394  func copyMap(src map[string]interface{}) map[string]interface{} {
   395  	dst := make(map[string]interface{})
   396  	for k, v := range src {
   397  		dst[k] = v
   398  	}
   399  	return dst
   400  }
   401  
   402  func TestGovernancePersistence(t *testing.T) {
   403  	gov := getGovernance()
   404  
   405  	MAXITEMS := int(10)
   406  
   407  	// Write Test
   408  	// WriteGovernance() and WriteGovernanceIdx()
   409  	for i := 1; i < MAXITEMS; i++ {
   410  		blockNum := params.DefaultEpoch * uint64(i)
   411  		tstMap := copyMap(testGovernanceMap)
   412  
   413  		// Make every stored governance map has a difference
   414  		tstMap["governance.unitprice"] = tstMap["governance.unitprice"].(uint64) + blockNum
   415  		if gov.CanWriteGovernanceState(blockNum) {
   416  			if err := gov.db.WriteGovernance(tstMap, blockNum); err != nil {
   417  				t.Errorf("Write governance failed: %v", err)
   418  			}
   419  		}
   420  	}
   421  
   422  	// Read Test
   423  	// ReadRecentGovernanceIdx() ReadGovernance()
   424  	tstIdx, _ := gov.db.ReadRecentGovernanceIdx(MAXITEMS)
   425  	length := len(tstIdx)
   426  	for i := 1; i < length; i++ {
   427  		num := tstIdx[i]
   428  		compMap, _ := gov.db.ReadGovernance(num)
   429  
   430  		expected := testGovernanceMap["governance.unitprice"].(uint64) + uint64(i)*params.DefaultEpoch
   431  		if uint64(compMap["governance.unitprice"].(float64)) != expected {
   432  			t.Errorf("Retrieved %v, Expected %v", compMap["governance.unitprice"], expected)
   433  		}
   434  	}
   435  
   436  	tstIdx2, _ := gov.db.ReadRecentGovernanceIdx(0)
   437  
   438  	if len(tstIdx2) != MAXITEMS {
   439  		t.Errorf("ReadRecentGovernanceIdx with 0 failure. want %v have %v", MAXITEMS, len(tstIdx2))
   440  	}
   441  
   442  	// ReadGovernanceAtNumber
   443  
   444  	for i := 0; i < MAXITEMS; i++ {
   445  		num := params.DefaultEpoch*uint64(i) + 123
   446  		idx, _, err := gov.db.ReadGovernanceAtNumber(num, params.DefaultEpoch)
   447  		if err != nil {
   448  			t.Errorf("Failed to get the governance information for block %d", num)
   449  		}
   450  		tValue := num - (num % params.DefaultEpoch)
   451  		if tValue >= params.DefaultEpoch {
   452  			tValue -= params.DefaultEpoch
   453  		}
   454  		if idx != tValue {
   455  			t.Errorf("Wrong block number, Want %v, have %v", tValue, idx)
   456  		}
   457  	}
   458  }
   459  
   460  type governanceData struct {
   461  	n uint64
   462  	e uint64
   463  }
   464  
   465  var tstGovernanceInfo = []governanceData{
   466  	{n: 1, e: 25000000000},
   467  	{n: 1209600, e: 25001209600},
   468  	{n: 2419200, e: 25002419200},
   469  	{n: 3628800, e: 25003628800},
   470  	{n: 4838400, e: 25004838400},
   471  }
   472  
   473  var tstGovernanceData = []governanceData{
   474  	{n: 123, e: 1}, // 1 is set at params.TestChainConfig
   475  	{n: 604923, e: 1},
   476  	{n: 1209723, e: 25000000000},
   477  	{n: 1814523, e: 25001209600},
   478  	{n: 2419323, e: 25001209600},
   479  	{n: 3024123, e: 25002419200},
   480  	{n: 3628923, e: 25002419200},
   481  	{n: 4233723, e: 25003628800},
   482  	{n: 4838523, e: 25003628800},
   483  	{n: 5443323, e: 25004838400},
   484  }
   485  
   486  func TestSaveGovernance(t *testing.T) {
   487  	gov := getGovernance()
   488  
   489  	MAXITEMS := int(10)
   490  
   491  	// Set Data
   492  	for i := 0; i < len(tstGovernanceInfo); i++ {
   493  		blockNum := tstGovernanceInfo[i].n
   494  		tstMap := copyMap(testGovernanceMap)
   495  
   496  		// Make every stored governance map has a difference
   497  		tstMap["governance.unitprice"] = tstGovernanceInfo[i].e
   498  		src := NewGovernanceSet()
   499  		delta := NewGovernanceSet()
   500  		src.Import(tstMap)
   501  		if err := gov.WriteGovernance(blockNum, src, delta); err != nil {
   502  			t.Errorf("Error in storing governance: %v", err)
   503  		}
   504  	}
   505  
   506  	// retrieve governance information. some will come from cache, others will be searched
   507  	for i := 0; i < MAXITEMS; i++ {
   508  		blockNum := tstGovernanceData[i].n
   509  		_, data, err := gov.ReadGovernance(blockNum)
   510  		if err == nil {
   511  			if data["governance.unitprice"] != tstGovernanceData[i].e {
   512  				t.Errorf("Data mismatch want %v, have %v for block %d", tstGovernanceData[i].e, data["governance.unitprice"], tstGovernanceData[i].n)
   513  			}
   514  		}
   515  	}
   516  }
   517  
   518  type epochTest struct {
   519  	v uint64
   520  	e uint64
   521  }
   522  
   523  // Assume epoch is 30
   524  var epochTestData = []epochTest{
   525  	{0, 0},
   526  	{30, 0},
   527  	{60, 30},
   528  	{90, 60},
   529  	{120, 90},
   530  	{150, 120},
   531  	{180, 150},
   532  	{210, 180},
   533  	{240, 210},
   534  	{270, 240},
   535  	{300, 270},
   536  	{330, 300},
   537  	{360, 330},
   538  }
   539  
   540  func TestCalcGovernanceInfoBlock(t *testing.T) {
   541  	for _, v := range epochTestData {
   542  		res := CalcGovernanceInfoBlock(v.v, 30)
   543  		if res != v.e {
   544  			t.Errorf("Governance Block Number Mismatch: want %v, have %v", v.e, res)
   545  		}
   546  	}
   547  }
   548  
   549  func TestVoteValueNilInterface(t *testing.T) {
   550  	gov := getGovernance()
   551  	gVote := new(GovernanceVote)
   552  	var test []byte
   553  
   554  	gVote.Key = "istanbul.policy"
   555  	// gVote.Value is an interface list
   556  	{
   557  		gVote.Value = []interface{}{[]byte{1, 2}}
   558  		test, _ = rlp.EncodeToBytes(gVote)
   559  		if err := rlp.DecodeBytes(test, gVote); err != nil {
   560  			t.Fatal("RLP decode error")
   561  		}
   562  
   563  		// Parse vote.Value and make it has appropriate type
   564  		_, err := gov.ParseVoteValue(gVote)
   565  		assert.Equal(t, ErrValueTypeMismatch, err)
   566  	}
   567  
   568  	// gVote.Value is an empty interface list
   569  	{
   570  		gVote.Value = []interface{}{[]byte{}}
   571  		test, _ = rlp.EncodeToBytes(gVote)
   572  		if err := rlp.DecodeBytes(test, gVote); err != nil {
   573  			t.Fatal("RLP decode error")
   574  		}
   575  
   576  		// Parse vote.Value and make it has appropriate type
   577  		_, err := gov.ParseVoteValue(gVote)
   578  		assert.Equal(t, ErrValueTypeMismatch, err)
   579  	}
   580  
   581  	// gVote.Value is nil
   582  	{
   583  		gVote.Value = nil
   584  		test, _ = rlp.EncodeToBytes(gVote)
   585  		if err := rlp.DecodeBytes(test, gVote); err != nil {
   586  			t.Fatal("RLP decode error")
   587  		}
   588  
   589  		// Parse vote.Value and make it has appropriate type
   590  		_, err := gov.ParseVoteValue(gVote)
   591  		assert.Equal(t, ErrValueTypeMismatch, err)
   592  	}
   593  
   594  	// gVote.Value is uint8 list
   595  	{
   596  		gVote.Value = []uint8{0x11}
   597  		test, _ = rlp.EncodeToBytes(gVote)
   598  		if err := rlp.DecodeBytes(test, gVote); err != nil {
   599  			t.Fatal("RLP decode error")
   600  		}
   601  
   602  		// Parse vote.Value and make it has appropriate type
   603  		_, err := gov.ParseVoteValue(gVote)
   604  		assert.NoError(t, err)
   605  	}
   606  
   607  	gVote.Key = "governance.addvalidator"
   608  	{
   609  		gVote.Value = [][]uint8{{0x3, 0x4}, {0x5, 0x6}}
   610  		test, _ = rlp.EncodeToBytes(gVote)
   611  		if err := rlp.DecodeBytes(test, gVote); err != nil {
   612  			t.Fatal("RLP decode error")
   613  		}
   614  		// Parse vote.Value and make it has appropriate type
   615  		_, err := gov.ParseVoteValue(gVote)
   616  		assert.Equal(t, ErrValueTypeMismatch, err)
   617  	}
   618  
   619  	{
   620  		gVote.Value = []uint8{0x1, 0x2, 0x3}
   621  		test, _ = rlp.EncodeToBytes(gVote)
   622  		if err := rlp.DecodeBytes(test, gVote); err != nil {
   623  			t.Fatal("RLP decode error")
   624  		}
   625  
   626  		// Parse vote.Value and make it has appropriate type
   627  		_, err := gov.ParseVoteValue(gVote)
   628  		assert.NoError(t, err)
   629  	}
   630  }
   631  
   632  func TestBaoBabGenesisHash(t *testing.T) {
   633  	baobabHash := params.BaobabGenesisHash
   634  	genesis := blockchain.DefaultBaobabGenesisBlock()
   635  	genesis.Governance = blockchain.SetGenesisGovernance(genesis)
   636  	blockchain.InitDeriveSha(genesis.Config)
   637  
   638  	db := database.NewMemoryDBManager()
   639  	block, _ := genesis.Commit(common.Hash{}, db)
   640  	if block.Hash() != baobabHash {
   641  		t.Errorf("Generated hash is not equal to Baobab's hash. Want %v, Have %v", baobabHash.String(), block.Hash().String())
   642  	}
   643  }
   644  
   645  func TestCypressGenesisHash(t *testing.T) {
   646  	cypressHash := params.CypressGenesisHash
   647  	genesis := blockchain.DefaultGenesisBlock()
   648  	genesis.Governance = blockchain.SetGenesisGovernance(genesis)
   649  	blockchain.InitDeriveSha(genesis.Config)
   650  
   651  	db := database.NewMemoryDBManager()
   652  	block, _ := genesis.Commit(common.Hash{}, db)
   653  	if block.Hash() != cypressHash {
   654  		t.Errorf("Generated hash is not equal to Cypress's hash. Want %v, Have %v", cypressHash.String(), block.Hash().String())
   655  	}
   656  }
   657  
   658  func TestGovernance_initializeCache(t *testing.T) {
   659  	dbm := database.NewDBManager(&database.DBConfig{DBType: database.MemoryDB})
   660  	config := getTestConfig()
   661  	config.Istanbul.Epoch = 30
   662  
   663  	gov := NewGovernanceInitialize(config, dbm)
   664  
   665  	testData := []struct {
   666  		// test input
   667  		governanceUpdateNum int
   668  		blockNums           []uint64
   669  		unitPrices          []uint64
   670  		currentBlockNum     int64
   671  		// expected result
   672  		unitPriceInCurrentSet uint64
   673  		actualGovernanceBlock uint64
   674  	}{
   675  		{0, []uint64{0}, []uint64{1}, 20, 1, 0},
   676  		{0, []uint64{0}, []uint64{1}, 50, 1, 0},
   677  		{0, []uint64{0}, []uint64{1}, 80, 1, 0},
   678  		{3, []uint64{0, 30, 60, 90}, []uint64{1, 2, 3, 4}, 90, 3, 60},
   679  		{3, []uint64{0, 30, 60, 90}, []uint64{1, 2, 3, 4}, 110, 3, 60},
   680  		{3, []uint64{0, 30, 60, 90}, []uint64{1, 2, 3, 4}, 130, 4, 90},
   681  	}
   682  
   683  	for _, tc := range testData {
   684  		// 1. initializing
   685  
   686  		// store governance items to the governance db for 'tc.governanceUpdateNum' times
   687  		for idx := 1; idx <= tc.governanceUpdateNum; idx++ {
   688  			config.UnitPrice = tc.unitPrices[idx]
   689  
   690  			src := GetGovernanceItemsFromChainConfig(config)
   691  			delta := NewGovernanceSet()
   692  
   693  			if ret := gov.WriteGovernance(tc.blockNums[idx], src, delta); ret != nil {
   694  				t.Errorf("Error in testing WriteGovernance, %v", ret)
   695  			}
   696  		}
   697  		// store head block (fake block, it only contains block number) to the headerDB
   698  		header := &types.Header{Number: big.NewInt(tc.currentBlockNum)}
   699  		gov.db.WriteHeadBlockHash(header.Hash())
   700  		gov.db.WriteHeader(header)
   701  
   702  		// reset idxCache and itemCache. purpose - reproduce the environment of the restarted node
   703  		gov.idxCache = nil
   704  		gov.itemCache.Purge()
   705  
   706  		// 2. call initializeCache
   707  		err := gov.initializeCache(config)
   708  
   709  		// 3. check the affected values with expected results
   710  		assert.NoError(t, err)
   711  
   712  		v, ok := gov.currentSet.GetValue(GovernanceKeyMap["governance.unitprice"])
   713  		assert.True(t, ok)
   714  		assert.Equal(t, tc.unitPriceInCurrentSet, v)
   715  
   716  		assert.Equal(t, tc.blockNums, gov.idxCache) // the order should be same
   717  		assert.True(t, gov.itemCache.Contains(getGovernanceCacheKey(tc.blockNums[tc.governanceUpdateNum])))
   718  		assert.Equal(t, tc.actualGovernanceBlock, gov.actualGovernanceBlock.Load().(uint64))
   719  	}
   720  }
   721  
   722  func TestGovernance_ReadGovernanceState(t *testing.T) {
   723  	dbm := database.NewDBManager(&database.DBConfig{DBType: database.MemoryDB})
   724  	config := getTestConfig()
   725  	bn := uint64(1024)
   726  
   727  	gjson := &governanceJSON{
   728  		BlockNumber: bn,
   729  		ChainConfig: config,
   730  		VoteMap: map[string]VoteStatus{
   731  			"governance.unitprice": {
   732  				Value:  float64(0),
   733  				Casted: true,
   734  				Num:    304,
   735  			},
   736  		},
   737  		NodeAddress: common.StringToAddress("0x0000000000000000000000000000000000000000"),
   738  		GovernanceVotes: []GovernanceVote{
   739  			{
   740  				Validator: common.StringToAddress("0xaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"),
   741  				Key:       "governance.unitprice",
   742  				Value:     float64(50000000000),
   743  			},
   744  		},
   745  		GovernanceTally: []GovernanceTallyItem{
   746  			{
   747  				Key:   "governance.unitprice",
   748  				Value: float64(50000000000),
   749  				Votes: 3,
   750  			},
   751  		},
   752  		CurrentSet: map[string]interface{}{
   753  			"reward.stakingupdateinterval":  config.Governance.Reward.StakingUpdateInterval,
   754  			"reward.proposerupdateinterval": config.Governance.Reward.ProposerUpdateInterval,
   755  		},
   756  		ChangeSet: map[string]interface{}{
   757  			"governance.unitprice": uint64(50000000000),
   758  		},
   759  	}
   760  
   761  	b, err := json.Marshal(gjson)
   762  	assert.Nil(t, err)
   763  
   764  	dbm.WriteGovernanceState(b)
   765  	gov := NewGovernanceInitialize(config, dbm)
   766  	gov.ReadGovernanceState()
   767  
   768  	assert.Equal(t, bn, gov.lastGovernanceStateBlock)
   769  	assert.Equal(t, gjson.VoteMap, gov.voteMap.items)
   770  	assert.Equal(t, gjson.NodeAddress, gov.nodeAddress.Load())
   771  	assert.Equal(t, gjson.GovernanceVotes, gov.GovernanceVotes.items)
   772  	assert.Equal(t, gjson.GovernanceTally, gov.GovernanceTallies.items)
   773  	assert.Equal(t, gjson.CurrentSet, gov.currentSet.items)
   774  	assert.Equal(t, gjson.ChangeSet, gov.changeSet.items)
   775  
   776  	assert.Equal(t, config.Governance.Reward.StakingUpdateInterval, gov.stakingUpdateInterval())
   777  	assert.Equal(t, config.Governance.Reward.ProposerUpdateInterval, gov.proposerUpdateInterval())
   778  }
   779  
   780  func TestWriteGovernance_idxCache(t *testing.T) {
   781  	gov := getGovernance()
   782  
   783  	tstMap := copyMap(testGovernanceMap)
   784  
   785  	src := NewGovernanceSet()
   786  	delta := NewGovernanceSet()
   787  	src.Import(tstMap)
   788  
   789  	blockNum := []uint64{30, 30, 60, 60, 50}
   790  
   791  	for _, num := range blockNum {
   792  		if ret := gov.WriteGovernance(num, src, delta); ret != nil {
   793  			t.Errorf("Error in testing WriteGovernance, %v", ret)
   794  		}
   795  	}
   796  
   797  	// idxCache should have 0, 30 and 60
   798  	if len(gov.idxCache) != 3 || gov.idxCache[len(gov.idxCache)-1] != 60 {
   799  		t.Errorf("idxCache has wrong value")
   800  	}
   801  }
   802  
   803  func getTestValidators() []common.Address {
   804  	return []common.Address{
   805  		common.HexToAddress("0x414790CA82C14A8B975cEBd66098c3dA590bf969"), // Node Address for test
   806  		common.HexToAddress("0x604973C51f6389dF2782E018000c3AC1257dee90"),
   807  		common.HexToAddress("0x5Ac1689ae5F521B05145C5Cd15a3E8F6ab39Af19"),
   808  		common.HexToAddress("0x0688CaC68bbF7c1a0faedA109c668a868BEd855E"),
   809  	}
   810  }
   811  
   812  func getTestDemotedValidators() []common.Address {
   813  	return []common.Address{
   814  		common.HexToAddress("0x3BB17a8A4f915cC9A8CAAcdC062Ef9b903511Ffa"),
   815  		common.HexToAddress("0x82588D33A48e6Bda012714f1C680d254ff607472"),
   816  		common.HexToAddress("0xceB7ADDFBa9665d8767173D47dE4453D7b7B900D"),
   817  		common.HexToAddress("0x38Ea854792EB956620E53090E8bc4e5C5C917123"),
   818  	}
   819  }
   820  
   821  func getTestRewards() []common.Address {
   822  	return []common.Address{
   823  		common.HexToAddress("0x2A35FE72F847aa0B509e4055883aE90c87558AaD"),
   824  		common.HexToAddress("0xF91B8EBa583C7fa603B400BE17fBaB7629568A4a"),
   825  		common.HexToAddress("0x240ed27c8bDc9Bb6cA08fa3D239699Fba525d05a"),
   826  		common.HexToAddress("0x3B980293396Fb0e827929D573e3e42d2EA902502"),
   827  	}
   828  }
   829  
   830  func getTestVotingPowers(num int) []uint64 {
   831  	vps := make([]uint64, 0, num)
   832  	for i := 0; i < num; i++ {
   833  		vps = append(vps, 1000)
   834  	}
   835  	return vps
   836  }
   837  
   838  const (
   839  	GovernanceModeBallot = "ballot"
   840  )
   841  
   842  func TestGovernance_HandleGovernanceVote_None_mode(t *testing.T) {
   843  	// Create ValidatorSet
   844  	validators := getTestValidators()
   845  	demotedValidators := getTestDemotedValidators()
   846  	rewards := getTestRewards()
   847  
   848  	blockCounter := big.NewInt(0)
   849  	valSet := validator.NewWeightedCouncil(validators, demotedValidators, rewards, getTestVotingPowers(len(validators)), nil, istanbul.WeightedRandom, 21, 0, 0, nil)
   850  	gov := getGovernance()
   851  	gov.nodeAddress.Store(validators[len(validators)-1])
   852  
   853  	votes := make([]GovernanceVote, 0)
   854  	tally := make([]GovernanceTallyItem, 0)
   855  
   856  	proposer := validators[0]
   857  	self := validators[len(validators)-1]
   858  	header := &types.Header{}
   859  
   860  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
   861  	// Test for "none" mode
   862  	header.Number = blockCounter.Add(blockCounter, common.Big1)
   863  	header.BlockScore = common.Big1
   864  	gov.AddVote("governance.unitprice", uint64(22000))
   865  	header.Vote = gov.GetEncodedVote(proposer, blockCounter.Uint64())
   866  
   867  	gov.HandleGovernanceVote(valSet, votes, tally, header, proposer, self, true)
   868  	gov.RemoveVote("governance.unitprice", uint64(22000), 0)
   869  
   870  	if _, ok := gov.changeSet.items["governance.unitprice"]; !ok {
   871  		t.Errorf("Vote had to be applied but it wasn't")
   872  	}
   873  	gov.voteMap.Clear()
   874  
   875  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
   876  	// Test for "istanbul.timeout" in "none" mode
   877  	header.Number = blockCounter.Add(blockCounter, common.Big1)
   878  	header.BlockScore = common.Big1
   879  
   880  	newValue := istanbul.DefaultConfig.Timeout + uint64(10000)
   881  	gov.AddVote("istanbul.timeout", newValue)
   882  	header.Vote = gov.GetEncodedVote(proposer, blockCounter.Uint64())
   883  
   884  	gov.HandleGovernanceVote(valSet, votes, tally, header, proposer, self, true)
   885  	gov.RemoveVote("istanbul.timeout", newValue, 0)
   886  	assert.Equal(t, istanbul.DefaultConfig.Timeout, newValue, "Vote had to be applied but it wasn't")
   887  
   888  	gov.voteMap.Clear()
   889  
   890  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
   891  	// Test removing a validator
   892  	header.Number = blockCounter.Add(blockCounter, common.Big1)
   893  	gov.AddVote("governance.removevalidator", validators[1].String())
   894  	header.Vote = gov.GetEncodedVote(proposer, blockCounter.Uint64())
   895  
   896  	gov.HandleGovernanceVote(valSet, votes, tally, header, proposer, self, true)
   897  	gov.RemoveVote("governance.removevalidator", validators[1], 0)
   898  	if i, _ := valSet.GetByAddress(validators[1]); i != -1 {
   899  		t.Errorf("Validator removal failed, %d validators remains", valSet.Size())
   900  	}
   901  	gov.voteMap.Clear()
   902  
   903  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
   904  	// Test removing a non-existing validator
   905  	header.Number = blockCounter.Add(blockCounter, common.Big1)
   906  	gov.AddVote("governance.removevalidator", validators[1].String())
   907  	header.Vote = gov.GetEncodedVote(proposer, blockCounter.Uint64())
   908  
   909  	gov.HandleGovernanceVote(valSet, votes, tally, header, proposer, proposer, true) // self = proposer
   910  	// check if casted
   911  	if !gov.voteMap.items["governance.removevalidator"].Casted {
   912  		t.Errorf("Removing a non-existing validator failed")
   913  	}
   914  	gov.RemoveVote("governance.removevalidator", validators[1], 0)
   915  	if i, _ := valSet.GetByAddress(validators[1]); i != -1 {
   916  		t.Errorf("Removing a non-existing validator failed, %d validators remains", valSet.Size())
   917  	}
   918  	gov.voteMap.Clear()
   919  
   920  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
   921  	// Test adding a validator
   922  	header.Number = blockCounter.Add(blockCounter, common.Big1)
   923  	gov.AddVote("governance.addvalidator", validators[1].String())
   924  	header.Vote = gov.GetEncodedVote(proposer, blockCounter.Uint64())
   925  
   926  	gov.HandleGovernanceVote(valSet, votes, tally, header, proposer, self, true)
   927  	gov.RemoveVote("governance.addvalidator", validators[1], 0)
   928  	if i, _ := valSet.GetByAddress(validators[1]); i == -1 {
   929  		t.Errorf("Validator addition failed, %d validators remains", valSet.Size())
   930  	}
   931  	gov.voteMap.Clear()
   932  
   933  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
   934  	// Test adding an existing validator
   935  	header.Number = blockCounter.Add(blockCounter, common.Big1)
   936  	gov.AddVote("governance.addvalidator", validators[1].String())
   937  	header.Vote = gov.GetEncodedVote(proposer, blockCounter.Uint64())
   938  
   939  	gov.HandleGovernanceVote(valSet, votes, tally, header, proposer, proposer, true) // self = proposer
   940  	// check if casted
   941  	if !gov.voteMap.items["governance.addvalidator"].Casted {
   942  		t.Errorf("Adding an existing validator failed")
   943  	}
   944  	gov.RemoveVote("governance.addvalidator", validators[1], 0)
   945  	if i, _ := valSet.GetByAddress(validators[1]); i == -1 {
   946  		t.Errorf("Validator addition failed, %d validators remains", valSet.Size())
   947  	}
   948  	gov.voteMap.Clear()
   949  
   950  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
   951  	// Test removing a demoted validator
   952  	header.Number = blockCounter.Add(blockCounter, common.Big1)
   953  	gov.AddVote("governance.removevalidator", demotedValidators[1].String())
   954  	header.Vote = gov.GetEncodedVote(proposer, blockCounter.Uint64())
   955  
   956  	gov.HandleGovernanceVote(valSet, votes, tally, header, proposer, self, true)
   957  	gov.RemoveVote("governance.removevalidator", demotedValidators[1], 0)
   958  	if i, _ := valSet.GetDemotedByAddress(demotedValidators[1]); i != -1 {
   959  		t.Errorf("Demoted validator removal failed, %d demoted validators remains", len(valSet.DemotedList()))
   960  	}
   961  	gov.voteMap.Clear()
   962  
   963  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
   964  	// Test adding a demoted validator
   965  	header.Number = blockCounter.Add(blockCounter, common.Big1)
   966  	gov.AddVote("governance.addvalidator", demotedValidators[1].String())
   967  	header.Vote = gov.GetEncodedVote(proposer, blockCounter.Uint64())
   968  
   969  	gov.HandleGovernanceVote(valSet, votes, tally, header, proposer, self, true)
   970  	gov.RemoveVote("governance.addvalidator", demotedValidators[1], 0)
   971  	// At first, demoted validator is added to the validators, but it will be refreshed right after
   972  	// So, we here check only if the adding demoted validator to validators
   973  	if i, _ := valSet.GetByAddress(demotedValidators[1]); i == -1 {
   974  		t.Errorf("Demoted validator addition failed, %d demoted validators remains", len(valSet.DemotedList()))
   975  	}
   976  	gov.voteMap.Clear()
   977  }
   978  
   979  func TestGovernance_HandleGovernanceVote_Ballot_mode(t *testing.T) {
   980  	// Create ValidatorSet
   981  	validators := getTestValidators()
   982  	demotedValidators := getTestDemotedValidators()
   983  	rewards := getTestRewards()
   984  
   985  	blockCounter := big.NewInt(0)
   986  	var valSet istanbul.ValidatorSet
   987  	valSet = validator.NewWeightedCouncil(validators, demotedValidators, rewards, getTestVotingPowers(len(validators)), nil, istanbul.WeightedRandom, 21, 0, 0, nil)
   988  
   989  	config := getTestConfig()
   990  	config.Governance.GovernanceMode = GovernanceModeBallot
   991  	dbm := database.NewDBManager(&database.DBConfig{DBType: database.MemoryDB})
   992  	gov := NewGovernanceInitialize(config, dbm)
   993  	gov.nodeAddress.Store(validators[len(validators)-1])
   994  
   995  	votes := make([]GovernanceVote, 0)
   996  	tally := make([]GovernanceTallyItem, 0)
   997  
   998  	self := validators[len(validators)-1]
   999  	header := &types.Header{}
  1000  
  1001  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
  1002  	// Test for "ballot" mode
  1003  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1004  	header.BlockScore = common.Big1
  1005  	gov.AddVote("governance.unitprice", uint64(22000))
  1006  
  1007  	header.Vote = gov.GetEncodedVote(validators[0], blockCounter.Uint64())
  1008  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[0], self, true)
  1009  
  1010  	header.Vote = gov.GetEncodedVote(validators[1], blockCounter.Uint64())
  1011  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[1], self, true)
  1012  
  1013  	if _, ok := gov.changeSet.items["governance.unitprice"]; ok {
  1014  		t.Errorf("Vote shouldn't be applied yet but it was applied")
  1015  	}
  1016  
  1017  	header.Vote = gov.GetEncodedVote(validators[2], blockCounter.Uint64())
  1018  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[2], self, true)
  1019  	if _, ok := gov.changeSet.items["governance.unitprice"]; !ok {
  1020  		t.Errorf("Vote should be applied but it was not")
  1021  	}
  1022  
  1023  	gov.RemoveVote("governance.unitprice", uint64(22000), blockCounter.Uint64())
  1024  	gov.voteMap.Clear()
  1025  
  1026  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
  1027  	// Test for "istanbul.timeout" in "ballot" mode
  1028  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1029  	header.BlockScore = common.Big1
  1030  	newValue := istanbul.DefaultConfig.Timeout + uint64(10000)
  1031  	gov.AddVote("istanbul.timeout", newValue)
  1032  
  1033  	header.Vote = gov.GetEncodedVote(validators[0], blockCounter.Uint64())
  1034  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[0], self, true)
  1035  
  1036  	header.Vote = gov.GetEncodedVote(validators[1], blockCounter.Uint64())
  1037  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[1], self, true)
  1038  
  1039  	assert.NotEqual(t, istanbul.DefaultConfig.Timeout, newValue, "Vote shouldn't be applied yet but it was applied")
  1040  
  1041  	header.Vote = gov.GetEncodedVote(validators[2], blockCounter.Uint64())
  1042  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[2], self, true)
  1043  
  1044  	assert.Equal(t, istanbul.DefaultConfig.Timeout, newValue, "Vote should be applied but it was not")
  1045  	gov.RemoveVote("istanbul.timeout", newValue, blockCounter.Uint64())
  1046  	gov.voteMap.Clear()
  1047  
  1048  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
  1049  	// Test removing a validator, because there are 4 nodes 3 votes are required to remove a validator
  1050  	gov.AddVote("governance.removevalidator", validators[1].String())
  1051  
  1052  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1053  	header.Vote = gov.GetEncodedVote(validators[0], blockCounter.Uint64())
  1054  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[0], self, true)
  1055  
  1056  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1057  	header.Vote = gov.GetEncodedVote(validators[2], blockCounter.Uint64())
  1058  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[2], self, true)
  1059  	if i, _ := valSet.GetByAddress(validators[1]); i == -1 {
  1060  		t.Errorf("Validator removal shouldn't be done yet, %d validators remains", valSet.Size())
  1061  	}
  1062  
  1063  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1064  	header.Vote = gov.GetEncodedVote(validators[3], blockCounter.Uint64())
  1065  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[3], self, true)
  1066  
  1067  	if i, _ := valSet.GetByAddress(validators[1]); i != -1 {
  1068  		t.Errorf("Validator removal failed, %d validators remains", valSet.Size())
  1069  	}
  1070  	gov.RemoveVote("governance.removevalidator", validators[1], blockCounter.Uint64())
  1071  	gov.voteMap.Clear()
  1072  
  1073  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
  1074  	// Test removing a non-existing validator. Because there are 3 nodes, 2 votes are required to remove a validator
  1075  	gov.AddVote("governance.removevalidator", validators[1].String())
  1076  
  1077  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1078  	header.Vote = gov.GetEncodedVote(validators[0], blockCounter.Uint64())
  1079  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[0], validators[0], true)
  1080  	// check if casted
  1081  	if !gov.voteMap.items["governance.removevalidator"].Casted {
  1082  		t.Errorf("Removing a non-existing validator failed")
  1083  	}
  1084  
  1085  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1086  	header.Vote = gov.GetEncodedVote(validators[2], blockCounter.Uint64())
  1087  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[2], validators[2], true)
  1088  	// check if casted
  1089  	if !gov.voteMap.items["governance.removevalidator"].Casted {
  1090  		t.Errorf("Removing a non-existing validator failed")
  1091  	}
  1092  
  1093  	gov.RemoveVote("governance.removevalidator", validators[1], blockCounter.Uint64())
  1094  	gov.voteMap.Clear()
  1095  
  1096  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
  1097  	// Test adding a validator, because there are 3 nodes 2 plus votes are required to add a new validator
  1098  	gov.AddVote("governance.addvalidator", validators[1].String())
  1099  
  1100  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1101  	header.Vote = gov.GetEncodedVote(validators[0], blockCounter.Uint64())
  1102  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[0], self, true)
  1103  	if i, _ := valSet.GetByAddress(validators[1]); i != -1 {
  1104  		t.Errorf("Validator addition shouldn't be done yet, %d validators remains", valSet.Size())
  1105  	}
  1106  
  1107  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1108  	header.Vote = gov.GetEncodedVote(validators[2], blockCounter.Uint64())
  1109  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[2], self, true)
  1110  
  1111  	if i, _ := valSet.GetByAddress(validators[1]); i == -1 {
  1112  		t.Errorf("Validator addition failed, %d validators remains", valSet.Size())
  1113  	}
  1114  	gov.RemoveVote("governance.addvalidator", validators[1], blockCounter.Uint64())
  1115  	gov.voteMap.Clear()
  1116  
  1117  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
  1118  	// Test adding an existing validator, because there are 3 nodes 2 plus votes are required to add a new validator
  1119  	gov.AddVote("governance.addvalidator", validators[1].String())
  1120  
  1121  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1122  	header.Vote = gov.GetEncodedVote(validators[0], blockCounter.Uint64())
  1123  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[0], validators[0], true)
  1124  	// check if casted
  1125  	if !gov.voteMap.items["governance.addvalidator"].Casted {
  1126  		t.Errorf("Adding an existing validator failed")
  1127  	}
  1128  
  1129  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1130  	header.Vote = gov.GetEncodedVote(validators[2], blockCounter.Uint64())
  1131  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[2], validators[2], true)
  1132  	// check if casted
  1133  	if !gov.voteMap.items["governance.addvalidator"].Casted {
  1134  		t.Errorf("Adding an existing validator failed")
  1135  	}
  1136  
  1137  	gov.RemoveVote("governance.addvalidator", validators[1], blockCounter.Uint64())
  1138  	gov.voteMap.Clear()
  1139  
  1140  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
  1141  	// Test removing a demoted validator, because there are 4 nodes 3 votes are required to remove a demoted validator
  1142  	gov.AddVote("governance.removevalidator", demotedValidators[1].String())
  1143  
  1144  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1145  	header.Vote = gov.GetEncodedVote(validators[0], blockCounter.Uint64())
  1146  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[0], self, true)
  1147  
  1148  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1149  	header.Vote = gov.GetEncodedVote(validators[2], blockCounter.Uint64())
  1150  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[2], self, true)
  1151  	if i, _ := valSet.GetDemotedByAddress(demotedValidators[1]); i == -1 {
  1152  		t.Errorf("Demoted validator removal shouldn't be done yet, %d validators remains", len(valSet.DemotedList()))
  1153  	}
  1154  
  1155  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1156  	header.Vote = gov.GetEncodedVote(validators[3], blockCounter.Uint64())
  1157  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[3], self, true)
  1158  
  1159  	if i, _ := valSet.GetDemotedByAddress(demotedValidators[1]); i != -1 {
  1160  		t.Errorf("Demoted validator removal failed, %d validators remains", len(valSet.DemotedList()))
  1161  	}
  1162  	gov.voteMap.Clear()
  1163  
  1164  	//////////////////////////////////////////////////////////////////////////////////////////////////////////
  1165  	// Test adding a demoted validator, because there are 4 nodes 3 votes are required to add a demoted validator
  1166  	gov.AddVote("governance.addvalidator", demotedValidators[1].String())
  1167  
  1168  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1169  	header.Vote = gov.GetEncodedVote(validators[0], blockCounter.Uint64())
  1170  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[0], self, true)
  1171  	if i, _ := valSet.GetByAddress(demotedValidators[1]); i != -1 {
  1172  		t.Errorf("Validator addition shouldn't be done yet, %d validators remains", len(valSet.DemotedList()))
  1173  	}
  1174  
  1175  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1176  	header.Vote = gov.GetEncodedVote(validators[2], blockCounter.Uint64())
  1177  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[2], self, true)
  1178  
  1179  	header.Number = blockCounter.Add(blockCounter, common.Big1)
  1180  	header.Vote = gov.GetEncodedVote(validators[3], blockCounter.Uint64())
  1181  	valSet, votes, tally = gov.HandleGovernanceVote(valSet, votes, tally, header, validators[3], self, true)
  1182  
  1183  	// At first, demoted validator is added to the validators, but it will be refreshed right after
  1184  	// So, we here check only if the adding demoted validator to validators
  1185  	if i, _ := valSet.GetByAddress(demotedValidators[1]); i == -1 {
  1186  		t.Errorf("Demoted validator addition failed, %d validators remains", len(valSet.DemotedList()))
  1187  	}
  1188  	gov.voteMap.Clear()
  1189  }
  1190  
  1191  func TestGovernance_checkVote(t *testing.T) {
  1192  	// Create ValidatorSet
  1193  	council := getTestValidators()
  1194  	validators := []common.Address{council[0], council[1]}
  1195  	demotedValidators := []common.Address{council[2], council[3]}
  1196  
  1197  	valSet := validator.NewWeightedCouncil(validators, demotedValidators, nil, getTestVotingPowers(len(validators)), nil, istanbul.WeightedRandom, 21, 0, 0, nil)
  1198  
  1199  	config := getTestConfig()
  1200  	dbm := database.NewDBManager(&database.DBConfig{DBType: database.MemoryDB})
  1201  	gov := NewGovernanceInitialize(config, dbm)
  1202  
  1203  	unknown := common.HexToAddress("0xa")
  1204  
  1205  	// for adding validator
  1206  	assert.True(t, gov.checkVote(unknown, true, valSet))
  1207  	assert.True(t, gov.checkVote(validators[0], false, valSet))
  1208  	assert.True(t, gov.checkVote(demotedValidators[0], false, valSet))
  1209  
  1210  	// for removing validator
  1211  	assert.False(t, gov.checkVote(unknown, false, valSet))
  1212  	assert.False(t, gov.checkVote(validators[1], true, valSet))
  1213  	assert.False(t, gov.checkVote(demotedValidators[1], true, valSet))
  1214  }
  1215  
  1216  func TestGovernance_VerifyGovernance(t *testing.T) {
  1217  	gov := getGovernance()
  1218  	vote := GovernanceVote{
  1219  		Key:   "governance.governingnode",
  1220  		Value: common.HexToAddress("000000000000000000000000000abcd000000000"),
  1221  	}
  1222  	gov.updateChangeSet(vote)
  1223  
  1224  	// consensus/istanbul/backend/engine.go:Prepare()
  1225  	// Correct case
  1226  	g := gov.GetGovernanceChange()
  1227  	j, err := json.Marshal(g)
  1228  	assert.Nil(t, err)
  1229  	r, err := rlp.EncodeToBytes(j)
  1230  	assert.Nil(t, err)
  1231  	err = gov.VerifyGovernance(r)
  1232  	assert.Nil(t, err)
  1233  
  1234  	// Value mismatch
  1235  	g = gov.GetGovernanceChange()
  1236  	g["governance.governingnode"] = "000000000000000000000000000abcd000001111"
  1237  	j, err = json.Marshal(g)
  1238  	assert.Nil(t, err)
  1239  	r, err = rlp.EncodeToBytes(j)
  1240  	assert.Nil(t, err)
  1241  	err = gov.VerifyGovernance(r)
  1242  	assert.Equal(t, ErrVoteValueMismatch, err)
  1243  
  1244  	// Type mismatch
  1245  	g = gov.GetGovernanceChange()
  1246  	g["governance.governingnode"] = 123
  1247  	j, err = json.Marshal(g)
  1248  	assert.Nil(t, err)
  1249  	r, err = rlp.EncodeToBytes(j)
  1250  	assert.Nil(t, err)
  1251  	err = gov.VerifyGovernance(r)
  1252  	assert.Equal(t, ErrVoteValueMismatch, err)
  1253  
  1254  	// Length mismatch
  1255  	g = gov.GetGovernanceChange()
  1256  	g["governance.governingnode"] = 123
  1257  	g["istanbul.epoch"] = uint64(10000)
  1258  	j, err = json.Marshal(g)
  1259  	assert.Nil(t, err)
  1260  	r, err = rlp.EncodeToBytes(j)
  1261  	assert.Nil(t, err)
  1262  	err = gov.VerifyGovernance(r)
  1263  	assert.Equal(t, ErrVoteValueMismatch, err)
  1264  }
  1265  
  1266  func TestGovernance_ParamsAt(t *testing.T) {
  1267  	valueA := uint64(0x11)
  1268  	valueB := uint64(0x22)
  1269  	valueC := uint64(0x33)
  1270  	koreBlock := uint64(100)
  1271  
  1272  	dbm := database.NewDBManager(&database.DBConfig{DBType: database.MemoryDB})
  1273  	config := getTestConfig()
  1274  	config.Istanbul.Epoch = 30
  1275  	config.Istanbul.SubGroupSize = valueA
  1276  	config.KoreCompatibleBlock = new(big.Int).SetUint64(koreBlock)
  1277  	gov := NewGovernanceInitialize(config, dbm)
  1278  
  1279  	// Write to database. Note that we must use gov.WriteGovernance(), not db.WriteGovernance()
  1280  	// The reason is that gov.ReadGovernance() depends on the caches, and that
  1281  	// gov.WriteGovernance() sets idxCache accordingly, whereas db.WriteGovernance don't
  1282  	items := gov.CurrentParams().StrMap()
  1283  	gset := NewGovernanceSet()
  1284  
  1285  	items["istanbul.committeesize"] = valueB
  1286  	gset.Import(items)
  1287  	gov.WriteGovernance(30, NewGovernanceSet(), gset)
  1288  
  1289  	items["istanbul.committeesize"] = valueC
  1290  	gset.Import(items)
  1291  	gov.WriteGovernance(120, NewGovernanceSet(), gset)
  1292  
  1293  	testcases := []struct {
  1294  		num   uint64
  1295  		value uint64
  1296  	}{
  1297  		{59, valueA},
  1298  		{60, valueA},
  1299  		{61, valueB},
  1300  		{149, valueB},
  1301  		{150, valueC},
  1302  		{151, valueC},
  1303  	}
  1304  	for _, tc := range testcases {
  1305  		// Check that e.EffectiveParams() == tc
  1306  		pset, err := gov.EffectiveParams(tc.num)
  1307  		assert.Nil(t, err)
  1308  		assert.Equal(t, tc.value, pset.CommitteeSize(), "Wrong at %d", tc.num)
  1309  	}
  1310  }