mirror of
https://github.com/fluencelabs/tendermint
synced 2025-06-20 08:26:31 +00:00
abci: VoteInfo, ValidatorUpdate. See ADR-018
This commit is contained in:
@ -7,12 +7,10 @@ import (
|
|||||||
|
|
||||||
// RandVal creates one random validator, with a key derived
|
// RandVal creates one random validator, with a key derived
|
||||||
// from the input value
|
// from the input value
|
||||||
func RandVal(i int) types.Validator {
|
func RandVal(i int) types.ValidatorUpdate {
|
||||||
addr := cmn.RandBytes(20)
|
|
||||||
pubkey := cmn.RandBytes(32)
|
pubkey := cmn.RandBytes(32)
|
||||||
power := cmn.RandUint16() + 1
|
power := cmn.RandUint16() + 1
|
||||||
v := types.Ed25519Validator(pubkey, int64(power))
|
v := types.Ed25519ValidatorUpdate(pubkey, int64(power))
|
||||||
v.Address = addr
|
|
||||||
return v
|
return v
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -20,8 +18,8 @@ func RandVal(i int) types.Validator {
|
|||||||
// the application. Note that the keys are deterministically
|
// the application. Note that the keys are deterministically
|
||||||
// derived from the index in the array, while the power is
|
// derived from the index in the array, while the power is
|
||||||
// random (Change this if not desired)
|
// random (Change this if not desired)
|
||||||
func RandVals(cnt int) []types.Validator {
|
func RandVals(cnt int) []types.ValidatorUpdate {
|
||||||
res := make([]types.Validator, cnt)
|
res := make([]types.ValidatorUpdate, cnt)
|
||||||
for i := 0; i < cnt; i++ {
|
for i := 0; i < cnt; i++ {
|
||||||
res[i] = RandVal(i)
|
res[i] = RandVal(i)
|
||||||
}
|
}
|
||||||
|
@ -122,11 +122,11 @@ func TestValUpdates(t *testing.T) {
|
|||||||
vals1, vals2 := vals[:nInit], kvstore.Validators()
|
vals1, vals2 := vals[:nInit], kvstore.Validators()
|
||||||
valsEqual(t, vals1, vals2)
|
valsEqual(t, vals1, vals2)
|
||||||
|
|
||||||
var v1, v2, v3 types.Validator
|
var v1, v2, v3 types.ValidatorUpdate
|
||||||
|
|
||||||
// add some validators
|
// add some validators
|
||||||
v1, v2 = vals[nInit], vals[nInit+1]
|
v1, v2 = vals[nInit], vals[nInit+1]
|
||||||
diff := []types.Validator{v1, v2}
|
diff := []types.ValidatorUpdate{v1, v2}
|
||||||
tx1 := MakeValSetChangeTx(v1.PubKey, v1.Power)
|
tx1 := MakeValSetChangeTx(v1.PubKey, v1.Power)
|
||||||
tx2 := MakeValSetChangeTx(v2.PubKey, v2.Power)
|
tx2 := MakeValSetChangeTx(v2.PubKey, v2.Power)
|
||||||
|
|
||||||
@ -140,7 +140,7 @@ func TestValUpdates(t *testing.T) {
|
|||||||
v1.Power = 0
|
v1.Power = 0
|
||||||
v2.Power = 0
|
v2.Power = 0
|
||||||
v3.Power = 0
|
v3.Power = 0
|
||||||
diff = []types.Validator{v1, v2, v3}
|
diff = []types.ValidatorUpdate{v1, v2, v3}
|
||||||
tx1 = MakeValSetChangeTx(v1.PubKey, v1.Power)
|
tx1 = MakeValSetChangeTx(v1.PubKey, v1.Power)
|
||||||
tx2 = MakeValSetChangeTx(v2.PubKey, v2.Power)
|
tx2 = MakeValSetChangeTx(v2.PubKey, v2.Power)
|
||||||
tx3 := MakeValSetChangeTx(v3.PubKey, v3.Power)
|
tx3 := MakeValSetChangeTx(v3.PubKey, v3.Power)
|
||||||
@ -158,18 +158,18 @@ func TestValUpdates(t *testing.T) {
|
|||||||
} else {
|
} else {
|
||||||
v1.Power = 5
|
v1.Power = 5
|
||||||
}
|
}
|
||||||
diff = []types.Validator{v1}
|
diff = []types.ValidatorUpdate{v1}
|
||||||
tx1 = MakeValSetChangeTx(v1.PubKey, v1.Power)
|
tx1 = MakeValSetChangeTx(v1.PubKey, v1.Power)
|
||||||
|
|
||||||
makeApplyBlock(t, kvstore, 3, diff, tx1)
|
makeApplyBlock(t, kvstore, 3, diff, tx1)
|
||||||
|
|
||||||
vals1 = append([]types.Validator{v1}, vals1[1:]...)
|
vals1 = append([]types.ValidatorUpdate{v1}, vals1[1:]...)
|
||||||
vals2 = kvstore.Validators()
|
vals2 = kvstore.Validators()
|
||||||
valsEqual(t, vals1, vals2)
|
valsEqual(t, vals1, vals2)
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func makeApplyBlock(t *testing.T, kvstore types.Application, heightInt int, diff []types.Validator, txs ...[]byte) {
|
func makeApplyBlock(t *testing.T, kvstore types.Application, heightInt int, diff []types.ValidatorUpdate, txs ...[]byte) {
|
||||||
// make and apply block
|
// make and apply block
|
||||||
height := int64(heightInt)
|
height := int64(heightInt)
|
||||||
hash := []byte("foo")
|
hash := []byte("foo")
|
||||||
@ -191,12 +191,12 @@ func makeApplyBlock(t *testing.T, kvstore types.Application, heightInt int, diff
|
|||||||
}
|
}
|
||||||
|
|
||||||
// order doesn't matter
|
// order doesn't matter
|
||||||
func valsEqual(t *testing.T, vals1, vals2 []types.Validator) {
|
func valsEqual(t *testing.T, vals1, vals2 []types.ValidatorUpdate) {
|
||||||
if len(vals1) != len(vals2) {
|
if len(vals1) != len(vals2) {
|
||||||
t.Fatalf("vals dont match in len. got %d, expected %d", len(vals2), len(vals1))
|
t.Fatalf("vals dont match in len. got %d, expected %d", len(vals2), len(vals1))
|
||||||
}
|
}
|
||||||
sort.Sort(types.Validators(vals1))
|
sort.Sort(types.ValidatorUpdates(vals1))
|
||||||
sort.Sort(types.Validators(vals2))
|
sort.Sort(types.ValidatorUpdates(vals2))
|
||||||
for i, v1 := range vals1 {
|
for i, v1 := range vals1 {
|
||||||
v2 := vals2[i]
|
v2 := vals2[i]
|
||||||
if !bytes.Equal(v1.PubKey.Data, v2.PubKey.Data) ||
|
if !bytes.Equal(v1.PubKey.Data, v2.PubKey.Data) ||
|
||||||
|
@ -25,7 +25,7 @@ type PersistentKVStoreApplication struct {
|
|||||||
app *KVStoreApplication
|
app *KVStoreApplication
|
||||||
|
|
||||||
// validator set
|
// validator set
|
||||||
ValUpdates []types.Validator
|
ValUpdates []types.ValidatorUpdate
|
||||||
|
|
||||||
logger log.Logger
|
logger log.Logger
|
||||||
}
|
}
|
||||||
@ -101,7 +101,7 @@ func (app *PersistentKVStoreApplication) InitChain(req types.RequestInitChain) t
|
|||||||
// Track the block hash and header information
|
// Track the block hash and header information
|
||||||
func (app *PersistentKVStoreApplication) BeginBlock(req types.RequestBeginBlock) types.ResponseBeginBlock {
|
func (app *PersistentKVStoreApplication) BeginBlock(req types.RequestBeginBlock) types.ResponseBeginBlock {
|
||||||
// reset valset changes
|
// reset valset changes
|
||||||
app.ValUpdates = make([]types.Validator, 0)
|
app.ValUpdates = make([]types.ValidatorUpdate, 0)
|
||||||
return types.ResponseBeginBlock{}
|
return types.ResponseBeginBlock{}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -113,11 +113,11 @@ func (app *PersistentKVStoreApplication) EndBlock(req types.RequestEndBlock) typ
|
|||||||
//---------------------------------------------
|
//---------------------------------------------
|
||||||
// update validators
|
// update validators
|
||||||
|
|
||||||
func (app *PersistentKVStoreApplication) Validators() (validators []types.Validator) {
|
func (app *PersistentKVStoreApplication) Validators() (validators []types.ValidatorUpdate) {
|
||||||
itr := app.app.state.db.Iterator(nil, nil)
|
itr := app.app.state.db.Iterator(nil, nil)
|
||||||
for ; itr.Valid(); itr.Next() {
|
for ; itr.Valid(); itr.Next() {
|
||||||
if isValidatorTx(itr.Key()) {
|
if isValidatorTx(itr.Key()) {
|
||||||
validator := new(types.Validator)
|
validator := new(types.ValidatorUpdate)
|
||||||
err := types.ReadMessage(bytes.NewBuffer(itr.Value()), validator)
|
err := types.ReadMessage(bytes.NewBuffer(itr.Value()), validator)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
panic(err)
|
panic(err)
|
||||||
@ -167,11 +167,11 @@ func (app *PersistentKVStoreApplication) execValidatorTx(tx []byte) types.Respon
|
|||||||
}
|
}
|
||||||
|
|
||||||
// update
|
// update
|
||||||
return app.updateValidator(types.Ed25519Validator(pubkey, int64(power)))
|
return app.updateValidator(types.Ed25519ValidatorUpdate(pubkey, int64(power)))
|
||||||
}
|
}
|
||||||
|
|
||||||
// add, update, or remove a validator
|
// add, update, or remove a validator
|
||||||
func (app *PersistentKVStoreApplication) updateValidator(v types.Validator) types.ResponseDeliverTx {
|
func (app *PersistentKVStoreApplication) updateValidator(v types.ValidatorUpdate) types.ResponseDeliverTx {
|
||||||
key := []byte("val:" + string(v.PubKey.Data))
|
key := []byte("val:" + string(v.PubKey.Data))
|
||||||
if v.Power == 0 {
|
if v.Power == 0 {
|
||||||
// remove validator
|
// remove validator
|
||||||
|
@ -12,11 +12,11 @@ import (
|
|||||||
|
|
||||||
func InitChain(client abcicli.Client) error {
|
func InitChain(client abcicli.Client) error {
|
||||||
total := 10
|
total := 10
|
||||||
vals := make([]types.Validator, total)
|
vals := make([]types.ValidatorUpdate, total)
|
||||||
for i := 0; i < total; i++ {
|
for i := 0; i < total; i++ {
|
||||||
pubkey := cmn.RandBytes(33)
|
pubkey := cmn.RandBytes(33)
|
||||||
power := cmn.RandInt()
|
power := cmn.RandInt()
|
||||||
vals[i] = types.Ed25519Validator(pubkey, int64(power))
|
vals[i] = types.Ed25519ValidatorUpdate(pubkey, int64(power))
|
||||||
}
|
}
|
||||||
_, err := client.InitChainSync(types.RequestInitChain{
|
_, err := client.InitChainSync(types.RequestInitChain{
|
||||||
Validators: vals,
|
Validators: vals,
|
||||||
|
@ -4,8 +4,8 @@ const (
|
|||||||
PubKeyEd25519 = "ed25519"
|
PubKeyEd25519 = "ed25519"
|
||||||
)
|
)
|
||||||
|
|
||||||
func Ed25519Validator(pubkey []byte, power int64) Validator {
|
func Ed25519ValidatorUpdate(pubkey []byte, power int64) ValidatorUpdate {
|
||||||
return Validator{
|
return ValidatorUpdate{
|
||||||
// Address:
|
// Address:
|
||||||
PubKey: PubKey{
|
PubKey: PubKey{
|
||||||
Type: PubKeyEd25519,
|
Type: PubKeyEd25519,
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -60,7 +60,7 @@ message RequestInitChain {
|
|||||||
google.protobuf.Timestamp time = 1 [(gogoproto.nullable)=false, (gogoproto.stdtime)=true];
|
google.protobuf.Timestamp time = 1 [(gogoproto.nullable)=false, (gogoproto.stdtime)=true];
|
||||||
string chain_id = 2;
|
string chain_id = 2;
|
||||||
ConsensusParams consensus_params = 3;
|
ConsensusParams consensus_params = 3;
|
||||||
repeated Validator validators = 4 [(gogoproto.nullable)=false];
|
repeated ValidatorUpdate validators = 4 [(gogoproto.nullable)=false];
|
||||||
bytes app_state_bytes = 5;
|
bytes app_state_bytes = 5;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -143,7 +143,7 @@ message ResponseSetOption {
|
|||||||
|
|
||||||
message ResponseInitChain {
|
message ResponseInitChain {
|
||||||
ConsensusParams consensus_params = 1;
|
ConsensusParams consensus_params = 1;
|
||||||
repeated Validator validators = 2 [(gogoproto.nullable)=false];
|
repeated ValidatorUpdate validators = 2 [(gogoproto.nullable)=false];
|
||||||
}
|
}
|
||||||
|
|
||||||
message ResponseQuery {
|
message ResponseQuery {
|
||||||
@ -183,7 +183,7 @@ message ResponseDeliverTx {
|
|||||||
}
|
}
|
||||||
|
|
||||||
message ResponseEndBlock {
|
message ResponseEndBlock {
|
||||||
repeated Validator validator_updates = 1 [(gogoproto.nullable)=false];
|
repeated ValidatorUpdate validator_updates = 1 [(gogoproto.nullable)=false];
|
||||||
ConsensusParams consensus_param_updates = 2;
|
ConsensusParams consensus_param_updates = 2;
|
||||||
repeated common.KVPair tags = 3 [(gogoproto.nullable)=false, (gogoproto.jsontag)="tags,omitempty"];
|
repeated common.KVPair tags = 3 [(gogoproto.nullable)=false, (gogoproto.jsontag)="tags,omitempty"];
|
||||||
}
|
}
|
||||||
@ -225,8 +225,7 @@ message BlockGossip {
|
|||||||
}
|
}
|
||||||
|
|
||||||
message LastCommitInfo {
|
message LastCommitInfo {
|
||||||
int32 commit_round = 1;
|
repeated VoteInfo commit_votes = 1 [(gogoproto.nullable)=false];
|
||||||
repeated SigningValidator validators = 2 [(gogoproto.nullable)=false];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
//----------------------------------------
|
//----------------------------------------
|
||||||
@ -272,14 +271,20 @@ message PartSetHeader {
|
|||||||
// Validator
|
// Validator
|
||||||
message Validator {
|
message Validator {
|
||||||
bytes address = 1;
|
bytes address = 1;
|
||||||
PubKey pub_key = 2 [(gogoproto.nullable)=false];
|
|
||||||
int64 power = 3;
|
int64 power = 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Validator with an extra bool
|
// ValidatorUpdate
|
||||||
message SigningValidator {
|
message ValidatorUpdate {
|
||||||
|
PubKey pub_key = 1 [(gogoproto.nullable)=false];
|
||||||
|
int64 power = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
// VoteInfo
|
||||||
|
message VoteInfo {
|
||||||
Validator validator = 1 [(gogoproto.nullable)=false];
|
Validator validator = 1 [(gogoproto.nullable)=false];
|
||||||
bool signed_last_block = 2;
|
bool signed_last_block = 2;
|
||||||
|
int64 commit_round = 3;
|
||||||
}
|
}
|
||||||
|
|
||||||
message PubKey {
|
message PubKey {
|
||||||
|
@ -42,7 +42,8 @@ It has these top-level messages:
|
|||||||
BlockID
|
BlockID
|
||||||
PartSetHeader
|
PartSetHeader
|
||||||
Validator
|
Validator
|
||||||
SigningValidator
|
ValidatorUpdate
|
||||||
|
VoteInfo
|
||||||
PubKey
|
PubKey
|
||||||
Evidence
|
Evidence
|
||||||
*/
|
*/
|
||||||
@ -1970,15 +1971,15 @@ func TestValidatorMarshalTo(t *testing.T) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestSigningValidatorProto(t *testing.T) {
|
func TestValidatorUpdateProto(t *testing.T) {
|
||||||
seed := time.Now().UnixNano()
|
seed := time.Now().UnixNano()
|
||||||
popr := rand.New(rand.NewSource(seed))
|
popr := rand.New(rand.NewSource(seed))
|
||||||
p := NewPopulatedSigningValidator(popr, false)
|
p := NewPopulatedValidatorUpdate(popr, false)
|
||||||
dAtA, err := proto.Marshal(p)
|
dAtA, err := proto.Marshal(p)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
t.Fatalf("seed = %d, err = %v", seed, err)
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
}
|
}
|
||||||
msg := &SigningValidator{}
|
msg := &ValidatorUpdate{}
|
||||||
if err := proto.Unmarshal(dAtA, msg); err != nil {
|
if err := proto.Unmarshal(dAtA, msg); err != nil {
|
||||||
t.Fatalf("seed = %d, err = %v", seed, err)
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
}
|
}
|
||||||
@ -2001,10 +2002,10 @@ func TestSigningValidatorProto(t *testing.T) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestSigningValidatorMarshalTo(t *testing.T) {
|
func TestValidatorUpdateMarshalTo(t *testing.T) {
|
||||||
seed := time.Now().UnixNano()
|
seed := time.Now().UnixNano()
|
||||||
popr := rand.New(rand.NewSource(seed))
|
popr := rand.New(rand.NewSource(seed))
|
||||||
p := NewPopulatedSigningValidator(popr, false)
|
p := NewPopulatedValidatorUpdate(popr, false)
|
||||||
size := p.Size()
|
size := p.Size()
|
||||||
dAtA := make([]byte, size)
|
dAtA := make([]byte, size)
|
||||||
for i := range dAtA {
|
for i := range dAtA {
|
||||||
@ -2014,7 +2015,63 @@ func TestSigningValidatorMarshalTo(t *testing.T) {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
t.Fatalf("seed = %d, err = %v", seed, err)
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
}
|
}
|
||||||
msg := &SigningValidator{}
|
msg := &ValidatorUpdate{}
|
||||||
|
if err := proto.Unmarshal(dAtA, msg); err != nil {
|
||||||
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
|
}
|
||||||
|
for i := range dAtA {
|
||||||
|
dAtA[i] = byte(popr.Intn(256))
|
||||||
|
}
|
||||||
|
if !p.Equal(msg) {
|
||||||
|
t.Fatalf("seed = %d, %#v !Proto %#v", seed, msg, p)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestVoteInfoProto(t *testing.T) {
|
||||||
|
seed := time.Now().UnixNano()
|
||||||
|
popr := rand.New(rand.NewSource(seed))
|
||||||
|
p := NewPopulatedVoteInfo(popr, false)
|
||||||
|
dAtA, err := proto.Marshal(p)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
|
}
|
||||||
|
msg := &VoteInfo{}
|
||||||
|
if err := proto.Unmarshal(dAtA, msg); err != nil {
|
||||||
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
|
}
|
||||||
|
littlefuzz := make([]byte, len(dAtA))
|
||||||
|
copy(littlefuzz, dAtA)
|
||||||
|
for i := range dAtA {
|
||||||
|
dAtA[i] = byte(popr.Intn(256))
|
||||||
|
}
|
||||||
|
if !p.Equal(msg) {
|
||||||
|
t.Fatalf("seed = %d, %#v !Proto %#v", seed, msg, p)
|
||||||
|
}
|
||||||
|
if len(littlefuzz) > 0 {
|
||||||
|
fuzzamount := 100
|
||||||
|
for i := 0; i < fuzzamount; i++ {
|
||||||
|
littlefuzz[popr.Intn(len(littlefuzz))] = byte(popr.Intn(256))
|
||||||
|
littlefuzz = append(littlefuzz, byte(popr.Intn(256)))
|
||||||
|
}
|
||||||
|
// shouldn't panic
|
||||||
|
_ = proto.Unmarshal(littlefuzz, msg)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestVoteInfoMarshalTo(t *testing.T) {
|
||||||
|
seed := time.Now().UnixNano()
|
||||||
|
popr := rand.New(rand.NewSource(seed))
|
||||||
|
p := NewPopulatedVoteInfo(popr, false)
|
||||||
|
size := p.Size()
|
||||||
|
dAtA := make([]byte, size)
|
||||||
|
for i := range dAtA {
|
||||||
|
dAtA[i] = byte(popr.Intn(256))
|
||||||
|
}
|
||||||
|
_, err := p.MarshalTo(dAtA)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
|
}
|
||||||
|
msg := &VoteInfo{}
|
||||||
if err := proto.Unmarshal(dAtA, msg); err != nil {
|
if err := proto.Unmarshal(dAtA, msg); err != nil {
|
||||||
t.Fatalf("seed = %d, err = %v", seed, err)
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
}
|
}
|
||||||
@ -2750,16 +2807,34 @@ func TestValidatorJSON(t *testing.T) {
|
|||||||
t.Fatalf("seed = %d, %#v !Json Equal %#v", seed, msg, p)
|
t.Fatalf("seed = %d, %#v !Json Equal %#v", seed, msg, p)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
func TestSigningValidatorJSON(t *testing.T) {
|
func TestValidatorUpdateJSON(t *testing.T) {
|
||||||
seed := time.Now().UnixNano()
|
seed := time.Now().UnixNano()
|
||||||
popr := rand.New(rand.NewSource(seed))
|
popr := rand.New(rand.NewSource(seed))
|
||||||
p := NewPopulatedSigningValidator(popr, true)
|
p := NewPopulatedValidatorUpdate(popr, true)
|
||||||
marshaler := jsonpb.Marshaler{}
|
marshaler := jsonpb.Marshaler{}
|
||||||
jsondata, err := marshaler.MarshalToString(p)
|
jsondata, err := marshaler.MarshalToString(p)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
t.Fatalf("seed = %d, err = %v", seed, err)
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
}
|
}
|
||||||
msg := &SigningValidator{}
|
msg := &ValidatorUpdate{}
|
||||||
|
err = jsonpb.UnmarshalString(jsondata, msg)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
|
}
|
||||||
|
if !p.Equal(msg) {
|
||||||
|
t.Fatalf("seed = %d, %#v !Json Equal %#v", seed, msg, p)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
func TestVoteInfoJSON(t *testing.T) {
|
||||||
|
seed := time.Now().UnixNano()
|
||||||
|
popr := rand.New(rand.NewSource(seed))
|
||||||
|
p := NewPopulatedVoteInfo(popr, true)
|
||||||
|
marshaler := jsonpb.Marshaler{}
|
||||||
|
jsondata, err := marshaler.MarshalToString(p)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
|
}
|
||||||
|
msg := &VoteInfo{}
|
||||||
err = jsonpb.UnmarshalString(jsondata, msg)
|
err = jsonpb.UnmarshalString(jsondata, msg)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
t.Fatalf("seed = %d, err = %v", seed, err)
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
@ -3756,12 +3831,12 @@ func TestValidatorProtoCompactText(t *testing.T) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestSigningValidatorProtoText(t *testing.T) {
|
func TestValidatorUpdateProtoText(t *testing.T) {
|
||||||
seed := time.Now().UnixNano()
|
seed := time.Now().UnixNano()
|
||||||
popr := rand.New(rand.NewSource(seed))
|
popr := rand.New(rand.NewSource(seed))
|
||||||
p := NewPopulatedSigningValidator(popr, true)
|
p := NewPopulatedValidatorUpdate(popr, true)
|
||||||
dAtA := proto.MarshalTextString(p)
|
dAtA := proto.MarshalTextString(p)
|
||||||
msg := &SigningValidator{}
|
msg := &ValidatorUpdate{}
|
||||||
if err := proto.UnmarshalText(dAtA, msg); err != nil {
|
if err := proto.UnmarshalText(dAtA, msg); err != nil {
|
||||||
t.Fatalf("seed = %d, err = %v", seed, err)
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
}
|
}
|
||||||
@ -3770,12 +3845,40 @@ func TestSigningValidatorProtoText(t *testing.T) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestSigningValidatorProtoCompactText(t *testing.T) {
|
func TestValidatorUpdateProtoCompactText(t *testing.T) {
|
||||||
seed := time.Now().UnixNano()
|
seed := time.Now().UnixNano()
|
||||||
popr := rand.New(rand.NewSource(seed))
|
popr := rand.New(rand.NewSource(seed))
|
||||||
p := NewPopulatedSigningValidator(popr, true)
|
p := NewPopulatedValidatorUpdate(popr, true)
|
||||||
dAtA := proto.CompactTextString(p)
|
dAtA := proto.CompactTextString(p)
|
||||||
msg := &SigningValidator{}
|
msg := &ValidatorUpdate{}
|
||||||
|
if err := proto.UnmarshalText(dAtA, msg); err != nil {
|
||||||
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
|
}
|
||||||
|
if !p.Equal(msg) {
|
||||||
|
t.Fatalf("seed = %d, %#v !Proto %#v", seed, msg, p)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestVoteInfoProtoText(t *testing.T) {
|
||||||
|
seed := time.Now().UnixNano()
|
||||||
|
popr := rand.New(rand.NewSource(seed))
|
||||||
|
p := NewPopulatedVoteInfo(popr, true)
|
||||||
|
dAtA := proto.MarshalTextString(p)
|
||||||
|
msg := &VoteInfo{}
|
||||||
|
if err := proto.UnmarshalText(dAtA, msg); err != nil {
|
||||||
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
|
}
|
||||||
|
if !p.Equal(msg) {
|
||||||
|
t.Fatalf("seed = %d, %#v !Proto %#v", seed, msg, p)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestVoteInfoProtoCompactText(t *testing.T) {
|
||||||
|
seed := time.Now().UnixNano()
|
||||||
|
popr := rand.New(rand.NewSource(seed))
|
||||||
|
p := NewPopulatedVoteInfo(popr, true)
|
||||||
|
dAtA := proto.CompactTextString(p)
|
||||||
|
msg := &VoteInfo{}
|
||||||
if err := proto.UnmarshalText(dAtA, msg); err != nil {
|
if err := proto.UnmarshalText(dAtA, msg); err != nil {
|
||||||
t.Fatalf("seed = %d, err = %v", seed, err)
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
}
|
}
|
||||||
@ -4588,10 +4691,32 @@ func TestValidatorSize(t *testing.T) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestSigningValidatorSize(t *testing.T) {
|
func TestValidatorUpdateSize(t *testing.T) {
|
||||||
seed := time.Now().UnixNano()
|
seed := time.Now().UnixNano()
|
||||||
popr := rand.New(rand.NewSource(seed))
|
popr := rand.New(rand.NewSource(seed))
|
||||||
p := NewPopulatedSigningValidator(popr, true)
|
p := NewPopulatedValidatorUpdate(popr, true)
|
||||||
|
size2 := proto.Size(p)
|
||||||
|
dAtA, err := proto.Marshal(p)
|
||||||
|
if err != nil {
|
||||||
|
t.Fatalf("seed = %d, err = %v", seed, err)
|
||||||
|
}
|
||||||
|
size := p.Size()
|
||||||
|
if len(dAtA) != size {
|
||||||
|
t.Errorf("seed = %d, size %v != marshalled size %v", seed, size, len(dAtA))
|
||||||
|
}
|
||||||
|
if size2 != size {
|
||||||
|
t.Errorf("seed = %d, size %v != before marshal proto.Size %v", seed, size, size2)
|
||||||
|
}
|
||||||
|
size3 := proto.Size(p)
|
||||||
|
if size3 != size {
|
||||||
|
t.Errorf("seed = %d, size %v != after marshal proto.Size %v", seed, size, size3)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestVoteInfoSize(t *testing.T) {
|
||||||
|
seed := time.Now().UnixNano()
|
||||||
|
popr := rand.New(rand.NewSource(seed))
|
||||||
|
p := NewPopulatedVoteInfo(popr, true)
|
||||||
size2 := proto.Size(p)
|
size2 := proto.Size(p)
|
||||||
dAtA, err := proto.Marshal(p)
|
dAtA, err := proto.Marshal(p)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -2,58 +2,33 @@ package types
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
"bytes"
|
||||||
"encoding/json"
|
|
||||||
"sort"
|
"sort"
|
||||||
|
|
||||||
cmn "github.com/tendermint/tendermint/libs/common"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
//------------------------------------------------------------------------------
|
//------------------------------------------------------------------------------
|
||||||
|
|
||||||
// Validators is a list of validators that implements the Sort interface
|
// ValidatorUpdates is a list of validators that implements the Sort interface
|
||||||
type Validators []Validator
|
type ValidatorUpdates []ValidatorUpdate
|
||||||
|
|
||||||
var _ sort.Interface = (Validators)(nil)
|
var _ sort.Interface = (ValidatorUpdates)(nil)
|
||||||
|
|
||||||
// All these methods for Validators:
|
// All these methods for ValidatorUpdates:
|
||||||
// Len, Less and Swap
|
// Len, Less and Swap
|
||||||
// are for Validators to implement sort.Interface
|
// are for ValidatorUpdates to implement sort.Interface
|
||||||
// which will be used by the sort package.
|
// which will be used by the sort package.
|
||||||
// See Issue https://github.com/tendermint/abci/issues/212
|
// See Issue https://github.com/tendermint/abci/issues/212
|
||||||
|
|
||||||
func (v Validators) Len() int {
|
func (v ValidatorUpdates) Len() int {
|
||||||
return len(v)
|
return len(v)
|
||||||
}
|
}
|
||||||
|
|
||||||
// XXX: doesn't distinguish same validator with different power
|
// XXX: doesn't distinguish same validator with different power
|
||||||
func (v Validators) Less(i, j int) bool {
|
func (v ValidatorUpdates) Less(i, j int) bool {
|
||||||
return bytes.Compare(v[i].PubKey.Data, v[j].PubKey.Data) <= 0
|
return bytes.Compare(v[i].PubKey.Data, v[j].PubKey.Data) <= 0
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v Validators) Swap(i, j int) {
|
func (v ValidatorUpdates) Swap(i, j int) {
|
||||||
v1 := v[i]
|
v1 := v[i]
|
||||||
v[i] = v[j]
|
v[i] = v[j]
|
||||||
v[j] = v1
|
v[j] = v1
|
||||||
}
|
}
|
||||||
|
|
||||||
func ValidatorsString(vs Validators) string {
|
|
||||||
s := make([]validatorPretty, len(vs))
|
|
||||||
for i, v := range vs {
|
|
||||||
s[i] = validatorPretty{
|
|
||||||
Address: v.Address,
|
|
||||||
PubKey: v.PubKey.Data,
|
|
||||||
Power: v.Power,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
b, err := json.Marshal(s)
|
|
||||||
if err != nil {
|
|
||||||
panic(err.Error())
|
|
||||||
}
|
|
||||||
return string(b)
|
|
||||||
}
|
|
||||||
|
|
||||||
type validatorPretty struct {
|
|
||||||
Address cmn.HexBytes `json:"address"`
|
|
||||||
PubKey []byte `json:"pub_key"`
|
|
||||||
Power int64 `json:"power"`
|
|
||||||
}
|
|
||||||
|
@ -354,7 +354,7 @@ func randConsensusNet(nValidators int, testName string, tickerFunc func() Timeou
|
|||||||
}
|
}
|
||||||
ensureDir(path.Dir(thisConfig.Consensus.WalFile()), 0700) // dir for wal
|
ensureDir(path.Dir(thisConfig.Consensus.WalFile()), 0700) // dir for wal
|
||||||
app := appFunc()
|
app := appFunc()
|
||||||
vals := types.TM2PB.Validators(state.Validators)
|
vals := types.TM2PB.ValidatorUpdates(state.Validators)
|
||||||
app.InitChain(abci.RequestInitChain{Validators: vals})
|
app.InitChain(abci.RequestInitChain{Validators: vals})
|
||||||
|
|
||||||
css[i] = newConsensusStateWithConfig(thisConfig, state, privVals[i], app)
|
css[i] = newConsensusStateWithConfig(thisConfig, state, privVals[i], app)
|
||||||
@ -386,7 +386,7 @@ func randConsensusNetWithPeers(nValidators, nPeers int, testName string, tickerF
|
|||||||
}
|
}
|
||||||
|
|
||||||
app := appFunc()
|
app := appFunc()
|
||||||
vals := types.TM2PB.Validators(state.Validators)
|
vals := types.TM2PB.ValidatorUpdates(state.Validators)
|
||||||
app.InitChain(abci.RequestInitChain{Validators: vals})
|
app.InitChain(abci.RequestInitChain{Validators: vals})
|
||||||
|
|
||||||
css[i] = newConsensusStateWithConfig(thisConfig, state, privVal, app)
|
css[i] = newConsensusStateWithConfig(thisConfig, state, privVal, app)
|
||||||
|
@ -118,7 +118,7 @@ func TestReactorWithEvidence(t *testing.T) {
|
|||||||
thisConfig := ResetConfig(fmt.Sprintf("%s_%d", testName, i))
|
thisConfig := ResetConfig(fmt.Sprintf("%s_%d", testName, i))
|
||||||
ensureDir(path.Dir(thisConfig.Consensus.WalFile()), 0700) // dir for wal
|
ensureDir(path.Dir(thisConfig.Consensus.WalFile()), 0700) // dir for wal
|
||||||
app := appFunc()
|
app := appFunc()
|
||||||
vals := types.TM2PB.Validators(state.Validators)
|
vals := types.TM2PB.ValidatorUpdates(state.Validators)
|
||||||
app.InitChain(abci.RequestInitChain{Validators: vals})
|
app.InitChain(abci.RequestInitChain{Validators: vals})
|
||||||
|
|
||||||
pv := privVals[i]
|
pv := privVals[i]
|
||||||
|
@ -266,7 +266,7 @@ func (h *Handshaker) ReplayBlocks(state sm.State, appHash []byte, appBlockHeight
|
|||||||
|
|
||||||
// If appBlockHeight == 0 it means that we are at genesis and hence should send InitChain.
|
// If appBlockHeight == 0 it means that we are at genesis and hence should send InitChain.
|
||||||
if appBlockHeight == 0 {
|
if appBlockHeight == 0 {
|
||||||
nextVals := types.TM2PB.Validators(state.NextValidators) // state.Validators would work too.
|
nextVals := types.TM2PB.ValidatorUpdates(state.NextValidators) // state.Validators would work too.
|
||||||
csParams := types.TM2PB.ConsensusParams(h.genDoc.ConsensusParams)
|
csParams := types.TM2PB.ConsensusParams(h.genDoc.ConsensusParams)
|
||||||
req := abci.RequestInitChain{
|
req := abci.RequestInitChain{
|
||||||
Time: h.genDoc.GenesisTime,
|
Time: h.genDoc.GenesisTime,
|
||||||
@ -282,7 +282,7 @@ func (h *Handshaker) ReplayBlocks(state sm.State, appHash []byte, appBlockHeight
|
|||||||
|
|
||||||
// If the app returned validators or consensus params, update the state.
|
// If the app returned validators or consensus params, update the state.
|
||||||
if len(res.Validators) > 0 {
|
if len(res.Validators) > 0 {
|
||||||
vals, err := types.PB2TM.Validators(res.Validators)
|
vals, err := types.PB2TM.ValidatorUpdates(res.Validators)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
@ -416,7 +416,7 @@ func buildAppStateFromChain(proxyApp proxy.AppConns, stateDB dbm.DB,
|
|||||||
}
|
}
|
||||||
defer proxyApp.Stop()
|
defer proxyApp.Stop()
|
||||||
|
|
||||||
validators := types.TM2PB.Validators(state.Validators)
|
validators := types.TM2PB.ValidatorUpdates(state.Validators)
|
||||||
if _, err := proxyApp.Consensus().InitChainSync(abci.RequestInitChain{
|
if _, err := proxyApp.Consensus().InitChainSync(abci.RequestInitChain{
|
||||||
Validators: validators,
|
Validators: validators,
|
||||||
}); err != nil {
|
}); err != nil {
|
||||||
@ -453,7 +453,7 @@ func buildTMStateFromChain(config *cfg.Config, stateDB dbm.DB, state sm.State, c
|
|||||||
}
|
}
|
||||||
defer proxyApp.Stop()
|
defer proxyApp.Stop()
|
||||||
|
|
||||||
validators := types.TM2PB.Validators(state.Validators)
|
validators := types.TM2PB.ValidatorUpdates(state.Validators)
|
||||||
if _, err := proxyApp.Consensus().InitChainSync(abci.RequestInitChain{
|
if _, err := proxyApp.Consensus().InitChainSync(abci.RequestInitChain{
|
||||||
Validators: validators,
|
Validators: validators,
|
||||||
}); err != nil {
|
}); err != nil {
|
||||||
@ -639,7 +639,7 @@ func (bs *mockBlockStore) LoadSeenCommit(height int64) *types.Commit {
|
|||||||
func TestInitChainUpdateValidators(t *testing.T) {
|
func TestInitChainUpdateValidators(t *testing.T) {
|
||||||
val, _ := types.RandValidator(true, 10)
|
val, _ := types.RandValidator(true, 10)
|
||||||
vals := types.NewValidatorSet([]*types.Validator{val})
|
vals := types.NewValidatorSet([]*types.Validator{val})
|
||||||
app := &initChainApp{vals: types.TM2PB.Validators(vals)}
|
app := &initChainApp{vals: types.TM2PB.ValidatorUpdates(vals)}
|
||||||
clientCreator := proxy.NewLocalClientCreator(app)
|
clientCreator := proxy.NewLocalClientCreator(app)
|
||||||
|
|
||||||
config := ResetConfig("proxy_test_")
|
config := ResetConfig("proxy_test_")
|
||||||
@ -666,7 +666,7 @@ func TestInitChainUpdateValidators(t *testing.T) {
|
|||||||
assert.Equal(t, newValAddr, expectValAddr)
|
assert.Equal(t, newValAddr, expectValAddr)
|
||||||
}
|
}
|
||||||
|
|
||||||
func newInitChainApp(vals []abci.Validator) *initChainApp {
|
func newInitChainApp(vals []abci.ValidatorUpdate) *initChainApp {
|
||||||
return &initChainApp{
|
return &initChainApp{
|
||||||
vals: vals,
|
vals: vals,
|
||||||
}
|
}
|
||||||
@ -675,7 +675,7 @@ func newInitChainApp(vals []abci.Validator) *initChainApp {
|
|||||||
// returns the vals on InitChain
|
// returns the vals on InitChain
|
||||||
type initChainApp struct {
|
type initChainApp struct {
|
||||||
abci.BaseApplication
|
abci.BaseApplication
|
||||||
vals []abci.Validator
|
vals []abci.ValidatorUpdate
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ica *initChainApp) InitChain(req abci.RequestInitChain) abci.ResponseInitChain {
|
func (ica *initChainApp) InitChain(req abci.RequestInitChain) abci.ResponseInitChain {
|
||||||
|
@ -184,15 +184,14 @@ func execBlockOnProxyApp(logger log.Logger, proxyAppConn proxy.AppConnConsensus,
|
|||||||
}
|
}
|
||||||
proxyAppConn.SetResponseCallback(proxyCb)
|
proxyAppConn.SetResponseCallback(proxyCb)
|
||||||
|
|
||||||
signVals, byzVals := getBeginBlockValidatorInfo(block, lastValSet, stateDB)
|
voteInfos, byzVals := getBeginBlockValidatorInfo(block, lastValSet, stateDB)
|
||||||
|
|
||||||
// Begin block.
|
// Begin block.
|
||||||
_, err := proxyAppConn.BeginBlockSync(abci.RequestBeginBlock{
|
_, err := proxyAppConn.BeginBlockSync(abci.RequestBeginBlock{
|
||||||
Hash: block.Hash(),
|
Hash: block.Hash(),
|
||||||
Header: types.TM2PB.Header(&block.Header),
|
Header: types.TM2PB.Header(&block.Header),
|
||||||
LastCommitInfo: abci.LastCommitInfo{
|
LastCommitInfo: abci.LastCommitInfo{
|
||||||
CommitRound: int32(block.LastCommit.Round()),
|
CommitVotes: voteInfos,
|
||||||
Validators: signVals,
|
|
||||||
},
|
},
|
||||||
ByzantineValidators: byzVals,
|
ByzantineValidators: byzVals,
|
||||||
})
|
})
|
||||||
@ -218,15 +217,15 @@ func execBlockOnProxyApp(logger log.Logger, proxyAppConn proxy.AppConnConsensus,
|
|||||||
|
|
||||||
logger.Info("Executed block", "height", block.Height, "validTxs", validTxs, "invalidTxs", invalidTxs)
|
logger.Info("Executed block", "height", block.Height, "validTxs", validTxs, "invalidTxs", invalidTxs)
|
||||||
|
|
||||||
valUpdates := abciResponses.EndBlock.ValidatorUpdates
|
if len(abciResponses.EndBlock.ValidatorUpdates) > 0 {
|
||||||
if len(valUpdates) > 0 {
|
// TODO: cleanup the formatting
|
||||||
logger.Info("Updates to validators", "updates", abci.ValidatorsString(valUpdates))
|
logger.Info("Updates to validators", "updates", abciResponses.EndBlock.ValidatorUpdates)
|
||||||
}
|
}
|
||||||
|
|
||||||
return abciResponses, nil
|
return abciResponses, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func getBeginBlockValidatorInfo(block *types.Block, lastValSet *types.ValidatorSet, stateDB dbm.DB) ([]abci.SigningValidator, []abci.Evidence) {
|
func getBeginBlockValidatorInfo(block *types.Block, lastValSet *types.ValidatorSet, stateDB dbm.DB) ([]abci.VoteInfo, []abci.Evidence) {
|
||||||
|
|
||||||
// Sanity check that commit length matches validator set size -
|
// Sanity check that commit length matches validator set size -
|
||||||
// only applies after first block
|
// only applies after first block
|
||||||
@ -241,17 +240,22 @@ func getBeginBlockValidatorInfo(block *types.Block, lastValSet *types.ValidatorS
|
|||||||
}
|
}
|
||||||
|
|
||||||
// determine which validators did not sign last block.
|
// determine which validators did not sign last block.
|
||||||
signVals := make([]abci.SigningValidator, len(lastValSet.Validators))
|
voteInfos := make([]abci.VoteInfo, len(lastValSet.Validators))
|
||||||
for i, val := range lastValSet.Validators {
|
for i, val := range lastValSet.Validators {
|
||||||
var vote *types.Vote
|
var vote *types.Vote
|
||||||
|
var commitRound = -1
|
||||||
if i < len(block.LastCommit.Precommits) {
|
if i < len(block.LastCommit.Precommits) {
|
||||||
vote = block.LastCommit.Precommits[i]
|
vote = block.LastCommit.Precommits[i]
|
||||||
|
if vote != nil {
|
||||||
|
commitRound = vote.Round
|
||||||
|
}
|
||||||
}
|
}
|
||||||
val := abci.SigningValidator{
|
voteInfo := abci.VoteInfo{
|
||||||
Validator: types.TM2PB.ValidatorWithoutPubKey(val),
|
Validator: types.TM2PB.Validator(val),
|
||||||
SignedLastBlock: vote != nil,
|
SignedLastBlock: vote != nil, // XXX: should we replace with commitRound == -1 ?
|
||||||
|
CommitRound: int64(commitRound), //XXX: why is round an int?
|
||||||
}
|
}
|
||||||
signVals[i] = val
|
voteInfos[i] = voteInfo
|
||||||
}
|
}
|
||||||
|
|
||||||
byzVals := make([]abci.Evidence, len(block.Evidence.Evidence))
|
byzVals := make([]abci.Evidence, len(block.Evidence.Evidence))
|
||||||
@ -266,15 +270,15 @@ func getBeginBlockValidatorInfo(block *types.Block, lastValSet *types.ValidatorS
|
|||||||
byzVals[i] = types.TM2PB.Evidence(ev, valset, block.Time)
|
byzVals[i] = types.TM2PB.Evidence(ev, valset, block.Time)
|
||||||
}
|
}
|
||||||
|
|
||||||
return signVals, byzVals
|
return voteInfos, byzVals
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// If more or equal than 1/3 of total voting power changed in one block, then
|
// If more or equal than 1/3 of total voting power changed in one block, then
|
||||||
// a light client could never prove the transition externally. See
|
// a light client could never prove the transition externally. See
|
||||||
// ./lite/doc.go for details on how a light client tracks validators.
|
// ./lite/doc.go for details on how a light client tracks validators.
|
||||||
func updateValidators(currentSet *types.ValidatorSet, abciUpdates []abci.Validator) error {
|
func updateValidators(currentSet *types.ValidatorSet, abciUpdates []abci.ValidatorUpdate) error {
|
||||||
updates, err := types.PB2TM.Validators(abciUpdates)
|
updates, err := types.PB2TM.ValidatorUpdates(abciUpdates)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -86,7 +86,7 @@ func TestBeginBlockValidators(t *testing.T) {
|
|||||||
|
|
||||||
// -> app receives a list of validators with a bool indicating if they signed
|
// -> app receives a list of validators with a bool indicating if they signed
|
||||||
ctr := 0
|
ctr := 0
|
||||||
for i, v := range app.Validators {
|
for i, v := range app.CommitVotes {
|
||||||
if ctr < len(tc.expectedAbsentValidators) &&
|
if ctr < len(tc.expectedAbsentValidators) &&
|
||||||
tc.expectedAbsentValidators[ctr] == i {
|
tc.expectedAbsentValidators[ctr] == i {
|
||||||
|
|
||||||
@ -160,7 +160,7 @@ func TestUpdateValidators(t *testing.T) {
|
|||||||
name string
|
name string
|
||||||
|
|
||||||
currentSet *types.ValidatorSet
|
currentSet *types.ValidatorSet
|
||||||
abciUpdates []abci.Validator
|
abciUpdates []abci.ValidatorUpdate
|
||||||
|
|
||||||
resultingSet *types.ValidatorSet
|
resultingSet *types.ValidatorSet
|
||||||
shouldErr bool
|
shouldErr bool
|
||||||
@ -169,7 +169,7 @@ func TestUpdateValidators(t *testing.T) {
|
|||||||
"adding a validator is OK",
|
"adding a validator is OK",
|
||||||
|
|
||||||
types.NewValidatorSet([]*types.Validator{val1}),
|
types.NewValidatorSet([]*types.Validator{val1}),
|
||||||
[]abci.Validator{{Address: []byte{}, PubKey: types.TM2PB.PubKey(pubkey2), Power: 20}},
|
[]abci.ValidatorUpdate{{PubKey: types.TM2PB.PubKey(pubkey2), Power: 20}},
|
||||||
|
|
||||||
types.NewValidatorSet([]*types.Validator{val1, val2}),
|
types.NewValidatorSet([]*types.Validator{val1, val2}),
|
||||||
false,
|
false,
|
||||||
@ -178,7 +178,7 @@ func TestUpdateValidators(t *testing.T) {
|
|||||||
"updating a validator is OK",
|
"updating a validator is OK",
|
||||||
|
|
||||||
types.NewValidatorSet([]*types.Validator{val1}),
|
types.NewValidatorSet([]*types.Validator{val1}),
|
||||||
[]abci.Validator{{Address: []byte{}, PubKey: types.TM2PB.PubKey(pubkey1), Power: 20}},
|
[]abci.ValidatorUpdate{{PubKey: types.TM2PB.PubKey(pubkey1), Power: 20}},
|
||||||
|
|
||||||
types.NewValidatorSet([]*types.Validator{types.NewValidator(pubkey1, 20)}),
|
types.NewValidatorSet([]*types.Validator{types.NewValidator(pubkey1, 20)}),
|
||||||
false,
|
false,
|
||||||
@ -187,7 +187,7 @@ func TestUpdateValidators(t *testing.T) {
|
|||||||
"removing a validator is OK",
|
"removing a validator is OK",
|
||||||
|
|
||||||
types.NewValidatorSet([]*types.Validator{val1, val2}),
|
types.NewValidatorSet([]*types.Validator{val1, val2}),
|
||||||
[]abci.Validator{{Address: []byte{}, PubKey: types.TM2PB.PubKey(pubkey2), Power: 0}},
|
[]abci.ValidatorUpdate{{PubKey: types.TM2PB.PubKey(pubkey2), Power: 0}},
|
||||||
|
|
||||||
types.NewValidatorSet([]*types.Validator{val1}),
|
types.NewValidatorSet([]*types.Validator{val1}),
|
||||||
false,
|
false,
|
||||||
@ -197,7 +197,7 @@ func TestUpdateValidators(t *testing.T) {
|
|||||||
"removing a non-existing validator results in error",
|
"removing a non-existing validator results in error",
|
||||||
|
|
||||||
types.NewValidatorSet([]*types.Validator{val1}),
|
types.NewValidatorSet([]*types.Validator{val1}),
|
||||||
[]abci.Validator{{Address: []byte{}, PubKey: types.TM2PB.PubKey(pubkey2), Power: 0}},
|
[]abci.ValidatorUpdate{{PubKey: types.TM2PB.PubKey(pubkey2), Power: 0}},
|
||||||
|
|
||||||
types.NewValidatorSet([]*types.Validator{val1}),
|
types.NewValidatorSet([]*types.Validator{val1}),
|
||||||
true,
|
true,
|
||||||
@ -207,7 +207,7 @@ func TestUpdateValidators(t *testing.T) {
|
|||||||
"adding a validator with negative power results in error",
|
"adding a validator with negative power results in error",
|
||||||
|
|
||||||
types.NewValidatorSet([]*types.Validator{val1}),
|
types.NewValidatorSet([]*types.Validator{val1}),
|
||||||
[]abci.Validator{{Address: []byte{}, PubKey: types.TM2PB.PubKey(pubkey2), Power: -100}},
|
[]abci.ValidatorUpdate{{PubKey: types.TM2PB.PubKey(pubkey2), Power: -100}},
|
||||||
|
|
||||||
types.NewValidatorSet([]*types.Validator{val1}),
|
types.NewValidatorSet([]*types.Validator{val1}),
|
||||||
true,
|
true,
|
||||||
@ -335,7 +335,7 @@ func makeBlock(state State, height int64) *types.Block {
|
|||||||
type testApp struct {
|
type testApp struct {
|
||||||
abci.BaseApplication
|
abci.BaseApplication
|
||||||
|
|
||||||
Validators []abci.SigningValidator
|
CommitVotes []abci.VoteInfo
|
||||||
ByzantineValidators []abci.Evidence
|
ByzantineValidators []abci.Evidence
|
||||||
ValidatorUpdates []abci.Validator
|
ValidatorUpdates []abci.Validator
|
||||||
}
|
}
|
||||||
@ -347,7 +347,7 @@ func (app *testApp) Info(req abci.RequestInfo) (resInfo abci.ResponseInfo) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (app *testApp) BeginBlock(req abci.RequestBeginBlock) abci.ResponseBeginBlock {
|
func (app *testApp) BeginBlock(req abci.RequestBeginBlock) abci.ResponseBeginBlock {
|
||||||
app.Validators = req.LastCommitInfo.Validators
|
app.CommitVotes = req.LastCommitInfo.CommitVotes
|
||||||
app.ByzantineValidators = req.ByzantineValidators
|
app.ByzantineValidators = req.ByzantineValidators
|
||||||
return abci.ResponseBeginBlock{}
|
return abci.ResponseBeginBlock{}
|
||||||
}
|
}
|
||||||
|
@ -78,8 +78,8 @@ func TestABCIResponsesSaveLoad1(t *testing.T) {
|
|||||||
abciResponses := NewABCIResponses(block)
|
abciResponses := NewABCIResponses(block)
|
||||||
abciResponses.DeliverTx[0] = &abci.ResponseDeliverTx{Data: []byte("foo"), Tags: nil}
|
abciResponses.DeliverTx[0] = &abci.ResponseDeliverTx{Data: []byte("foo"), Tags: nil}
|
||||||
abciResponses.DeliverTx[1] = &abci.ResponseDeliverTx{Data: []byte("bar"), Log: "ok", Tags: nil}
|
abciResponses.DeliverTx[1] = &abci.ResponseDeliverTx{Data: []byte("bar"), Log: "ok", Tags: nil}
|
||||||
abciResponses.EndBlock = &abci.ResponseEndBlock{ValidatorUpdates: []abci.Validator{
|
abciResponses.EndBlock = &abci.ResponseEndBlock{ValidatorUpdates: []abci.ValidatorUpdate{
|
||||||
types.TM2PB.ValidatorFromPubKeyAndPower(ed25519.GenPrivKey().PubKey(), 10),
|
types.TM2PB.NewValidatorUpdate(ed25519.GenPrivKey().PubKey(), 10),
|
||||||
}}
|
}}
|
||||||
|
|
||||||
saveABCIResponses(stateDB, block.Height, abciResponses)
|
saveABCIResponses(stateDB, block.Height, abciResponses)
|
||||||
@ -454,9 +454,9 @@ func makeHeaderPartsResponsesValPubKeyChange(state State, height int64,
|
|||||||
_, val := state.NextValidators.GetByIndex(0)
|
_, val := state.NextValidators.GetByIndex(0)
|
||||||
if !bytes.Equal(pubkey.Bytes(), val.PubKey.Bytes()) {
|
if !bytes.Equal(pubkey.Bytes(), val.PubKey.Bytes()) {
|
||||||
abciResponses.EndBlock = &abci.ResponseEndBlock{
|
abciResponses.EndBlock = &abci.ResponseEndBlock{
|
||||||
ValidatorUpdates: []abci.Validator{
|
ValidatorUpdates: []abci.ValidatorUpdate{
|
||||||
types.TM2PB.ValidatorFromPubKeyAndPower(val.PubKey, 0),
|
types.TM2PB.NewValidatorUpdate(val.PubKey, 0),
|
||||||
types.TM2PB.ValidatorFromPubKeyAndPower(pubkey, 10),
|
types.TM2PB.NewValidatorUpdate(pubkey, 10),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -476,8 +476,8 @@ func makeHeaderPartsResponsesValPowerChange(state State, height int64,
|
|||||||
_, val := state.NextValidators.GetByIndex(0)
|
_, val := state.NextValidators.GetByIndex(0)
|
||||||
if val.VotingPower != power {
|
if val.VotingPower != power {
|
||||||
abciResponses.EndBlock = &abci.ResponseEndBlock{
|
abciResponses.EndBlock = &abci.ResponseEndBlock{
|
||||||
ValidatorUpdates: []abci.Validator{
|
ValidatorUpdates: []abci.ValidatorUpdate{
|
||||||
types.TM2PB.ValidatorFromPubKeyAndPower(val.PubKey, power),
|
types.TM2PB.NewValidatorUpdate(val.PubKey, power),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,7 +1,6 @@
|
|||||||
package types
|
package types
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"bytes"
|
|
||||||
"fmt"
|
"fmt"
|
||||||
"reflect"
|
"reflect"
|
||||||
"time"
|
"time"
|
||||||
@ -56,7 +55,7 @@ func (tm2pb) Header(header *Header) abci.Header {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (tm2pb) ValidatorWithoutPubKey(val *Validator) abci.Validator {
|
func (tm2pb) Validator(val *Validator) abci.Validator {
|
||||||
return abci.Validator{
|
return abci.Validator{
|
||||||
Address: val.PubKey.Address(),
|
Address: val.PubKey.Address(),
|
||||||
Power: val.VotingPower,
|
Power: val.VotingPower,
|
||||||
@ -78,11 +77,10 @@ func (tm2pb) PartSetHeader(header PartSetHeader) abci.PartSetHeader {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// XXX: panics on unknown pubkey type
|
// XXX: panics on unknown pubkey type
|
||||||
func (tm2pb) Validator(val *Validator) abci.Validator {
|
func (tm2pb) ValidatorUpdate(val *Validator) abci.ValidatorUpdate {
|
||||||
return abci.Validator{
|
return abci.ValidatorUpdate{
|
||||||
Address: val.PubKey.Address(),
|
PubKey: TM2PB.PubKey(val.PubKey),
|
||||||
PubKey: TM2PB.PubKey(val.PubKey),
|
Power: val.VotingPower,
|
||||||
Power: val.VotingPower,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -106,10 +104,10 @@ func (tm2pb) PubKey(pubKey crypto.PubKey) abci.PubKey {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// XXX: panics on nil or unknown pubkey type
|
// XXX: panics on nil or unknown pubkey type
|
||||||
func (tm2pb) Validators(vals *ValidatorSet) []abci.Validator {
|
func (tm2pb) ValidatorUpdates(vals *ValidatorSet) []abci.ValidatorUpdate {
|
||||||
validators := make([]abci.Validator, vals.Size())
|
validators := make([]abci.ValidatorUpdate, vals.Size())
|
||||||
for i, val := range vals.Validators {
|
for i, val := range vals.Validators {
|
||||||
validators[i] = TM2PB.Validator(val)
|
validators[i] = TM2PB.ValidatorUpdate(val)
|
||||||
}
|
}
|
||||||
return validators
|
return validators
|
||||||
}
|
}
|
||||||
@ -156,7 +154,7 @@ func (tm2pb) Evidence(ev Evidence, valSet *ValidatorSet, evTime time.Time) abci.
|
|||||||
|
|
||||||
return abci.Evidence{
|
return abci.Evidence{
|
||||||
Type: evType,
|
Type: evType,
|
||||||
Validator: TM2PB.ValidatorWithoutPubKey(val),
|
Validator: TM2PB.Validator(val),
|
||||||
Height: ev.Height(),
|
Height: ev.Height(),
|
||||||
Time: evTime,
|
Time: evTime,
|
||||||
TotalVotingPower: valSet.TotalVotingPower(),
|
TotalVotingPower: valSet.TotalVotingPower(),
|
||||||
@ -164,12 +162,11 @@ func (tm2pb) Evidence(ev Evidence, valSet *ValidatorSet, evTime time.Time) abci.
|
|||||||
}
|
}
|
||||||
|
|
||||||
// XXX: panics on nil or unknown pubkey type
|
// XXX: panics on nil or unknown pubkey type
|
||||||
func (tm2pb) ValidatorFromPubKeyAndPower(pubkey crypto.PubKey, power int64) abci.Validator {
|
func (tm2pb) NewValidatorUpdate(pubkey crypto.PubKey, power int64) abci.ValidatorUpdate {
|
||||||
pubkeyABCI := TM2PB.PubKey(pubkey)
|
pubkeyABCI := TM2PB.PubKey(pubkey)
|
||||||
return abci.Validator{
|
return abci.ValidatorUpdate{
|
||||||
Address: pubkey.Address(),
|
PubKey: pubkeyABCI,
|
||||||
PubKey: pubkeyABCI,
|
Power: power,
|
||||||
Power: power,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -205,7 +202,7 @@ func (pb2tm) PubKey(pubKey abci.PubKey) (crypto.PubKey, error) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (pb2tm) Validators(vals []abci.Validator) ([]*Validator, error) {
|
func (pb2tm) ValidatorUpdates(vals []abci.ValidatorUpdate) ([]*Validator, error) {
|
||||||
tmVals := make([]*Validator, len(vals))
|
tmVals := make([]*Validator, len(vals))
|
||||||
for i, v := range vals {
|
for i, v := range vals {
|
||||||
pub, err := PB2TM.PubKey(v.PubKey)
|
pub, err := PB2TM.PubKey(v.PubKey)
|
||||||
@ -214,17 +211,13 @@ func (pb2tm) Validators(vals []abci.Validator) ([]*Validator, error) {
|
|||||||
}
|
}
|
||||||
// If the app provided an address too, it must match.
|
// If the app provided an address too, it must match.
|
||||||
// This is just a sanity check.
|
// This is just a sanity check.
|
||||||
if len(v.Address) > 0 {
|
/*if len(v.Address) > 0 {
|
||||||
if !bytes.Equal(pub.Address(), v.Address) {
|
if !bytes.Equal(pub.Address(), v.Address) {
|
||||||
return nil, fmt.Errorf("Validator.Address (%X) does not match PubKey.Address (%X)",
|
return nil, fmt.Errorf("Validator.Address (%X) does not match PubKey.Address (%X)",
|
||||||
v.Address, pub.Address())
|
v.Address, pub.Address())
|
||||||
}
|
}
|
||||||
}
|
}*/
|
||||||
tmVals[i] = &Validator{
|
tmVals[i] = NewValidator(pub, v.Power)
|
||||||
Address: pub.Address(),
|
|
||||||
PubKey: pub,
|
|
||||||
VotingPower: v.Power,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return tmVals, nil
|
return tmVals, nil
|
||||||
}
|
}
|
||||||
|
@ -41,26 +41,26 @@ func TestABCIValidators(t *testing.T) {
|
|||||||
VotingPower: 10,
|
VotingPower: 10,
|
||||||
}
|
}
|
||||||
|
|
||||||
abciVal := TM2PB.Validator(tmVal)
|
abciVal := TM2PB.ValidatorUpdate(tmVal)
|
||||||
tmVals, err := PB2TM.Validators([]abci.Validator{abciVal})
|
tmVals, err := PB2TM.ValidatorUpdates([]abci.ValidatorUpdate{abciVal})
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, tmValExpected, tmVals[0])
|
assert.Equal(t, tmValExpected, tmVals[0])
|
||||||
|
|
||||||
abciVals := TM2PB.Validators(NewValidatorSet(tmVals))
|
abciVals := TM2PB.ValidatorUpdates(NewValidatorSet(tmVals))
|
||||||
assert.Equal(t, []abci.Validator{abciVal}, abciVals)
|
assert.Equal(t, []abci.ValidatorUpdate{abciVal}, abciVals)
|
||||||
|
|
||||||
// val with address
|
// val with address
|
||||||
tmVal.Address = pkEd.Address()
|
tmVal.Address = pkEd.Address()
|
||||||
|
|
||||||
abciVal = TM2PB.Validator(tmVal)
|
abciVal = TM2PB.ValidatorUpdate(tmVal)
|
||||||
tmVals, err = PB2TM.Validators([]abci.Validator{abciVal})
|
tmVals, err = PB2TM.ValidatorUpdates([]abci.ValidatorUpdate{abciVal})
|
||||||
assert.Nil(t, err)
|
assert.Nil(t, err)
|
||||||
assert.Equal(t, tmValExpected, tmVals[0])
|
assert.Equal(t, tmValExpected, tmVals[0])
|
||||||
|
|
||||||
// val with incorrect address
|
// val with incorrect pubkey daya
|
||||||
abciVal = TM2PB.Validator(tmVal)
|
abciVal = TM2PB.ValidatorUpdate(tmVal)
|
||||||
abciVal.Address = []byte("incorrect!")
|
abciVal.PubKey.Data = []byte("incorrect!")
|
||||||
tmVals, err = PB2TM.Validators([]abci.Validator{abciVal})
|
tmVals, err = PB2TM.ValidatorUpdates([]abci.ValidatorUpdate{abciVal})
|
||||||
assert.NotNil(t, err)
|
assert.NotNil(t, err)
|
||||||
assert.Nil(t, tmVals)
|
assert.Nil(t, tmVals)
|
||||||
}
|
}
|
||||||
@ -104,9 +104,6 @@ func TestABCIEvidence(t *testing.T) {
|
|||||||
)
|
)
|
||||||
|
|
||||||
assert.Equal(t, "duplicate/vote", abciEv.Type)
|
assert.Equal(t, "duplicate/vote", abciEv.Type)
|
||||||
|
|
||||||
// test we do not send pubkeys
|
|
||||||
assert.Empty(t, abciEv.Validator.PubKey)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
type pubKeyEddie struct{}
|
type pubKeyEddie struct{}
|
||||||
@ -119,17 +116,17 @@ func (pubKeyEddie) Equals(crypto.PubKey) bool { return false }
|
|||||||
func TestABCIValidatorFromPubKeyAndPower(t *testing.T) {
|
func TestABCIValidatorFromPubKeyAndPower(t *testing.T) {
|
||||||
pubkey := ed25519.GenPrivKey().PubKey()
|
pubkey := ed25519.GenPrivKey().PubKey()
|
||||||
|
|
||||||
abciVal := TM2PB.ValidatorFromPubKeyAndPower(pubkey, 10)
|
abciVal := TM2PB.NewValidatorUpdate(pubkey, 10)
|
||||||
assert.Equal(t, int64(10), abciVal.Power)
|
assert.Equal(t, int64(10), abciVal.Power)
|
||||||
|
|
||||||
assert.Panics(t, func() { TM2PB.ValidatorFromPubKeyAndPower(nil, 10) })
|
assert.Panics(t, func() { TM2PB.NewValidatorUpdate(nil, 10) })
|
||||||
assert.Panics(t, func() { TM2PB.ValidatorFromPubKeyAndPower(pubKeyEddie{}, 10) })
|
assert.Panics(t, func() { TM2PB.NewValidatorUpdate(pubKeyEddie{}, 10) })
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestABCIValidatorWithoutPubKey(t *testing.T) {
|
func TestABCIValidatorWithoutPubKey(t *testing.T) {
|
||||||
pkEd := ed25519.GenPrivKey().PubKey()
|
pkEd := ed25519.GenPrivKey().PubKey()
|
||||||
|
|
||||||
abciVal := TM2PB.ValidatorWithoutPubKey(&Validator{
|
abciVal := TM2PB.Validator(&Validator{
|
||||||
Address: pkEd.Address(),
|
Address: pkEd.Address(),
|
||||||
PubKey: pkEd,
|
PubKey: pkEd,
|
||||||
VotingPower: 10,
|
VotingPower: 10,
|
||||||
|
Reference in New Issue
Block a user