mirror of
https://github.com/tendermint/tendermint.git
synced 2026-08-28 20:06:24 +00:00
Merge branch 'master' into marko/bringbackdocs
This commit is contained in:
@@ -24,7 +24,7 @@ jobs:
|
||||
with:
|
||||
go-version: "1.17"
|
||||
- uses: actions/checkout@v3
|
||||
- uses: technote-space/get-diff-action@v6.0.1
|
||||
- uses: technote-space/get-diff-action@v6
|
||||
with:
|
||||
PATTERNS: |
|
||||
**/**.go
|
||||
@@ -45,7 +45,7 @@ jobs:
|
||||
with:
|
||||
go-version: "1.17"
|
||||
- uses: actions/checkout@v3
|
||||
- uses: technote-space/get-diff-action@v6.0.1
|
||||
- uses: technote-space/get-diff-action@v6
|
||||
with:
|
||||
PATTERNS: |
|
||||
**/**.go
|
||||
@@ -67,7 +67,7 @@ jobs:
|
||||
with:
|
||||
go-version: "1.17"
|
||||
- uses: actions/checkout@v3
|
||||
- uses: technote-space/get-diff-action@v6.0.1
|
||||
- uses: technote-space/get-diff-action@v6
|
||||
with:
|
||||
PATTERNS: |
|
||||
**/**.go
|
||||
|
||||
@@ -11,7 +11,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
- uses: technote-space/get-diff-action@v6.0.1
|
||||
- uses: technote-space/get-diff-action@v6
|
||||
with:
|
||||
PATTERNS: |
|
||||
docs/architecture/**
|
||||
|
||||
@@ -18,7 +18,7 @@ jobs:
|
||||
with:
|
||||
go-version: '1.17'
|
||||
- uses: actions/checkout@v3
|
||||
- uses: technote-space/get-diff-action@v6.0.1
|
||||
- uses: technote-space/get-diff-action@v6
|
||||
with:
|
||||
PATTERNS: |
|
||||
**/**.go
|
||||
|
||||
@@ -21,7 +21,7 @@ jobs:
|
||||
- uses: actions/setup-go@v3
|
||||
with:
|
||||
go-version: '^1.17'
|
||||
- uses: technote-space/get-diff-action@v6.0.1
|
||||
- uses: technote-space/get-diff-action@v6
|
||||
with:
|
||||
PATTERNS: |
|
||||
**/**.go
|
||||
|
||||
@@ -12,7 +12,7 @@ jobs:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
- uses: technote-space/get-diff-action@v6.0.1
|
||||
- uses: technote-space/get-diff-action@v6
|
||||
with:
|
||||
PATTERNS: |
|
||||
**/**.md
|
||||
|
||||
@@ -20,7 +20,7 @@ jobs:
|
||||
with:
|
||||
go-version: "1.17"
|
||||
- uses: actions/checkout@v3
|
||||
- uses: technote-space/get-diff-action@v6.0.1
|
||||
- uses: technote-space/get-diff-action@v6
|
||||
with:
|
||||
PATTERNS: |
|
||||
**/**.go
|
||||
@@ -42,7 +42,7 @@ jobs:
|
||||
needs: tests
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
- uses: technote-space/get-diff-action@v6.0.1
|
||||
- uses: technote-space/get-diff-action@v6
|
||||
with:
|
||||
PATTERNS: |
|
||||
**/**.go
|
||||
|
||||
@@ -52,6 +52,9 @@ func dialerFunc(ctx context.Context, addr string) (net.Conn, error) {
|
||||
}
|
||||
|
||||
func (cli *grpcClient) OnStart(ctx context.Context) error {
|
||||
timer := time.NewTimer(0)
|
||||
defer timer.Stop()
|
||||
|
||||
RETRY_LOOP:
|
||||
for {
|
||||
conn, err := grpc.Dial(cli.addr,
|
||||
@@ -63,8 +66,13 @@ RETRY_LOOP:
|
||||
return err
|
||||
}
|
||||
cli.logger.Error(fmt.Sprintf("abci.grpcClient failed to connect to %v. Retrying...\n", cli.addr), "err", err)
|
||||
time.Sleep(time.Second * dialRetryIntervalSeconds)
|
||||
continue RETRY_LOOP
|
||||
timer.Reset(time.Second * dialRetryIntervalSeconds)
|
||||
select {
|
||||
case <-ctx.Done():
|
||||
return ctx.Err()
|
||||
case <-timer.C:
|
||||
continue RETRY_LOOP
|
||||
}
|
||||
}
|
||||
|
||||
cli.logger.Info("Dialed server. Waiting for echo.", "addr", cli.addr)
|
||||
@@ -82,7 +90,13 @@ RETRY_LOOP:
|
||||
}
|
||||
|
||||
cli.logger.Error("Echo failed", "err", err)
|
||||
time.Sleep(time.Second * echoRetryIntervalSeconds)
|
||||
timer.Reset(time.Second * echoRetryIntervalSeconds)
|
||||
select {
|
||||
case <-ctx.Done():
|
||||
return ctx.Err()
|
||||
case <-timer.C:
|
||||
continue ENSURE_CONNECTED
|
||||
}
|
||||
}
|
||||
|
||||
cli.client = client
|
||||
|
||||
@@ -64,6 +64,8 @@ func (cli *socketClient) OnStart(ctx context.Context) error {
|
||||
err error
|
||||
conn net.Conn
|
||||
)
|
||||
timer := time.NewTimer(0)
|
||||
defer timer.Stop()
|
||||
|
||||
for {
|
||||
conn, err = tmnet.Connect(cli.addr)
|
||||
@@ -73,8 +75,15 @@ func (cli *socketClient) OnStart(ctx context.Context) error {
|
||||
}
|
||||
cli.logger.Error(fmt.Sprintf("abci.socketClient failed to connect to %v. Retrying after %vs...",
|
||||
cli.addr, dialRetryIntervalSeconds), "err", err)
|
||||
time.Sleep(time.Second * dialRetryIntervalSeconds)
|
||||
continue
|
||||
|
||||
timer.Reset(time.Second * dialRetryIntervalSeconds)
|
||||
select {
|
||||
case <-ctx.Done():
|
||||
return ctx.Err()
|
||||
case <-timer.C:
|
||||
continue
|
||||
}
|
||||
|
||||
}
|
||||
cli.conn = conn
|
||||
|
||||
@@ -90,11 +99,7 @@ func (cli *socketClient) OnStop() {
|
||||
if cli.conn != nil {
|
||||
cli.conn.Close()
|
||||
}
|
||||
|
||||
// this timeout is arbitrary.
|
||||
ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second)
|
||||
defer cancel()
|
||||
cli.drainQueue(ctx)
|
||||
cli.drainQueue()
|
||||
}
|
||||
|
||||
// Error returns an error if the client was stopped abruptly.
|
||||
@@ -113,12 +118,6 @@ func (cli *socketClient) sendRequestsRoutine(ctx context.Context, conn io.Writer
|
||||
case <-ctx.Done():
|
||||
return
|
||||
case reqres := <-cli.reqQueue:
|
||||
if ctx.Err() != nil {
|
||||
return
|
||||
}
|
||||
|
||||
cli.willSendReq(reqres)
|
||||
|
||||
if err := types.WriteMessage(reqres.Request, bw); err != nil {
|
||||
cli.stopForError(fmt.Errorf("write to buffer: %w", err))
|
||||
return
|
||||
@@ -162,6 +161,11 @@ func (cli *socketClient) recvResponseRoutine(ctx context.Context, conn io.Reader
|
||||
func (cli *socketClient) willSendReq(reqres *requestAndResponse) {
|
||||
cli.mtx.Lock()
|
||||
defer cli.mtx.Unlock()
|
||||
|
||||
if !cli.IsRunning() {
|
||||
return
|
||||
}
|
||||
|
||||
cli.reqSent.PushBack(reqres)
|
||||
}
|
||||
|
||||
@@ -189,6 +193,47 @@ func (cli *socketClient) didRecvResponse(res *types.Response) error {
|
||||
|
||||
//----------------------------------------
|
||||
|
||||
func (cli *socketClient) doRequest(ctx context.Context, req *types.Request) (*types.Response, error) {
|
||||
if !cli.IsRunning() {
|
||||
return nil, errors.New("client has stopped")
|
||||
}
|
||||
|
||||
reqres := makeReqRes(req)
|
||||
cli.willSendReq(reqres)
|
||||
|
||||
select {
|
||||
case cli.reqQueue <- reqres:
|
||||
case <-ctx.Done():
|
||||
return nil, fmt.Errorf("can't queue req: %w", ctx.Err())
|
||||
}
|
||||
|
||||
select {
|
||||
case <-reqres.signal:
|
||||
if err := cli.Error(); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return reqres.Response, nil
|
||||
case <-ctx.Done():
|
||||
return nil, ctx.Err()
|
||||
}
|
||||
}
|
||||
|
||||
// drainQueue marks as complete and discards all remaining pending requests
|
||||
// from the queue.
|
||||
func (cli *socketClient) drainQueue() {
|
||||
cli.mtx.Lock()
|
||||
defer cli.mtx.Unlock()
|
||||
|
||||
// mark all in-flight messages as resolved (they will get cli.Error())
|
||||
for req := cli.reqSent.Front(); req != nil; req = req.Next() {
|
||||
reqres := req.Value.(*requestAndResponse)
|
||||
reqres.markDone()
|
||||
}
|
||||
}
|
||||
|
||||
//----------------------------------------
|
||||
|
||||
func (cli *socketClient) Flush(ctx context.Context) error {
|
||||
_, err := cli.doRequest(ctx, types.ToRequestFlush())
|
||||
if err != nil {
|
||||
@@ -319,58 +364,6 @@ func (cli *socketClient) FinalizeBlock(ctx context.Context, req types.RequestFin
|
||||
|
||||
//----------------------------------------
|
||||
|
||||
func (cli *socketClient) doRequest(ctx context.Context, req *types.Request) (*types.Response, error) {
|
||||
reqres := makeReqRes(req)
|
||||
|
||||
select {
|
||||
case cli.reqQueue <- reqres:
|
||||
case <-ctx.Done():
|
||||
return nil, fmt.Errorf("can't queue req: %w", ctx.Err())
|
||||
}
|
||||
|
||||
select {
|
||||
case <-reqres.signal:
|
||||
if err := cli.Error(); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return reqres.Response, nil
|
||||
case <-ctx.Done():
|
||||
return nil, ctx.Err()
|
||||
}
|
||||
}
|
||||
|
||||
// drainQueue marks as complete and discards all remaining pending requests
|
||||
// from the queue.
|
||||
func (cli *socketClient) drainQueue(ctx context.Context) {
|
||||
cli.mtx.Lock()
|
||||
defer cli.mtx.Unlock()
|
||||
|
||||
// mark all in-flight messages as resolved (they will get cli.Error())
|
||||
for req := cli.reqSent.Front(); req != nil; req = req.Next() {
|
||||
reqres := req.Value.(*requestAndResponse)
|
||||
reqres.markDone()
|
||||
}
|
||||
|
||||
// Mark all queued messages as resolved.
|
||||
//
|
||||
// TODO(creachadair): We can't simply range the channel, because it is never
|
||||
// closed, and the writer continues to add work.
|
||||
// See https://github.com/tendermint/tendermint/issues/6996.
|
||||
for {
|
||||
select {
|
||||
case <-ctx.Done():
|
||||
return
|
||||
case reqres := <-cli.reqQueue:
|
||||
reqres.markDone()
|
||||
default:
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//----------------------------------------
|
||||
|
||||
func resMatchesReq(req *types.Request, res *types.Response) (ok bool) {
|
||||
switch req.Value.(type) {
|
||||
case *types.Request_Echo:
|
||||
|
||||
@@ -1,14 +1,11 @@
|
||||
package kvstore
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
|
||||
dbm "github.com/tendermint/tm-db"
|
||||
|
||||
"github.com/tendermint/tendermint/abci/types"
|
||||
"github.com/tendermint/tendermint/libs/log"
|
||||
cryptoproto "github.com/tendermint/tendermint/proto/tendermint/crypto"
|
||||
ptypes "github.com/tendermint/tendermint/proto/tendermint/types"
|
||||
)
|
||||
|
||||
const (
|
||||
@@ -45,34 +42,3 @@ func (app *PersistentKVStoreApplication) OfferSnapshot(req types.RequestOfferSna
|
||||
func (app *PersistentKVStoreApplication) ApplySnapshotChunk(req types.RequestApplySnapshotChunk) types.ResponseApplySnapshotChunk {
|
||||
return types.ResponseApplySnapshotChunk{Result: types.ResponseApplySnapshotChunk_ABORT}
|
||||
}
|
||||
|
||||
func (app *PersistentKVStoreApplication) ExtendVote(req types.RequestExtendVote) types.ResponseExtendVote {
|
||||
return types.ResponseExtendVote{VoteExtension: ConstructVoteExtension(req.Vote.ValidatorAddress)}
|
||||
}
|
||||
|
||||
func (app *PersistentKVStoreApplication) VerifyVoteExtension(req types.RequestVerifyVoteExtension) types.ResponseVerifyVoteExtension {
|
||||
return types.RespondVerifyVoteExtension(app.verifyExtension(req.Vote.ValidatorAddress, req.Vote.VoteExtension))
|
||||
}
|
||||
|
||||
// -----------------------------
|
||||
|
||||
func ConstructVoteExtension(valAddr []byte) *ptypes.VoteExtension {
|
||||
return &ptypes.VoteExtension{
|
||||
AppDataToSign: valAddr,
|
||||
AppDataSelfAuthenticating: valAddr,
|
||||
}
|
||||
}
|
||||
|
||||
func (app *PersistentKVStoreApplication) verifyExtension(valAddr []byte, ext *ptypes.VoteExtension) bool {
|
||||
if ext == nil {
|
||||
return false
|
||||
}
|
||||
canonical := ConstructVoteExtension(valAddr)
|
||||
if !bytes.Equal(canonical.AppDataToSign, ext.AppDataToSign) {
|
||||
return false
|
||||
}
|
||||
if !bytes.Equal(canonical.AppDataSelfAuthenticating, ext.AppDataSelfAuthenticating) {
|
||||
return false
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
@@ -5,8 +5,6 @@ import (
|
||||
"encoding/json"
|
||||
|
||||
"github.com/gogo/protobuf/jsonpb"
|
||||
|
||||
types "github.com/tendermint/tendermint/proto/tendermint/types"
|
||||
)
|
||||
|
||||
const (
|
||||
@@ -157,15 +155,6 @@ var _ jsonRoundTripper = (*EventAttribute)(nil)
|
||||
// -----------------------------------------------
|
||||
// construct Result data
|
||||
|
||||
func RespondExtendVote(appDataToSign, appDataSelfAuthenticating []byte) ResponseExtendVote {
|
||||
return ResponseExtendVote{
|
||||
VoteExtension: &types.VoteExtension{
|
||||
AppDataToSign: appDataToSign,
|
||||
AppDataSelfAuthenticating: appDataSelfAuthenticating,
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
func RespondVerifyVoteExtension(ok bool) ResponseVerifyVoteExtension {
|
||||
status := ResponseVerifyVoteExtension_REJECT
|
||||
if ok {
|
||||
|
||||
+474
-308
@@ -1521,7 +1521,8 @@ func (m *RequestProcessProposal) GetProposerAddress() []byte {
|
||||
|
||||
// Extends a vote with application-side injection
|
||||
type RequestExtendVote struct {
|
||||
Vote *types1.Vote `protobuf:"bytes,1,opt,name=vote,proto3" json:"vote,omitempty"`
|
||||
Hash []byte `protobuf:"bytes,1,opt,name=hash,proto3" json:"hash,omitempty"`
|
||||
Height int64 `protobuf:"varint,2,opt,name=height,proto3" json:"height,omitempty"`
|
||||
}
|
||||
|
||||
func (m *RequestExtendVote) Reset() { *m = RequestExtendVote{} }
|
||||
@@ -1557,16 +1558,26 @@ func (m *RequestExtendVote) XXX_DiscardUnknown() {
|
||||
|
||||
var xxx_messageInfo_RequestExtendVote proto.InternalMessageInfo
|
||||
|
||||
func (m *RequestExtendVote) GetVote() *types1.Vote {
|
||||
func (m *RequestExtendVote) GetHash() []byte {
|
||||
if m != nil {
|
||||
return m.Vote
|
||||
return m.Hash
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (m *RequestExtendVote) GetHeight() int64 {
|
||||
if m != nil {
|
||||
return m.Height
|
||||
}
|
||||
return 0
|
||||
}
|
||||
|
||||
// Verify the vote extension
|
||||
type RequestVerifyVoteExtension struct {
|
||||
Vote *types1.Vote `protobuf:"bytes,1,opt,name=vote,proto3" json:"vote,omitempty"`
|
||||
Hash []byte `protobuf:"bytes,1,opt,name=hash,proto3" json:"hash,omitempty"`
|
||||
ValidatorAddress []byte `protobuf:"bytes,2,opt,name=validator_address,json=validatorAddress,proto3" json:"validator_address,omitempty"`
|
||||
Height int64 `protobuf:"varint,3,opt,name=height,proto3" json:"height,omitempty"`
|
||||
VoteExtension []byte `protobuf:"bytes,4,opt,name=vote_extension,json=voteExtension,proto3" json:"vote_extension,omitempty"`
|
||||
}
|
||||
|
||||
func (m *RequestVerifyVoteExtension) Reset() { *m = RequestVerifyVoteExtension{} }
|
||||
@@ -1602,9 +1613,30 @@ func (m *RequestVerifyVoteExtension) XXX_DiscardUnknown() {
|
||||
|
||||
var xxx_messageInfo_RequestVerifyVoteExtension proto.InternalMessageInfo
|
||||
|
||||
func (m *RequestVerifyVoteExtension) GetVote() *types1.Vote {
|
||||
func (m *RequestVerifyVoteExtension) GetHash() []byte {
|
||||
if m != nil {
|
||||
return m.Vote
|
||||
return m.Hash
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (m *RequestVerifyVoteExtension) GetValidatorAddress() []byte {
|
||||
if m != nil {
|
||||
return m.ValidatorAddress
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (m *RequestVerifyVoteExtension) GetHeight() int64 {
|
||||
if m != nil {
|
||||
return m.Height
|
||||
}
|
||||
return 0
|
||||
}
|
||||
|
||||
func (m *RequestVerifyVoteExtension) GetVoteExtension() []byte {
|
||||
if m != nil {
|
||||
return m.VoteExtension
|
||||
}
|
||||
return nil
|
||||
}
|
||||
@@ -3131,7 +3163,7 @@ func (m *ResponseProcessProposal) GetConsensusParamUpdates() *types1.ConsensusPa
|
||||
}
|
||||
|
||||
type ResponseExtendVote struct {
|
||||
VoteExtension *types1.VoteExtension `protobuf:"bytes,1,opt,name=vote_extension,json=voteExtension,proto3" json:"vote_extension,omitempty"`
|
||||
VoteExtension []byte `protobuf:"bytes,1,opt,name=vote_extension,json=voteExtension,proto3" json:"vote_extension,omitempty"`
|
||||
}
|
||||
|
||||
func (m *ResponseExtendVote) Reset() { *m = ResponseExtendVote{} }
|
||||
@@ -3167,7 +3199,7 @@ func (m *ResponseExtendVote) XXX_DiscardUnknown() {
|
||||
|
||||
var xxx_messageInfo_ResponseExtendVote proto.InternalMessageInfo
|
||||
|
||||
func (m *ResponseExtendVote) GetVoteExtension() *types1.VoteExtension {
|
||||
func (m *ResponseExtendVote) GetVoteExtension() []byte {
|
||||
if m != nil {
|
||||
return m.VoteExtension
|
||||
}
|
||||
@@ -3354,8 +3386,14 @@ func (m *CommitInfo) GetVotes() []VoteInfo {
|
||||
return nil
|
||||
}
|
||||
|
||||
// ExtendedCommitInfo is similar to CommitInfo except that it is only used in
|
||||
// the PrepareProposal request such that Tendermint can provide vote extensions
|
||||
// to the application.
|
||||
type ExtendedCommitInfo struct {
|
||||
Round int32 `protobuf:"varint,1,opt,name=round,proto3" json:"round,omitempty"`
|
||||
// The round at which the block proposer decided in the previous height.
|
||||
Round int32 `protobuf:"varint,1,opt,name=round,proto3" json:"round,omitempty"`
|
||||
// List of validators' addresses in the last validator set with their voting
|
||||
// information, including vote extensions.
|
||||
Votes []ExtendedVoteInfo `protobuf:"bytes,2,rep,name=votes,proto3" json:"votes"`
|
||||
}
|
||||
|
||||
@@ -3908,10 +3946,14 @@ func (m *VoteInfo) GetSignedLastBlock() bool {
|
||||
return false
|
||||
}
|
||||
|
||||
// ExtendedVoteInfo
|
||||
type ExtendedVoteInfo struct {
|
||||
Validator Validator `protobuf:"bytes,1,opt,name=validator,proto3" json:"validator"`
|
||||
SignedLastBlock bool `protobuf:"varint,2,opt,name=signed_last_block,json=signedLastBlock,proto3" json:"signed_last_block,omitempty"`
|
||||
VoteExtension []byte `protobuf:"bytes,3,opt,name=vote_extension,json=voteExtension,proto3" json:"vote_extension,omitempty"`
|
||||
// The validator that sent the vote.
|
||||
Validator Validator `protobuf:"bytes,1,opt,name=validator,proto3" json:"validator"`
|
||||
// Indicates whether the validator signed the last block, allowing for rewards based on validator availability.
|
||||
SignedLastBlock bool `protobuf:"varint,2,opt,name=signed_last_block,json=signedLastBlock,proto3" json:"signed_last_block,omitempty"`
|
||||
// Non-deterministic extension provided by the sending validator's application.
|
||||
VoteExtension []byte `protobuf:"bytes,3,opt,name=vote_extension,json=voteExtension,proto3" json:"vote_extension,omitempty"`
|
||||
}
|
||||
|
||||
func (m *ExtendedVoteInfo) Reset() { *m = ExtendedVoteInfo{} }
|
||||
@@ -4193,223 +4235,224 @@ func init() {
|
||||
func init() { proto.RegisterFile("tendermint/abci/types.proto", fileDescriptor_252557cfdd89a31a) }
|
||||
|
||||
var fileDescriptor_252557cfdd89a31a = []byte{
|
||||
// 3451 bytes of a gzipped FileDescriptorProto
|
||||
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xec, 0x5b, 0x4b, 0x73, 0x23, 0xd5,
|
||||
0xf5, 0xd7, 0xfb, 0x71, 0x64, 0x3d, 0x7c, 0x6d, 0x06, 0x8d, 0x98, 0xb1, 0x87, 0x9e, 0x02, 0x66,
|
||||
0x06, 0xf0, 0xf0, 0x9f, 0xf9, 0x0f, 0x0c, 0x01, 0x42, 0xd9, 0xb2, 0x8c, 0x3c, 0xe3, 0xb1, 0x4d,
|
||||
0x5b, 0x36, 0x45, 0x42, 0xa6, 0x69, 0xa9, 0xaf, 0xad, 0x66, 0x24, 0x75, 0xd3, 0xdd, 0x32, 0x32,
|
||||
0xcb, 0x50, 0x6c, 0xa8, 0x54, 0x85, 0x4d, 0x2a, 0xc9, 0x82, 0x5d, 0x52, 0x95, 0x7c, 0x83, 0xac,
|
||||
0xb2, 0xca, 0x82, 0x45, 0x16, 0xac, 0x92, 0x54, 0x16, 0x24, 0x05, 0xbb, 0x7c, 0x81, 0xec, 0x92,
|
||||
0xd4, 0x7d, 0xf4, 0x53, 0x6a, 0xa9, 0xc5, 0x00, 0x55, 0xa9, 0xb0, 0xd3, 0x3d, 0x7d, 0xce, 0xe9,
|
||||
0xbe, 0xf7, 0x9e, 0x7b, 0x1e, 0xbf, 0x73, 0x05, 0x8f, 0x59, 0x78, 0xa0, 0x60, 0xa3, 0xaf, 0x0e,
|
||||
0xac, 0xeb, 0x72, 0xbb, 0xa3, 0x5e, 0xb7, 0xce, 0x74, 0x6c, 0xae, 0xe9, 0x86, 0x66, 0x69, 0xa8,
|
||||
0xec, 0x3e, 0x5c, 0x23, 0x0f, 0x6b, 0x17, 0x3d, 0xdc, 0x1d, 0xe3, 0x4c, 0xb7, 0xb4, 0xeb, 0xba,
|
||||
0xa1, 0x69, 0xc7, 0x8c, 0xbf, 0x76, 0xc1, 0xf3, 0x98, 0xea, 0xf1, 0x6a, 0xf3, 0x3d, 0xe5, 0xc2,
|
||||
0x0f, 0xf0, 0x99, 0xfd, 0xf4, 0xe2, 0x98, 0xac, 0x2e, 0x1b, 0x72, 0xdf, 0x7e, 0xbc, 0x7a, 0xa2,
|
||||
0x69, 0x27, 0x3d, 0x7c, 0x9d, 0x8e, 0xda, 0xc3, 0xe3, 0xeb, 0x96, 0xda, 0xc7, 0xa6, 0x25, 0xf7,
|
||||
0x75, 0xce, 0xb0, 0x7c, 0xa2, 0x9d, 0x68, 0xf4, 0xe7, 0x75, 0xf2, 0x8b, 0x51, 0x85, 0x7f, 0x03,
|
||||
0x64, 0x45, 0xfc, 0xee, 0x10, 0x9b, 0x16, 0xba, 0x01, 0x29, 0xdc, 0xe9, 0x6a, 0xd5, 0xf8, 0xa5,
|
||||
0xf8, 0x95, 0xc2, 0x8d, 0x0b, 0x6b, 0x81, 0xc9, 0xad, 0x71, 0xbe, 0x46, 0xa7, 0xab, 0x35, 0x63,
|
||||
0x22, 0xe5, 0x45, 0xb7, 0x20, 0x7d, 0xdc, 0x1b, 0x9a, 0xdd, 0x6a, 0x82, 0x0a, 0x5d, 0x0c, 0x13,
|
||||
0xda, 0x22, 0x4c, 0xcd, 0x98, 0xc8, 0xb8, 0xc9, 0xab, 0xd4, 0xc1, 0xb1, 0x56, 0x4d, 0x4e, 0x7f,
|
||||
0xd5, 0xf6, 0xe0, 0x98, 0xbe, 0x8a, 0xf0, 0xa2, 0x0d, 0x00, 0x75, 0xa0, 0x5a, 0x52, 0xa7, 0x2b,
|
||||
0xab, 0x83, 0x6a, 0x8a, 0x4a, 0x3e, 0x1e, 0x2e, 0xa9, 0x5a, 0x75, 0xc2, 0xd8, 0x8c, 0x89, 0x79,
|
||||
0xd5, 0x1e, 0x90, 0xcf, 0x7d, 0x77, 0x88, 0x8d, 0xb3, 0x6a, 0x7a, 0xfa, 0xe7, 0xbe, 0x4e, 0x98,
|
||||
0xc8, 0xe7, 0x52, 0x6e, 0xb4, 0x0d, 0x85, 0x36, 0x3e, 0x51, 0x07, 0x52, 0xbb, 0xa7, 0x75, 0x1e,
|
||||
0x54, 0x33, 0x54, 0x58, 0x08, 0x13, 0xde, 0x20, 0xac, 0x1b, 0x84, 0x73, 0x23, 0x51, 0x8d, 0x37,
|
||||
0x63, 0x22, 0xb4, 0x1d, 0x0a, 0x7a, 0x19, 0x72, 0x9d, 0x2e, 0xee, 0x3c, 0x90, 0xac, 0x51, 0x35,
|
||||
0x4b, 0xf5, 0xac, 0x86, 0xe9, 0xa9, 0x13, 0xbe, 0xd6, 0xa8, 0x19, 0x13, 0xb3, 0x1d, 0xf6, 0x13,
|
||||
0x6d, 0x01, 0x28, 0xb8, 0xa7, 0x9e, 0x62, 0x83, 0xc8, 0xe7, 0xa6, 0xaf, 0xc1, 0x26, 0xe3, 0x6c,
|
||||
0x8d, 0xf8, 0x67, 0xe4, 0x15, 0x9b, 0x80, 0xea, 0x90, 0xc7, 0x03, 0x85, 0x4f, 0x27, 0x4f, 0xd5,
|
||||
0x5c, 0x0a, 0xdd, 0xef, 0x81, 0xe2, 0x9d, 0x4c, 0x0e, 0xf3, 0x31, 0xba, 0x0d, 0x99, 0x8e, 0xd6,
|
||||
0xef, 0xab, 0x56, 0x15, 0xa8, 0x86, 0x95, 0xd0, 0x89, 0x50, 0xae, 0x66, 0x4c, 0xe4, 0xfc, 0x68,
|
||||
0x17, 0x4a, 0x3d, 0xd5, 0xb4, 0x24, 0x73, 0x20, 0xeb, 0x66, 0x57, 0xb3, 0xcc, 0x6a, 0x81, 0x6a,
|
||||
0x78, 0x22, 0x4c, 0xc3, 0x8e, 0x6a, 0x5a, 0x07, 0x36, 0x73, 0x33, 0x26, 0x16, 0x7b, 0x5e, 0x02,
|
||||
0xd1, 0xa7, 0x1d, 0x1f, 0x63, 0xc3, 0x51, 0x58, 0x5d, 0x98, 0xae, 0x6f, 0x8f, 0x70, 0xdb, 0xf2,
|
||||
0x44, 0x9f, 0xe6, 0x25, 0xa0, 0x1f, 0xc2, 0x52, 0x4f, 0x93, 0x15, 0x47, 0x9d, 0xd4, 0xe9, 0x0e,
|
||||
0x07, 0x0f, 0xaa, 0x45, 0xaa, 0xf4, 0x6a, 0xe8, 0x47, 0x6a, 0xb2, 0x62, 0xab, 0xa8, 0x13, 0x81,
|
||||
0x66, 0x4c, 0x5c, 0xec, 0x05, 0x89, 0xe8, 0x3e, 0x2c, 0xcb, 0xba, 0xde, 0x3b, 0x0b, 0x6a, 0x2f,
|
||||
0x51, 0xed, 0xd7, 0xc2, 0xb4, 0xaf, 0x13, 0x99, 0xa0, 0x7a, 0x24, 0x8f, 0x51, 0x51, 0x0b, 0x2a,
|
||||
0xba, 0x81, 0x75, 0xd9, 0xc0, 0x92, 0x6e, 0x68, 0xba, 0x66, 0xca, 0xbd, 0x6a, 0x99, 0xea, 0x7e,
|
||||
0x2a, 0x4c, 0xf7, 0x3e, 0xe3, 0xdf, 0xe7, 0xec, 0xcd, 0x98, 0x58, 0xd6, 0xfd, 0x24, 0xa6, 0x55,
|
||||
0xeb, 0x60, 0xd3, 0x74, 0xb5, 0x56, 0x66, 0x69, 0xa5, 0xfc, 0x7e, 0xad, 0x3e, 0x12, 0x6a, 0x40,
|
||||
0x01, 0x8f, 0x88, 0xb8, 0x74, 0xaa, 0x59, 0xb8, 0xba, 0x38, 0xfd, 0x60, 0x35, 0x28, 0xeb, 0x91,
|
||||
0x66, 0x61, 0x72, 0xa8, 0xb0, 0x33, 0x42, 0x32, 0x3c, 0x72, 0x8a, 0x0d, 0xf5, 0xf8, 0x8c, 0xaa,
|
||||
0x91, 0xe8, 0x13, 0x53, 0xd5, 0x06, 0x55, 0x44, 0x15, 0x3e, 0x1d, 0xa6, 0xf0, 0x88, 0x0a, 0x11,
|
||||
0x15, 0x0d, 0x5b, 0xa4, 0x19, 0x13, 0x97, 0x4e, 0xc7, 0xc9, 0xc4, 0xc4, 0x8e, 0xd5, 0x81, 0xdc,
|
||||
0x53, 0xdf, 0xc7, 0xfc, 0xd8, 0x2c, 0x4d, 0x37, 0xb1, 0x2d, 0xce, 0x4d, 0xcf, 0x0a, 0x31, 0xb1,
|
||||
0x63, 0x2f, 0x61, 0x23, 0x0b, 0xe9, 0x53, 0xb9, 0x37, 0xc4, 0xc2, 0x53, 0x50, 0xf0, 0x38, 0x56,
|
||||
0x54, 0x85, 0x6c, 0x1f, 0x9b, 0xa6, 0x7c, 0x82, 0xa9, 0x1f, 0xce, 0x8b, 0xf6, 0x50, 0x28, 0xc1,
|
||||
0x82, 0xd7, 0x99, 0x0a, 0x1f, 0xc7, 0x1d, 0x49, 0xe2, 0x27, 0x89, 0xe4, 0x29, 0x36, 0xe8, 0xb4,
|
||||
0xb9, 0x24, 0x1f, 0xa2, 0xcb, 0x50, 0xa4, 0x9f, 0x2c, 0xd9, 0xcf, 0x89, 0xb3, 0x4e, 0x89, 0x0b,
|
||||
0x94, 0x78, 0xc4, 0x99, 0x56, 0xa1, 0xa0, 0xdf, 0xd0, 0x1d, 0x96, 0x24, 0x65, 0x01, 0xfd, 0x86,
|
||||
0x6e, 0x33, 0x3c, 0x0e, 0x0b, 0x64, 0x7e, 0x0e, 0x47, 0x8a, 0xbe, 0xa4, 0x40, 0x68, 0x9c, 0x45,
|
||||
0xf8, 0x63, 0x02, 0x2a, 0x41, 0x07, 0x8c, 0x6e, 0x43, 0x8a, 0xc4, 0x22, 0x1e, 0x56, 0x6a, 0x6b,
|
||||
0x2c, 0x50, 0xad, 0xd9, 0x81, 0x6a, 0xad, 0x65, 0x07, 0xaa, 0x8d, 0xdc, 0xa7, 0x9f, 0xaf, 0xc6,
|
||||
0x3e, 0xfe, 0xdb, 0x6a, 0x5c, 0xa4, 0x12, 0xe8, 0x3c, 0xf1, 0x95, 0xb2, 0x3a, 0x90, 0x54, 0x85,
|
||||
0x7e, 0x72, 0x9e, 0x38, 0x42, 0x59, 0x1d, 0x6c, 0x2b, 0x68, 0x07, 0x2a, 0x1d, 0x6d, 0x60, 0xe2,
|
||||
0x81, 0x39, 0x34, 0x25, 0x16, 0x08, 0x79, 0x30, 0xf1, 0xb9, 0x43, 0x16, 0x5e, 0xeb, 0x36, 0xe7,
|
||||
0x3e, 0x65, 0x14, 0xcb, 0x1d, 0x3f, 0x81, 0xb8, 0xd5, 0x53, 0xb9, 0xa7, 0x2a, 0xb2, 0xa5, 0x19,
|
||||
0x66, 0x35, 0x75, 0x29, 0x39, 0xd1, 0x1f, 0x1e, 0xd9, 0x2c, 0x87, 0xba, 0x22, 0x5b, 0x78, 0x23,
|
||||
0x45, 0x3e, 0x57, 0xf4, 0x48, 0xa2, 0x27, 0xa1, 0x2c, 0xeb, 0xba, 0x64, 0x5a, 0xb2, 0x85, 0xa5,
|
||||
0xf6, 0x99, 0x85, 0x4d, 0x1a, 0x68, 0x16, 0xc4, 0xa2, 0xac, 0xeb, 0x07, 0x84, 0xba, 0x41, 0x88,
|
||||
0xe8, 0x09, 0x28, 0x91, 0x98, 0xa4, 0xca, 0x3d, 0xa9, 0x8b, 0xd5, 0x93, 0xae, 0x45, 0x43, 0x4a,
|
||||
0x52, 0x2c, 0x72, 0x6a, 0x93, 0x12, 0x05, 0xc5, 0xd9, 0x71, 0x1a, 0x8f, 0x10, 0x82, 0x94, 0x22,
|
||||
0x5b, 0x32, 0x5d, 0xc9, 0x05, 0x91, 0xfe, 0x26, 0x34, 0x5d, 0xb6, 0xba, 0x7c, 0x7d, 0xe8, 0x6f,
|
||||
0x74, 0x0e, 0x32, 0x5c, 0x6d, 0x92, 0xaa, 0xe5, 0x23, 0xb4, 0x0c, 0x69, 0xdd, 0xd0, 0x4e, 0x31,
|
||||
0xdd, 0xba, 0x9c, 0xc8, 0x06, 0xc2, 0x07, 0x09, 0x58, 0x1c, 0x8b, 0x5c, 0x44, 0x6f, 0x57, 0x36,
|
||||
0xbb, 0xf6, 0xbb, 0xc8, 0x6f, 0xf4, 0x3c, 0xd1, 0x2b, 0x2b, 0xd8, 0xe0, 0xd1, 0xbe, 0x3a, 0xbe,
|
||||
0xd4, 0x4d, 0xfa, 0x9c, 0x2f, 0x0d, 0xe7, 0x46, 0x77, 0xa1, 0xd2, 0x93, 0x4d, 0x4b, 0x62, 0xde,
|
||||
0x5f, 0xf2, 0x44, 0xfe, 0xc7, 0xc6, 0x16, 0x99, 0xc5, 0x0a, 0x62, 0xd0, 0x5c, 0x49, 0x89, 0x88,
|
||||
0xba, 0x54, 0x74, 0x08, 0xcb, 0xed, 0xb3, 0xf7, 0xe5, 0x81, 0xa5, 0x0e, 0xb0, 0x34, 0xb6, 0x6b,
|
||||
0xe3, 0xa9, 0xc4, 0x3d, 0xd5, 0x6c, 0xe3, 0xae, 0x7c, 0xaa, 0x6a, 0xf6, 0x67, 0x2d, 0x39, 0xf2,
|
||||
0xce, 0x8e, 0x9a, 0x82, 0x08, 0x25, 0x7f, 0xd8, 0x45, 0x25, 0x48, 0x58, 0x23, 0x3e, 0xff, 0x84,
|
||||
0x35, 0x42, 0xcf, 0x41, 0x8a, 0xcc, 0x91, 0xce, 0xbd, 0x34, 0xe1, 0x45, 0x5c, 0xae, 0x75, 0xa6,
|
||||
0x63, 0x91, 0x72, 0x0a, 0x82, 0x73, 0x1a, 0x9c, 0x50, 0x1c, 0xd4, 0x2a, 0x5c, 0x85, 0x72, 0x20,
|
||||
0xce, 0x7a, 0xb6, 0x2f, 0xee, 0xdd, 0x3e, 0xa1, 0x0c, 0x45, 0x5f, 0x40, 0x15, 0xce, 0xc1, 0xf2,
|
||||
0xa4, 0xf8, 0x28, 0x74, 0x1d, 0xba, 0x2f, 0xce, 0xa1, 0x5b, 0x90, 0x73, 0x02, 0x24, 0x3b, 0x8d,
|
||||
0xe7, 0xc7, 0x66, 0x61, 0x33, 0x8b, 0x0e, 0x2b, 0x39, 0x86, 0xc4, 0xaa, 0xa9, 0x39, 0x24, 0xe8,
|
||||
0x87, 0x67, 0x65, 0x5d, 0x6f, 0xca, 0x66, 0x57, 0x78, 0x1b, 0xaa, 0x61, 0xc1, 0x2f, 0x30, 0x8d,
|
||||
0x94, 0x63, 0x85, 0xe7, 0x20, 0x73, 0xac, 0x19, 0x7d, 0xd9, 0xa2, 0xca, 0x8a, 0x22, 0x1f, 0x11,
|
||||
0xeb, 0x64, 0x81, 0x30, 0x49, 0xc9, 0x6c, 0x20, 0x48, 0x70, 0x3e, 0x34, 0x00, 0x12, 0x11, 0x75,
|
||||
0xa0, 0x60, 0xb6, 0x9e, 0x45, 0x91, 0x0d, 0x5c, 0x45, 0xec, 0x63, 0xd9, 0x80, 0xbc, 0xd6, 0xa4,
|
||||
0x73, 0xa5, 0xfa, 0xf3, 0x22, 0x1f, 0x09, 0xbf, 0x4d, 0xc2, 0xb9, 0xc9, 0x61, 0x10, 0x5d, 0x82,
|
||||
0x85, 0xbe, 0x3c, 0x92, 0xac, 0x11, 0x3f, 0xcb, 0x6c, 0x3b, 0xa0, 0x2f, 0x8f, 0x5a, 0x23, 0x76,
|
||||
0x90, 0x2b, 0x90, 0xb4, 0x46, 0x66, 0x35, 0x71, 0x29, 0x79, 0x65, 0x41, 0x24, 0x3f, 0xd1, 0x21,
|
||||
0x2c, 0xf6, 0xb4, 0x8e, 0xdc, 0x93, 0x3c, 0x16, 0xcf, 0x8d, 0xfd, 0xf2, 0xd8, 0x62, 0xb3, 0x80,
|
||||
0x86, 0x95, 0x31, 0xa3, 0x2f, 0x53, 0x1d, 0x3b, 0x8e, 0xe5, 0x7f, 0x43, 0x56, 0xef, 0xd9, 0xa3,
|
||||
0xb4, 0xcf, 0x53, 0xd8, 0x3e, 0x3b, 0x33, 0xb7, 0xcf, 0x7e, 0x0e, 0x96, 0x07, 0x78, 0x64, 0x79,
|
||||
0xbe, 0x91, 0x19, 0x4e, 0x96, 0xee, 0x05, 0x22, 0xcf, 0xdc, 0xf7, 0x13, 0x1b, 0x42, 0x57, 0x69,
|
||||
0x66, 0xa1, 0x6b, 0x26, 0x36, 0x24, 0x59, 0x51, 0x0c, 0x6c, 0x9a, 0x34, 0xb3, 0x5d, 0xa0, 0xe9,
|
||||
0x02, 0xa5, 0xaf, 0x33, 0xb2, 0xf0, 0x4b, 0xef, 0x5e, 0xf9, 0x33, 0x09, 0xbe, 0x13, 0x71, 0x77,
|
||||
0x27, 0x0e, 0x60, 0x99, 0xcb, 0x2b, 0xbe, 0xcd, 0x48, 0x44, 0xf5, 0x3c, 0xc8, 0x16, 0x8f, 0xb0,
|
||||
0x0f, 0xc9, 0x87, 0xdb, 0x07, 0xdb, 0xdb, 0xa6, 0x3c, 0xde, 0xf6, 0xbf, 0x6c, 0x6f, 0x5e, 0x75,
|
||||
0xa2, 0x88, 0x9b, 0xa6, 0xa1, 0x6b, 0x90, 0xa2, 0x89, 0x1d, 0xf3, 0x36, 0xe7, 0xc6, 0xe3, 0x05,
|
||||
0xe1, 0x12, 0x29, 0x8f, 0xd0, 0x84, 0x5a, 0x78, 0x5a, 0x36, 0x97, 0xa6, 0x9f, 0x25, 0x1d, 0x07,
|
||||
0xe8, 0xcb, 0xc2, 0x26, 0x18, 0xc9, 0xeb, 0xb0, 0xa4, 0xe0, 0x8e, 0xaa, 0x7c, 0x55, 0x1b, 0x59,
|
||||
0xe4, 0xd2, 0xdf, 0x99, 0x48, 0x04, 0x13, 0xf9, 0x73, 0x01, 0x72, 0x22, 0x36, 0x75, 0x92, 0x7d,
|
||||
0xa1, 0x0d, 0xc8, 0xe3, 0x51, 0x07, 0xeb, 0x96, 0x9d, 0xb0, 0x4e, 0x4e, 0xfc, 0x19, 0x77, 0xc3,
|
||||
0xe6, 0x24, 0x65, 0xac, 0x23, 0x86, 0x6e, 0x72, 0xc4, 0x22, 0x1c, 0x7c, 0xe0, 0xe2, 0x5e, 0xc8,
|
||||
0xe2, 0x79, 0x1b, 0xb2, 0x48, 0x86, 0x56, 0xad, 0x4c, 0x2a, 0x80, 0x59, 0xdc, 0xe4, 0x98, 0x45,
|
||||
0x6a, 0xc6, 0xcb, 0x7c, 0xa0, 0x45, 0xdd, 0x07, 0x5a, 0xa4, 0x67, 0x4c, 0x33, 0x04, 0xb5, 0x78,
|
||||
0xde, 0x46, 0x2d, 0x32, 0x33, 0xbe, 0x38, 0x00, 0x5b, 0xdc, 0xf1, 0xc3, 0x16, 0xd9, 0x90, 0x28,
|
||||
0x64, 0x4b, 0x4f, 0xc5, 0x2d, 0x5e, 0xf1, 0xe0, 0x16, 0xb9, 0x50, 0xc0, 0x80, 0x29, 0x9a, 0x00,
|
||||
0x5c, 0xbc, 0xe6, 0x03, 0x2e, 0xf2, 0x33, 0xd6, 0x61, 0x0a, 0x72, 0xb1, 0xe9, 0x45, 0x2e, 0x20,
|
||||
0x14, 0x00, 0xe1, 0xfb, 0x1e, 0x06, 0x5d, 0xbc, 0xe8, 0x40, 0x17, 0x85, 0x50, 0x0c, 0x86, 0xcf,
|
||||
0x25, 0x88, 0x5d, 0xec, 0x8d, 0x61, 0x17, 0x0c, 0x6b, 0x78, 0x32, 0x54, 0xc5, 0x0c, 0xf0, 0x62,
|
||||
0x6f, 0x0c, 0xbc, 0x28, 0xce, 0x50, 0x38, 0x03, 0xbd, 0x78, 0x6b, 0x32, 0x7a, 0x11, 0x8e, 0x2f,
|
||||
0xf0, 0xcf, 0x8c, 0x06, 0x5f, 0x48, 0x21, 0xf0, 0x45, 0x39, 0xb4, 0xd4, 0x66, 0xea, 0x23, 0xe3,
|
||||
0x17, 0x87, 0x13, 0xf0, 0x0b, 0x86, 0x34, 0x5c, 0x09, 0x55, 0x1e, 0x01, 0xc0, 0x38, 0x9c, 0x00,
|
||||
0x60, 0x2c, 0xce, 0x54, 0x3b, 0x13, 0xc1, 0xd8, 0xf2, 0x23, 0x18, 0x68, 0xc6, 0x19, 0x0b, 0x85,
|
||||
0x30, 0xda, 0x61, 0x10, 0x06, 0x83, 0x19, 0x9e, 0x09, 0xd5, 0x38, 0x07, 0x86, 0xb1, 0x37, 0x86,
|
||||
0x61, 0x2c, 0xcf, 0xb0, 0xb4, 0xa8, 0x20, 0xc6, 0x55, 0x12, 0xfc, 0x03, 0xae, 0x9a, 0xe4, 0xe1,
|
||||
0xd8, 0x30, 0x34, 0x83, 0xc3, 0x11, 0x6c, 0x20, 0x5c, 0x21, 0x45, 0xad, 0xeb, 0x96, 0xa7, 0x00,
|
||||
0x1e, 0xb4, 0xde, 0xf1, 0xb8, 0x62, 0xe1, 0x77, 0x71, 0x57, 0x96, 0xd6, 0x82, 0xde, 0x82, 0x38,
|
||||
0xcf, 0x0b, 0x62, 0x0f, 0x0c, 0x92, 0xf0, 0xc3, 0x20, 0xab, 0x50, 0x20, 0x75, 0x4c, 0x00, 0xe1,
|
||||
0x90, 0x75, 0x07, 0xe1, 0xb8, 0x06, 0x8b, 0x34, 0x09, 0x60, 0x60, 0x09, 0x8f, 0xac, 0x29, 0x1a,
|
||||
0x59, 0xcb, 0xe4, 0x01, 0x5b, 0x05, 0x16, 0x62, 0x9f, 0x85, 0x25, 0x0f, 0xaf, 0x53, 0x1f, 0xb1,
|
||||
0x72, 0xbf, 0xe2, 0x70, 0xaf, 0xf3, 0x42, 0xe9, 0x0f, 0x71, 0x77, 0x85, 0x5c, 0x68, 0x64, 0x12,
|
||||
0x8a, 0x11, 0xff, 0x9a, 0x50, 0x8c, 0xc4, 0x57, 0x46, 0x31, 0xbc, 0xf5, 0x5e, 0xd2, 0x5f, 0xef,
|
||||
0xfd, 0x33, 0xee, 0xee, 0x89, 0x83, 0x49, 0x74, 0x34, 0x05, 0xf3, 0x0a, 0x8c, 0xfe, 0x26, 0x69,
|
||||
0x56, 0x4f, 0x3b, 0xe1, 0x75, 0x16, 0xf9, 0x49, 0xb8, 0x9c, 0xd8, 0x99, 0xe7, 0xa1, 0xd1, 0x29,
|
||||
0xde, 0x58, 0xee, 0xc2, 0x8b, 0xb7, 0x0a, 0x24, 0x1f, 0x60, 0x16, 0xe9, 0x16, 0x44, 0xf2, 0x93,
|
||||
0xf0, 0x51, 0x23, 0xe3, 0x39, 0x08, 0x1b, 0xa0, 0xdb, 0x90, 0xa7, 0x9d, 0x15, 0x49, 0xd3, 0x4d,
|
||||
0x1e, 0x90, 0x7c, 0xe9, 0x1a, 0x6b, 0xa0, 0xac, 0xed, 0x13, 0x9e, 0x3d, 0xdd, 0x14, 0x73, 0x3a,
|
||||
0xff, 0xe5, 0x49, 0x9a, 0xf2, 0xbe, 0xa4, 0xe9, 0x02, 0xe4, 0xc9, 0xd7, 0x9b, 0xba, 0xdc, 0xc1,
|
||||
0x34, 0xb2, 0xe4, 0x45, 0x97, 0x20, 0xdc, 0x07, 0x34, 0x1e, 0x27, 0x51, 0x13, 0x32, 0xf8, 0x14,
|
||||
0x0f, 0x2c, 0x96, 0x53, 0x06, 0xf2, 0x52, 0x56, 0xe2, 0x91, 0xc7, 0x1b, 0x55, 0xb2, 0xc8, 0xff,
|
||||
0xf8, 0x7c, 0xb5, 0xc2, 0xb8, 0x9f, 0xd1, 0xfa, 0xaa, 0x85, 0xfb, 0xba, 0x75, 0x26, 0x72, 0x79,
|
||||
0xe1, 0xaf, 0x09, 0x28, 0x07, 0xe2, 0xe7, 0xc4, 0xb5, 0xb5, 0x4d, 0x3e, 0xe1, 0xc1, 0x80, 0xa2,
|
||||
0xad, 0xf7, 0x45, 0x80, 0x13, 0xd9, 0x94, 0xde, 0x93, 0x07, 0x16, 0x56, 0xf8, 0xa2, 0xe7, 0x4f,
|
||||
0x64, 0xf3, 0x0d, 0x4a, 0x20, 0xbb, 0x4e, 0x1e, 0x0f, 0x4d, 0xac, 0x70, 0x34, 0x2a, 0x7b, 0x22,
|
||||
0x9b, 0x87, 0x26, 0x56, 0x3c, 0xb3, 0xcc, 0x3e, 0xdc, 0x2c, 0xfd, 0x6b, 0x9c, 0x0b, 0xac, 0xb1,
|
||||
0xa7, 0x44, 0xcf, 0x7b, 0x4b, 0x74, 0x54, 0x83, 0x9c, 0x6e, 0xa8, 0x9a, 0xa1, 0x5a, 0x67, 0x74,
|
||||
0x63, 0x92, 0xa2, 0x33, 0x46, 0x97, 0xa1, 0xd8, 0xc7, 0x7d, 0x5d, 0xd3, 0x7a, 0x12, 0x73, 0x36,
|
||||
0x05, 0x2a, 0xba, 0xc0, 0x89, 0x0d, 0xea, 0x73, 0x3e, 0x4c, 0xb8, 0xa7, 0xcf, 0x85, 0x62, 0xbe,
|
||||
0xde, 0xe5, 0x5d, 0x99, 0xb0, 0xbc, 0x1e, 0x0a, 0x99, 0x44, 0x60, 0x7d, 0x9d, 0xf1, 0xb7, 0xb5,
|
||||
0xc0, 0xc2, 0x4f, 0x28, 0x3e, 0xeb, 0xcf, 0x8d, 0xd0, 0x01, 0x2c, 0x3a, 0x87, 0x5f, 0x1a, 0x52,
|
||||
0xa7, 0x60, 0x9b, 0x73, 0x54, 0xef, 0x51, 0x39, 0xf5, 0x93, 0x4d, 0xf4, 0x26, 0x3c, 0x1a, 0xf0,
|
||||
0x6c, 0x8e, 0xea, 0x44, 0x54, 0x07, 0xf7, 0x88, 0xdf, 0xc1, 0xd9, 0xaa, 0xdd, 0xc5, 0x4a, 0x3e,
|
||||
0xe4, 0x99, 0xdb, 0x86, 0x92, 0x3f, 0xcd, 0x9b, 0xb8, 0xfd, 0x97, 0xa1, 0x68, 0x60, 0x4b, 0x56,
|
||||
0x07, 0x92, 0x0f, 0x54, 0x5d, 0x60, 0x44, 0x0e, 0xd5, 0xee, 0xc3, 0x23, 0x13, 0xd3, 0x3d, 0xf4,
|
||||
0x02, 0xe4, 0xdd, 0x4c, 0x91, 0xad, 0xea, 0x14, 0xd0, 0xcd, 0xe5, 0x15, 0x7e, 0x1f, 0x77, 0x55,
|
||||
0xfa, 0x61, 0xbc, 0x06, 0x64, 0x0c, 0x6c, 0x0e, 0x7b, 0x0c, 0x58, 0x2b, 0xdd, 0x78, 0x36, 0x5a,
|
||||
0xa2, 0x48, 0xa8, 0xc3, 0x9e, 0x25, 0x72, 0x61, 0xe1, 0x3e, 0x64, 0x18, 0x05, 0x15, 0x20, 0x7b,
|
||||
0xb8, 0x7b, 0x77, 0x77, 0xef, 0x8d, 0xdd, 0x4a, 0x0c, 0x01, 0x64, 0xd6, 0xeb, 0xf5, 0xc6, 0x7e,
|
||||
0xab, 0x12, 0x47, 0x79, 0x48, 0xaf, 0x6f, 0xec, 0x89, 0xad, 0x4a, 0x82, 0x90, 0xc5, 0xc6, 0x9d,
|
||||
0x46, 0xbd, 0x55, 0x49, 0xa2, 0x45, 0x28, 0xb2, 0xdf, 0xd2, 0xd6, 0x9e, 0x78, 0x6f, 0xbd, 0x55,
|
||||
0x49, 0x79, 0x48, 0x07, 0x8d, 0xdd, 0xcd, 0x86, 0x58, 0x49, 0x0b, 0xff, 0x07, 0xe7, 0x43, 0x53,
|
||||
0x4b, 0x17, 0xa3, 0x8b, 0x7b, 0x30, 0x3a, 0xe1, 0x17, 0x09, 0xa8, 0x85, 0xe7, 0x8b, 0xe8, 0x4e,
|
||||
0x60, 0xe2, 0x37, 0xe6, 0x48, 0x36, 0x03, 0xb3, 0x47, 0x4f, 0x40, 0xc9, 0xc0, 0xc7, 0xd8, 0xea,
|
||||
0x74, 0x59, 0xfe, 0xca, 0x02, 0x66, 0x51, 0x2c, 0x72, 0x2a, 0x15, 0x32, 0x19, 0xdb, 0x3b, 0xb8,
|
||||
0x63, 0x49, 0xcc, 0x17, 0x31, 0xa3, 0xcb, 0x13, 0x36, 0x42, 0x3d, 0x60, 0x44, 0xe1, 0xed, 0xb9,
|
||||
0xd6, 0x32, 0x0f, 0x69, 0xb1, 0xd1, 0x12, 0xdf, 0xac, 0x24, 0x11, 0x82, 0x12, 0xfd, 0x29, 0x1d,
|
||||
0xec, 0xae, 0xef, 0x1f, 0x34, 0xf7, 0xc8, 0x5a, 0x2e, 0x41, 0xd9, 0x5e, 0x4b, 0x9b, 0x98, 0x16,
|
||||
0xfe, 0x94, 0x80, 0x47, 0x43, 0xb2, 0x5d, 0x74, 0x1b, 0xc0, 0x1a, 0x49, 0x06, 0xee, 0x68, 0x86,
|
||||
0x12, 0x6e, 0x64, 0xad, 0x91, 0x48, 0x39, 0xc4, 0xbc, 0xc5, 0x7f, 0x99, 0x53, 0xa0, 0x5d, 0xf4,
|
||||
0x32, 0x57, 0x4a, 0x66, 0x65, 0x1f, 0xb5, 0x8b, 0x13, 0x10, 0x4c, 0xdc, 0x21, 0x8a, 0xe9, 0xda,
|
||||
0x52, 0xc5, 0x94, 0x1f, 0xdd, 0x9b, 0xe4, 0x54, 0x22, 0x36, 0x56, 0xe6, 0x73, 0x27, 0xe9, 0x87,
|
||||
0x73, 0x27, 0xc2, 0xaf, 0x92, 0xde, 0x85, 0xf5, 0x27, 0xf7, 0x7b, 0x90, 0x31, 0x2d, 0xd9, 0x1a,
|
||||
0x9a, 0xdc, 0xe0, 0x5e, 0x88, 0x5a, 0x29, 0xac, 0xd9, 0x3f, 0x0e, 0xa8, 0xb8, 0xc8, 0xd5, 0x7c,
|
||||
0xb7, 0xde, 0xa6, 0x70, 0x0b, 0x4a, 0xfe, 0xc5, 0x09, 0x3f, 0x32, 0xae, 0xcf, 0x49, 0x08, 0x6f,
|
||||
0xb9, 0xf9, 0x97, 0x07, 0x5f, 0xdc, 0x82, 0x52, 0xa0, 0x5c, 0x8a, 0x8f, 0xd7, 0xf3, 0x2e, 0x3e,
|
||||
0xe8, 0x94, 0x42, 0x62, 0xf1, 0xd4, 0x3b, 0x14, 0x7e, 0x1d, 0x87, 0xc7, 0xa6, 0x14, 0x54, 0xe8,
|
||||
0xf5, 0x80, 0x21, 0xbc, 0x38, 0x4f, 0x39, 0xb6, 0xc6, 0x68, 0x7e, 0x53, 0x10, 0x6e, 0xc2, 0x82,
|
||||
0x97, 0x1e, 0x6d, 0x15, 0x7e, 0x9a, 0x74, 0x83, 0x82, 0x1f, 0xda, 0xfc, 0xda, 0x32, 0xd1, 0x80,
|
||||
0x21, 0x26, 0xe6, 0x34, 0xc4, 0x89, 0xd9, 0x44, 0xf2, 0x9b, 0xcb, 0x26, 0x52, 0x0f, 0x99, 0x4d,
|
||||
0x78, 0x4f, 0x64, 0xda, 0x7f, 0x22, 0xc7, 0x02, 0x7f, 0x66, 0x42, 0xe0, 0x7f, 0x13, 0xc0, 0xd3,
|
||||
0x9c, 0x5c, 0x86, 0xb4, 0xa1, 0x0d, 0x07, 0x0a, 0x35, 0x93, 0xb4, 0xc8, 0x06, 0xe8, 0x16, 0xa4,
|
||||
0x89, 0xb9, 0xd9, 0x8b, 0x39, 0xee, 0x9a, 0x89, 0xb9, 0x78, 0x40, 0x65, 0xc6, 0x2d, 0xa8, 0x80,
|
||||
0xc6, 0x1b, 0x44, 0x21, 0xaf, 0x78, 0xc5, 0xff, 0x8a, 0xc7, 0x43, 0x5b, 0x4d, 0x93, 0x5f, 0xf5,
|
||||
0x3e, 0xa4, 0xa9, 0x79, 0x90, 0x04, 0x88, 0x36, 0x39, 0x79, 0x45, 0x4d, 0x7e, 0xa3, 0x1f, 0x01,
|
||||
0xc8, 0x96, 0x65, 0xa8, 0xed, 0xa1, 0xfb, 0x82, 0xd5, 0xc9, 0xe6, 0xb5, 0x6e, 0xf3, 0x6d, 0x5c,
|
||||
0xe0, 0x76, 0xb6, 0xec, 0x8a, 0x7a, 0x6c, 0xcd, 0xa3, 0x50, 0xd8, 0x85, 0x92, 0x5f, 0xd6, 0xae,
|
||||
0x01, 0xd9, 0x37, 0xf8, 0x6b, 0x40, 0x56, 0xd2, 0xf3, 0x1a, 0xd0, 0xa9, 0x20, 0x93, 0xac, 0x9f,
|
||||
0x4d, 0x07, 0xc2, 0xbf, 0xe2, 0xb0, 0xe0, 0xb5, 0xce, 0xff, 0xb5, 0x32, 0x4a, 0xf8, 0x30, 0x0e,
|
||||
0x39, 0x67, 0xf2, 0x21, 0xcd, 0x64, 0x77, 0xed, 0x12, 0xde, 0xd6, 0x29, 0xeb, 0x4e, 0x27, 0x9d,
|
||||
0x9e, 0xf7, 0x4b, 0x4e, 0xc6, 0x15, 0x86, 0x7a, 0x7b, 0x57, 0xda, 0x6e, 0xfb, 0xf3, 0x04, 0xf3,
|
||||
0xe7, 0xfc, 0x3b, 0x48, 0xaa, 0x81, 0xbe, 0x07, 0x19, 0xb9, 0xe3, 0x60, 0xfd, 0xa5, 0x09, 0xe0,
|
||||
0xaf, 0xcd, 0xba, 0xd6, 0x1a, 0xad, 0x53, 0x4e, 0x91, 0x4b, 0xf0, 0xaf, 0x4a, 0x38, 0x3d, 0xf3,
|
||||
0x57, 0x89, 0x5e, 0xc6, 0xe3, 0x77, 0x9b, 0x25, 0x80, 0xc3, 0xdd, 0x7b, 0x7b, 0x9b, 0xdb, 0x5b,
|
||||
0xdb, 0x8d, 0x4d, 0x9e, 0x73, 0x6d, 0x6e, 0x36, 0x36, 0x2b, 0x09, 0xc2, 0x27, 0x36, 0xee, 0xed,
|
||||
0x1d, 0x35, 0x36, 0x2b, 0x49, 0xe1, 0x25, 0xc8, 0x3b, 0xae, 0x07, 0x55, 0x21, 0x6b, 0xf7, 0x2d,
|
||||
0xe2, 0xdc, 0x01, 0xb0, 0x21, 0xbd, 0x2f, 0xa1, 0xbd, 0xc7, 0x3b, 0xc6, 0x49, 0x91, 0x0d, 0x04,
|
||||
0x05, 0xca, 0x01, 0xbf, 0x85, 0x5e, 0x82, 0xac, 0x3e, 0x6c, 0x4b, 0xb6, 0xd1, 0x06, 0xba, 0x3c,
|
||||
0x36, 0x14, 0x31, 0x6c, 0xf7, 0xd4, 0xce, 0x5d, 0x7c, 0x66, 0x2f, 0x93, 0x3e, 0x6c, 0xdf, 0x65,
|
||||
0xb6, 0xcd, 0xde, 0x92, 0xf0, 0xbe, 0xe5, 0xc7, 0x71, 0xc8, 0xd9, 0x67, 0x15, 0x7d, 0x1f, 0xf2,
|
||||
0x8e, 0x4f, 0x74, 0xee, 0xd1, 0x84, 0x3a, 0x53, 0xae, 0xdf, 0x15, 0x41, 0xd7, 0x60, 0xd1, 0x54,
|
||||
0x4f, 0x06, 0x76, 0x93, 0x8b, 0x61, 0x7f, 0x09, 0x7a, 0x68, 0xca, 0xec, 0xc1, 0x8e, 0x0d, 0x58,
|
||||
0xdd, 0x49, 0xe5, 0x92, 0x95, 0xd4, 0x9d, 0x54, 0x2e, 0x55, 0x49, 0x93, 0xb0, 0x58, 0x09, 0x3a,
|
||||
0x8e, 0x6f, 0xf3, 0x63, 0x48, 0xfa, 0x1d, 0x88, 0xef, 0xcc, 0x36, 0x03, 0xe1, 0xfb, 0x83, 0x04,
|
||||
0x14, 0x3c, 0x6d, 0x34, 0xf4, 0xff, 0x1e, 0x2f, 0x56, 0x9a, 0x10, 0x77, 0x3c, 0xbc, 0xee, 0x75,
|
||||
0x0d, 0xff, 0xc4, 0x12, 0xf3, 0x4f, 0x2c, 0xec, 0xda, 0x8d, 0xdd, 0x8d, 0x4b, 0xcd, 0xdd, 0x8d,
|
||||
0x7b, 0x06, 0x90, 0xa5, 0x59, 0x72, 0x4f, 0x3a, 0xd5, 0x2c, 0x75, 0x70, 0x22, 0x31, 0x3b, 0x61,
|
||||
0x3e, 0xa7, 0x42, 0x9f, 0x1c, 0xd1, 0x07, 0xfb, 0x8e, 0xc9, 0x38, 0x45, 0xe2, 0xbc, 0xb7, 0x2f,
|
||||
0xce, 0x41, 0x86, 0xd7, 0x41, 0xec, 0xfa, 0x05, 0x1f, 0x4d, 0x6c, 0x3b, 0xd6, 0x20, 0xd7, 0xc7,
|
||||
0x96, 0x4c, 0x1d, 0x28, 0x8b, 0x99, 0xce, 0xf8, 0xda, 0x8b, 0x50, 0xf0, 0x5c, 0x84, 0x21, 0x3e,
|
||||
0x75, 0xb7, 0xf1, 0x46, 0x25, 0x56, 0xcb, 0x7e, 0xf4, 0xc9, 0xa5, 0xe4, 0x2e, 0x7e, 0x8f, 0x1c,
|
||||
0x37, 0xb1, 0x51, 0x6f, 0x36, 0xea, 0x77, 0x2b, 0xf1, 0x5a, 0xe1, 0xa3, 0x4f, 0x2e, 0x65, 0x45,
|
||||
0x4c, 0xbb, 0x44, 0xd7, 0xee, 0x42, 0x39, 0xb0, 0x31, 0xfe, 0xd3, 0x8d, 0xa0, 0xb4, 0x79, 0xb8,
|
||||
0xbf, 0xb3, 0x5d, 0x5f, 0x6f, 0x35, 0xa4, 0xa3, 0xbd, 0x56, 0xa3, 0x12, 0x47, 0x8f, 0xc2, 0xd2,
|
||||
0xce, 0xf6, 0x6b, 0xcd, 0x96, 0x54, 0xdf, 0xd9, 0x6e, 0xec, 0xb6, 0xa4, 0xf5, 0x56, 0x6b, 0xbd,
|
||||
0x7e, 0xb7, 0x92, 0xb8, 0xf1, 0x9b, 0x02, 0x94, 0xd7, 0x37, 0xea, 0xdb, 0xa4, 0x12, 0x54, 0x3b,
|
||||
0x32, 0xf5, 0x15, 0x75, 0x48, 0x51, 0xc8, 0x79, 0xea, 0xd5, 0xe6, 0xda, 0xf4, 0x36, 0x22, 0xda,
|
||||
0x82, 0x34, 0x45, 0xa3, 0xd1, 0xf4, 0xbb, 0xce, 0xb5, 0x19, 0x7d, 0x45, 0xf2, 0x31, 0xf4, 0x38,
|
||||
0x4d, 0xbd, 0xfc, 0x5c, 0x9b, 0xde, 0x66, 0x44, 0x3b, 0x90, 0xb5, 0xc1, 0xc2, 0x59, 0xd7, 0x88,
|
||||
0x6b, 0x33, 0xfb, 0x75, 0x64, 0x6a, 0x0c, 0xd4, 0x9d, 0x7e, 0x2f, 0xba, 0x36, 0xa3, 0x01, 0x89,
|
||||
0xb6, 0x21, 0xc3, 0xf1, 0x94, 0x19, 0x57, 0x82, 0x6b, 0xb3, 0xfa, 0x6e, 0x48, 0x84, 0xbc, 0x0b,
|
||||
0x97, 0xcf, 0xbe, 0xed, 0x5d, 0x8b, 0xd0, 0x5b, 0x45, 0xf7, 0xa1, 0xe8, 0xc7, 0x68, 0xa2, 0x5d,
|
||||
0x3b, 0xae, 0x45, 0xec, 0xf0, 0x11, 0xfd, 0x7e, 0xc0, 0x26, 0xda, 0x35, 0xe4, 0x5a, 0xc4, 0x86,
|
||||
0x1f, 0x7a, 0x07, 0x16, 0xc7, 0x01, 0x95, 0xe8, 0xb7, 0x92, 0x6b, 0x73, 0xb4, 0x00, 0x51, 0x1f,
|
||||
0xd0, 0x04, 0x20, 0x66, 0x8e, 0x4b, 0xca, 0xb5, 0x79, 0x3a, 0x82, 0x48, 0x81, 0x72, 0x10, 0xdc,
|
||||
0x88, 0x7a, 0x69, 0xb9, 0x16, 0xb9, 0x3b, 0xc8, 0xde, 0xe2, 0xaf, 0xf4, 0xa3, 0x5e, 0x62, 0xae,
|
||||
0x45, 0x6e, 0x16, 0xa2, 0x43, 0x00, 0x4f, 0xa5, 0x1a, 0xe1, 0x52, 0x73, 0x2d, 0x4a, 0xdb, 0x10,
|
||||
0xe9, 0xb0, 0x34, 0xa9, 0x42, 0x9d, 0xe7, 0x8e, 0x73, 0x6d, 0xae, 0x6e, 0x22, 0xb1, 0x67, 0x7f,
|
||||
0xad, 0x19, 0xed, 0xce, 0x73, 0x2d, 0x62, 0x5b, 0x71, 0xa3, 0xf1, 0xe9, 0x17, 0x2b, 0xf1, 0xcf,
|
||||
0xbe, 0x58, 0x89, 0xff, 0xfd, 0x8b, 0x95, 0xf8, 0xc7, 0x5f, 0xae, 0xc4, 0x3e, 0xfb, 0x72, 0x25,
|
||||
0xf6, 0x97, 0x2f, 0x57, 0x62, 0x3f, 0x78, 0xfa, 0x44, 0xb5, 0xba, 0xc3, 0xf6, 0x5a, 0x47, 0xeb,
|
||||
0x5f, 0xf7, 0xfe, 0xfd, 0x65, 0xd2, 0x5f, 0x72, 0xda, 0x19, 0x1a, 0x50, 0x6f, 0xfe, 0x27, 0x00,
|
||||
0x00, 0xff, 0xff, 0xc7, 0x45, 0xe7, 0x5f, 0xb2, 0x33, 0x00, 0x00,
|
||||
// 3459 bytes of a gzipped FileDescriptorProto
|
||||
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xec, 0x5b, 0x4b, 0x93, 0x1b, 0xd5,
|
||||
0xf5, 0x97, 0x5a, 0xef, 0xa3, 0xd1, 0x63, 0xee, 0x0c, 0x46, 0x16, 0xf6, 0x8c, 0x69, 0x97, 0xc1,
|
||||
0x36, 0x30, 0xe6, 0x3f, 0xfe, 0x1b, 0x4c, 0x0c, 0xa1, 0x66, 0x34, 0x32, 0x1a, 0x7b, 0x3c, 0x33,
|
||||
0xf4, 0x68, 0x4c, 0x91, 0x87, 0x9b, 0x96, 0xfa, 0xce, 0xa8, 0xb1, 0xa4, 0x6e, 0xba, 0x5b, 0x83,
|
||||
0x86, 0x65, 0x28, 0x36, 0x54, 0xaa, 0xc2, 0x26, 0x95, 0xa4, 0x2a, 0xec, 0x92, 0xaa, 0xe4, 0x1b,
|
||||
0x64, 0x95, 0x55, 0x16, 0x2c, 0xb2, 0x60, 0x95, 0xa4, 0xb2, 0x20, 0x29, 0xd8, 0xe5, 0x0b, 0x64,
|
||||
0x97, 0xa4, 0xee, 0xa3, 0x5f, 0x52, 0xb7, 0x1e, 0x18, 0xa8, 0x4a, 0x85, 0x9d, 0xfa, 0xf4, 0x39,
|
||||
0xa7, 0xef, 0xe3, 0xdc, 0xf3, 0xf8, 0x9d, 0x2b, 0x78, 0xc2, 0xc6, 0x7d, 0x15, 0x9b, 0x3d, 0xad,
|
||||
0x6f, 0x5f, 0x53, 0x5a, 0x6d, 0xed, 0x9a, 0x7d, 0x6a, 0x60, 0x6b, 0xcd, 0x30, 0x75, 0x5b, 0x47,
|
||||
0x25, 0xef, 0xe5, 0x1a, 0x79, 0x59, 0x3d, 0xef, 0xe3, 0x6e, 0x9b, 0xa7, 0x86, 0xad, 0x5f, 0x33,
|
||||
0x4c, 0x5d, 0x3f, 0x62, 0xfc, 0xd5, 0x73, 0xbe, 0xd7, 0x54, 0x8f, 0x5f, 0x5b, 0xe0, 0x2d, 0x17,
|
||||
0x7e, 0x88, 0x4f, 0x9d, 0xb7, 0xe7, 0xc7, 0x64, 0x0d, 0xc5, 0x54, 0x7a, 0xce, 0xeb, 0xd5, 0x63,
|
||||
0x5d, 0x3f, 0xee, 0xe2, 0x6b, 0xf4, 0xa9, 0x35, 0x38, 0xba, 0x66, 0x6b, 0x3d, 0x6c, 0xd9, 0x4a,
|
||||
0xcf, 0xe0, 0x0c, 0xcb, 0xc7, 0xfa, 0xb1, 0x4e, 0x7f, 0x5e, 0x23, 0xbf, 0x18, 0x55, 0xfc, 0x37,
|
||||
0x40, 0x46, 0xc2, 0xef, 0x0c, 0xb0, 0x65, 0xa3, 0x75, 0x48, 0xe2, 0x76, 0x47, 0xaf, 0xc4, 0x2f,
|
||||
0xc4, 0x2f, 0xe7, 0xd7, 0xcf, 0xad, 0x8d, 0x4c, 0x6e, 0x8d, 0xf3, 0xd5, 0xdb, 0x1d, 0xbd, 0x11,
|
||||
0x93, 0x28, 0x2f, 0xba, 0x01, 0xa9, 0xa3, 0xee, 0xc0, 0xea, 0x54, 0x04, 0x2a, 0x74, 0x3e, 0x4a,
|
||||
0xe8, 0x36, 0x61, 0x6a, 0xc4, 0x24, 0xc6, 0x4d, 0x3e, 0xa5, 0xf5, 0x8f, 0xf4, 0x4a, 0x62, 0xf2,
|
||||
0xa7, 0xb6, 0xfb, 0x47, 0xf4, 0x53, 0x84, 0x17, 0x6d, 0x02, 0x68, 0x7d, 0xcd, 0x96, 0xdb, 0x1d,
|
||||
0x45, 0xeb, 0x57, 0x92, 0x54, 0xf2, 0xc9, 0x68, 0x49, 0xcd, 0xae, 0x11, 0xc6, 0x46, 0x4c, 0xca,
|
||||
0x69, 0xce, 0x03, 0x19, 0xee, 0x3b, 0x03, 0x6c, 0x9e, 0x56, 0x52, 0x93, 0x87, 0xfb, 0x3a, 0x61,
|
||||
0x22, 0xc3, 0xa5, 0xdc, 0x68, 0x1b, 0xf2, 0x2d, 0x7c, 0xac, 0xf5, 0xe5, 0x56, 0x57, 0x6f, 0x3f,
|
||||
0xac, 0xa4, 0xa9, 0xb0, 0x18, 0x25, 0xbc, 0x49, 0x58, 0x37, 0x09, 0xe7, 0xa6, 0x50, 0x89, 0x37,
|
||||
0x62, 0x12, 0xb4, 0x5c, 0x0a, 0x7a, 0x19, 0xb2, 0xed, 0x0e, 0x6e, 0x3f, 0x94, 0xed, 0x61, 0x25,
|
||||
0x43, 0xf5, 0xac, 0x46, 0xe9, 0xa9, 0x11, 0xbe, 0xe6, 0xb0, 0x11, 0x93, 0x32, 0x6d, 0xf6, 0x13,
|
||||
0xdd, 0x06, 0x50, 0x71, 0x57, 0x3b, 0xc1, 0x26, 0x91, 0xcf, 0x4e, 0x5e, 0x83, 0x2d, 0xc6, 0xd9,
|
||||
0x1c, 0xf2, 0x61, 0xe4, 0x54, 0x87, 0x80, 0x6a, 0x90, 0xc3, 0x7d, 0x95, 0x4f, 0x27, 0x47, 0xd5,
|
||||
0x5c, 0x88, 0xdc, 0xef, 0xbe, 0xea, 0x9f, 0x4c, 0x16, 0xf3, 0x67, 0x74, 0x13, 0xd2, 0x6d, 0xbd,
|
||||
0xd7, 0xd3, 0xec, 0x0a, 0x50, 0x0d, 0x2b, 0x91, 0x13, 0xa1, 0x5c, 0x8d, 0x98, 0xc4, 0xf9, 0xd1,
|
||||
0x2e, 0x14, 0xbb, 0x9a, 0x65, 0xcb, 0x56, 0x5f, 0x31, 0xac, 0x8e, 0x6e, 0x5b, 0x95, 0x3c, 0xd5,
|
||||
0x70, 0x29, 0x4a, 0xc3, 0x8e, 0x66, 0xd9, 0x07, 0x0e, 0x73, 0x23, 0x26, 0x15, 0xba, 0x7e, 0x02,
|
||||
0xd1, 0xa7, 0x1f, 0x1d, 0x61, 0xd3, 0x55, 0x58, 0x59, 0x98, 0xac, 0x6f, 0x8f, 0x70, 0x3b, 0xf2,
|
||||
0x44, 0x9f, 0xee, 0x27, 0xa0, 0xef, 0xc3, 0x52, 0x57, 0x57, 0x54, 0x57, 0x9d, 0xdc, 0xee, 0x0c,
|
||||
0xfa, 0x0f, 0x2b, 0x05, 0xaa, 0xf4, 0x4a, 0xe4, 0x20, 0x75, 0x45, 0x75, 0x54, 0xd4, 0x88, 0x40,
|
||||
0x23, 0x26, 0x2d, 0x76, 0x47, 0x89, 0xe8, 0x01, 0x2c, 0x2b, 0x86, 0xd1, 0x3d, 0x1d, 0xd5, 0x5e,
|
||||
0xa4, 0xda, 0xaf, 0x46, 0x69, 0xdf, 0x20, 0x32, 0xa3, 0xea, 0x91, 0x32, 0x46, 0x45, 0x4d, 0x28,
|
||||
0x1b, 0x26, 0x36, 0x14, 0x13, 0xcb, 0x86, 0xa9, 0x1b, 0xba, 0xa5, 0x74, 0x2b, 0x25, 0xaa, 0xfb,
|
||||
0xe9, 0x28, 0xdd, 0xfb, 0x8c, 0x7f, 0x9f, 0xb3, 0x37, 0x62, 0x52, 0xc9, 0x08, 0x92, 0x98, 0x56,
|
||||
0xbd, 0x8d, 0x2d, 0xcb, 0xd3, 0x5a, 0x9e, 0xa6, 0x95, 0xf2, 0x07, 0xb5, 0x06, 0x48, 0xa8, 0x0e,
|
||||
0x79, 0x3c, 0x24, 0xe2, 0xf2, 0x89, 0x6e, 0xe3, 0xca, 0xe2, 0xe4, 0x83, 0x55, 0xa7, 0xac, 0xf7,
|
||||
0x75, 0x1b, 0x93, 0x43, 0x85, 0xdd, 0x27, 0xa4, 0xc0, 0x63, 0x27, 0xd8, 0xd4, 0x8e, 0x4e, 0xa9,
|
||||
0x1a, 0x99, 0xbe, 0xb1, 0x34, 0xbd, 0x5f, 0x41, 0x54, 0xe1, 0x33, 0x51, 0x0a, 0xef, 0x53, 0x21,
|
||||
0xa2, 0xa2, 0xee, 0x88, 0x34, 0x62, 0xd2, 0xd2, 0xc9, 0x38, 0x99, 0x98, 0xd8, 0x91, 0xd6, 0x57,
|
||||
0xba, 0xda, 0x7b, 0x98, 0x1f, 0x9b, 0xa5, 0xc9, 0x26, 0x76, 0x9b, 0x73, 0xd3, 0xb3, 0x42, 0x4c,
|
||||
0xec, 0xc8, 0x4f, 0xd8, 0xcc, 0x40, 0xea, 0x44, 0xe9, 0x0e, 0xb0, 0xf8, 0x34, 0xe4, 0x7d, 0x8e,
|
||||
0x15, 0x55, 0x20, 0xd3, 0xc3, 0x96, 0xa5, 0x1c, 0x63, 0xea, 0x87, 0x73, 0x92, 0xf3, 0x28, 0x16,
|
||||
0x61, 0xc1, 0xef, 0x4c, 0xc5, 0x8f, 0xe2, 0xae, 0x24, 0xf1, 0x93, 0x44, 0xf2, 0x04, 0x9b, 0x74,
|
||||
0xda, 0x5c, 0x92, 0x3f, 0xa2, 0x8b, 0x50, 0xa0, 0x43, 0x96, 0x9d, 0xf7, 0xc4, 0x59, 0x27, 0xa5,
|
||||
0x05, 0x4a, 0xbc, 0xcf, 0x99, 0x56, 0x21, 0x6f, 0xac, 0x1b, 0x2e, 0x4b, 0x82, 0xb2, 0x80, 0xb1,
|
||||
0x6e, 0x38, 0x0c, 0x4f, 0xc2, 0x02, 0x99, 0x9f, 0xcb, 0x91, 0xa4, 0x1f, 0xc9, 0x13, 0x1a, 0x67,
|
||||
0x11, 0xff, 0x28, 0x40, 0x79, 0xd4, 0x01, 0xa3, 0x9b, 0x90, 0x24, 0xb1, 0x88, 0x87, 0x95, 0xea,
|
||||
0x1a, 0x0b, 0x54, 0x6b, 0x4e, 0xa0, 0x5a, 0x6b, 0x3a, 0x81, 0x6a, 0x33, 0xfb, 0xc9, 0x67, 0xab,
|
||||
0xb1, 0x8f, 0xfe, 0xb6, 0x1a, 0x97, 0xa8, 0x04, 0x3a, 0x4b, 0x7c, 0xa5, 0xa2, 0xf5, 0x65, 0x4d,
|
||||
0xa5, 0x43, 0xce, 0x11, 0x47, 0xa8, 0x68, 0xfd, 0x6d, 0x15, 0xed, 0x40, 0xb9, 0xad, 0xf7, 0x2d,
|
||||
0xdc, 0xb7, 0x06, 0x96, 0xcc, 0x02, 0x21, 0x0f, 0x26, 0x01, 0x77, 0xc8, 0xc2, 0x6b, 0xcd, 0xe1,
|
||||
0xdc, 0xa7, 0x8c, 0x52, 0xa9, 0x1d, 0x24, 0x10, 0xb7, 0x7a, 0xa2, 0x74, 0x35, 0x55, 0xb1, 0x75,
|
||||
0xd3, 0xaa, 0x24, 0x2f, 0x24, 0x42, 0xfd, 0xe1, 0x7d, 0x87, 0xe5, 0xd0, 0x50, 0x15, 0x1b, 0x6f,
|
||||
0x26, 0xc9, 0x70, 0x25, 0x9f, 0x24, 0x7a, 0x0a, 0x4a, 0x8a, 0x61, 0xc8, 0x96, 0xad, 0xd8, 0x58,
|
||||
0x6e, 0x9d, 0xda, 0xd8, 0xa2, 0x81, 0x66, 0x41, 0x2a, 0x28, 0x86, 0x71, 0x40, 0xa8, 0x9b, 0x84,
|
||||
0x88, 0x2e, 0x41, 0x91, 0xc4, 0x24, 0x4d, 0xe9, 0xca, 0x1d, 0xac, 0x1d, 0x77, 0x6c, 0x1a, 0x52,
|
||||
0x12, 0x52, 0x81, 0x53, 0x1b, 0x94, 0x28, 0xaa, 0xee, 0x8e, 0xd3, 0x78, 0x84, 0x10, 0x24, 0x55,
|
||||
0xc5, 0x56, 0xe8, 0x4a, 0x2e, 0x48, 0xf4, 0x37, 0xa1, 0x19, 0x8a, 0xdd, 0xe1, 0xeb, 0x43, 0x7f,
|
||||
0xa3, 0x33, 0x90, 0xe6, 0x6a, 0x13, 0x54, 0x2d, 0x7f, 0x42, 0xcb, 0x90, 0x32, 0x4c, 0xfd, 0x04,
|
||||
0xd3, 0xad, 0xcb, 0x4a, 0xec, 0x41, 0x7c, 0x5f, 0x80, 0xc5, 0xb1, 0xc8, 0x45, 0xf4, 0x76, 0x14,
|
||||
0xab, 0xe3, 0x7c, 0x8b, 0xfc, 0x46, 0x2f, 0x10, 0xbd, 0x8a, 0x8a, 0x4d, 0x1e, 0xed, 0x2b, 0xe3,
|
||||
0x4b, 0xdd, 0xa0, 0xef, 0xf9, 0xd2, 0x70, 0x6e, 0x74, 0x17, 0xca, 0x5d, 0xc5, 0xb2, 0x65, 0xe6,
|
||||
0xfd, 0x65, 0x5f, 0xe4, 0x7f, 0x62, 0x6c, 0x91, 0x59, 0xac, 0x20, 0x06, 0xcd, 0x95, 0x14, 0x89,
|
||||
0xa8, 0x47, 0x45, 0x87, 0xb0, 0xdc, 0x3a, 0x7d, 0x4f, 0xe9, 0xdb, 0x5a, 0x1f, 0xcb, 0x63, 0xbb,
|
||||
0x36, 0x9e, 0x4a, 0xdc, 0xd3, 0xac, 0x16, 0xee, 0x28, 0x27, 0x9a, 0xee, 0x0c, 0x6b, 0xc9, 0x95,
|
||||
0x77, 0x77, 0xd4, 0x12, 0x25, 0x28, 0x06, 0xc3, 0x2e, 0x2a, 0x82, 0x60, 0x0f, 0xf9, 0xfc, 0x05,
|
||||
0x7b, 0x88, 0x9e, 0x87, 0x24, 0x99, 0x23, 0x9d, 0x7b, 0x31, 0xe4, 0x43, 0x5c, 0xae, 0x79, 0x6a,
|
||||
0x60, 0x89, 0x72, 0x8a, 0xa2, 0x7b, 0x1a, 0xdc, 0x50, 0x3c, 0xaa, 0x55, 0xbc, 0x02, 0xa5, 0x91,
|
||||
0x38, 0xeb, 0xdb, 0xbe, 0xb8, 0x7f, 0xfb, 0xc4, 0x12, 0x14, 0x02, 0x01, 0x55, 0x3c, 0x03, 0xcb,
|
||||
0x61, 0xf1, 0x51, 0xec, 0xb8, 0xf4, 0x40, 0x9c, 0x43, 0x37, 0x20, 0xeb, 0x06, 0x48, 0x76, 0x1a,
|
||||
0xcf, 0x8e, 0xcd, 0xc2, 0x61, 0x96, 0x5c, 0x56, 0x72, 0x0c, 0x89, 0x55, 0x53, 0x73, 0x10, 0xe8,
|
||||
0xc0, 0x33, 0x8a, 0x61, 0x34, 0x14, 0xab, 0x23, 0xbe, 0x05, 0x95, 0xa8, 0xe0, 0x37, 0x32, 0x8d,
|
||||
0xa4, 0x6b, 0x85, 0x67, 0x20, 0x7d, 0xa4, 0x9b, 0x3d, 0xc5, 0xa6, 0xca, 0x0a, 0x12, 0x7f, 0x22,
|
||||
0xd6, 0xc9, 0x02, 0x61, 0x82, 0x92, 0xd9, 0x83, 0x28, 0xc3, 0xd9, 0xc8, 0x00, 0x48, 0x44, 0xb4,
|
||||
0xbe, 0x8a, 0xd9, 0x7a, 0x16, 0x24, 0xf6, 0xe0, 0x29, 0x62, 0x83, 0x65, 0x0f, 0xe4, 0xb3, 0x16,
|
||||
0x9d, 0x2b, 0xd5, 0x9f, 0x93, 0xf8, 0x93, 0xf8, 0xdb, 0x04, 0x9c, 0x09, 0x0f, 0x83, 0xe8, 0x02,
|
||||
0x2c, 0xf4, 0x94, 0xa1, 0x6c, 0x0f, 0xf9, 0x59, 0x66, 0xdb, 0x01, 0x3d, 0x65, 0xd8, 0x1c, 0xb2,
|
||||
0x83, 0x5c, 0x86, 0x84, 0x3d, 0xb4, 0x2a, 0xc2, 0x85, 0xc4, 0xe5, 0x05, 0x89, 0xfc, 0x44, 0x87,
|
||||
0xb0, 0xd8, 0xd5, 0xdb, 0x4a, 0x57, 0xf6, 0x59, 0x3c, 0x37, 0xf6, 0x8b, 0x63, 0x8b, 0xcd, 0x02,
|
||||
0x1a, 0x56, 0xc7, 0x8c, 0xbe, 0x44, 0x75, 0xec, 0xb8, 0x96, 0xff, 0x35, 0x59, 0xbd, 0x6f, 0x8f,
|
||||
0x52, 0x01, 0x4f, 0xe1, 0xf8, 0xec, 0xf4, 0xdc, 0x3e, 0xfb, 0x79, 0x58, 0xee, 0xe3, 0xa1, 0xed,
|
||||
0x1b, 0x23, 0x33, 0x9c, 0x0c, 0xdd, 0x0b, 0x44, 0xde, 0x79, 0xdf, 0x27, 0x36, 0x84, 0xae, 0xd0,
|
||||
0xcc, 0xc2, 0xd0, 0x2d, 0x6c, 0xca, 0x8a, 0xaa, 0x9a, 0xd8, 0xb2, 0x68, 0x66, 0xbb, 0x40, 0xd3,
|
||||
0x05, 0x4a, 0xdf, 0x60, 0x64, 0xf1, 0x17, 0xfe, 0xbd, 0x0a, 0x66, 0x12, 0x7c, 0x27, 0xe2, 0xde,
|
||||
0x4e, 0x1c, 0xc0, 0x32, 0x97, 0x57, 0x03, 0x9b, 0x21, 0xcc, 0xea, 0x79, 0x90, 0x23, 0x3e, 0xc3,
|
||||
0x3e, 0x24, 0x1e, 0x6d, 0x1f, 0x1c, 0x6f, 0x9b, 0xf4, 0x79, 0xdb, 0xff, 0xb2, 0xbd, 0x79, 0xd5,
|
||||
0x8d, 0x22, 0x5e, 0x9a, 0x16, 0x1a, 0x45, 0xbc, 0x79, 0x09, 0x01, 0xf7, 0xf6, 0xcb, 0x38, 0x54,
|
||||
0xa3, 0xf3, 0xb2, 0x50, 0x55, 0xcf, 0xc0, 0xa2, 0x3b, 0x17, 0x77, 0x7c, 0xec, 0xd4, 0x97, 0xdd,
|
||||
0x17, 0x7c, 0x80, 0x91, 0x51, 0xf1, 0x12, 0x14, 0x47, 0xb2, 0x46, 0xb6, 0x0b, 0x85, 0x13, 0xff,
|
||||
0xf7, 0xc5, 0x9f, 0x26, 0x5c, 0xaf, 0x1a, 0x48, 0xed, 0x42, 0x2c, 0xef, 0x75, 0x58, 0x52, 0x71,
|
||||
0x5b, 0x53, 0xbf, 0xac, 0xe1, 0x2d, 0x72, 0xe9, 0x6f, 0xed, 0x6e, 0x06, 0xbb, 0xfb, 0x73, 0x1e,
|
||||
0xb2, 0x12, 0xb6, 0x0c, 0x92, 0xd2, 0xa1, 0x4d, 0xc8, 0xe1, 0x61, 0x1b, 0x1b, 0xb6, 0x93, 0x05,
|
||||
0x87, 0x57, 0x13, 0x8c, 0xbb, 0xee, 0x70, 0x92, 0xda, 0xd8, 0x15, 0x43, 0xd7, 0x39, 0x0c, 0x12,
|
||||
0x8d, 0x68, 0x70, 0x71, 0x3f, 0x0e, 0xf2, 0x82, 0x83, 0x83, 0x24, 0x22, 0x4b, 0x61, 0x26, 0x35,
|
||||
0x02, 0x84, 0x5c, 0xe7, 0x40, 0x48, 0x72, 0xca, 0xc7, 0x02, 0x48, 0x48, 0x2d, 0x80, 0x84, 0xa4,
|
||||
0xa6, 0x4c, 0x33, 0x02, 0x0a, 0x79, 0xc1, 0x81, 0x42, 0xd2, 0x53, 0x46, 0x3c, 0x82, 0x85, 0xdc,
|
||||
0x09, 0x62, 0x21, 0x99, 0x88, 0xd0, 0xe6, 0x48, 0x4f, 0x04, 0x43, 0x5e, 0xf1, 0x81, 0x21, 0xd9,
|
||||
0x48, 0x14, 0x82, 0x29, 0x0a, 0x41, 0x43, 0x5e, 0x0b, 0xa0, 0x21, 0xb9, 0x29, 0xeb, 0x30, 0x01,
|
||||
0x0e, 0xd9, 0xf2, 0xc3, 0x21, 0x10, 0x89, 0xaa, 0xf0, 0x7d, 0x8f, 0xc2, 0x43, 0x5e, 0x72, 0xf1,
|
||||
0x90, 0x7c, 0x24, 0xb0, 0xc3, 0xe7, 0x32, 0x0a, 0x88, 0xec, 0x8d, 0x01, 0x22, 0x0c, 0xc0, 0x78,
|
||||
0x2a, 0x52, 0xc5, 0x14, 0x44, 0x64, 0x6f, 0x0c, 0x11, 0x29, 0x4c, 0x51, 0x38, 0x05, 0x12, 0xf9,
|
||||
0x41, 0x38, 0x24, 0x12, 0x0d, 0x5a, 0xf0, 0x61, 0xce, 0x86, 0x89, 0xc8, 0x11, 0x98, 0x48, 0x29,
|
||||
0xb2, 0x7e, 0x67, 0xea, 0x67, 0x06, 0x45, 0x0e, 0x43, 0x40, 0x11, 0x06, 0x5f, 0x5c, 0x8e, 0x54,
|
||||
0x3e, 0x03, 0x2a, 0x72, 0x18, 0x82, 0x8a, 0x2c, 0x4e, 0x55, 0x3b, 0x15, 0x16, 0xb9, 0x1d, 0x84,
|
||||
0x45, 0xd0, 0x94, 0x33, 0x16, 0x89, 0x8b, 0xb4, 0xa2, 0x70, 0x11, 0x86, 0x5d, 0x3c, 0x1b, 0xa9,
|
||||
0x71, 0x0e, 0x60, 0x64, 0x6f, 0x0c, 0x18, 0x59, 0x9e, 0x62, 0x69, 0xb3, 0x22, 0x23, 0x57, 0x48,
|
||||
0x46, 0x31, 0xe2, 0xaa, 0x49, 0x72, 0x8f, 0x4d, 0x53, 0x37, 0x39, 0xc6, 0xc1, 0x1e, 0xc4, 0xcb,
|
||||
0xa4, 0x52, 0xf6, 0xdc, 0xf2, 0x04, 0x14, 0x85, 0x16, 0x51, 0x3e, 0x57, 0x2c, 0xfe, 0x2e, 0xee,
|
||||
0xc9, 0xd2, 0x02, 0xd3, 0x5f, 0x65, 0xe7, 0x78, 0x95, 0xed, 0xc3, 0x56, 0x84, 0x20, 0xb6, 0xb2,
|
||||
0x0a, 0x79, 0x52, 0x1c, 0x8d, 0xc0, 0x26, 0x8a, 0xe1, 0xc2, 0x26, 0x57, 0x61, 0x91, 0x26, 0x01,
|
||||
0x0c, 0x81, 0xe1, 0x91, 0x35, 0x49, 0x23, 0x6b, 0x89, 0xbc, 0x60, 0xab, 0xc0, 0x42, 0xec, 0x73,
|
||||
0xb0, 0xe4, 0xe3, 0x75, 0x8b, 0x2e, 0x86, 0x21, 0x94, 0x5d, 0xee, 0x0d, 0x5e, 0x7d, 0xfd, 0x21,
|
||||
0xee, 0xad, 0x90, 0x87, 0xb7, 0x84, 0x41, 0x23, 0xf1, 0xaf, 0x08, 0x1a, 0x11, 0xbe, 0x34, 0x34,
|
||||
0xe2, 0x2f, 0x22, 0x13, 0xc1, 0x22, 0xf2, 0x9f, 0x71, 0x6f, 0x4f, 0x5c, 0xa0, 0xa3, 0xad, 0xab,
|
||||
0x98, 0x97, 0x75, 0xf4, 0x37, 0x49, 0xb3, 0xba, 0xfa, 0x31, 0x2f, 0xde, 0xc8, 0x4f, 0xc2, 0xe5,
|
||||
0xc6, 0xce, 0x1c, 0x0f, 0x8d, 0x6e, 0x45, 0xc8, 0x72, 0x17, 0x5e, 0x11, 0x96, 0x21, 0xf1, 0x10,
|
||||
0xb3, 0x48, 0xb7, 0x20, 0x91, 0x9f, 0x84, 0x8f, 0x1a, 0x19, 0xcf, 0x41, 0xd8, 0x03, 0xba, 0x09,
|
||||
0x39, 0xda, 0xae, 0x91, 0x75, 0xc3, 0xe2, 0x01, 0x29, 0x90, 0xae, 0xb1, 0xae, 0xcc, 0xda, 0x3e,
|
||||
0xe1, 0xd9, 0x33, 0x2c, 0x29, 0x6b, 0xf0, 0x5f, 0xbe, 0xa4, 0x29, 0x17, 0x48, 0x9a, 0xce, 0x41,
|
||||
0x8e, 0x8c, 0xde, 0x32, 0x94, 0x36, 0xa6, 0x91, 0x25, 0x27, 0x79, 0x04, 0xf1, 0x01, 0xa0, 0xf1,
|
||||
0x38, 0x89, 0x1a, 0x90, 0xc6, 0x27, 0xb8, 0x6f, 0xb3, 0x9c, 0x32, 0xbf, 0x7e, 0x66, 0xbc, 0x6e,
|
||||
0x24, 0xaf, 0x37, 0x2b, 0x64, 0x91, 0xff, 0xf1, 0xd9, 0x6a, 0x99, 0x71, 0x3f, 0xab, 0xf7, 0x34,
|
||||
0x1b, 0xf7, 0x0c, 0xfb, 0x54, 0xe2, 0xf2, 0xe2, 0x5f, 0x05, 0x28, 0x8d, 0xc4, 0xcf, 0xd0, 0xb5,
|
||||
0x75, 0x4c, 0x5e, 0xf0, 0x01, 0x4b, 0xb3, 0xad, 0xf7, 0x79, 0x80, 0x63, 0xc5, 0x92, 0xdf, 0x55,
|
||||
0xfa, 0x36, 0x56, 0xf9, 0xa2, 0xe7, 0x8e, 0x15, 0xeb, 0x0d, 0x4a, 0x20, 0xbb, 0x4e, 0x5e, 0x0f,
|
||||
0x2c, 0xac, 0x72, 0x88, 0x2b, 0x73, 0xac, 0x58, 0x87, 0x16, 0x56, 0x7d, 0xb3, 0xcc, 0x3c, 0xda,
|
||||
0x2c, 0x83, 0x6b, 0x9c, 0x1d, 0x59, 0x63, 0x5f, 0xdd, 0x9f, 0xf3, 0xd7, 0xfd, 0xa8, 0x0a, 0x59,
|
||||
0xc3, 0xd4, 0x74, 0x53, 0xb3, 0x4f, 0xe9, 0xc6, 0x24, 0x24, 0xf7, 0x19, 0x5d, 0x84, 0x42, 0x0f,
|
||||
0xf7, 0x0c, 0x5d, 0xef, 0xca, 0xcc, 0xd9, 0xe4, 0xa9, 0xe8, 0x02, 0x27, 0xd6, 0xa9, 0xcf, 0xf9,
|
||||
0x40, 0xf0, 0x4e, 0x9f, 0x87, 0xef, 0x7c, 0xb5, 0xcb, 0xbb, 0x12, 0xb2, 0xbc, 0x3e, 0x0a, 0x99,
|
||||
0xc4, 0xc8, 0xfa, 0xba, 0xcf, 0xdf, 0xd4, 0x02, 0x8b, 0x3f, 0xa6, 0xa0, 0x6f, 0x30, 0x37, 0x42,
|
||||
0x07, 0xfe, 0xca, 0x6c, 0x40, 0x9d, 0x82, 0x63, 0xce, 0xb3, 0x7a, 0x0f, 0xaf, 0x82, 0x63, 0x64,
|
||||
0x0b, 0xbd, 0x09, 0x8f, 0x8f, 0x78, 0x36, 0x57, 0xb5, 0x30, 0xab, 0x83, 0x7b, 0x2c, 0xe8, 0xe0,
|
||||
0x1c, 0xd5, 0xde, 0x62, 0x25, 0x1e, 0xf1, 0xcc, 0x6d, 0x43, 0x31, 0x98, 0xe6, 0x85, 0x6e, 0xff,
|
||||
0x45, 0x28, 0x98, 0xd8, 0x56, 0xb4, 0xbe, 0x1c, 0xa8, 0x49, 0x17, 0x18, 0x91, 0xe3, 0xbf, 0xfb,
|
||||
0xf0, 0x58, 0x68, 0xba, 0x87, 0x5e, 0x84, 0x9c, 0x97, 0x29, 0xb2, 0x55, 0x9d, 0x80, 0xe4, 0x79,
|
||||
0xbc, 0xe2, 0xef, 0xe3, 0x9e, 0xca, 0x20, 0x36, 0x58, 0x87, 0xb4, 0x89, 0xad, 0x41, 0x97, 0xa1,
|
||||
0x75, 0xc5, 0xf5, 0xe7, 0x66, 0x4b, 0x14, 0x09, 0x75, 0xd0, 0xb5, 0x25, 0x2e, 0x2c, 0x3e, 0x80,
|
||||
0x34, 0xa3, 0xa0, 0x3c, 0x64, 0x0e, 0x77, 0xef, 0xee, 0xee, 0xbd, 0xb1, 0x5b, 0x8e, 0x21, 0x80,
|
||||
0xf4, 0x46, 0xad, 0x56, 0xdf, 0x6f, 0x96, 0xe3, 0x28, 0x07, 0xa9, 0x8d, 0xcd, 0x3d, 0xa9, 0x59,
|
||||
0x16, 0x08, 0x59, 0xaa, 0xdf, 0xa9, 0xd7, 0x9a, 0xe5, 0x04, 0x5a, 0x84, 0x02, 0xfb, 0x2d, 0xdf,
|
||||
0xde, 0x93, 0xee, 0x6d, 0x34, 0xcb, 0x49, 0x1f, 0xe9, 0xa0, 0xbe, 0xbb, 0x55, 0x97, 0xca, 0x29,
|
||||
0xf1, 0xff, 0xe0, 0x6c, 0x64, 0x6a, 0xe9, 0x01, 0x7f, 0x71, 0x1f, 0xf0, 0x27, 0xfe, 0x5c, 0x80,
|
||||
0x6a, 0x74, 0xbe, 0x88, 0xee, 0x8c, 0x4c, 0x7c, 0x7d, 0x8e, 0x64, 0x73, 0x64, 0xf6, 0xe8, 0x12,
|
||||
0x14, 0x4d, 0x7c, 0x84, 0xed, 0x76, 0x87, 0xe5, 0xaf, 0x2c, 0x60, 0x16, 0xa4, 0x02, 0xa7, 0x52,
|
||||
0x21, 0x8b, 0xb1, 0xbd, 0x8d, 0xdb, 0xb6, 0xcc, 0x7c, 0x11, 0x33, 0xba, 0x1c, 0x61, 0x23, 0xd4,
|
||||
0x03, 0x46, 0x14, 0xdf, 0x9a, 0x6b, 0x2d, 0x73, 0x90, 0x92, 0xea, 0x4d, 0xe9, 0xcd, 0x72, 0x02,
|
||||
0x21, 0x28, 0xd2, 0x9f, 0xf2, 0xc1, 0xee, 0xc6, 0xfe, 0x41, 0x63, 0x8f, 0xac, 0xe5, 0x12, 0x94,
|
||||
0x9c, 0xb5, 0x74, 0x88, 0x29, 0xf1, 0x4f, 0x02, 0x3c, 0x1e, 0x91, 0xed, 0xa2, 0x9b, 0x00, 0xf6,
|
||||
0x50, 0x36, 0x71, 0x5b, 0x37, 0xd5, 0x68, 0x23, 0x6b, 0x0e, 0x25, 0xca, 0x21, 0xe5, 0x6c, 0xfe,
|
||||
0xcb, 0x9a, 0x80, 0x17, 0xa3, 0x97, 0xb9, 0x52, 0x32, 0x2b, 0xe7, 0xa8, 0x9d, 0x0f, 0x81, 0x45,
|
||||
0x71, 0x9b, 0x28, 0xa6, 0x6b, 0x4b, 0x15, 0x53, 0x7e, 0x74, 0x2f, 0xcc, 0xa9, 0xcc, 0xd8, 0xad,
|
||||
0x99, 0xcf, 0x9d, 0xa4, 0x1e, 0xcd, 0x9d, 0x88, 0xbf, 0x4a, 0xf8, 0x17, 0x36, 0x98, 0xdc, 0xef,
|
||||
0x41, 0xda, 0xb2, 0x15, 0x7b, 0x60, 0x71, 0x83, 0x7b, 0x71, 0xd6, 0x4a, 0x61, 0xcd, 0xf9, 0x71,
|
||||
0x40, 0xc5, 0x25, 0xae, 0xe6, 0xdb, 0xf5, 0xb6, 0xc4, 0x1b, 0x50, 0x0c, 0x2e, 0x4e, 0xf4, 0x91,
|
||||
0xf1, 0x7c, 0x8e, 0x20, 0xde, 0xf2, 0xf2, 0x2f, 0x1f, 0x68, 0x39, 0x0e, 0x08, 0xc6, 0xc3, 0x00,
|
||||
0xc1, 0x5f, 0xc7, 0xe1, 0x89, 0x09, 0xf5, 0x12, 0x7a, 0x7d, 0x64, 0x9f, 0x5f, 0x9a, 0xa7, 0xda,
|
||||
0x5a, 0x63, 0xb4, 0xe0, 0x4e, 0x8b, 0xd7, 0x61, 0xc1, 0x4f, 0x9f, 0x6d, 0x92, 0x3f, 0x49, 0x78,
|
||||
0x3e, 0x3f, 0x88, 0x5c, 0x7e, 0x65, 0x89, 0xe6, 0x88, 0x9d, 0x09, 0x73, 0xda, 0x59, 0x68, 0xb2,
|
||||
0x90, 0xf8, 0xfa, 0x92, 0x85, 0xe4, 0x23, 0x26, 0x0b, 0xfe, 0x03, 0x97, 0x0a, 0x1e, 0xb8, 0xb1,
|
||||
0xb8, 0x9e, 0x0e, 0x89, 0xeb, 0x6f, 0x02, 0xf8, 0x1a, 0x9a, 0xcb, 0x90, 0x32, 0xf5, 0x41, 0x5f,
|
||||
0xa5, 0x66, 0x92, 0x92, 0xd8, 0x03, 0xba, 0x01, 0x29, 0x62, 0x6e, 0xce, 0x62, 0x8e, 0x7b, 0x5e,
|
||||
0x62, 0x2e, 0x3e, 0xcc, 0x98, 0x71, 0x8b, 0x1a, 0xa0, 0xf1, 0xa6, 0x52, 0xc4, 0x27, 0x5e, 0x09,
|
||||
0x7e, 0xe2, 0xc9, 0xc8, 0xf6, 0x54, 0xf8, 0xa7, 0xde, 0x83, 0x14, 0x35, 0x0f, 0x92, 0xdf, 0xd0,
|
||||
0xc6, 0x28, 0x2f, 0x98, 0xc9, 0x6f, 0xf4, 0x43, 0x00, 0xc5, 0xb6, 0x4d, 0xad, 0x35, 0xf0, 0x3e,
|
||||
0xb0, 0x1a, 0x6e, 0x5e, 0x1b, 0x0e, 0xdf, 0xe6, 0x39, 0x6e, 0x67, 0xcb, 0x9e, 0xa8, 0xcf, 0xd6,
|
||||
0x7c, 0x0a, 0xc5, 0x5d, 0x28, 0x06, 0x65, 0x9d, 0x12, 0x8f, 0x8d, 0x21, 0x58, 0xe2, 0xb1, 0x8a,
|
||||
0x9d, 0x97, 0x78, 0x6e, 0x81, 0x98, 0x60, 0x3d, 0x70, 0xfa, 0x20, 0xfe, 0x2b, 0x0e, 0x0b, 0x7e,
|
||||
0xeb, 0xfc, 0x5f, 0xab, 0x92, 0xc4, 0x0f, 0xe2, 0x90, 0x75, 0x27, 0x1f, 0xd1, 0x80, 0xf6, 0xd6,
|
||||
0x4e, 0xf0, 0xb7, 0x5b, 0x59, 0x47, 0x3b, 0xe1, 0xf6, 0xc9, 0x6f, 0xb9, 0x09, 0x55, 0x14, 0xa8,
|
||||
0xed, 0x5f, 0x69, 0xe7, 0xaa, 0x00, 0xcf, 0x1f, 0x7f, 0xc6, 0xc7, 0x41, 0x32, 0x09, 0xf4, 0x1d,
|
||||
0x48, 0x2b, 0x6d, 0x17, 0xca, 0x2f, 0x86, 0x60, 0xbb, 0x0e, 0xeb, 0x5a, 0x73, 0xb8, 0x41, 0x39,
|
||||
0x25, 0x2e, 0xc1, 0x47, 0x25, 0xb8, 0x7d, 0xf6, 0x57, 0x89, 0x5e, 0xc6, 0x13, 0x74, 0x9b, 0x45,
|
||||
0x80, 0xc3, 0xdd, 0x7b, 0x7b, 0x5b, 0xdb, 0xb7, 0xb7, 0xeb, 0x5b, 0x3c, 0xa5, 0xda, 0xda, 0xaa,
|
||||
0x6f, 0x95, 0x05, 0xc2, 0x27, 0xd5, 0xef, 0xed, 0xdd, 0xaf, 0x6f, 0x95, 0x13, 0xe2, 0x2d, 0xc8,
|
||||
0xb9, 0xae, 0x07, 0x55, 0x20, 0xe3, 0xb4, 0x25, 0xe2, 0xdc, 0x01, 0xf0, 0x2e, 0xd3, 0x32, 0xa4,
|
||||
0x0c, 0xfd, 0x5d, 0xde, 0x65, 0x4e, 0x48, 0xec, 0x41, 0x54, 0xa1, 0x34, 0xe2, 0xb7, 0xd0, 0x2d,
|
||||
0xc8, 0x18, 0x83, 0x96, 0xec, 0x18, 0xed, 0x48, 0x13, 0xc7, 0x41, 0x1a, 0x06, 0xad, 0xae, 0xd6,
|
||||
0xbe, 0x8b, 0x4f, 0x9d, 0x65, 0x32, 0x06, 0xad, 0xbb, 0xcc, 0xb6, 0xd9, 0x57, 0x04, 0xff, 0x57,
|
||||
0x7e, 0x14, 0x87, 0xac, 0x73, 0x56, 0xd1, 0x77, 0x21, 0xe7, 0xfa, 0x44, 0xf7, 0xee, 0x4d, 0xa4,
|
||||
0x33, 0xe5, 0xfa, 0x3d, 0x11, 0x74, 0x15, 0x16, 0x2d, 0xed, 0xb8, 0xef, 0xf4, 0xb0, 0x18, 0xb4,
|
||||
0x27, 0xd0, 0x43, 0x53, 0x62, 0x2f, 0x76, 0x1c, 0x3c, 0xea, 0x4e, 0x32, 0x9b, 0x28, 0x27, 0xef,
|
||||
0x24, 0xb3, 0xc9, 0x72, 0x8a, 0x84, 0xc5, 0xf2, 0xa8, 0xe3, 0xf8, 0x26, 0x07, 0x13, 0x12, 0xbe,
|
||||
0x13, 0x61, 0xe1, 0xfb, 0x7d, 0x01, 0xf2, 0xbe, 0x2e, 0x19, 0xfa, 0x7f, 0x9f, 0x17, 0x2b, 0x86,
|
||||
0xc4, 0x1d, 0x1f, 0xaf, 0x77, 0xc5, 0x23, 0x38, 0x31, 0x61, 0xfe, 0x89, 0x45, 0x35, 0x25, 0x9d,
|
||||
0x66, 0x5b, 0x72, 0xee, 0x66, 0xdb, 0xb3, 0x80, 0x6c, 0xdd, 0x56, 0xba, 0xf2, 0x89, 0x6e, 0x6b,
|
||||
0xfd, 0x63, 0x99, 0xd9, 0x09, 0xf3, 0x39, 0x65, 0xfa, 0xe6, 0x3e, 0x7d, 0xb1, 0xef, 0x9a, 0x8c,
|
||||
0x5b, 0x03, 0xce, 0x7b, 0x63, 0xe3, 0x0c, 0xa4, 0x79, 0x99, 0xc3, 0xae, 0x6c, 0xf0, 0xa7, 0xd0,
|
||||
0xae, 0x62, 0x15, 0xb2, 0x3d, 0x6c, 0x2b, 0xd4, 0x81, 0xb2, 0x98, 0xe9, 0x3e, 0x5f, 0x7d, 0x09,
|
||||
0xf2, 0xbe, 0xcb, 0x33, 0xc4, 0xa7, 0xee, 0xd6, 0xdf, 0x28, 0xc7, 0xaa, 0x99, 0x0f, 0x3f, 0xbe,
|
||||
0x90, 0xd8, 0xc5, 0xef, 0x92, 0xe3, 0x26, 0xd5, 0x6b, 0x8d, 0x7a, 0xed, 0x6e, 0x39, 0x5e, 0xcd,
|
||||
0x7f, 0xf8, 0xf1, 0x85, 0x8c, 0x84, 0x69, 0x13, 0xe8, 0xea, 0x5d, 0x28, 0x8d, 0x6c, 0x4c, 0xf0,
|
||||
0x74, 0x23, 0x28, 0x6e, 0x1d, 0xee, 0xef, 0x6c, 0xd7, 0x36, 0x9a, 0x75, 0xf9, 0xfe, 0x5e, 0xb3,
|
||||
0x5e, 0x8e, 0xa3, 0xc7, 0x61, 0x69, 0x67, 0xfb, 0xb5, 0x46, 0x53, 0xae, 0xed, 0x6c, 0xd7, 0x77,
|
||||
0x9b, 0xf2, 0x46, 0xb3, 0xb9, 0x51, 0xbb, 0x5b, 0x16, 0xd6, 0x7f, 0x93, 0x87, 0xd2, 0xc6, 0x66,
|
||||
0x6d, 0x9b, 0x14, 0x7a, 0x5a, 0x5b, 0xa1, 0xbe, 0xa2, 0x06, 0x49, 0x8a, 0x28, 0x4f, 0xbc, 0x0e,
|
||||
0x5d, 0x9d, 0xdc, 0x25, 0x44, 0xb7, 0x21, 0x45, 0xc1, 0x66, 0x34, 0xf9, 0x7e, 0x74, 0x75, 0x4a,
|
||||
0xdb, 0x90, 0x0c, 0x86, 0x1e, 0xa7, 0x89, 0x17, 0xa6, 0xab, 0x93, 0xbb, 0x88, 0x68, 0x07, 0x32,
|
||||
0x0e, 0x16, 0x38, 0xed, 0xea, 0x71, 0x75, 0x6a, 0x3b, 0x8e, 0x4c, 0x8d, 0x61, 0xb6, 0x93, 0xef,
|
||||
0x52, 0x57, 0xa7, 0xf4, 0x17, 0xd1, 0x36, 0xa4, 0x39, 0x5c, 0x32, 0xe5, 0x1a, 0x71, 0x75, 0x5a,
|
||||
0x5b, 0x0d, 0x49, 0x90, 0xf3, 0xd0, 0xf0, 0xe9, 0x37, 0xc4, 0xab, 0x33, 0xb4, 0x4e, 0xd1, 0x03,
|
||||
0x28, 0x04, 0x21, 0x98, 0xd9, 0xae, 0x2a, 0x57, 0x67, 0x6c, 0xe0, 0x11, 0xfd, 0x41, 0x3c, 0x66,
|
||||
0xb6, 0xab, 0xcb, 0xd5, 0x19, 0xfb, 0x79, 0xe8, 0x6d, 0x58, 0x1c, 0xc7, 0x4b, 0x66, 0xbf, 0xc9,
|
||||
0x5c, 0x9d, 0xa3, 0xc3, 0x87, 0x7a, 0x80, 0x42, 0x70, 0x96, 0x39, 0x2e, 0x36, 0x57, 0xe7, 0x69,
|
||||
0xf8, 0x21, 0x15, 0x4a, 0xa3, 0xd8, 0xc5, 0xac, 0x17, 0x9d, 0xab, 0x33, 0x37, 0xff, 0xd8, 0x57,
|
||||
0x82, 0x85, 0xfc, 0xac, 0x17, 0x9f, 0xab, 0x33, 0xf7, 0x02, 0xd1, 0x21, 0x80, 0xaf, 0x10, 0x9d,
|
||||
0xe1, 0x22, 0x74, 0x75, 0x96, 0xae, 0x20, 0x32, 0x60, 0x29, 0xac, 0x42, 0x9d, 0xe7, 0x5e, 0x74,
|
||||
0x75, 0xae, 0x66, 0x21, 0xb1, 0xe7, 0x60, 0xad, 0x39, 0xdb, 0x3d, 0xe9, 0xea, 0x8c, 0x5d, 0xc3,
|
||||
0xcd, 0xfa, 0x27, 0x9f, 0xaf, 0xc4, 0x3f, 0xfd, 0x7c, 0x25, 0xfe, 0xf7, 0xcf, 0x57, 0xe2, 0x1f,
|
||||
0x7d, 0xb1, 0x12, 0xfb, 0xf4, 0x8b, 0x95, 0xd8, 0x5f, 0xbe, 0x58, 0x89, 0x7d, 0xef, 0x99, 0x63,
|
||||
0xcd, 0xee, 0x0c, 0x5a, 0x6b, 0x6d, 0xbd, 0x77, 0xcd, 0xff, 0x97, 0x99, 0xb0, 0xbf, 0xf1, 0xb4,
|
||||
0xd2, 0x34, 0xa0, 0x5e, 0xff, 0x4f, 0x00, 0x00, 0x00, 0xff, 0xff, 0x97, 0x52, 0xf8, 0x77, 0xe6,
|
||||
0x33, 0x00, 0x00,
|
||||
}
|
||||
|
||||
// Reference imports to suppress errors if they are not otherwise used.
|
||||
@@ -6222,15 +6265,15 @@ func (m *RequestExtendVote) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
_ = i
|
||||
var l int
|
||||
_ = l
|
||||
if m.Vote != nil {
|
||||
{
|
||||
size, err := m.Vote.MarshalToSizedBuffer(dAtA[:i])
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
i -= size
|
||||
i = encodeVarintTypes(dAtA, i, uint64(size))
|
||||
}
|
||||
if m.Height != 0 {
|
||||
i = encodeVarintTypes(dAtA, i, uint64(m.Height))
|
||||
i--
|
||||
dAtA[i] = 0x10
|
||||
}
|
||||
if len(m.Hash) > 0 {
|
||||
i -= len(m.Hash)
|
||||
copy(dAtA[i:], m.Hash)
|
||||
i = encodeVarintTypes(dAtA, i, uint64(len(m.Hash)))
|
||||
i--
|
||||
dAtA[i] = 0xa
|
||||
}
|
||||
@@ -6257,15 +6300,29 @@ func (m *RequestVerifyVoteExtension) MarshalToSizedBuffer(dAtA []byte) (int, err
|
||||
_ = i
|
||||
var l int
|
||||
_ = l
|
||||
if m.Vote != nil {
|
||||
{
|
||||
size, err := m.Vote.MarshalToSizedBuffer(dAtA[:i])
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
i -= size
|
||||
i = encodeVarintTypes(dAtA, i, uint64(size))
|
||||
}
|
||||
if len(m.VoteExtension) > 0 {
|
||||
i -= len(m.VoteExtension)
|
||||
copy(dAtA[i:], m.VoteExtension)
|
||||
i = encodeVarintTypes(dAtA, i, uint64(len(m.VoteExtension)))
|
||||
i--
|
||||
dAtA[i] = 0x22
|
||||
}
|
||||
if m.Height != 0 {
|
||||
i = encodeVarintTypes(dAtA, i, uint64(m.Height))
|
||||
i--
|
||||
dAtA[i] = 0x18
|
||||
}
|
||||
if len(m.ValidatorAddress) > 0 {
|
||||
i -= len(m.ValidatorAddress)
|
||||
copy(dAtA[i:], m.ValidatorAddress)
|
||||
i = encodeVarintTypes(dAtA, i, uint64(len(m.ValidatorAddress)))
|
||||
i--
|
||||
dAtA[i] = 0x12
|
||||
}
|
||||
if len(m.Hash) > 0 {
|
||||
i -= len(m.Hash)
|
||||
copy(dAtA[i:], m.Hash)
|
||||
i = encodeVarintTypes(dAtA, i, uint64(len(m.Hash)))
|
||||
i--
|
||||
dAtA[i] = 0xa
|
||||
}
|
||||
@@ -6306,12 +6363,12 @@ func (m *RequestFinalizeBlock) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
i--
|
||||
dAtA[i] = 0x3a
|
||||
}
|
||||
n31, err31 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Time, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Time):])
|
||||
if err31 != nil {
|
||||
return 0, err31
|
||||
n29, err29 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Time, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Time):])
|
||||
if err29 != nil {
|
||||
return 0, err29
|
||||
}
|
||||
i -= n31
|
||||
i = encodeVarintTypes(dAtA, i, uint64(n31))
|
||||
i -= n29
|
||||
i = encodeVarintTypes(dAtA, i, uint64(n29))
|
||||
i--
|
||||
dAtA[i] = 0x32
|
||||
if m.Height != 0 {
|
||||
@@ -7541,20 +7598,20 @@ func (m *ResponseApplySnapshotChunk) MarshalToSizedBuffer(dAtA []byte) (int, err
|
||||
}
|
||||
}
|
||||
if len(m.RefetchChunks) > 0 {
|
||||
dAtA57 := make([]byte, len(m.RefetchChunks)*10)
|
||||
var j56 int
|
||||
dAtA55 := make([]byte, len(m.RefetchChunks)*10)
|
||||
var j54 int
|
||||
for _, num := range m.RefetchChunks {
|
||||
for num >= 1<<7 {
|
||||
dAtA57[j56] = uint8(uint64(num)&0x7f | 0x80)
|
||||
dAtA55[j54] = uint8(uint64(num)&0x7f | 0x80)
|
||||
num >>= 7
|
||||
j56++
|
||||
j54++
|
||||
}
|
||||
dAtA57[j56] = uint8(num)
|
||||
j56++
|
||||
dAtA55[j54] = uint8(num)
|
||||
j54++
|
||||
}
|
||||
i -= j56
|
||||
copy(dAtA[i:], dAtA57[:j56])
|
||||
i = encodeVarintTypes(dAtA, i, uint64(j56))
|
||||
i -= j54
|
||||
copy(dAtA[i:], dAtA55[:j54])
|
||||
i = encodeVarintTypes(dAtA, i, uint64(j54))
|
||||
i--
|
||||
dAtA[i] = 0x12
|
||||
}
|
||||
@@ -7745,15 +7802,10 @@ func (m *ResponseExtendVote) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
_ = i
|
||||
var l int
|
||||
_ = l
|
||||
if m.VoteExtension != nil {
|
||||
{
|
||||
size, err := m.VoteExtension.MarshalToSizedBuffer(dAtA[:i])
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
i -= size
|
||||
i = encodeVarintTypes(dAtA, i, uint64(size))
|
||||
}
|
||||
if len(m.VoteExtension) > 0 {
|
||||
i -= len(m.VoteExtension)
|
||||
copy(dAtA[i:], m.VoteExtension)
|
||||
i = encodeVarintTypes(dAtA, i, uint64(len(m.VoteExtension)))
|
||||
i--
|
||||
dAtA[i] = 0xa
|
||||
}
|
||||
@@ -8408,12 +8460,12 @@ func (m *Misbehavior) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
i--
|
||||
dAtA[i] = 0x28
|
||||
}
|
||||
n66, err66 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Time, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Time):])
|
||||
if err66 != nil {
|
||||
return 0, err66
|
||||
n63, err63 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Time, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Time):])
|
||||
if err63 != nil {
|
||||
return 0, err63
|
||||
}
|
||||
i -= n66
|
||||
i = encodeVarintTypes(dAtA, i, uint64(n66))
|
||||
i -= n63
|
||||
i = encodeVarintTypes(dAtA, i, uint64(n63))
|
||||
i--
|
||||
dAtA[i] = 0x22
|
||||
if m.Height != 0 {
|
||||
@@ -9064,10 +9116,13 @@ func (m *RequestExtendVote) Size() (n int) {
|
||||
}
|
||||
var l int
|
||||
_ = l
|
||||
if m.Vote != nil {
|
||||
l = m.Vote.Size()
|
||||
l = len(m.Hash)
|
||||
if l > 0 {
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
if m.Height != 0 {
|
||||
n += 1 + sovTypes(uint64(m.Height))
|
||||
}
|
||||
return n
|
||||
}
|
||||
|
||||
@@ -9077,8 +9132,19 @@ func (m *RequestVerifyVoteExtension) Size() (n int) {
|
||||
}
|
||||
var l int
|
||||
_ = l
|
||||
if m.Vote != nil {
|
||||
l = m.Vote.Size()
|
||||
l = len(m.Hash)
|
||||
if l > 0 {
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
l = len(m.ValidatorAddress)
|
||||
if l > 0 {
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
if m.Height != 0 {
|
||||
n += 1 + sovTypes(uint64(m.Height))
|
||||
}
|
||||
l = len(m.VoteExtension)
|
||||
if l > 0 {
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
return n
|
||||
@@ -9788,8 +9854,8 @@ func (m *ResponseExtendVote) Size() (n int) {
|
||||
}
|
||||
var l int
|
||||
_ = l
|
||||
if m.VoteExtension != nil {
|
||||
l = m.VoteExtension.Size()
|
||||
l = len(m.VoteExtension)
|
||||
if l > 0 {
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
return n
|
||||
@@ -13029,9 +13095,9 @@ func (m *RequestExtendVote) Unmarshal(dAtA []byte) error {
|
||||
switch fieldNum {
|
||||
case 1:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field Vote", wireType)
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field Hash", wireType)
|
||||
}
|
||||
var msglen int
|
||||
var byteLen int
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
@@ -13041,28 +13107,45 @@ func (m *RequestExtendVote) Unmarshal(dAtA []byte) error {
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
msglen |= int(b&0x7F) << shift
|
||||
byteLen |= int(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
if msglen < 0 {
|
||||
if byteLen < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
postIndex := iNdEx + msglen
|
||||
postIndex := iNdEx + byteLen
|
||||
if postIndex < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
if m.Vote == nil {
|
||||
m.Vote = &types1.Vote{}
|
||||
}
|
||||
if err := m.Vote.Unmarshal(dAtA[iNdEx:postIndex]); err != nil {
|
||||
return err
|
||||
m.Hash = append(m.Hash[:0], dAtA[iNdEx:postIndex]...)
|
||||
if m.Hash == nil {
|
||||
m.Hash = []byte{}
|
||||
}
|
||||
iNdEx = postIndex
|
||||
case 2:
|
||||
if wireType != 0 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field Height", wireType)
|
||||
}
|
||||
m.Height = 0
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
m.Height |= int64(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
default:
|
||||
iNdEx = preIndex
|
||||
skippy, err := skipTypes(dAtA[iNdEx:])
|
||||
@@ -13115,9 +13198,9 @@ func (m *RequestVerifyVoteExtension) Unmarshal(dAtA []byte) error {
|
||||
switch fieldNum {
|
||||
case 1:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field Vote", wireType)
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field Hash", wireType)
|
||||
}
|
||||
var msglen int
|
||||
var byteLen int
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
@@ -13127,26 +13210,111 @@ func (m *RequestVerifyVoteExtension) Unmarshal(dAtA []byte) error {
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
msglen |= int(b&0x7F) << shift
|
||||
byteLen |= int(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
if msglen < 0 {
|
||||
if byteLen < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
postIndex := iNdEx + msglen
|
||||
postIndex := iNdEx + byteLen
|
||||
if postIndex < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
if m.Vote == nil {
|
||||
m.Vote = &types1.Vote{}
|
||||
m.Hash = append(m.Hash[:0], dAtA[iNdEx:postIndex]...)
|
||||
if m.Hash == nil {
|
||||
m.Hash = []byte{}
|
||||
}
|
||||
if err := m.Vote.Unmarshal(dAtA[iNdEx:postIndex]); err != nil {
|
||||
return err
|
||||
iNdEx = postIndex
|
||||
case 2:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field ValidatorAddress", wireType)
|
||||
}
|
||||
var byteLen int
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
byteLen |= int(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
if byteLen < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
postIndex := iNdEx + byteLen
|
||||
if postIndex < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
m.ValidatorAddress = append(m.ValidatorAddress[:0], dAtA[iNdEx:postIndex]...)
|
||||
if m.ValidatorAddress == nil {
|
||||
m.ValidatorAddress = []byte{}
|
||||
}
|
||||
iNdEx = postIndex
|
||||
case 3:
|
||||
if wireType != 0 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field Height", wireType)
|
||||
}
|
||||
m.Height = 0
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
m.Height |= int64(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
case 4:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field VoteExtension", wireType)
|
||||
}
|
||||
var byteLen int
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
byteLen |= int(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
if byteLen < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
postIndex := iNdEx + byteLen
|
||||
if postIndex < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
m.VoteExtension = append(m.VoteExtension[:0], dAtA[iNdEx:postIndex]...)
|
||||
if m.VoteExtension == nil {
|
||||
m.VoteExtension = []byte{}
|
||||
}
|
||||
iNdEx = postIndex
|
||||
default:
|
||||
@@ -16926,7 +17094,7 @@ func (m *ResponseExtendVote) Unmarshal(dAtA []byte) error {
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field VoteExtension", wireType)
|
||||
}
|
||||
var msglen int
|
||||
var byteLen int
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
@@ -16936,26 +17104,24 @@ func (m *ResponseExtendVote) Unmarshal(dAtA []byte) error {
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
msglen |= int(b&0x7F) << shift
|
||||
byteLen |= int(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
if msglen < 0 {
|
||||
if byteLen < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
postIndex := iNdEx + msglen
|
||||
postIndex := iNdEx + byteLen
|
||||
if postIndex < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
m.VoteExtension = append(m.VoteExtension[:0], dAtA[iNdEx:postIndex]...)
|
||||
if m.VoteExtension == nil {
|
||||
m.VoteExtension = &types1.VoteExtension{}
|
||||
}
|
||||
if err := m.VoteExtension.Unmarshal(dAtA[iNdEx:postIndex]); err != nil {
|
||||
return err
|
||||
m.VoteExtension = []byte{}
|
||||
}
|
||||
iNdEx = postIndex
|
||||
default:
|
||||
|
||||
@@ -42,7 +42,7 @@ require (
|
||||
github.com/creachadair/taskgroup v0.3.2
|
||||
github.com/golangci/golangci-lint v1.45.2
|
||||
github.com/google/go-cmp v0.5.7
|
||||
github.com/vektra/mockery/v2 v2.10.6
|
||||
github.com/vektra/mockery/v2 v2.11.0
|
||||
gotest.tools v2.2.0+incompatible
|
||||
)
|
||||
|
||||
|
||||
@@ -1055,8 +1055,8 @@ github.com/valyala/bytebufferpool v1.0.0/go.mod h1:6bBcMArwyJ5K/AmCkWv1jt77kVWyC
|
||||
github.com/valyala/fasthttp v1.30.0/go.mod h1:2rsYD01CKFrjjsvFxx75KlEUNpWNBY9JWD3K/7o2Cus=
|
||||
github.com/valyala/quicktemplate v1.7.0/go.mod h1:sqKJnoaOF88V07vkO+9FL8fb9uZg/VPSJnLYn+LmLk8=
|
||||
github.com/valyala/tcplisten v1.0.0/go.mod h1:T0xQ8SeCZGxckz9qRXTfG43PvQ/mcWh7FwZEA7Ioqkc=
|
||||
github.com/vektra/mockery/v2 v2.10.6 h1:iLVqC9FozavYx27ZwfXipuizLBN8YzXlh9x5fufk48w=
|
||||
github.com/vektra/mockery/v2 v2.10.6/go.mod h1:8vf4KDDUptfkyypzdHLuE7OE2xA7Gdt60WgIS8PgD+U=
|
||||
github.com/vektra/mockery/v2 v2.11.0 h1:9NkC3urGvJS9B0ve5aTbFjksbO9f/u5cZFgCTVJ30jg=
|
||||
github.com/vektra/mockery/v2 v2.11.0/go.mod h1:8vf4KDDUptfkyypzdHLuE7OE2xA7Gdt60WgIS8PgD+U=
|
||||
github.com/viki-org/dnscache v0.0.0-20130720023526-c70c1f23c5d8/go.mod h1:dniwbG03GafCjFohMDmz6Zc6oCuiqgH6tGNyXTkHzXE=
|
||||
github.com/vishvananda/netlink v1.1.0/go.mod h1:cTgwzPIzzgDAYoQrMm0EdrjRUBkTqKYppBueQtXaqoE=
|
||||
github.com/vishvananda/netns v0.0.0-20191106174202-0a2b9b5464df/go.mod h1:JP3t17pCcGlemwknint6hfoeCVQrEMVwxRLRjXpq+BU=
|
||||
|
||||
@@ -359,7 +359,7 @@ func (r *Reactor) SwitchToBlockSync(ctx context.Context, state sm.State) error {
|
||||
go r.requestRoutine(ctx, bsCh)
|
||||
go r.poolRoutine(ctx, true, bsCh)
|
||||
|
||||
if err := r.PublishStatus(ctx, types.EventDataBlockSyncStatus{
|
||||
if err := r.PublishStatus(types.EventDataBlockSyncStatus{
|
||||
Complete: false,
|
||||
Height: state.LastBlockHeight,
|
||||
}); err != nil {
|
||||
@@ -609,11 +609,11 @@ func (r *Reactor) GetRemainingSyncTime() time.Duration {
|
||||
return time.Duration(int64(remain * float64(time.Second)))
|
||||
}
|
||||
|
||||
func (r *Reactor) PublishStatus(ctx context.Context, event types.EventDataBlockSyncStatus) error {
|
||||
func (r *Reactor) PublishStatus(event types.EventDataBlockSyncStatus) error {
|
||||
if r.eventBus == nil {
|
||||
return errors.New("event bus is not configured")
|
||||
}
|
||||
return r.eventBus.PublishEventBlockSyncStatus(ctx, event)
|
||||
return r.eventBus.PublishEventBlockSyncStatus(event)
|
||||
}
|
||||
|
||||
// atomicBool is an atomic Boolean, safe for concurrent use by multiple
|
||||
|
||||
@@ -50,7 +50,6 @@ func setup(
|
||||
genDoc *types.GenesisDoc,
|
||||
privVal types.PrivValidator,
|
||||
maxBlockHeights []int64,
|
||||
chBuf uint,
|
||||
) *reactorTestSuite {
|
||||
t.Helper()
|
||||
|
||||
@@ -228,7 +227,7 @@ func TestReactor_AbruptDisconnect(t *testing.T) {
|
||||
genDoc := factory.GenesisDoc(cfg, time.Now(), valSet.Validators, factory.ConsensusParams())
|
||||
maxBlockHeight := int64(64)
|
||||
|
||||
rts := setup(ctx, t, genDoc, privVals[0], []int64{maxBlockHeight, 0}, 0)
|
||||
rts := setup(ctx, t, genDoc, privVals[0], []int64{maxBlockHeight, 0})
|
||||
|
||||
require.Equal(t, maxBlockHeight, rts.reactors[rts.nodes[0]].store.Height())
|
||||
|
||||
@@ -268,7 +267,7 @@ func TestReactor_SyncTime(t *testing.T) {
|
||||
genDoc := factory.GenesisDoc(cfg, time.Now(), valSet.Validators, factory.ConsensusParams())
|
||||
maxBlockHeight := int64(101)
|
||||
|
||||
rts := setup(ctx, t, genDoc, privVals[0], []int64{maxBlockHeight, 0}, 0)
|
||||
rts := setup(ctx, t, genDoc, privVals[0], []int64{maxBlockHeight, 0})
|
||||
require.Equal(t, maxBlockHeight, rts.reactors[rts.nodes[0]].store.Height())
|
||||
rts.start(ctx, t)
|
||||
|
||||
@@ -296,7 +295,7 @@ func TestReactor_NoBlockResponse(t *testing.T) {
|
||||
genDoc := factory.GenesisDoc(cfg, time.Now(), valSet.Validators, factory.ConsensusParams())
|
||||
maxBlockHeight := int64(65)
|
||||
|
||||
rts := setup(ctx, t, genDoc, privVals[0], []int64{maxBlockHeight, 0}, 0)
|
||||
rts := setup(ctx, t, genDoc, privVals[0], []int64{maxBlockHeight, 0})
|
||||
|
||||
require.Equal(t, maxBlockHeight, rts.reactors[rts.nodes[0]].store.Height())
|
||||
|
||||
@@ -348,7 +347,7 @@ func TestReactor_BadBlockStopsPeer(t *testing.T) {
|
||||
valSet, privVals := factory.ValidatorSet(ctx, t, 1, 30)
|
||||
genDoc := factory.GenesisDoc(cfg, time.Now(), valSet.Validators, factory.ConsensusParams())
|
||||
|
||||
rts := setup(ctx, t, genDoc, privVals[0], []int64{maxBlockHeight, 0, 0, 0, 0}, 1000)
|
||||
rts := setup(ctx, t, genDoc, privVals[0], []int64{maxBlockHeight, 0, 0, 0, 0})
|
||||
|
||||
require.Equal(t, maxBlockHeight, rts.reactors[rts.nodes[0]].store.Height())
|
||||
|
||||
|
||||
@@ -96,7 +96,7 @@ func TestByzantinePrevoteEquivocation(t *testing.T) {
|
||||
|
||||
// Make State
|
||||
blockExec := sm.NewBlockExecutor(stateStore, log.NewNopLogger(), proxyAppConnCon, mempool, evpool, blockStore, eventBus, sm.NopMetrics())
|
||||
cs, err := NewState(ctx, logger, thisConfig.Consensus, stateStore, blockExec, blockStore, mempool, evpool, eventBus)
|
||||
cs, err := NewState(logger, thisConfig.Consensus, stateStore, blockExec, blockStore, mempool, evpool, eventBus)
|
||||
require.NoError(t, err)
|
||||
// set private validator
|
||||
pv := privVals[i]
|
||||
@@ -203,7 +203,7 @@ func TestByzantinePrevoteEquivocation(t *testing.T) {
|
||||
proposerAddr := lazyNodeState.privValidatorPubKey.Address()
|
||||
|
||||
block, err := lazyNodeState.blockExec.CreateProposalBlock(
|
||||
ctx, lazyNodeState.Height, lazyNodeState.state, commit, proposerAddr, nil)
|
||||
ctx, lazyNodeState.Height, lazyNodeState.state, commit, proposerAddr, lazyNodeState.LastCommit.GetVotes())
|
||||
require.NoError(t, err)
|
||||
blockParts, err := block.MakePartSet(types.BlockPartSizeBytes)
|
||||
require.NoError(t, err)
|
||||
|
||||
@@ -112,7 +112,8 @@ func (vs *validatorStub) signVote(
|
||||
ctx context.Context,
|
||||
voteType tmproto.SignedMsgType,
|
||||
chainID string,
|
||||
blockID types.BlockID) (*types.Vote, error) {
|
||||
blockID types.BlockID,
|
||||
voteExtension []byte) (*types.Vote, error) {
|
||||
|
||||
pubKey, err := vs.PrivValidator.GetPubKey(ctx)
|
||||
if err != nil {
|
||||
@@ -120,28 +121,30 @@ func (vs *validatorStub) signVote(
|
||||
}
|
||||
|
||||
vote := &types.Vote{
|
||||
ValidatorIndex: vs.Index,
|
||||
ValidatorAddress: pubKey.Address(),
|
||||
Type: voteType,
|
||||
Height: vs.Height,
|
||||
Round: vs.Round,
|
||||
Timestamp: vs.clock.Now(),
|
||||
Type: voteType,
|
||||
BlockID: blockID,
|
||||
VoteExtension: types.VoteExtensionFromProto(kvstore.ConstructVoteExtension(pubKey.Address())),
|
||||
Timestamp: vs.clock.Now(),
|
||||
ValidatorAddress: pubKey.Address(),
|
||||
ValidatorIndex: vs.Index,
|
||||
Extension: voteExtension,
|
||||
}
|
||||
v := vote.ToProto()
|
||||
if err := vs.PrivValidator.SignVote(ctx, chainID, v); err != nil {
|
||||
if err = vs.PrivValidator.SignVote(ctx, chainID, v); err != nil {
|
||||
return nil, fmt.Errorf("sign vote failed: %w", err)
|
||||
}
|
||||
|
||||
// ref: signVote in FilePV, the vote should use the privious vote info when the sign data is the same.
|
||||
// ref: signVote in FilePV, the vote should use the previous vote info when the sign data is the same.
|
||||
if signDataIsEqual(vs.lastVote, v) {
|
||||
v.Signature = vs.lastVote.Signature
|
||||
v.Timestamp = vs.lastVote.Timestamp
|
||||
v.ExtensionSignature = vs.lastVote.ExtensionSignature
|
||||
}
|
||||
|
||||
vote.Signature = v.Signature
|
||||
vote.Timestamp = v.Timestamp
|
||||
vote.ExtensionSignature = v.ExtensionSignature
|
||||
|
||||
return vote, err
|
||||
}
|
||||
@@ -155,13 +158,9 @@ func signVote(
|
||||
chainID string,
|
||||
blockID types.BlockID) *types.Vote {
|
||||
|
||||
v, err := vs.signVote(ctx, voteType, chainID, blockID)
|
||||
v, err := vs.signVote(ctx, voteType, chainID, blockID, []byte("extension"))
|
||||
require.NoError(t, err, "failed to sign vote")
|
||||
|
||||
// TODO: remove hardcoded vote extension.
|
||||
// currently set for abci/examples/kvstore/persistent_kvstore.go
|
||||
v.VoteExtension = types.VoteExtensionFromProto(kvstore.ConstructVoteExtension(v.ValidatorAddress))
|
||||
|
||||
vs.lastVote = v
|
||||
|
||||
return v
|
||||
@@ -351,18 +350,19 @@ func validatePrecommit(
|
||||
require.True(t, bytes.Equal(vote.BlockID.Hash, votedBlockHash), "Expected precommit to be for proposal block")
|
||||
}
|
||||
|
||||
rs := cs.GetRoundState()
|
||||
if lockedBlockHash == nil {
|
||||
require.False(t, cs.LockedRound != lockRound || cs.LockedBlock != nil,
|
||||
require.False(t, rs.LockedRound != lockRound || rs.LockedBlock != nil,
|
||||
"Expected to be locked on nil at round %d. Got locked at round %d with block %v",
|
||||
lockRound,
|
||||
cs.LockedRound,
|
||||
cs.LockedBlock)
|
||||
rs.LockedRound,
|
||||
rs.LockedBlock)
|
||||
} else {
|
||||
require.False(t, cs.LockedRound != lockRound || !bytes.Equal(cs.LockedBlock.Hash(), lockedBlockHash),
|
||||
require.False(t, rs.LockedRound != lockRound || !bytes.Equal(rs.LockedBlock.Hash(), lockedBlockHash),
|
||||
"Expected block to be locked on round %d, got %d. Got locked block %X, expected %X",
|
||||
lockRound,
|
||||
cs.LockedRound,
|
||||
cs.LockedBlock.Hash(),
|
||||
rs.LockedRound,
|
||||
rs.LockedBlock.Hash(),
|
||||
lockedBlockHash)
|
||||
}
|
||||
}
|
||||
@@ -491,8 +491,7 @@ func newStateWithConfigAndBlockStore(
|
||||
require.NoError(t, eventBus.Start(ctx))
|
||||
|
||||
blockExec := sm.NewBlockExecutor(stateStore, logger, proxyAppConnCon, mempool, evpool, blockStore, eventBus, sm.NopMetrics())
|
||||
cs, err := NewState(ctx,
|
||||
logger.With("module", "consensus"),
|
||||
cs, err := NewState(logger.With("module", "consensus"),
|
||||
thisConfig.Consensus,
|
||||
stateStore,
|
||||
blockExec,
|
||||
@@ -731,10 +730,9 @@ func ensureVoteMatch(t *testing.T, voteCh <-chan tmpubsub.Message, height int64,
|
||||
msg.Data())
|
||||
|
||||
vote := voteEvent.Vote
|
||||
require.Equal(t, height, vote.Height)
|
||||
require.Equal(t, round, vote.Round)
|
||||
|
||||
require.Equal(t, voteType, vote.Type)
|
||||
require.Equal(t, height, vote.Height, "expected height %d, but got %d", height, vote.Height)
|
||||
require.Equal(t, round, vote.Round, "expected round %d, but got %d", round, vote.Round)
|
||||
require.Equal(t, voteType, vote.Type, "expected type %s, but got %s", voteType, vote.Type)
|
||||
if hash == nil {
|
||||
require.Nil(t, vote.BlockID.Hash, "Expected prevote to be for nil, got %X", vote.BlockID.Hash)
|
||||
} else {
|
||||
@@ -742,6 +740,7 @@ func ensureVoteMatch(t *testing.T, voteCh <-chan tmpubsub.Message, height int64,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func ensureVote(t *testing.T, voteCh <-chan tmpubsub.Message, height int64, round int32, voteType tmproto.SignedMsgType) {
|
||||
t.Helper()
|
||||
msg := ensureMessageBeforeTimeout(t, voteCh, ensureTimeout)
|
||||
@@ -750,10 +749,9 @@ func ensureVote(t *testing.T, voteCh <-chan tmpubsub.Message, height int64, roun
|
||||
msg.Data())
|
||||
|
||||
vote := voteEvent.Vote
|
||||
require.Equal(t, height, vote.Height)
|
||||
require.Equal(t, round, vote.Round)
|
||||
|
||||
require.Equal(t, voteType, vote.Type)
|
||||
require.Equal(t, height, vote.Height, "expected height %d, but got %d", height, vote.Height)
|
||||
require.Equal(t, round, vote.Round, "expected round %d, but got %d", round, vote.Round)
|
||||
require.Equal(t, voteType, vote.Type, "expected type %s, but got %s", voteType, vote.Type)
|
||||
}
|
||||
|
||||
func ensureNewEventOnChannel(t *testing.T, ch <-chan tmpubsub.Message) {
|
||||
@@ -987,5 +985,6 @@ func signDataIsEqual(v1 *types.Vote, v2 *tmproto.Vote) bool {
|
||||
v1.Height == v2.GetHeight() &&
|
||||
v1.Round == v2.Round &&
|
||||
bytes.Equal(v1.ValidatorAddress.Bytes(), v2.GetValidatorAddress()) &&
|
||||
v1.ValidatorIndex == v2.GetValidatorIndex()
|
||||
v1.ValidatorIndex == v2.GetValidatorIndex() &&
|
||||
bytes.Equal(v1.Extension, v2.Extension)
|
||||
}
|
||||
|
||||
@@ -357,11 +357,6 @@ func TestConsMsgsVectors(t *testing.T) {
|
||||
}
|
||||
pbProposal := proposal.ToProto()
|
||||
|
||||
ext := types.VoteExtension{
|
||||
AppDataToSign: []byte("signed"),
|
||||
AppDataSelfAuthenticating: []byte("auth"),
|
||||
}
|
||||
|
||||
v := &types.Vote{
|
||||
ValidatorAddress: []byte("add_more_exclamation"),
|
||||
ValidatorIndex: 1,
|
||||
@@ -370,7 +365,7 @@ func TestConsMsgsVectors(t *testing.T) {
|
||||
Timestamp: date,
|
||||
Type: tmproto.PrecommitType,
|
||||
BlockID: bi,
|
||||
VoteExtension: ext,
|
||||
Extension: []byte("extension"),
|
||||
}
|
||||
vpb := v.ToProto()
|
||||
|
||||
@@ -407,7 +402,7 @@ func TestConsMsgsVectors(t *testing.T) {
|
||||
"2a36080110011a3008011204746573741a26080110011a206164645f6d6f72655f6578636c616d6174696f6e5f6d61726b735f636f64652d"},
|
||||
{"Vote", &tmcons.Message{Sum: &tmcons.Message_Vote{
|
||||
Vote: &tmcons.Vote{Vote: vpb}}},
|
||||
"3280010a7e0802100122480a206164645f6d6f72655f6578636c616d6174696f6e5f6d61726b735f636f64652d1224080112206164645f6d6f72655f6578636c616d6174696f6e5f6d61726b735f636f64652d2a0608c0b89fdc0532146164645f6d6f72655f6578636c616d6174696f6e38014a0e0a067369676e6564120461757468"},
|
||||
"327b0a790802100122480a206164645f6d6f72655f6578636c616d6174696f6e5f6d61726b735f636f64652d1224080112206164645f6d6f72655f6578636c616d6174696f6e5f6d61726b735f636f64652d2a0608c0b89fdc0532146164645f6d6f72655f6578636c616d6174696f6e38014a09657874656e73696f6e"},
|
||||
{"HasVote", &tmcons.Message{Sum: &tmcons.Message_HasVote{
|
||||
HasVote: &tmcons.HasVote{Height: 1, Round: 1, Type: tmproto.PrevoteType, Index: 1}}},
|
||||
"3a080801100118012001"},
|
||||
|
||||
@@ -210,7 +210,7 @@ func (r *Reactor) OnStart(ctx context.Context) error {
|
||||
// leak the goroutine when stopping the reactor.
|
||||
go r.peerStatsRoutine(ctx, peerUpdates)
|
||||
|
||||
r.subscribeToBroadcastEvents(chBundle.state)
|
||||
r.subscribeToBroadcastEvents(ctx, chBundle.state)
|
||||
|
||||
if !r.WaitSync() {
|
||||
if err := r.state.Start(ctx); err != nil {
|
||||
@@ -260,7 +260,7 @@ func (r *Reactor) SwitchToConsensus(ctx context.Context, state sm.State, skipWAL
|
||||
|
||||
// NOTE: The line below causes broadcastNewRoundStepRoutine() to broadcast a
|
||||
// NewRoundStepMessage.
|
||||
r.state.updateToState(ctx, state)
|
||||
r.state.updateToState(state)
|
||||
if err := r.state.Start(ctx); err != nil {
|
||||
panic(fmt.Sprintf(`failed to start consensus state: %v
|
||||
|
||||
@@ -284,7 +284,7 @@ conR:
|
||||
}
|
||||
|
||||
d := types.EventDataBlockSyncStatus{Complete: true, Height: state.LastBlockHeight}
|
||||
if err := r.eventBus.PublishEventBlockSyncStatus(ctx, d); err != nil {
|
||||
if err := r.eventBus.PublishEventBlockSyncStatus(d); err != nil {
|
||||
r.logger.Error("failed to emit the blocksync complete event", "err", err)
|
||||
}
|
||||
}
|
||||
@@ -344,13 +344,13 @@ func (r *Reactor) broadcastHasVoteMessage(ctx context.Context, vote *types.Vote,
|
||||
// subscribeToBroadcastEvents subscribes for new round steps and votes using the
|
||||
// internal pubsub defined in the consensus state to broadcast them to peers
|
||||
// upon receiving.
|
||||
func (r *Reactor) subscribeToBroadcastEvents(stateCh *p2p.Channel) {
|
||||
func (r *Reactor) subscribeToBroadcastEvents(ctx context.Context, stateCh *p2p.Channel) {
|
||||
onStopCh := r.state.getOnStopCh()
|
||||
|
||||
err := r.state.evsw.AddListenerForEvent(
|
||||
listenerIDConsensus,
|
||||
types.EventNewRoundStepValue,
|
||||
func(ctx context.Context, data tmevents.EventData) error {
|
||||
func(data tmevents.EventData) error {
|
||||
if err := r.broadcastNewRoundStepMessage(ctx, data.(*cstypes.RoundState), stateCh); err != nil {
|
||||
return err
|
||||
}
|
||||
@@ -371,7 +371,7 @@ func (r *Reactor) subscribeToBroadcastEvents(stateCh *p2p.Channel) {
|
||||
err = r.state.evsw.AddListenerForEvent(
|
||||
listenerIDConsensus,
|
||||
types.EventValidBlockValue,
|
||||
func(ctx context.Context, data tmevents.EventData) error {
|
||||
func(data tmevents.EventData) error {
|
||||
return r.broadcastNewValidBlockMessage(ctx, data.(*cstypes.RoundState), stateCh)
|
||||
},
|
||||
)
|
||||
@@ -382,7 +382,7 @@ func (r *Reactor) subscribeToBroadcastEvents(stateCh *p2p.Channel) {
|
||||
err = r.state.evsw.AddListenerForEvent(
|
||||
listenerIDConsensus,
|
||||
types.EventVoteValue,
|
||||
func(ctx context.Context, data tmevents.EventData) error {
|
||||
func(data tmevents.EventData) error {
|
||||
return r.broadcastHasVoteMessage(ctx, data.(*types.Vote), stateCh)
|
||||
},
|
||||
)
|
||||
|
||||
@@ -505,7 +505,7 @@ func TestReactorWithEvidence(t *testing.T) {
|
||||
|
||||
blockExec := sm.NewBlockExecutor(stateStore, log.NewNopLogger(), proxyAppConnCon, mempool, evpool, blockStore, eventBus, sm.NopMetrics())
|
||||
|
||||
cs, err := NewState(ctx, logger.With("validator", i, "module", "consensus"),
|
||||
cs, err := NewState(logger.With("validator", i, "module", "consensus"),
|
||||
thisConfig.Consensus, stateStore, blockExec, blockStore, mempool, evpool2, eventBus)
|
||||
require.NoError(t, err)
|
||||
cs.SetPrivValidator(ctx, pv)
|
||||
|
||||
@@ -429,7 +429,7 @@ func (h *Handshaker) ReplayBlocks(
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
mockApp, err := newMockProxyApp(ctx, h.logger, appHash, abciResponses)
|
||||
mockApp, err := newMockProxyApp(h.logger, appHash, abciResponses)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
@@ -145,7 +145,7 @@ func (pb *playback) replayReset(ctx context.Context, count int, newStepSub event
|
||||
pb.cs.Stop()
|
||||
pb.cs.Wait()
|
||||
|
||||
newCS, err := NewState(ctx, pb.cs.logger, pb.cs.config, pb.stateStore, pb.cs.blockExec,
|
||||
newCS, err := NewState(pb.cs.logger, pb.cs.config, pb.stateStore, pb.cs.blockExec,
|
||||
pb.cs.blockStore, pb.cs.txNotifier, pb.cs.evpool, pb.cs.eventBus)
|
||||
if err != nil {
|
||||
return err
|
||||
@@ -350,7 +350,7 @@ func newConsensusStateForReplay(
|
||||
mempool, evpool := emptyMempool{}, sm.EmptyEvidencePool{}
|
||||
blockExec := sm.NewBlockExecutor(stateStore, logger, proxyApp, mempool, evpool, blockStore, eventBus, sm.NopMetrics())
|
||||
|
||||
consensusState, err := NewState(ctx, logger, csConfig, stateStore, blockExec,
|
||||
consensusState, err := NewState(logger, csConfig, stateStore, blockExec,
|
||||
blockStore, mempool, evpool, eventBus)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
|
||||
@@ -57,7 +57,6 @@ func (emptyMempool) CloseWAL() {}
|
||||
// the real app.
|
||||
|
||||
func newMockProxyApp(
|
||||
ctx context.Context,
|
||||
logger log.Logger,
|
||||
appHash []byte,
|
||||
abciResponses *tmstate.ABCIResponses,
|
||||
|
||||
+41
-43
@@ -194,7 +194,6 @@ func SkipStateStoreBootstrap(sm *State) {
|
||||
|
||||
// NewState returns a new State.
|
||||
func NewState(
|
||||
ctx context.Context,
|
||||
logger log.Logger,
|
||||
cfg *config.ConsensusConfig,
|
||||
store sm.Store,
|
||||
@@ -240,7 +239,7 @@ func NewState(
|
||||
// node-fragments gracefully while letting the nodes
|
||||
// themselves avoid this.
|
||||
if !cs.skipBootstrapping {
|
||||
if err := cs.updateStateFromStore(ctx); err != nil {
|
||||
if err := cs.updateStateFromStore(); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
}
|
||||
@@ -248,7 +247,7 @@ func NewState(
|
||||
return cs, nil
|
||||
}
|
||||
|
||||
func (cs *State) updateStateFromStore(ctx context.Context) error {
|
||||
func (cs *State) updateStateFromStore() error {
|
||||
if cs.initialStatePopulated {
|
||||
return nil
|
||||
}
|
||||
@@ -265,7 +264,7 @@ func (cs *State) updateStateFromStore(ctx context.Context) error {
|
||||
cs.reconstructLastCommit(state)
|
||||
}
|
||||
|
||||
cs.updateToState(ctx, state)
|
||||
cs.updateToState(state)
|
||||
|
||||
cs.initialStatePopulated = true
|
||||
return nil
|
||||
@@ -393,7 +392,7 @@ func (cs *State) LoadCommit(height int64) *types.Commit {
|
||||
// OnStart loads the latest state via the WAL, and starts the timeout and
|
||||
// receive routines.
|
||||
func (cs *State) OnStart(ctx context.Context) error {
|
||||
if err := cs.updateStateFromStore(ctx); err != nil {
|
||||
if err := cs.updateStateFromStore(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
@@ -718,7 +717,7 @@ func (cs *State) reconstructLastCommit(state sm.State) {
|
||||
|
||||
// Updates State and increments height to match that of state.
|
||||
// The round becomes 0 and cs.Step becomes cstypes.RoundStepNewHeight.
|
||||
func (cs *State) updateToState(ctx context.Context, state sm.State) {
|
||||
func (cs *State) updateToState(state sm.State) {
|
||||
if cs.CommitRound > -1 && 0 < cs.Height && cs.Height != state.LastBlockHeight {
|
||||
panic(fmt.Sprintf(
|
||||
"updateToState() expected state height of %v but found %v",
|
||||
@@ -753,7 +752,7 @@ func (cs *State) updateToState(ctx context.Context, state sm.State) {
|
||||
"new_height", state.LastBlockHeight+1,
|
||||
"old_height", cs.state.LastBlockHeight+1,
|
||||
)
|
||||
cs.newStep(ctx)
|
||||
cs.newStep()
|
||||
return
|
||||
}
|
||||
}
|
||||
@@ -823,10 +822,10 @@ func (cs *State) updateToState(ctx context.Context, state sm.State) {
|
||||
cs.state = state
|
||||
|
||||
// Finally, broadcast RoundState
|
||||
cs.newStep(ctx)
|
||||
cs.newStep()
|
||||
}
|
||||
|
||||
func (cs *State) newStep(ctx context.Context) {
|
||||
func (cs *State) newStep() {
|
||||
rs := cs.RoundStateEvent()
|
||||
if err := cs.wal.Write(rs); err != nil {
|
||||
cs.logger.Error("failed writing to WAL", "err", err)
|
||||
@@ -836,11 +835,11 @@ func (cs *State) newStep(ctx context.Context) {
|
||||
|
||||
// newStep is called by updateToState in NewState before the eventBus is set!
|
||||
if cs.eventBus != nil {
|
||||
if err := cs.eventBus.PublishEventNewRoundStep(ctx, rs); err != nil {
|
||||
if err := cs.eventBus.PublishEventNewRoundStep(rs); err != nil {
|
||||
cs.logger.Error("failed publishing new round step", "err", err)
|
||||
}
|
||||
|
||||
cs.evsw.FireEvent(ctx, types.EventNewRoundStepValue, &cs.RoundState)
|
||||
cs.evsw.FireEvent(types.EventNewRoundStepValue, &cs.RoundState)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -923,7 +922,6 @@ func (cs *State) receiveRoutine(ctx context.Context, maxSteps int) {
|
||||
if err := cs.wal.Write(mi); err != nil {
|
||||
cs.logger.Error("failed writing to WAL", "err", err)
|
||||
}
|
||||
|
||||
// handles proposals, block parts, votes
|
||||
// may generate internal events (votes, complete proposals, 2/3 majorities)
|
||||
cs.handleMsg(ctx, mi)
|
||||
@@ -977,7 +975,7 @@ func (cs *State) handleMsg(ctx context.Context, mi msgInfo) {
|
||||
|
||||
case *BlockPartMessage:
|
||||
// if the proposal is complete, we'll enterPrevote or tryFinalizeCommit
|
||||
added, err = cs.addProposalBlockPart(ctx, msg, peerID)
|
||||
added, err = cs.addProposalBlockPart(msg, peerID)
|
||||
|
||||
// We unlock here to yield to any routines that need to read the the RoundState.
|
||||
// Previously, this code held the lock from the point at which the final block
|
||||
@@ -1083,21 +1081,21 @@ func (cs *State) handleTimeout(
|
||||
cs.enterPropose(ctx, ti.Height, 0)
|
||||
|
||||
case cstypes.RoundStepPropose:
|
||||
if err := cs.eventBus.PublishEventTimeoutPropose(ctx, cs.RoundStateEvent()); err != nil {
|
||||
if err := cs.eventBus.PublishEventTimeoutPropose(cs.RoundStateEvent()); err != nil {
|
||||
cs.logger.Error("failed publishing timeout propose", "err", err)
|
||||
}
|
||||
|
||||
cs.enterPrevote(ctx, ti.Height, ti.Round)
|
||||
|
||||
case cstypes.RoundStepPrevoteWait:
|
||||
if err := cs.eventBus.PublishEventTimeoutWait(ctx, cs.RoundStateEvent()); err != nil {
|
||||
if err := cs.eventBus.PublishEventTimeoutWait(cs.RoundStateEvent()); err != nil {
|
||||
cs.logger.Error("failed publishing timeout wait", "err", err)
|
||||
}
|
||||
|
||||
cs.enterPrecommit(ctx, ti.Height, ti.Round)
|
||||
|
||||
case cstypes.RoundStepPrecommitWait:
|
||||
if err := cs.eventBus.PublishEventTimeoutWait(ctx, cs.RoundStateEvent()); err != nil {
|
||||
if err := cs.eventBus.PublishEventTimeoutWait(cs.RoundStateEvent()); err != nil {
|
||||
cs.logger.Error("failed publishing timeout wait", "err", err)
|
||||
}
|
||||
|
||||
@@ -1200,7 +1198,7 @@ func (cs *State) enterNewRound(ctx context.Context, height int64, round int32) {
|
||||
cs.Votes.SetRound(r) // also track next round (round+1) to allow round-skipping
|
||||
cs.TriggeredTimeoutPrecommit = false
|
||||
|
||||
if err := cs.eventBus.PublishEventNewRound(ctx, cs.NewRoundEvent()); err != nil {
|
||||
if err := cs.eventBus.PublishEventNewRound(cs.NewRoundEvent()); err != nil {
|
||||
cs.logger.Error("failed publishing new round", "err", err)
|
||||
}
|
||||
// Wait for txs to be available in the mempool
|
||||
@@ -1263,7 +1261,7 @@ func (cs *State) enterPropose(ctx context.Context, height int64, round int32) {
|
||||
defer func() {
|
||||
// Done enterPropose:
|
||||
cs.updateRoundStep(round, cstypes.RoundStepPropose)
|
||||
cs.newStep(ctx)
|
||||
cs.newStep()
|
||||
|
||||
// If we have the whole proposal + POL, then goto Prevote now.
|
||||
// else, we'll enterPrevote when the rest of the proposal is received (in AddProposalBlockPart),
|
||||
@@ -1455,7 +1453,7 @@ func (cs *State) enterPrevote(ctx context.Context, height int64, round int32) {
|
||||
defer func() {
|
||||
// Done enterPrevote:
|
||||
cs.updateRoundStep(round, cstypes.RoundStepPrevote)
|
||||
cs.newStep(ctx)
|
||||
cs.newStep()
|
||||
}()
|
||||
|
||||
logger.Debug("entering prevote step", "current", fmt.Sprintf("%v/%v/%v", cs.Height, cs.Round, cs.Step))
|
||||
@@ -1606,7 +1604,7 @@ func (cs *State) defaultDoPrevote(ctx context.Context, height int64, round int32
|
||||
}
|
||||
|
||||
// Enter: any +2/3 prevotes at next round.
|
||||
func (cs *State) enterPrevoteWait(ctx context.Context, height int64, round int32) {
|
||||
func (cs *State) enterPrevoteWait(height int64, round int32) {
|
||||
logger := cs.logger.With("height", height, "round", round)
|
||||
|
||||
if cs.Height != height || round < cs.Round || (cs.Round == round && cstypes.RoundStepPrevoteWait <= cs.Step) {
|
||||
@@ -1629,7 +1627,7 @@ func (cs *State) enterPrevoteWait(ctx context.Context, height int64, round int32
|
||||
defer func() {
|
||||
// Done enterPrevoteWait:
|
||||
cs.updateRoundStep(round, cstypes.RoundStepPrevoteWait)
|
||||
cs.newStep(ctx)
|
||||
cs.newStep()
|
||||
}()
|
||||
|
||||
// Wait for some more prevotes; enterPrecommit
|
||||
@@ -1657,7 +1655,7 @@ func (cs *State) enterPrecommit(ctx context.Context, height int64, round int32)
|
||||
defer func() {
|
||||
// Done enterPrecommit:
|
||||
cs.updateRoundStep(round, cstypes.RoundStepPrecommit)
|
||||
cs.newStep(ctx)
|
||||
cs.newStep()
|
||||
}()
|
||||
|
||||
// check for a polka
|
||||
@@ -1676,7 +1674,7 @@ func (cs *State) enterPrecommit(ctx context.Context, height int64, round int32)
|
||||
}
|
||||
|
||||
// At this point +2/3 prevoted for a particular block or nil.
|
||||
if err := cs.eventBus.PublishEventPolka(ctx, cs.RoundStateEvent()); err != nil {
|
||||
if err := cs.eventBus.PublishEventPolka(cs.RoundStateEvent()); err != nil {
|
||||
logger.Error("failed publishing polka", "err", err)
|
||||
}
|
||||
|
||||
@@ -1713,7 +1711,7 @@ func (cs *State) enterPrecommit(ctx context.Context, height int64, round int32)
|
||||
logger.Debug("precommit step: +2/3 prevoted locked block; relocking")
|
||||
cs.LockedRound = round
|
||||
|
||||
if err := cs.eventBus.PublishEventRelock(ctx, cs.RoundStateEvent()); err != nil {
|
||||
if err := cs.eventBus.PublishEventRelock(cs.RoundStateEvent()); err != nil {
|
||||
logger.Error("precommit step: failed publishing event relock", "err", err)
|
||||
}
|
||||
|
||||
@@ -1736,7 +1734,7 @@ func (cs *State) enterPrecommit(ctx context.Context, height int64, round int32)
|
||||
cs.LockedBlock = cs.ProposalBlock
|
||||
cs.LockedBlockParts = cs.ProposalBlockParts
|
||||
|
||||
if err := cs.eventBus.PublishEventLock(ctx, cs.RoundStateEvent()); err != nil {
|
||||
if err := cs.eventBus.PublishEventLock(cs.RoundStateEvent()); err != nil {
|
||||
logger.Error("precommit step: failed publishing event lock", "err", err)
|
||||
}
|
||||
|
||||
@@ -1758,7 +1756,7 @@ func (cs *State) enterPrecommit(ctx context.Context, height int64, round int32)
|
||||
}
|
||||
|
||||
// Enter: any +2/3 precommits for next round.
|
||||
func (cs *State) enterPrecommitWait(ctx context.Context, height int64, round int32) {
|
||||
func (cs *State) enterPrecommitWait(height int64, round int32) {
|
||||
logger := cs.logger.With("height", height, "round", round)
|
||||
|
||||
if cs.Height != height || round < cs.Round || (cs.Round == round && cs.TriggeredTimeoutPrecommit) {
|
||||
@@ -1782,7 +1780,7 @@ func (cs *State) enterPrecommitWait(ctx context.Context, height int64, round int
|
||||
defer func() {
|
||||
// Done enterPrecommitWait:
|
||||
cs.TriggeredTimeoutPrecommit = true
|
||||
cs.newStep(ctx)
|
||||
cs.newStep()
|
||||
}()
|
||||
|
||||
// wait for some more precommits; enterNewRound
|
||||
@@ -1809,7 +1807,7 @@ func (cs *State) enterCommit(ctx context.Context, height int64, commitRound int3
|
||||
cs.updateRoundStep(cs.Round, cstypes.RoundStepCommit)
|
||||
cs.CommitRound = commitRound
|
||||
cs.CommitTime = tmtime.Now()
|
||||
cs.newStep(ctx)
|
||||
cs.newStep()
|
||||
|
||||
// Maybe finalize immediately.
|
||||
cs.tryFinalizeCommit(ctx, height)
|
||||
@@ -1844,11 +1842,11 @@ func (cs *State) enterCommit(ctx context.Context, height int64, commitRound int3
|
||||
cs.metrics.MarkBlockGossipStarted()
|
||||
cs.ProposalBlockParts = types.NewPartSetFromHeader(blockID.PartSetHeader)
|
||||
|
||||
if err := cs.eventBus.PublishEventValidBlock(ctx, cs.RoundStateEvent()); err != nil {
|
||||
if err := cs.eventBus.PublishEventValidBlock(cs.RoundStateEvent()); err != nil {
|
||||
logger.Error("failed publishing valid block", "err", err)
|
||||
}
|
||||
|
||||
cs.evsw.FireEvent(ctx, types.EventValidBlockValue, &cs.RoundState)
|
||||
cs.evsw.FireEvent(types.EventValidBlockValue, &cs.RoundState)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1975,7 +1973,7 @@ func (cs *State) finalizeCommit(ctx context.Context, height int64) {
|
||||
cs.RecordMetrics(height, block)
|
||||
|
||||
// NewHeightStep!
|
||||
cs.updateToState(ctx, stateCopy)
|
||||
cs.updateToState(stateCopy)
|
||||
|
||||
// Private validator might have changed it's key pair => refetch pubkey.
|
||||
if err := cs.updatePrivValidatorPubKey(ctx); err != nil {
|
||||
@@ -2130,7 +2128,6 @@ func (cs *State) defaultSetProposal(proposal *types.Proposal, recvTime time.Time
|
||||
// Asynchronously triggers either enterPrevote (before we timeout of propose) or tryFinalizeCommit,
|
||||
// once we have the full block.
|
||||
func (cs *State) addProposalBlockPart(
|
||||
ctx context.Context,
|
||||
msg *BlockPartMessage,
|
||||
peerID types.NodeID,
|
||||
) (added bool, err error) {
|
||||
@@ -2196,7 +2193,7 @@ func (cs *State) addProposalBlockPart(
|
||||
// NOTE: it's possible to receive complete proposal blocks for future rounds without having the proposal
|
||||
cs.logger.Info("received complete proposal block", "height", cs.ProposalBlock.Height, "hash", cs.ProposalBlock.Hash())
|
||||
|
||||
if err := cs.eventBus.PublishEventCompleteProposal(ctx, cs.CompleteProposalEvent()); err != nil {
|
||||
if err := cs.eventBus.PublishEventCompleteProposal(cs.CompleteProposalEvent()); err != nil {
|
||||
cs.logger.Error("failed publishing event complete proposal", "err", err)
|
||||
}
|
||||
}
|
||||
@@ -2315,11 +2312,11 @@ func (cs *State) addVote(
|
||||
}
|
||||
|
||||
cs.logger.Debug("added vote to last precommits", "last_commit", cs.LastCommit.StringShort())
|
||||
if err := cs.eventBus.PublishEventVote(ctx, types.EventDataVote{Vote: vote}); err != nil {
|
||||
if err := cs.eventBus.PublishEventVote(types.EventDataVote{Vote: vote}); err != nil {
|
||||
return added, err
|
||||
}
|
||||
|
||||
cs.evsw.FireEvent(ctx, types.EventVoteValue, vote)
|
||||
cs.evsw.FireEvent(types.EventVoteValue, vote)
|
||||
|
||||
// if we can skip timeoutCommit and have all the votes now,
|
||||
if cs.bypassCommitTimeout() && cs.LastCommit.HasAll() {
|
||||
@@ -2352,10 +2349,10 @@ func (cs *State) addVote(
|
||||
return
|
||||
}
|
||||
|
||||
if err := cs.eventBus.PublishEventVote(ctx, types.EventDataVote{Vote: vote}); err != nil {
|
||||
if err := cs.eventBus.PublishEventVote(types.EventDataVote{Vote: vote}); err != nil {
|
||||
return added, err
|
||||
}
|
||||
cs.evsw.FireEvent(ctx, types.EventVoteValue, vote)
|
||||
cs.evsw.FireEvent(types.EventVoteValue, vote)
|
||||
|
||||
switch vote.Type {
|
||||
case tmproto.PrevoteType:
|
||||
@@ -2390,8 +2387,8 @@ func (cs *State) addVote(
|
||||
cs.ProposalBlockParts = types.NewPartSetFromHeader(blockID.PartSetHeader)
|
||||
}
|
||||
|
||||
cs.evsw.FireEvent(ctx, types.EventValidBlockValue, &cs.RoundState)
|
||||
if err := cs.eventBus.PublishEventValidBlock(ctx, cs.RoundStateEvent()); err != nil {
|
||||
cs.evsw.FireEvent(types.EventValidBlockValue, &cs.RoundState)
|
||||
if err := cs.eventBus.PublishEventValidBlock(cs.RoundStateEvent()); err != nil {
|
||||
return added, err
|
||||
}
|
||||
}
|
||||
@@ -2408,7 +2405,7 @@ func (cs *State) addVote(
|
||||
if ok && (cs.isProposalComplete() || blockID.IsNil()) {
|
||||
cs.enterPrecommit(ctx, height, vote.Round)
|
||||
} else if prevotes.HasTwoThirdsAny() {
|
||||
cs.enterPrevoteWait(ctx, height, vote.Round)
|
||||
cs.enterPrevoteWait(height, vote.Round)
|
||||
}
|
||||
|
||||
case cs.Proposal != nil && 0 <= cs.Proposal.POLRound && cs.Proposal.POLRound == vote.Round:
|
||||
@@ -2439,11 +2436,11 @@ func (cs *State) addVote(
|
||||
cs.enterNewRound(ctx, cs.Height, 0)
|
||||
}
|
||||
} else {
|
||||
cs.enterPrecommitWait(ctx, height, vote.Round)
|
||||
cs.enterPrecommitWait(height, vote.Round)
|
||||
}
|
||||
} else if cs.Round <= vote.Round && precommits.HasTwoThirdsAny() {
|
||||
cs.enterNewRound(ctx, height, vote.Round)
|
||||
cs.enterPrecommitWait(ctx, height, vote.Round)
|
||||
cs.enterPrecommitWait(height, vote.Round)
|
||||
}
|
||||
|
||||
default:
|
||||
@@ -2494,7 +2491,7 @@ func (cs *State) signVote(
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
vote.VoteExtension = ext
|
||||
vote.Extension = ext
|
||||
default:
|
||||
timeout = time.Second
|
||||
}
|
||||
@@ -2506,6 +2503,7 @@ func (cs *State) signVote(
|
||||
|
||||
err := cs.privValidator.SignVote(ctxto, cs.state.ChainID, v)
|
||||
vote.Signature = v.Signature
|
||||
vote.ExtensionSignature = v.ExtensionSignature
|
||||
vote.Timestamp = v.Timestamp
|
||||
|
||||
return vote, err
|
||||
|
||||
@@ -2015,6 +2015,235 @@ func TestFinalizeBlockCalled(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
// TestExtendVoteCalled tests that the vote extension methods are called at the
|
||||
// correct point in the consensus algorithm.
|
||||
func TestExtendVoteCalled(t *testing.T) {
|
||||
config := configSetup(t)
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
m := abcimocks.NewBaseMock()
|
||||
m.On("ProcessProposal", mock.Anything).Return(abci.ResponseProcessProposal{Status: abci.ResponseProcessProposal_ACCEPT})
|
||||
m.On("ExtendVote", mock.Anything).Return(abci.ResponseExtendVote{
|
||||
VoteExtension: []byte("extension"),
|
||||
})
|
||||
m.On("VerifyVoteExtension", mock.Anything).Return(abci.ResponseVerifyVoteExtension{
|
||||
Status: abci.ResponseVerifyVoteExtension_ACCEPT,
|
||||
})
|
||||
m.On("FinalizeBlock", mock.Anything).Return(abci.ResponseFinalizeBlock{}).Maybe()
|
||||
cs1, vss := makeState(ctx, t, makeStateArgs{config: config, application: m})
|
||||
height, round := cs1.Height, cs1.Round
|
||||
|
||||
proposalCh := subscribe(ctx, t, cs1.eventBus, types.EventQueryCompleteProposal)
|
||||
newRoundCh := subscribe(ctx, t, cs1.eventBus, types.EventQueryNewRound)
|
||||
pv1, err := cs1.privValidator.GetPubKey(ctx)
|
||||
require.NoError(t, err)
|
||||
addr := pv1.Address()
|
||||
voteCh := subscribeToVoter(ctx, t, cs1, addr)
|
||||
|
||||
startTestRound(ctx, cs1, cs1.Height, round)
|
||||
ensureNewRound(t, newRoundCh, height, round)
|
||||
ensureNewProposal(t, proposalCh, height, round)
|
||||
|
||||
m.AssertNotCalled(t, "ExtendVote", mock.Anything)
|
||||
|
||||
rs := cs1.GetRoundState()
|
||||
|
||||
blockID := types.BlockID{
|
||||
Hash: rs.ProposalBlock.Hash(),
|
||||
PartSetHeader: rs.ProposalBlockParts.Header(),
|
||||
}
|
||||
signAddVotes(ctx, t, cs1, tmproto.PrevoteType, config.ChainID(), blockID, vss[1:]...)
|
||||
ensurePrevoteMatch(t, voteCh, height, round, blockID.Hash)
|
||||
|
||||
ensurePrecommit(t, voteCh, height, round)
|
||||
|
||||
m.AssertCalled(t, "ExtendVote", abci.RequestExtendVote{
|
||||
Height: height,
|
||||
Hash: blockID.Hash,
|
||||
})
|
||||
|
||||
m.AssertCalled(t, "VerifyVoteExtension", abci.RequestVerifyVoteExtension{
|
||||
Hash: blockID.Hash,
|
||||
ValidatorAddress: addr,
|
||||
Height: height,
|
||||
VoteExtension: []byte("extension"),
|
||||
})
|
||||
|
||||
signAddVotes(ctx, t, cs1, tmproto.PrecommitType, config.ChainID(), blockID, vss[1:]...)
|
||||
ensureNewRound(t, newRoundCh, height+1, 0)
|
||||
m.AssertExpectations(t)
|
||||
|
||||
// Only 3 of the vote extensions are seen, as consensus proceeds as soon as the +2/3 threshold
|
||||
// is observed by the consensus engine.
|
||||
for _, pv := range vss[:3] {
|
||||
pv, err := pv.GetPubKey(ctx)
|
||||
require.NoError(t, err)
|
||||
addr := pv.Address()
|
||||
m.AssertCalled(t, "VerifyVoteExtension", abci.RequestVerifyVoteExtension{
|
||||
Hash: blockID.Hash,
|
||||
ValidatorAddress: addr,
|
||||
Height: height,
|
||||
VoteExtension: []byte("extension"),
|
||||
})
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// TestVerifyVoteExtensionNotCalledOnAbsentPrecommit tests that the VerifyVoteExtension
|
||||
// method is not called for a validator's vote that is never delivered.
|
||||
func TestVerifyVoteExtensionNotCalledOnAbsentPrecommit(t *testing.T) {
|
||||
config := configSetup(t)
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
m := abcimocks.NewBaseMock()
|
||||
m.On("ProcessProposal", mock.Anything).Return(abci.ResponseProcessProposal{Status: abci.ResponseProcessProposal_ACCEPT})
|
||||
m.On("ExtendVote", mock.Anything).Return(abci.ResponseExtendVote{
|
||||
VoteExtension: []byte("extension"),
|
||||
})
|
||||
m.On("VerifyVoteExtension", mock.Anything).Return(abci.ResponseVerifyVoteExtension{
|
||||
Status: abci.ResponseVerifyVoteExtension_ACCEPT,
|
||||
})
|
||||
m.On("FinalizeBlock", mock.Anything).Return(abci.ResponseFinalizeBlock{}).Maybe()
|
||||
cs1, vss := makeState(ctx, t, makeStateArgs{config: config, application: m})
|
||||
height, round := cs1.Height, cs1.Round
|
||||
|
||||
proposalCh := subscribe(ctx, t, cs1.eventBus, types.EventQueryCompleteProposal)
|
||||
newRoundCh := subscribe(ctx, t, cs1.eventBus, types.EventQueryNewRound)
|
||||
pv1, err := cs1.privValidator.GetPubKey(ctx)
|
||||
require.NoError(t, err)
|
||||
addr := pv1.Address()
|
||||
voteCh := subscribeToVoter(ctx, t, cs1, addr)
|
||||
|
||||
startTestRound(ctx, cs1, cs1.Height, round)
|
||||
ensureNewRound(t, newRoundCh, height, round)
|
||||
ensureNewProposal(t, proposalCh, height, round)
|
||||
rs := cs1.GetRoundState()
|
||||
|
||||
blockID := types.BlockID{
|
||||
Hash: rs.ProposalBlock.Hash(),
|
||||
PartSetHeader: rs.ProposalBlockParts.Header(),
|
||||
}
|
||||
signAddVotes(ctx, t, cs1, tmproto.PrevoteType, config.ChainID(), blockID, vss[2:]...)
|
||||
ensurePrevoteMatch(t, voteCh, height, round, blockID.Hash)
|
||||
|
||||
ensurePrecommit(t, voteCh, height, round)
|
||||
|
||||
m.AssertCalled(t, "ExtendVote", abci.RequestExtendVote{
|
||||
Height: height,
|
||||
Hash: blockID.Hash,
|
||||
})
|
||||
|
||||
m.AssertCalled(t, "VerifyVoteExtension", abci.RequestVerifyVoteExtension{
|
||||
Hash: blockID.Hash,
|
||||
ValidatorAddress: addr,
|
||||
Height: height,
|
||||
VoteExtension: []byte("extension"),
|
||||
})
|
||||
|
||||
signAddVotes(ctx, t, cs1, tmproto.PrecommitType, config.ChainID(), blockID, vss[2:]...)
|
||||
ensureNewRound(t, newRoundCh, height+1, 0)
|
||||
m.AssertExpectations(t)
|
||||
|
||||
// vss[1] did not issue a precommit for the block, ensure that a vote extension
|
||||
// for its address was not sent to the application.
|
||||
pv, err := vss[1].GetPubKey(ctx)
|
||||
require.NoError(t, err)
|
||||
addr = pv.Address()
|
||||
|
||||
m.AssertNotCalled(t, "VerifyVoteExtension", abci.RequestVerifyVoteExtension{
|
||||
Hash: blockID.Hash,
|
||||
ValidatorAddress: addr,
|
||||
Height: height,
|
||||
VoteExtension: []byte("extension"),
|
||||
})
|
||||
|
||||
}
|
||||
|
||||
// TestPrepareProposalReceivesVoteExtensions tests that the PrepareProposal method
|
||||
// is called with the vote extensions from the previous height. The test functions
|
||||
// be completing a consensus height with a mock application as the proposer. The
|
||||
// test then proceeds to fail sever rounds of consensus until the mock application
|
||||
// is the proposer again and ensures that the mock application receives the set of
|
||||
// vote extensions from the previous consensus instance.
|
||||
func TestPrepareProposalReceivesVoteExtensions(t *testing.T) {
|
||||
config := configSetup(t)
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
// create a list of vote extensions, one for each validator.
|
||||
voteExtensions := [][]byte{
|
||||
[]byte("extension 0"),
|
||||
[]byte("extension 1"),
|
||||
[]byte("extension 2"),
|
||||
[]byte("extension 3"),
|
||||
}
|
||||
|
||||
m := abcimocks.NewBaseMock()
|
||||
m.On("ExtendVote", mock.Anything).Return(abci.ResponseExtendVote{
|
||||
VoteExtension: voteExtensions[0],
|
||||
})
|
||||
m.On("PrepareProposal", mock.Anything).Return(abci.ResponsePrepareProposal{}).Once()
|
||||
|
||||
cs1, vss := makeState(ctx, t, makeStateArgs{config: config, application: m})
|
||||
height, round := cs1.Height, cs1.Round
|
||||
|
||||
newRoundCh := subscribe(ctx, t, cs1.eventBus, types.EventQueryNewRound)
|
||||
proposalCh := subscribe(ctx, t, cs1.eventBus, types.EventQueryCompleteProposal)
|
||||
pv1, err := cs1.privValidator.GetPubKey(ctx)
|
||||
require.NoError(t, err)
|
||||
addr := pv1.Address()
|
||||
voteCh := subscribeToVoter(ctx, t, cs1, addr)
|
||||
|
||||
startTestRound(ctx, cs1, height, round)
|
||||
ensureNewRound(t, newRoundCh, height, round)
|
||||
ensureNewProposal(t, proposalCh, height, round)
|
||||
|
||||
rs := cs1.GetRoundState()
|
||||
blockID := types.BlockID{
|
||||
Hash: rs.ProposalBlock.Hash(),
|
||||
PartSetHeader: rs.ProposalBlockParts.Header(),
|
||||
}
|
||||
signAddVotes(ctx, t, cs1, tmproto.PrevoteType, config.ChainID(), blockID, vss[1:]...)
|
||||
|
||||
// create a precommit for each validator with the associated vote extension.
|
||||
for i, vs := range vss[1:] {
|
||||
signAddPrecommitWithExtension(ctx, t, cs1, config.ChainID(), blockID, voteExtensions[i+1], vs)
|
||||
}
|
||||
|
||||
ensurePrevote(t, voteCh, height, round)
|
||||
|
||||
// ensure that the height is committed.
|
||||
ensurePrecommitMatch(t, voteCh, height, round, blockID.Hash)
|
||||
incrementHeight(vss[1:]...)
|
||||
|
||||
height++
|
||||
round = 0
|
||||
ensureNewRound(t, newRoundCh, height, round)
|
||||
incrementRound(vss[1:]...)
|
||||
incrementRound(vss[1:]...)
|
||||
incrementRound(vss[1:]...)
|
||||
round = 3
|
||||
|
||||
// capture the prepare proposal request.
|
||||
rpp := abci.RequestPrepareProposal{}
|
||||
m.On("PrepareProposal", mock.MatchedBy(func(r abci.RequestPrepareProposal) bool {
|
||||
rpp = r
|
||||
return true
|
||||
})).Return(abci.ResponsePrepareProposal{})
|
||||
|
||||
signAddVotes(ctx, t, cs1, tmproto.PrecommitType, config.ChainID(), types.BlockID{}, vss[1:]...)
|
||||
ensureNewRound(t, newRoundCh, height, round)
|
||||
ensureNewProposal(t, proposalCh, height, round)
|
||||
|
||||
// ensure that the proposer received the list of vote extensions from the
|
||||
// previous height.
|
||||
for i := range vss {
|
||||
require.Equal(t, rpp.LocalLastCommit.Votes[i].VoteExtension, voteExtensions[i])
|
||||
}
|
||||
}
|
||||
|
||||
// 4 vals, 3 Nil Precommits at P0
|
||||
// What we want:
|
||||
// P0 waits for timeoutPrecommit before starting next round
|
||||
@@ -2719,3 +2948,15 @@ func subscribe(
|
||||
}()
|
||||
return ch
|
||||
}
|
||||
|
||||
func signAddPrecommitWithExtension(ctx context.Context,
|
||||
t *testing.T,
|
||||
cs *State,
|
||||
chainID string,
|
||||
blockID types.BlockID,
|
||||
extension []byte,
|
||||
stub *validatorStub) {
|
||||
v, err := stub.signVote(ctx, tmproto.PrecommitType, chainID, blockID, extension)
|
||||
require.NoError(t, err, "failed to sign vote")
|
||||
addVotes(cs, v)
|
||||
}
|
||||
|
||||
@@ -88,6 +88,7 @@ func makeVoteHR(
|
||||
require.NoError(t, err, "Error signing vote")
|
||||
|
||||
vote.Signature = v.Signature
|
||||
vote.ExtensionSignature = v.ExtensionSignature
|
||||
|
||||
return vote
|
||||
}
|
||||
|
||||
@@ -81,7 +81,7 @@ func WALGenerateNBlocks(ctx context.Context, t *testing.T, logger log.Logger, wr
|
||||
mempool := emptyMempool{}
|
||||
evpool := sm.EmptyEvidencePool{}
|
||||
blockExec := sm.NewBlockExecutor(stateStore, log.NewNopLogger(), proxyApp, mempool, evpool, blockStore, eventBus, sm.NopMetrics())
|
||||
consensusState, err := NewState(ctx, logger, cfg.Consensus, stateStore, blockExec, blockStore, mempool, evpool, eventBus)
|
||||
consensusState, err := NewState(logger, cfg.Consensus, stateStore, blockExec, blockStore, mempool, evpool, eventBus)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
@@ -66,7 +66,7 @@ func (b *EventBus) Observe(ctx context.Context, observe func(tmpubsub.Message) e
|
||||
return b.pubsub.Observe(ctx, observe, queries...)
|
||||
}
|
||||
|
||||
func (b *EventBus) Publish(ctx context.Context, eventValue string, eventData types.EventData) error {
|
||||
func (b *EventBus) Publish(eventValue string, eventData types.EventData) error {
|
||||
tokens := strings.Split(types.EventTypeKey, ".")
|
||||
event := abci.Event{
|
||||
Type: tokens[0],
|
||||
@@ -78,19 +78,19 @@ func (b *EventBus) Publish(ctx context.Context, eventValue string, eventData typ
|
||||
},
|
||||
}
|
||||
|
||||
return b.pubsub.PublishWithEvents(ctx, eventData, []abci.Event{event})
|
||||
return b.pubsub.PublishWithEvents(eventData, []abci.Event{event})
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventNewBlock(ctx context.Context, data types.EventDataNewBlock) error {
|
||||
func (b *EventBus) PublishEventNewBlock(data types.EventDataNewBlock) error {
|
||||
events := data.ResultFinalizeBlock.Events
|
||||
|
||||
// add Tendermint-reserved new block event
|
||||
events = append(events, types.EventNewBlock)
|
||||
|
||||
return b.pubsub.PublishWithEvents(ctx, data, events)
|
||||
return b.pubsub.PublishWithEvents(data, events)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventNewBlockHeader(ctx context.Context, data types.EventDataNewBlockHeader) error {
|
||||
func (b *EventBus) PublishEventNewBlockHeader(data types.EventDataNewBlockHeader) error {
|
||||
// no explicit deadline for publishing events
|
||||
|
||||
events := data.ResultFinalizeBlock.Events
|
||||
@@ -98,33 +98,33 @@ func (b *EventBus) PublishEventNewBlockHeader(ctx context.Context, data types.Ev
|
||||
// add Tendermint-reserved new block header event
|
||||
events = append(events, types.EventNewBlockHeader)
|
||||
|
||||
return b.pubsub.PublishWithEvents(ctx, data, events)
|
||||
return b.pubsub.PublishWithEvents(data, events)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventNewEvidence(ctx context.Context, evidence types.EventDataNewEvidence) error {
|
||||
return b.Publish(ctx, types.EventNewEvidenceValue, evidence)
|
||||
func (b *EventBus) PublishEventNewEvidence(evidence types.EventDataNewEvidence) error {
|
||||
return b.Publish(types.EventNewEvidenceValue, evidence)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventVote(ctx context.Context, data types.EventDataVote) error {
|
||||
return b.Publish(ctx, types.EventVoteValue, data)
|
||||
func (b *EventBus) PublishEventVote(data types.EventDataVote) error {
|
||||
return b.Publish(types.EventVoteValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventValidBlock(ctx context.Context, data types.EventDataRoundState) error {
|
||||
return b.Publish(ctx, types.EventValidBlockValue, data)
|
||||
func (b *EventBus) PublishEventValidBlock(data types.EventDataRoundState) error {
|
||||
return b.Publish(types.EventValidBlockValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventBlockSyncStatus(ctx context.Context, data types.EventDataBlockSyncStatus) error {
|
||||
return b.Publish(ctx, types.EventBlockSyncStatusValue, data)
|
||||
func (b *EventBus) PublishEventBlockSyncStatus(data types.EventDataBlockSyncStatus) error {
|
||||
return b.Publish(types.EventBlockSyncStatusValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventStateSyncStatus(ctx context.Context, data types.EventDataStateSyncStatus) error {
|
||||
return b.Publish(ctx, types.EventStateSyncStatusValue, data)
|
||||
func (b *EventBus) PublishEventStateSyncStatus(data types.EventDataStateSyncStatus) error {
|
||||
return b.Publish(types.EventStateSyncStatusValue, data)
|
||||
}
|
||||
|
||||
// PublishEventTx publishes tx event with events from Result. Note it will add
|
||||
// predefined keys (EventTypeKey, TxHashKey). Existing events with the same keys
|
||||
// will be overwritten.
|
||||
func (b *EventBus) PublishEventTx(ctx context.Context, data types.EventDataTx) error {
|
||||
func (b *EventBus) PublishEventTx(data types.EventDataTx) error {
|
||||
events := data.Result.Events
|
||||
|
||||
// add Tendermint-reserved events
|
||||
@@ -152,45 +152,45 @@ func (b *EventBus) PublishEventTx(ctx context.Context, data types.EventDataTx) e
|
||||
},
|
||||
})
|
||||
|
||||
return b.pubsub.PublishWithEvents(ctx, data, events)
|
||||
return b.pubsub.PublishWithEvents(data, events)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventNewRoundStep(ctx context.Context, data types.EventDataRoundState) error {
|
||||
return b.Publish(ctx, types.EventNewRoundStepValue, data)
|
||||
func (b *EventBus) PublishEventNewRoundStep(data types.EventDataRoundState) error {
|
||||
return b.Publish(types.EventNewRoundStepValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventTimeoutPropose(ctx context.Context, data types.EventDataRoundState) error {
|
||||
return b.Publish(ctx, types.EventTimeoutProposeValue, data)
|
||||
func (b *EventBus) PublishEventTimeoutPropose(data types.EventDataRoundState) error {
|
||||
return b.Publish(types.EventTimeoutProposeValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventTimeoutWait(ctx context.Context, data types.EventDataRoundState) error {
|
||||
return b.Publish(ctx, types.EventTimeoutWaitValue, data)
|
||||
func (b *EventBus) PublishEventTimeoutWait(data types.EventDataRoundState) error {
|
||||
return b.Publish(types.EventTimeoutWaitValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventNewRound(ctx context.Context, data types.EventDataNewRound) error {
|
||||
return b.Publish(ctx, types.EventNewRoundValue, data)
|
||||
func (b *EventBus) PublishEventNewRound(data types.EventDataNewRound) error {
|
||||
return b.Publish(types.EventNewRoundValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventCompleteProposal(ctx context.Context, data types.EventDataCompleteProposal) error {
|
||||
return b.Publish(ctx, types.EventCompleteProposalValue, data)
|
||||
func (b *EventBus) PublishEventCompleteProposal(data types.EventDataCompleteProposal) error {
|
||||
return b.Publish(types.EventCompleteProposalValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventPolka(ctx context.Context, data types.EventDataRoundState) error {
|
||||
return b.Publish(ctx, types.EventPolkaValue, data)
|
||||
func (b *EventBus) PublishEventPolka(data types.EventDataRoundState) error {
|
||||
return b.Publish(types.EventPolkaValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventRelock(ctx context.Context, data types.EventDataRoundState) error {
|
||||
return b.Publish(ctx, types.EventRelockValue, data)
|
||||
func (b *EventBus) PublishEventRelock(data types.EventDataRoundState) error {
|
||||
return b.Publish(types.EventRelockValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventLock(ctx context.Context, data types.EventDataRoundState) error {
|
||||
return b.Publish(ctx, types.EventLockValue, data)
|
||||
func (b *EventBus) PublishEventLock(data types.EventDataRoundState) error {
|
||||
return b.Publish(types.EventLockValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventValidatorSetUpdates(ctx context.Context, data types.EventDataValidatorSetUpdates) error {
|
||||
return b.Publish(ctx, types.EventValidatorSetUpdatesValue, data)
|
||||
func (b *EventBus) PublishEventValidatorSetUpdates(data types.EventDataValidatorSetUpdates) error {
|
||||
return b.Publish(types.EventValidatorSetUpdatesValue, data)
|
||||
}
|
||||
|
||||
func (b *EventBus) PublishEventEvidenceValidated(ctx context.Context, evidence types.EventDataEvidenceValidated) error {
|
||||
return b.Publish(ctx, types.EventEvidenceValidatedValue, evidence)
|
||||
func (b *EventBus) PublishEventEvidenceValidated(evidence types.EventDataEvidenceValidated) error {
|
||||
return b.Publish(types.EventEvidenceValidatedValue, evidence)
|
||||
}
|
||||
|
||||
@@ -55,7 +55,7 @@ func TestEventBusPublishEventTx(t *testing.T) {
|
||||
assert.Equal(t, result, edt.Result)
|
||||
}()
|
||||
|
||||
err = eventBus.PublishEventTx(ctx, types.EventDataTx{
|
||||
err = eventBus.PublishEventTx(types.EventDataTx{
|
||||
TxResult: abci.TxResult{
|
||||
Height: 1,
|
||||
Index: 0,
|
||||
@@ -112,7 +112,7 @@ func TestEventBusPublishEventNewBlock(t *testing.T) {
|
||||
assert.Equal(t, resultFinalizeBlock, edt.ResultFinalizeBlock)
|
||||
}()
|
||||
|
||||
err = eventBus.PublishEventNewBlock(ctx, types.EventDataNewBlock{
|
||||
err = eventBus.PublishEventNewBlock(types.EventDataNewBlock{
|
||||
Block: block,
|
||||
BlockID: blockID,
|
||||
ResultFinalizeBlock: resultFinalizeBlock,
|
||||
@@ -223,7 +223,7 @@ func TestEventBusPublishEventTxDuplicateKeys(t *testing.T) {
|
||||
}
|
||||
}()
|
||||
|
||||
assert.NoError(t, eventBus.PublishEventTx(ctx, types.EventDataTx{
|
||||
assert.NoError(t, eventBus.PublishEventTx(types.EventDataTx{
|
||||
TxResult: abci.TxResult{
|
||||
Height: 1,
|
||||
Index: 0,
|
||||
@@ -280,7 +280,7 @@ func TestEventBusPublishEventNewBlockHeader(t *testing.T) {
|
||||
assert.Equal(t, resultFinalizeBlock, edt.ResultFinalizeBlock)
|
||||
}()
|
||||
|
||||
err = eventBus.PublishEventNewBlockHeader(ctx, types.EventDataNewBlockHeader{
|
||||
err = eventBus.PublishEventNewBlockHeader(types.EventDataNewBlockHeader{
|
||||
Header: block.Header,
|
||||
ResultFinalizeBlock: resultFinalizeBlock,
|
||||
})
|
||||
@@ -322,7 +322,7 @@ func TestEventBusPublishEventEvidenceValidated(t *testing.T) {
|
||||
assert.Equal(t, int64(1), edt.Height)
|
||||
}()
|
||||
|
||||
err = eventBus.PublishEventEvidenceValidated(ctx, types.EventDataEvidenceValidated{
|
||||
err = eventBus.PublishEventEvidenceValidated(types.EventDataEvidenceValidated{
|
||||
Evidence: ev,
|
||||
Height: int64(1),
|
||||
})
|
||||
@@ -364,7 +364,7 @@ func TestEventBusPublishEventNewEvidence(t *testing.T) {
|
||||
assert.Equal(t, int64(4), edt.Height)
|
||||
}()
|
||||
|
||||
err = eventBus.PublishEventNewEvidence(ctx, types.EventDataNewEvidence{
|
||||
err = eventBus.PublishEventNewEvidence(types.EventDataNewEvidence{
|
||||
Evidence: ev,
|
||||
Height: 4,
|
||||
})
|
||||
@@ -408,22 +408,22 @@ func TestEventBusPublish(t *testing.T) {
|
||||
}
|
||||
}()
|
||||
|
||||
require.NoError(t, eventBus.Publish(ctx, types.EventNewBlockHeaderValue,
|
||||
require.NoError(t, eventBus.Publish(types.EventNewBlockHeaderValue,
|
||||
types.EventDataNewBlockHeader{}))
|
||||
require.NoError(t, eventBus.PublishEventNewBlock(ctx, types.EventDataNewBlock{}))
|
||||
require.NoError(t, eventBus.PublishEventNewBlockHeader(ctx, types.EventDataNewBlockHeader{}))
|
||||
require.NoError(t, eventBus.PublishEventVote(ctx, types.EventDataVote{}))
|
||||
require.NoError(t, eventBus.PublishEventNewRoundStep(ctx, types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventTimeoutPropose(ctx, types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventTimeoutWait(ctx, types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventNewRound(ctx, types.EventDataNewRound{}))
|
||||
require.NoError(t, eventBus.PublishEventCompleteProposal(ctx, types.EventDataCompleteProposal{}))
|
||||
require.NoError(t, eventBus.PublishEventPolka(ctx, types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventRelock(ctx, types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventLock(ctx, types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventValidatorSetUpdates(ctx, types.EventDataValidatorSetUpdates{}))
|
||||
require.NoError(t, eventBus.PublishEventBlockSyncStatus(ctx, types.EventDataBlockSyncStatus{}))
|
||||
require.NoError(t, eventBus.PublishEventStateSyncStatus(ctx, types.EventDataStateSyncStatus{}))
|
||||
require.NoError(t, eventBus.PublishEventNewBlock(types.EventDataNewBlock{}))
|
||||
require.NoError(t, eventBus.PublishEventNewBlockHeader(types.EventDataNewBlockHeader{}))
|
||||
require.NoError(t, eventBus.PublishEventVote(types.EventDataVote{}))
|
||||
require.NoError(t, eventBus.PublishEventNewRoundStep(types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventTimeoutPropose(types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventTimeoutWait(types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventNewRound(types.EventDataNewRound{}))
|
||||
require.NoError(t, eventBus.PublishEventCompleteProposal(types.EventDataCompleteProposal{}))
|
||||
require.NoError(t, eventBus.PublishEventPolka(types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventRelock(types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventLock(types.EventDataRoundState{}))
|
||||
require.NoError(t, eventBus.PublishEventValidatorSetUpdates(types.EventDataValidatorSetUpdates{}))
|
||||
require.NoError(t, eventBus.PublishEventBlockSyncStatus(types.EventDataBlockSyncStatus{}))
|
||||
require.NoError(t, eventBus.PublishEventStateSyncStatus(types.EventDataStateSyncStatus{}))
|
||||
|
||||
require.GreaterOrEqual(t, <-count, numEventsExpected)
|
||||
}
|
||||
@@ -505,7 +505,7 @@ func benchmarkEventBus(numClients int, randQueries bool, randEvents bool, b *tes
|
||||
eventValue = randEventValue()
|
||||
}
|
||||
|
||||
err := eventBus.Publish(ctx, eventValue, types.EventDataString("Gamora"))
|
||||
err := eventBus.Publish(eventValue, types.EventDataString("Gamora"))
|
||||
if err != nil {
|
||||
b.Error(err)
|
||||
}
|
||||
|
||||
@@ -338,7 +338,7 @@ func (evpool *Pool) addPendingEvidence(ctx context.Context, ev types.Evidence) e
|
||||
return nil
|
||||
|
||||
}
|
||||
return evpool.eventBus.PublishEventEvidenceValidated(ctx, types.EventDataEvidenceValidated{
|
||||
return evpool.eventBus.PublishEventEvidenceValidated(types.EventDataEvidenceValidated{
|
||||
Evidence: ev,
|
||||
Height: ev.Height(),
|
||||
})
|
||||
|
||||
@@ -46,7 +46,7 @@ type reactorTestSuite struct {
|
||||
numStateStores int
|
||||
}
|
||||
|
||||
func setup(ctx context.Context, t *testing.T, stateStores []sm.Store, chBuf uint) *reactorTestSuite {
|
||||
func setup(ctx context.Context, t *testing.T, stateStores []sm.Store) *reactorTestSuite {
|
||||
t.Helper()
|
||||
|
||||
pID := make([]byte, 16)
|
||||
@@ -245,7 +245,7 @@ func TestReactorMultiDisconnect(t *testing.T) {
|
||||
stateDB1 := initializeValidatorState(ctx, t, val, height)
|
||||
stateDB2 := initializeValidatorState(ctx, t, val, height)
|
||||
|
||||
rts := setup(ctx, t, []sm.Store{stateDB1, stateDB2}, 20)
|
||||
rts := setup(ctx, t, []sm.Store{stateDB1, stateDB2})
|
||||
primary := rts.nodes[0]
|
||||
secondary := rts.nodes[1]
|
||||
|
||||
@@ -290,7 +290,7 @@ func TestReactorBroadcastEvidence(t *testing.T) {
|
||||
stateDBs[i] = initializeValidatorState(ctx, t, val, height)
|
||||
}
|
||||
|
||||
rts := setup(ctx, t, stateDBs, 0)
|
||||
rts := setup(ctx, t, stateDBs)
|
||||
|
||||
rts.start(ctx, t)
|
||||
|
||||
@@ -348,7 +348,7 @@ func TestReactorBroadcastEvidence_Lagging(t *testing.T) {
|
||||
stateDB1 := initializeValidatorState(ctx, t, val, height1)
|
||||
stateDB2 := initializeValidatorState(ctx, t, val, height2)
|
||||
|
||||
rts := setup(ctx, t, []sm.Store{stateDB1, stateDB2}, 100)
|
||||
rts := setup(ctx, t, []sm.Store{stateDB1, stateDB2})
|
||||
rts.start(ctx, t)
|
||||
|
||||
primary := rts.nodes[0]
|
||||
@@ -382,7 +382,7 @@ func TestReactorBroadcastEvidence_Pending(t *testing.T) {
|
||||
stateDB1 := initializeValidatorState(ctx, t, val, height)
|
||||
stateDB2 := initializeValidatorState(ctx, t, val, height)
|
||||
|
||||
rts := setup(ctx, t, []sm.Store{stateDB1, stateDB2}, 100)
|
||||
rts := setup(ctx, t, []sm.Store{stateDB1, stateDB2})
|
||||
primary := rts.nodes[0]
|
||||
secondary := rts.nodes[1]
|
||||
|
||||
@@ -423,7 +423,7 @@ func TestReactorBroadcastEvidence_Committed(t *testing.T) {
|
||||
stateDB1 := initializeValidatorState(ctx, t, val, height)
|
||||
stateDB2 := initializeValidatorState(ctx, t, val, height)
|
||||
|
||||
rts := setup(ctx, t, []sm.Store{stateDB1, stateDB2}, 0)
|
||||
rts := setup(ctx, t, []sm.Store{stateDB1, stateDB2})
|
||||
|
||||
primary := rts.nodes[0]
|
||||
secondary := rts.nodes[1]
|
||||
@@ -482,7 +482,7 @@ func TestReactorBroadcastEvidence_FullyConnected(t *testing.T) {
|
||||
stateDBs[i] = initializeValidatorState(ctx, t, val, height)
|
||||
}
|
||||
|
||||
rts := setup(ctx, t, stateDBs, 0)
|
||||
rts := setup(ctx, t, stateDBs)
|
||||
rts.start(ctx, t)
|
||||
|
||||
evList := createEvidenceList(ctx, t, rts.pools[rts.network.RandomNode().NodeID], val, numEvidence)
|
||||
|
||||
@@ -25,7 +25,7 @@ func BenchmarkTxMempool_CheckTx(b *testing.B) {
|
||||
|
||||
// setup the cache and the mempool number for hitting GetEvictableTxs during the
|
||||
// benchmark. 5000 is the current default mempool size in the TM config.
|
||||
txmp := setup(ctx, b, client, 10000)
|
||||
txmp := setup(b, client, 10000)
|
||||
txmp.config.Size = 5000
|
||||
|
||||
rng := rand.New(rand.NewSource(time.Now().UnixNano()))
|
||||
|
||||
@@ -72,7 +72,7 @@ func (app *application) CheckTx(req abci.RequestCheckTx) abci.ResponseCheckTx {
|
||||
}
|
||||
}
|
||||
|
||||
func setup(ctx context.Context, t testing.TB, app abciclient.Client, cacheSize int, options ...TxMempoolOption) *TxMempool {
|
||||
func setup(t testing.TB, app abciclient.Client, cacheSize int, options ...TxMempoolOption) *TxMempool {
|
||||
t.Helper()
|
||||
|
||||
logger := log.NewNopLogger()
|
||||
@@ -131,7 +131,7 @@ func TestTxMempool_TxsAvailable(t *testing.T) {
|
||||
}
|
||||
t.Cleanup(client.Wait)
|
||||
|
||||
txmp := setup(ctx, t, client, 0)
|
||||
txmp := setup(t, client, 0)
|
||||
txmp.EnableTxsAvailable()
|
||||
|
||||
ensureNoTxFire := func() {
|
||||
@@ -194,7 +194,7 @@ func TestTxMempool_Size(t *testing.T) {
|
||||
}
|
||||
t.Cleanup(client.Wait)
|
||||
|
||||
txmp := setup(ctx, t, client, 0)
|
||||
txmp := setup(t, client, 0)
|
||||
txs := checkTxs(ctx, t, txmp, 100, 0)
|
||||
require.Equal(t, len(txs), txmp.Size())
|
||||
require.Equal(t, int64(5690), txmp.SizeBytes())
|
||||
@@ -227,7 +227,7 @@ func TestTxMempool_Flush(t *testing.T) {
|
||||
}
|
||||
t.Cleanup(client.Wait)
|
||||
|
||||
txmp := setup(ctx, t, client, 0)
|
||||
txmp := setup(t, client, 0)
|
||||
txs := checkTxs(ctx, t, txmp, 100, 0)
|
||||
require.Equal(t, len(txs), txmp.Size())
|
||||
require.Equal(t, int64(5690), txmp.SizeBytes())
|
||||
@@ -261,7 +261,7 @@ func TestTxMempool_ReapMaxBytesMaxGas(t *testing.T) {
|
||||
}
|
||||
t.Cleanup(client.Wait)
|
||||
|
||||
txmp := setup(ctx, t, client, 0)
|
||||
txmp := setup(t, client, 0)
|
||||
tTxs := checkTxs(ctx, t, txmp, 100, 0) // all txs request 1 gas unit
|
||||
require.Equal(t, len(tTxs), txmp.Size())
|
||||
require.Equal(t, int64(5690), txmp.SizeBytes())
|
||||
@@ -320,7 +320,7 @@ func TestTxMempool_ReapMaxTxs(t *testing.T) {
|
||||
}
|
||||
t.Cleanup(client.Wait)
|
||||
|
||||
txmp := setup(ctx, t, client, 0)
|
||||
txmp := setup(t, client, 0)
|
||||
tTxs := checkTxs(ctx, t, txmp, 100, 0)
|
||||
require.Equal(t, len(tTxs), txmp.Size())
|
||||
require.Equal(t, int64(5690), txmp.SizeBytes())
|
||||
@@ -377,7 +377,7 @@ func TestTxMempool_CheckTxExceedsMaxSize(t *testing.T) {
|
||||
t.Fatal(err)
|
||||
}
|
||||
t.Cleanup(client.Wait)
|
||||
txmp := setup(ctx, t, client, 0)
|
||||
txmp := setup(t, client, 0)
|
||||
|
||||
rng := rand.New(rand.NewSource(time.Now().UnixNano()))
|
||||
tx := make([]byte, txmp.config.MaxTxBytes+1)
|
||||
@@ -403,7 +403,7 @@ func TestTxMempool_CheckTxSamePeer(t *testing.T) {
|
||||
}
|
||||
t.Cleanup(client.Wait)
|
||||
|
||||
txmp := setup(ctx, t, client, 100)
|
||||
txmp := setup(t, client, 100)
|
||||
peerID := uint16(1)
|
||||
rng := rand.New(rand.NewSource(time.Now().UnixNano()))
|
||||
|
||||
@@ -427,7 +427,7 @@ func TestTxMempool_CheckTxSameSender(t *testing.T) {
|
||||
}
|
||||
t.Cleanup(client.Wait)
|
||||
|
||||
txmp := setup(ctx, t, client, 100)
|
||||
txmp := setup(t, client, 100)
|
||||
peerID := uint16(1)
|
||||
rng := rand.New(rand.NewSource(time.Now().UnixNano()))
|
||||
|
||||
@@ -458,7 +458,7 @@ func TestTxMempool_ConcurrentTxs(t *testing.T) {
|
||||
}
|
||||
t.Cleanup(client.Wait)
|
||||
|
||||
txmp := setup(ctx, t, client, 100)
|
||||
txmp := setup(t, client, 100)
|
||||
rng := rand.New(rand.NewSource(time.Now().UnixNano()))
|
||||
checkTxDone := make(chan struct{})
|
||||
|
||||
@@ -531,7 +531,7 @@ func TestTxMempool_ExpiredTxs_NumBlocks(t *testing.T) {
|
||||
}
|
||||
t.Cleanup(client.Wait)
|
||||
|
||||
txmp := setup(ctx, t, client, 500)
|
||||
txmp := setup(t, client, 500)
|
||||
txmp.height = 100
|
||||
txmp.config.TTLNumBlocks = 10
|
||||
|
||||
@@ -612,7 +612,7 @@ func TestTxMempool_CheckTxPostCheckError(t *testing.T) {
|
||||
postCheckFn := func(_ types.Tx, _ *abci.ResponseCheckTx) error {
|
||||
return testCase.err
|
||||
}
|
||||
txmp := setup(ctx, t, client, 0, WithPostCheck(postCheckFn))
|
||||
txmp := setup(t, client, 0, WithPostCheck(postCheckFn))
|
||||
rng := rand.New(rand.NewSource(time.Now().UnixNano()))
|
||||
tx := make([]byte, txmp.config.MaxTxBytes-1)
|
||||
_, err := rng.Read(tx)
|
||||
|
||||
@@ -68,7 +68,7 @@ func setupReactors(ctx context.Context, t *testing.T, logger log.Logger, numNode
|
||||
require.NoError(t, client.Start(ctx))
|
||||
t.Cleanup(client.Wait)
|
||||
|
||||
mempool := setup(ctx, t, client, 0)
|
||||
mempool := setup(t, client, 0)
|
||||
rts.mempools[nodeID] = mempool
|
||||
|
||||
rts.peerChans[nodeID] = make(chan p2p.PeerUpdate, chBuf)
|
||||
|
||||
@@ -228,7 +228,7 @@ func TestDeriveSecretsAndChallengeGolden(t *testing.T) {
|
||||
goldenFilepath := filepath.Join("testdata", t.Name()+".golden")
|
||||
if *update {
|
||||
t.Logf("Updating golden test vector file %s", goldenFilepath)
|
||||
data := createGoldenTestVectors(t)
|
||||
data := createGoldenTestVectors()
|
||||
require.NoError(t, os.WriteFile(goldenFilepath, []byte(data), 0644))
|
||||
}
|
||||
f, err := os.Open(goldenFilepath)
|
||||
@@ -306,7 +306,7 @@ func readLots(t *testing.T, wg *sync.WaitGroup, conn io.Reader, n int) {
|
||||
// Creates the data for a test vector file.
|
||||
// The file format is:
|
||||
// Hex(diffie_hellman_secret), loc_is_least, Hex(recvSecret), Hex(sendSecret), Hex(challenge)
|
||||
func createGoldenTestVectors(t *testing.T) string {
|
||||
func createGoldenTestVectors() string {
|
||||
data := ""
|
||||
for i := 0; i < 32; i++ {
|
||||
randSecretVector := tmrand.Bytes(32)
|
||||
|
||||
@@ -26,6 +26,7 @@ func newConnTracker(max uint, window time.Duration) connectionTracker {
|
||||
cache: make(map[string]uint),
|
||||
lastConnect: make(map[string]time.Time),
|
||||
max: max,
|
||||
window: window,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -43,7 +44,7 @@ func (rat *connTrackerImpl) AddConn(addr net.IP) error {
|
||||
if num := rat.cache[address]; num >= rat.max {
|
||||
return fmt.Errorf("%q has %d connections [max=%d]", address, num, rat.max)
|
||||
} else if num == 0 {
|
||||
// if there is already at least connection, check to
|
||||
// if there is already at least one connection, check to
|
||||
// see if it was established before within the window,
|
||||
// and error if so.
|
||||
if last := rat.lastConnect[address]; time.Since(last) < rat.window {
|
||||
|
||||
@@ -70,4 +70,15 @@ func TestConnTracker(t *testing.T) {
|
||||
}
|
||||
require.Equal(t, 10, ct.Len())
|
||||
})
|
||||
t.Run("Window", func(t *testing.T) {
|
||||
const window = 100 * time.Millisecond
|
||||
ct := newConnTracker(10, window)
|
||||
ip := randLocalIPv4()
|
||||
require.NoError(t, ct.AddConn(ip))
|
||||
ct.RemoveConn(ip)
|
||||
require.Error(t, ct.AddConn(ip))
|
||||
time.Sleep(window)
|
||||
require.NoError(t, ct.AddConn(ip))
|
||||
})
|
||||
|
||||
}
|
||||
|
||||
@@ -151,14 +151,14 @@ func TestReactorErrorsOnReceivingTooManyPeers(t *testing.T) {
|
||||
defer cancel()
|
||||
|
||||
r := setupSingle(ctx, t)
|
||||
peer := p2p.NodeAddress{Protocol: p2p.MemoryProtocol, NodeID: randomNodeID(t)}
|
||||
peer := p2p.NodeAddress{Protocol: p2p.MemoryProtocol, NodeID: randomNodeID()}
|
||||
added, err := r.manager.Add(peer)
|
||||
require.NoError(t, err)
|
||||
require.True(t, added)
|
||||
|
||||
addresses := make([]p2pproto.PexAddress, 101)
|
||||
for i := 0; i < len(addresses); i++ {
|
||||
nodeAddress := p2p.NodeAddress{Protocol: p2p.MemoryProtocol, NodeID: randomNodeID(t)}
|
||||
nodeAddress := p2p.NodeAddress{Protocol: p2p.MemoryProtocol, NodeID: randomNodeID()}
|
||||
addresses[i] = p2pproto.PexAddress{
|
||||
URL: nodeAddress.String(),
|
||||
}
|
||||
@@ -730,6 +730,6 @@ func newNodeID(t *testing.T, id string) types.NodeID {
|
||||
return nodeID
|
||||
}
|
||||
|
||||
func randomNodeID(t *testing.T) types.NodeID {
|
||||
func randomNodeID() types.NodeID {
|
||||
return types.NodeIDFromPubKey(ed25519.GenPrivKey().PubKey())
|
||||
}
|
||||
|
||||
@@ -29,6 +29,6 @@ func TestExample(t *testing.T) {
|
||||
Attributes: []abci.EventAttribute{{Key: "name", Value: "John"}},
|
||||
},
|
||||
}
|
||||
require.NoError(t, s.PublishWithEvents(ctx, pubstring("Tombstone"), events))
|
||||
require.NoError(t, s.PublishWithEvents(pubstring("Tombstone"), events))
|
||||
sub.mustReceive(ctx, pubstring("Tombstone"))
|
||||
}
|
||||
|
||||
@@ -287,16 +287,16 @@ func (s *Server) NumClientSubscriptions(clientID string) int {
|
||||
}
|
||||
|
||||
// Publish publishes the given message. An error will be returned to the caller
|
||||
// if the context is canceled.
|
||||
func (s *Server) Publish(ctx context.Context, msg types.EventData) error {
|
||||
return s.publish(ctx, msg, []abci.Event{})
|
||||
// if the pubsub server has shut down.
|
||||
func (s *Server) Publish(msg types.EventData) error {
|
||||
return s.publish(msg, []abci.Event{})
|
||||
}
|
||||
|
||||
// PublishWithEvents publishes the given message with the set of events. The set
|
||||
// is matched with clients queries. If there is a match, the message is sent to
|
||||
// the client.
|
||||
func (s *Server) PublishWithEvents(ctx context.Context, msg types.EventData, events []abci.Event) error {
|
||||
return s.publish(ctx, msg, events)
|
||||
func (s *Server) PublishWithEvents(msg types.EventData, events []abci.Event) error {
|
||||
return s.publish(msg, events)
|
||||
}
|
||||
|
||||
// OnStop implements part of the Service interface. It is a no-op.
|
||||
@@ -309,15 +309,13 @@ func (s *Server) Wait() { <-s.exited; s.BaseService.Wait() }
|
||||
// OnStart implements Service.OnStart by starting the server.
|
||||
func (s *Server) OnStart(ctx context.Context) error { s.run(ctx); return nil }
|
||||
|
||||
func (s *Server) publish(ctx context.Context, data types.EventData, events []abci.Event) error {
|
||||
func (s *Server) publish(data types.EventData, events []abci.Event) error {
|
||||
s.pubs.RLock()
|
||||
defer s.pubs.RUnlock()
|
||||
|
||||
select {
|
||||
case <-s.done:
|
||||
return ErrServerStopped
|
||||
case <-ctx.Done():
|
||||
return ctx.Err()
|
||||
case s.queue <- item{
|
||||
Data: data,
|
||||
Events: events,
|
||||
|
||||
@@ -42,7 +42,7 @@ func TestSubscribeWithArgs(t *testing.T) {
|
||||
require.Equal(t, 1, s.NumClients())
|
||||
require.Equal(t, 1, s.NumClientSubscriptions(clientID))
|
||||
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Ka-Zar")))
|
||||
require.NoError(t, s.Publish(pubstring("Ka-Zar")))
|
||||
sub.mustReceive(ctx, pubstring("Ka-Zar"))
|
||||
})
|
||||
t.Run("PositiveLimit", func(t *testing.T) {
|
||||
@@ -51,7 +51,7 @@ func TestSubscribeWithArgs(t *testing.T) {
|
||||
Query: query.All,
|
||||
Limit: 10,
|
||||
}))
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Aggamon")))
|
||||
require.NoError(t, s.Publish(pubstring("Aggamon")))
|
||||
sub.mustReceive(ctx, pubstring("Aggamon"))
|
||||
})
|
||||
}
|
||||
@@ -72,7 +72,7 @@ func TestObserver(t *testing.T) {
|
||||
}))
|
||||
|
||||
const input = pubstring("Lions and tigers and bears, oh my!")
|
||||
require.NoError(t, s.Publish(ctx, input))
|
||||
require.NoError(t, s.Publish(input))
|
||||
<-done
|
||||
require.Equal(t, got, input)
|
||||
}
|
||||
@@ -106,9 +106,9 @@ func TestPublishDoesNotBlock(t *testing.T) {
|
||||
go func() {
|
||||
defer close(published)
|
||||
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Quicksilver")))
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Asylum")))
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Ivan")))
|
||||
require.NoError(t, s.Publish(pubstring("Quicksilver")))
|
||||
require.NoError(t, s.Publish(pubstring("Asylum")))
|
||||
require.NoError(t, s.Publish(pubstring("Ivan")))
|
||||
}()
|
||||
|
||||
select {
|
||||
@@ -149,9 +149,9 @@ func TestSlowSubscriber(t *testing.T) {
|
||||
Query: query.All,
|
||||
}))
|
||||
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Fat Cobra")))
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Viper")))
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Black Panther")))
|
||||
require.NoError(t, s.Publish(pubstring("Fat Cobra")))
|
||||
require.NoError(t, s.Publish(pubstring("Viper")))
|
||||
require.NoError(t, s.Publish(pubstring("Black Panther")))
|
||||
|
||||
// We had capacity for one item, so we should get that item, but after that
|
||||
// the subscription should have been terminated by the publisher.
|
||||
@@ -176,7 +176,7 @@ func TestDifferentClients(t *testing.T) {
|
||||
Attributes: []abci.EventAttribute{{Key: "type", Value: "NewBlock"}},
|
||||
}}
|
||||
|
||||
require.NoError(t, s.PublishWithEvents(ctx, pubstring("Iceman"), events))
|
||||
require.NoError(t, s.PublishWithEvents(pubstring("Iceman"), events))
|
||||
sub1.mustReceive(ctx, pubstring("Iceman"))
|
||||
|
||||
sub2 := newTestSub(t).must(s.SubscribeWithArgs(ctx, pubsub.SubscribeArgs{
|
||||
@@ -195,7 +195,7 @@ func TestDifferentClients(t *testing.T) {
|
||||
},
|
||||
}
|
||||
|
||||
require.NoError(t, s.PublishWithEvents(ctx, pubstring("Ultimo"), events))
|
||||
require.NoError(t, s.PublishWithEvents(pubstring("Ultimo"), events))
|
||||
sub1.mustReceive(ctx, pubstring("Ultimo"))
|
||||
sub2.mustReceive(ctx, pubstring("Ultimo"))
|
||||
|
||||
@@ -210,7 +210,7 @@ func TestDifferentClients(t *testing.T) {
|
||||
Attributes: []abci.EventAttribute{{Key: "type", Value: "NewRoundStep"}},
|
||||
}}
|
||||
|
||||
require.NoError(t, s.PublishWithEvents(ctx, pubstring("Valeria Richards"), events))
|
||||
require.NoError(t, s.PublishWithEvents(pubstring("Valeria Richards"), events))
|
||||
sub3.mustTimeOut(ctx, 100*time.Millisecond)
|
||||
}
|
||||
|
||||
@@ -259,7 +259,7 @@ func TestSubscribeDuplicateKeys(t *testing.T) {
|
||||
},
|
||||
}
|
||||
|
||||
require.NoError(t, s.PublishWithEvents(ctx, pubstring("Iceman"), events))
|
||||
require.NoError(t, s.PublishWithEvents(pubstring("Iceman"), events))
|
||||
|
||||
if tc.expected != nil {
|
||||
sub.mustReceive(ctx, tc.expected)
|
||||
@@ -288,7 +288,7 @@ func TestClientSubscribesTwice(t *testing.T) {
|
||||
Query: q,
|
||||
}))
|
||||
|
||||
require.NoError(t, s.PublishWithEvents(ctx, pubstring("Goblin Queen"), events))
|
||||
require.NoError(t, s.PublishWithEvents(pubstring("Goblin Queen"), events))
|
||||
sub1.mustReceive(ctx, pubstring("Goblin Queen"))
|
||||
|
||||
// Subscribing a second time with the same client ID and query fails.
|
||||
@@ -302,7 +302,7 @@ func TestClientSubscribesTwice(t *testing.T) {
|
||||
}
|
||||
|
||||
// The attempt to re-subscribe does not disrupt the existing sub.
|
||||
require.NoError(t, s.PublishWithEvents(ctx, pubstring("Spider-Man"), events))
|
||||
require.NoError(t, s.PublishWithEvents(pubstring("Spider-Man"), events))
|
||||
sub1.mustReceive(ctx, pubstring("Spider-Man"))
|
||||
}
|
||||
|
||||
@@ -325,7 +325,7 @@ func TestUnsubscribe(t *testing.T) {
|
||||
}))
|
||||
|
||||
// Publishing should still work.
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Nick Fury")))
|
||||
require.NoError(t, s.Publish(pubstring("Nick Fury")))
|
||||
|
||||
// The unsubscribed subscriber should report as such.
|
||||
sub.mustFail(ctx, pubsub.ErrUnsubscribed)
|
||||
@@ -373,7 +373,7 @@ func TestResubscribe(t *testing.T) {
|
||||
|
||||
sub := newTestSub(t).must(s.SubscribeWithArgs(ctx, args))
|
||||
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Cable")))
|
||||
require.NoError(t, s.Publish(pubstring("Cable")))
|
||||
sub.mustReceive(ctx, pubstring("Cable"))
|
||||
}
|
||||
|
||||
@@ -394,7 +394,7 @@ func TestUnsubscribeAll(t *testing.T) {
|
||||
}))
|
||||
|
||||
require.NoError(t, s.UnsubscribeAll(ctx, clientID))
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Nick Fury")))
|
||||
require.NoError(t, s.Publish(pubstring("Nick Fury")))
|
||||
|
||||
sub1.mustFail(ctx, pubsub.ErrUnsubscribed)
|
||||
sub2.mustFail(ctx, pubsub.ErrUnsubscribed)
|
||||
@@ -410,13 +410,24 @@ func TestBufferCapacity(t *testing.T) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Nighthawk")))
|
||||
require.NoError(t, s.Publish(ctx, pubstring("Sage")))
|
||||
require.NoError(t, s.Publish(pubstring("Nighthawk")))
|
||||
require.NoError(t, s.Publish(pubstring("Sage")))
|
||||
|
||||
ctx, cancel = context.WithTimeout(ctx, 100*time.Millisecond)
|
||||
defer cancel()
|
||||
|
||||
require.ErrorIs(t, s.Publish(ctx, pubstring("Ironclad")), context.DeadlineExceeded)
|
||||
sig := make(chan struct{})
|
||||
|
||||
go func() { defer close(sig); _ = s.Publish(pubstring("Ironclad")) }()
|
||||
|
||||
select {
|
||||
case <-sig:
|
||||
t.Fatal("should not fire")
|
||||
|
||||
case <-ctx.Done():
|
||||
return
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
func newTestServer(ctx context.Context, t testing.TB, logger log.Logger) *pubsub.Server {
|
||||
|
||||
+46
-19
@@ -7,6 +7,7 @@ import (
|
||||
|
||||
abciclient "github.com/tendermint/tendermint/abci/client"
|
||||
abci "github.com/tendermint/tendermint/abci/types"
|
||||
"github.com/tendermint/tendermint/crypto"
|
||||
"github.com/tendermint/tendermint/crypto/encoding"
|
||||
"github.com/tendermint/tendermint/crypto/merkle"
|
||||
"github.com/tendermint/tendermint/internal/eventbus"
|
||||
@@ -291,34 +292,38 @@ func (blockExec *BlockExecutor) ApplyBlock(
|
||||
|
||||
// Events are fired after everything else.
|
||||
// NOTE: if we crash between Commit and Save, events wont be fired during replay
|
||||
fireEvents(ctx, blockExec.logger, blockExec.eventBus, block, blockID, finalizeBlockResponse, validatorUpdates)
|
||||
fireEvents(blockExec.logger, blockExec.eventBus, block, blockID, finalizeBlockResponse, validatorUpdates)
|
||||
|
||||
return state, nil
|
||||
}
|
||||
|
||||
func (blockExec *BlockExecutor) ExtendVote(ctx context.Context, vote *types.Vote) (types.VoteExtension, error) {
|
||||
func (blockExec *BlockExecutor) ExtendVote(ctx context.Context, vote *types.Vote) ([]byte, error) {
|
||||
req := abci.RequestExtendVote{
|
||||
Vote: vote.ToProto(),
|
||||
Hash: vote.BlockID.Hash,
|
||||
Height: vote.Height,
|
||||
}
|
||||
|
||||
resp, err := blockExec.appClient.ExtendVote(ctx, req)
|
||||
if err != nil {
|
||||
return types.VoteExtension{}, err
|
||||
panic(fmt.Errorf("ExtendVote call failed: %w", err))
|
||||
}
|
||||
return types.VoteExtensionFromProto(resp.VoteExtension), nil
|
||||
return resp.VoteExtension, nil
|
||||
}
|
||||
|
||||
func (blockExec *BlockExecutor) VerifyVoteExtension(ctx context.Context, vote *types.Vote) error {
|
||||
req := abci.RequestVerifyVoteExtension{
|
||||
Vote: vote.ToProto(),
|
||||
Hash: vote.BlockID.Hash,
|
||||
ValidatorAddress: vote.ValidatorAddress,
|
||||
Height: vote.Height,
|
||||
VoteExtension: vote.Extension,
|
||||
}
|
||||
|
||||
resp, err := blockExec.appClient.VerifyVoteExtension(ctx, req)
|
||||
if err != nil {
|
||||
return err
|
||||
panic(fmt.Errorf("VerifyVoteExtension call failed: %w", err))
|
||||
}
|
||||
|
||||
if resp.IsErr() {
|
||||
if !resp.IsOK() {
|
||||
return types.ErrVoteInvalidExtension
|
||||
}
|
||||
|
||||
@@ -417,16 +422,39 @@ func buildLastCommitInfo(block *types.Block, store Store, initialHeight int64) a
|
||||
}
|
||||
}
|
||||
|
||||
// extendedCommitInfo expects a CommitInfo struct along with all of the
|
||||
// original votes relating to that commit, including their vote extensions. The
|
||||
// order of votes does not matter.
|
||||
func extendedCommitInfo(c abci.CommitInfo, votes []*types.Vote) abci.ExtendedCommitInfo {
|
||||
if len(c.Votes) != len(votes) {
|
||||
panic(fmt.Sprintf("extendedCommitInfo: number of votes from commit differ from the number of votes supplied (%d != %d)", len(c.Votes), len(votes)))
|
||||
}
|
||||
votesByVal := make(map[string]*types.Vote)
|
||||
for _, vote := range votes {
|
||||
if vote != nil {
|
||||
valAddr := vote.ValidatorAddress.String()
|
||||
if _, ok := votesByVal[valAddr]; ok {
|
||||
panic(fmt.Sprintf("extendedCommitInfo: found duplicate vote for validator with address %s", valAddr))
|
||||
}
|
||||
votesByVal[valAddr] = vote
|
||||
}
|
||||
}
|
||||
vs := make([]abci.ExtendedVoteInfo, len(c.Votes))
|
||||
for i := range vs {
|
||||
var ext []byte
|
||||
// votes[i] will be nil if c.Votes[i].SignedLastBlock is false
|
||||
if c.Votes[i].SignedLastBlock {
|
||||
valAddr := crypto.Address(c.Votes[i].Validator.Address).String()
|
||||
vote, ok := votesByVal[valAddr]
|
||||
if !ok || vote == nil {
|
||||
panic(fmt.Sprintf("extendedCommitInfo: validator with address %s signed last block, but could not find vote for it", valAddr))
|
||||
}
|
||||
ext = vote.Extension
|
||||
}
|
||||
vs[i] = abci.ExtendedVoteInfo{
|
||||
Validator: c.Votes[i].Validator,
|
||||
SignedLastBlock: c.Votes[i].SignedLastBlock,
|
||||
/*
|
||||
TODO: Include vote extensions information when implementing vote extensions.
|
||||
VoteExtension: []byte{},
|
||||
*/
|
||||
VoteExtension: ext,
|
||||
}
|
||||
}
|
||||
return abci.ExtendedCommitInfo{
|
||||
@@ -530,7 +558,6 @@ func (state State) Update(
|
||||
// Fire TxEvent for every tx.
|
||||
// NOTE: if Tendermint crashes before commit, some or all of these events may be published again.
|
||||
func fireEvents(
|
||||
ctx context.Context,
|
||||
logger log.Logger,
|
||||
eventBus types.BlockEventPublisher,
|
||||
block *types.Block,
|
||||
@@ -538,7 +565,7 @@ func fireEvents(
|
||||
finalizeBlockResponse *abci.ResponseFinalizeBlock,
|
||||
validatorUpdates []*types.Validator,
|
||||
) {
|
||||
if err := eventBus.PublishEventNewBlock(ctx, types.EventDataNewBlock{
|
||||
if err := eventBus.PublishEventNewBlock(types.EventDataNewBlock{
|
||||
Block: block,
|
||||
BlockID: blockID,
|
||||
ResultFinalizeBlock: *finalizeBlockResponse,
|
||||
@@ -546,7 +573,7 @@ func fireEvents(
|
||||
logger.Error("failed publishing new block", "err", err)
|
||||
}
|
||||
|
||||
if err := eventBus.PublishEventNewBlockHeader(ctx, types.EventDataNewBlockHeader{
|
||||
if err := eventBus.PublishEventNewBlockHeader(types.EventDataNewBlockHeader{
|
||||
Header: block.Header,
|
||||
NumTxs: int64(len(block.Txs)),
|
||||
ResultFinalizeBlock: *finalizeBlockResponse,
|
||||
@@ -556,7 +583,7 @@ func fireEvents(
|
||||
|
||||
if len(block.Evidence) != 0 {
|
||||
for _, ev := range block.Evidence {
|
||||
if err := eventBus.PublishEventNewEvidence(ctx, types.EventDataNewEvidence{
|
||||
if err := eventBus.PublishEventNewEvidence(types.EventDataNewEvidence{
|
||||
Evidence: ev,
|
||||
Height: block.Height,
|
||||
}); err != nil {
|
||||
@@ -572,7 +599,7 @@ func fireEvents(
|
||||
}
|
||||
|
||||
for i, tx := range block.Data.Txs {
|
||||
if err := eventBus.PublishEventTx(ctx, types.EventDataTx{
|
||||
if err := eventBus.PublishEventTx(types.EventDataTx{
|
||||
TxResult: abci.TxResult{
|
||||
Height: block.Height,
|
||||
Index: uint32(i),
|
||||
@@ -585,7 +612,7 @@ func fireEvents(
|
||||
}
|
||||
|
||||
if len(finalizeBlockResponse.ValidatorUpdates) > 0 {
|
||||
if err := eventBus.PublishEventValidatorSetUpdates(ctx,
|
||||
if err := eventBus.PublishEventValidatorSetUpdates(
|
||||
types.EventDataValidatorSetUpdates{ValidatorUpdates: validatorUpdates}); err != nil {
|
||||
logger.Error("failed publishing event", "err", err)
|
||||
}
|
||||
@@ -644,7 +671,7 @@ func ExecCommitBlock(
|
||||
}
|
||||
|
||||
blockID := types.BlockID{Hash: block.Hash(), PartSetHeader: bps.Header()}
|
||||
fireEvents(ctx, be.logger, be.eventBus, block, blockID, finalizeBlockResponse, validatorUpdates)
|
||||
fireEvents(be.logger, be.eventBus, block, blockID, finalizeBlockResponse, validatorUpdates)
|
||||
}
|
||||
|
||||
// Commit block, get hash back
|
||||
|
||||
@@ -654,8 +654,8 @@ func TestEmptyPrepareProposal(t *testing.T) {
|
||||
sm.NopMetrics(),
|
||||
)
|
||||
pa, _ := state.Validators.GetByIndex(0)
|
||||
commit := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
_, err = blockExec.CreateProposalBlock(ctx, height, state, commit, pa, nil)
|
||||
commit, votes := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
_, err = blockExec.CreateProposalBlock(ctx, height, state, commit, pa, votes)
|
||||
require.NoError(t, err)
|
||||
}
|
||||
|
||||
@@ -709,8 +709,8 @@ func TestPrepareProposalErrorOnNonExistingRemoved(t *testing.T) {
|
||||
sm.NopMetrics(),
|
||||
)
|
||||
pa, _ := state.Validators.GetByIndex(0)
|
||||
commit := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, nil)
|
||||
commit, votes := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, votes)
|
||||
require.Nil(t, block)
|
||||
require.ErrorContains(t, err, "new transaction incorrectly marked as removed")
|
||||
|
||||
@@ -765,8 +765,8 @@ func TestPrepareProposalRemoveTxs(t *testing.T) {
|
||||
sm.NopMetrics(),
|
||||
)
|
||||
pa, _ := state.Validators.GetByIndex(0)
|
||||
commit := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, nil)
|
||||
commit, votes := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, votes)
|
||||
require.NoError(t, err)
|
||||
require.Len(t, block.Data.Txs.ToSliceOfBytes(), len(trs)-2)
|
||||
|
||||
@@ -824,8 +824,8 @@ func TestPrepareProposalAddedTxsIncluded(t *testing.T) {
|
||||
sm.NopMetrics(),
|
||||
)
|
||||
pa, _ := state.Validators.GetByIndex(0)
|
||||
commit := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, nil)
|
||||
commit, votes := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, votes)
|
||||
require.NoError(t, err)
|
||||
|
||||
require.Equal(t, txs[0], block.Data.Txs[0])
|
||||
@@ -880,8 +880,8 @@ func TestPrepareProposalReorderTxs(t *testing.T) {
|
||||
sm.NopMetrics(),
|
||||
)
|
||||
pa, _ := state.Validators.GetByIndex(0)
|
||||
commit := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, nil)
|
||||
commit, votes := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, votes)
|
||||
require.NoError(t, err)
|
||||
for i, tx := range block.Data.Txs {
|
||||
require.Equal(t, types.Tx(trs[i].Tx), tx)
|
||||
@@ -940,9 +940,9 @@ func TestPrepareProposalErrorOnTooManyTxs(t *testing.T) {
|
||||
sm.NopMetrics(),
|
||||
)
|
||||
pa, _ := state.Validators.GetByIndex(0)
|
||||
commit := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
commit, votes := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, nil)
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, votes)
|
||||
require.Nil(t, block)
|
||||
require.ErrorContains(t, err, "transaction data size exceeds maximum")
|
||||
|
||||
@@ -992,9 +992,9 @@ func TestPrepareProposalErrorOnPrepareProposalError(t *testing.T) {
|
||||
sm.NopMetrics(),
|
||||
)
|
||||
pa, _ := state.Validators.GetByIndex(0)
|
||||
commit := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
commit, votes := makeValidCommit(ctx, t, height, types.BlockID{}, state.Validators, privVals)
|
||||
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, nil)
|
||||
block, err := blockExec.CreateProposalBlock(ctx, height, state, commit, pa, votes)
|
||||
require.Nil(t, block)
|
||||
require.ErrorContains(t, err, "an injected error")
|
||||
|
||||
|
||||
@@ -46,7 +46,7 @@ func makeAndCommitGoodBlock(
|
||||
state, blockID := makeAndApplyGoodBlock(ctx, t, state, height, lastCommit, proposerAddr, blockExec, evidence)
|
||||
|
||||
// Simulate a lastCommit for this block from all validators for the next height
|
||||
commit := makeValidCommit(ctx, t, height, blockID, state.Validators, privVals)
|
||||
commit, _ := makeValidCommit(ctx, t, height, blockID, state.Validators, privVals)
|
||||
|
||||
return state, blockID, commit
|
||||
}
|
||||
@@ -82,17 +82,19 @@ func makeValidCommit(
|
||||
blockID types.BlockID,
|
||||
vals *types.ValidatorSet,
|
||||
privVals map[string]types.PrivValidator,
|
||||
) *types.Commit {
|
||||
) (*types.Commit, []*types.Vote) {
|
||||
t.Helper()
|
||||
sigs := make([]types.CommitSig, 0)
|
||||
sigs := make([]types.CommitSig, vals.Size())
|
||||
votes := make([]*types.Vote, vals.Size())
|
||||
for i := 0; i < vals.Size(); i++ {
|
||||
_, val := vals.GetByIndex(int32(i))
|
||||
vote, err := factory.MakeVote(ctx, privVals[val.Address.String()], chainID, int32(i), height, 0, 2, blockID, time.Now())
|
||||
require.NoError(t, err)
|
||||
sigs = append(sigs, vote.CommitSig())
|
||||
sigs[i] = vote.CommitSig()
|
||||
votes[i] = vote
|
||||
}
|
||||
|
||||
return types.NewCommit(height, 0, blockID, sigs)
|
||||
return types.NewCommit(height, 0, blockID, sigs), votes
|
||||
}
|
||||
|
||||
func makeState(t *testing.T, nVals, height int) (sm.State, dbm.DB, map[string]types.PrivValidator) {
|
||||
|
||||
@@ -54,8 +54,7 @@ func TestIndexerServiceIndexesBlocks(t *testing.T) {
|
||||
assert.False(t, indexer.IndexingEnabled([]indexer.EventSink{}))
|
||||
|
||||
// event sink setup
|
||||
pool, err := setupDB(t)
|
||||
assert.NoError(t, err)
|
||||
pool := setupDB(t)
|
||||
|
||||
store := dbm.NewMemDB()
|
||||
eventSinks := []indexer.EventSink{kv.NewEventSink(store), pSink}
|
||||
@@ -71,7 +70,7 @@ func TestIndexerServiceIndexesBlocks(t *testing.T) {
|
||||
t.Cleanup(service.Wait)
|
||||
|
||||
// publish block with txs
|
||||
err = eventBus.PublishEventNewBlockHeader(ctx, types.EventDataNewBlockHeader{
|
||||
err = eventBus.PublishEventNewBlockHeader(types.EventDataNewBlockHeader{
|
||||
Header: types.Header{Height: 1},
|
||||
NumTxs: int64(2),
|
||||
})
|
||||
@@ -82,7 +81,7 @@ func TestIndexerServiceIndexesBlocks(t *testing.T) {
|
||||
Tx: types.Tx("foo"),
|
||||
Result: abci.ExecTxResult{Code: 0},
|
||||
}
|
||||
err = eventBus.PublishEventTx(ctx, types.EventDataTx{TxResult: *txResult1})
|
||||
err = eventBus.PublishEventTx(types.EventDataTx{TxResult: *txResult1})
|
||||
require.NoError(t, err)
|
||||
txResult2 := &abci.TxResult{
|
||||
Height: 1,
|
||||
@@ -90,7 +89,7 @@ func TestIndexerServiceIndexesBlocks(t *testing.T) {
|
||||
Tx: types.Tx("bar"),
|
||||
Result: abci.ExecTxResult{Code: 0},
|
||||
}
|
||||
err = eventBus.PublishEventTx(ctx, types.EventDataTx{TxResult: *txResult2})
|
||||
err = eventBus.PublishEventTx(types.EventDataTx{TxResult: *txResult2})
|
||||
require.NoError(t, err)
|
||||
|
||||
time.Sleep(100 * time.Millisecond)
|
||||
@@ -133,7 +132,7 @@ func resetDB(t *testing.T) {
|
||||
assert.NoError(t, err)
|
||||
}
|
||||
|
||||
func setupDB(t *testing.T) (*dockertest.Pool, error) {
|
||||
func setupDB(t *testing.T) *dockertest.Pool {
|
||||
t.Helper()
|
||||
pool, err := dockertest.NewPool(os.Getenv("DOCKER_URL"))
|
||||
assert.NoError(t, err)
|
||||
@@ -187,7 +186,7 @@ func setupDB(t *testing.T) (*dockertest.Pool, error) {
|
||||
err = migrator.Apply(psqldb, sm)
|
||||
assert.NoError(t, err)
|
||||
|
||||
return pool, nil
|
||||
return pool
|
||||
}
|
||||
|
||||
func teardown(t *testing.T, pool *dockertest.Pool) error {
|
||||
|
||||
@@ -333,7 +333,7 @@ func (r *Reactor) OnStop() {
|
||||
// of historical blocks before participating in consensus
|
||||
func (r *Reactor) Sync(ctx context.Context) (sm.State, error) {
|
||||
if r.eventBus != nil {
|
||||
if err := r.eventBus.PublishEventStateSyncStatus(ctx, types.EventDataStateSyncStatus{
|
||||
if err := r.eventBus.PublishEventStateSyncStatus(types.EventDataStateSyncStatus{
|
||||
Complete: false,
|
||||
Height: r.initialHeight,
|
||||
}); err != nil {
|
||||
@@ -387,7 +387,7 @@ func (r *Reactor) Sync(ctx context.Context) (sm.State, error) {
|
||||
}
|
||||
|
||||
if r.eventBus != nil {
|
||||
if err := r.eventBus.PublishEventStateSyncStatus(ctx, types.EventDataStateSyncStatus{
|
||||
if err := r.eventBus.PublishEventStateSyncStatus(types.EventDataStateSyncStatus{
|
||||
Complete: true,
|
||||
Height: state.LastBlockHeight,
|
||||
}); err != nil {
|
||||
|
||||
@@ -379,7 +379,7 @@ func (s *stateProviderP2P) consensusParams(ctx context.Context, height int64) (t
|
||||
}
|
||||
|
||||
wg.Add(1)
|
||||
go func(p *BlockProvider, peer types.NodeID) {
|
||||
go func(peer types.NodeID) {
|
||||
defer wg.Done()
|
||||
|
||||
timer := time.NewTimer(0)
|
||||
@@ -424,7 +424,7 @@ func (s *stateProviderP2P) consensusParams(ctx context.Context, height int64) (t
|
||||
}
|
||||
}
|
||||
|
||||
}(p, peer)
|
||||
}(peer)
|
||||
}
|
||||
sig := make(chan struct{})
|
||||
go func() { wg.Wait(); close(sig) }()
|
||||
|
||||
@@ -17,7 +17,6 @@ import (
|
||||
"github.com/tendermint/tendermint/crypto"
|
||||
sm "github.com/tendermint/tendermint/internal/state"
|
||||
"github.com/tendermint/tendermint/internal/state/test/factory"
|
||||
"github.com/tendermint/tendermint/libs/log"
|
||||
tmrand "github.com/tendermint/tendermint/libs/rand"
|
||||
tmtime "github.com/tendermint/tendermint/libs/time"
|
||||
"github.com/tendermint/tendermint/types"
|
||||
@@ -46,7 +45,7 @@ func makeTestCommit(height int64, timestamp time.Time) *types.Commit {
|
||||
commitSigs)
|
||||
}
|
||||
|
||||
func makeStateAndBlockStore(dir string, logger log.Logger) (sm.State, *BlockStore, cleanupFunc, error) {
|
||||
func makeStateAndBlockStore(dir string) (sm.State, *BlockStore, cleanupFunc, error) {
|
||||
cfg, err := config.ResetTestRoot(dir, "blockchain_reactor_test")
|
||||
if err != nil {
|
||||
return sm.State{}, nil, nil, err
|
||||
@@ -81,7 +80,7 @@ func TestMain(m *testing.M) {
|
||||
}
|
||||
var cleanup cleanupFunc
|
||||
|
||||
state, _, cleanup, err = makeStateAndBlockStore(dir, log.NewNopLogger())
|
||||
state, _, cleanup, err = makeStateAndBlockStore(dir)
|
||||
if err != nil {
|
||||
stdlog.Fatal(err)
|
||||
}
|
||||
@@ -103,7 +102,7 @@ func TestMain(m *testing.M) {
|
||||
|
||||
// TODO: This test should be simplified ...
|
||||
func TestBlockStoreSaveLoadBlock(t *testing.T) {
|
||||
state, bs, cleanup, err := makeStateAndBlockStore(t.TempDir(), log.NewNopLogger())
|
||||
state, bs, cleanup, err := makeStateAndBlockStore(t.TempDir())
|
||||
defer cleanup()
|
||||
require.NoError(t, err)
|
||||
require.Equal(t, bs.Base(), int64(0), "initially the base should be zero")
|
||||
@@ -492,7 +491,7 @@ func TestLoadBlockMeta(t *testing.T) {
|
||||
}
|
||||
|
||||
func TestBlockFetchAtHeight(t *testing.T) {
|
||||
state, bs, cleanup, err := makeStateAndBlockStore(t.TempDir(), log.NewNopLogger())
|
||||
state, bs, cleanup, err := makeStateAndBlockStore(t.TempDir())
|
||||
defer cleanup()
|
||||
require.NoError(t, err)
|
||||
require.Equal(t, bs.Height(), int64(0), "initially the height should be zero")
|
||||
|
||||
@@ -31,6 +31,7 @@ func MakeCommit(ctx context.Context, blockID types.BlockID, height int64, round
|
||||
return nil, err
|
||||
}
|
||||
vote.Signature = v.Signature
|
||||
vote.ExtensionSignature = v.ExtensionSignature
|
||||
if _, err := voteSet.AddVote(vote); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
@@ -13,25 +13,25 @@ import (
|
||||
tmprotobits "github.com/tendermint/tendermint/proto/tendermint/libs/bits"
|
||||
)
|
||||
|
||||
func randBitArray(bits int) (*BitArray, []byte) {
|
||||
func randBitArray(bits int) *BitArray {
|
||||
src := tmrand.Bytes((bits + 7) / 8)
|
||||
bA := NewBitArray(bits)
|
||||
for i := 0; i < len(src); i++ {
|
||||
for j := 0; j < 8; j++ {
|
||||
if i*8+j >= bits {
|
||||
return bA, src
|
||||
return bA
|
||||
}
|
||||
setBit := src[i]&(1<<uint(j)) > 0
|
||||
bA.SetIndex(i*8+j, setBit)
|
||||
}
|
||||
}
|
||||
return bA, src
|
||||
return bA
|
||||
}
|
||||
|
||||
func TestAnd(t *testing.T) {
|
||||
|
||||
bA1, _ := randBitArray(51)
|
||||
bA2, _ := randBitArray(31)
|
||||
bA1 := randBitArray(51)
|
||||
bA2 := randBitArray(31)
|
||||
bA3 := bA1.And(bA2)
|
||||
|
||||
var bNil *BitArray
|
||||
@@ -54,9 +54,8 @@ func TestAnd(t *testing.T) {
|
||||
}
|
||||
|
||||
func TestOr(t *testing.T) {
|
||||
|
||||
bA1, _ := randBitArray(51)
|
||||
bA2, _ := randBitArray(31)
|
||||
bA1 := randBitArray(51)
|
||||
bA2 := randBitArray(31)
|
||||
bA3 := bA1.Or(bA2)
|
||||
|
||||
bNil := (*BitArray)(nil)
|
||||
@@ -191,10 +190,7 @@ func TestEmptyFull(t *testing.T) {
|
||||
}
|
||||
|
||||
func TestUpdateNeverPanics(t *testing.T) {
|
||||
newRandBitArray := func(n int) *BitArray {
|
||||
ba, _ := randBitArray(n)
|
||||
return ba
|
||||
}
|
||||
newRandBitArray := func(n int) *BitArray { return randBitArray(n) }
|
||||
pairs := []struct {
|
||||
a, b *BitArray
|
||||
}{
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
package events
|
||||
|
||||
import (
|
||||
"context"
|
||||
"sync"
|
||||
)
|
||||
|
||||
@@ -20,7 +19,7 @@ type Eventable interface {
|
||||
//
|
||||
// FireEvent fires an event with the given name and data.
|
||||
type Fireable interface {
|
||||
FireEvent(ctx context.Context, eventValue string, data EventData)
|
||||
FireEvent(eventValue string, data EventData)
|
||||
}
|
||||
|
||||
// EventSwitch is the interface for synchronous pubsub, where listeners
|
||||
@@ -62,7 +61,7 @@ func (evsw *eventSwitch) AddListenerForEvent(listenerID, eventValue string, cb E
|
||||
return nil
|
||||
}
|
||||
|
||||
func (evsw *eventSwitch) FireEvent(ctx context.Context, event string, data EventData) {
|
||||
func (evsw *eventSwitch) FireEvent(event string, data EventData) {
|
||||
// Get the eventCell
|
||||
evsw.mtx.RLock()
|
||||
eventCell := evsw.eventCells[event]
|
||||
@@ -73,12 +72,12 @@ func (evsw *eventSwitch) FireEvent(ctx context.Context, event string, data Event
|
||||
}
|
||||
|
||||
// Fire event for all listeners in eventCell
|
||||
eventCell.fireEvent(ctx, data)
|
||||
eventCell.fireEvent(data)
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
type EventCallback func(ctx context.Context, data EventData) error
|
||||
type EventCallback func(data EventData) error
|
||||
|
||||
// eventCell handles keeping track of listener callbacks for a given event.
|
||||
type eventCell struct {
|
||||
@@ -98,7 +97,7 @@ func (cell *eventCell) addListener(listenerID string, cb EventCallback) {
|
||||
cell.listeners[listenerID] = cb
|
||||
}
|
||||
|
||||
func (cell *eventCell) fireEvent(ctx context.Context, data EventData) {
|
||||
func (cell *eventCell) fireEvent(data EventData) {
|
||||
cell.mtx.RLock()
|
||||
eventCallbacks := make([]EventCallback, 0, len(cell.listeners))
|
||||
for _, cb := range cell.listeners {
|
||||
@@ -107,7 +106,7 @@ func (cell *eventCell) fireEvent(ctx context.Context, data EventData) {
|
||||
cell.mtx.RUnlock()
|
||||
|
||||
for _, cb := range eventCallbacks {
|
||||
if err := cb(ctx, data); err != nil {
|
||||
if err := cb(data); err != nil {
|
||||
// should we log or abort here?
|
||||
continue
|
||||
}
|
||||
|
||||
+24
-19
@@ -7,6 +7,7 @@ import (
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/fortytw2/leaktest"
|
||||
"github.com/stretchr/testify/require"
|
||||
)
|
||||
|
||||
@@ -20,7 +21,7 @@ func TestAddListenerForEventFireOnce(t *testing.T) {
|
||||
|
||||
messages := make(chan EventData)
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener", "event",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case messages <- data:
|
||||
return nil
|
||||
@@ -28,7 +29,7 @@ func TestAddListenerForEventFireOnce(t *testing.T) {
|
||||
return ctx.Err()
|
||||
}
|
||||
}))
|
||||
go evsw.FireEvent(ctx, "event", "data")
|
||||
go evsw.FireEvent("event", "data")
|
||||
received := <-messages
|
||||
if received != "data" {
|
||||
t.Errorf("message received does not match: %v", received)
|
||||
@@ -48,7 +49,7 @@ func TestAddListenerForEventFireMany(t *testing.T) {
|
||||
numbers := make(chan uint64, 4)
|
||||
// subscribe one listener for one event
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener", "event",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers <- data.(uint64):
|
||||
return nil
|
||||
@@ -75,6 +76,8 @@ func TestAddListenerForDifferentEvents(t *testing.T) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
t.Cleanup(leaktest.Check(t))
|
||||
|
||||
evsw := NewEventSwitch()
|
||||
|
||||
doneSum := make(chan uint64)
|
||||
@@ -84,7 +87,7 @@ func TestAddListenerForDifferentEvents(t *testing.T) {
|
||||
numbers := make(chan uint64, 4)
|
||||
// subscribe one listener to three events
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener", "event1",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers <- data.(uint64):
|
||||
return nil
|
||||
@@ -93,7 +96,7 @@ func TestAddListenerForDifferentEvents(t *testing.T) {
|
||||
}
|
||||
}))
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener", "event2",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers <- data.(uint64):
|
||||
return nil
|
||||
@@ -102,7 +105,7 @@ func TestAddListenerForDifferentEvents(t *testing.T) {
|
||||
}
|
||||
}))
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener", "event3",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers <- data.(uint64):
|
||||
return nil
|
||||
@@ -135,6 +138,8 @@ func TestAddDifferentListenerForDifferentEvents(t *testing.T) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
t.Cleanup(leaktest.Check(t))
|
||||
|
||||
evsw := NewEventSwitch()
|
||||
|
||||
doneSum1 := make(chan uint64)
|
||||
@@ -146,7 +151,7 @@ func TestAddDifferentListenerForDifferentEvents(t *testing.T) {
|
||||
numbers2 := make(chan uint64, 4)
|
||||
// subscribe two listener to three events
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener1", "event1",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers1 <- data.(uint64):
|
||||
return nil
|
||||
@@ -155,7 +160,7 @@ func TestAddDifferentListenerForDifferentEvents(t *testing.T) {
|
||||
}
|
||||
}))
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener1", "event2",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers1 <- data.(uint64):
|
||||
return nil
|
||||
@@ -164,7 +169,7 @@ func TestAddDifferentListenerForDifferentEvents(t *testing.T) {
|
||||
}
|
||||
}))
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener1", "event3",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers1 <- data.(uint64):
|
||||
return nil
|
||||
@@ -173,7 +178,7 @@ func TestAddDifferentListenerForDifferentEvents(t *testing.T) {
|
||||
}
|
||||
}))
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener2", "event2",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers2 <- data.(uint64):
|
||||
return nil
|
||||
@@ -182,7 +187,7 @@ func TestAddDifferentListenerForDifferentEvents(t *testing.T) {
|
||||
}
|
||||
}))
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener2", "event3",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers2 <- data.(uint64):
|
||||
return nil
|
||||
@@ -238,7 +243,7 @@ func TestManageListenersAsync(t *testing.T) {
|
||||
numbers2 := make(chan uint64, 4)
|
||||
// subscribe two listener to three events
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener1", "event1",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers1 <- data.(uint64):
|
||||
return nil
|
||||
@@ -247,7 +252,7 @@ func TestManageListenersAsync(t *testing.T) {
|
||||
}
|
||||
}))
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener1", "event2",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers1 <- data.(uint64):
|
||||
return nil
|
||||
@@ -256,7 +261,7 @@ func TestManageListenersAsync(t *testing.T) {
|
||||
}
|
||||
}))
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener1", "event3",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers1 <- data.(uint64):
|
||||
return nil
|
||||
@@ -265,7 +270,7 @@ func TestManageListenersAsync(t *testing.T) {
|
||||
}
|
||||
}))
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener2", "event1",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers2 <- data.(uint64):
|
||||
return nil
|
||||
@@ -274,7 +279,7 @@ func TestManageListenersAsync(t *testing.T) {
|
||||
}
|
||||
}))
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener2", "event2",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers2 <- data.(uint64):
|
||||
return nil
|
||||
@@ -283,7 +288,7 @@ func TestManageListenersAsync(t *testing.T) {
|
||||
}
|
||||
}))
|
||||
require.NoError(t, evsw.AddListenerForEvent("listener2", "event3",
|
||||
func(ctx context.Context, data EventData) error {
|
||||
func(data EventData) error {
|
||||
select {
|
||||
case numbers2 <- data.(uint64):
|
||||
return nil
|
||||
@@ -303,7 +308,7 @@ func TestManageListenersAsync(t *testing.T) {
|
||||
eventNumber := r1.Intn(3) + 1
|
||||
go evsw.AddListenerForEvent(fmt.Sprintf("listener%v", listenerNumber), //nolint:errcheck // ignore for tests
|
||||
fmt.Sprintf("event%v", eventNumber),
|
||||
func(context.Context, EventData) error { return nil })
|
||||
func(EventData) error { return nil })
|
||||
}
|
||||
}
|
||||
addListenersStress()
|
||||
@@ -358,7 +363,7 @@ func fireEvents(ctx context.Context, evsw Fireable, event string, doneChan chan
|
||||
break
|
||||
}
|
||||
|
||||
evsw.FireEvent(ctx, event, i)
|
||||
evsw.FireEvent(event, i)
|
||||
sentSum += i
|
||||
}
|
||||
|
||||
|
||||
@@ -69,7 +69,7 @@ func BenchmarkSequence(b *testing.B) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
headers, vals, _ := genLightBlocksWithKeys(b, chainID, 1000, 100, 1, bTime)
|
||||
headers, vals, _ := genLightBlocksWithKeys(b, 1000, 100, 1, bTime)
|
||||
benchmarkFullNode := newProviderBenchmarkImpl(headers, vals)
|
||||
genesisBlock, _ := benchmarkFullNode.LightBlock(ctx, 1)
|
||||
|
||||
@@ -106,7 +106,7 @@ func BenchmarkBisection(b *testing.B) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
headers, vals, _ := genLightBlocksWithKeys(b, chainID, 1000, 100, 1, bTime)
|
||||
headers, vals, _ := genLightBlocksWithKeys(b, 1000, 100, 1, bTime)
|
||||
benchmarkFullNode := newProviderBenchmarkImpl(headers, vals)
|
||||
genesisBlock, _ := benchmarkFullNode.LightBlock(ctx, 1)
|
||||
|
||||
@@ -142,7 +142,7 @@ func BenchmarkBackwards(b *testing.B) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
headers, vals, _ := genLightBlocksWithKeys(b, chainID, 1000, 100, 1, bTime)
|
||||
headers, vals, _ := genLightBlocksWithKeys(b, 1000, 100, 1, bTime)
|
||||
benchmarkFullNode := newProviderBenchmarkImpl(headers, vals)
|
||||
trustedBlock, _ := benchmarkFullNode.LightBlock(ctx, 0)
|
||||
|
||||
|
||||
@@ -387,7 +387,7 @@ func TestClient(t *testing.T) {
|
||||
// the appropriate range
|
||||
|
||||
numBlocks := int64(300)
|
||||
mockHeaders, mockVals, _ := genLightBlocksWithKeys(t, chainID, numBlocks, 101, 2, bTime)
|
||||
mockHeaders, mockVals, _ := genLightBlocksWithKeys(t, numBlocks, 101, 2, bTime)
|
||||
|
||||
lastBlock := &types.LightBlock{SignedHeader: mockHeaders[numBlocks], ValidatorSet: mockVals[numBlocks]}
|
||||
mockNode := &provider_mocks.Provider{}
|
||||
@@ -773,7 +773,7 @@ func TestClient(t *testing.T) {
|
||||
logger := log.NewNopLogger()
|
||||
|
||||
{
|
||||
headers, vals, _ := genLightBlocksWithKeys(t, chainID, 9, 3, 0, bTime)
|
||||
headers, vals, _ := genLightBlocksWithKeys(t, 9, 3, 0, bTime)
|
||||
delete(headers, 1)
|
||||
delete(headers, 2)
|
||||
delete(vals, 1)
|
||||
|
||||
+10
-10
@@ -35,7 +35,7 @@ func TestLightClientAttackEvidence_Lunatic(t *testing.T) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
witnessHeaders, witnessValidators, chainKeys := genLightBlocksWithKeys(t, chainID, latestHeight, valSize, 2, bTime)
|
||||
witnessHeaders, witnessValidators, chainKeys := genLightBlocksWithKeys(t, latestHeight, valSize, 2, bTime)
|
||||
|
||||
forgedKeys := chainKeys[divergenceHeight-1].ChangeKeys(3) // we change 3 out of the 5 validators (still 2/5 remain)
|
||||
forgedVals := forgedKeys.ToValidators(2, 0)
|
||||
@@ -153,7 +153,7 @@ func TestLightClientAttackEvidence_Equivocation(t *testing.T) {
|
||||
// validators don't change in this network (however we still use a map just for convenience)
|
||||
primaryValidators = make(map[int64]*types.ValidatorSet, testCase.latestHeight)
|
||||
)
|
||||
witnessHeaders, witnessValidators, chainKeys := genLightBlocksWithKeys(t, chainID,
|
||||
witnessHeaders, witnessValidators, chainKeys := genLightBlocksWithKeys(t,
|
||||
testCase.latestHeight+1, valSize, 2, bTime)
|
||||
for height := int64(1); height <= testCase.latestHeight; height++ {
|
||||
if height < testCase.divergenceHeight {
|
||||
@@ -250,7 +250,7 @@ func TestLightClientAttackEvidence_ForwardLunatic(t *testing.T) {
|
||||
defer cancel()
|
||||
logger := log.NewNopLogger()
|
||||
|
||||
witnessHeaders, witnessValidators, chainKeys := genLightBlocksWithKeys(t, chainID, latestHeight, valSize, 2, bTime)
|
||||
witnessHeaders, witnessValidators, chainKeys := genLightBlocksWithKeys(t, latestHeight, valSize, 2, bTime)
|
||||
for _, unusedHeader := range []int64{3, 5, 6, 8} {
|
||||
delete(witnessHeaders, unusedHeader)
|
||||
}
|
||||
@@ -401,13 +401,13 @@ func TestClientDivergentTraces1(t *testing.T) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
headers, vals, _ := genLightBlocksWithKeys(t, chainID, 1, 5, 2, bTime)
|
||||
headers, vals, _ := genLightBlocksWithKeys(t, 1, 5, 2, bTime)
|
||||
mockPrimary := mockNodeFromHeadersAndVals(headers, vals)
|
||||
mockPrimary.On("ID").Return("mockPrimary")
|
||||
|
||||
firstBlock, err := mockPrimary.LightBlock(ctx, 1)
|
||||
require.NoError(t, err)
|
||||
headers, vals, _ = genLightBlocksWithKeys(t, chainID, 1, 5, 2, bTime)
|
||||
headers, vals, _ = genLightBlocksWithKeys(t, 1, 5, 2, bTime)
|
||||
mockWitness := mockNodeFromHeadersAndVals(headers, vals)
|
||||
mockWitness.On("ID").Return("mockWitness")
|
||||
|
||||
@@ -439,7 +439,7 @@ func TestClientDivergentTraces2(t *testing.T) {
|
||||
defer cancel()
|
||||
logger := log.NewNopLogger()
|
||||
|
||||
headers, vals, _ := genLightBlocksWithKeys(t, chainID, 2, 5, 2, bTime)
|
||||
headers, vals, _ := genLightBlocksWithKeys(t, 2, 5, 2, bTime)
|
||||
mockPrimaryNode := mockNodeFromHeadersAndVals(headers, vals)
|
||||
mockPrimaryNode.On("ID").Return("mockPrimaryNode")
|
||||
|
||||
@@ -485,7 +485,7 @@ func TestClientDivergentTraces3(t *testing.T) {
|
||||
logger := log.NewNopLogger()
|
||||
|
||||
//
|
||||
primaryHeaders, primaryVals, _ := genLightBlocksWithKeys(t, chainID, 2, 5, 2, bTime)
|
||||
primaryHeaders, primaryVals, _ := genLightBlocksWithKeys(t, 2, 5, 2, bTime)
|
||||
mockPrimary := mockNodeFromHeadersAndVals(primaryHeaders, primaryVals)
|
||||
mockPrimary.On("ID").Return("mockPrimary")
|
||||
|
||||
@@ -495,7 +495,7 @@ func TestClientDivergentTraces3(t *testing.T) {
|
||||
firstBlock, err := mockPrimary.LightBlock(ctx, 1)
|
||||
require.NoError(t, err)
|
||||
|
||||
mockHeaders, mockVals, _ := genLightBlocksWithKeys(t, chainID, 2, 5, 2, bTime)
|
||||
mockHeaders, mockVals, _ := genLightBlocksWithKeys(t, 2, 5, 2, bTime)
|
||||
mockHeaders[1] = primaryHeaders[1]
|
||||
mockVals[1] = primaryVals[1]
|
||||
mockWitness := mockNodeFromHeadersAndVals(mockHeaders, mockVals)
|
||||
@@ -530,7 +530,7 @@ func TestClientDivergentTraces4(t *testing.T) {
|
||||
logger := log.NewNopLogger()
|
||||
|
||||
//
|
||||
primaryHeaders, primaryVals, _ := genLightBlocksWithKeys(t, chainID, 2, 5, 2, bTime)
|
||||
primaryHeaders, primaryVals, _ := genLightBlocksWithKeys(t, 2, 5, 2, bTime)
|
||||
mockPrimary := mockNodeFromHeadersAndVals(primaryHeaders, primaryVals)
|
||||
mockPrimary.On("ID").Return("mockPrimary")
|
||||
|
||||
@@ -540,7 +540,7 @@ func TestClientDivergentTraces4(t *testing.T) {
|
||||
firstBlock, err := mockPrimary.LightBlock(ctx, 1)
|
||||
require.NoError(t, err)
|
||||
|
||||
witnessHeaders, witnessVals, _ := genLightBlocksWithKeys(t, chainID, 2, 5, 2, bTime)
|
||||
witnessHeaders, witnessVals, _ := genLightBlocksWithKeys(t, 2, 5, 2, bTime)
|
||||
primaryHeaders[2] = witnessHeaders[2]
|
||||
primaryVals[2] = witnessVals[2]
|
||||
mockWitness := mockNodeFromHeadersAndVals(primaryHeaders, primaryVals)
|
||||
|
||||
@@ -160,7 +160,6 @@ func (pkz privKeys) ChangeKeys(delta int) privKeys {
|
||||
// NOTE: Expected to have a large validator set size ~ 100 validators.
|
||||
func genLightBlocksWithKeys(
|
||||
t testing.TB,
|
||||
chainID string,
|
||||
numBlocks int64,
|
||||
valSize int,
|
||||
valVariation float32,
|
||||
|
||||
+40
-19
@@ -29,6 +29,7 @@ import (
|
||||
rpccore "github.com/tendermint/tendermint/internal/rpc/core"
|
||||
sm "github.com/tendermint/tendermint/internal/state"
|
||||
"github.com/tendermint/tendermint/internal/state/indexer"
|
||||
"github.com/tendermint/tendermint/internal/state/indexer/sink"
|
||||
"github.com/tendermint/tendermint/internal/statesync"
|
||||
"github.com/tendermint/tendermint/internal/store"
|
||||
"github.com/tendermint/tendermint/libs/log"
|
||||
@@ -168,15 +169,19 @@ func makeNode(
|
||||
Metrics: nodeMetrics.eventlog,
|
||||
})
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("initializing event log: %w", err)
|
||||
return nil, combineCloseError(fmt.Errorf("initializing event log: %w", err), makeCloser(closers))
|
||||
}
|
||||
}
|
||||
|
||||
indexerService, eventSinks, err := createIndexerService(
|
||||
cfg, dbProvider, eventBus, logger, genDoc.ChainID, nodeMetrics.indexer)
|
||||
eventSinks, err := sink.EventSinksFromConfig(cfg, dbProvider, genDoc.ChainID)
|
||||
if err != nil {
|
||||
return nil, combineCloseError(err, makeCloser(closers))
|
||||
}
|
||||
indexerService := indexer.NewService(indexer.ServiceArgs{
|
||||
Sinks: eventSinks,
|
||||
EventBus: eventBus,
|
||||
Logger: logger.With("module", "txindex"),
|
||||
Metrics: nodeMetrics.indexer,
|
||||
})
|
||||
|
||||
privValidator, err := createPrivval(ctx, logger, cfg, genDoc, filePrivval)
|
||||
if err != nil {
|
||||
@@ -260,11 +265,8 @@ func makeNode(
|
||||
node.rpcEnv.EvidencePool = evPool
|
||||
node.evPool = evPool
|
||||
|
||||
mpReactor, mp, err := createMempoolReactor(logger, cfg, proxyApp, stateStore, nodeMetrics.mempool,
|
||||
mpReactor, mp := createMempoolReactor(logger, cfg, proxyApp, stateStore, nodeMetrics.mempool,
|
||||
peerManager.Subscribe, node.router.OpenChannel, peerManager.GetHeight)
|
||||
if err != nil {
|
||||
return nil, combineCloseError(err, makeCloser(closers))
|
||||
}
|
||||
node.rpcEnv.Mempool = mp
|
||||
node.services = append(node.services, mpReactor)
|
||||
|
||||
@@ -292,16 +294,32 @@ func makeNode(
|
||||
blockSync := !onlyValidatorIsUs(state, pubKey)
|
||||
waitSync := stateSync || blockSync
|
||||
|
||||
csReactor, csState, err := createConsensusReactor(ctx,
|
||||
cfg, stateStore, blockExec, blockStore, mp, evPool,
|
||||
privValidator, nodeMetrics.consensus, waitSync, eventBus,
|
||||
peerManager, node.router.OpenChannel, logger,
|
||||
csState, err := consensus.NewState(logger.With("module", "consensus"),
|
||||
cfg.Consensus,
|
||||
stateStore,
|
||||
blockExec,
|
||||
blockStore,
|
||||
mp,
|
||||
evPool,
|
||||
eventBus,
|
||||
consensus.StateMetrics(nodeMetrics.consensus),
|
||||
consensus.SkipStateStoreBootstrap,
|
||||
)
|
||||
if err != nil {
|
||||
return nil, combineCloseError(err, makeCloser(closers))
|
||||
}
|
||||
node.services = append(node.services, csReactor)
|
||||
node.rpcEnv.ConsensusState = csState
|
||||
|
||||
csReactor := consensus.NewReactor(
|
||||
logger,
|
||||
csState,
|
||||
node.router.OpenChannel,
|
||||
peerManager.Subscribe,
|
||||
eventBus,
|
||||
waitSync,
|
||||
nodeMetrics.consensus,
|
||||
)
|
||||
node.services = append(node.services, csReactor)
|
||||
node.rpcEnv.ConsensusReactor = csReactor
|
||||
|
||||
// Create the blockchain reactor. Note, we do not start block sync if we're
|
||||
@@ -370,6 +388,9 @@ func makeNode(
|
||||
))
|
||||
|
||||
if cfg.Mode == config.ModeValidator {
|
||||
if privValidator != nil {
|
||||
csState.SetPrivValidator(ctx, privValidator)
|
||||
}
|
||||
node.rpcEnv.PubKey = pubKey
|
||||
}
|
||||
|
||||
@@ -423,7 +444,7 @@ func (n *nodeImpl) OnStart(ctx context.Context) error {
|
||||
// Start Internal Services
|
||||
|
||||
if n.config.RPC.PprofListenAddress != "" {
|
||||
rpcCtx, rpcCancel := context.WithCancel(ctx)
|
||||
signal := make(chan struct{})
|
||||
srv := &http.Server{Addr: n.config.RPC.PprofListenAddress, Handler: nil}
|
||||
go func() {
|
||||
select {
|
||||
@@ -431,7 +452,7 @@ func (n *nodeImpl) OnStart(ctx context.Context) error {
|
||||
sctx, scancel := context.WithTimeout(context.Background(), time.Second)
|
||||
defer scancel()
|
||||
_ = srv.Shutdown(sctx)
|
||||
case <-rpcCtx.Done():
|
||||
case <-signal:
|
||||
}
|
||||
}()
|
||||
|
||||
@@ -440,7 +461,7 @@ func (n *nodeImpl) OnStart(ctx context.Context) error {
|
||||
|
||||
if err := srv.ListenAndServe(); err != nil {
|
||||
n.logger.Error("pprof server error", "err", err)
|
||||
rpcCancel()
|
||||
close(signal)
|
||||
}
|
||||
}()
|
||||
}
|
||||
@@ -562,21 +583,21 @@ func (n *nodeImpl) startPrometheusServer(ctx context.Context, addr string) *http
|
||||
),
|
||||
}
|
||||
|
||||
promCtx, promCancel := context.WithCancel(ctx)
|
||||
signal := make(chan struct{})
|
||||
go func() {
|
||||
select {
|
||||
case <-ctx.Done():
|
||||
sctx, scancel := context.WithTimeout(context.Background(), time.Second)
|
||||
defer scancel()
|
||||
_ = srv.Shutdown(sctx)
|
||||
case <-promCtx.Done():
|
||||
case <-signal:
|
||||
}
|
||||
}()
|
||||
|
||||
go func() {
|
||||
if err := srv.ListenAndServe(); err != nil {
|
||||
n.logger.Error("Prometheus HTTP server ListenAndServe", "err", err)
|
||||
promCancel()
|
||||
close(signal)
|
||||
}
|
||||
}()
|
||||
|
||||
|
||||
+15
-7
@@ -28,6 +28,7 @@ import (
|
||||
"github.com/tendermint/tendermint/internal/pubsub"
|
||||
sm "github.com/tendermint/tendermint/internal/state"
|
||||
"github.com/tendermint/tendermint/internal/state/indexer"
|
||||
"github.com/tendermint/tendermint/internal/state/indexer/sink"
|
||||
"github.com/tendermint/tendermint/internal/store"
|
||||
"github.com/tendermint/tendermint/internal/test/factory"
|
||||
"github.com/tendermint/tendermint/libs/log"
|
||||
@@ -454,7 +455,8 @@ func TestMaxProposalBlockSize(t *testing.T) {
|
||||
err = proxyApp.Start(ctx)
|
||||
require.NoError(t, err)
|
||||
|
||||
state, stateDB, _ := state(t, types.MaxVotesCount, int64(1))
|
||||
state, stateDB, privVals := state(t, types.MaxVotesCount, int64(1))
|
||||
|
||||
stateStore := sm.NewStore(stateDB)
|
||||
blockStore := store.NewBlockStore(dbm.NewMemDB())
|
||||
const maxBytes int64 = 1024 * 1024 * 2
|
||||
@@ -537,17 +539,25 @@ func TestMaxProposalBlockSize(t *testing.T) {
|
||||
BlockID: blockID,
|
||||
}
|
||||
|
||||
votes := make([]*types.Vote, types.MaxVotesCount)
|
||||
|
||||
// add maximum amount of signatures to a single commit
|
||||
for i := 0; i < types.MaxVotesCount; i++ {
|
||||
pubKey, err := privVals[i].GetPubKey(ctx)
|
||||
require.NoError(t, err)
|
||||
votes[i] = &types.Vote{
|
||||
ValidatorAddress: pubKey.Address(),
|
||||
}
|
||||
commit.Signatures = append(commit.Signatures, cs)
|
||||
}
|
||||
|
||||
block, err := blockExec.CreateProposalBlock(
|
||||
ctx,
|
||||
math.MaxInt64,
|
||||
state, commit,
|
||||
state,
|
||||
commit,
|
||||
proposerAddr,
|
||||
nil,
|
||||
votes,
|
||||
)
|
||||
require.NoError(t, err)
|
||||
partSet, err := block.MakePartSet(types.BlockPartSizeBytes)
|
||||
@@ -627,11 +637,9 @@ func TestNodeSetEventSink(t *testing.T) {
|
||||
genDoc, err := types.GenesisDocFromFile(cfg.GenesisFile())
|
||||
require.NoError(t, err)
|
||||
|
||||
indexService, eventSinks, err := createIndexerService(cfg,
|
||||
config.DefaultDBProvider, eventBus, logger, genDoc.ChainID,
|
||||
indexer.NopMetrics())
|
||||
eventSinks, err := sink.EventSinksFromConfig(cfg, config.DefaultDBProvider, genDoc.ChainID)
|
||||
require.NoError(t, err)
|
||||
t.Cleanup(indexService.Wait)
|
||||
|
||||
return eventSinks
|
||||
}
|
||||
cleanup := func(ns service.Service) func() {
|
||||
|
||||
+4
-85
@@ -23,7 +23,6 @@ import (
|
||||
"github.com/tendermint/tendermint/internal/p2p/pex"
|
||||
sm "github.com/tendermint/tendermint/internal/state"
|
||||
"github.com/tendermint/tendermint/internal/state/indexer"
|
||||
"github.com/tendermint/tendermint/internal/state/indexer/sink"
|
||||
"github.com/tendermint/tendermint/internal/statesync"
|
||||
"github.com/tendermint/tendermint/internal/store"
|
||||
"github.com/tendermint/tendermint/libs/log"
|
||||
@@ -95,29 +94,6 @@ func initDBs(
|
||||
return blockStore, stateDB, makeCloser(closers), nil
|
||||
}
|
||||
|
||||
func createIndexerService(
|
||||
cfg *config.Config,
|
||||
dbProvider config.DBProvider,
|
||||
eventBus *eventbus.EventBus,
|
||||
logger log.Logger,
|
||||
chainID string,
|
||||
metrics *indexer.Metrics,
|
||||
) (*indexer.Service, []indexer.EventSink, error) {
|
||||
eventSinks, err := sink.EventSinksFromConfig(cfg, dbProvider, chainID)
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
indexerService := indexer.NewService(indexer.ServiceArgs{
|
||||
Sinks: eventSinks,
|
||||
EventBus: eventBus,
|
||||
Logger: logger.With("module", "txindex"),
|
||||
Metrics: metrics,
|
||||
})
|
||||
|
||||
return indexerService, eventSinks, nil
|
||||
}
|
||||
|
||||
func logNodeStartupInfo(state sm.State, pubKey crypto.PubKey, logger log.Logger, mode string) {
|
||||
// Log the version info.
|
||||
logger.Info("Version info",
|
||||
@@ -172,7 +148,7 @@ func createMempoolReactor(
|
||||
peerEvents p2p.PeerEventSubscriber,
|
||||
chCreator p2p.ChannelCreator,
|
||||
peerHeight func(types.NodeID) int64,
|
||||
) (service.Service, mempool.Mempool, error) {
|
||||
) (service.Service, mempool.Mempool) {
|
||||
logger = logger.With("module", "mempool")
|
||||
|
||||
mp := mempool.NewTxMempool(
|
||||
@@ -197,7 +173,7 @@ func createMempoolReactor(
|
||||
mp.EnableTxsAvailable()
|
||||
}
|
||||
|
||||
return reactor, mp, nil
|
||||
return reactor, mp
|
||||
}
|
||||
|
||||
func createEvidenceReactor(
|
||||
@@ -215,70 +191,13 @@ func createEvidenceReactor(
|
||||
if err != nil {
|
||||
return nil, nil, func() error { return nil }, fmt.Errorf("unable to initialize evidence db: %w", err)
|
||||
}
|
||||
dbCloser := evidenceDB.Close
|
||||
|
||||
logger = logger.With("module", "evidence")
|
||||
|
||||
evidencePool := evidence.NewPool(logger, evidenceDB, store, blockStore, metrics, eventBus)
|
||||
evidenceReactor := evidence.NewReactor(logger, chCreator, peerEvents, evidencePool)
|
||||
|
||||
evidenceReactor := evidence.NewReactor(
|
||||
logger,
|
||||
chCreator,
|
||||
peerEvents,
|
||||
evidencePool,
|
||||
)
|
||||
|
||||
return evidenceReactor, evidencePool, dbCloser, nil
|
||||
}
|
||||
|
||||
func createConsensusReactor(
|
||||
ctx context.Context,
|
||||
cfg *config.Config,
|
||||
store sm.Store,
|
||||
blockExec *sm.BlockExecutor,
|
||||
blockStore sm.BlockStore,
|
||||
mp mempool.Mempool,
|
||||
evidencePool *evidence.Pool,
|
||||
privValidator types.PrivValidator,
|
||||
csMetrics *consensus.Metrics,
|
||||
waitSync bool,
|
||||
eventBus *eventbus.EventBus,
|
||||
peerManager *p2p.PeerManager,
|
||||
chCreator p2p.ChannelCreator,
|
||||
logger log.Logger,
|
||||
) (*consensus.Reactor, *consensus.State, error) {
|
||||
logger = logger.With("module", "consensus")
|
||||
|
||||
consensusState, err := consensus.NewState(ctx,
|
||||
logger,
|
||||
cfg.Consensus,
|
||||
store,
|
||||
blockExec,
|
||||
blockStore,
|
||||
mp,
|
||||
evidencePool,
|
||||
eventBus,
|
||||
consensus.StateMetrics(csMetrics),
|
||||
consensus.SkipStateStoreBootstrap,
|
||||
)
|
||||
if err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
if privValidator != nil && cfg.Mode == config.ModeValidator {
|
||||
consensusState.SetPrivValidator(ctx, privValidator)
|
||||
}
|
||||
|
||||
reactor := consensus.NewReactor(
|
||||
logger,
|
||||
consensusState,
|
||||
chCreator,
|
||||
peerManager.Subscribe,
|
||||
eventBus,
|
||||
waitSync,
|
||||
csMetrics,
|
||||
)
|
||||
return reactor, consensusState, nil
|
||||
return evidenceReactor, evidencePool, evidenceDB.Close, nil
|
||||
}
|
||||
|
||||
func createPeerManager(
|
||||
|
||||
+29
-8
@@ -117,6 +117,14 @@ type FilePVLastSignState struct {
|
||||
filePath string
|
||||
}
|
||||
|
||||
func (lss *FilePVLastSignState) reset() {
|
||||
lss.Height = 0
|
||||
lss.Round = 0
|
||||
lss.Step = 0
|
||||
lss.Signature = nil
|
||||
lss.SignBytes = nil
|
||||
}
|
||||
|
||||
// checkHRS checks the given height, round, step (HRS) against that of the
|
||||
// FilePVLastSignState. It returns an error if the arguments constitute a regression,
|
||||
// or if they match but the SignBytes are empty.
|
||||
@@ -328,12 +336,7 @@ func (pv *FilePV) Save() error {
|
||||
// Reset resets all fields in the FilePV.
|
||||
// NOTE: Unsafe!
|
||||
func (pv *FilePV) Reset() error {
|
||||
var sig []byte
|
||||
pv.LastSignState.Height = 0
|
||||
pv.LastSignState.Round = 0
|
||||
pv.LastSignState.Step = 0
|
||||
pv.LastSignState.Signature = sig
|
||||
pv.LastSignState.SignBytes = nil
|
||||
pv.LastSignState.reset()
|
||||
return pv.Save()
|
||||
}
|
||||
|
||||
@@ -369,6 +372,12 @@ func (pv *FilePV) signVote(chainID string, vote *tmproto.Vote) error {
|
||||
}
|
||||
|
||||
signBytes := types.VoteSignBytes(chainID, vote)
|
||||
extSignBytes := types.VoteExtensionSignBytes(chainID, vote)
|
||||
// We always sign the vote extension. See below for details.
|
||||
extSig, err := pv.Key.PrivKey.Sign(extSignBytes)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// We might crash before writing to the wal,
|
||||
// causing us to try to re-sign for the same HRS.
|
||||
@@ -379,6 +388,8 @@ func (pv *FilePV) signVote(chainID string, vote *tmproto.Vote) error {
|
||||
if bytes.Equal(signBytes, lss.SignBytes) {
|
||||
vote.Signature = lss.Signature
|
||||
} else {
|
||||
// Compares the canonicalized votes (i.e. without vote extensions
|
||||
// or vote extension signatures).
|
||||
timestamp, ok, err := checkVotesOnlyDifferByTimestamp(lss.SignBytes, signBytes)
|
||||
if err != nil {
|
||||
return err
|
||||
@@ -390,6 +401,12 @@ func (pv *FilePV) signVote(chainID string, vote *tmproto.Vote) error {
|
||||
vote.Timestamp = timestamp
|
||||
vote.Signature = lss.Signature
|
||||
}
|
||||
|
||||
// Vote extensions are non-deterministic, so it's possible that an
|
||||
// application may have created a different extension. We therefore
|
||||
// always re-sign the vote extension.
|
||||
vote.ExtensionSignature = extSig
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -402,6 +419,8 @@ func (pv *FilePV) signVote(chainID string, vote *tmproto.Vote) error {
|
||||
return err
|
||||
}
|
||||
vote.Signature = sig
|
||||
vote.ExtensionSignature = extSig
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -453,8 +472,10 @@ func (pv *FilePV) saveSigned(height int64, round int32, step int8, signBytes []b
|
||||
|
||||
//-----------------------------------------------------------------------------------------
|
||||
|
||||
// returns the timestamp from the lastSignBytes.
|
||||
// returns true if the only difference in the votes is their timestamp.
|
||||
// Returns the timestamp from the lastSignBytes.
|
||||
// Returns true if the only difference in the votes is their timestamp.
|
||||
// Performs these checks on the canonical votes (excluding the vote extension
|
||||
// and vote extension signatures).
|
||||
func checkVotesOnlyDifferByTimestamp(lastSignBytes, newSignBytes []byte) (time.Time, bool, error) {
|
||||
var lastVote, newVote tmproto.CanonicalVote
|
||||
if err := protoio.UnmarshalDelimited(lastSignBytes, &lastVote); err != nil {
|
||||
|
||||
+91
-41
@@ -21,20 +21,14 @@ import (
|
||||
)
|
||||
|
||||
func TestGenLoadValidator(t *testing.T) {
|
||||
tempKeyFile, err := os.CreateTemp(t.TempDir(), "priv_validator_key_")
|
||||
require.NoError(t, err)
|
||||
tempStateFile, err := os.CreateTemp(t.TempDir(), "priv_validator_state_")
|
||||
require.NoError(t, err)
|
||||
|
||||
privVal, err := GenFilePV(tempKeyFile.Name(), tempStateFile.Name(), "")
|
||||
require.NoError(t, err)
|
||||
privVal, tempKeyFileName, tempStateFileName := newTestFilePV(t)
|
||||
|
||||
height := int64(100)
|
||||
privVal.LastSignState.Height = height
|
||||
require.NoError(t, privVal.Save())
|
||||
addr := privVal.GetAddress()
|
||||
|
||||
privVal, err = LoadFilePV(tempKeyFile.Name(), tempStateFile.Name())
|
||||
privVal, err := LoadFilePV(tempKeyFileName, tempStateFileName)
|
||||
assert.NoError(t, err)
|
||||
assert.Equal(t, addr, privVal.GetAddress(), "expected privval addr to be the same")
|
||||
assert.Equal(t, height, privVal.LastSignState.Height, "expected privval.LastHeight to have been saved")
|
||||
@@ -44,14 +38,8 @@ func TestResetValidator(t *testing.T) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
tempKeyFile, err := os.CreateTemp(t.TempDir(), "priv_validator_key_")
|
||||
require.NoError(t, err)
|
||||
tempStateFile, err := os.CreateTemp(t.TempDir(), "priv_validator_state_")
|
||||
require.NoError(t, err)
|
||||
|
||||
privVal, err := GenFilePV(tempKeyFile.Name(), tempStateFile.Name(), "")
|
||||
require.NoError(t, err)
|
||||
emptyState := FilePVLastSignState{filePath: tempStateFile.Name()}
|
||||
privVal, _, tempStateFileName := newTestFilePV(t)
|
||||
emptyState := FilePVLastSignState{filePath: tempStateFileName}
|
||||
|
||||
// new priv val has empty state
|
||||
assert.Equal(t, privVal.LastSignState, emptyState)
|
||||
@@ -61,8 +49,8 @@ func TestResetValidator(t *testing.T) {
|
||||
voteType := tmproto.PrevoteType
|
||||
randBytes := tmrand.Bytes(tmhash.Size)
|
||||
blockID := types.BlockID{Hash: randBytes, PartSetHeader: types.PartSetHeader{}}
|
||||
vote := newVote(privVal.Key.Address, 0, height, round, voteType, blockID)
|
||||
err = privVal.SignVote(ctx, "mychainid", vote.ToProto())
|
||||
vote := newVote(privVal.Key.Address, 0, height, round, voteType, blockID, nil)
|
||||
err := privVal.SignVote(ctx, "mychainid", vote.ToProto())
|
||||
assert.NoError(t, err, "expected no error signing vote")
|
||||
|
||||
// priv val after signing is not same as empty
|
||||
@@ -160,13 +148,7 @@ func TestSignVote(t *testing.T) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
tempKeyFile, err := os.CreateTemp(t.TempDir(), "priv_validator_key_")
|
||||
require.NoError(t, err)
|
||||
tempStateFile, err := os.CreateTemp(t.TempDir(), "priv_validator_state_")
|
||||
require.NoError(t, err)
|
||||
|
||||
privVal, err := GenFilePV(tempKeyFile.Name(), tempStateFile.Name(), "")
|
||||
require.NoError(t, err)
|
||||
privVal, _, _ := newTestFilePV(t)
|
||||
|
||||
randbytes := tmrand.Bytes(tmhash.Size)
|
||||
randbytes2 := tmrand.Bytes(tmhash.Size)
|
||||
@@ -180,10 +162,10 @@ func TestSignVote(t *testing.T) {
|
||||
voteType := tmproto.PrevoteType
|
||||
|
||||
// sign a vote for first time
|
||||
vote := newVote(privVal.Key.Address, 0, height, round, voteType, block1)
|
||||
vote := newVote(privVal.Key.Address, 0, height, round, voteType, block1, nil)
|
||||
v := vote.ToProto()
|
||||
|
||||
err = privVal.SignVote(ctx, "mychainid", v)
|
||||
err := privVal.SignVote(ctx, "mychainid", v)
|
||||
assert.NoError(t, err, "expected no error signing vote")
|
||||
|
||||
// try to sign the same vote again; should be fine
|
||||
@@ -192,10 +174,10 @@ func TestSignVote(t *testing.T) {
|
||||
|
||||
// now try some bad votes
|
||||
cases := []*types.Vote{
|
||||
newVote(privVal.Key.Address, 0, height, round-1, voteType, block1), // round regression
|
||||
newVote(privVal.Key.Address, 0, height-1, round, voteType, block1), // height regression
|
||||
newVote(privVal.Key.Address, 0, height-2, round+4, voteType, block1), // height regression and different round
|
||||
newVote(privVal.Key.Address, 0, height, round, voteType, block2), // different block
|
||||
newVote(privVal.Key.Address, 0, height, round-1, voteType, block1, nil), // round regression
|
||||
newVote(privVal.Key.Address, 0, height-1, round, voteType, block1, nil), // height regression
|
||||
newVote(privVal.Key.Address, 0, height-2, round+4, voteType, block1, nil), // height regression and different round
|
||||
newVote(privVal.Key.Address, 0, height, round, voteType, block2, nil), // different block
|
||||
}
|
||||
|
||||
for _, c := range cases {
|
||||
@@ -215,13 +197,7 @@ func TestSignProposal(t *testing.T) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
tempKeyFile, err := os.CreateTemp(t.TempDir(), "priv_validator_key_")
|
||||
require.NoError(t, err)
|
||||
tempStateFile, err := os.CreateTemp(t.TempDir(), "priv_validator_state_")
|
||||
require.NoError(t, err)
|
||||
|
||||
privVal, err := GenFilePV(tempKeyFile.Name(), tempStateFile.Name(), "")
|
||||
require.NoError(t, err)
|
||||
privVal, _, _ := newTestFilePV(t)
|
||||
|
||||
randbytes := tmrand.Bytes(tmhash.Size)
|
||||
randbytes2 := tmrand.Bytes(tmhash.Size)
|
||||
@@ -237,7 +213,7 @@ func TestSignProposal(t *testing.T) {
|
||||
proposal := newProposal(height, round, block1, ts)
|
||||
pbp := proposal.ToProto()
|
||||
|
||||
err = privVal.SignProposal(ctx, "mychainid", pbp)
|
||||
err := privVal.SignProposal(ctx, "mychainid", pbp)
|
||||
assert.NoError(t, err, "expected no error signing proposal")
|
||||
|
||||
// try to sign the same proposal again; should be fine
|
||||
@@ -278,7 +254,7 @@ func TestDifferByTimestamp(t *testing.T) {
|
||||
{
|
||||
voteType := tmproto.PrevoteType
|
||||
blockID := types.BlockID{Hash: randbytes, PartSetHeader: types.PartSetHeader{}}
|
||||
vote := newVote(privVal.Key.Address, 0, height, round, voteType, blockID)
|
||||
vote := newVote(privVal.Key.Address, 0, height, round, voteType, blockID, nil)
|
||||
v := vote.ToProto()
|
||||
err := privVal.SignVote(ctx, "mychainid", v)
|
||||
require.NoError(t, err, "expected no error signing vote")
|
||||
@@ -300,8 +276,69 @@ func TestDifferByTimestamp(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestVoteExtensionsAreAlwaysSigned(t *testing.T) {
|
||||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
privVal, _, _ := newTestFilePV(t)
|
||||
pubKey, err := privVal.GetPubKey(ctx)
|
||||
assert.NoError(t, err)
|
||||
|
||||
block := types.BlockID{
|
||||
Hash: tmrand.Bytes(tmhash.Size),
|
||||
PartSetHeader: types.PartSetHeader{Total: 5, Hash: tmrand.Bytes(tmhash.Size)},
|
||||
}
|
||||
|
||||
height, round := int64(10), int32(1)
|
||||
voteType := tmproto.PrecommitType
|
||||
|
||||
// We initially sign this vote without an extension
|
||||
vote1 := newVote(privVal.Key.Address, 0, height, round, voteType, block, nil)
|
||||
vpb1 := vote1.ToProto()
|
||||
|
||||
err = privVal.SignVote(ctx, "mychainid", vpb1)
|
||||
assert.NoError(t, err, "expected no error signing vote")
|
||||
assert.NotNil(t, vpb1.ExtensionSignature)
|
||||
|
||||
vesb1 := types.VoteExtensionSignBytes("mychainid", vpb1)
|
||||
assert.True(t, pubKey.VerifySignature(vesb1, vpb1.ExtensionSignature))
|
||||
|
||||
// We duplicate this vote precisely, including its timestamp, but change
|
||||
// its extension
|
||||
vote2 := vote1.Copy()
|
||||
vote2.Extension = []byte("new extension")
|
||||
vpb2 := vote2.ToProto()
|
||||
|
||||
err = privVal.SignVote(ctx, "mychainid", vpb2)
|
||||
assert.NoError(t, err, "expected no error signing same vote with manipulated vote extension")
|
||||
|
||||
// We need to ensure that a valid new extension signature has been created
|
||||
// that validates against the vote extension sign bytes with the new
|
||||
// extension, and does not validate against the vote extension sign bytes
|
||||
// with the old extension.
|
||||
vesb2 := types.VoteExtensionSignBytes("mychainid", vpb2)
|
||||
assert.True(t, pubKey.VerifySignature(vesb2, vpb2.ExtensionSignature))
|
||||
assert.False(t, pubKey.VerifySignature(vesb1, vpb2.ExtensionSignature))
|
||||
|
||||
// We now manipulate the timestamp of the vote with the extension, as per
|
||||
// TestDifferByTimestamp
|
||||
expectedTimestamp := vpb2.Timestamp
|
||||
|
||||
vpb2.Timestamp = vpb2.Timestamp.Add(time.Millisecond)
|
||||
vpb2.Signature = nil
|
||||
vpb2.ExtensionSignature = nil
|
||||
|
||||
err = privVal.SignVote(ctx, "mychainid", vpb2)
|
||||
assert.NoError(t, err, "expected no error signing same vote with manipulated timestamp and vote extension")
|
||||
assert.Equal(t, expectedTimestamp, vpb2.Timestamp)
|
||||
|
||||
vesb3 := types.VoteExtensionSignBytes("mychainid", vpb2)
|
||||
assert.True(t, pubKey.VerifySignature(vesb3, vpb2.ExtensionSignature))
|
||||
assert.False(t, pubKey.VerifySignature(vesb1, vpb2.ExtensionSignature))
|
||||
}
|
||||
|
||||
func newVote(addr types.Address, idx int32, height int64, round int32,
|
||||
typ tmproto.SignedMsgType, blockID types.BlockID) *types.Vote {
|
||||
typ tmproto.SignedMsgType, blockID types.BlockID, extension []byte) *types.Vote {
|
||||
return &types.Vote{
|
||||
ValidatorAddress: addr,
|
||||
ValidatorIndex: idx,
|
||||
@@ -310,6 +347,7 @@ func newVote(addr types.Address, idx int32, height int64, round int32,
|
||||
Type: typ,
|
||||
Timestamp: tmtime.Now(),
|
||||
BlockID: blockID,
|
||||
Extension: extension,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -321,3 +359,15 @@ func newProposal(height int64, round int32, blockID types.BlockID, t time.Time)
|
||||
Timestamp: t,
|
||||
}
|
||||
}
|
||||
|
||||
func newTestFilePV(t *testing.T) (*FilePV, string, string) {
|
||||
tempKeyFile, err := os.CreateTemp(t.TempDir(), "priv_validator_key_")
|
||||
require.NoError(t, err)
|
||||
tempStateFile, err := os.CreateTemp(t.TempDir(), "priv_validator_state_")
|
||||
require.NoError(t, err)
|
||||
|
||||
privVal, err := GenFilePV(tempKeyFile.Name(), tempStateFile.Name(), "")
|
||||
require.NoError(t, err)
|
||||
|
||||
return privVal, tempKeyFile.Name(), tempStateFile.Name()
|
||||
}
|
||||
|
||||
+8
-17
@@ -22,23 +22,14 @@ var stamp = time.Date(2019, 10, 13, 16, 14, 44, 0, time.UTC)
|
||||
|
||||
func exampleVote() *types.Vote {
|
||||
return &types.Vote{
|
||||
Type: tmproto.SignedMsgType(1),
|
||||
Height: 3,
|
||||
Round: 2,
|
||||
Timestamp: stamp,
|
||||
BlockID: types.BlockID{
|
||||
Hash: tmhash.Sum([]byte("blockID_hash")),
|
||||
PartSetHeader: types.PartSetHeader{
|
||||
Total: 1000000,
|
||||
Hash: tmhash.Sum([]byte("blockID_part_set_header_hash")),
|
||||
},
|
||||
},
|
||||
Type: tmproto.PrecommitType,
|
||||
Height: 3,
|
||||
Round: 2,
|
||||
BlockID: types.BlockID{Hash: tmhash.Sum([]byte("blockID_hash")), PartSetHeader: types.PartSetHeader{Total: 1000000, Hash: tmhash.Sum([]byte("blockID_part_set_header_hash"))}},
|
||||
Timestamp: stamp,
|
||||
ValidatorAddress: crypto.AddressHash([]byte("validator_address")),
|
||||
ValidatorIndex: 56789,
|
||||
VoteExtension: types.VoteExtension{
|
||||
AppDataToSign: []byte("app_data_signed"),
|
||||
AppDataSelfAuthenticating: []byte("app_data_self_authenticating"),
|
||||
},
|
||||
Extension: []byte("extension"),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -87,8 +78,8 @@ func TestPrivvalVectors(t *testing.T) {
|
||||
{"pubKey request", &privproto.PubKeyRequest{}, "0a00"},
|
||||
{"pubKey response", &privproto.PubKeyResponse{PubKey: ppk, Error: nil}, "12240a220a20556a436f1218d30942efe798420f51dc9b6a311b929c578257457d05c5fcf230"},
|
||||
{"pubKey response with error", &privproto.PubKeyResponse{PubKey: cryptoproto.PublicKey{}, Error: remoteError}, "12140a0012100801120c697427732061206572726f72"},
|
||||
{"Vote Request", &privproto.SignVoteRequest{Vote: votepb}, "1aa8010aa501080110031802224a0a208b01023386c371778ecb6368573e539afc3cc860ec3a2f614e54fe5652f4fc80122608c0843d122072db3d959635dff1bb567bedaa70573392c5159666a3f8caf11e413aac52207a2a0608f49a8ded0532146af1f4111082efb388211bc72c55bcd61e9ac3d538d5bb034a2f0a0f6170705f646174615f7369676e6564121c6170705f646174615f73656c665f61757468656e7469636174696e67"},
|
||||
{"Vote Response", &privproto.SignedVoteResponse{Vote: *votepb, Error: nil}, "22a8010aa501080110031802224a0a208b01023386c371778ecb6368573e539afc3cc860ec3a2f614e54fe5652f4fc80122608c0843d122072db3d959635dff1bb567bedaa70573392c5159666a3f8caf11e413aac52207a2a0608f49a8ded0532146af1f4111082efb388211bc72c55bcd61e9ac3d538d5bb034a2f0a0f6170705f646174615f7369676e6564121c6170705f646174615f73656c665f61757468656e7469636174696e67"},
|
||||
{"Vote Request", &privproto.SignVoteRequest{Vote: votepb}, "1a81010a7f080210031802224a0a208b01023386c371778ecb6368573e539afc3cc860ec3a2f614e54fe5652f4fc80122608c0843d122072db3d959635dff1bb567bedaa70573392c5159666a3f8caf11e413aac52207a2a0608f49a8ded0532146af1f4111082efb388211bc72c55bcd61e9ac3d538d5bb034a09657874656e73696f6e"},
|
||||
{"Vote Response", &privproto.SignedVoteResponse{Vote: *votepb, Error: nil}, "2281010a7f080210031802224a0a208b01023386c371778ecb6368573e539afc3cc860ec3a2f614e54fe5652f4fc80122608c0843d122072db3d959635dff1bb567bedaa70573392c5159666a3f8caf11e413aac52207a2a0608f49a8ded0532146af1f4111082efb388211bc72c55bcd61e9ac3d538d5bb034a09657874656e73696f6e"},
|
||||
{"Vote Response with error", &privproto.SignedVoteResponse{Vote: tmproto.Vote{}, Error: remoteError}, "22250a11220212002a0b088092b8c398feffffff0112100801120c697427732061206572726f72"},
|
||||
{"Proposal Request", &privproto.SignProposalRequest{Proposal: proposalpb}, "2a700a6e08011003180220022a4a0a208b01023386c371778ecb6368573e539afc3cc860ec3a2f614e54fe5652f4fc80122608c0843d122072db3d959635dff1bb567bedaa70573392c5159666a3f8caf11e413aac52207a320608f49a8ded053a10697427732061207369676e6174757265"},
|
||||
{"Proposal Response", &privproto.SignedProposalResponse{Proposal: *proposalpb, Error: nil}, "32700a6e08011003180220022a4a0a208b01023386c371778ecb6368573e539afc3cc860ec3a2f614e54fe5652f4fc80122608c0843d122072db3d959635dff1bb567bedaa70573392c5159666a3f8caf11e413aac52207a320608f49a8ded053a10697427732061207369676e6174757265"},
|
||||
|
||||
@@ -384,7 +384,10 @@ message CommitInfo {
|
||||
}
|
||||
|
||||
message ExtendedCommitInfo {
|
||||
int32 round = 1;
|
||||
// The round at which the block proposer decided in the previous height.
|
||||
int32 round = 1;
|
||||
// List of validators' addresses in the last validator set with their voting
|
||||
// information, including vote extensions.
|
||||
repeated ExtendedVoteInfo votes = 2 [(gogoproto.nullable) = false];
|
||||
}
|
||||
|
||||
@@ -465,19 +468,12 @@ message VoteInfo {
|
||||
|
||||
// ExtendedVoteInfo
|
||||
message ExtendedVoteInfo {
|
||||
Validator validator = 1 [(gogoproto.nullable) = false];
|
||||
bool signed_last_block = 2;
|
||||
bytes vote_extension = 3;
|
||||
}
|
||||
|
||||
// CanonicalVoteExtension
|
||||
// TODO: move this to core Tendermint data structures
|
||||
message CanonicalVoteExtension {
|
||||
bytes extension = 1;
|
||||
int64 height = 2;
|
||||
int32 round = 3;
|
||||
string chain_id = 4;
|
||||
bytes address = 5;
|
||||
// The validator that sent the vote.
|
||||
Validator validator = 1 [(gogoproto.nullable) = false];
|
||||
// Indicates whether the validator signed the last block, allowing for rewards based on validator availability.
|
||||
bool signed_last_block = 2;
|
||||
// Non-deterministic extension provided by the sending validator's application.
|
||||
bytes vote_extension = 3;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -153,12 +153,16 @@ message RequestProcessProposal {
|
||||
|
||||
// Extends a vote with application-side injection
|
||||
message RequestExtendVote {
|
||||
types.Vote vote = 1;
|
||||
bytes hash = 1;
|
||||
int64 height = 2;
|
||||
}
|
||||
|
||||
// Verify the vote extension
|
||||
message RequestVerifyVoteExtension {
|
||||
types.Vote vote = 1;
|
||||
bytes hash = 1;
|
||||
bytes validator_address = 2;
|
||||
int64 height = 3;
|
||||
bytes vote_extension = 4;
|
||||
}
|
||||
|
||||
message RequestFinalizeBlock {
|
||||
@@ -348,7 +352,7 @@ message ResponseProcessProposal {
|
||||
}
|
||||
|
||||
message ResponseExtendVote {
|
||||
tendermint.types.VoteExtension vote_extension = 1;
|
||||
bytes vote_extension = 1;
|
||||
}
|
||||
|
||||
message ResponseVerifyVoteExtension {
|
||||
@@ -379,8 +383,14 @@ message CommitInfo {
|
||||
repeated VoteInfo votes = 2 [(gogoproto.nullable) = false];
|
||||
}
|
||||
|
||||
// ExtendedCommitInfo is similar to CommitInfo except that it is only used in
|
||||
// the PrepareProposal request such that Tendermint can provide vote extensions
|
||||
// to the application.
|
||||
message ExtendedCommitInfo {
|
||||
int32 round = 1;
|
||||
// The round at which the block proposer decided in the previous height.
|
||||
int32 round = 1;
|
||||
// List of validators' addresses in the last validator set with their voting
|
||||
// information, including vote extensions.
|
||||
repeated ExtendedVoteInfo votes = 2 [(gogoproto.nullable) = false];
|
||||
}
|
||||
|
||||
@@ -461,10 +471,14 @@ message VoteInfo {
|
||||
reserved 4; // Placeholder for app_signed_extension in v0.37
|
||||
}
|
||||
|
||||
// ExtendedVoteInfo
|
||||
message ExtendedVoteInfo {
|
||||
Validator validator = 1 [(gogoproto.nullable) = false];
|
||||
bool signed_last_block = 2;
|
||||
bytes vote_extension = 3;
|
||||
// The validator that sent the vote.
|
||||
Validator validator = 1 [(gogoproto.nullable) = false];
|
||||
// Indicates whether the validator signed the last block, allowing for rewards based on validator availability.
|
||||
bool signed_last_block = 2;
|
||||
// Non-deterministic extension provided by the sending validator's application.
|
||||
bytes vote_extension = 3;
|
||||
}
|
||||
|
||||
enum MisbehaviorType {
|
||||
|
||||
@@ -225,13 +225,12 @@ func (m *CanonicalProposal) GetChainID() string {
|
||||
}
|
||||
|
||||
type CanonicalVote struct {
|
||||
Type SignedMsgType `protobuf:"varint,1,opt,name=type,proto3,enum=tendermint.types.SignedMsgType" json:"type,omitempty"`
|
||||
Height int64 `protobuf:"fixed64,2,opt,name=height,proto3" json:"height,omitempty"`
|
||||
Round int64 `protobuf:"fixed64,3,opt,name=round,proto3" json:"round,omitempty"`
|
||||
BlockID *CanonicalBlockID `protobuf:"bytes,4,opt,name=block_id,json=blockId,proto3" json:"block_id,omitempty"`
|
||||
Timestamp time.Time `protobuf:"bytes,5,opt,name=timestamp,proto3,stdtime" json:"timestamp"`
|
||||
ChainID string `protobuf:"bytes,6,opt,name=chain_id,json=chainId,proto3" json:"chain_id,omitempty"`
|
||||
VoteExtension *VoteExtensionToSign `protobuf:"bytes,7,opt,name=vote_extension,json=voteExtension,proto3" json:"vote_extension,omitempty"`
|
||||
Type SignedMsgType `protobuf:"varint,1,opt,name=type,proto3,enum=tendermint.types.SignedMsgType" json:"type,omitempty"`
|
||||
Height int64 `protobuf:"fixed64,2,opt,name=height,proto3" json:"height,omitempty"`
|
||||
Round int64 `protobuf:"fixed64,3,opt,name=round,proto3" json:"round,omitempty"`
|
||||
BlockID *CanonicalBlockID `protobuf:"bytes,4,opt,name=block_id,json=blockId,proto3" json:"block_id,omitempty"`
|
||||
Timestamp time.Time `protobuf:"bytes,5,opt,name=timestamp,proto3,stdtime" json:"timestamp"`
|
||||
ChainID string `protobuf:"bytes,6,opt,name=chain_id,json=chainId,proto3" json:"chain_id,omitempty"`
|
||||
}
|
||||
|
||||
func (m *CanonicalVote) Reset() { *m = CanonicalVote{} }
|
||||
@@ -309,57 +308,121 @@ func (m *CanonicalVote) GetChainID() string {
|
||||
return ""
|
||||
}
|
||||
|
||||
func (m *CanonicalVote) GetVoteExtension() *VoteExtensionToSign {
|
||||
// CanonicalVoteExtension provides us a way to serialize a vote extension from
|
||||
// a particular validator such that we can sign over those serialized bytes.
|
||||
type CanonicalVoteExtension struct {
|
||||
Extension []byte `protobuf:"bytes,1,opt,name=extension,proto3" json:"extension,omitempty"`
|
||||
Height int64 `protobuf:"fixed64,2,opt,name=height,proto3" json:"height,omitempty"`
|
||||
Round int64 `protobuf:"fixed64,3,opt,name=round,proto3" json:"round,omitempty"`
|
||||
ChainId string `protobuf:"bytes,4,opt,name=chain_id,json=chainId,proto3" json:"chain_id,omitempty"`
|
||||
}
|
||||
|
||||
func (m *CanonicalVoteExtension) Reset() { *m = CanonicalVoteExtension{} }
|
||||
func (m *CanonicalVoteExtension) String() string { return proto.CompactTextString(m) }
|
||||
func (*CanonicalVoteExtension) ProtoMessage() {}
|
||||
func (*CanonicalVoteExtension) Descriptor() ([]byte, []int) {
|
||||
return fileDescriptor_8d1a1a84ff7267ed, []int{4}
|
||||
}
|
||||
func (m *CanonicalVoteExtension) XXX_Unmarshal(b []byte) error {
|
||||
return m.Unmarshal(b)
|
||||
}
|
||||
func (m *CanonicalVoteExtension) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
|
||||
if deterministic {
|
||||
return xxx_messageInfo_CanonicalVoteExtension.Marshal(b, m, deterministic)
|
||||
} else {
|
||||
b = b[:cap(b)]
|
||||
n, err := m.MarshalToSizedBuffer(b)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return b[:n], nil
|
||||
}
|
||||
}
|
||||
func (m *CanonicalVoteExtension) XXX_Merge(src proto.Message) {
|
||||
xxx_messageInfo_CanonicalVoteExtension.Merge(m, src)
|
||||
}
|
||||
func (m *CanonicalVoteExtension) XXX_Size() int {
|
||||
return m.Size()
|
||||
}
|
||||
func (m *CanonicalVoteExtension) XXX_DiscardUnknown() {
|
||||
xxx_messageInfo_CanonicalVoteExtension.DiscardUnknown(m)
|
||||
}
|
||||
|
||||
var xxx_messageInfo_CanonicalVoteExtension proto.InternalMessageInfo
|
||||
|
||||
func (m *CanonicalVoteExtension) GetExtension() []byte {
|
||||
if m != nil {
|
||||
return m.VoteExtension
|
||||
return m.Extension
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (m *CanonicalVoteExtension) GetHeight() int64 {
|
||||
if m != nil {
|
||||
return m.Height
|
||||
}
|
||||
return 0
|
||||
}
|
||||
|
||||
func (m *CanonicalVoteExtension) GetRound() int64 {
|
||||
if m != nil {
|
||||
return m.Round
|
||||
}
|
||||
return 0
|
||||
}
|
||||
|
||||
func (m *CanonicalVoteExtension) GetChainId() string {
|
||||
if m != nil {
|
||||
return m.ChainId
|
||||
}
|
||||
return ""
|
||||
}
|
||||
|
||||
func init() {
|
||||
proto.RegisterType((*CanonicalBlockID)(nil), "tendermint.types.CanonicalBlockID")
|
||||
proto.RegisterType((*CanonicalPartSetHeader)(nil), "tendermint.types.CanonicalPartSetHeader")
|
||||
proto.RegisterType((*CanonicalProposal)(nil), "tendermint.types.CanonicalProposal")
|
||||
proto.RegisterType((*CanonicalVote)(nil), "tendermint.types.CanonicalVote")
|
||||
proto.RegisterType((*CanonicalVoteExtension)(nil), "tendermint.types.CanonicalVoteExtension")
|
||||
}
|
||||
|
||||
func init() { proto.RegisterFile("tendermint/types/canonical.proto", fileDescriptor_8d1a1a84ff7267ed) }
|
||||
|
||||
var fileDescriptor_8d1a1a84ff7267ed = []byte{
|
||||
// 522 bytes of a gzipped FileDescriptorProto
|
||||
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x94, 0x3f, 0x6f, 0xd3, 0x40,
|
||||
0x18, 0xc6, 0xe3, 0xd4, 0x49, 0x9c, 0x4b, 0x53, 0xc2, 0xa9, 0xaa, 0xac, 0x08, 0xd9, 0x96, 0x25,
|
||||
0x90, 0x59, 0x6c, 0x29, 0x1d, 0xd8, 0x5d, 0x90, 0x08, 0x2a, 0xa2, 0x5c, 0xa3, 0x0e, 0x2c, 0xd6,
|
||||
0xc5, 0x3e, 0x6c, 0x0b, 0xc7, 0x67, 0xd9, 0x97, 0x8a, 0x2e, 0x7c, 0x86, 0x7e, 0xac, 0x8e, 0x1d,
|
||||
0x61, 0x09, 0xc8, 0xf9, 0x12, 0x8c, 0xe8, 0xce, 0x49, 0x1c, 0x25, 0xc0, 0x02, 0xea, 0x12, 0xbd,
|
||||
0x7f, 0x1e, 0xbf, 0xef, 0xa3, 0xdf, 0xab, 0x1c, 0x30, 0x18, 0x49, 0x03, 0x92, 0xcf, 0xe2, 0x94,
|
||||
0x39, 0xec, 0x26, 0x23, 0x85, 0xe3, 0xe3, 0x94, 0xa6, 0xb1, 0x8f, 0x13, 0x3b, 0xcb, 0x29, 0xa3,
|
||||
0x70, 0x50, 0x2b, 0x6c, 0xa1, 0x18, 0x1e, 0x87, 0x34, 0xa4, 0xa2, 0xe9, 0xf0, 0xa8, 0xd2, 0x0d,
|
||||
0x9f, 0xec, 0x4d, 0x12, 0xbf, 0xab, 0xae, 0x1e, 0x52, 0x1a, 0x26, 0xc4, 0x11, 0xd9, 0x74, 0xfe,
|
||||
0xd1, 0x61, 0xf1, 0x8c, 0x14, 0x0c, 0xcf, 0xb2, 0x4a, 0x60, 0x7e, 0x01, 0x83, 0xb3, 0xf5, 0x66,
|
||||
0x37, 0xa1, 0xfe, 0xa7, 0xf1, 0x4b, 0x08, 0x81, 0x1c, 0xe1, 0x22, 0x52, 0x25, 0x43, 0xb2, 0x0e,
|
||||
0x91, 0x88, 0xe1, 0x15, 0x78, 0x94, 0xe1, 0x9c, 0x79, 0x05, 0x61, 0x5e, 0x44, 0x70, 0x40, 0x72,
|
||||
0xb5, 0x69, 0x48, 0x56, 0x6f, 0x64, 0xd9, 0xbb, 0x46, 0xed, 0xcd, 0xc0, 0x0b, 0x9c, 0xb3, 0x4b,
|
||||
0xc2, 0x5e, 0x0b, 0xbd, 0x2b, 0xdf, 0x2d, 0xf4, 0x06, 0xea, 0x67, 0xdb, 0x45, 0xd3, 0x05, 0x27,
|
||||
0xbf, 0x97, 0xc3, 0x63, 0xd0, 0x62, 0x94, 0xe1, 0x44, 0xd8, 0xe8, 0xa3, 0x2a, 0xd9, 0x78, 0x6b,
|
||||
0xd6, 0xde, 0xcc, 0x6f, 0x4d, 0xf0, 0xb8, 0x1e, 0x92, 0xd3, 0x8c, 0x16, 0x38, 0x81, 0xa7, 0x40,
|
||||
0xe6, 0x76, 0xc4, 0xe7, 0x47, 0x23, 0x7d, 0xdf, 0xe6, 0x65, 0x1c, 0xa6, 0x24, 0x78, 0x5b, 0x84,
|
||||
0x93, 0x9b, 0x8c, 0x20, 0x21, 0x86, 0x27, 0xa0, 0x1d, 0x91, 0x38, 0x8c, 0x98, 0x58, 0x30, 0x40,
|
||||
0xab, 0x8c, 0x9b, 0xc9, 0xe9, 0x3c, 0x0d, 0xd4, 0x03, 0x51, 0xae, 0x12, 0xf8, 0x1c, 0x74, 0x33,
|
||||
0x9a, 0x78, 0x55, 0x47, 0x36, 0x24, 0xeb, 0xc0, 0x3d, 0x2c, 0x17, 0xba, 0x72, 0xf1, 0xee, 0x1c,
|
||||
0xf1, 0x1a, 0x52, 0x32, 0x9a, 0x88, 0x08, 0xbe, 0x01, 0xca, 0x94, 0xe3, 0xf5, 0xe2, 0x40, 0x6d,
|
||||
0x09, 0x70, 0xe6, 0x5f, 0xc0, 0xad, 0x2e, 0xe1, 0xf6, 0xca, 0x85, 0xde, 0x59, 0x25, 0xa8, 0x23,
|
||||
0x06, 0x8c, 0x03, 0xe8, 0x82, 0xee, 0xe6, 0x8c, 0x6a, 0x5b, 0x0c, 0x1b, 0xda, 0xd5, 0xa1, 0xed,
|
||||
0xf5, 0xa1, 0xed, 0xc9, 0x5a, 0xe1, 0x2a, 0x9c, 0xfb, 0xed, 0x77, 0x5d, 0x42, 0xf5, 0x67, 0xf0,
|
||||
0x19, 0x50, 0xfc, 0x08, 0xc7, 0x29, 0xf7, 0xd3, 0x31, 0x24, 0xab, 0x5b, 0xed, 0x3a, 0xe3, 0x35,
|
||||
0xbe, 0x4b, 0x34, 0xc7, 0x81, 0xf9, 0xb3, 0x09, 0xfa, 0x1b, 0x5b, 0x57, 0x94, 0x91, 0x87, 0xe0,
|
||||
0xba, 0x0d, 0x4b, 0xfe, 0x9f, 0xb0, 0x5a, 0xff, 0x0e, 0xab, 0xfd, 0x67, 0x58, 0xf0, 0x1c, 0x1c,
|
||||
0x5d, 0x53, 0x46, 0x3c, 0xf2, 0x99, 0x91, 0xb4, 0x88, 0x69, 0x2a, 0xd0, 0xf6, 0x46, 0x4f, 0xf7,
|
||||
0xdd, 0x73, 0x94, 0xaf, 0xd6, 0xb2, 0x09, 0xe5, 0xcc, 0x50, 0xff, 0x7a, 0xbb, 0xe8, 0xbe, 0xbf,
|
||||
0x2b, 0x35, 0xe9, 0xbe, 0xd4, 0xa4, 0x1f, 0xa5, 0x26, 0xdd, 0x2e, 0xb5, 0xc6, 0xfd, 0x52, 0x6b,
|
||||
0x7c, 0x5d, 0x6a, 0x8d, 0x0f, 0x2f, 0xc2, 0x98, 0x45, 0xf3, 0xa9, 0xed, 0xd3, 0x99, 0xb3, 0xfd,
|
||||
0xf7, 0xaf, 0xc3, 0xea, 0x99, 0xd8, 0x7d, 0x1a, 0xa6, 0x6d, 0x51, 0x3f, 0xfd, 0x15, 0x00, 0x00,
|
||||
0xff, 0xff, 0x4e, 0x61, 0xcb, 0xc4, 0x7f, 0x04, 0x00, 0x00,
|
||||
// 523 bytes of a gzipped FileDescriptorProto
|
||||
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x54, 0xc1, 0x6e, 0xd3, 0x40,
|
||||
0x10, 0x8d, 0x53, 0x27, 0xb1, 0xb7, 0x0d, 0x84, 0x55, 0x55, 0x99, 0xa8, 0xb2, 0x2d, 0x1f, 0x90,
|
||||
0xb9, 0xd8, 0x52, 0x7b, 0xe0, 0xee, 0x82, 0x44, 0x10, 0x88, 0xe2, 0x56, 0x3d, 0x70, 0x89, 0x36,
|
||||
0xf6, 0x62, 0x5b, 0x38, 0xde, 0x95, 0xbd, 0x91, 0xe8, 0x05, 0x7e, 0xa1, 0xdf, 0xc1, 0x97, 0xf4,
|
||||
0xd8, 0x23, 0x5c, 0x02, 0x72, 0x7e, 0x04, 0xed, 0xda, 0xb1, 0xad, 0x16, 0x55, 0x42, 0x20, 0x2e,
|
||||
0xd1, 0xcc, 0x9b, 0xb7, 0x33, 0x4f, 0x6f, 0xe2, 0x01, 0x26, 0xc3, 0x59, 0x88, 0xf3, 0x65, 0x92,
|
||||
0x31, 0x97, 0x5d, 0x52, 0x5c, 0xb8, 0x01, 0xca, 0x48, 0x96, 0x04, 0x28, 0x75, 0x68, 0x4e, 0x18,
|
||||
0x81, 0x93, 0x96, 0xe1, 0x08, 0xc6, 0x74, 0x3f, 0x22, 0x11, 0x11, 0x45, 0x97, 0x47, 0x15, 0x6f,
|
||||
0x7a, 0x78, 0xa7, 0x93, 0xf8, 0xad, 0xab, 0x46, 0x44, 0x48, 0x94, 0x62, 0x57, 0x64, 0x8b, 0xd5,
|
||||
0x07, 0x97, 0x25, 0x4b, 0x5c, 0x30, 0xb4, 0xa4, 0x15, 0xc1, 0xfa, 0x0c, 0x26, 0x27, 0xdb, 0xc9,
|
||||
0x5e, 0x4a, 0x82, 0x8f, 0xb3, 0xe7, 0x10, 0x02, 0x39, 0x46, 0x45, 0xac, 0x49, 0xa6, 0x64, 0xef,
|
||||
0xf9, 0x22, 0x86, 0x17, 0xe0, 0x21, 0x45, 0x39, 0x9b, 0x17, 0x98, 0xcd, 0x63, 0x8c, 0x42, 0x9c,
|
||||
0x6b, 0x7d, 0x53, 0xb2, 0x77, 0x8f, 0x6c, 0xe7, 0xb6, 0x50, 0xa7, 0x69, 0x78, 0x8a, 0x72, 0x76,
|
||||
0x86, 0xd9, 0x4b, 0xc1, 0xf7, 0xe4, 0xeb, 0xb5, 0xd1, 0xf3, 0xc7, 0xb4, 0x0b, 0x5a, 0x1e, 0x38,
|
||||
0xf8, 0x3d, 0x1d, 0xee, 0x83, 0x01, 0x23, 0x0c, 0xa5, 0x42, 0xc6, 0xd8, 0xaf, 0x92, 0x46, 0x5b,
|
||||
0xbf, 0xd5, 0x66, 0x7d, 0xef, 0x83, 0x47, 0x6d, 0x93, 0x9c, 0x50, 0x52, 0xa0, 0x14, 0x1e, 0x03,
|
||||
0x99, 0xcb, 0x11, 0xcf, 0x1f, 0x1c, 0x19, 0x77, 0x65, 0x9e, 0x25, 0x51, 0x86, 0xc3, 0x37, 0x45,
|
||||
0x74, 0x7e, 0x49, 0xb1, 0x2f, 0xc8, 0xf0, 0x00, 0x0c, 0x63, 0x9c, 0x44, 0x31, 0x13, 0x03, 0x26,
|
||||
0x7e, 0x9d, 0x71, 0x31, 0x39, 0x59, 0x65, 0xa1, 0xb6, 0x23, 0xe0, 0x2a, 0x81, 0x4f, 0x81, 0x4a,
|
||||
0x49, 0x3a, 0xaf, 0x2a, 0xb2, 0x29, 0xd9, 0x3b, 0xde, 0x5e, 0xb9, 0x36, 0x94, 0xd3, 0xb7, 0xaf,
|
||||
0x7d, 0x8e, 0xf9, 0x0a, 0x25, 0xa9, 0x88, 0xe0, 0x2b, 0xa0, 0x2c, 0xb8, 0xbd, 0xf3, 0x24, 0xd4,
|
||||
0x06, 0xc2, 0x38, 0xeb, 0x1e, 0xe3, 0xea, 0x4d, 0x78, 0xbb, 0xe5, 0xda, 0x18, 0xd5, 0x89, 0x3f,
|
||||
0x12, 0x0d, 0x66, 0x21, 0xf4, 0x80, 0xda, 0xac, 0x51, 0x1b, 0x8a, 0x66, 0x53, 0xa7, 0x5a, 0xb4,
|
||||
0xb3, 0x5d, 0xb4, 0x73, 0xbe, 0x65, 0x78, 0x0a, 0xf7, 0xfd, 0xea, 0x87, 0x21, 0xf9, 0xed, 0x33,
|
||||
0xf8, 0x04, 0x28, 0x41, 0x8c, 0x92, 0x8c, 0xeb, 0x19, 0x99, 0x92, 0xad, 0x56, 0xb3, 0x4e, 0x38,
|
||||
0xc6, 0x67, 0x89, 0xe2, 0x2c, 0xb4, 0xbe, 0xf6, 0xc1, 0xb8, 0x91, 0x75, 0x41, 0x18, 0xfe, 0x1f,
|
||||
0xbe, 0x76, 0xcd, 0x92, 0xff, 0xa5, 0x59, 0x83, 0xbf, 0x37, 0x6b, 0x78, 0x8f, 0x59, 0x5f, 0x3a,
|
||||
0x7f, 0x66, 0xee, 0xd5, 0x8b, 0x4f, 0x0c, 0x67, 0x45, 0x42, 0x32, 0x78, 0x08, 0x54, 0xbc, 0x4d,
|
||||
0xea, 0xef, 0xaa, 0x05, 0xfe, 0xd0, 0x9d, 0xc7, 0x1d, 0x35, 0xdc, 0x1d, 0xb5, 0x11, 0xe0, 0xbd,
|
||||
0xbb, 0x2e, 0x75, 0xe9, 0xa6, 0xd4, 0xa5, 0x9f, 0xa5, 0x2e, 0x5d, 0x6d, 0xf4, 0xde, 0xcd, 0x46,
|
||||
0xef, 0x7d, 0xdb, 0xe8, 0xbd, 0xf7, 0xcf, 0xa2, 0x84, 0xc5, 0xab, 0x85, 0x13, 0x90, 0xa5, 0xdb,
|
||||
0xbd, 0x18, 0x6d, 0x58, 0x5d, 0x96, 0xdb, 0xd7, 0x64, 0x31, 0x14, 0xf8, 0xf1, 0xaf, 0x00, 0x00,
|
||||
0x00, 0xff, 0xff, 0x2b, 0x89, 0x89, 0x5b, 0xb2, 0x04, 0x00, 0x00,
|
||||
}
|
||||
|
||||
func (m *CanonicalBlockID) Marshal() (dAtA []byte, err error) {
|
||||
@@ -529,18 +592,6 @@ func (m *CanonicalVote) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
_ = i
|
||||
var l int
|
||||
_ = l
|
||||
if m.VoteExtension != nil {
|
||||
{
|
||||
size, err := m.VoteExtension.MarshalToSizedBuffer(dAtA[:i])
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
i -= size
|
||||
i = encodeVarintCanonical(dAtA, i, uint64(size))
|
||||
}
|
||||
i--
|
||||
dAtA[i] = 0x3a
|
||||
}
|
||||
if len(m.ChainID) > 0 {
|
||||
i -= len(m.ChainID)
|
||||
copy(dAtA[i:], m.ChainID)
|
||||
@@ -548,12 +599,12 @@ func (m *CanonicalVote) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
i--
|
||||
dAtA[i] = 0x32
|
||||
}
|
||||
n5, err5 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Timestamp, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Timestamp):])
|
||||
if err5 != nil {
|
||||
return 0, err5
|
||||
n4, err4 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Timestamp, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Timestamp):])
|
||||
if err4 != nil {
|
||||
return 0, err4
|
||||
}
|
||||
i -= n5
|
||||
i = encodeVarintCanonical(dAtA, i, uint64(n5))
|
||||
i -= n4
|
||||
i = encodeVarintCanonical(dAtA, i, uint64(n4))
|
||||
i--
|
||||
dAtA[i] = 0x2a
|
||||
if m.BlockID != nil {
|
||||
@@ -588,6 +639,55 @@ func (m *CanonicalVote) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
return len(dAtA) - i, nil
|
||||
}
|
||||
|
||||
func (m *CanonicalVoteExtension) Marshal() (dAtA []byte, err error) {
|
||||
size := m.Size()
|
||||
dAtA = make([]byte, size)
|
||||
n, err := m.MarshalToSizedBuffer(dAtA[:size])
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return dAtA[:n], nil
|
||||
}
|
||||
|
||||
func (m *CanonicalVoteExtension) MarshalTo(dAtA []byte) (int, error) {
|
||||
size := m.Size()
|
||||
return m.MarshalToSizedBuffer(dAtA[:size])
|
||||
}
|
||||
|
||||
func (m *CanonicalVoteExtension) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
i := len(dAtA)
|
||||
_ = i
|
||||
var l int
|
||||
_ = l
|
||||
if len(m.ChainId) > 0 {
|
||||
i -= len(m.ChainId)
|
||||
copy(dAtA[i:], m.ChainId)
|
||||
i = encodeVarintCanonical(dAtA, i, uint64(len(m.ChainId)))
|
||||
i--
|
||||
dAtA[i] = 0x22
|
||||
}
|
||||
if m.Round != 0 {
|
||||
i -= 8
|
||||
encoding_binary.LittleEndian.PutUint64(dAtA[i:], uint64(m.Round))
|
||||
i--
|
||||
dAtA[i] = 0x19
|
||||
}
|
||||
if m.Height != 0 {
|
||||
i -= 8
|
||||
encoding_binary.LittleEndian.PutUint64(dAtA[i:], uint64(m.Height))
|
||||
i--
|
||||
dAtA[i] = 0x11
|
||||
}
|
||||
if len(m.Extension) > 0 {
|
||||
i -= len(m.Extension)
|
||||
copy(dAtA[i:], m.Extension)
|
||||
i = encodeVarintCanonical(dAtA, i, uint64(len(m.Extension)))
|
||||
i--
|
||||
dAtA[i] = 0xa
|
||||
}
|
||||
return len(dAtA) - i, nil
|
||||
}
|
||||
|
||||
func encodeVarintCanonical(dAtA []byte, offset int, v uint64) int {
|
||||
offset -= sovCanonical(v)
|
||||
base := offset
|
||||
@@ -686,8 +786,27 @@ func (m *CanonicalVote) Size() (n int) {
|
||||
if l > 0 {
|
||||
n += 1 + l + sovCanonical(uint64(l))
|
||||
}
|
||||
if m.VoteExtension != nil {
|
||||
l = m.VoteExtension.Size()
|
||||
return n
|
||||
}
|
||||
|
||||
func (m *CanonicalVoteExtension) Size() (n int) {
|
||||
if m == nil {
|
||||
return 0
|
||||
}
|
||||
var l int
|
||||
_ = l
|
||||
l = len(m.Extension)
|
||||
if l > 0 {
|
||||
n += 1 + l + sovCanonical(uint64(l))
|
||||
}
|
||||
if m.Height != 0 {
|
||||
n += 9
|
||||
}
|
||||
if m.Round != 0 {
|
||||
n += 9
|
||||
}
|
||||
l = len(m.ChainId)
|
||||
if l > 0 {
|
||||
n += 1 + l + sovCanonical(uint64(l))
|
||||
}
|
||||
return n
|
||||
@@ -1297,11 +1416,61 @@ func (m *CanonicalVote) Unmarshal(dAtA []byte) error {
|
||||
}
|
||||
m.ChainID = string(dAtA[iNdEx:postIndex])
|
||||
iNdEx = postIndex
|
||||
case 7:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field VoteExtension", wireType)
|
||||
default:
|
||||
iNdEx = preIndex
|
||||
skippy, err := skipCanonical(dAtA[iNdEx:])
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
var msglen int
|
||||
if (skippy < 0) || (iNdEx+skippy) < 0 {
|
||||
return ErrInvalidLengthCanonical
|
||||
}
|
||||
if (iNdEx + skippy) > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
iNdEx += skippy
|
||||
}
|
||||
}
|
||||
|
||||
if iNdEx > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
return nil
|
||||
}
|
||||
func (m *CanonicalVoteExtension) Unmarshal(dAtA []byte) error {
|
||||
l := len(dAtA)
|
||||
iNdEx := 0
|
||||
for iNdEx < l {
|
||||
preIndex := iNdEx
|
||||
var wire uint64
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowCanonical
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
wire |= uint64(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
fieldNum := int32(wire >> 3)
|
||||
wireType := int(wire & 0x7)
|
||||
if wireType == 4 {
|
||||
return fmt.Errorf("proto: CanonicalVoteExtension: wiretype end group for non-group")
|
||||
}
|
||||
if fieldNum <= 0 {
|
||||
return fmt.Errorf("proto: CanonicalVoteExtension: illegal tag %d (wire type %d)", fieldNum, wire)
|
||||
}
|
||||
switch fieldNum {
|
||||
case 1:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field Extension", wireType)
|
||||
}
|
||||
var byteLen int
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowCanonical
|
||||
@@ -1311,27 +1480,77 @@ func (m *CanonicalVote) Unmarshal(dAtA []byte) error {
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
msglen |= int(b&0x7F) << shift
|
||||
byteLen |= int(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
if msglen < 0 {
|
||||
if byteLen < 0 {
|
||||
return ErrInvalidLengthCanonical
|
||||
}
|
||||
postIndex := iNdEx + msglen
|
||||
postIndex := iNdEx + byteLen
|
||||
if postIndex < 0 {
|
||||
return ErrInvalidLengthCanonical
|
||||
}
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
if m.VoteExtension == nil {
|
||||
m.VoteExtension = &VoteExtensionToSign{}
|
||||
m.Extension = append(m.Extension[:0], dAtA[iNdEx:postIndex]...)
|
||||
if m.Extension == nil {
|
||||
m.Extension = []byte{}
|
||||
}
|
||||
if err := m.VoteExtension.Unmarshal(dAtA[iNdEx:postIndex]); err != nil {
|
||||
return err
|
||||
iNdEx = postIndex
|
||||
case 2:
|
||||
if wireType != 1 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field Height", wireType)
|
||||
}
|
||||
m.Height = 0
|
||||
if (iNdEx + 8) > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
m.Height = int64(encoding_binary.LittleEndian.Uint64(dAtA[iNdEx:]))
|
||||
iNdEx += 8
|
||||
case 3:
|
||||
if wireType != 1 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field Round", wireType)
|
||||
}
|
||||
m.Round = 0
|
||||
if (iNdEx + 8) > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
m.Round = int64(encoding_binary.LittleEndian.Uint64(dAtA[iNdEx:]))
|
||||
iNdEx += 8
|
||||
case 4:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field ChainId", wireType)
|
||||
}
|
||||
var stringLen uint64
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowCanonical
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
stringLen |= uint64(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
intStringLen := int(stringLen)
|
||||
if intStringLen < 0 {
|
||||
return ErrInvalidLengthCanonical
|
||||
}
|
||||
postIndex := iNdEx + intStringLen
|
||||
if postIndex < 0 {
|
||||
return ErrInvalidLengthCanonical
|
||||
}
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
m.ChainId = string(dAtA[iNdEx:postIndex])
|
||||
iNdEx = postIndex
|
||||
default:
|
||||
iNdEx = preIndex
|
||||
|
||||
@@ -35,3 +35,12 @@ message CanonicalVote {
|
||||
google.protobuf.Timestamp timestamp = 5 [(gogoproto.nullable) = false, (gogoproto.stdtime) = true];
|
||||
string chain_id = 6 [(gogoproto.customname) = "ChainID"];
|
||||
}
|
||||
|
||||
// CanonicalVoteExtension provides us a way to serialize a vote extension from
|
||||
// a particular validator such that we can sign over those serialized bytes.
|
||||
message CanonicalVoteExtension {
|
||||
bytes extension = 1;
|
||||
sfixed64 height = 2;
|
||||
sfixed64 round = 3;
|
||||
string chain_id = 4;
|
||||
}
|
||||
|
||||
+153
-566
@@ -466,15 +466,22 @@ func (m *Data) GetTxs() [][]byte {
|
||||
// Vote represents a prevote, precommit, or commit vote from validators for
|
||||
// consensus.
|
||||
type Vote struct {
|
||||
Type SignedMsgType `protobuf:"varint,1,opt,name=type,proto3,enum=tendermint.types.SignedMsgType" json:"type,omitempty"`
|
||||
Height int64 `protobuf:"varint,2,opt,name=height,proto3" json:"height,omitempty"`
|
||||
Round int32 `protobuf:"varint,3,opt,name=round,proto3" json:"round,omitempty"`
|
||||
BlockID BlockID `protobuf:"bytes,4,opt,name=block_id,json=blockId,proto3" json:"block_id"`
|
||||
Timestamp time.Time `protobuf:"bytes,5,opt,name=timestamp,proto3,stdtime" json:"timestamp"`
|
||||
ValidatorAddress []byte `protobuf:"bytes,6,opt,name=validator_address,json=validatorAddress,proto3" json:"validator_address,omitempty"`
|
||||
ValidatorIndex int32 `protobuf:"varint,7,opt,name=validator_index,json=validatorIndex,proto3" json:"validator_index,omitempty"`
|
||||
Signature []byte `protobuf:"bytes,8,opt,name=signature,proto3" json:"signature,omitempty"`
|
||||
VoteExtension *VoteExtension `protobuf:"bytes,9,opt,name=vote_extension,json=voteExtension,proto3" json:"vote_extension,omitempty"`
|
||||
Type SignedMsgType `protobuf:"varint,1,opt,name=type,proto3,enum=tendermint.types.SignedMsgType" json:"type,omitempty"`
|
||||
Height int64 `protobuf:"varint,2,opt,name=height,proto3" json:"height,omitempty"`
|
||||
Round int32 `protobuf:"varint,3,opt,name=round,proto3" json:"round,omitempty"`
|
||||
BlockID BlockID `protobuf:"bytes,4,opt,name=block_id,json=blockId,proto3" json:"block_id"`
|
||||
Timestamp time.Time `protobuf:"bytes,5,opt,name=timestamp,proto3,stdtime" json:"timestamp"`
|
||||
ValidatorAddress []byte `protobuf:"bytes,6,opt,name=validator_address,json=validatorAddress,proto3" json:"validator_address,omitempty"`
|
||||
ValidatorIndex int32 `protobuf:"varint,7,opt,name=validator_index,json=validatorIndex,proto3" json:"validator_index,omitempty"`
|
||||
// Vote signature by the validator if they participated in consensus for the
|
||||
// associated block.
|
||||
Signature []byte `protobuf:"bytes,8,opt,name=signature,proto3" json:"signature,omitempty"`
|
||||
// Vote extension provided by the application. Only valid for precommit
|
||||
// messages.
|
||||
Extension []byte `protobuf:"bytes,9,opt,name=extension,proto3" json:"extension,omitempty"`
|
||||
// Vote extension signature by the validator if they participated in
|
||||
// consensus for the associated block.
|
||||
ExtensionSignature []byte `protobuf:"bytes,10,opt,name=extension_signature,json=extensionSignature,proto3" json:"extension_signature,omitempty"`
|
||||
}
|
||||
|
||||
func (m *Vote) Reset() { *m = Vote{} }
|
||||
@@ -566,108 +573,16 @@ func (m *Vote) GetSignature() []byte {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (m *Vote) GetVoteExtension() *VoteExtension {
|
||||
func (m *Vote) GetExtension() []byte {
|
||||
if m != nil {
|
||||
return m.VoteExtension
|
||||
return m.Extension
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// VoteExtension is app-defined additional information to the validator votes.
|
||||
type VoteExtension struct {
|
||||
AppDataToSign []byte `protobuf:"bytes,1,opt,name=app_data_to_sign,json=appDataToSign,proto3" json:"app_data_to_sign,omitempty"`
|
||||
AppDataSelfAuthenticating []byte `protobuf:"bytes,2,opt,name=app_data_self_authenticating,json=appDataSelfAuthenticating,proto3" json:"app_data_self_authenticating,omitempty"`
|
||||
}
|
||||
|
||||
func (m *VoteExtension) Reset() { *m = VoteExtension{} }
|
||||
func (m *VoteExtension) String() string { return proto.CompactTextString(m) }
|
||||
func (*VoteExtension) ProtoMessage() {}
|
||||
func (*VoteExtension) Descriptor() ([]byte, []int) {
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{6}
|
||||
}
|
||||
func (m *VoteExtension) XXX_Unmarshal(b []byte) error {
|
||||
return m.Unmarshal(b)
|
||||
}
|
||||
func (m *VoteExtension) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
|
||||
if deterministic {
|
||||
return xxx_messageInfo_VoteExtension.Marshal(b, m, deterministic)
|
||||
} else {
|
||||
b = b[:cap(b)]
|
||||
n, err := m.MarshalToSizedBuffer(b)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return b[:n], nil
|
||||
}
|
||||
}
|
||||
func (m *VoteExtension) XXX_Merge(src proto.Message) {
|
||||
xxx_messageInfo_VoteExtension.Merge(m, src)
|
||||
}
|
||||
func (m *VoteExtension) XXX_Size() int {
|
||||
return m.Size()
|
||||
}
|
||||
func (m *VoteExtension) XXX_DiscardUnknown() {
|
||||
xxx_messageInfo_VoteExtension.DiscardUnknown(m)
|
||||
}
|
||||
|
||||
var xxx_messageInfo_VoteExtension proto.InternalMessageInfo
|
||||
|
||||
func (m *VoteExtension) GetAppDataToSign() []byte {
|
||||
func (m *Vote) GetExtensionSignature() []byte {
|
||||
if m != nil {
|
||||
return m.AppDataToSign
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (m *VoteExtension) GetAppDataSelfAuthenticating() []byte {
|
||||
if m != nil {
|
||||
return m.AppDataSelfAuthenticating
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// VoteExtensionToSign is a subset of VoteExtension that is signed by the validators private key.
|
||||
// VoteExtensionToSign is extracted from an existing VoteExtension.
|
||||
type VoteExtensionToSign struct {
|
||||
AppDataToSign []byte `protobuf:"bytes,1,opt,name=app_data_to_sign,json=appDataToSign,proto3" json:"app_data_to_sign,omitempty"`
|
||||
}
|
||||
|
||||
func (m *VoteExtensionToSign) Reset() { *m = VoteExtensionToSign{} }
|
||||
func (m *VoteExtensionToSign) String() string { return proto.CompactTextString(m) }
|
||||
func (*VoteExtensionToSign) ProtoMessage() {}
|
||||
func (*VoteExtensionToSign) Descriptor() ([]byte, []int) {
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{7}
|
||||
}
|
||||
func (m *VoteExtensionToSign) XXX_Unmarshal(b []byte) error {
|
||||
return m.Unmarshal(b)
|
||||
}
|
||||
func (m *VoteExtensionToSign) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
|
||||
if deterministic {
|
||||
return xxx_messageInfo_VoteExtensionToSign.Marshal(b, m, deterministic)
|
||||
} else {
|
||||
b = b[:cap(b)]
|
||||
n, err := m.MarshalToSizedBuffer(b)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return b[:n], nil
|
||||
}
|
||||
}
|
||||
func (m *VoteExtensionToSign) XXX_Merge(src proto.Message) {
|
||||
xxx_messageInfo_VoteExtensionToSign.Merge(m, src)
|
||||
}
|
||||
func (m *VoteExtensionToSign) XXX_Size() int {
|
||||
return m.Size()
|
||||
}
|
||||
func (m *VoteExtensionToSign) XXX_DiscardUnknown() {
|
||||
xxx_messageInfo_VoteExtensionToSign.DiscardUnknown(m)
|
||||
}
|
||||
|
||||
var xxx_messageInfo_VoteExtensionToSign proto.InternalMessageInfo
|
||||
|
||||
func (m *VoteExtensionToSign) GetAppDataToSign() []byte {
|
||||
if m != nil {
|
||||
return m.AppDataToSign
|
||||
return m.ExtensionSignature
|
||||
}
|
||||
return nil
|
||||
}
|
||||
@@ -685,7 +600,7 @@ func (m *Commit) Reset() { *m = Commit{} }
|
||||
func (m *Commit) String() string { return proto.CompactTextString(m) }
|
||||
func (*Commit) ProtoMessage() {}
|
||||
func (*Commit) Descriptor() ([]byte, []int) {
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{8}
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{6}
|
||||
}
|
||||
func (m *Commit) XXX_Unmarshal(b []byte) error {
|
||||
return m.Unmarshal(b)
|
||||
@@ -744,18 +659,17 @@ func (m *Commit) GetSignatures() []CommitSig {
|
||||
|
||||
// CommitSig is a part of the Vote included in a Commit.
|
||||
type CommitSig struct {
|
||||
BlockIdFlag BlockIDFlag `protobuf:"varint,1,opt,name=block_id_flag,json=blockIdFlag,proto3,enum=tendermint.types.BlockIDFlag" json:"block_id_flag,omitempty"`
|
||||
ValidatorAddress []byte `protobuf:"bytes,2,opt,name=validator_address,json=validatorAddress,proto3" json:"validator_address,omitempty"`
|
||||
Timestamp time.Time `protobuf:"bytes,3,opt,name=timestamp,proto3,stdtime" json:"timestamp"`
|
||||
Signature []byte `protobuf:"bytes,4,opt,name=signature,proto3" json:"signature,omitempty"`
|
||||
VoteExtension *VoteExtensionToSign `protobuf:"bytes,5,opt,name=vote_extension,json=voteExtension,proto3" json:"vote_extension,omitempty"`
|
||||
BlockIdFlag BlockIDFlag `protobuf:"varint,1,opt,name=block_id_flag,json=blockIdFlag,proto3,enum=tendermint.types.BlockIDFlag" json:"block_id_flag,omitempty"`
|
||||
ValidatorAddress []byte `protobuf:"bytes,2,opt,name=validator_address,json=validatorAddress,proto3" json:"validator_address,omitempty"`
|
||||
Timestamp time.Time `protobuf:"bytes,3,opt,name=timestamp,proto3,stdtime" json:"timestamp"`
|
||||
Signature []byte `protobuf:"bytes,4,opt,name=signature,proto3" json:"signature,omitempty"`
|
||||
}
|
||||
|
||||
func (m *CommitSig) Reset() { *m = CommitSig{} }
|
||||
func (m *CommitSig) String() string { return proto.CompactTextString(m) }
|
||||
func (*CommitSig) ProtoMessage() {}
|
||||
func (*CommitSig) Descriptor() ([]byte, []int) {
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{9}
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{7}
|
||||
}
|
||||
func (m *CommitSig) XXX_Unmarshal(b []byte) error {
|
||||
return m.Unmarshal(b)
|
||||
@@ -812,13 +726,6 @@ func (m *CommitSig) GetSignature() []byte {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (m *CommitSig) GetVoteExtension() *VoteExtensionToSign {
|
||||
if m != nil {
|
||||
return m.VoteExtension
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
type Proposal struct {
|
||||
Type SignedMsgType `protobuf:"varint,1,opt,name=type,proto3,enum=tendermint.types.SignedMsgType" json:"type,omitempty"`
|
||||
Height int64 `protobuf:"varint,2,opt,name=height,proto3" json:"height,omitempty"`
|
||||
@@ -833,7 +740,7 @@ func (m *Proposal) Reset() { *m = Proposal{} }
|
||||
func (m *Proposal) String() string { return proto.CompactTextString(m) }
|
||||
func (*Proposal) ProtoMessage() {}
|
||||
func (*Proposal) Descriptor() ([]byte, []int) {
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{10}
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{8}
|
||||
}
|
||||
func (m *Proposal) XXX_Unmarshal(b []byte) error {
|
||||
return m.Unmarshal(b)
|
||||
@@ -920,7 +827,7 @@ func (m *SignedHeader) Reset() { *m = SignedHeader{} }
|
||||
func (m *SignedHeader) String() string { return proto.CompactTextString(m) }
|
||||
func (*SignedHeader) ProtoMessage() {}
|
||||
func (*SignedHeader) Descriptor() ([]byte, []int) {
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{11}
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{9}
|
||||
}
|
||||
func (m *SignedHeader) XXX_Unmarshal(b []byte) error {
|
||||
return m.Unmarshal(b)
|
||||
@@ -972,7 +879,7 @@ func (m *LightBlock) Reset() { *m = LightBlock{} }
|
||||
func (m *LightBlock) String() string { return proto.CompactTextString(m) }
|
||||
func (*LightBlock) ProtoMessage() {}
|
||||
func (*LightBlock) Descriptor() ([]byte, []int) {
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{12}
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{10}
|
||||
}
|
||||
func (m *LightBlock) XXX_Unmarshal(b []byte) error {
|
||||
return m.Unmarshal(b)
|
||||
@@ -1026,7 +933,7 @@ func (m *BlockMeta) Reset() { *m = BlockMeta{} }
|
||||
func (m *BlockMeta) String() string { return proto.CompactTextString(m) }
|
||||
func (*BlockMeta) ProtoMessage() {}
|
||||
func (*BlockMeta) Descriptor() ([]byte, []int) {
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{13}
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{11}
|
||||
}
|
||||
func (m *BlockMeta) XXX_Unmarshal(b []byte) error {
|
||||
return m.Unmarshal(b)
|
||||
@@ -1095,7 +1002,7 @@ func (m *TxProof) Reset() { *m = TxProof{} }
|
||||
func (m *TxProof) String() string { return proto.CompactTextString(m) }
|
||||
func (*TxProof) ProtoMessage() {}
|
||||
func (*TxProof) Descriptor() ([]byte, []int) {
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{14}
|
||||
return fileDescriptor_d3a6e55e2345de56, []int{12}
|
||||
}
|
||||
func (m *TxProof) XXX_Unmarshal(b []byte) error {
|
||||
return m.Unmarshal(b)
|
||||
@@ -1154,8 +1061,6 @@ func init() {
|
||||
proto.RegisterType((*Header)(nil), "tendermint.types.Header")
|
||||
proto.RegisterType((*Data)(nil), "tendermint.types.Data")
|
||||
proto.RegisterType((*Vote)(nil), "tendermint.types.Vote")
|
||||
proto.RegisterType((*VoteExtension)(nil), "tendermint.types.VoteExtension")
|
||||
proto.RegisterType((*VoteExtensionToSign)(nil), "tendermint.types.VoteExtensionToSign")
|
||||
proto.RegisterType((*Commit)(nil), "tendermint.types.Commit")
|
||||
proto.RegisterType((*CommitSig)(nil), "tendermint.types.CommitSig")
|
||||
proto.RegisterType((*Proposal)(nil), "tendermint.types.Proposal")
|
||||
@@ -1168,96 +1073,91 @@ func init() {
|
||||
func init() { proto.RegisterFile("tendermint/types/types.proto", fileDescriptor_d3a6e55e2345de56) }
|
||||
|
||||
var fileDescriptor_d3a6e55e2345de56 = []byte{
|
||||
// 1423 bytes of a gzipped FileDescriptorProto
|
||||
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x57, 0x4f, 0x6f, 0xdb, 0x64,
|
||||
0x18, 0xaf, 0x13, 0xb7, 0x49, 0x9e, 0xc4, 0x6d, 0xfa, 0xd2, 0x6d, 0x69, 0xb6, 0xa6, 0x91, 0xd1,
|
||||
0x58, 0x37, 0x50, 0x3a, 0x3a, 0xc4, 0x9f, 0x03, 0xa0, 0x24, 0xcd, 0xb6, 0x68, 0x6d, 0x1a, 0x9c,
|
||||
0x6c, 0x08, 0x2e, 0x96, 0x93, 0xbc, 0x4d, 0xcc, 0x1c, 0xdb, 0xb2, 0xdf, 0x94, 0x76, 0x9f, 0x00,
|
||||
0xf5, 0xb4, 0x13, 0xb7, 0x9e, 0xe0, 0x80, 0xc4, 0x05, 0x89, 0x2f, 0x80, 0x38, 0xed, 0xb8, 0x1b,
|
||||
0x9c, 0x06, 0xea, 0x24, 0x3e, 0x07, 0x7a, 0xff, 0xc4, 0xb1, 0x9b, 0x86, 0x4d, 0xd5, 0xc4, 0x25,
|
||||
0xf2, 0xfb, 0x3c, 0xbf, 0xe7, 0xff, 0xcf, 0x8f, 0xdf, 0xc0, 0x35, 0x82, 0xed, 0x1e, 0xf6, 0x86,
|
||||
0xa6, 0x4d, 0x36, 0xc9, 0x91, 0x8b, 0x7d, 0xfe, 0x5b, 0x72, 0x3d, 0x87, 0x38, 0x28, 0x3b, 0xd1,
|
||||
0x96, 0x98, 0x3c, 0xbf, 0xd2, 0x77, 0xfa, 0x0e, 0x53, 0x6e, 0xd2, 0x27, 0x8e, 0xcb, 0xaf, 0xf7,
|
||||
0x1d, 0xa7, 0x6f, 0xe1, 0x4d, 0x76, 0xea, 0x8c, 0xf6, 0x37, 0x89, 0x39, 0xc4, 0x3e, 0x31, 0x86,
|
||||
0xae, 0x00, 0xac, 0x85, 0xc2, 0x74, 0xbd, 0x23, 0x97, 0x38, 0x14, 0xeb, 0xec, 0x0b, 0x75, 0x21,
|
||||
0xa4, 0x3e, 0xc0, 0x9e, 0x6f, 0x3a, 0x76, 0x38, 0x8f, 0x7c, 0x71, 0x2a, 0xcb, 0x03, 0xc3, 0x32,
|
||||
0x7b, 0x06, 0x71, 0x3c, 0x8e, 0x50, 0x3f, 0x01, 0xa5, 0x69, 0x78, 0xa4, 0x85, 0xc9, 0x7d, 0x6c,
|
||||
0xf4, 0xb0, 0x87, 0x56, 0x60, 0x9e, 0x38, 0xc4, 0xb0, 0x72, 0x52, 0x51, 0xda, 0x50, 0x34, 0x7e,
|
||||
0x40, 0x08, 0xe4, 0x81, 0xe1, 0x0f, 0x72, 0xb1, 0xa2, 0xb4, 0x91, 0xd1, 0xd8, 0xb3, 0x3a, 0x00,
|
||||
0x99, 0x9a, 0x52, 0x0b, 0xd3, 0xee, 0xe1, 0xc3, 0xb1, 0x05, 0x3b, 0x50, 0x69, 0xe7, 0x88, 0x60,
|
||||
0x5f, 0x98, 0xf0, 0x03, 0xfa, 0x00, 0xe6, 0x59, 0xfe, 0xb9, 0x78, 0x51, 0xda, 0x48, 0x6f, 0xe5,
|
||||
0x4a, 0xa1, 0x46, 0xf1, 0xfa, 0x4a, 0x4d, 0xaa, 0xaf, 0xc8, 0xcf, 0x5e, 0xac, 0xcf, 0x69, 0x1c,
|
||||
0xac, 0x5a, 0x90, 0xa8, 0x58, 0x4e, 0xf7, 0x71, 0x7d, 0x3b, 0x48, 0x44, 0x9a, 0x24, 0x82, 0x76,
|
||||
0x61, 0xc9, 0x35, 0x3c, 0xa2, 0xfb, 0x98, 0xe8, 0x03, 0x56, 0x05, 0x0b, 0x9a, 0xde, 0x5a, 0x2f,
|
||||
0x9d, 0x9d, 0x43, 0x29, 0x52, 0xac, 0x88, 0xa2, 0xb8, 0x61, 0xa1, 0xfa, 0x8f, 0x0c, 0x0b, 0xa2,
|
||||
0x19, 0x9f, 0x42, 0x42, 0xb4, 0x95, 0x05, 0x4c, 0x6f, 0xad, 0x85, 0x3d, 0x0a, 0x55, 0xa9, 0xea,
|
||||
0xd8, 0x3e, 0xb6, 0xfd, 0x91, 0x2f, 0xfc, 0x8d, 0x6d, 0xd0, 0x3b, 0x90, 0xec, 0x0e, 0x0c, 0xd3,
|
||||
0xd6, 0xcd, 0x1e, 0xcb, 0x28, 0x55, 0x49, 0x9f, 0xbe, 0x58, 0x4f, 0x54, 0xa9, 0xac, 0xbe, 0xad,
|
||||
0x25, 0x98, 0xb2, 0xde, 0x43, 0x97, 0x61, 0x61, 0x80, 0xcd, 0xfe, 0x80, 0xb0, 0xb6, 0xc4, 0x35,
|
||||
0x71, 0x42, 0x1f, 0x83, 0x4c, 0x09, 0x91, 0x93, 0x59, 0xec, 0x7c, 0x89, 0xb3, 0xa5, 0x34, 0x66,
|
||||
0x4b, 0xa9, 0x3d, 0x66, 0x4b, 0x25, 0x49, 0x03, 0x3f, 0xfd, 0x6b, 0x5d, 0xd2, 0x98, 0x05, 0xaa,
|
||||
0x82, 0x62, 0x19, 0x3e, 0xd1, 0x3b, 0xb4, 0x6d, 0x34, 0xfc, 0x3c, 0x73, 0xb1, 0x3a, 0xdd, 0x10,
|
||||
0xd1, 0x58, 0x91, 0x7a, 0x9a, 0x5a, 0x71, 0x51, 0x0f, 0x6d, 0x40, 0x96, 0x39, 0xe9, 0x3a, 0xc3,
|
||||
0xa1, 0x49, 0x74, 0xd6, 0xf7, 0x05, 0xd6, 0xf7, 0x45, 0x2a, 0xaf, 0x32, 0xf1, 0x7d, 0x3a, 0x81,
|
||||
0xab, 0x90, 0xea, 0x19, 0xc4, 0xe0, 0x90, 0x04, 0x83, 0x24, 0xa9, 0x80, 0x29, 0x6f, 0xc0, 0x52,
|
||||
0xc0, 0x3a, 0x9f, 0x43, 0x92, 0xdc, 0xcb, 0x44, 0xcc, 0x80, 0xb7, 0x61, 0xc5, 0xc6, 0x87, 0x44,
|
||||
0x3f, 0x8b, 0x4e, 0x31, 0x34, 0xa2, 0xba, 0x47, 0x51, 0x8b, 0xeb, 0xb0, 0xd8, 0x1d, 0x37, 0x9f,
|
||||
0x63, 0x81, 0x61, 0x95, 0x40, 0xca, 0x60, 0xab, 0x90, 0x34, 0x5c, 0x97, 0x03, 0xd2, 0x0c, 0x90,
|
||||
0x30, 0x5c, 0x97, 0xa9, 0x6e, 0xc1, 0x32, 0xab, 0xd1, 0xc3, 0xfe, 0xc8, 0x22, 0xc2, 0x49, 0x86,
|
||||
0x61, 0x96, 0xa8, 0x42, 0xe3, 0x72, 0x86, 0x7d, 0x1b, 0x14, 0x7c, 0x60, 0xf6, 0xb0, 0xdd, 0xc5,
|
||||
0x1c, 0xa7, 0x30, 0x5c, 0x66, 0x2c, 0x64, 0xa0, 0x9b, 0x90, 0x75, 0x3d, 0xc7, 0x75, 0x7c, 0xec,
|
||||
0xe9, 0x46, 0xaf, 0xe7, 0x61, 0xdf, 0xcf, 0x2d, 0x72, 0x7f, 0x63, 0x79, 0x99, 0x8b, 0xd5, 0x1c,
|
||||
0xc8, 0xdb, 0x06, 0x31, 0x50, 0x16, 0xe2, 0xe4, 0xd0, 0xcf, 0x49, 0xc5, 0xf8, 0x46, 0x46, 0xa3,
|
||||
0x8f, 0xea, 0x2f, 0x71, 0x90, 0x1f, 0x39, 0x04, 0xa3, 0x3b, 0x20, 0xd3, 0x31, 0x31, 0xf6, 0x2d,
|
||||
0x9e, 0xc7, 0xe7, 0x96, 0xd9, 0xb7, 0x71, 0x6f, 0xd7, 0xef, 0xb7, 0x8f, 0x5c, 0xac, 0x31, 0x70,
|
||||
0x88, 0x4e, 0xb1, 0x08, 0x9d, 0x56, 0x60, 0xde, 0x73, 0x46, 0x76, 0x8f, 0xb1, 0x6c, 0x5e, 0xe3,
|
||||
0x07, 0x54, 0x83, 0x64, 0xc0, 0x12, 0xf9, 0x55, 0x2c, 0x59, 0xa2, 0x2c, 0xa1, 0x1c, 0x16, 0x02,
|
||||
0x2d, 0xd1, 0x11, 0x64, 0xa9, 0x40, 0x2a, 0x58, 0x5e, 0x82, 0x6d, 0xaf, 0x47, 0xd8, 0x89, 0x19,
|
||||
0x7a, 0x17, 0x96, 0x83, 0xd9, 0x07, 0xcd, 0xe3, 0x8c, 0xcb, 0x06, 0x0a, 0xd1, 0xbd, 0x08, 0xad,
|
||||
0x74, 0xbe, 0x80, 0x12, 0xac, 0xae, 0x09, 0xad, 0xea, 0x6c, 0x13, 0x5d, 0x83, 0x94, 0x6f, 0xf6,
|
||||
0x6d, 0x83, 0x8c, 0x3c, 0x2c, 0x98, 0x37, 0x11, 0xa0, 0xbb, 0xb0, 0x78, 0xe0, 0x10, 0xac, 0xe3,
|
||||
0x43, 0x82, 0x6d, 0xf6, 0xa6, 0xa7, 0x66, 0xed, 0x0e, 0x3a, 0x91, 0xda, 0x18, 0xa6, 0x29, 0x07,
|
||||
0xe1, 0xa3, 0x7a, 0x04, 0x4a, 0x44, 0x8f, 0x6e, 0x40, 0x96, 0x92, 0x8e, 0xbd, 0x17, 0xc4, 0xd1,
|
||||
0x69, 0x44, 0xb1, 0xb5, 0x14, 0xc3, 0x75, 0xe9, 0xe0, 0xdb, 0x0e, 0x9d, 0x1e, 0xfa, 0x1c, 0xae,
|
||||
0x05, 0x40, 0x1f, 0x5b, 0xfb, 0xba, 0x31, 0x22, 0x03, 0x6c, 0x13, 0xb3, 0x6b, 0x10, 0xd3, 0xee,
|
||||
0x8b, 0x05, 0xba, 0x2a, 0x8c, 0x5a, 0xd8, 0xda, 0x2f, 0x47, 0x00, 0xea, 0x67, 0xf0, 0x56, 0x24,
|
||||
0xb4, 0xf0, 0xfb, 0xba, 0x09, 0xa8, 0xbf, 0x49, 0xb0, 0xc0, 0x5f, 0xe6, 0x10, 0x75, 0xa4, 0xf3,
|
||||
0xa9, 0x13, 0x9b, 0x45, 0x9d, 0xf8, 0xc5, 0xa9, 0x53, 0x06, 0x08, 0xe6, 0xe1, 0xe7, 0xe4, 0x62,
|
||||
0x7c, 0x23, 0xbd, 0x75, 0x75, 0xda, 0x11, 0x4f, 0xb1, 0x65, 0xf6, 0xc5, 0xae, 0x0a, 0x19, 0xa9,
|
||||
0x3f, 0xc7, 0x20, 0x15, 0xe8, 0x51, 0x19, 0x94, 0x71, 0x5e, 0xfa, 0xbe, 0x65, 0xf4, 0xc5, 0xeb,
|
||||
0xb3, 0x36, 0x33, 0xb9, 0xbb, 0x96, 0xd1, 0xd7, 0xd2, 0x22, 0x1f, 0x7a, 0x38, 0x9f, 0x8a, 0xb1,
|
||||
0x19, 0x54, 0x8c, 0x70, 0x3f, 0x7e, 0x31, 0xee, 0x47, 0x58, 0x2a, 0x9f, 0x65, 0xe9, 0xce, 0x14,
|
||||
0x4b, 0xf9, 0x2b, 0x76, 0xfd, 0x15, 0x2c, 0xe5, 0x13, 0x3e, 0xcb, 0xd5, 0x5f, 0x63, 0x90, 0x6c,
|
||||
0xb2, 0x65, 0x64, 0x58, 0xff, 0xc7, 0x8a, 0xb9, 0x0a, 0x29, 0xd7, 0xb1, 0x74, 0xae, 0x91, 0x99,
|
||||
0x26, 0xe9, 0x3a, 0x96, 0x36, 0x45, 0xa2, 0xf9, 0x37, 0xb4, 0x7f, 0x16, 0xde, 0xc0, 0x0c, 0x12,
|
||||
0x67, 0x66, 0xa0, 0x7a, 0x90, 0xe1, 0xad, 0x10, 0x97, 0x83, 0xdb, 0xb4, 0x07, 0xec, 0xb6, 0x21,
|
||||
0x4d, 0x5f, 0x66, 0x78, 0xda, 0x1c, 0xa9, 0x09, 0x1c, 0xb5, 0xe0, 0xdf, 0x52, 0x71, 0x3f, 0xc9,
|
||||
0xcd, 0x22, 0xb9, 0x26, 0x70, 0xea, 0xf7, 0x12, 0xc0, 0x0e, 0xed, 0x2c, 0xab, 0x97, 0x7e, 0xd6,
|
||||
0x7d, 0x96, 0x82, 0x1e, 0x89, 0x5c, 0x98, 0x35, 0x34, 0x11, 0x3f, 0xe3, 0x87, 0xf3, 0xae, 0x82,
|
||||
0x32, 0xa1, 0xb6, 0x8f, 0xc7, 0xc9, 0x9c, 0xe3, 0x24, 0xf8, 0xda, 0xb6, 0x30, 0xd1, 0x32, 0x07,
|
||||
0xa1, 0x93, 0xfa, 0xbb, 0x04, 0x29, 0x96, 0xd3, 0x2e, 0x26, 0x46, 0x64, 0x86, 0xd2, 0xc5, 0x67,
|
||||
0xb8, 0x06, 0xc0, 0xdd, 0xf8, 0xe6, 0x13, 0x2c, 0x98, 0x95, 0x62, 0x92, 0x96, 0xf9, 0x04, 0xa3,
|
||||
0x0f, 0x83, 0x86, 0xc7, 0xff, 0xbb, 0xe1, 0x62, 0x41, 0x8c, 0xdb, 0x7e, 0x05, 0x12, 0xf6, 0x68,
|
||||
0xa8, 0xd3, 0x6f, 0xac, 0xcc, 0xd9, 0x6a, 0x8f, 0x86, 0xed, 0x43, 0x5f, 0xfd, 0x06, 0x12, 0xed,
|
||||
0x43, 0x76, 0xdf, 0xa4, 0x14, 0xf5, 0x1c, 0x47, 0x5c, 0x72, 0xf8, 0x96, 0x4c, 0x52, 0x01, 0xfb,
|
||||
0xa6, 0x23, 0x90, 0xe9, 0x16, 0x1d, 0xdf, 0x7e, 0xe9, 0x33, 0x2a, 0xbd, 0xe6, 0x4d, 0x56, 0xdc,
|
||||
0x61, 0x6f, 0xfd, 0x21, 0x41, 0x3a, 0xb4, 0x6d, 0xd0, 0xfb, 0x70, 0xa9, 0xb2, 0xb3, 0x57, 0x7d,
|
||||
0xa0, 0xd7, 0xb7, 0xf5, 0xbb, 0x3b, 0xe5, 0x7b, 0xfa, 0xc3, 0xc6, 0x83, 0xc6, 0xde, 0x97, 0x8d,
|
||||
0xec, 0x5c, 0xfe, 0xf2, 0xf1, 0x49, 0x11, 0x85, 0xb0, 0x0f, 0xed, 0xc7, 0xb6, 0xf3, 0xad, 0x8d,
|
||||
0x36, 0x61, 0x25, 0x6a, 0x52, 0xae, 0xb4, 0x6a, 0x8d, 0x76, 0x56, 0xca, 0x5f, 0x3a, 0x3e, 0x29,
|
||||
0x2e, 0x87, 0x2c, 0xca, 0x1d, 0x1f, 0xdb, 0x64, 0xda, 0xa0, 0xba, 0xb7, 0xbb, 0x5b, 0x6f, 0x67,
|
||||
0x63, 0x53, 0x06, 0x62, 0xfd, 0xdf, 0x84, 0xe5, 0xa8, 0x41, 0xa3, 0xbe, 0x93, 0x8d, 0xe7, 0xd1,
|
||||
0xf1, 0x49, 0x71, 0x31, 0x84, 0x6e, 0x98, 0x56, 0x3e, 0xf9, 0xdd, 0x0f, 0x85, 0xb9, 0x9f, 0x7e,
|
||||
0x2c, 0x48, 0xb4, 0x32, 0x25, 0xb2, 0x23, 0xd0, 0x7b, 0x70, 0xa5, 0x55, 0xbf, 0xd7, 0xa8, 0x6d,
|
||||
0xeb, 0xbb, 0xad, 0x7b, 0x7a, 0xfb, 0xab, 0x66, 0x2d, 0x54, 0xdd, 0xd2, 0xf1, 0x49, 0x31, 0x2d,
|
||||
0x4a, 0x9a, 0x85, 0x6e, 0x6a, 0xb5, 0x47, 0x7b, 0xed, 0x5a, 0x56, 0xe2, 0xe8, 0xa6, 0x87, 0xe9,
|
||||
0x02, 0x63, 0xe8, 0xdb, 0xb0, 0x7a, 0x0e, 0x3a, 0x28, 0x6c, 0xf9, 0xf8, 0xa4, 0xa8, 0x34, 0x3d,
|
||||
0xcc, 0xdf, 0x1f, 0x66, 0x51, 0x82, 0xdc, 0xb4, 0xc5, 0x5e, 0x73, 0xaf, 0x55, 0xde, 0xc9, 0x16,
|
||||
0xf3, 0xd9, 0xe3, 0x93, 0x62, 0x66, 0xbc, 0x0c, 0x29, 0x7e, 0x52, 0x59, 0xe5, 0x8b, 0x67, 0xa7,
|
||||
0x05, 0xe9, 0xf9, 0x69, 0x41, 0xfa, 0xfb, 0xb4, 0x20, 0x3d, 0x7d, 0x59, 0x98, 0x7b, 0xfe, 0xb2,
|
||||
0x30, 0xf7, 0xe7, 0xcb, 0xc2, 0xdc, 0xd7, 0x1f, 0xf5, 0x4d, 0x32, 0x18, 0x75, 0x4a, 0x5d, 0x67,
|
||||
0xb8, 0x19, 0xfe, 0x8f, 0x35, 0x79, 0xe4, 0xff, 0xf5, 0xce, 0xfe, 0xff, 0xea, 0x2c, 0x30, 0xf9,
|
||||
0x9d, 0x7f, 0x03, 0x00, 0x00, 0xff, 0xff, 0x38, 0xfc, 0x14, 0xb1, 0x40, 0x0e, 0x00, 0x00,
|
||||
// 1341 bytes of a gzipped FileDescriptorProto
|
||||
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x57, 0xcf, 0x73, 0xdb, 0xc4,
|
||||
0x17, 0x8f, 0x62, 0x25, 0xb6, 0x9f, 0xed, 0xc4, 0xd9, 0x6f, 0xda, 0xba, 0x6e, 0xe3, 0x68, 0xfc,
|
||||
0x1d, 0x20, 0x2d, 0x8c, 0x52, 0x52, 0x86, 0x1f, 0x07, 0x0e, 0xb6, 0x93, 0xb6, 0x9e, 0x26, 0x8e,
|
||||
0x91, 0xdd, 0x32, 0x70, 0xd1, 0xc8, 0xd6, 0xd6, 0x16, 0x95, 0x25, 0x8d, 0x76, 0x1d, 0x92, 0xfe,
|
||||
0x05, 0x4c, 0x4e, 0x3d, 0x71, 0xcb, 0x09, 0x0e, 0xdc, 0x39, 0x70, 0x65, 0x38, 0xf5, 0xd8, 0x1b,
|
||||
0x5c, 0x28, 0x4c, 0x3a, 0xc3, 0xdf, 0xc1, 0xec, 0x0f, 0xc9, 0x72, 0x9c, 0x40, 0xa7, 0xd3, 0xe1,
|
||||
0xe2, 0xd1, 0xbe, 0xf7, 0x79, 0x6f, 0xdf, 0x8f, 0xcf, 0xee, 0x5b, 0xc3, 0x75, 0x8a, 0x3d, 0x1b,
|
||||
0x87, 0x23, 0xc7, 0xa3, 0x9b, 0xf4, 0x28, 0xc0, 0x44, 0xfc, 0xea, 0x41, 0xe8, 0x53, 0x1f, 0x15,
|
||||
0x27, 0x5a, 0x9d, 0xcb, 0xcb, 0xab, 0x03, 0x7f, 0xe0, 0x73, 0xe5, 0x26, 0xfb, 0x12, 0xb8, 0xf2,
|
||||
0xfa, 0xc0, 0xf7, 0x07, 0x2e, 0xde, 0xe4, 0xab, 0xde, 0xf8, 0xd1, 0x26, 0x75, 0x46, 0x98, 0x50,
|
||||
0x6b, 0x14, 0x48, 0xc0, 0x5a, 0x62, 0x9b, 0x7e, 0x78, 0x14, 0x50, 0x9f, 0x61, 0xfd, 0x47, 0x52,
|
||||
0x5d, 0x49, 0xa8, 0x0f, 0x70, 0x48, 0x1c, 0xdf, 0x4b, 0xc6, 0x51, 0xd6, 0x66, 0xa2, 0x3c, 0xb0,
|
||||
0x5c, 0xc7, 0xb6, 0xa8, 0x1f, 0x0a, 0x44, 0xf5, 0x13, 0x28, 0xb4, 0xad, 0x90, 0x76, 0x30, 0xbd,
|
||||
0x87, 0x2d, 0x1b, 0x87, 0x68, 0x15, 0x16, 0xa8, 0x4f, 0x2d, 0xb7, 0xa4, 0x68, 0xca, 0x46, 0xc1,
|
||||
0x10, 0x0b, 0x84, 0x40, 0x1d, 0x5a, 0x64, 0x58, 0x9a, 0xd7, 0x94, 0x8d, 0xbc, 0xc1, 0xbf, 0xab,
|
||||
0x43, 0x50, 0x99, 0x29, 0xb3, 0x70, 0x3c, 0x1b, 0x1f, 0x46, 0x16, 0x7c, 0xc1, 0xa4, 0xbd, 0x23,
|
||||
0x8a, 0x89, 0x34, 0x11, 0x0b, 0xf4, 0x01, 0x2c, 0xf0, 0xf8, 0x4b, 0x29, 0x4d, 0xd9, 0xc8, 0x6d,
|
||||
0x95, 0xf4, 0x44, 0xa1, 0x44, 0x7e, 0x7a, 0x9b, 0xe9, 0xeb, 0xea, 0xb3, 0x17, 0xeb, 0x73, 0x86,
|
||||
0x00, 0x57, 0x5d, 0x48, 0xd7, 0x5d, 0xbf, 0xff, 0xb8, 0xb9, 0x1d, 0x07, 0xa2, 0x4c, 0x02, 0x41,
|
||||
0x7b, 0xb0, 0x1c, 0x58, 0x21, 0x35, 0x09, 0xa6, 0xe6, 0x90, 0x67, 0xc1, 0x37, 0xcd, 0x6d, 0xad,
|
||||
0xeb, 0x67, 0xfb, 0xa0, 0x4f, 0x25, 0x2b, 0x77, 0x29, 0x04, 0x49, 0x61, 0xf5, 0x2f, 0x15, 0x16,
|
||||
0x65, 0x31, 0x3e, 0x85, 0xb4, 0x2c, 0x2b, 0xdf, 0x30, 0xb7, 0xb5, 0x96, 0xf4, 0x28, 0x55, 0x7a,
|
||||
0xc3, 0xf7, 0x08, 0xf6, 0xc8, 0x98, 0x48, 0x7f, 0x91, 0x0d, 0x7a, 0x1b, 0x32, 0xfd, 0xa1, 0xe5,
|
||||
0x78, 0xa6, 0x63, 0xf3, 0x88, 0xb2, 0xf5, 0xdc, 0xe9, 0x8b, 0xf5, 0x74, 0x83, 0xc9, 0x9a, 0xdb,
|
||||
0x46, 0x9a, 0x2b, 0x9b, 0x36, 0xba, 0x0c, 0x8b, 0x43, 0xec, 0x0c, 0x86, 0x94, 0x97, 0x25, 0x65,
|
||||
0xc8, 0x15, 0xfa, 0x18, 0x54, 0x46, 0x88, 0x92, 0xca, 0xf7, 0x2e, 0xeb, 0x82, 0x2d, 0x7a, 0xc4,
|
||||
0x16, 0xbd, 0x1b, 0xb1, 0xa5, 0x9e, 0x61, 0x1b, 0x3f, 0xfd, 0x63, 0x5d, 0x31, 0xb8, 0x05, 0x6a,
|
||||
0x40, 0xc1, 0xb5, 0x08, 0x35, 0x7b, 0xac, 0x6c, 0x6c, 0xfb, 0x05, 0xee, 0xe2, 0xea, 0x6c, 0x41,
|
||||
0x64, 0x61, 0x65, 0xe8, 0x39, 0x66, 0x25, 0x44, 0x36, 0xda, 0x80, 0x22, 0x77, 0xd2, 0xf7, 0x47,
|
||||
0x23, 0x87, 0x9a, 0xbc, 0xee, 0x8b, 0xbc, 0xee, 0x4b, 0x4c, 0xde, 0xe0, 0xe2, 0x7b, 0xac, 0x03,
|
||||
0xd7, 0x20, 0x6b, 0x5b, 0xd4, 0x12, 0x90, 0x34, 0x87, 0x64, 0x98, 0x80, 0x2b, 0xdf, 0x81, 0xe5,
|
||||
0x98, 0x75, 0x44, 0x40, 0x32, 0xc2, 0xcb, 0x44, 0xcc, 0x81, 0xb7, 0x60, 0xd5, 0xc3, 0x87, 0xd4,
|
||||
0x3c, 0x8b, 0xce, 0x72, 0x34, 0x62, 0xba, 0x87, 0xd3, 0x16, 0x6f, 0xc1, 0x52, 0x3f, 0x2a, 0xbe,
|
||||
0xc0, 0x02, 0xc7, 0x16, 0x62, 0x29, 0x87, 0x5d, 0x85, 0x8c, 0x15, 0x04, 0x02, 0x90, 0xe3, 0x80,
|
||||
0xb4, 0x15, 0x04, 0x5c, 0x75, 0x13, 0x56, 0x78, 0x8e, 0x21, 0x26, 0x63, 0x97, 0x4a, 0x27, 0x79,
|
||||
0x8e, 0x59, 0x66, 0x0a, 0x43, 0xc8, 0x39, 0xf6, 0xff, 0x50, 0xc0, 0x07, 0x8e, 0x8d, 0xbd, 0x3e,
|
||||
0x16, 0xb8, 0x02, 0xc7, 0xe5, 0x23, 0x21, 0x07, 0xdd, 0x80, 0x62, 0x10, 0xfa, 0x81, 0x4f, 0x70,
|
||||
0x68, 0x5a, 0xb6, 0x1d, 0x62, 0x42, 0x4a, 0x4b, 0xc2, 0x5f, 0x24, 0xaf, 0x09, 0x71, 0xb5, 0x04,
|
||||
0xea, 0xb6, 0x45, 0x2d, 0x54, 0x84, 0x14, 0x3d, 0x24, 0x25, 0x45, 0x4b, 0x6d, 0xe4, 0x0d, 0xf6,
|
||||
0x59, 0xfd, 0x29, 0x05, 0xea, 0x43, 0x9f, 0x62, 0x74, 0x1b, 0x54, 0xd6, 0x26, 0xce, 0xbe, 0xa5,
|
||||
0xf3, 0xf8, 0xdc, 0x71, 0x06, 0x1e, 0xb6, 0xf7, 0xc8, 0xa0, 0x7b, 0x14, 0x60, 0x83, 0x83, 0x13,
|
||||
0x74, 0x9a, 0x9f, 0xa2, 0xd3, 0x2a, 0x2c, 0x84, 0xfe, 0xd8, 0xb3, 0x39, 0xcb, 0x16, 0x0c, 0xb1,
|
||||
0x40, 0x3b, 0x90, 0x89, 0x59, 0xa2, 0xfe, 0x1b, 0x4b, 0x96, 0x19, 0x4b, 0x18, 0x87, 0xa5, 0xc0,
|
||||
0x48, 0xf7, 0x24, 0x59, 0xea, 0x90, 0x8d, 0x2f, 0x2f, 0xc9, 0xb6, 0x57, 0x23, 0xec, 0xc4, 0x0c,
|
||||
0xbd, 0x0b, 0x2b, 0x71, 0xef, 0xe3, 0xe2, 0x09, 0xc6, 0x15, 0x63, 0x85, 0xac, 0xde, 0x14, 0xad,
|
||||
0x4c, 0x71, 0x01, 0xa5, 0x79, 0x5e, 0x13, 0x5a, 0x35, 0xf9, 0x4d, 0x74, 0x1d, 0xb2, 0xc4, 0x19,
|
||||
0x78, 0x16, 0x1d, 0x87, 0x58, 0x32, 0x6f, 0x22, 0x60, 0x5a, 0x7c, 0x48, 0xb1, 0xc7, 0x0f, 0xb9,
|
||||
0x60, 0xda, 0x44, 0x80, 0x36, 0xe1, 0x7f, 0xf1, 0xc2, 0x9c, 0x78, 0x11, 0x2c, 0x43, 0xb1, 0xaa,
|
||||
0x13, 0x69, 0xaa, 0x3f, 0x2b, 0xb0, 0x28, 0x0e, 0x46, 0xa2, 0x0d, 0xca, 0xf9, 0x6d, 0x98, 0xbf,
|
||||
0xa8, 0x0d, 0xa9, 0xd7, 0x6f, 0x43, 0x0d, 0x20, 0x0e, 0x93, 0x94, 0x54, 0x2d, 0xb5, 0x91, 0xdb,
|
||||
0xba, 0x36, 0xeb, 0x48, 0x84, 0xd8, 0x71, 0x06, 0xf2, 0xdc, 0x27, 0x8c, 0xaa, 0xbf, 0x2b, 0x90,
|
||||
0x8d, 0xf5, 0xa8, 0x06, 0x85, 0x28, 0x2e, 0xf3, 0x91, 0x6b, 0x0d, 0x24, 0x15, 0xd7, 0x2e, 0x0c,
|
||||
0xee, 0x8e, 0x6b, 0x0d, 0x8c, 0x9c, 0x8c, 0x87, 0x2d, 0xce, 0x6f, 0xeb, 0xfc, 0x05, 0x6d, 0x9d,
|
||||
0xe2, 0x51, 0xea, 0xf5, 0x78, 0x34, 0xd5, 0x71, 0xf5, 0x4c, 0xc7, 0xab, 0x3f, 0xce, 0x43, 0xa6,
|
||||
0xcd, 0x8f, 0xa2, 0xe5, 0xfe, 0x17, 0x07, 0xec, 0x1a, 0x64, 0x03, 0xdf, 0x35, 0x85, 0x46, 0xe5,
|
||||
0x9a, 0x4c, 0xe0, 0xbb, 0xc6, 0x4c, 0xdb, 0x17, 0xde, 0xd0, 0xe9, 0x5b, 0x7c, 0x03, 0x55, 0x4b,
|
||||
0x9f, 0xad, 0x5a, 0x08, 0x79, 0x51, 0x0a, 0x39, 0x1a, 0x6f, 0xb1, 0x1a, 0xf0, 0x59, 0xab, 0xcc,
|
||||
0x8e, 0x72, 0x11, 0xb6, 0x40, 0x1a, 0x12, 0xc7, 0x2c, 0xc4, 0x24, 0x91, 0xd3, 0xb9, 0x74, 0x11,
|
||||
0x2d, 0x0d, 0x89, 0xab, 0x7e, 0xab, 0x00, 0xec, 0xb2, 0xca, 0xf2, 0x7c, 0xd9, 0x50, 0x23, 0x3c,
|
||||
0x04, 0x73, 0x6a, 0xe7, 0xca, 0x45, 0x4d, 0x93, 0xfb, 0xe7, 0x49, 0x32, 0xee, 0x06, 0x14, 0x26,
|
||||
0x64, 0x24, 0x38, 0x0a, 0xe6, 0x1c, 0x27, 0xf1, 0xac, 0xe9, 0x60, 0x6a, 0xe4, 0x0f, 0x12, 0xab,
|
||||
0xea, 0x2f, 0x0a, 0x64, 0x79, 0x4c, 0x7b, 0x98, 0x5a, 0x53, 0x3d, 0x54, 0x5e, 0xbf, 0x87, 0x6b,
|
||||
0x00, 0xc2, 0x0d, 0x71, 0x9e, 0x60, 0xc9, 0xac, 0x2c, 0x97, 0x74, 0x9c, 0x27, 0x18, 0x7d, 0x18,
|
||||
0x17, 0x3c, 0xf5, 0xcf, 0x05, 0x97, 0x47, 0x3a, 0x2a, 0xfb, 0x15, 0x48, 0x7b, 0xe3, 0x91, 0xc9,
|
||||
0x26, 0x8c, 0x2a, 0xd8, 0xea, 0x8d, 0x47, 0xdd, 0x43, 0x52, 0xfd, 0x0a, 0xd2, 0xdd, 0x43, 0xfe,
|
||||
0xda, 0x62, 0x14, 0x0d, 0x7d, 0x5f, 0x8e, 0x78, 0xf1, 0xb4, 0xca, 0x30, 0x01, 0x9f, 0x68, 0x08,
|
||||
0x54, 0x36, 0xcb, 0xa3, 0xb7, 0x1f, 0xfb, 0x46, 0xfa, 0x2b, 0xbe, 0xe3, 0xe4, 0x0b, 0xee, 0xe6,
|
||||
0xaf, 0x0a, 0xe4, 0x12, 0xf7, 0x03, 0x7a, 0x1f, 0x2e, 0xd5, 0x77, 0xf7, 0x1b, 0xf7, 0xcd, 0xe6,
|
||||
0xb6, 0x79, 0x67, 0xb7, 0x76, 0xd7, 0x7c, 0xd0, 0xba, 0xdf, 0xda, 0xff, 0xbc, 0x55, 0x9c, 0x2b,
|
||||
0x5f, 0x3e, 0x3e, 0xd1, 0x50, 0x02, 0xfb, 0xc0, 0x7b, 0xec, 0xf9, 0x5f, 0xb3, 0xab, 0x78, 0x75,
|
||||
0xda, 0xa4, 0x56, 0xef, 0xec, 0xb4, 0xba, 0x45, 0xa5, 0x7c, 0xe9, 0xf8, 0x44, 0x5b, 0x49, 0x58,
|
||||
0xd4, 0x7a, 0x04, 0x7b, 0x74, 0xd6, 0xa0, 0xb1, 0xbf, 0xb7, 0xd7, 0xec, 0x16, 0xe7, 0x67, 0x0c,
|
||||
0xe4, 0x85, 0x7d, 0x03, 0x56, 0xa6, 0x0d, 0x5a, 0xcd, 0xdd, 0x62, 0xaa, 0x8c, 0x8e, 0x4f, 0xb4,
|
||||
0xa5, 0x04, 0xba, 0xe5, 0xb8, 0xe5, 0xcc, 0x37, 0xdf, 0x55, 0xe6, 0x7e, 0xf8, 0xbe, 0xa2, 0xb0,
|
||||
0xcc, 0x0a, 0x53, 0x77, 0x04, 0x7a, 0x0f, 0xae, 0x74, 0x9a, 0x77, 0x5b, 0x3b, 0xdb, 0xe6, 0x5e,
|
||||
0xe7, 0xae, 0xd9, 0xfd, 0xa2, 0xbd, 0x93, 0xc8, 0x6e, 0xf9, 0xf8, 0x44, 0xcb, 0xc9, 0x94, 0x2e,
|
||||
0x42, 0xb7, 0x8d, 0x9d, 0x87, 0xfb, 0xdd, 0x9d, 0xa2, 0x22, 0xd0, 0xed, 0x10, 0x1f, 0xf8, 0x14,
|
||||
0x73, 0xf4, 0x2d, 0xb8, 0x7a, 0x0e, 0x3a, 0x4e, 0x6c, 0xe5, 0xf8, 0x44, 0x2b, 0xb4, 0x43, 0x2c,
|
||||
0xce, 0x0f, 0xb7, 0xd0, 0xa1, 0x34, 0x6b, 0xb1, 0xdf, 0xde, 0xef, 0xd4, 0x76, 0x8b, 0x5a, 0xb9,
|
||||
0x78, 0x7c, 0xa2, 0xe5, 0xa3, 0xcb, 0x90, 0xe1, 0x27, 0x99, 0xd5, 0x3f, 0x7b, 0x76, 0x5a, 0x51,
|
||||
0x9e, 0x9f, 0x56, 0x94, 0x3f, 0x4f, 0x2b, 0xca, 0xd3, 0x97, 0x95, 0xb9, 0xe7, 0x2f, 0x2b, 0x73,
|
||||
0xbf, 0xbd, 0xac, 0xcc, 0x7d, 0xf9, 0xd1, 0xc0, 0xa1, 0xc3, 0x71, 0x4f, 0xef, 0xfb, 0xa3, 0xcd,
|
||||
0xe4, 0x3f, 0x8c, 0xc9, 0xa7, 0xf8, 0xa7, 0x73, 0xf6, 0xdf, 0x47, 0x6f, 0x91, 0xcb, 0x6f, 0xff,
|
||||
0x1d, 0x00, 0x00, 0xff, 0xff, 0xbb, 0xc0, 0x81, 0x37, 0x3e, 0x0d, 0x00, 0x00,
|
||||
}
|
||||
|
||||
func (m *PartSetHeader) Marshal() (dAtA []byte, err error) {
|
||||
@@ -1558,15 +1458,17 @@ func (m *Vote) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
_ = i
|
||||
var l int
|
||||
_ = l
|
||||
if m.VoteExtension != nil {
|
||||
{
|
||||
size, err := m.VoteExtension.MarshalToSizedBuffer(dAtA[:i])
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
i -= size
|
||||
i = encodeVarintTypes(dAtA, i, uint64(size))
|
||||
}
|
||||
if len(m.ExtensionSignature) > 0 {
|
||||
i -= len(m.ExtensionSignature)
|
||||
copy(dAtA[i:], m.ExtensionSignature)
|
||||
i = encodeVarintTypes(dAtA, i, uint64(len(m.ExtensionSignature)))
|
||||
i--
|
||||
dAtA[i] = 0x52
|
||||
}
|
||||
if len(m.Extension) > 0 {
|
||||
i -= len(m.Extension)
|
||||
copy(dAtA[i:], m.Extension)
|
||||
i = encodeVarintTypes(dAtA, i, uint64(len(m.Extension)))
|
||||
i--
|
||||
dAtA[i] = 0x4a
|
||||
}
|
||||
@@ -1589,12 +1491,12 @@ func (m *Vote) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
i--
|
||||
dAtA[i] = 0x32
|
||||
}
|
||||
n7, err7 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Timestamp, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Timestamp):])
|
||||
if err7 != nil {
|
||||
return 0, err7
|
||||
n6, err6 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Timestamp, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Timestamp):])
|
||||
if err6 != nil {
|
||||
return 0, err6
|
||||
}
|
||||
i -= n7
|
||||
i = encodeVarintTypes(dAtA, i, uint64(n7))
|
||||
i -= n6
|
||||
i = encodeVarintTypes(dAtA, i, uint64(n6))
|
||||
i--
|
||||
dAtA[i] = 0x2a
|
||||
{
|
||||
@@ -1625,73 +1527,6 @@ func (m *Vote) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
return len(dAtA) - i, nil
|
||||
}
|
||||
|
||||
func (m *VoteExtension) Marshal() (dAtA []byte, err error) {
|
||||
size := m.Size()
|
||||
dAtA = make([]byte, size)
|
||||
n, err := m.MarshalToSizedBuffer(dAtA[:size])
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return dAtA[:n], nil
|
||||
}
|
||||
|
||||
func (m *VoteExtension) MarshalTo(dAtA []byte) (int, error) {
|
||||
size := m.Size()
|
||||
return m.MarshalToSizedBuffer(dAtA[:size])
|
||||
}
|
||||
|
||||
func (m *VoteExtension) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
i := len(dAtA)
|
||||
_ = i
|
||||
var l int
|
||||
_ = l
|
||||
if len(m.AppDataSelfAuthenticating) > 0 {
|
||||
i -= len(m.AppDataSelfAuthenticating)
|
||||
copy(dAtA[i:], m.AppDataSelfAuthenticating)
|
||||
i = encodeVarintTypes(dAtA, i, uint64(len(m.AppDataSelfAuthenticating)))
|
||||
i--
|
||||
dAtA[i] = 0x12
|
||||
}
|
||||
if len(m.AppDataToSign) > 0 {
|
||||
i -= len(m.AppDataToSign)
|
||||
copy(dAtA[i:], m.AppDataToSign)
|
||||
i = encodeVarintTypes(dAtA, i, uint64(len(m.AppDataToSign)))
|
||||
i--
|
||||
dAtA[i] = 0xa
|
||||
}
|
||||
return len(dAtA) - i, nil
|
||||
}
|
||||
|
||||
func (m *VoteExtensionToSign) Marshal() (dAtA []byte, err error) {
|
||||
size := m.Size()
|
||||
dAtA = make([]byte, size)
|
||||
n, err := m.MarshalToSizedBuffer(dAtA[:size])
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return dAtA[:n], nil
|
||||
}
|
||||
|
||||
func (m *VoteExtensionToSign) MarshalTo(dAtA []byte) (int, error) {
|
||||
size := m.Size()
|
||||
return m.MarshalToSizedBuffer(dAtA[:size])
|
||||
}
|
||||
|
||||
func (m *VoteExtensionToSign) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
i := len(dAtA)
|
||||
_ = i
|
||||
var l int
|
||||
_ = l
|
||||
if len(m.AppDataToSign) > 0 {
|
||||
i -= len(m.AppDataToSign)
|
||||
copy(dAtA[i:], m.AppDataToSign)
|
||||
i = encodeVarintTypes(dAtA, i, uint64(len(m.AppDataToSign)))
|
||||
i--
|
||||
dAtA[i] = 0xa
|
||||
}
|
||||
return len(dAtA) - i, nil
|
||||
}
|
||||
|
||||
func (m *Commit) Marshal() (dAtA []byte, err error) {
|
||||
size := m.Size()
|
||||
dAtA = make([]byte, size)
|
||||
@@ -1769,18 +1604,6 @@ func (m *CommitSig) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
_ = i
|
||||
var l int
|
||||
_ = l
|
||||
if m.VoteExtension != nil {
|
||||
{
|
||||
size, err := m.VoteExtension.MarshalToSizedBuffer(dAtA[:i])
|
||||
if err != nil {
|
||||
return 0, err
|
||||
}
|
||||
i -= size
|
||||
i = encodeVarintTypes(dAtA, i, uint64(size))
|
||||
}
|
||||
i--
|
||||
dAtA[i] = 0x2a
|
||||
}
|
||||
if len(m.Signature) > 0 {
|
||||
i -= len(m.Signature)
|
||||
copy(dAtA[i:], m.Signature)
|
||||
@@ -1788,12 +1611,12 @@ func (m *CommitSig) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
i--
|
||||
dAtA[i] = 0x22
|
||||
}
|
||||
n11, err11 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Timestamp, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Timestamp):])
|
||||
if err11 != nil {
|
||||
return 0, err11
|
||||
n9, err9 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Timestamp, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Timestamp):])
|
||||
if err9 != nil {
|
||||
return 0, err9
|
||||
}
|
||||
i -= n11
|
||||
i = encodeVarintTypes(dAtA, i, uint64(n11))
|
||||
i -= n9
|
||||
i = encodeVarintTypes(dAtA, i, uint64(n9))
|
||||
i--
|
||||
dAtA[i] = 0x1a
|
||||
if len(m.ValidatorAddress) > 0 {
|
||||
@@ -1838,12 +1661,12 @@ func (m *Proposal) MarshalToSizedBuffer(dAtA []byte) (int, error) {
|
||||
i--
|
||||
dAtA[i] = 0x3a
|
||||
}
|
||||
n12, err12 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Timestamp, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Timestamp):])
|
||||
if err12 != nil {
|
||||
return 0, err12
|
||||
n10, err10 := github_com_gogo_protobuf_types.StdTimeMarshalTo(m.Timestamp, dAtA[i-github_com_gogo_protobuf_types.SizeOfStdTime(m.Timestamp):])
|
||||
if err10 != nil {
|
||||
return 0, err10
|
||||
}
|
||||
i -= n12
|
||||
i = encodeVarintTypes(dAtA, i, uint64(n12))
|
||||
i -= n10
|
||||
i = encodeVarintTypes(dAtA, i, uint64(n10))
|
||||
i--
|
||||
dAtA[i] = 0x32
|
||||
{
|
||||
@@ -2238,37 +2061,11 @@ func (m *Vote) Size() (n int) {
|
||||
if l > 0 {
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
if m.VoteExtension != nil {
|
||||
l = m.VoteExtension.Size()
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
return n
|
||||
}
|
||||
|
||||
func (m *VoteExtension) Size() (n int) {
|
||||
if m == nil {
|
||||
return 0
|
||||
}
|
||||
var l int
|
||||
_ = l
|
||||
l = len(m.AppDataToSign)
|
||||
l = len(m.Extension)
|
||||
if l > 0 {
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
l = len(m.AppDataSelfAuthenticating)
|
||||
if l > 0 {
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
return n
|
||||
}
|
||||
|
||||
func (m *VoteExtensionToSign) Size() (n int) {
|
||||
if m == nil {
|
||||
return 0
|
||||
}
|
||||
var l int
|
||||
_ = l
|
||||
l = len(m.AppDataToSign)
|
||||
l = len(m.ExtensionSignature)
|
||||
if l > 0 {
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
@@ -2317,10 +2114,6 @@ func (m *CommitSig) Size() (n int) {
|
||||
if l > 0 {
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
if m.VoteExtension != nil {
|
||||
l = m.VoteExtension.Size()
|
||||
n += 1 + l + sovTypes(uint64(l))
|
||||
}
|
||||
return n
|
||||
}
|
||||
|
||||
@@ -3618,93 +3411,7 @@ func (m *Vote) Unmarshal(dAtA []byte) error {
|
||||
iNdEx = postIndex
|
||||
case 9:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field VoteExtension", wireType)
|
||||
}
|
||||
var msglen int
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
msglen |= int(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
if msglen < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
postIndex := iNdEx + msglen
|
||||
if postIndex < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
if m.VoteExtension == nil {
|
||||
m.VoteExtension = &VoteExtension{}
|
||||
}
|
||||
if err := m.VoteExtension.Unmarshal(dAtA[iNdEx:postIndex]); err != nil {
|
||||
return err
|
||||
}
|
||||
iNdEx = postIndex
|
||||
default:
|
||||
iNdEx = preIndex
|
||||
skippy, err := skipTypes(dAtA[iNdEx:])
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if (skippy < 0) || (iNdEx+skippy) < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
if (iNdEx + skippy) > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
iNdEx += skippy
|
||||
}
|
||||
}
|
||||
|
||||
if iNdEx > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
return nil
|
||||
}
|
||||
func (m *VoteExtension) Unmarshal(dAtA []byte) error {
|
||||
l := len(dAtA)
|
||||
iNdEx := 0
|
||||
for iNdEx < l {
|
||||
preIndex := iNdEx
|
||||
var wire uint64
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
wire |= uint64(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
fieldNum := int32(wire >> 3)
|
||||
wireType := int(wire & 0x7)
|
||||
if wireType == 4 {
|
||||
return fmt.Errorf("proto: VoteExtension: wiretype end group for non-group")
|
||||
}
|
||||
if fieldNum <= 0 {
|
||||
return fmt.Errorf("proto: VoteExtension: illegal tag %d (wire type %d)", fieldNum, wire)
|
||||
}
|
||||
switch fieldNum {
|
||||
case 1:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field AppDataToSign", wireType)
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field Extension", wireType)
|
||||
}
|
||||
var byteLen int
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
@@ -3731,14 +3438,14 @@ func (m *VoteExtension) Unmarshal(dAtA []byte) error {
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
m.AppDataToSign = append(m.AppDataToSign[:0], dAtA[iNdEx:postIndex]...)
|
||||
if m.AppDataToSign == nil {
|
||||
m.AppDataToSign = []byte{}
|
||||
m.Extension = append(m.Extension[:0], dAtA[iNdEx:postIndex]...)
|
||||
if m.Extension == nil {
|
||||
m.Extension = []byte{}
|
||||
}
|
||||
iNdEx = postIndex
|
||||
case 2:
|
||||
case 10:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field AppDataSelfAuthenticating", wireType)
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field ExtensionSignature", wireType)
|
||||
}
|
||||
var byteLen int
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
@@ -3765,93 +3472,9 @@ func (m *VoteExtension) Unmarshal(dAtA []byte) error {
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
m.AppDataSelfAuthenticating = append(m.AppDataSelfAuthenticating[:0], dAtA[iNdEx:postIndex]...)
|
||||
if m.AppDataSelfAuthenticating == nil {
|
||||
m.AppDataSelfAuthenticating = []byte{}
|
||||
}
|
||||
iNdEx = postIndex
|
||||
default:
|
||||
iNdEx = preIndex
|
||||
skippy, err := skipTypes(dAtA[iNdEx:])
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if (skippy < 0) || (iNdEx+skippy) < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
if (iNdEx + skippy) > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
iNdEx += skippy
|
||||
}
|
||||
}
|
||||
|
||||
if iNdEx > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
return nil
|
||||
}
|
||||
func (m *VoteExtensionToSign) Unmarshal(dAtA []byte) error {
|
||||
l := len(dAtA)
|
||||
iNdEx := 0
|
||||
for iNdEx < l {
|
||||
preIndex := iNdEx
|
||||
var wire uint64
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
wire |= uint64(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
fieldNum := int32(wire >> 3)
|
||||
wireType := int(wire & 0x7)
|
||||
if wireType == 4 {
|
||||
return fmt.Errorf("proto: VoteExtensionToSign: wiretype end group for non-group")
|
||||
}
|
||||
if fieldNum <= 0 {
|
||||
return fmt.Errorf("proto: VoteExtensionToSign: illegal tag %d (wire type %d)", fieldNum, wire)
|
||||
}
|
||||
switch fieldNum {
|
||||
case 1:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field AppDataToSign", wireType)
|
||||
}
|
||||
var byteLen int
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
byteLen |= int(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
if byteLen < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
postIndex := iNdEx + byteLen
|
||||
if postIndex < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
m.AppDataToSign = append(m.AppDataToSign[:0], dAtA[iNdEx:postIndex]...)
|
||||
if m.AppDataToSign == nil {
|
||||
m.AppDataToSign = []byte{}
|
||||
m.ExtensionSignature = append(m.ExtensionSignature[:0], dAtA[iNdEx:postIndex]...)
|
||||
if m.ExtensionSignature == nil {
|
||||
m.ExtensionSignature = []byte{}
|
||||
}
|
||||
iNdEx = postIndex
|
||||
default:
|
||||
@@ -4179,42 +3802,6 @@ func (m *CommitSig) Unmarshal(dAtA []byte) error {
|
||||
m.Signature = []byte{}
|
||||
}
|
||||
iNdEx = postIndex
|
||||
case 5:
|
||||
if wireType != 2 {
|
||||
return fmt.Errorf("proto: wrong wireType = %d for field VoteExtension", wireType)
|
||||
}
|
||||
var msglen int
|
||||
for shift := uint(0); ; shift += 7 {
|
||||
if shift >= 64 {
|
||||
return ErrIntOverflowTypes
|
||||
}
|
||||
if iNdEx >= l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
b := dAtA[iNdEx]
|
||||
iNdEx++
|
||||
msglen |= int(b&0x7F) << shift
|
||||
if b < 0x80 {
|
||||
break
|
||||
}
|
||||
}
|
||||
if msglen < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
postIndex := iNdEx + msglen
|
||||
if postIndex < 0 {
|
||||
return ErrInvalidLengthTypes
|
||||
}
|
||||
if postIndex > l {
|
||||
return io.ErrUnexpectedEOF
|
||||
}
|
||||
if m.VoteExtension == nil {
|
||||
m.VoteExtension = &VoteExtensionToSign{}
|
||||
}
|
||||
if err := m.VoteExtension.Unmarshal(dAtA[iNdEx:postIndex]); err != nil {
|
||||
return err
|
||||
}
|
||||
iNdEx = postIndex
|
||||
default:
|
||||
iNdEx = preIndex
|
||||
skippy, err := skipTypes(dAtA[iNdEx:])
|
||||
|
||||
@@ -112,7 +112,15 @@ message Vote {
|
||||
[(gogoproto.nullable) = false, (gogoproto.stdtime) = true];
|
||||
bytes validator_address = 6;
|
||||
int32 validator_index = 7;
|
||||
bytes signature = 8;
|
||||
// Vote signature by the validator if they participated in consensus for the
|
||||
// associated block.
|
||||
bytes signature = 8;
|
||||
// Vote extension provided by the application. Only valid for precommit
|
||||
// messages.
|
||||
bytes extension = 9;
|
||||
// Vote extension signature by the validator if they participated in
|
||||
// consensus for the associated block.
|
||||
bytes extension_signature = 10;
|
||||
}
|
||||
|
||||
// Commit contains the evidence that a block was committed by a set of
|
||||
|
||||
@@ -189,6 +189,5 @@ type MissedItemsError struct {
|
||||
|
||||
// Error satisfies the error interface.
|
||||
func (e *MissedItemsError) Error() string {
|
||||
return fmt.Sprintf("missed events matching %q between %q and %q",
|
||||
e.Query, e.NewestSeen, e.OldestPresent)
|
||||
return fmt.Sprintf("missed events matching %q between %q and %q", e.Query, e.NewestSeen, e.OldestPresent)
|
||||
}
|
||||
|
||||
+14
-69
@@ -207,19 +207,11 @@ func (c *baseRPCClient) ABCIInfo(ctx context.Context) (*coretypes.ResultABCIInfo
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) ABCIQuery(
|
||||
ctx context.Context,
|
||||
path string,
|
||||
data bytes.HexBytes,
|
||||
) (*coretypes.ResultABCIQuery, error) {
|
||||
func (c *baseRPCClient) ABCIQuery(ctx context.Context, path string, data bytes.HexBytes) (*coretypes.ResultABCIQuery, error) {
|
||||
return c.ABCIQueryWithOptions(ctx, path, data, rpcclient.DefaultABCIQueryOptions)
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) ABCIQueryWithOptions(
|
||||
ctx context.Context,
|
||||
path string,
|
||||
data bytes.HexBytes,
|
||||
opts rpcclient.ABCIQueryOptions) (*coretypes.ResultABCIQuery, error) {
|
||||
func (c *baseRPCClient) ABCIQueryWithOptions(ctx context.Context, path string, data bytes.HexBytes, opts rpcclient.ABCIQueryOptions) (*coretypes.ResultABCIQuery, error) {
|
||||
result := new(coretypes.ResultABCIQuery)
|
||||
if err := c.caller.Call(ctx, "abci_query", abciQueryArgs{
|
||||
Path: path,
|
||||
@@ -232,10 +224,7 @@ func (c *baseRPCClient) ABCIQueryWithOptions(
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) BroadcastTxCommit(
|
||||
ctx context.Context,
|
||||
tx types.Tx,
|
||||
) (*coretypes.ResultBroadcastTxCommit, error) {
|
||||
func (c *baseRPCClient) BroadcastTxCommit(ctx context.Context, tx types.Tx) (*coretypes.ResultBroadcastTxCommit, error) {
|
||||
result := new(coretypes.ResultBroadcastTxCommit)
|
||||
if err := c.caller.Call(ctx, "broadcast_tx_commit", txArgs{Tx: tx}, result); err != nil {
|
||||
return nil, err
|
||||
@@ -243,25 +232,15 @@ func (c *baseRPCClient) BroadcastTxCommit(
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) BroadcastTxAsync(
|
||||
ctx context.Context,
|
||||
tx types.Tx,
|
||||
) (*coretypes.ResultBroadcastTx, error) {
|
||||
func (c *baseRPCClient) BroadcastTxAsync(ctx context.Context, tx types.Tx) (*coretypes.ResultBroadcastTx, error) {
|
||||
return c.broadcastTX(ctx, "broadcast_tx_async", tx)
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) BroadcastTxSync(
|
||||
ctx context.Context,
|
||||
tx types.Tx,
|
||||
) (*coretypes.ResultBroadcastTx, error) {
|
||||
func (c *baseRPCClient) BroadcastTxSync(ctx context.Context, tx types.Tx) (*coretypes.ResultBroadcastTx, error) {
|
||||
return c.broadcastTX(ctx, "broadcast_tx_sync", tx)
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) broadcastTX(
|
||||
ctx context.Context,
|
||||
route string,
|
||||
tx types.Tx,
|
||||
) (*coretypes.ResultBroadcastTx, error) {
|
||||
func (c *baseRPCClient) broadcastTX(ctx context.Context, route string, tx types.Tx) (*coretypes.ResultBroadcastTx, error) {
|
||||
result := new(coretypes.ResultBroadcastTx)
|
||||
if err := c.caller.Call(ctx, route, txArgs{Tx: tx}, result); err != nil {
|
||||
return nil, err
|
||||
@@ -269,11 +248,7 @@ func (c *baseRPCClient) broadcastTX(
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) UnconfirmedTxs(
|
||||
ctx context.Context,
|
||||
page *int,
|
||||
perPage *int,
|
||||
) (*coretypes.ResultUnconfirmedTxs, error) {
|
||||
func (c *baseRPCClient) UnconfirmedTxs(ctx context.Context, page *int, perPage *int) (*coretypes.ResultUnconfirmedTxs, error) {
|
||||
result := new(coretypes.ResultUnconfirmedTxs)
|
||||
|
||||
if err := c.caller.Call(ctx, "unconfirmed_txs", unconfirmedArgs{Page: page, PerPage: perPage}, result); err != nil {
|
||||
@@ -329,10 +304,7 @@ func (c *baseRPCClient) ConsensusState(ctx context.Context) (*coretypes.ResultCo
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) ConsensusParams(
|
||||
ctx context.Context,
|
||||
height *int64,
|
||||
) (*coretypes.ResultConsensusParams, error) {
|
||||
func (c *baseRPCClient) ConsensusParams(ctx context.Context, height *int64) (*coretypes.ResultConsensusParams, error) {
|
||||
result := new(coretypes.ResultConsensusParams)
|
||||
if err := c.caller.Call(ctx, "consensus_params", heightArgs{Height: height}, result); err != nil {
|
||||
return nil, err
|
||||
@@ -356,11 +328,7 @@ func (c *baseRPCClient) Health(ctx context.Context) (*coretypes.ResultHealth, er
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) BlockchainInfo(
|
||||
ctx context.Context,
|
||||
minHeight,
|
||||
maxHeight int64,
|
||||
) (*coretypes.ResultBlockchainInfo, error) {
|
||||
func (c *baseRPCClient) BlockchainInfo(ctx context.Context, minHeight, maxHeight int64) (*coretypes.ResultBlockchainInfo, error) {
|
||||
result := new(coretypes.ResultBlockchainInfo)
|
||||
if err := c.caller.Call(ctx, "blockchain", blockchainInfoArgs{
|
||||
MinHeight: minHeight,
|
||||
@@ -403,10 +371,7 @@ func (c *baseRPCClient) BlockByHash(ctx context.Context, hash bytes.HexBytes) (*
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) BlockResults(
|
||||
ctx context.Context,
|
||||
height *int64,
|
||||
) (*coretypes.ResultBlockResults, error) {
|
||||
func (c *baseRPCClient) BlockResults(ctx context.Context, height *int64) (*coretypes.ResultBlockResults, error) {
|
||||
result := new(coretypes.ResultBlockResults)
|
||||
if err := c.caller.Call(ctx, "block_results", heightArgs{Height: height}, result); err != nil {
|
||||
return nil, err
|
||||
@@ -446,14 +411,7 @@ func (c *baseRPCClient) Tx(ctx context.Context, hash bytes.HexBytes, prove bool)
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) TxSearch(
|
||||
ctx context.Context,
|
||||
query string,
|
||||
prove bool,
|
||||
page,
|
||||
perPage *int,
|
||||
orderBy string,
|
||||
) (*coretypes.ResultTxSearch, error) {
|
||||
func (c *baseRPCClient) TxSearch(ctx context.Context, query string, prove bool, page, perPage *int, orderBy string) (*coretypes.ResultTxSearch, error) {
|
||||
result := new(coretypes.ResultTxSearch)
|
||||
if err := c.caller.Call(ctx, "tx_search", searchArgs{
|
||||
Query: query,
|
||||
@@ -468,12 +426,7 @@ func (c *baseRPCClient) TxSearch(
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) BlockSearch(
|
||||
ctx context.Context,
|
||||
query string,
|
||||
page, perPage *int,
|
||||
orderBy string,
|
||||
) (*coretypes.ResultBlockSearch, error) {
|
||||
func (c *baseRPCClient) BlockSearch(ctx context.Context, query string, page, perPage *int, orderBy string) (*coretypes.ResultBlockSearch, error) {
|
||||
result := new(coretypes.ResultBlockSearch)
|
||||
if err := c.caller.Call(ctx, "block_search", searchArgs{
|
||||
Query: query,
|
||||
@@ -487,12 +440,7 @@ func (c *baseRPCClient) BlockSearch(
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) Validators(
|
||||
ctx context.Context,
|
||||
height *int64,
|
||||
page,
|
||||
perPage *int,
|
||||
) (*coretypes.ResultValidators, error) {
|
||||
func (c *baseRPCClient) Validators(ctx context.Context, height *int64, page, perPage *int) (*coretypes.ResultValidators, error) {
|
||||
result := new(coretypes.ResultValidators)
|
||||
if err := c.caller.Call(ctx, "validators", validatorArgs{
|
||||
Height: height,
|
||||
@@ -504,10 +452,7 @@ func (c *baseRPCClient) Validators(
|
||||
return result, nil
|
||||
}
|
||||
|
||||
func (c *baseRPCClient) BroadcastEvidence(
|
||||
ctx context.Context,
|
||||
ev types.Evidence,
|
||||
) (*coretypes.ResultBroadcastEvidence, error) {
|
||||
func (c *baseRPCClient) BroadcastEvidence(ctx context.Context, ev types.Evidence) (*coretypes.ResultBroadcastEvidence, error) {
|
||||
result := new(coretypes.ResultBroadcastEvidence)
|
||||
if err := c.caller.Call(ctx, "broadcast_evidence", evidenceArgs{
|
||||
Evidence: coretypes.Evidence{Value: ev},
|
||||
|
||||
@@ -107,6 +107,7 @@ func (w *wsEvents) Unsubscribe(ctx context.Context, subscriber, query string) er
|
||||
}
|
||||
|
||||
w.mtx.Lock()
|
||||
defer w.mtx.Unlock()
|
||||
info, ok := w.subscriptions[query]
|
||||
if ok {
|
||||
if info.id != "" {
|
||||
@@ -114,7 +115,6 @@ func (w *wsEvents) Unsubscribe(ctx context.Context, subscriber, query string) er
|
||||
}
|
||||
delete(w.subscriptions, info.query)
|
||||
}
|
||||
w.mtx.Unlock()
|
||||
|
||||
return nil
|
||||
}
|
||||
@@ -129,8 +129,8 @@ func (w *wsEvents) UnsubscribeAll(ctx context.Context, subscriber string) error
|
||||
}
|
||||
|
||||
w.mtx.Lock()
|
||||
defer w.mtx.Unlock()
|
||||
w.subscriptions = make(map[string]*wsSubscription)
|
||||
w.mtx.Unlock()
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
+20
-32
@@ -78,11 +78,7 @@ func (c *Local) ABCIQuery(ctx context.Context, path string, data bytes.HexBytes)
|
||||
return c.ABCIQueryWithOptions(ctx, path, data, rpcclient.DefaultABCIQueryOptions)
|
||||
}
|
||||
|
||||
func (c *Local) ABCIQueryWithOptions(
|
||||
ctx context.Context,
|
||||
path string,
|
||||
data bytes.HexBytes,
|
||||
opts rpcclient.ABCIQueryOptions) (*coretypes.ResultABCIQuery, error) {
|
||||
func (c *Local) ABCIQueryWithOptions(ctx context.Context, path string, data bytes.HexBytes, opts rpcclient.ABCIQueryOptions) (*coretypes.ResultABCIQuery, error) {
|
||||
return c.env.ABCIQuery(ctx, path, data, opts.Height, opts.Prove)
|
||||
}
|
||||
|
||||
@@ -189,23 +185,11 @@ func (c *Local) Tx(ctx context.Context, hash bytes.HexBytes, prove bool) (*coret
|
||||
return c.env.Tx(ctx, hash, prove)
|
||||
}
|
||||
|
||||
func (c *Local) TxSearch(
|
||||
ctx context.Context,
|
||||
queryString string,
|
||||
prove bool,
|
||||
page,
|
||||
perPage *int,
|
||||
orderBy string,
|
||||
) (*coretypes.ResultTxSearch, error) {
|
||||
func (c *Local) TxSearch(ctx context.Context, queryString string, prove bool, page, perPage *int, orderBy string) (*coretypes.ResultTxSearch, error) {
|
||||
return c.env.TxSearch(ctx, queryString, prove, page, perPage, orderBy)
|
||||
}
|
||||
|
||||
func (c *Local) BlockSearch(
|
||||
ctx context.Context,
|
||||
queryString string,
|
||||
page, perPage *int,
|
||||
orderBy string,
|
||||
) (*coretypes.ResultBlockSearch, error) {
|
||||
func (c *Local) BlockSearch(ctx context.Context, queryString string, page, perPage *int, orderBy string) (*coretypes.ResultBlockSearch, error) {
|
||||
return c.env.BlockSearch(ctx, queryString, page, perPage, orderBy)
|
||||
}
|
||||
|
||||
@@ -213,11 +197,7 @@ func (c *Local) BroadcastEvidence(ctx context.Context, ev types.Evidence) (*core
|
||||
return c.env.BroadcastEvidence(ctx, coretypes.Evidence{Value: ev})
|
||||
}
|
||||
|
||||
func (c *Local) Subscribe(
|
||||
ctx context.Context,
|
||||
subscriber,
|
||||
queryString string,
|
||||
capacity ...int) (out <-chan coretypes.ResultEvent, err error) {
|
||||
func (c *Local) Subscribe(ctx context.Context, subscriber, queryString string, capacity ...int) (<-chan coretypes.ResultEvent, error) {
|
||||
q, err := query.New(queryString)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed to parse query: %w", err)
|
||||
@@ -251,12 +231,7 @@ func (c *Local) Subscribe(
|
||||
return outc, nil
|
||||
}
|
||||
|
||||
func (c *Local) eventsRoutine(
|
||||
ctx context.Context,
|
||||
sub eventbus.Subscription,
|
||||
subArgs pubsub.SubscribeArgs,
|
||||
outc chan<- coretypes.ResultEvent,
|
||||
) {
|
||||
func (c *Local) eventsRoutine(ctx context.Context, sub eventbus.Subscription, subArgs pubsub.SubscribeArgs, outc chan<- coretypes.ResultEvent) {
|
||||
qstr := subArgs.Query.String()
|
||||
for {
|
||||
msg, err := sub.Next(ctx)
|
||||
@@ -271,17 +246,24 @@ func (c *Local) eventsRoutine(
|
||||
}
|
||||
continue
|
||||
}
|
||||
outc <- coretypes.ResultEvent{
|
||||
select {
|
||||
case outc <- coretypes.ResultEvent{
|
||||
SubscriptionID: msg.SubscriptionID(),
|
||||
Query: qstr,
|
||||
Data: msg.Data(),
|
||||
Events: msg.Events(),
|
||||
}:
|
||||
case <-ctx.Done():
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Try to resubscribe with exponential backoff.
|
||||
func (c *Local) resubscribe(ctx context.Context, subArgs pubsub.SubscribeArgs) eventbus.Subscription {
|
||||
timer := time.NewTimer(0)
|
||||
defer timer.Stop()
|
||||
|
||||
attempts := 0
|
||||
for {
|
||||
if !c.IsRunning() {
|
||||
@@ -294,7 +276,13 @@ func (c *Local) resubscribe(ctx context.Context, subArgs pubsub.SubscribeArgs) e
|
||||
}
|
||||
|
||||
attempts++
|
||||
time.Sleep((10 << uint(attempts)) * time.Millisecond) // 10ms -> 20ms -> 40ms
|
||||
timer.Reset((10 << uint(attempts)) * time.Millisecond) // 10ms -> 20ms -> 40ms
|
||||
select {
|
||||
case <-timer.C:
|
||||
continue
|
||||
case <-ctx.Done():
|
||||
return nil
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -46,13 +46,7 @@ func DefaultConfig() *Config {
|
||||
|
||||
// Serve creates a http.Server and calls Serve with the given listener. It
|
||||
// wraps handler to recover panics and limit the request body size.
|
||||
func Serve(
|
||||
ctx context.Context,
|
||||
listener net.Listener,
|
||||
handler http.Handler,
|
||||
logger log.Logger,
|
||||
config *Config,
|
||||
) error {
|
||||
func Serve(ctx context.Context, listener net.Listener, handler http.Handler, logger log.Logger, config *Config) error {
|
||||
logger.Info(fmt.Sprintf("Starting RPC HTTP server on %s", listener.Addr()))
|
||||
h := recoverAndLogHandler(MaxBytesHandler(handler, config.MaxBodyBytes), logger)
|
||||
s := &http.Server{
|
||||
@@ -83,19 +77,14 @@ func Serve(
|
||||
// Serve creates a http.Server and calls ServeTLS with the given listener,
|
||||
// certFile and keyFile. It wraps handler to recover panics and limit the
|
||||
// request body size.
|
||||
func ServeTLS(
|
||||
ctx context.Context,
|
||||
listener net.Listener,
|
||||
handler http.Handler,
|
||||
certFile, keyFile string,
|
||||
logger log.Logger,
|
||||
config *Config,
|
||||
) error {
|
||||
logger.Info(fmt.Sprintf("Starting RPC HTTPS server on %s (cert: %q, key: %q)",
|
||||
listener.Addr(), certFile, keyFile))
|
||||
h := recoverAndLogHandler(MaxBytesHandler(handler, config.MaxBodyBytes), logger)
|
||||
func ServeTLS(ctx context.Context, listener net.Listener, handler http.Handler, certFile, keyFile string, logger log.Logger, config *Config) error {
|
||||
logger.Info("Starting RPC HTTPS server",
|
||||
"listenterAddr", listener.Addr(),
|
||||
"certFile", certFile,
|
||||
"keyFile", keyFile)
|
||||
|
||||
s := &http.Server{
|
||||
Handler: h,
|
||||
Handler: recoverAndLogHandler(MaxBytesHandler(handler, config.MaxBodyBytes), logger),
|
||||
ReadTimeout: config.ReadTimeout,
|
||||
WriteTimeout: config.WriteTimeout,
|
||||
MaxHeaderBytes: config.MaxHeaderBytes,
|
||||
|
||||
@@ -36,11 +36,7 @@ type WebsocketManager struct {
|
||||
|
||||
// NewWebsocketManager returns a new WebsocketManager that passes a map of
|
||||
// functions, connection options and logger to new WS connections.
|
||||
func NewWebsocketManager(
|
||||
logger log.Logger,
|
||||
funcMap map[string]*RPCFunc,
|
||||
wsConnOptions ...func(*wsConnection),
|
||||
) *WebsocketManager {
|
||||
func NewWebsocketManager(logger log.Logger, funcMap map[string]*RPCFunc, wsConnOptions ...func(*wsConnection)) *WebsocketManager {
|
||||
return &WebsocketManager{
|
||||
funcMap: funcMap,
|
||||
Upgrader: websocket.Upgrader{
|
||||
@@ -137,12 +133,7 @@ type wsConnection struct {
|
||||
// description of how to configure ping period and pong wait time. NOTE: if the
|
||||
// write buffer is full, pongs may be dropped, which may cause clients to
|
||||
// disconnect. see https://github.com/gorilla/websocket/issues/97
|
||||
func newWSConnection(
|
||||
baseConn *websocket.Conn,
|
||||
funcMap map[string]*RPCFunc,
|
||||
logger log.Logger,
|
||||
options ...func(*wsConnection),
|
||||
) *wsConnection {
|
||||
func newWSConnection(baseConn *websocket.Conn, funcMap map[string]*RPCFunc, logger log.Logger, options ...func(*wsConnection)) *wsConnection {
|
||||
wsc := &wsConnection{
|
||||
Logger: logger,
|
||||
remoteAddr: baseConn.RemoteAddr().String(),
|
||||
|
||||
+2
-2
@@ -12,9 +12,9 @@ cp ./proto/tendermint/types/types.proto.intermediate ./proto/tendermint/types/ty
|
||||
|
||||
MODNAME="$(go list -m)"
|
||||
find ./proto/tendermint -name '*.proto' -not -path "./proto/tendermint/abci/types.proto" \
|
||||
-exec sh ./scripts/protopackage.sh {} "$MODNAME" ';'
|
||||
-exec ./scripts/protopackage.sh {} "$MODNAME" ';'
|
||||
|
||||
sh ./scripts/protopackage.sh ./proto/tendermint/abci/types.proto $MODNAME "abci/types"
|
||||
./scripts/protopackage.sh ./proto/tendermint/abci/types.proto $MODNAME "abci/types"
|
||||
|
||||
make proto-gen
|
||||
|
||||
|
||||
@@ -25,6 +25,7 @@ func TestGuessConfigVersion(t *testing.T) {
|
||||
path, want string
|
||||
}{
|
||||
{"testdata/non-config.toml", ""},
|
||||
{"testdata/v30-config.toml", ""},
|
||||
{"testdata/v31-config.toml", ""},
|
||||
{"testdata/v32-config.toml", "v0.32"},
|
||||
{"testdata/v33-config.toml", "v0.33"},
|
||||
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
-M consensus.blocktime-iota
|
||||
+M mempool.max-txs-bytes
|
||||
+M rpc.max-subscription-clients
|
||||
+M rpc.max-subscriptions-per-client
|
||||
+M rpc.timeout-broadcast-tx-commit
|
||||
+M rpc.tls-cert-file
|
||||
+M rpc.tls-key-file
|
||||
+252
@@ -0,0 +1,252 @@
|
||||
# This is a TOML config file.
|
||||
# For more information, see https://github.com/toml-lang/toml
|
||||
|
||||
##### main base config options #####
|
||||
|
||||
# TCP or UNIX socket address of the ABCI application,
|
||||
# or the name of an ABCI application compiled in with the Tendermint binary
|
||||
proxy_app = "tcp://127.0.0.1:26658"
|
||||
|
||||
# A custom human readable name for this node
|
||||
moniker = "localhost"
|
||||
|
||||
# If this node is many blocks behind the tip of the chain, FastSync
|
||||
# allows them to catchup quickly by downloading blocks in parallel
|
||||
# and verifying their commits
|
||||
fast_sync = true
|
||||
|
||||
# Database backend: leveldb | memdb | cleveldb
|
||||
db_backend = "leveldb"
|
||||
|
||||
# Database directory
|
||||
db_dir = "data"
|
||||
|
||||
# Output level for logging, including package level options
|
||||
log_level = "main:info,state:info,*:error"
|
||||
|
||||
# Output format: 'plain' (colored text) or 'json'
|
||||
log_format = "plain"
|
||||
|
||||
##### additional base config options #####
|
||||
|
||||
# Path to the JSON file containing the initial validator set and other meta data
|
||||
genesis_file = "config/genesis.json"
|
||||
|
||||
# Path to the JSON file containing the private key to use as a validator in the consensus protocol
|
||||
priv_validator_key_file = "config/priv_validator_key.json"
|
||||
|
||||
# Path to the JSON file containing the last sign state of a validator
|
||||
priv_validator_state_file = "data/priv_validator_state.json"
|
||||
|
||||
# TCP or UNIX socket address for Tendermint to listen on for
|
||||
# connections from an external PrivValidator process
|
||||
priv_validator_laddr = ""
|
||||
|
||||
# Path to the JSON file containing the private key to use for node authentication in the p2p protocol
|
||||
node_key_file = "config/node_key.json"
|
||||
|
||||
# Mechanism to connect to the ABCI application: socket | grpc
|
||||
abci = "socket"
|
||||
|
||||
# TCP or UNIX socket address for the profiling server to listen on
|
||||
prof_laddr = ""
|
||||
|
||||
# If true, query the ABCI app on connecting to a new peer
|
||||
# so the app can decide if we should keep the connection or not
|
||||
filter_peers = false
|
||||
|
||||
##### advanced configuration options #####
|
||||
|
||||
##### rpc server configuration options #####
|
||||
[rpc]
|
||||
|
||||
# TCP or UNIX socket address for the RPC server to listen on
|
||||
laddr = "tcp://0.0.0.0:26657"
|
||||
|
||||
# A list of origins a cross-domain request can be executed from
|
||||
# Default value '[]' disables cors support
|
||||
# Use '["*"]' to allow any origin
|
||||
cors_allowed_origins = []
|
||||
|
||||
# A list of methods the client is allowed to use with cross-domain requests
|
||||
cors_allowed_methods = ["HEAD", "GET", "POST", ]
|
||||
|
||||
# A list of non simple headers the client is allowed to use with cross-domain requests
|
||||
cors_allowed_headers = ["Origin", "Accept", "Content-Type", "X-Requested-With", "X-Server-Time", ]
|
||||
|
||||
# TCP or UNIX socket address for the gRPC server to listen on
|
||||
# NOTE: This server only supports /broadcast_tx_commit
|
||||
grpc_laddr = ""
|
||||
|
||||
# Maximum number of simultaneous connections.
|
||||
# Does not include RPC (HTTP&WebSocket) connections. See max_open_connections
|
||||
# If you want to accept a larger number than the default, make sure
|
||||
# you increase your OS limits.
|
||||
# 0 - unlimited.
|
||||
# Should be < {ulimit -Sn} - {MaxNumInboundPeers} - {MaxNumOutboundPeers} - {N of wal, db and other open files}
|
||||
# 1024 - 40 - 10 - 50 = 924 = ~900
|
||||
grpc_max_open_connections = 900
|
||||
|
||||
# Activate unsafe RPC commands like /dial_seeds and /unsafe_flush_mempool
|
||||
unsafe = false
|
||||
|
||||
# Maximum number of simultaneous connections (including WebSocket).
|
||||
# Does not include gRPC connections. See grpc_max_open_connections
|
||||
# If you want to accept a larger number than the default, make sure
|
||||
# you increase your OS limits.
|
||||
# 0 - unlimited.
|
||||
# Should be < {ulimit -Sn} - {MaxNumInboundPeers} - {MaxNumOutboundPeers} - {N of wal, db and other open files}
|
||||
# 1024 - 40 - 10 - 50 = 924 = ~900
|
||||
max_open_connections = 900
|
||||
|
||||
##### peer to peer configuration options #####
|
||||
[p2p]
|
||||
|
||||
# Address to listen for incoming connections
|
||||
laddr = "tcp://0.0.0.0:26656"
|
||||
|
||||
# Address to advertise to peers for them to dial
|
||||
# If empty, will use the same port as the laddr,
|
||||
# and will introspect on the listener or use UPnP
|
||||
# to figure out the address.
|
||||
external_address = ""
|
||||
|
||||
# Comma separated list of seed nodes to connect to
|
||||
seeds = ""
|
||||
|
||||
# Comma separated list of nodes to keep persistent connections to
|
||||
persistent_peers = ""
|
||||
|
||||
# UPNP port forwarding
|
||||
upnp = false
|
||||
|
||||
# Path to address book
|
||||
addr_book_file = "config/addrbook.json"
|
||||
|
||||
# Set true for strict address routability rules
|
||||
# Set false for private or local networks
|
||||
addr_book_strict = true
|
||||
|
||||
# Maximum number of inbound peers
|
||||
max_num_inbound_peers = 40
|
||||
|
||||
# Maximum number of outbound peers to connect to, excluding persistent peers
|
||||
max_num_outbound_peers = 10
|
||||
|
||||
# Time to wait before flushing messages out on the connection
|
||||
flush_throttle_timeout = "100ms"
|
||||
|
||||
# Maximum size of a message packet payload, in bytes
|
||||
max_packet_msg_payload_size = 1024
|
||||
|
||||
# Rate at which packets can be sent, in bytes/second
|
||||
send_rate = 5120000
|
||||
|
||||
# Rate at which packets can be received, in bytes/second
|
||||
recv_rate = 5120000
|
||||
|
||||
# Set true to enable the peer-exchange reactor
|
||||
pex = true
|
||||
|
||||
# Seed mode, in which node constantly crawls the network and looks for
|
||||
# peers. If another node asks it for addresses, it responds and disconnects.
|
||||
#
|
||||
# Does not work if the peer-exchange reactor is disabled.
|
||||
seed_mode = false
|
||||
|
||||
# Comma separated list of peer IDs to keep private (will not be gossiped to other peers)
|
||||
private_peer_ids = ""
|
||||
|
||||
# Toggle to disable guard against peers connecting from the same ip.
|
||||
allow_duplicate_ip = false
|
||||
|
||||
# Peer connection configuration.
|
||||
handshake_timeout = "20s"
|
||||
dial_timeout = "3s"
|
||||
|
||||
##### mempool configuration options #####
|
||||
[mempool]
|
||||
|
||||
recheck = true
|
||||
broadcast = true
|
||||
wal_dir = ""
|
||||
|
||||
# size of the mempool
|
||||
size = 5000
|
||||
|
||||
# size of the cache (used to filter transactions we saw earlier)
|
||||
cache_size = 10000
|
||||
|
||||
##### consensus configuration options #####
|
||||
[consensus]
|
||||
|
||||
wal_file = "data/cs.wal/wal"
|
||||
|
||||
timeout_propose = "3s"
|
||||
timeout_propose_delta = "500ms"
|
||||
timeout_prevote = "1s"
|
||||
timeout_prevote_delta = "500ms"
|
||||
timeout_precommit = "1s"
|
||||
timeout_precommit_delta = "500ms"
|
||||
timeout_commit = "1s"
|
||||
|
||||
# Make progress as soon as we have all the precommits (as if TimeoutCommit = 0)
|
||||
skip_timeout_commit = false
|
||||
|
||||
# EmptyBlocks mode and possible interval between empty blocks
|
||||
create_empty_blocks = true
|
||||
create_empty_blocks_interval = "0s"
|
||||
|
||||
# Reactor sleep duration parameters
|
||||
peer_gossip_sleep_duration = "100ms"
|
||||
peer_query_maj23_sleep_duration = "2s"
|
||||
|
||||
# Block time parameters. Corresponds to the minimum time increment between consecutive blocks.
|
||||
blocktime_iota = "1s"
|
||||
|
||||
##### transactions indexer configuration options #####
|
||||
[tx_index]
|
||||
|
||||
# What indexer to use for transactions
|
||||
#
|
||||
# Options:
|
||||
# 1) "null"
|
||||
# 2) "kv" (default) - the simplest possible indexer, backed by key-value storage (defaults to levelDB; see DBBackend).
|
||||
indexer = "kv"
|
||||
|
||||
# Comma-separated list of tags to index (by default the only tag is "tx.hash")
|
||||
#
|
||||
# You can also index transactions by height by adding "tx.height" tag here.
|
||||
#
|
||||
# It's recommended to index only a subset of tags due to possible memory
|
||||
# bloat. This is, of course, depends on the indexer's DB and the volume of
|
||||
# transactions.
|
||||
index_tags = ""
|
||||
|
||||
# When set to true, tells indexer to index all tags (predefined tags:
|
||||
# "tx.hash", "tx.height" and all tags from DeliverTx responses).
|
||||
#
|
||||
# Note this may be not desirable (see the comment above). IndexTags has a
|
||||
# precedence over IndexAllTags (i.e. when given both, IndexTags will be
|
||||
# indexed).
|
||||
index_all_tags = false
|
||||
|
||||
##### instrumentation configuration options #####
|
||||
[instrumentation]
|
||||
|
||||
# When true, Prometheus metrics are served under /metrics on
|
||||
# PrometheusListenAddr.
|
||||
# Check out the documentation for the list of available metrics.
|
||||
prometheus = false
|
||||
|
||||
# Address to listen for Prometheus collector(s) connections
|
||||
prometheus_listen_addr = ":26660"
|
||||
|
||||
# Maximum number of simultaneous connections.
|
||||
# If you want to accept a larger number than the default, make sure
|
||||
# you increase your OS limits.
|
||||
# 0 - unlimited.
|
||||
max_open_connections = 3
|
||||
|
||||
# Instrumentation namespace
|
||||
namespace = "tendermint"
|
||||
@@ -1,4 +1,4 @@
|
||||
#!/usr/bin/sh
|
||||
#!/bin/bash
|
||||
set -eo pipefail
|
||||
|
||||
# This script appends the "option go_package" proto option to the file located at $FNAME.
|
||||
|
||||
@@ -115,7 +115,7 @@ func getAllSeenCommits(ctx context.Context, db dbm.DB) ([]toMigrate, error) {
|
||||
return scData, nil
|
||||
}
|
||||
|
||||
func renameRecord(ctx context.Context, db dbm.DB, keep toMigrate) error {
|
||||
func renameRecord(db dbm.DB, keep toMigrate) error {
|
||||
wantKey := makeKeyFromPrefix(prefixSeenCommit)
|
||||
if bytes.Equal(keep.key, wantKey) {
|
||||
return nil // we already did this conversion
|
||||
@@ -143,7 +143,7 @@ func renameRecord(ctx context.Context, db dbm.DB, keep toMigrate) error {
|
||||
return cerr
|
||||
}
|
||||
|
||||
func deleteRecords(ctx context.Context, db dbm.DB, scData []toMigrate) error {
|
||||
func deleteRecords(db dbm.DB, scData []toMigrate) error {
|
||||
// delete all the remaining stale values in a single batch
|
||||
batch := db.NewBatch()
|
||||
|
||||
@@ -179,7 +179,7 @@ func Migrate(ctx context.Context, db dbm.DB) error {
|
||||
// retain only the latest.
|
||||
keep, remove := scData[0], scData[1:]
|
||||
|
||||
if err := renameRecord(ctx, db, keep); err != nil {
|
||||
if err := renameRecord(db, keep); err != nil {
|
||||
return fmt.Errorf("renaming seen commit record: %w", err)
|
||||
}
|
||||
|
||||
@@ -189,7 +189,7 @@ func Migrate(ctx context.Context, db dbm.DB) error {
|
||||
|
||||
// Remove any older seen commits. Prior to v0.35, we kept these records for
|
||||
// all heights, but v0.35 keeps only the latest.
|
||||
if err := deleteRecords(ctx, db, remove); err != nil {
|
||||
if err := deleteRecords(db, remove); err != nil {
|
||||
return fmt.Errorf("writing data: %w", err)
|
||||
}
|
||||
|
||||
|
||||
+168
-3
@@ -3,20 +3,29 @@ package app
|
||||
import (
|
||||
"bytes"
|
||||
"encoding/base64"
|
||||
"encoding/binary"
|
||||
"errors"
|
||||
"fmt"
|
||||
"math/rand"
|
||||
"path/filepath"
|
||||
"sort"
|
||||
"strconv"
|
||||
"strings"
|
||||
"sync"
|
||||
|
||||
"github.com/tendermint/tendermint/abci/example/code"
|
||||
abci "github.com/tendermint/tendermint/abci/types"
|
||||
"github.com/tendermint/tendermint/crypto"
|
||||
"github.com/tendermint/tendermint/libs/log"
|
||||
"github.com/tendermint/tendermint/proto/tendermint/types"
|
||||
"github.com/tendermint/tendermint/version"
|
||||
)
|
||||
|
||||
const (
|
||||
voteExtensionKey string = "extensionSum"
|
||||
voteExtensionMaxVal int64 = 128
|
||||
)
|
||||
|
||||
// Application is an ABCI application for use by end-to-end tests. It is a
|
||||
// simple key/value store for strings, storing data in memory and persisting
|
||||
// to disk as JSON, taking state sync snapshots if requested.
|
||||
@@ -215,10 +224,10 @@ func (app *Application) Commit() abci.ResponseCommit {
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
app.logger.Info("Created state sync snapshot", "height", snapshot.Height)
|
||||
app.logger.Info("created state sync snapshot", "height", snapshot.Height)
|
||||
err = app.snapshots.Prune(maxSnapshotCount)
|
||||
if err != nil {
|
||||
app.logger.Error("Failed to prune snapshots", "err", err)
|
||||
app.logger.Error("failed to prune snapshots", "err", err)
|
||||
}
|
||||
}
|
||||
retainHeight := int64(0)
|
||||
@@ -304,7 +313,74 @@ func (app *Application) ApplySnapshotChunk(req abci.RequestApplySnapshotChunk) a
|
||||
return abci.ResponseApplySnapshotChunk{Result: abci.ResponseApplySnapshotChunk_ACCEPT}
|
||||
}
|
||||
|
||||
// PrepareProposal will take the given transactions and attempt to prepare a
|
||||
// proposal from them when it's our turn to do so. In the process, vote
|
||||
// extensions from the previous round of consensus, if present, will be used to
|
||||
// construct a special transaction whose value is the sum of all of the vote
|
||||
// extensions from the previous round.
|
||||
//
|
||||
// NB: Assumes that the supplied transactions do not exceed `req.MaxTxBytes`.
|
||||
// If adding a special vote extension-generated transaction would cause the
|
||||
// total number of transaction bytes to exceed `req.MaxTxBytes`, we will not
|
||||
// append our special vote extension transaction.
|
||||
func (app *Application) PrepareProposal(req abci.RequestPrepareProposal) abci.ResponsePrepareProposal {
|
||||
var sum int64
|
||||
var extCount int
|
||||
for _, vote := range req.LocalLastCommit.Votes {
|
||||
if !vote.SignedLastBlock || len(vote.VoteExtension) == 0 {
|
||||
continue
|
||||
}
|
||||
extValue, err := parseVoteExtension(vote.VoteExtension)
|
||||
// This should have been verified in VerifyVoteExtension
|
||||
if err != nil {
|
||||
panic(fmt.Errorf("failed to parse vote extension in PrepareProposal: %w", err))
|
||||
}
|
||||
valAddr := crypto.Address(vote.Validator.Address)
|
||||
app.logger.Info("got vote extension value in PrepareProposal", "valAddr", valAddr, "value", extValue)
|
||||
sum += extValue
|
||||
extCount++
|
||||
}
|
||||
// We only generate our special transaction if we have vote extensions
|
||||
if extCount > 0 {
|
||||
var totalBytes int64
|
||||
extTxPrefix := fmt.Sprintf("%s=", voteExtensionKey)
|
||||
extTx := []byte(fmt.Sprintf("%s%d", extTxPrefix, sum))
|
||||
app.logger.Info("preparing proposal with custom transaction from vote extensions", "tx", extTx)
|
||||
// Our generated transaction takes precedence over any supplied
|
||||
// transaction that attempts to modify the "extensionSum" value.
|
||||
txRecords := make([]*abci.TxRecord, len(req.Txs)+1)
|
||||
for i, tx := range req.Txs {
|
||||
if strings.HasPrefix(string(tx), extTxPrefix) {
|
||||
txRecords[i] = &abci.TxRecord{
|
||||
Action: abci.TxRecord_REMOVED,
|
||||
Tx: tx,
|
||||
}
|
||||
} else {
|
||||
txRecords[i] = &abci.TxRecord{
|
||||
Action: abci.TxRecord_UNMODIFIED,
|
||||
Tx: tx,
|
||||
}
|
||||
totalBytes += int64(len(tx))
|
||||
}
|
||||
}
|
||||
if totalBytes+int64(len(extTx)) < req.MaxTxBytes {
|
||||
txRecords[len(req.Txs)] = &abci.TxRecord{
|
||||
Action: abci.TxRecord_ADDED,
|
||||
Tx: extTx,
|
||||
}
|
||||
} else {
|
||||
app.logger.Info(
|
||||
"too many txs to include special vote extension-generated tx",
|
||||
"totalBytes", totalBytes,
|
||||
"MaxTxBytes", req.MaxTxBytes,
|
||||
"extTx", extTx,
|
||||
"extTxLen", len(extTx),
|
||||
)
|
||||
}
|
||||
return abci.ResponsePrepareProposal{
|
||||
TxRecords: txRecords,
|
||||
}
|
||||
}
|
||||
// None of the transactions are modified by this application.
|
||||
trs := make([]*abci.TxRecord, 0, len(req.Txs))
|
||||
var totalBytes int64
|
||||
@@ -325,14 +401,87 @@ func (app *Application) PrepareProposal(req abci.RequestPrepareProposal) abci.Re
|
||||
// It accepts any proposal that does not contain a malformed transaction.
|
||||
func (app *Application) ProcessProposal(req abci.RequestProcessProposal) abci.ResponseProcessProposal {
|
||||
for _, tx := range req.Txs {
|
||||
_, _, err := parseTx(tx)
|
||||
k, v, err := parseTx(tx)
|
||||
if err != nil {
|
||||
app.logger.Error("malformed transaction in ProcessProposal", "tx", tx, "err", err)
|
||||
return abci.ResponseProcessProposal{Status: abci.ResponseProcessProposal_REJECT}
|
||||
}
|
||||
// Additional check for vote extension-related txs
|
||||
if k == voteExtensionKey {
|
||||
_, err := strconv.Atoi(v)
|
||||
if err != nil {
|
||||
app.logger.Error("malformed vote extension transaction", k, v, "err", err)
|
||||
return abci.ResponseProcessProposal{Status: abci.ResponseProcessProposal_REJECT}
|
||||
}
|
||||
}
|
||||
}
|
||||
return abci.ResponseProcessProposal{Status: abci.ResponseProcessProposal_ACCEPT}
|
||||
}
|
||||
|
||||
// ExtendVote will produce vote extensions in the form of random numbers to
|
||||
// demonstrate vote extension nondeterminism.
|
||||
//
|
||||
// In the next block, if there are any vote extensions from the previous block,
|
||||
// a new transaction will be proposed that updates a special value in the
|
||||
// key/value store ("extensionSum") with the sum of all of the numbers collected
|
||||
// from the vote extensions.
|
||||
func (app *Application) ExtendVote(req abci.RequestExtendVote) abci.ResponseExtendVote {
|
||||
// We ignore any requests for vote extensions that don't match our expected
|
||||
// next height.
|
||||
if req.Height != int64(app.state.Height)+1 {
|
||||
app.logger.Error(
|
||||
"got unexpected height in ExtendVote request",
|
||||
"expectedHeight", app.state.Height+1,
|
||||
"requestHeight", req.Height,
|
||||
)
|
||||
return abci.ResponseExtendVote{}
|
||||
}
|
||||
ext := make([]byte, binary.MaxVarintLen64)
|
||||
// We don't care that these values are generated by a weak random number
|
||||
// generator. It's just for test purposes.
|
||||
// nolint:gosec // G404: Use of weak random number generator
|
||||
num := rand.Int63n(voteExtensionMaxVal)
|
||||
extLen := binary.PutVarint(ext, num)
|
||||
app.logger.Info("generated vote extension", "num", num, "ext", fmt.Sprintf("%x", ext[:extLen]), "state.Height", app.state.Height)
|
||||
return abci.ResponseExtendVote{
|
||||
VoteExtension: ext[:extLen],
|
||||
}
|
||||
}
|
||||
|
||||
// VerifyVoteExtension simply validates vote extensions from other validators
|
||||
// without doing anything about them. In this case, it just makes sure that the
|
||||
// vote extension is a well-formed integer value.
|
||||
func (app *Application) VerifyVoteExtension(req abci.RequestVerifyVoteExtension) abci.ResponseVerifyVoteExtension {
|
||||
// We allow vote extensions to be optional
|
||||
if len(req.VoteExtension) == 0 {
|
||||
return abci.ResponseVerifyVoteExtension{
|
||||
Status: abci.ResponseVerifyVoteExtension_ACCEPT,
|
||||
}
|
||||
}
|
||||
if req.Height != int64(app.state.Height)+1 {
|
||||
app.logger.Error(
|
||||
"got unexpected height in VerifyVoteExtension request",
|
||||
"expectedHeight", app.state.Height,
|
||||
"requestHeight", req.Height,
|
||||
)
|
||||
return abci.ResponseVerifyVoteExtension{
|
||||
Status: abci.ResponseVerifyVoteExtension_REJECT,
|
||||
}
|
||||
}
|
||||
|
||||
num, err := parseVoteExtension(req.VoteExtension)
|
||||
if err != nil {
|
||||
app.logger.Error("failed to verify vote extension", "req", req, "err", err)
|
||||
return abci.ResponseVerifyVoteExtension{
|
||||
Status: abci.ResponseVerifyVoteExtension_REJECT,
|
||||
}
|
||||
}
|
||||
app.logger.Info("verified vote extension value", "req", req, "num", num)
|
||||
return abci.ResponseVerifyVoteExtension{
|
||||
Status: abci.ResponseVerifyVoteExtension_ACCEPT,
|
||||
}
|
||||
}
|
||||
|
||||
func (app *Application) Rollback() error {
|
||||
app.mu.Lock()
|
||||
defer app.mu.Unlock()
|
||||
@@ -378,3 +527,19 @@ func parseTx(tx []byte) (string, string, error) {
|
||||
}
|
||||
return string(parts[0]), string(parts[1]), nil
|
||||
}
|
||||
|
||||
// parseVoteExtension attempts to parse the given extension data into a positive
|
||||
// integer value.
|
||||
func parseVoteExtension(ext []byte) (int64, error) {
|
||||
num, errVal := binary.Varint(ext)
|
||||
if errVal == 0 {
|
||||
return 0, errors.New("vote extension is too small to parse")
|
||||
}
|
||||
if errVal < 0 {
|
||||
return 0, errors.New("vote extension value is too large")
|
||||
}
|
||||
if num >= voteExtensionMaxVal {
|
||||
return 0, fmt.Errorf("vote extension value must be smaller than %d (was %d)", voteExtensionMaxVal, num)
|
||||
}
|
||||
return num, nil
|
||||
}
|
||||
|
||||
@@ -134,7 +134,7 @@ func NewCLI(logger log.Logger) *CLI {
|
||||
if err = Wait(ctx, logger, cli.testnet, 5); err != nil { // wait for network to settle before tests
|
||||
return err
|
||||
}
|
||||
if err := Test(logger, cli.testnet); err != nil {
|
||||
if err := Test(cli.testnet); err != nil {
|
||||
return err
|
||||
}
|
||||
return nil
|
||||
@@ -259,7 +259,7 @@ func NewCLI(logger log.Logger) *CLI {
|
||||
Use: "test",
|
||||
Short: "Runs test cases against a running testnet",
|
||||
RunE: func(cmd *cobra.Command, args []string) error {
|
||||
return Test(logger, cli.testnet)
|
||||
return Test(cli.testnet)
|
||||
},
|
||||
})
|
||||
|
||||
|
||||
@@ -3,12 +3,11 @@ package main
|
||||
import (
|
||||
"os"
|
||||
|
||||
"github.com/tendermint/tendermint/libs/log"
|
||||
e2e "github.com/tendermint/tendermint/test/e2e/pkg"
|
||||
)
|
||||
|
||||
// Test runs test cases under tests/
|
||||
func Test(logger log.Logger, testnet *e2e.Testnet) error {
|
||||
func Test(testnet *e2e.Testnet) error {
|
||||
err := os.Setenv("E2E_MANIFEST", testnet.File)
|
||||
if err != nil {
|
||||
return err
|
||||
|
||||
@@ -5,6 +5,7 @@ import (
|
||||
"context"
|
||||
"fmt"
|
||||
"math/rand"
|
||||
"strconv"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
@@ -45,9 +46,11 @@ func TestApp_Hash(t *testing.T) {
|
||||
testNode(t, func(ctx context.Context, t *testing.T, node e2e.Node) {
|
||||
client, err := node.Client()
|
||||
require.NoError(t, err)
|
||||
|
||||
info, err := client.ABCIInfo(ctx)
|
||||
require.NoError(t, err)
|
||||
require.NotEmpty(t, info.Response.LastBlockAppHash, "expected app to return app hash")
|
||||
|
||||
// In next-block execution, the app hash is stored in the next block
|
||||
blockHeight := info.Response.LastBlockHeight + 1
|
||||
|
||||
@@ -60,7 +63,6 @@ func TestApp_Hash(t *testing.T) {
|
||||
|
||||
block, err := client.Block(ctx, &blockHeight)
|
||||
require.NoError(t, err)
|
||||
|
||||
require.Equal(t, blockHeight, block.Block.Height)
|
||||
require.Equal(t,
|
||||
fmt.Sprintf("%x", info.Response.LastBlockAppHash),
|
||||
@@ -185,3 +187,18 @@ func TestApp_Tx(t *testing.T) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
func TestApp_VoteExtensions(t *testing.T) {
|
||||
testNode(t, func(ctx context.Context, t *testing.T, node e2e.Node) {
|
||||
client, err := node.Client()
|
||||
require.NoError(t, err)
|
||||
|
||||
// This special value should have been created by way of vote extensions
|
||||
resp, err := client.ABCIQuery(ctx, "", []byte("extensionSum"))
|
||||
require.NoError(t, err)
|
||||
|
||||
extSum, err := strconv.Atoi(string(resp.Response.Value))
|
||||
require.NoError(t, err)
|
||||
require.GreaterOrEqual(t, extSum, 0)
|
||||
})
|
||||
}
|
||||
|
||||
@@ -1,29 +0,0 @@
|
||||
#!/usr/bin/make -f
|
||||
|
||||
.PHONY: fuzz-mempool
|
||||
fuzz-mempool:
|
||||
cd mempool && \
|
||||
rm -f *-fuzz.zip && \
|
||||
go-fuzz-build && \
|
||||
go-fuzz
|
||||
|
||||
.PHONY: fuzz-p2p-sc
|
||||
fuzz-p2p-sc:
|
||||
cd p2p/secretconnection && \
|
||||
rm -f *-fuzz.zip && \
|
||||
go run ./init-corpus/main.go && \
|
||||
go-fuzz-build && \
|
||||
go-fuzz
|
||||
|
||||
.PHONY: fuzz-rpc-server
|
||||
fuzz-rpc-server:
|
||||
cd rpc/jsonrpc/server && \
|
||||
rm -f *-fuzz.zip && \
|
||||
go-fuzz-build && \
|
||||
go-fuzz
|
||||
|
||||
clean:
|
||||
find . -name corpus -type d -exec rm -rf {} +;
|
||||
find . -name crashers -type d -exec rm -rf {} +;
|
||||
find . -name suppressions -type d -exec rm -rf {} +;
|
||||
find . -name *\.zip -type f -delete
|
||||
+6
-56
@@ -5,68 +5,18 @@ Fuzzing for various packages in Tendermint using [go-fuzz](https://github.com/dv
|
||||
Inputs:
|
||||
|
||||
- mempool `CheckTx` (using kvstore in-process ABCI app)
|
||||
- p2p `Addrbook#AddAddress`
|
||||
- p2p `pex.Reactor#Receive`
|
||||
- p2p `SecretConnection#Read` and `SecretConnection#Write`
|
||||
- rpc jsonrpc server
|
||||
|
||||
## Directory structure
|
||||
|
||||
```
|
||||
| test
|
||||
| |- corpus/
|
||||
| |- crashers/
|
||||
| |- init-corpus/
|
||||
| |- suppressions/
|
||||
| |- testdata/
|
||||
| |- <testname>.go
|
||||
```
|
||||
|
||||
`/corpus` directory contains corpus data. The idea is to help the fuzzier to
|
||||
understand what bytes sequences are semantically valid (e.g. if we're testing
|
||||
PNG decoder, then we would put black-white PNG into corpus directory; with
|
||||
blockchain reactor - we would put blockchain messages into corpus).
|
||||
|
||||
`/init-corpus` (if present) contains a script for generating corpus data.
|
||||
|
||||
`/testdata` directory may contain an additional data (like `addrbook.json`).
|
||||
|
||||
Upon running the fuzzier, `/crashers` and `/suppressions` dirs will be created,
|
||||
along with <testname>.zip archive. `/crashers` will show any inputs, which have
|
||||
lead to panics (plus a trace). `/suppressions` will show any suppressed inputs.
|
||||
|
||||
## Running
|
||||
|
||||
```sh
|
||||
make fuzz-mempool
|
||||
make fuzz-p2p-addrbook
|
||||
make fuzz-p2p-pex
|
||||
make fuzz-p2p-sc
|
||||
make fuzz-rpc-server
|
||||
```
|
||||
|
||||
Each command will create corpus data (if needed), generate a fuzz archive and
|
||||
call `go-fuzz` executable.
|
||||
|
||||
Then watch out for the respective outputs in the fuzzer output to announce new
|
||||
crashers which can be found in the directory `crashers`.
|
||||
|
||||
For example if we find
|
||||
The fuzz tests are in native Go fuzzing format. Use the `go`
|
||||
tool to run them:
|
||||
|
||||
```sh
|
||||
ls crashers/
|
||||
61bde465f47c93254d64d643c3b2480e0a54666e
|
||||
61bde465f47c93254d64d643c3b2480e0a54666e.output
|
||||
61bde465f47c93254d64d643c3b2480e0a54666e.quoted
|
||||
da39a3ee5e6b4b0d3255bfef95601890afd80709
|
||||
da39a3ee5e6b4b0d3255bfef95601890afd80709.output
|
||||
da39a3ee5e6b4b0d3255bfef95601890afd80709.quoted
|
||||
go test -fuzz Mempool ./tests
|
||||
go test -fuzz P2PSecretConnection ./tests
|
||||
go test -fuzz RPCJSONRPCServer ./tests
|
||||
```
|
||||
|
||||
the crashing bytes generated by the fuzzer will be in
|
||||
`61bde465f47c93254d64d643c3b2480e0a54666e` the respective crash report in
|
||||
`61bde465f47c93254d64d643c3b2480e0a54666e.output`
|
||||
|
||||
and the bug report can be created by retrieving the bytes in
|
||||
`61bde465f47c93254d64d643c3b2480e0a54666e` and feeding those back into the
|
||||
`Fuzz` function.
|
||||
See [the Go Fuzzing introduction](https://go.dev/doc/fuzz/) for more information.
|
||||
|
||||
@@ -1,34 +0,0 @@
|
||||
package mempool_test
|
||||
|
||||
import (
|
||||
"io"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
mempool "github.com/tendermint/tendermint/test/fuzz/mempool"
|
||||
)
|
||||
|
||||
const testdataCasesDir = "testdata/cases"
|
||||
|
||||
func TestMempoolTestdataCases(t *testing.T) {
|
||||
entries, err := os.ReadDir(testdataCasesDir)
|
||||
require.NoError(t, err)
|
||||
|
||||
for _, e := range entries {
|
||||
entry := e
|
||||
t.Run(entry.Name(), func(t *testing.T) {
|
||||
defer func() {
|
||||
r := recover()
|
||||
require.Nilf(t, r, "testdata/cases test panic")
|
||||
}()
|
||||
f, err := os.Open(filepath.Join(testdataCasesDir, entry.Name()))
|
||||
require.NoError(t, err)
|
||||
input, err := io.ReadAll(f)
|
||||
require.NoError(t, err)
|
||||
mempool.Fuzz(input)
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -1,10 +1,22 @@
|
||||
#!/bin/bash -eu
|
||||
#!/bin/bash
|
||||
|
||||
set -euo pipefail
|
||||
|
||||
export FUZZ_ROOT="github.com/tendermint/tendermint"
|
||||
|
||||
(cd test/fuzz/p2p/secretconnection; go run ./init-corpus/main.go)
|
||||
compile_go_fuzzer "$FUZZ_ROOT"/test/fuzz/p2p/secretconnection Fuzz fuzz_p2p_secretconnection fuzz
|
||||
build_go_fuzzer() {
|
||||
local function="$1"
|
||||
local fuzzer="$2"
|
||||
|
||||
compile_go_fuzzer "$FUZZ_ROOT"/test/fuzz/mempool Fuzz fuzz_mempool fuzz
|
||||
gotip run github.com/orijtech/otils/corpus2ossfuzz@latest -o "$OUT"/"$fuzzer"_seed_corpus.zip -corpus test/fuzz/tests/testdata/fuzz/"$function"
|
||||
compile_native_go_fuzzer "$FUZZ_ROOT"/test/fuzz/tests "$function" "$fuzzer"
|
||||
}
|
||||
|
||||
compile_go_fuzzer "$FUZZ_ROOT"/test/fuzz/rpc/jsonrpc/server Fuzz fuzz_rpc_jsonrpc_server fuzz
|
||||
gotip get github.com/AdamKorcz/go-118-fuzz-build/utils
|
||||
gotip get github.com/prometheus/common/expfmt@v0.32.1
|
||||
|
||||
build_go_fuzzer FuzzP2PSecretConnection fuzz_p2p_secretconnection
|
||||
|
||||
build_go_fuzzer FuzzMempool fuzz_mempool
|
||||
|
||||
build_go_fuzzer FuzzRPCJSONRPCServer fuzz_rpc_jsonrpc_server
|
||||
|
||||
@@ -1,34 +0,0 @@
|
||||
package secretconnection_test
|
||||
|
||||
import (
|
||||
"io"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
"github.com/tendermint/tendermint/test/fuzz/p2p/secretconnection"
|
||||
)
|
||||
|
||||
const testdataCasesDir = "testdata/cases"
|
||||
|
||||
func TestSecretConnectionTestdataCases(t *testing.T) {
|
||||
entries, err := os.ReadDir(testdataCasesDir)
|
||||
require.NoError(t, err)
|
||||
|
||||
for _, e := range entries {
|
||||
entry := e
|
||||
t.Run(entry.Name(), func(t *testing.T) {
|
||||
defer func() {
|
||||
r := recover()
|
||||
require.Nilf(t, r, "testdata/cases test panic")
|
||||
}()
|
||||
f, err := os.Open(filepath.Join(testdataCasesDir, entry.Name()))
|
||||
require.NoError(t, err)
|
||||
input, err := io.ReadAll(f)
|
||||
require.NoError(t, err)
|
||||
secretconnection.Fuzz(input)
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -1,47 +0,0 @@
|
||||
// nolint: gosec
|
||||
package main
|
||||
|
||||
import (
|
||||
"flag"
|
||||
"fmt"
|
||||
"log"
|
||||
"os"
|
||||
"path/filepath"
|
||||
)
|
||||
|
||||
func main() {
|
||||
baseDir := flag.String("base", ".", `where the "corpus" directory will live`)
|
||||
flag.Parse()
|
||||
|
||||
initCorpus(*baseDir)
|
||||
}
|
||||
|
||||
func initCorpus(baseDir string) {
|
||||
log.SetFlags(0)
|
||||
|
||||
corpusDir := filepath.Join(baseDir, "corpus")
|
||||
if err := os.MkdirAll(corpusDir, 0755); err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
|
||||
data := []string{
|
||||
"dadc04c2-cfb1-4aa9-a92a-c0bf780ec8b6",
|
||||
"",
|
||||
" ",
|
||||
" a ",
|
||||
`{"a": 12, "tsp": 999, k: "blue"}`,
|
||||
`9999.999`,
|
||||
`""`,
|
||||
`Tendermint fuzzing`,
|
||||
}
|
||||
|
||||
for i, datum := range data {
|
||||
filename := filepath.Join(corpusDir, fmt.Sprintf("%d", i))
|
||||
|
||||
if err := os.WriteFile(filename, []byte(datum), 0644); err != nil {
|
||||
log.Fatalf("can't write %v to %q: %v", datum, filename, err)
|
||||
}
|
||||
|
||||
log.Printf("wrote %q", filename)
|
||||
}
|
||||
}
|
||||
@@ -1,34 +0,0 @@
|
||||
package server_test
|
||||
|
||||
import (
|
||||
"io"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
"github.com/tendermint/tendermint/test/fuzz/rpc/jsonrpc/server"
|
||||
)
|
||||
|
||||
const testdataCasesDir = "testdata/cases"
|
||||
|
||||
func TestServerTestdataCases(t *testing.T) {
|
||||
entries, err := os.ReadDir(testdataCasesDir)
|
||||
require.NoError(t, err)
|
||||
|
||||
for _, e := range entries {
|
||||
entry := e
|
||||
t.Run(entry.Name(), func(t *testing.T) {
|
||||
defer func() {
|
||||
r := recover()
|
||||
require.Nilf(t, r, "testdata/cases test panic")
|
||||
}()
|
||||
f, err := os.Open(filepath.Join(testdataCasesDir, entry.Name()))
|
||||
require.NoError(t, err)
|
||||
input, err := io.ReadAll(f)
|
||||
require.NoError(t, err)
|
||||
server.Fuzz(input)
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -1,65 +0,0 @@
|
||||
package server
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"context"
|
||||
"encoding/json"
|
||||
"io"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
|
||||
"github.com/tendermint/tendermint/libs/log"
|
||||
rs "github.com/tendermint/tendermint/rpc/jsonrpc/server"
|
||||
"github.com/tendermint/tendermint/rpc/jsonrpc/types"
|
||||
)
|
||||
|
||||
var rpcFuncMap = map[string]*rs.RPCFunc{
|
||||
"c": rs.NewRPCFunc(func(ctx context.Context, s string, i int) (string, error) {
|
||||
return "foo", nil
|
||||
}, "s", "i"),
|
||||
}
|
||||
var mux *http.ServeMux
|
||||
|
||||
func init() {
|
||||
mux = http.NewServeMux()
|
||||
rs.RegisterRPCFuncs(mux, rpcFuncMap, log.NewNopLogger())
|
||||
}
|
||||
|
||||
func Fuzz(data []byte) int {
|
||||
if len(data) == 0 {
|
||||
return -1
|
||||
}
|
||||
|
||||
req, _ := http.NewRequest("POST", "http://localhost/", bytes.NewReader(data))
|
||||
rec := httptest.NewRecorder()
|
||||
mux.ServeHTTP(rec, req)
|
||||
res := rec.Result()
|
||||
blob, err := io.ReadAll(res.Body)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
if err := res.Body.Close(); err != nil {
|
||||
panic(err)
|
||||
}
|
||||
if len(blob) == 0 {
|
||||
return 1
|
||||
}
|
||||
|
||||
if outputJSONIsSlice(blob) {
|
||||
recv := []types.RPCResponse{}
|
||||
if err := json.Unmarshal(blob, &recv); err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return 1
|
||||
}
|
||||
recv := &types.RPCResponse{}
|
||||
if err := json.Unmarshal(blob, recv); err != nil {
|
||||
panic(err)
|
||||
}
|
||||
return 1
|
||||
}
|
||||
|
||||
func outputJSONIsSlice(input []byte) bool {
|
||||
slice := []interface{}{}
|
||||
return json.Unmarshal(input, &slice) == nil
|
||||
}
|
||||
-1
@@ -1 +0,0 @@
|
||||
[0]
|
||||
-1
@@ -1 +0,0 @@
|
||||
[0]
|
||||
-1
@@ -1 +0,0 @@
|
||||
[0,0]
|
||||
-1
@@ -1 +0,0 @@
|
||||
[{"iD":7},{"iD":7}]
|
||||
-1
@@ -1 +0,0 @@
|
||||
[{"iD":7},{"iD":7}]
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user