From f8809f5c46762f55906b1398563453a93ccd4c91 Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Mon, 8 Jun 2020 12:48:29 -0400 Subject: [PATCH 01/23] Updte tx generator --- client/tx_generator.go | 48 ++++++++++++++++++------------------------ 1 file changed, 20 insertions(+), 28 deletions(-) diff --git a/client/tx_generator.go b/client/tx_generator.go index f840bd39e922..0e50ca083be2 100644 --- a/client/tx_generator.go +++ b/client/tx_generator.go @@ -3,7 +3,8 @@ package client import ( "github.com/tendermint/tendermint/crypto" - "github.com/cosmos/cosmos-sdk/types" + sdk "github.com/cosmos/cosmos-sdk/types" + types "github.com/cosmos/cosmos-sdk/types/tx" ) type ( @@ -11,22 +12,14 @@ type ( // application-defined concrete transaction type. The type returned must // implement TxBuilder. TxGenerator interface { - NewTx() TxBuilder - NewFee() Fee - NewSignature() Signature - MarshalTx(tx types.Tx) ([]byte, error) - } - - Fee interface { - types.Fee - SetGas(uint64) - SetAmount(types.Coins) - } - - Signature interface { - types.Signature - SetPubKey(crypto.PubKey) error - SetSignature([]byte) + NewTxBuilder() TxBuilder + // WrapTxBuilder wraps an existing tx in a TxBuilder or returns an error + WrapTxBuilder(tx sdk.Tx) (TxBuilder, error) + TxEncoder() sdk.TxEncoder + TxDecoder() sdk.TxDecoder + TxJSONEncoder() sdk.TxEncoder + TxJSONDecoder() sdk.TxDecoder + SignModeHandler() types.SignModeHandler } // TxBuilder defines an interface which an application-defined concrete transaction @@ -34,18 +27,17 @@ type ( // signatures, and provide canonical bytes to sign over. The transaction must // also know how to encode itself. TxBuilder interface { - GetTx() types.Tx + GetTx() types.SigTx - SetMsgs(...types.Msg) error - GetSignatures() []types.Signature - SetSignatures(...Signature) error - GetFee() types.Fee - SetFee(Fee) error - GetMemo() string - SetMemo(string) + SetMsgs(msgs ...sdk.Msg) error + SetSignatures(signatures ...SignatureBuilder) error + SetMemo(memo string) + SetFee(amount sdk.Coins) + SetGasLimit(limit uint64) + } - // CanonicalSignBytes returns the canonical sign bytes to sign over, given a - // chain ID, along with an account and sequence number. - CanonicalSignBytes(cid string, num, seq uint64) ([]byte, error) + SignatureBuilder struct { + PubKey crypto.PubKey + Data types.SignatureData } ) From ef055c0d0be98791a706db5ca30fce7ce0df8353 Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Mon, 8 Jun 2020 20:56:21 -0400 Subject: [PATCH 02/23] Add sigv2, PublicKeyCodec --- client/tx_generator.go | 10 +-- crypto/codec/default.go | 87 ++++++++++++++++++++ crypto/types/codec.go | 38 +++++++++ crypto/types/types.go | 44 ++++++++++ crypto/types/types.pb.go | 118 +++++++++++++------------- crypto/types/types.proto | 7 +- types/result.go | 3 +- types/tx/interface.go | 38 +++++++++ types/tx/signature.go | 64 ++++++++++++++ types/tx/tx.go | 174 +++++++++++++++++++++++++++++++++++++++ x/bank/types/query.pb.go | 16 ++-- 11 files changed, 517 insertions(+), 82 deletions(-) create mode 100644 crypto/codec/default.go create mode 100644 crypto/types/codec.go create mode 100644 crypto/types/types.go create mode 100644 types/tx/interface.go create mode 100644 types/tx/signature.go create mode 100644 types/tx/tx.go diff --git a/client/tx_generator.go b/client/tx_generator.go index 0e50ca083be2..575d52ee3c92 100644 --- a/client/tx_generator.go +++ b/client/tx_generator.go @@ -1,8 +1,6 @@ package client import ( - "github.com/tendermint/tendermint/crypto" - sdk "github.com/cosmos/cosmos-sdk/types" types "github.com/cosmos/cosmos-sdk/types/tx" ) @@ -19,7 +17,6 @@ type ( TxDecoder() sdk.TxDecoder TxJSONEncoder() sdk.TxEncoder TxJSONDecoder() sdk.TxDecoder - SignModeHandler() types.SignModeHandler } // TxBuilder defines an interface which an application-defined concrete transaction @@ -30,14 +27,9 @@ type ( GetTx() types.SigTx SetMsgs(msgs ...sdk.Msg) error - SetSignatures(signatures ...SignatureBuilder) error + SetSignatures(signatures ...types.SignatureV2) error SetMemo(memo string) SetFee(amount sdk.Coins) SetGasLimit(limit uint64) } - - SignatureBuilder struct { - PubKey crypto.PubKey - Data types.SignatureData - } ) diff --git a/crypto/codec/default.go b/crypto/codec/default.go new file mode 100644 index 000000000000..7716cf5b1d2c --- /dev/null +++ b/crypto/codec/default.go @@ -0,0 +1,87 @@ +package codec + +import ( + "fmt" + + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + + "github.com/tendermint/tendermint/crypto" + ed255192 "github.com/tendermint/tendermint/crypto/ed25519" + "github.com/tendermint/tendermint/crypto/secp256k1" + "github.com/tendermint/tendermint/crypto/sr25519" + + "github.com/cosmos/cosmos-sdk/crypto/types" +) + +type DefaultPublicKeyCodec struct{} + +var _ types.PublicKeyCodec = DefaultPublicKeyCodec{} + +func (cdc DefaultPublicKeyCodec) Decode(key *types.PublicKey) (crypto.PubKey, error) { + switch key := key.Sum.(type) { + case *types.PublicKey_Secp256K1: + n := len(key.Secp256K1) + if n != secp256k1.PubKeySecp256k1Size { + return nil, fmt.Errorf("wrong length %d for secp256k1 public key", n) + } + var res secp256k1.PubKeySecp256k1 + copy(res[:], key.Secp256K1) + return res, nil + case *types.PublicKey_Ed25519: + n := len(key.Ed25519) + if n != ed255192.PubKeyEd25519Size { + return nil, fmt.Errorf("wrong length %d for ed25519 public key", n) + } + var res ed255192.PubKeyEd25519 + copy(res[:], key.Ed25519) + return res, nil + case *types.PublicKey_Sr25519: + n := len(key.Sr25519) + if n != sr25519.PubKeySr25519Size { + return nil, fmt.Errorf("wrong length %d for sr25519 public key", n) + } + var res sr25519.PubKeySr25519 + copy(res[:], key.Sr25519) + return res, nil + case *types.PublicKey_Multisig: + pubKeys := key.Multisig.PubKeys + resKeys := make([]crypto.PubKey, len(pubKeys)) + for i, k := range pubKeys { + dk, err := cdc.Decode(k) + if err != nil { + return nil, err + } + resKeys[i] = dk + } + return multisig.NewPubKeyMultisigThreshold(key.Multisig.K, resKeys), nil + default: + return nil, fmt.Errorf("can't encode PubKey of type %T", key) + } +} + +func (cdc DefaultPublicKeyCodec) Encode(key crypto.PubKey) (*types.PublicKey, error) { + switch key := key.(type) { + case secp256k1.PubKeySecp256k1: + return &types.PublicKey{Sum: &types.PublicKey_Secp256K1{Secp256K1: key[:]}}, nil + case ed255192.PubKeyEd25519: + return &types.PublicKey{Sum: &types.PublicKey_Ed25519{Ed25519: key[:]}}, nil + case sr25519.PubKeySr25519: + return &types.PublicKey{Sum: &types.PublicKey_Sr25519{Sr25519: key[:]}}, nil + case multisig.ThresholdMultisigPubKey: + pubKeys := key.PubKeys + resKeys := make([]*types.PublicKey, len(pubKeys)) + for i, k := range pubKeys { + dk, err := cdc.Encode(k) + if err != nil { + return nil, err + } + resKeys[i] = dk + } + return &types.PublicKey{Sum: &types.PublicKey_Multisig{Multisig: &types.PubKeyMultisigThreshold{ + K: key.K, + PubKeys: resKeys, + }}}, nil + default: + return nil, fmt.Errorf("can't encode PubKey of type %T", key) + } +} diff --git a/crypto/types/codec.go b/crypto/types/codec.go new file mode 100644 index 000000000000..1230a5a02dca --- /dev/null +++ b/crypto/types/codec.go @@ -0,0 +1,38 @@ +package types + +import ( + "github.com/tendermint/tendermint/crypto" +) + +type PublicKeyCodec interface { + Decode(key *PublicKey) (crypto.PubKey, error) + Encode(key crypto.PubKey) (*PublicKey, error) +} + +type publicKeyCodecCacheMiddleware struct { + cdc PublicKeyCodec +} + +func CacheWrapCodec(cdc PublicKeyCodec) PublicKeyCodec { + return publicKeyCodecCacheMiddleware{cdc: cdc} +} + +var _ PublicKeyCodec = publicKeyCodecCacheMiddleware{} + +func (p publicKeyCodecCacheMiddleware) Decode(key *PublicKey) (crypto.PubKey, error) { + res, err := p.cdc.Decode(key) + if err != nil { + return nil, err + } + key.cachedValue = res + return res, nil +} + +func (p publicKeyCodecCacheMiddleware) Encode(key crypto.PubKey) (*PublicKey, error) { + res, err := p.cdc.Encode(key) + if err != nil { + return nil, err + } + res.cachedValue = key + return res, nil +} diff --git a/crypto/types/types.go b/crypto/types/types.go new file mode 100644 index 000000000000..328910919597 --- /dev/null +++ b/crypto/types/types.go @@ -0,0 +1,44 @@ +package types + +import ( + "fmt" + + "github.com/tendermint/tendermint/crypto" +) + +// PublicKey specifies a public key +type PublicKey struct { + // sum specifies which type of public key is wrapped + // + // Types that are valid to be assigned to Sum: + // *PublicKey_Secp256K1 + // *PublicKey_Ed25519 + // *PublicKey_Sr25519 + // *PublicKey_Multisig + // *PublicKey_Secp256R1 + // *PublicKey_AminoMultisig + // *PublicKey_AnyPubkey + Sum isPublicKey_Sum `protobuf_oneof:"sum"` + + cachedValue crypto.PubKey +} + +// GetCachedPubKey returns the cached PubKey instance wrapped in the PublicKey. +// This will only be set if the PublicKeyCodec is cache-wrapped using CacheWrapCodec +func (pk PublicKey) GetCachedPubKey() crypto.PubKey { + return pk.cachedValue +} + +func DecodeMultisignatures(bz []byte) ([][]byte, error) { + multisig := MultiSignature{} + err := multisig.Unmarshal(bz) + if err != nil { + return nil, err + } + // unrecognized fields must be discarded because otherwise this would present a transaction malleability issue + // which could allow transactions to be bloated with arbitrary bytes + if len(multisig.XXX_unrecognized) > 0 { + return nil, fmt.Errorf("rejecting unrecognized fields found in MultiSignature") + } + return multisig.Signatures, nil +} diff --git a/crypto/types/types.pb.go b/crypto/types/types.pb.go index 6887feafd90f..d3b16767e952 100644 --- a/crypto/types/types.pb.go +++ b/crypto/types/types.pb.go @@ -24,20 +24,6 @@ var _ = math.Inf // proto package needs to be updated. const _ = proto.GoGoProtoPackageIsVersion3 // please upgrade the proto package -// PublicKey specifies a public key -type PublicKey struct { - // sum specifies which type of public key is wrapped - // - // Types that are valid to be assigned to Sum: - // *PublicKey_Secp256K1 - // *PublicKey_Ed25519 - // *PublicKey_Sr25519 - // *PublicKey_Multisig - // *PublicKey_Secp256R1 - // *PublicKey_AnyPubkey - Sum isPublicKey_Sum `protobuf_oneof:"sum"` -} - func (m *PublicKey) Reset() { *m = PublicKey{} } func (m *PublicKey) String() string { return proto.CompactTextString(m) } func (*PublicKey) ProtoMessage() {} @@ -168,7 +154,7 @@ func (*PublicKey) XXX_OneofWrappers() []interface{} { // keys and a threshold type PubKeyMultisigThreshold struct { K uint32 `protobuf:"varint,1,opt,name=threshold,proto3" json:"threshold,omitempty" yaml:"threshold"` - PubKeys []*PublicKey `protobuf:"bytes,2,rep,name=pubkeys,proto3" json:"pubkeys,omitempty" yaml:"pubkeys"` + PubKeys []*PublicKey `protobuf:"bytes,2,rep,name=public_keys,json=publicKeys,proto3" json:"public_keys,omitempty" yaml:"pubkeys"` } func (m *PubKeyMultisigThreshold) Reset() { *m = PubKeyMultisigThreshold{} } @@ -222,7 +208,8 @@ func (m *PubKeyMultisigThreshold) GetPubKeys() []*PublicKey { // See cosmos_sdk.tx.v1.ModeInfo.Multi for how to specify which signers signed // and with which modes type MultiSignature struct { - Sigs [][]byte `protobuf:"bytes,1,rep,name=sigs,proto3" json:"sigs,omitempty"` + Signatures [][]byte `protobuf:"bytes,1,rep,name=signatures,proto3" json:"signatures,omitempty"` + XXX_unrecognized []byte `json:"-"` } func (m *MultiSignature) Reset() { *m = MultiSignature{} } @@ -258,9 +245,9 @@ func (m *MultiSignature) XXX_DiscardUnknown() { var xxx_messageInfo_MultiSignature proto.InternalMessageInfo -func (m *MultiSignature) GetSigs() [][]byte { +func (m *MultiSignature) GetSignatures() [][]byte { if m != nil { - return m.Sigs + return m.Signatures } return nil } @@ -330,39 +317,40 @@ func init() { func init() { proto.RegisterFile("crypto/types/types.proto", fileDescriptor_2165b2a1badb1b0c) } var fileDescriptor_2165b2a1badb1b0c = []byte{ - // 501 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x74, 0x52, 0xcd, 0x6a, 0xdb, 0x40, - 0x18, 0x94, 0xec, 0xb8, 0x8e, 0x37, 0x69, 0xdc, 0x2e, 0x86, 0x2a, 0x86, 0x4a, 0x46, 0x94, 0xe2, - 0x16, 0x22, 0x61, 0x17, 0xb7, 0x34, 0xb7, 0x28, 0x97, 0x80, 0x29, 0x18, 0xa5, 0x87, 0x52, 0x28, - 0x42, 0x3f, 0x5b, 0x79, 0xb1, 0xa4, 0x15, 0xbb, 0xab, 0xd2, 0x7d, 0x89, 0xd2, 0x63, 0x8f, 0xe9, - 0xbd, 0x0f, 0xd2, 0x63, 0x8e, 0x3d, 0x99, 0x22, 0xbf, 0x41, 0x9e, 0xa0, 0x44, 0x2b, 0xc5, 0xa1, - 0x24, 0x17, 0x69, 0xf7, 0x9b, 0xf9, 0x46, 0x33, 0xdf, 0x27, 0xa0, 0x85, 0x54, 0xe4, 0x9c, 0xd8, - 0x5c, 0xe4, 0x88, 0xc9, 0xa7, 0x95, 0x53, 0xc2, 0x09, 0x1c, 0x84, 0x84, 0xa5, 0x84, 0x79, 0x2c, - 0x5a, 0x59, 0x92, 0x64, 0x7d, 0x99, 0x0c, 0x9f, 0xf3, 0x25, 0xa6, 0x91, 0x97, 0xfb, 0x94, 0x0b, - 0xbb, 0x22, 0xda, 0x31, 0x89, 0xc9, 0xf6, 0x24, 0xbb, 0x87, 0x87, 0x31, 0x21, 0x71, 0x82, 0x24, - 0x25, 0x28, 0x3e, 0xdb, 0x7e, 0x26, 0x24, 0x64, 0x7e, 0x6b, 0x81, 0xde, 0xa2, 0x08, 0x12, 0x1c, - 0xce, 0x91, 0x80, 0x3a, 0xe8, 0x31, 0x14, 0xe6, 0xd3, 0xd9, 0xeb, 0xd5, 0x44, 0x53, 0x47, 0xea, - 0x78, 0xff, 0x4c, 0x71, 0xb7, 0x25, 0x38, 0x04, 0x5d, 0x14, 0x4d, 0x67, 0xb3, 0xc9, 0x5b, 0xad, - 0x55, 0xa3, 0x4d, 0xe1, 0x1a, 0x63, 0x54, 0x62, 0xed, 0x06, 0xab, 0x0b, 0x70, 0x0e, 0x76, 0xd3, - 0x22, 0xe1, 0x98, 0xe1, 0x58, 0xdb, 0x19, 0xa9, 0xe3, 0xbd, 0xe9, 0x91, 0x75, 0x57, 0x22, 0x6b, - 0x51, 0x04, 0x73, 0x24, 0xde, 0xd5, 0xdc, 0xf7, 0x4b, 0x8a, 0xd8, 0x92, 0x24, 0xd1, 0x99, 0xe2, - 0xde, 0x08, 0xdc, 0x32, 0x49, 0x27, 0x5a, 0xe7, 0x3f, 0x93, 0x74, 0x02, 0x67, 0x00, 0xf8, 0x99, - 0xf0, 0xf2, 0x22, 0x58, 0x21, 0xa1, 0xf5, 0xab, 0xcf, 0x0d, 0x2c, 0x39, 0x02, 0xab, 0x19, 0x81, - 0x75, 0x92, 0x89, 0xeb, 0x36, 0x3f, 0x13, 0x8b, 0x8a, 0xe8, 0x74, 0x40, 0x9b, 0x15, 0xa9, 0xf9, - 0x4b, 0x05, 0x4f, 0xee, 0x71, 0x01, 0xdf, 0x80, 0x1e, 0x6f, 0x2e, 0xd5, 0x78, 0x1e, 0x3a, 0x87, - 0xe5, 0xda, 0x50, 0xe7, 0x57, 0x6b, 0xe3, 0x91, 0xf0, 0xd3, 0xe4, 0xd8, 0xbc, 0xc1, 0x4d, 0x77, - 0xcb, 0x85, 0x1f, 0x40, 0x57, 0xda, 0x61, 0x5a, 0x6b, 0xd4, 0x1e, 0xef, 0x4d, 0x8d, 0x7b, 0xe3, - 0xcb, 0x4d, 0x38, 0x4f, 0xcb, 0xb5, 0xd1, 0x95, 0x3e, 0xd8, 0xd5, 0xda, 0x38, 0x90, 0xea, 0xb5, - 0x88, 0xe9, 0x36, 0x72, 0xe6, 0x33, 0x70, 0x50, 0xf9, 0x3c, 0xc7, 0x71, 0xe6, 0xf3, 0x82, 0x22, - 0x08, 0xc1, 0x0e, 0xc3, 0x31, 0xd3, 0xd4, 0x51, 0x7b, 0xbc, 0xef, 0x56, 0x67, 0xf3, 0x13, 0xe8, - 0x9f, 0x92, 0x34, 0xf7, 0x43, 0xee, 0x60, 0x7e, 0x42, 0xa9, 0x2f, 0xe0, 0x4b, 0xf0, 0x18, 0x7d, - 0xe5, 0xd4, 0xf7, 0x02, 0xcc, 0x99, 0xc7, 0x38, 0xa1, 0xa8, 0xce, 0xe4, 0xf6, 0x2b, 0xc0, 0xc1, - 0x9c, 0x9d, 0x57, 0x65, 0x38, 0x00, 0x1d, 0x94, 0xa0, 0x94, 0xc9, 0xa5, 0xbb, 0xf2, 0x72, 0xbc, - 0xfb, 0xe3, 0xc2, 0x50, 0x2e, 0x7e, 0x1a, 0x8a, 0x73, 0xfa, 0xbb, 0xd4, 0xd5, 0xcb, 0x52, 0x57, - 0xff, 0x96, 0xba, 0xfa, 0x7d, 0xa3, 0x2b, 0x97, 0x1b, 0x5d, 0xf9, 0xb3, 0xd1, 0x95, 0x8f, 0x2f, - 0x62, 0xcc, 0x97, 0x45, 0x60, 0x85, 0x24, 0xb5, 0x65, 0xe2, 0xfa, 0x75, 0xc4, 0xa2, 0x95, 0x7d, - 0xfb, 0x77, 0x0f, 0x1e, 0x54, 0xab, 0x79, 0xf5, 0x2f, 0x00, 0x00, 0xff, 0xff, 0x1e, 0xd7, 0x43, - 0xb2, 0x05, 0x03, 0x00, 0x00, + // 519 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x74, 0x53, 0x41, 0x6a, 0xdb, 0x40, + 0x14, 0x95, 0x62, 0xbb, 0x89, 0xc7, 0x69, 0xdc, 0x0e, 0x86, 0x2a, 0x86, 0x4a, 0x46, 0x8b, 0xe2, + 0x16, 0x22, 0x61, 0x17, 0xa7, 0xd4, 0xbb, 0x38, 0x9b, 0x80, 0x29, 0x18, 0xa5, 0xab, 0x42, 0x11, + 0x92, 0x3c, 0x95, 0x85, 0x25, 0x8f, 0x98, 0x3f, 0x2a, 0x9d, 0x5b, 0x74, 0xd1, 0x45, 0x97, 0xc9, + 0x19, 0x7a, 0x89, 0x2e, 0xbd, 0xec, 0xca, 0x14, 0xfb, 0x02, 0x25, 0x27, 0x28, 0xd6, 0x48, 0xb1, + 0x29, 0xcd, 0x46, 0xd2, 0x7f, 0xef, 0x8d, 0xfe, 0xfb, 0xef, 0x4b, 0x48, 0x0b, 0x98, 0x48, 0x39, + 0xb5, 0xb9, 0x48, 0x09, 0xc8, 0xab, 0x95, 0x32, 0xca, 0x29, 0x6e, 0x05, 0x14, 0x12, 0x0a, 0x2e, + 0x4c, 0xe7, 0x96, 0x14, 0x59, 0x9f, 0x7b, 0xed, 0x17, 0x7c, 0x16, 0xb1, 0xa9, 0x9b, 0x7a, 0x8c, + 0x0b, 0x3b, 0x17, 0xda, 0x21, 0x0d, 0xe9, 0xee, 0x49, 0x9e, 0x6e, 0x9f, 0x86, 0x94, 0x86, 0x31, + 0x91, 0x12, 0x3f, 0xfb, 0x64, 0x7b, 0x0b, 0x21, 0x29, 0xf3, 0xdb, 0x01, 0xaa, 0x4f, 0x32, 0x3f, + 0x8e, 0x82, 0x31, 0x11, 0x58, 0x47, 0x75, 0x20, 0x41, 0xda, 0x1f, 0x9c, 0xcf, 0x7b, 0x9a, 0xda, + 0x51, 0xbb, 0xc7, 0x57, 0x8a, 0xb3, 0x83, 0x70, 0x1b, 0x1d, 0x92, 0x69, 0x7f, 0x30, 0xe8, 0xbd, + 0xd5, 0x0e, 0x0a, 0xb6, 0x04, 0xb6, 0x1c, 0x30, 0xc9, 0x55, 0x4a, 0xae, 0x00, 0xf0, 0x18, 0x1d, + 0x25, 0x59, 0xcc, 0x23, 0x88, 0x42, 0xad, 0xda, 0x51, 0xbb, 0x8d, 0xfe, 0x99, 0xf5, 0xbf, 0x89, + 0xac, 0x49, 0xe6, 0x8f, 0x89, 0x78, 0x57, 0x68, 0xdf, 0xcf, 0x18, 0x81, 0x19, 0x8d, 0xa7, 0x57, + 0x8a, 0x73, 0xff, 0x82, 0x3d, 0x93, 0xac, 0xa7, 0xd5, 0xfe, 0x31, 0xc9, 0x7a, 0x78, 0x80, 0x90, + 0xb7, 0x10, 0x6e, 0x9a, 0xf9, 0x73, 0x22, 0xb4, 0x66, 0xde, 0xae, 0x65, 0xc9, 0x08, 0xac, 0x32, + 0x02, 0xeb, 0x62, 0x21, 0xb6, 0xc7, 0xbc, 0x85, 0x98, 0xe4, 0xc2, 0x61, 0xf5, 0xcf, 0xad, 0xa1, + 0x8c, 0x6a, 0xa8, 0x02, 0x59, 0x62, 0xfe, 0x50, 0xd1, 0xb3, 0x07, 0xbc, 0xe0, 0x37, 0xa8, 0xce, + 0xcb, 0x22, 0x0f, 0xe9, 0xf1, 0xe8, 0x74, 0xbd, 0x32, 0xd4, 0xf1, 0xdd, 0xca, 0x78, 0x22, 0xbc, + 0x24, 0x1e, 0x9a, 0xf7, 0xbc, 0xe9, 0xec, 0xb4, 0xd8, 0x45, 0x8d, 0x34, 0x8f, 0xda, 0x9d, 0x13, + 0x01, 0xda, 0x41, 0xa7, 0xd2, 0x6d, 0xf4, 0x8d, 0x07, 0x83, 0x90, 0x3b, 0x19, 0x3d, 0x5f, 0xaf, + 0x8c, 0x43, 0xe9, 0x05, 0xee, 0x56, 0xc6, 0x89, 0xec, 0x20, 0xa7, 0x03, 0xd3, 0x41, 0x69, 0xa9, + 0x04, 0xf3, 0x1c, 0x9d, 0xe4, 0x76, 0xaf, 0xa3, 0x70, 0xe1, 0xf1, 0x8c, 0x11, 0xac, 0x23, 0x04, + 0x65, 0x01, 0x9a, 0xda, 0xa9, 0x74, 0x8f, 0x9d, 0x3d, 0x64, 0x58, 0x5d, 0xde, 0x1a, 0xaa, 0xf9, + 0x11, 0x35, 0x2f, 0x69, 0x92, 0x7a, 0x01, 0x1f, 0x45, 0xfc, 0x82, 0x31, 0x4f, 0xe0, 0x57, 0xe8, + 0x29, 0xf9, 0xc2, 0x99, 0xe7, 0xfa, 0x11, 0x07, 0x17, 0x38, 0x65, 0xa4, 0x18, 0xd6, 0x69, 0xe6, + 0xc4, 0x28, 0xe2, 0x70, 0x9d, 0xc3, 0xb8, 0x85, 0x6a, 0x24, 0x26, 0x09, 0xc8, 0x6f, 0xc2, 0x91, + 0xc5, 0xf0, 0xe8, 0xfb, 0x8d, 0xa1, 0xdc, 0x6c, 0x33, 0xbd, 0xfc, 0xb9, 0xd6, 0xd5, 0xe5, 0x5a, + 0x57, 0x7f, 0xaf, 0x75, 0xf5, 0xeb, 0x46, 0x57, 0x96, 0x1b, 0x5d, 0xf9, 0xb5, 0xd1, 0x95, 0x0f, + 0x2f, 0xc3, 0x88, 0xcf, 0x32, 0xdf, 0x0a, 0x68, 0x62, 0xcb, 0x18, 0x8a, 0xdb, 0x19, 0x4c, 0xe7, + 0xf6, 0xfe, 0xdf, 0xe0, 0x3f, 0xca, 0x37, 0xf7, 0xfa, 0x6f, 0x00, 0x00, 0x00, 0xff, 0xff, 0xa8, + 0xe1, 0x36, 0x1c, 0x24, 0x03, 0x00, 0x00, } func (m *PublicKey) Marshal() (dAtA []byte, err error) { @@ -565,11 +553,15 @@ func (m *MultiSignature) MarshalToSizedBuffer(dAtA []byte) (int, error) { _ = i var l int _ = l - if len(m.Sigs) > 0 { - for iNdEx := len(m.Sigs) - 1; iNdEx >= 0; iNdEx-- { - i -= len(m.Sigs[iNdEx]) - copy(dAtA[i:], m.Sigs[iNdEx]) - i = encodeVarintTypes(dAtA, i, uint64(len(m.Sigs[iNdEx]))) + if m.XXX_unrecognized != nil { + i -= len(m.XXX_unrecognized) + copy(dAtA[i:], m.XXX_unrecognized) + } + if len(m.Signatures) > 0 { + for iNdEx := len(m.Signatures) - 1; iNdEx >= 0; iNdEx-- { + i -= len(m.Signatures[iNdEx]) + copy(dAtA[i:], m.Signatures[iNdEx]) + i = encodeVarintTypes(dAtA, i, uint64(len(m.Signatures[iNdEx]))) i-- dAtA[i] = 0xa } @@ -731,12 +723,15 @@ func (m *MultiSignature) Size() (n int) { } var l int _ = l - if len(m.Sigs) > 0 { - for _, b := range m.Sigs { + if len(m.Signatures) > 0 { + for _, b := range m.Signatures { l = len(b) n += 1 + l + sovTypes(uint64(l)) } } + if m.XXX_unrecognized != nil { + n += len(m.XXX_unrecognized) + } return n } @@ -1138,7 +1133,7 @@ func (m *MultiSignature) Unmarshal(dAtA []byte) error { switch fieldNum { case 1: if wireType != 2 { - return fmt.Errorf("proto: wrong wireType = %d for field Sigs", wireType) + return fmt.Errorf("proto: wrong wireType = %d for field Signatures", wireType) } var byteLen int for shift := uint(0); ; shift += 7 { @@ -1165,8 +1160,8 @@ func (m *MultiSignature) Unmarshal(dAtA []byte) error { if postIndex > l { return io.ErrUnexpectedEOF } - m.Sigs = append(m.Sigs, make([]byte, postIndex-iNdEx)) - copy(m.Sigs[len(m.Sigs)-1], dAtA[iNdEx:postIndex]) + m.Signatures = append(m.Signatures, make([]byte, postIndex-iNdEx)) + copy(m.Signatures[len(m.Signatures)-1], dAtA[iNdEx:postIndex]) iNdEx = postIndex default: iNdEx = preIndex @@ -1183,6 +1178,7 @@ func (m *MultiSignature) Unmarshal(dAtA []byte) error { if (iNdEx + skippy) > l { return io.ErrUnexpectedEOF } + m.XXX_unrecognized = append(m.XXX_unrecognized, dAtA[iNdEx:iNdEx+skippy]...) iNdEx += skippy } } diff --git a/crypto/types/types.proto b/crypto/types/types.proto index 2496ad8e30d6..9015296d64de 100644 --- a/crypto/types/types.proto +++ b/crypto/types/types.proto @@ -20,20 +20,23 @@ message PublicKey { // not explicitly defined in the oneof google.protobuf.Any any_pubkey = 15; // 15 is largest field that occupies one byte } + + option (gogoproto.typedecl) = false; } // PubKeyMultisigThreshold specifies a public key type which nests multiple public // keys and a threshold message PubKeyMultisigThreshold { uint32 threshold = 1 [(gogoproto.customname) = "K", (gogoproto.moretags) = "yaml:\"threshold\""]; - repeated PublicKey pubkeys = 2 [(gogoproto.customname) = "PubKeys", (gogoproto.moretags) = "yaml:\"pubkeys\""]; + repeated PublicKey public_keys = 2 [(gogoproto.customname) = "PubKeys", (gogoproto.moretags) = "yaml:\"pubkeys\""]; } // MultiSignature wraps the signatures from a PubKeyMultisigThreshold. // See cosmos_sdk.tx.v1.ModeInfo.Multi for how to specify which signers signed // and with which modes message MultiSignature { - repeated bytes sigs = 1; + option (gogoproto.goproto_unrecognized) = true; + repeated bytes signatures = 1; } // CompactBitArray is an implementation of a space efficient bit array. diff --git a/types/result.go b/types/result.go index 156cd340c0f8..f1ff7e46c69d 100644 --- a/types/result.go +++ b/types/result.go @@ -9,10 +9,9 @@ import ( yaml "gopkg.in/yaml.v2" - ctypes "github.com/tendermint/tendermint/rpc/core/types" - "github.com/cosmos/cosmos-sdk/codec/legacy" "github.com/cosmos/cosmos-sdk/codec/types" + ctypes "github.com/tendermint/tendermint/rpc/core/types" ) func (gi GasInfo) String() string { diff --git a/types/tx/interface.go b/types/tx/interface.go new file mode 100644 index 000000000000..77e036b56b55 --- /dev/null +++ b/types/tx/interface.go @@ -0,0 +1,38 @@ +package types + +import ( + sdk "github.com/cosmos/cosmos-sdk/types" +) + +type ProtoTx interface { + sdk.Tx + FeeTx + TxWithMemo + SigTx + + GetBody() *TxBody + GetAuthInfo() *AuthInfo + GetSignatures() [][]byte + + GetBodyBytes() []byte + GetAuthInfoBytes() []byte +} + +// FeeTx defines the interface to be implemented by Tx to use the FeeDecorators +type FeeTx interface { + sdk.Tx + GetGas() uint64 + GetFee() sdk.Coins + FeePayer() sdk.AccAddress +} + +// Tx must have GetMemo() method to use ValidateMemoDecorator +type TxWithMemo interface { + sdk.Tx + GetMemo() string +} + +type SigTx interface { + sdk.Tx + GetSignaturesV2() ([]SignatureV2, error) +} diff --git a/types/tx/signature.go b/types/tx/signature.go new file mode 100644 index 000000000000..9c7db87978de --- /dev/null +++ b/types/tx/signature.go @@ -0,0 +1,64 @@ +package types + +import ( + "github.com/cosmos/cosmos-sdk/crypto/types" + "github.com/tendermint/tendermint/crypto" +) + +type SignatureV2 struct { + PubKey crypto.PubKey + Data SignatureData +} + +type SignatureData interface { + isSignatureData() +} + +type SingleSignatureData struct { + SignMode SignMode + Signature []byte +} + +type MultiSignatureData struct { + BitArray *types.CompactBitArray + Signatures []SignatureData +} + +var _, _ SignatureData = &SingleSignatureData{}, &MultiSignatureData{} + +func (m *SingleSignatureData) isSignatureData() {} +func (m *MultiSignatureData) isSignatureData() {} + +func ModeInfoToSignatureData(modeInfo *ModeInfo, sig []byte) (SignatureData, error) { + switch modeInfo := modeInfo.Sum.(type) { + case *ModeInfo_Single_: + return &SingleSignatureData{ + SignMode: modeInfo.Single.Mode, + Signature: sig, + }, nil + + case *ModeInfo_Multi_: + multi := modeInfo.Multi + + sigs, err := types.DecodeMultisignatures(sig) + if err != nil { + return nil, err + } + + sigData := make([]SignatureData, len(sigs)) + for i, mi := range multi.ModeInfos { + sigData[i], err = ModeInfoToSignatureData(mi, sigs[i]) + if err != nil { + return nil, err + } + } + + return &MultiSignatureData{ + BitArray: multi.Bitarray, + Signatures: sigData, + }, nil + + default: + panic("unexpected case") + } +} diff --git a/types/tx/tx.go b/types/tx/tx.go new file mode 100644 index 000000000000..aae11e4f8103 --- /dev/null +++ b/types/tx/tx.go @@ -0,0 +1,174 @@ +package types + +import ( + "github.com/tendermint/tendermint/crypto" + + codectypes "github.com/cosmos/cosmos-sdk/codec/types" + sdk "github.com/cosmos/cosmos-sdk/types" + sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" +) + +var _ ProtoTx = &Tx{} + +func NewTx() *Tx { + return &Tx{ + Body: &TxBody{}, + AuthInfo: &AuthInfo{ + SignerInfos: nil, + Fee: &Fee{}, + }, + Signatures: nil, + } +} + +func (tx *Tx) GetMsgs() []sdk.Msg { + anys := tx.Body.Messages + res := make([]sdk.Msg, len(anys)) + for i, any := range anys { + msg := any.GetCachedValue().(sdk.Msg) + res[i] = msg + } + return res +} + +func (tx *Tx) ValidateBasic() error { + sigs := tx.GetSignatures() + + if tx.GetGas() > MaxGasWanted { + return sdkerrors.Wrapf( + sdkerrors.ErrInvalidRequest, + "invalid gas supplied; %d > %d", tx.GetGas(), MaxGasWanted, + ) + } + if tx.GetFee().IsAnyNegative() { + return sdkerrors.Wrapf( + sdkerrors.ErrInsufficientFee, + "invalid fee provided: %s", tx.GetFee(), + ) + } + if len(sigs) == 0 { + return sdkerrors.ErrNoSignatures + } + if len(sigs) != len(tx.GetSigners()) { + return sdkerrors.Wrapf( + sdkerrors.ErrUnauthorized, + "wrong number of signers; expected %d, got %d", tx.GetSigners(), len(sigs), + ) + } + + return nil +} + +func (m *Tx) GetGas() uint64 { + return m.AuthInfo.Fee.GasLimit +} + +func (m *Tx) GetFee() sdk.Coins { + return m.AuthInfo.Fee.Amount +} + +func (m *Tx) FeePayer() sdk.AccAddress { + signers := m.GetSigners() + if signers != nil { + return signers[0] + } + return sdk.AccAddress{} +} + +func (m *Tx) GetMemo() string { + if m.Body == nil { + return "" + } + return m.Body.Memo +} + +func (m *Tx) GetSigners() []sdk.AccAddress { + var signers []sdk.AccAddress + seen := map[string]bool{} + + for _, msg := range m.GetMsgs() { + for _, addr := range msg.GetSigners() { + if !seen[addr.String()] { + signers = append(signers, addr) + seen[addr.String()] = true + } + } + } + return signers +} + +func (m *Tx) GetPubKeys() []crypto.PubKey { + signerInfos := m.AuthInfo.SignerInfos + res := make([]crypto.PubKey, len(signerInfos)) + for i, si := range signerInfos { + res[i] = si.PublicKey.GetCachedPubKey() + } + return res +} + +func (m *Tx) GetBodyBytes() []byte { + bz, err := m.Body.Marshal() + if err != nil { + panic(err) + } + return bz +} + +func (m *Tx) GetAuthInfoBytes() []byte { + bz, err := m.AuthInfo.Marshal() + if err != nil { + panic(err) + } + return bz +} + +var _ codectypes.UnpackInterfacesMessage = &Tx{} +var _ codectypes.UnpackInterfacesMessage = &TxBody{} +var _ codectypes.UnpackInterfacesMessage = &SignDoc{} + +func (m *Tx) UnpackInterfaces(unpacker codectypes.AnyUnpacker) error { + if m.Body != nil { + return m.Body.UnpackInterfaces(unpacker) + } + return nil +} + +func (m *SignDoc) UnpackInterfaces(unpacker codectypes.AnyUnpacker) error { + return m.Body.UnpackInterfaces(unpacker) +} + +func (m *TxBody) UnpackInterfaces(unpacker codectypes.AnyUnpacker) error { + for _, any := range m.Messages { + var msg sdk.Msg + err := unpacker.UnpackAny(any, &msg) + if err != nil { + return err + } + } + return nil +} + +func (m *Tx) GetSignaturesV2() ([]SignatureV2, error) { + signerInfos := m.AuthInfo.SignerInfos + sigs := m.Signatures + n := len(signerInfos) + res := make([]SignatureV2, n) + + for i, si := range signerInfos { + var err error + + data, err := ModeInfoToSignatureData(si.ModeInfo, sigs[i]) + if err != nil { + return nil, err + } + + pubKey := si.PublicKey.GetCachedPubKey() + + res[i] = SignatureV2{ + PubKey: pubKey, + Data: data, + } + } + + return res, nil +} diff --git a/x/bank/types/query.pb.go b/x/bank/types/query.pb.go index b9223cf7e00f..bd25ff3fb91a 100644 --- a/x/bank/types/query.pb.go +++ b/x/bank/types/query.pb.go @@ -30,7 +30,7 @@ var _ = math.Inf // proto package needs to be updated. const _ = proto.GoGoProtoPackageIsVersion3 // please upgrade the proto package -// QueryBalanceRequest is the request type for the Query.Balance RPC method +// QueryBalanceRequest is the request type for the Query/Balance RPC method type QueryBalanceRequest struct { // address is the address to query balances for Address github_com_cosmos_cosmos_sdk_types.AccAddress `protobuf:"bytes,1,opt,name=address,proto3,casttype=github.com/cosmos/cosmos-sdk/types.AccAddress" json:"address,omitempty"` @@ -85,7 +85,7 @@ func (m *QueryBalanceRequest) GetDenom() string { return "" } -// QueryBalanceResponse is the response type for the Query.Balance RPC method +// QueryBalanceResponse is the response type for the Query/Balance RPC method type QueryBalanceResponse struct { // balance is the balance of the coin Balance *types.Coin `protobuf:"bytes,1,opt,name=balance,proto3" json:"balance,omitempty"` @@ -131,7 +131,7 @@ func (m *QueryBalanceResponse) GetBalance() *types.Coin { return nil } -// QueryBalanceRequest is the request type for the Query.AllBalances RPC method +// QueryBalanceRequest is the request type for the Query/AllBalances RPC method type QueryAllBalancesRequest struct { // address is the address to query balances for Address github_com_cosmos_cosmos_sdk_types.AccAddress `protobuf:"bytes,1,opt,name=address,proto3,casttype=github.com/cosmos/cosmos-sdk/types.AccAddress" json:"address,omitempty"` @@ -177,7 +177,7 @@ func (m *QueryAllBalancesRequest) GetAddress() github_com_cosmos_cosmos_sdk_type return nil } -// QueryAllBalancesResponse is the response type for the Query.AllBalances RPC method +// QueryAllBalancesResponse is the response type for the Query/AllBalances RPC method type QueryAllBalancesResponse struct { // balances is the balances of the coins Balances github_com_cosmos_cosmos_sdk_types.Coins `protobuf:"bytes,1,rep,name=balances,proto3,castrepeated=github.com/cosmos/cosmos-sdk/types.Coins" json:"balances"` @@ -223,7 +223,7 @@ func (m *QueryAllBalancesResponse) GetBalances() github_com_cosmos_cosmos_sdk_ty return nil } -// QueryTotalSupplyRequest is the request type for the Query.TotalSupply RPC method +// QueryTotalSupplyRequest is the request type for the Query/TotalSupply RPC method type QueryTotalSupplyRequest struct { } @@ -260,7 +260,7 @@ func (m *QueryTotalSupplyRequest) XXX_DiscardUnknown() { var xxx_messageInfo_QueryTotalSupplyRequest proto.InternalMessageInfo -// QueryTotalSupplyResponse is the response type for the Query.TotalSupply RPC method +// QueryTotalSupplyResponse is the response type for the Query/TotalSupply RPC method type QueryTotalSupplyResponse struct { // supply is the supply of the coins Supply github_com_cosmos_cosmos_sdk_types.Coins `protobuf:"bytes,1,rep,name=supply,proto3,castrepeated=github.com/cosmos/cosmos-sdk/types.Coins" json:"supply"` @@ -306,7 +306,7 @@ func (m *QueryTotalSupplyResponse) GetSupply() github_com_cosmos_cosmos_sdk_type return nil } -// QuerySupplyOfRequest is the request type for the Query.SupplyOf RPC method +// QuerySupplyOfRequest is the request type for the Query/SupplyOf RPC method type QuerySupplyOfRequest struct { Denom string `protobuf:"bytes,1,opt,name=denom,proto3" json:"denom,omitempty"` } @@ -351,7 +351,7 @@ func (m *QuerySupplyOfRequest) GetDenom() string { return "" } -// QuerySupplyOfResponse is the response type for the Query.SupplyOf RPC method +// QuerySupplyOfResponse is the response type for the Query/SupplyOf RPC method type QuerySupplyOfResponse struct { // amount is the supply of the coin Amount github_com_cosmos_cosmos_sdk_types.Int `protobuf:"bytes,1,opt,name=amount,proto3,customtype=github.com/cosmos/cosmos-sdk/types.Int" json:"amount"` From 68f6185a36d11d49656671b0c065b02c7439b83f Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 13:09:55 -0400 Subject: [PATCH 03/23] revert changes --- client/tx_generator.go | 46 +++++++++++++++++++++++++++------------- crypto/types/types.proto | 2 -- go.sum | 3 --- 3 files changed, 31 insertions(+), 20 deletions(-) diff --git a/client/tx_generator.go b/client/tx_generator.go index 575d52ee3c92..f840bd39e922 100644 --- a/client/tx_generator.go +++ b/client/tx_generator.go @@ -1,8 +1,9 @@ package client import ( - sdk "github.com/cosmos/cosmos-sdk/types" - types "github.com/cosmos/cosmos-sdk/types/tx" + "github.com/tendermint/tendermint/crypto" + + "github.com/cosmos/cosmos-sdk/types" ) type ( @@ -10,13 +11,22 @@ type ( // application-defined concrete transaction type. The type returned must // implement TxBuilder. TxGenerator interface { - NewTxBuilder() TxBuilder - // WrapTxBuilder wraps an existing tx in a TxBuilder or returns an error - WrapTxBuilder(tx sdk.Tx) (TxBuilder, error) - TxEncoder() sdk.TxEncoder - TxDecoder() sdk.TxDecoder - TxJSONEncoder() sdk.TxEncoder - TxJSONDecoder() sdk.TxDecoder + NewTx() TxBuilder + NewFee() Fee + NewSignature() Signature + MarshalTx(tx types.Tx) ([]byte, error) + } + + Fee interface { + types.Fee + SetGas(uint64) + SetAmount(types.Coins) + } + + Signature interface { + types.Signature + SetPubKey(crypto.PubKey) error + SetSignature([]byte) } // TxBuilder defines an interface which an application-defined concrete transaction @@ -24,12 +34,18 @@ type ( // signatures, and provide canonical bytes to sign over. The transaction must // also know how to encode itself. TxBuilder interface { - GetTx() types.SigTx + GetTx() types.Tx + + SetMsgs(...types.Msg) error + GetSignatures() []types.Signature + SetSignatures(...Signature) error + GetFee() types.Fee + SetFee(Fee) error + GetMemo() string + SetMemo(string) - SetMsgs(msgs ...sdk.Msg) error - SetSignatures(signatures ...types.SignatureV2) error - SetMemo(memo string) - SetFee(amount sdk.Coins) - SetGasLimit(limit uint64) + // CanonicalSignBytes returns the canonical sign bytes to sign over, given a + // chain ID, along with an account and sequence number. + CanonicalSignBytes(cid string, num, seq uint64) ([]byte, error) } ) diff --git a/crypto/types/types.proto b/crypto/types/types.proto index 9015296d64de..97a2c67859b2 100644 --- a/crypto/types/types.proto +++ b/crypto/types/types.proto @@ -20,8 +20,6 @@ message PublicKey { // not explicitly defined in the oneof google.protobuf.Any any_pubkey = 15; // 15 is largest field that occupies one byte } - - option (gogoproto.typedecl) = false; } // PubKeyMultisigThreshold specifies a public key type which nests multiple public diff --git a/go.sum b/go.sum index 3bae58262634..f3859f33641e 100644 --- a/go.sum +++ b/go.sum @@ -78,7 +78,6 @@ github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDk github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc= github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa/go.mod h1:zn76sxSg3SzpJ0PPJaLDCu+Bu0Lg3sKTORVIj19EIF8= github.com/codahale/hdrhistogram v0.0.0-20161010025455-3a0bb77429bd/go.mod h1:sE/e/2PUdi/liOCUjSTXgM1o87ZssimdTWN964YiIeI= -github.com/confio/ics23 v0.6.0 h1:bQsi55t2+xjW6EWDl83IBF1VWurplbUu+OT6pukeiEo= github.com/confio/ics23-iavl v0.6.0 h1:vVRCuVaP38FCw1kTeEdFuGuiY+2vAGTBQoH7Zxkq/ws= github.com/confio/ics23-iavl v0.6.0/go.mod h1:mmXAxD1vWoO0VP8YHu6mM1QHGv71NQqa1iSVm4HeKcY= github.com/confio/ics23/go v0.0.0-20200323120010-7d9a00f0a2fa/go.mod h1:W1I3XC8d9N8OTu/ct5VJ84ylcOunZwMXsWkd27nvVts= @@ -467,8 +466,6 @@ github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UV github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= github.com/stretchr/testify v1.5.1 h1:nOGnQDM7FYENwehXlg/kFVnos3rEvtKTjRvOWSzb6H4= github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= -github.com/stretchr/testify v1.6.0 h1:jlIyCplCJFULU/01vCkhKuTyc3OorI3bJFuw6obfgho= -github.com/stretchr/testify v1.6.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/stretchr/testify v1.6.1 h1:hDPOHmpOpP40lSULcqw7IrRb/u7w6RpDC9399XyoNd0= github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/subosito/gotenv v1.2.0 h1:Slr1R9HxAlEKefgq5jn9U+DnETlIUa6HfgEzj0g5d7s= From 1f0195be7d9a8bfd69bfea0c66e57ec472b7a329 Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 13:12:12 -0400 Subject: [PATCH 04/23] revert changes --- types/result.go | 3 ++- x/bank/types/query.pb.go | 23 ++++++++++++----------- 2 files changed, 14 insertions(+), 12 deletions(-) diff --git a/types/result.go b/types/result.go index f1ff7e46c69d..156cd340c0f8 100644 --- a/types/result.go +++ b/types/result.go @@ -9,9 +9,10 @@ import ( yaml "gopkg.in/yaml.v2" + ctypes "github.com/tendermint/tendermint/rpc/core/types" + "github.com/cosmos/cosmos-sdk/codec/legacy" "github.com/cosmos/cosmos-sdk/codec/types" - ctypes "github.com/tendermint/tendermint/rpc/core/types" ) func (gi GasInfo) String() string { diff --git a/x/bank/types/query.pb.go b/x/bank/types/query.pb.go index bd25ff3fb91a..9ed92eafe322 100644 --- a/x/bank/types/query.pb.go +++ b/x/bank/types/query.pb.go @@ -6,6 +6,10 @@ package types import ( context "context" fmt "fmt" + io "io" + math "math" + math_bits "math/bits" + github_com_cosmos_cosmos_sdk_types "github.com/cosmos/cosmos-sdk/types" types "github.com/cosmos/cosmos-sdk/types" _ "github.com/gogo/protobuf/gogoproto" @@ -14,9 +18,6 @@ import ( grpc "google.golang.org/grpc" codes "google.golang.org/grpc/codes" status "google.golang.org/grpc/status" - io "io" - math "math" - math_bits "math/bits" ) // Reference imports to suppress errors if they are not otherwise used. @@ -30,7 +31,7 @@ var _ = math.Inf // proto package needs to be updated. const _ = proto.GoGoProtoPackageIsVersion3 // please upgrade the proto package -// QueryBalanceRequest is the request type for the Query/Balance RPC method +// QueryBalanceRequest is the request type for the Query.Balance RPC method type QueryBalanceRequest struct { // address is the address to query balances for Address github_com_cosmos_cosmos_sdk_types.AccAddress `protobuf:"bytes,1,opt,name=address,proto3,casttype=github.com/cosmos/cosmos-sdk/types.AccAddress" json:"address,omitempty"` @@ -85,7 +86,7 @@ func (m *QueryBalanceRequest) GetDenom() string { return "" } -// QueryBalanceResponse is the response type for the Query/Balance RPC method +// QueryBalanceResponse is the response type for the Query.Balance RPC method type QueryBalanceResponse struct { // balance is the balance of the coin Balance *types.Coin `protobuf:"bytes,1,opt,name=balance,proto3" json:"balance,omitempty"` @@ -131,7 +132,7 @@ func (m *QueryBalanceResponse) GetBalance() *types.Coin { return nil } -// QueryBalanceRequest is the request type for the Query/AllBalances RPC method +// QueryBalanceRequest is the request type for the Query.AllBalances RPC method type QueryAllBalancesRequest struct { // address is the address to query balances for Address github_com_cosmos_cosmos_sdk_types.AccAddress `protobuf:"bytes,1,opt,name=address,proto3,casttype=github.com/cosmos/cosmos-sdk/types.AccAddress" json:"address,omitempty"` @@ -177,7 +178,7 @@ func (m *QueryAllBalancesRequest) GetAddress() github_com_cosmos_cosmos_sdk_type return nil } -// QueryAllBalancesResponse is the response type for the Query/AllBalances RPC method +// QueryAllBalancesResponse is the response type for the Query.AllBalances RPC method type QueryAllBalancesResponse struct { // balances is the balances of the coins Balances github_com_cosmos_cosmos_sdk_types.Coins `protobuf:"bytes,1,rep,name=balances,proto3,castrepeated=github.com/cosmos/cosmos-sdk/types.Coins" json:"balances"` @@ -223,7 +224,7 @@ func (m *QueryAllBalancesResponse) GetBalances() github_com_cosmos_cosmos_sdk_ty return nil } -// QueryTotalSupplyRequest is the request type for the Query/TotalSupply RPC method +// QueryTotalSupplyRequest is the request type for the Query.TotalSupply RPC method type QueryTotalSupplyRequest struct { } @@ -260,7 +261,7 @@ func (m *QueryTotalSupplyRequest) XXX_DiscardUnknown() { var xxx_messageInfo_QueryTotalSupplyRequest proto.InternalMessageInfo -// QueryTotalSupplyResponse is the response type for the Query/TotalSupply RPC method +// QueryTotalSupplyResponse is the response type for the Query.TotalSupply RPC method type QueryTotalSupplyResponse struct { // supply is the supply of the coins Supply github_com_cosmos_cosmos_sdk_types.Coins `protobuf:"bytes,1,rep,name=supply,proto3,castrepeated=github.com/cosmos/cosmos-sdk/types.Coins" json:"supply"` @@ -306,7 +307,7 @@ func (m *QueryTotalSupplyResponse) GetSupply() github_com_cosmos_cosmos_sdk_type return nil } -// QuerySupplyOfRequest is the request type for the Query/SupplyOf RPC method +// QuerySupplyOfRequest is the request type for the Query.SupplyOf RPC method type QuerySupplyOfRequest struct { Denom string `protobuf:"bytes,1,opt,name=denom,proto3" json:"denom,omitempty"` } @@ -351,7 +352,7 @@ func (m *QuerySupplyOfRequest) GetDenom() string { return "" } -// QuerySupplyOfResponse is the response type for the Query/SupplyOf RPC method +// QuerySupplyOfResponse is the response type for the Query.SupplyOf RPC method type QuerySupplyOfResponse struct { // amount is the supply of the coin Amount github_com_cosmos_cosmos_sdk_types.Int `protobuf:"bytes,1,opt,name=amount,proto3,customtype=github.com/cosmos/cosmos-sdk/types.Int" json:"amount"` From 5d372a060d532f4f1320e9624ec353e2405aa3aa Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 13:12:50 -0400 Subject: [PATCH 05/23] updates --- crypto/types/codec.go | 38 ------------------- crypto/types/types.go | 25 ------------ crypto/types/types.pb.go | 82 +++++++++++++++++++++++----------------- x/bank/types/query.pb.go | 23 ++++++----- 4 files changed, 59 insertions(+), 109 deletions(-) delete mode 100644 crypto/types/codec.go diff --git a/crypto/types/codec.go b/crypto/types/codec.go deleted file mode 100644 index 1230a5a02dca..000000000000 --- a/crypto/types/codec.go +++ /dev/null @@ -1,38 +0,0 @@ -package types - -import ( - "github.com/tendermint/tendermint/crypto" -) - -type PublicKeyCodec interface { - Decode(key *PublicKey) (crypto.PubKey, error) - Encode(key crypto.PubKey) (*PublicKey, error) -} - -type publicKeyCodecCacheMiddleware struct { - cdc PublicKeyCodec -} - -func CacheWrapCodec(cdc PublicKeyCodec) PublicKeyCodec { - return publicKeyCodecCacheMiddleware{cdc: cdc} -} - -var _ PublicKeyCodec = publicKeyCodecCacheMiddleware{} - -func (p publicKeyCodecCacheMiddleware) Decode(key *PublicKey) (crypto.PubKey, error) { - res, err := p.cdc.Decode(key) - if err != nil { - return nil, err - } - key.cachedValue = res - return res, nil -} - -func (p publicKeyCodecCacheMiddleware) Encode(key crypto.PubKey) (*PublicKey, error) { - res, err := p.cdc.Encode(key) - if err != nil { - return nil, err - } - res.cachedValue = key - return res, nil -} diff --git a/crypto/types/types.go b/crypto/types/types.go index 328910919597..d61619e5dcbe 100644 --- a/crypto/types/types.go +++ b/crypto/types/types.go @@ -2,33 +2,8 @@ package types import ( "fmt" - - "github.com/tendermint/tendermint/crypto" ) -// PublicKey specifies a public key -type PublicKey struct { - // sum specifies which type of public key is wrapped - // - // Types that are valid to be assigned to Sum: - // *PublicKey_Secp256K1 - // *PublicKey_Ed25519 - // *PublicKey_Sr25519 - // *PublicKey_Multisig - // *PublicKey_Secp256R1 - // *PublicKey_AminoMultisig - // *PublicKey_AnyPubkey - Sum isPublicKey_Sum `protobuf_oneof:"sum"` - - cachedValue crypto.PubKey -} - -// GetCachedPubKey returns the cached PubKey instance wrapped in the PublicKey. -// This will only be set if the PublicKeyCodec is cache-wrapped using CacheWrapCodec -func (pk PublicKey) GetCachedPubKey() crypto.PubKey { - return pk.cachedValue -} - func DecodeMultisignatures(bz []byte) ([][]byte, error) { multisig := MultiSignature{} err := multisig.Unmarshal(bz) diff --git a/crypto/types/types.pb.go b/crypto/types/types.pb.go index d3b16767e952..a1f1b83dbf56 100644 --- a/crypto/types/types.pb.go +++ b/crypto/types/types.pb.go @@ -24,6 +24,20 @@ var _ = math.Inf // proto package needs to be updated. const _ = proto.GoGoProtoPackageIsVersion3 // please upgrade the proto package +// PublicKey specifies a public key +type PublicKey struct { + // sum specifies which type of public key is wrapped + // + // Types that are valid to be assigned to Sum: + // *PublicKey_Secp256K1 + // *PublicKey_Ed25519 + // *PublicKey_Sr25519 + // *PublicKey_Multisig + // *PublicKey_Secp256R1 + // *PublicKey_AnyPubkey + Sum isPublicKey_Sum `protobuf_oneof:"sum"` +} + func (m *PublicKey) Reset() { *m = PublicKey{} } func (m *PublicKey) String() string { return proto.CompactTextString(m) } func (*PublicKey) ProtoMessage() {} @@ -317,40 +331,40 @@ func init() { func init() { proto.RegisterFile("crypto/types/types.proto", fileDescriptor_2165b2a1badb1b0c) } var fileDescriptor_2165b2a1badb1b0c = []byte{ - // 519 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x74, 0x53, 0x41, 0x6a, 0xdb, 0x40, - 0x14, 0x95, 0x62, 0xbb, 0x89, 0xc7, 0x69, 0xdc, 0x0e, 0x86, 0x2a, 0x86, 0x4a, 0x46, 0x8b, 0xe2, - 0x16, 0x22, 0x61, 0x17, 0xa7, 0xd4, 0xbb, 0x38, 0x9b, 0x80, 0x29, 0x18, 0xa5, 0xab, 0x42, 0x11, - 0x92, 0x3c, 0x95, 0x85, 0x25, 0x8f, 0x98, 0x3f, 0x2a, 0x9d, 0x5b, 0x74, 0xd1, 0x45, 0x97, 0xc9, - 0x19, 0x7a, 0x89, 0x2e, 0xbd, 0xec, 0xca, 0x14, 0xfb, 0x02, 0x25, 0x27, 0x28, 0xd6, 0x48, 0xb1, - 0x29, 0xcd, 0x46, 0xd2, 0x7f, 0xef, 0x8d, 0xfe, 0xfb, 0xef, 0x4b, 0x48, 0x0b, 0x98, 0x48, 0x39, - 0xb5, 0xb9, 0x48, 0x09, 0xc8, 0xab, 0x95, 0x32, 0xca, 0x29, 0x6e, 0x05, 0x14, 0x12, 0x0a, 0x2e, - 0x4c, 0xe7, 0x96, 0x14, 0x59, 0x9f, 0x7b, 0xed, 0x17, 0x7c, 0x16, 0xb1, 0xa9, 0x9b, 0x7a, 0x8c, - 0x0b, 0x3b, 0x17, 0xda, 0x21, 0x0d, 0xe9, 0xee, 0x49, 0x9e, 0x6e, 0x9f, 0x86, 0x94, 0x86, 0x31, - 0x91, 0x12, 0x3f, 0xfb, 0x64, 0x7b, 0x0b, 0x21, 0x29, 0xf3, 0xdb, 0x01, 0xaa, 0x4f, 0x32, 0x3f, - 0x8e, 0x82, 0x31, 0x11, 0x58, 0x47, 0x75, 0x20, 0x41, 0xda, 0x1f, 0x9c, 0xcf, 0x7b, 0x9a, 0xda, - 0x51, 0xbb, 0xc7, 0x57, 0x8a, 0xb3, 0x83, 0x70, 0x1b, 0x1d, 0x92, 0x69, 0x7f, 0x30, 0xe8, 0xbd, - 0xd5, 0x0e, 0x0a, 0xb6, 0x04, 0xb6, 0x1c, 0x30, 0xc9, 0x55, 0x4a, 0xae, 0x00, 0xf0, 0x18, 0x1d, - 0x25, 0x59, 0xcc, 0x23, 0x88, 0x42, 0xad, 0xda, 0x51, 0xbb, 0x8d, 0xfe, 0x99, 0xf5, 0xbf, 0x89, - 0xac, 0x49, 0xe6, 0x8f, 0x89, 0x78, 0x57, 0x68, 0xdf, 0xcf, 0x18, 0x81, 0x19, 0x8d, 0xa7, 0x57, - 0x8a, 0x73, 0xff, 0x82, 0x3d, 0x93, 0xac, 0xa7, 0xd5, 0xfe, 0x31, 0xc9, 0x7a, 0x78, 0x80, 0x90, - 0xb7, 0x10, 0x6e, 0x9a, 0xf9, 0x73, 0x22, 0xb4, 0x66, 0xde, 0xae, 0x65, 0xc9, 0x08, 0xac, 0x32, - 0x02, 0xeb, 0x62, 0x21, 0xb6, 0xc7, 0xbc, 0x85, 0x98, 0xe4, 0xc2, 0x61, 0xf5, 0xcf, 0xad, 0xa1, - 0x8c, 0x6a, 0xa8, 0x02, 0x59, 0x62, 0xfe, 0x50, 0xd1, 0xb3, 0x07, 0xbc, 0xe0, 0x37, 0xa8, 0xce, - 0xcb, 0x22, 0x0f, 0xe9, 0xf1, 0xe8, 0x74, 0xbd, 0x32, 0xd4, 0xf1, 0xdd, 0xca, 0x78, 0x22, 0xbc, - 0x24, 0x1e, 0x9a, 0xf7, 0xbc, 0xe9, 0xec, 0xb4, 0xd8, 0x45, 0x8d, 0x34, 0x8f, 0xda, 0x9d, 0x13, - 0x01, 0xda, 0x41, 0xa7, 0xd2, 0x6d, 0xf4, 0x8d, 0x07, 0x83, 0x90, 0x3b, 0x19, 0x3d, 0x5f, 0xaf, - 0x8c, 0x43, 0xe9, 0x05, 0xee, 0x56, 0xc6, 0x89, 0xec, 0x20, 0xa7, 0x03, 0xd3, 0x41, 0x69, 0xa9, - 0x04, 0xf3, 0x1c, 0x9d, 0xe4, 0x76, 0xaf, 0xa3, 0x70, 0xe1, 0xf1, 0x8c, 0x11, 0xac, 0x23, 0x04, - 0x65, 0x01, 0x9a, 0xda, 0xa9, 0x74, 0x8f, 0x9d, 0x3d, 0x64, 0x58, 0x5d, 0xde, 0x1a, 0xaa, 0xf9, - 0x11, 0x35, 0x2f, 0x69, 0x92, 0x7a, 0x01, 0x1f, 0x45, 0xfc, 0x82, 0x31, 0x4f, 0xe0, 0x57, 0xe8, - 0x29, 0xf9, 0xc2, 0x99, 0xe7, 0xfa, 0x11, 0x07, 0x17, 0x38, 0x65, 0xa4, 0x18, 0xd6, 0x69, 0xe6, - 0xc4, 0x28, 0xe2, 0x70, 0x9d, 0xc3, 0xb8, 0x85, 0x6a, 0x24, 0x26, 0x09, 0xc8, 0x6f, 0xc2, 0x91, - 0xc5, 0xf0, 0xe8, 0xfb, 0x8d, 0xa1, 0xdc, 0x6c, 0x33, 0xbd, 0xfc, 0xb9, 0xd6, 0xd5, 0xe5, 0x5a, - 0x57, 0x7f, 0xaf, 0x75, 0xf5, 0xeb, 0x46, 0x57, 0x96, 0x1b, 0x5d, 0xf9, 0xb5, 0xd1, 0x95, 0x0f, - 0x2f, 0xc3, 0x88, 0xcf, 0x32, 0xdf, 0x0a, 0x68, 0x62, 0xcb, 0x18, 0x8a, 0xdb, 0x19, 0x4c, 0xe7, - 0xf6, 0xfe, 0xdf, 0xe0, 0x3f, 0xca, 0x37, 0xf7, 0xfa, 0x6f, 0x00, 0x00, 0x00, 0xff, 0xff, 0xa8, - 0xe1, 0x36, 0x1c, 0x24, 0x03, 0x00, 0x00, + // 514 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x74, 0x53, 0xc1, 0x6a, 0xdb, 0x4a, + 0x14, 0x95, 0xec, 0xf8, 0x25, 0x1e, 0xe7, 0xc5, 0xed, 0x60, 0xa8, 0x62, 0xa8, 0x64, 0xb4, 0x28, + 0x6e, 0x21, 0x12, 0x76, 0x71, 0x4a, 0xbd, 0x8b, 0xb2, 0x09, 0x98, 0x82, 0x51, 0xba, 0x2a, 0x14, + 0x21, 0xc9, 0x53, 0x59, 0x58, 0xf2, 0x88, 0xb9, 0xa3, 0xd2, 0xf9, 0x89, 0xd2, 0x65, 0x97, 0xc9, + 0x37, 0xf4, 0x27, 0xba, 0xf4, 0xb2, 0x2b, 0x53, 0xec, 0x3f, 0xc8, 0x17, 0x94, 0x68, 0xa4, 0xd8, + 0x94, 0x66, 0x23, 0xe9, 0x9e, 0x73, 0x46, 0xf7, 0xdc, 0x73, 0x25, 0xa4, 0x85, 0x4c, 0x64, 0x9c, + 0xda, 0x5c, 0x64, 0x04, 0xe4, 0xd5, 0xca, 0x18, 0xe5, 0x14, 0x77, 0x42, 0x0a, 0x29, 0x05, 0x0f, + 0x66, 0x0b, 0x4b, 0x8a, 0xac, 0xcf, 0x83, 0xee, 0x0b, 0x3e, 0x8f, 0xd9, 0xcc, 0xcb, 0x7c, 0xc6, + 0x85, 0x5d, 0x08, 0xed, 0x88, 0x46, 0x74, 0xf7, 0x24, 0x4f, 0x77, 0x4f, 0x23, 0x4a, 0xa3, 0x84, + 0x48, 0x49, 0x90, 0x7f, 0xb2, 0xfd, 0xa5, 0x90, 0x94, 0xf9, 0xb5, 0x86, 0x9a, 0xd3, 0x3c, 0x48, + 0xe2, 0x70, 0x42, 0x04, 0xd6, 0x51, 0x13, 0x48, 0x98, 0x0d, 0x47, 0xe7, 0x8b, 0x81, 0xa6, 0xf6, + 0xd4, 0xfe, 0xf1, 0x95, 0xe2, 0xee, 0x20, 0xdc, 0x45, 0x87, 0x64, 0x36, 0x1c, 0x8d, 0x06, 0x6f, + 0xb5, 0x5a, 0xc9, 0x56, 0xc0, 0x3d, 0x07, 0x4c, 0x72, 0xf5, 0x8a, 0x2b, 0x01, 0x3c, 0x41, 0x47, + 0x69, 0x9e, 0xf0, 0x18, 0xe2, 0x48, 0x3b, 0xe8, 0xa9, 0xfd, 0xd6, 0xf0, 0xcc, 0xfa, 0xd7, 0x44, + 0xd6, 0x34, 0x0f, 0x26, 0x44, 0xbc, 0x2b, 0xb5, 0xef, 0xe7, 0x8c, 0xc0, 0x9c, 0x26, 0xb3, 0x2b, + 0xc5, 0x7d, 0x78, 0xc1, 0x9e, 0x49, 0x36, 0xd0, 0x1a, 0x7f, 0x99, 0x64, 0x03, 0x3c, 0x42, 0xc8, + 0x5f, 0x0a, 0x2f, 0xcb, 0x83, 0x05, 0x11, 0x5a, 0xbb, 0x68, 0xd7, 0xb1, 0x64, 0x04, 0x56, 0x15, + 0x81, 0x75, 0xb1, 0x14, 0xf7, 0xc7, 0xfc, 0xa5, 0x98, 0x16, 0x42, 0xa7, 0x81, 0xea, 0x90, 0xa7, + 0xe6, 0x0f, 0x15, 0x3d, 0x7b, 0xc4, 0x05, 0x7e, 0x83, 0x9a, 0xbc, 0x2a, 0x8a, 0x78, 0xfe, 0x77, + 0x4e, 0x37, 0x6b, 0x43, 0x9d, 0xdc, 0xad, 0x8d, 0x27, 0xc2, 0x4f, 0x93, 0xb1, 0xf9, 0xc0, 0x9b, + 0xee, 0x4e, 0x8b, 0x3d, 0xd4, 0xca, 0x8a, 0x90, 0xbd, 0x05, 0x11, 0xa0, 0xd5, 0x7a, 0xf5, 0x7e, + 0x6b, 0x68, 0x3c, 0x1a, 0x81, 0xdc, 0x86, 0xf3, 0x7c, 0xb3, 0x36, 0x0e, 0xa5, 0x17, 0xb8, 0x5b, + 0x1b, 0x27, 0xb2, 0x83, 0x9c, 0x0b, 0x4c, 0x17, 0x65, 0x95, 0x12, 0xcc, 0x73, 0x74, 0x52, 0xd8, + 0xbd, 0x8e, 0xa3, 0xa5, 0xcf, 0x73, 0x46, 0xb0, 0x8e, 0x10, 0x54, 0x05, 0x68, 0x6a, 0xaf, 0xde, + 0x3f, 0x76, 0xf7, 0x90, 0xf1, 0xc1, 0xea, 0xd6, 0x50, 0xcd, 0x8f, 0xa8, 0x7d, 0x49, 0xd3, 0xcc, + 0x0f, 0xb9, 0x13, 0xf3, 0x0b, 0xc6, 0x7c, 0x81, 0x5f, 0xa1, 0xa7, 0xe4, 0x0b, 0x67, 0xbe, 0x17, + 0xc4, 0x1c, 0x3c, 0xe0, 0x94, 0x91, 0x72, 0x58, 0xb7, 0x5d, 0x10, 0x4e, 0xcc, 0xe1, 0xba, 0x80, + 0x71, 0x07, 0x35, 0x48, 0x42, 0x52, 0x90, 0x5f, 0x83, 0x2b, 0x8b, 0xf1, 0xd1, 0xf7, 0x1b, 0x43, + 0xb9, 0xb9, 0x35, 0x14, 0xe7, 0xf2, 0xe7, 0x46, 0x57, 0x57, 0x1b, 0x5d, 0xfd, 0xbd, 0xd1, 0xd5, + 0x6f, 0x5b, 0x5d, 0x59, 0x6d, 0x75, 0xe5, 0xd7, 0x56, 0x57, 0x3e, 0xbc, 0x8c, 0x62, 0x3e, 0xcf, + 0x03, 0x2b, 0xa4, 0xa9, 0x2d, 0x63, 0x28, 0x6f, 0x67, 0x30, 0x5b, 0xd8, 0xfb, 0xff, 0x41, 0xf0, + 0x5f, 0xb1, 0xb3, 0xd7, 0x7f, 0x02, 0x00, 0x00, 0xff, 0xff, 0xb8, 0x46, 0x56, 0x25, 0x1e, 0x03, + 0x00, 0x00, } func (m *PublicKey) Marshal() (dAtA []byte, err error) { diff --git a/x/bank/types/query.pb.go b/x/bank/types/query.pb.go index 9ed92eafe322..bd25ff3fb91a 100644 --- a/x/bank/types/query.pb.go +++ b/x/bank/types/query.pb.go @@ -6,10 +6,6 @@ package types import ( context "context" fmt "fmt" - io "io" - math "math" - math_bits "math/bits" - github_com_cosmos_cosmos_sdk_types "github.com/cosmos/cosmos-sdk/types" types "github.com/cosmos/cosmos-sdk/types" _ "github.com/gogo/protobuf/gogoproto" @@ -18,6 +14,9 @@ import ( grpc "google.golang.org/grpc" codes "google.golang.org/grpc/codes" status "google.golang.org/grpc/status" + io "io" + math "math" + math_bits "math/bits" ) // Reference imports to suppress errors if they are not otherwise used. @@ -31,7 +30,7 @@ var _ = math.Inf // proto package needs to be updated. const _ = proto.GoGoProtoPackageIsVersion3 // please upgrade the proto package -// QueryBalanceRequest is the request type for the Query.Balance RPC method +// QueryBalanceRequest is the request type for the Query/Balance RPC method type QueryBalanceRequest struct { // address is the address to query balances for Address github_com_cosmos_cosmos_sdk_types.AccAddress `protobuf:"bytes,1,opt,name=address,proto3,casttype=github.com/cosmos/cosmos-sdk/types.AccAddress" json:"address,omitempty"` @@ -86,7 +85,7 @@ func (m *QueryBalanceRequest) GetDenom() string { return "" } -// QueryBalanceResponse is the response type for the Query.Balance RPC method +// QueryBalanceResponse is the response type for the Query/Balance RPC method type QueryBalanceResponse struct { // balance is the balance of the coin Balance *types.Coin `protobuf:"bytes,1,opt,name=balance,proto3" json:"balance,omitempty"` @@ -132,7 +131,7 @@ func (m *QueryBalanceResponse) GetBalance() *types.Coin { return nil } -// QueryBalanceRequest is the request type for the Query.AllBalances RPC method +// QueryBalanceRequest is the request type for the Query/AllBalances RPC method type QueryAllBalancesRequest struct { // address is the address to query balances for Address github_com_cosmos_cosmos_sdk_types.AccAddress `protobuf:"bytes,1,opt,name=address,proto3,casttype=github.com/cosmos/cosmos-sdk/types.AccAddress" json:"address,omitempty"` @@ -178,7 +177,7 @@ func (m *QueryAllBalancesRequest) GetAddress() github_com_cosmos_cosmos_sdk_type return nil } -// QueryAllBalancesResponse is the response type for the Query.AllBalances RPC method +// QueryAllBalancesResponse is the response type for the Query/AllBalances RPC method type QueryAllBalancesResponse struct { // balances is the balances of the coins Balances github_com_cosmos_cosmos_sdk_types.Coins `protobuf:"bytes,1,rep,name=balances,proto3,castrepeated=github.com/cosmos/cosmos-sdk/types.Coins" json:"balances"` @@ -224,7 +223,7 @@ func (m *QueryAllBalancesResponse) GetBalances() github_com_cosmos_cosmos_sdk_ty return nil } -// QueryTotalSupplyRequest is the request type for the Query.TotalSupply RPC method +// QueryTotalSupplyRequest is the request type for the Query/TotalSupply RPC method type QueryTotalSupplyRequest struct { } @@ -261,7 +260,7 @@ func (m *QueryTotalSupplyRequest) XXX_DiscardUnknown() { var xxx_messageInfo_QueryTotalSupplyRequest proto.InternalMessageInfo -// QueryTotalSupplyResponse is the response type for the Query.TotalSupply RPC method +// QueryTotalSupplyResponse is the response type for the Query/TotalSupply RPC method type QueryTotalSupplyResponse struct { // supply is the supply of the coins Supply github_com_cosmos_cosmos_sdk_types.Coins `protobuf:"bytes,1,rep,name=supply,proto3,castrepeated=github.com/cosmos/cosmos-sdk/types.Coins" json:"supply"` @@ -307,7 +306,7 @@ func (m *QueryTotalSupplyResponse) GetSupply() github_com_cosmos_cosmos_sdk_type return nil } -// QuerySupplyOfRequest is the request type for the Query.SupplyOf RPC method +// QuerySupplyOfRequest is the request type for the Query/SupplyOf RPC method type QuerySupplyOfRequest struct { Denom string `protobuf:"bytes,1,opt,name=denom,proto3" json:"denom,omitempty"` } @@ -352,7 +351,7 @@ func (m *QuerySupplyOfRequest) GetDenom() string { return "" } -// QuerySupplyOfResponse is the response type for the Query.SupplyOf RPC method +// QuerySupplyOfResponse is the response type for the Query/SupplyOf RPC method type QuerySupplyOfResponse struct { // amount is the supply of the coin Amount github_com_cosmos_cosmos_sdk_types.Int `protobuf:"bytes,1,opt,name=amount,proto3,customtype=github.com/cosmos/cosmos-sdk/types.Int" json:"amount"` From 7f2a1171897bc735577c5d57cfd282f0dba29f6c Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 13:13:57 -0400 Subject: [PATCH 06/23] Updates --- crypto/codec/default.go | 87 ----------------------------------------- 1 file changed, 87 deletions(-) delete mode 100644 crypto/codec/default.go diff --git a/crypto/codec/default.go b/crypto/codec/default.go deleted file mode 100644 index 7716cf5b1d2c..000000000000 --- a/crypto/codec/default.go +++ /dev/null @@ -1,87 +0,0 @@ -package codec - -import ( - "fmt" - - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" - - "github.com/tendermint/tendermint/crypto" - ed255192 "github.com/tendermint/tendermint/crypto/ed25519" - "github.com/tendermint/tendermint/crypto/secp256k1" - "github.com/tendermint/tendermint/crypto/sr25519" - - "github.com/cosmos/cosmos-sdk/crypto/types" -) - -type DefaultPublicKeyCodec struct{} - -var _ types.PublicKeyCodec = DefaultPublicKeyCodec{} - -func (cdc DefaultPublicKeyCodec) Decode(key *types.PublicKey) (crypto.PubKey, error) { - switch key := key.Sum.(type) { - case *types.PublicKey_Secp256K1: - n := len(key.Secp256K1) - if n != secp256k1.PubKeySecp256k1Size { - return nil, fmt.Errorf("wrong length %d for secp256k1 public key", n) - } - var res secp256k1.PubKeySecp256k1 - copy(res[:], key.Secp256K1) - return res, nil - case *types.PublicKey_Ed25519: - n := len(key.Ed25519) - if n != ed255192.PubKeyEd25519Size { - return nil, fmt.Errorf("wrong length %d for ed25519 public key", n) - } - var res ed255192.PubKeyEd25519 - copy(res[:], key.Ed25519) - return res, nil - case *types.PublicKey_Sr25519: - n := len(key.Sr25519) - if n != sr25519.PubKeySr25519Size { - return nil, fmt.Errorf("wrong length %d for sr25519 public key", n) - } - var res sr25519.PubKeySr25519 - copy(res[:], key.Sr25519) - return res, nil - case *types.PublicKey_Multisig: - pubKeys := key.Multisig.PubKeys - resKeys := make([]crypto.PubKey, len(pubKeys)) - for i, k := range pubKeys { - dk, err := cdc.Decode(k) - if err != nil { - return nil, err - } - resKeys[i] = dk - } - return multisig.NewPubKeyMultisigThreshold(key.Multisig.K, resKeys), nil - default: - return nil, fmt.Errorf("can't encode PubKey of type %T", key) - } -} - -func (cdc DefaultPublicKeyCodec) Encode(key crypto.PubKey) (*types.PublicKey, error) { - switch key := key.(type) { - case secp256k1.PubKeySecp256k1: - return &types.PublicKey{Sum: &types.PublicKey_Secp256K1{Secp256K1: key[:]}}, nil - case ed255192.PubKeyEd25519: - return &types.PublicKey{Sum: &types.PublicKey_Ed25519{Ed25519: key[:]}}, nil - case sr25519.PubKeySr25519: - return &types.PublicKey{Sum: &types.PublicKey_Sr25519{Sr25519: key[:]}}, nil - case multisig.ThresholdMultisigPubKey: - pubKeys := key.PubKeys - resKeys := make([]*types.PublicKey, len(pubKeys)) - for i, k := range pubKeys { - dk, err := cdc.Encode(k) - if err != nil { - return nil, err - } - resKeys[i] = dk - } - return &types.PublicKey{Sum: &types.PublicKey_Multisig{Multisig: &types.PubKeyMultisigThreshold{ - K: key.K, - PubKeys: resKeys, - }}}, nil - default: - return nil, fmt.Errorf("can't encode PubKey of type %T", key) - } -} From b0915da3b459759e171804775c049103e58c23bc Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 14:34:07 -0400 Subject: [PATCH 07/23] Integrate multisig support --- client/keys/add.go | 4 +- client/keys/show.go | 4 +- client/keys/show_test.go | 2 +- crypto/codec/amino.go | 2 +- crypto/keyring/info.go | 4 +- crypto/keyring/keyring_test.go | 2 +- crypto/keyring/output_test.go | 2 +- .../multisig/codec.go => multisig/amino.go} | 8 + crypto/multisig/multisig_pubkey.go | 17 ++ crypto/{types => }/multisig/multisignature.go | 40 ++-- .../{types => }/multisig/threshold_pubkey.go | 70 ++++--- .../multisig/threshold_pubkey_test.go | 65 +++---- go.sum | 3 + types/tx/interface.go | 38 ---- types/tx/signature.go | 64 ------- types/tx/signing/signature.go | 8 + types/tx/signing/signature_data.go | 24 +++ types/tx/signing/types.pb.go | 84 +++++++++ types/tx/signing/types.proto | 22 +++ types/tx/tx.go | 174 ------------------ types/tx/types.pb.go | 153 ++++++--------- types/tx/types.proto | 21 +-- x/auth/ante/ante_test.go | 2 +- x/auth/ante/basic.go | 2 +- x/auth/ante/sigverify.go | 6 +- x/auth/ante/sigverify_test.go | 14 +- x/auth/client/cli/tx_multisign.go | 10 +- x/auth/client/cli/validate_sigs.go | 4 +- x/auth/signing/amino/amino.go | 16 +- x/auth/signing/amino/amino_test.go | 11 +- x/auth/signing/handler_map.go | 21 ++- x/auth/signing/handler_map_test.go | 15 +- x/auth/signing/sign_mode_handler.go | 8 +- x/auth/types/stdtx.go | 94 +++++++++- 34 files changed, 486 insertions(+), 528 deletions(-) rename crypto/{types/multisig/codec.go => multisig/amino.go} (75%) create mode 100644 crypto/multisig/multisig_pubkey.go rename crypto/{types => }/multisig/multisignature.go (54%) rename crypto/{types => }/multisig/threshold_pubkey.go (52%) rename crypto/{types => }/multisig/threshold_pubkey_test.go (68%) delete mode 100644 types/tx/interface.go delete mode 100644 types/tx/signature.go create mode 100644 types/tx/signing/signature.go create mode 100644 types/tx/signing/signature_data.go create mode 100644 types/tx/signing/types.pb.go create mode 100644 types/tx/signing/types.proto delete mode 100644 types/tx/tx.go diff --git a/client/keys/add.go b/client/keys/add.go index 1159148edc35..3f433ecd7705 100644 --- a/client/keys/add.go +++ b/client/keys/add.go @@ -14,7 +14,7 @@ import ( "github.com/cosmos/cosmos-sdk/client/input" "github.com/cosmos/cosmos-sdk/crypto/hd" "github.com/cosmos/cosmos-sdk/crypto/keyring" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/spf13/cobra" @@ -169,7 +169,7 @@ func RunAddCmd(cmd *cobra.Command, args []string, kb keyring.Keyring, inBuf *buf }) } - pk := multisig.NewPubKeyMultisigThreshold(multisigThreshold, pks) + pk := multisig.NewPubKeyMultisigThreshold(uint32(multisigThreshold), pks) if _, err := kb.SaveMultisig(name, pk); err != nil { return err } diff --git a/client/keys/show.go b/client/keys/show.go index 465aa0007a89..217efb163a5b 100644 --- a/client/keys/show.go +++ b/client/keys/show.go @@ -13,7 +13,7 @@ import ( "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/crypto" "github.com/cosmos/cosmos-sdk/crypto/keyring" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" sdk "github.com/cosmos/cosmos-sdk/types" ) @@ -83,7 +83,7 @@ func runShowCmd(cmd *cobra.Command, args []string) (err error) { return err } - multikey := multisig.NewPubKeyMultisigThreshold(multisigThreshold, pks) + multikey := multisig.NewPubKeyMultisigThreshold(uint32(multisigThreshold), pks) info = keyring.NewMultiInfo(defaultMultiSigKeyName, multikey) } diff --git a/client/keys/show_test.go b/client/keys/show_test.go index 079e56b4a7c5..13958b67baac 100644 --- a/client/keys/show_test.go +++ b/client/keys/show_test.go @@ -12,7 +12,7 @@ import ( "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/crypto/hd" "github.com/cosmos/cosmos-sdk/crypto/keyring" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" "github.com/cosmos/cosmos-sdk/tests" sdk "github.com/cosmos/cosmos-sdk/types" ) diff --git a/crypto/codec/amino.go b/crypto/codec/amino.go index 9ef14fe93d8d..825ab500d0a4 100644 --- a/crypto/codec/amino.go +++ b/crypto/codec/amino.go @@ -7,7 +7,7 @@ import ( "github.com/tendermint/tendermint/crypto/sr25519" "github.com/cosmos/cosmos-sdk/codec" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" ) var amino *codec.Codec diff --git a/crypto/keyring/info.go b/crypto/keyring/info.go index 74bb62d774f2..cf504204d95e 100644 --- a/crypto/keyring/info.go +++ b/crypto/keyring/info.go @@ -6,7 +6,7 @@ import ( "github.com/tendermint/tendermint/crypto" "github.com/cosmos/cosmos-sdk/crypto/hd" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" "github.com/cosmos/cosmos-sdk/types" ) @@ -202,7 +202,7 @@ func NewMultiInfo(name string, pub crypto.PubKey) Info { return &multiInfo{ Name: name, PubKey: pub, - Threshold: multiPK.K, + Threshold: uint(multiPK.K), PubKeys: pubKeys, } } diff --git a/crypto/keyring/keyring_test.go b/crypto/keyring/keyring_test.go index 55646c1e3af6..2bac99dc82f4 100644 --- a/crypto/keyring/keyring_test.go +++ b/crypto/keyring/keyring_test.go @@ -14,7 +14,7 @@ import ( "github.com/cosmos/cosmos-sdk/crypto" "github.com/cosmos/cosmos-sdk/crypto/hd" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" "github.com/cosmos/cosmos-sdk/tests" sdk "github.com/cosmos/cosmos-sdk/types" ) diff --git a/crypto/keyring/output_test.go b/crypto/keyring/output_test.go index 150a546b589f..33b7d09dc3cf 100644 --- a/crypto/keyring/output_test.go +++ b/crypto/keyring/output_test.go @@ -7,7 +7,7 @@ import ( "github.com/tendermint/tendermint/crypto" "github.com/tendermint/tendermint/crypto/secp256k1" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" sdk "github.com/cosmos/cosmos-sdk/types" ) diff --git a/crypto/types/multisig/codec.go b/crypto/multisig/amino.go similarity index 75% rename from crypto/types/multisig/codec.go rename to crypto/multisig/amino.go index 9fedd111b1c5..e76711f9c475 100644 --- a/crypto/types/multisig/codec.go +++ b/crypto/multisig/amino.go @@ -1,6 +1,7 @@ package multisig import ( + "github.com/cosmos/cosmos-sdk/crypto/types" amino "github.com/tendermint/go-amino" "github.com/tendermint/tendermint/crypto" @@ -28,3 +29,10 @@ func init() { cdc.RegisterConcrete(secp256k1.PubKeySecp256k1{}, secp256k1.PubKeyAminoName, nil) } + +// AminoMultisignature is used to represent the signature object used in the multisigs. +// Sigs is a list of signatures, sorted by corresponding index. +type AminoMultisignature struct { + BitArray *types.CompactBitArray + Sigs [][]byte +} diff --git a/crypto/multisig/multisig_pubkey.go b/crypto/multisig/multisig_pubkey.go new file mode 100644 index 000000000000..da5dfe529a3f --- /dev/null +++ b/crypto/multisig/multisig_pubkey.go @@ -0,0 +1,17 @@ +package multisig + +import ( + "github.com/tendermint/tendermint/crypto" + + "github.com/cosmos/cosmos-sdk/types/tx/signing" +) + +type GetSignBytesFunc func(mode signing.SignMode) ([]byte, error) + +type MultisigPubKey interface { + crypto.PubKey + + VerifyMultisignature(getSignBytes GetSignBytesFunc, sig *signing.MultiSignatureData) bool + GetPubKeys() []crypto.PubKey + Threshold() uint32 +} diff --git a/crypto/types/multisig/multisignature.go b/crypto/multisig/multisignature.go similarity index 54% rename from crypto/types/multisig/multisignature.go rename to crypto/multisig/multisignature.go index 2e21935f26ad..d04e95c3bcc1 100644 --- a/crypto/types/multisig/multisignature.go +++ b/crypto/multisig/multisignature.go @@ -4,23 +4,16 @@ import ( "fmt" "strings" + "github.com/cosmos/cosmos-sdk/types/tx/signing" + "github.com/tendermint/tendermint/crypto" "github.com/cosmos/cosmos-sdk/crypto/types" ) -// Multisignature is used to represent the signature object used in the multisigs. -// Sigs is a list of signatures, sorted by corresponding index. -type Multisignature struct { - BitArray *types.CompactBitArray - Sigs [][]byte -} - -// NewMultisig returns a new Multisignature of size n. -func NewMultisig(n int) *Multisignature { - // Default the signature list to have a capacity of two, since we can - // expect that most multisigs will require multiple signers. - return &Multisignature{types.NewCompactBitArray(n), make([][]byte, 0, 2)} +// NewMultisig returns a new MultiSignatureData +func NewMultisig(n int) *signing.MultiSignatureData { + return &signing.MultiSignatureData{BitArray: types.NewCompactBitArray(n), Signatures: make([]signing.SignatureData, 0, n)} } // GetIndex returns the index of pk in keys. Returns -1 if not found @@ -35,29 +28,29 @@ func getIndex(pk crypto.PubKey, keys []crypto.PubKey) int { // AddSignature adds a signature to the multisig, at the corresponding index. // If the signature already exists, replace it. -func (mSig *Multisignature) AddSignature(sig []byte, index int) { +func AddSignature(mSig *signing.MultiSignatureData, sig signing.SignatureData, index int) { newSigIndex := mSig.BitArray.NumTrueBitsBefore(index) // Signature already exists, just replace the value there if mSig.BitArray.GetIndex(index) { - mSig.Sigs[newSigIndex] = sig + mSig.Signatures[newSigIndex] = sig return } mSig.BitArray.SetIndex(index, true) // Optimization if the index is the greatest index - if newSigIndex == len(mSig.Sigs) { - mSig.Sigs = append(mSig.Sigs, sig) + if newSigIndex == len(mSig.Signatures) { + mSig.Signatures = append(mSig.Signatures, sig) return } // Expand slice by one with a dummy element, move all elements after i // over by one, then place the new signature in that gap. - mSig.Sigs = append(mSig.Sigs, make([]byte, 0)) - copy(mSig.Sigs[newSigIndex+1:], mSig.Sigs[newSigIndex:]) - mSig.Sigs[newSigIndex] = sig + mSig.Signatures = append(mSig.Signatures, &signing.SingleSignatureData{}) + copy(mSig.Signatures[newSigIndex+1:], mSig.Signatures[newSigIndex:]) + mSig.Signatures[newSigIndex] = sig } // AddSignatureFromPubKey adds a signature to the multisig, at the index in // keys corresponding to the provided pubkey. -func (mSig *Multisignature) AddSignatureFromPubKey(sig []byte, pubkey crypto.PubKey, keys []crypto.PubKey) error { +func AddSignatureFromPubKey(mSig *signing.MultiSignatureData, sig signing.SignatureData, pubkey crypto.PubKey, keys []crypto.PubKey) error { index := getIndex(pubkey, keys) if index == -1 { keysStr := make([]string, len(keys)) @@ -68,11 +61,10 @@ func (mSig *Multisignature) AddSignatureFromPubKey(sig []byte, pubkey crypto.Pub return fmt.Errorf("provided key %X doesn't exist in pubkeys: \n%s", pubkey.Bytes(), strings.Join(keysStr, "\n")) } - mSig.AddSignature(sig, index) + AddSignature(mSig, sig, index) return nil } -// Marshal the multisignature with amino -func (mSig *Multisignature) Marshal() []byte { - return cdc.MustMarshalBinaryBare(mSig) +func AddSignatureV2(mSig *signing.MultiSignatureData, sig signing.SignatureV2, keys []crypto.PubKey) error { + return AddSignatureFromPubKey(mSig, sig.Data, sig.PubKey, keys) } diff --git a/crypto/types/multisig/threshold_pubkey.go b/crypto/multisig/threshold_pubkey.go similarity index 52% rename from crypto/types/multisig/threshold_pubkey.go rename to crypto/multisig/threshold_pubkey.go index 13fa11638cce..d5c51b9385ee 100644 --- a/crypto/types/multisig/threshold_pubkey.go +++ b/crypto/multisig/threshold_pubkey.go @@ -1,24 +1,29 @@ package multisig import ( + "github.com/cosmos/cosmos-sdk/types/tx/signing" "github.com/tendermint/tendermint/crypto" ) // PubKeyMultisigThreshold implements a K of N threshold multisig. type PubKeyMultisigThreshold struct { - K uint `json:"threshold"` + K uint32 `json:"threshold"` PubKeys []crypto.PubKey `json:"pubkeys"` } -var _ crypto.PubKey = PubKeyMultisigThreshold{} +func (pk PubKeyMultisigThreshold) Threshold() uint32 { + return pk.K +} + +var _ MultisigPubKey = PubKeyMultisigThreshold{} // NewPubKeyMultisigThreshold returns a new PubKeyMultisigThreshold. // Panics if len(pubkeys) < k or 0 >= k. -func NewPubKeyMultisigThreshold(k int, pubkeys []crypto.PubKey) crypto.PubKey { +func NewPubKeyMultisigThreshold(k uint32, pubkeys []crypto.PubKey) MultisigPubKey { if k <= 0 { panic("threshold k of n multisignature: k <= 0") } - if len(pubkeys) < k { + if len(pubkeys) < int(k) { panic("threshold k of n multisignature: len(pubkeys) < k") } for _, pubkey := range pubkeys { @@ -26,39 +31,54 @@ func NewPubKeyMultisigThreshold(k int, pubkeys []crypto.PubKey) crypto.PubKey { panic("nil pubkey") } } - return PubKeyMultisigThreshold{uint(k), pubkeys} + return PubKeyMultisigThreshold{k, pubkeys} } -// VerifyBytes expects sig to be an amino encoded version of a MultiSignature. -// Returns true iff the multisignature contains k or more signatures -// for the correct corresponding keys, -// and all signatures are valid. (Not just k of the signatures) -// The multisig uses a bitarray, so multiple signatures for the same key is not -// a concern. -func (pk PubKeyMultisigThreshold) VerifyBytes(msg []byte, marshalledSig []byte) bool { - var sig Multisignature - err := cdc.UnmarshalBinaryBare(marshalledSig, &sig) - if err != nil { - return false - } - size := sig.BitArray.Size() +// VerifyBytes should not be used with this PubKeyMultisigThreshold, instead VerifyMultisignature +// must be used +func (pk PubKeyMultisigThreshold) VerifyBytes([]byte, []byte) bool { + return false +} + +func (pk PubKeyMultisigThreshold) VerifyMultisignature(getSignBytes GetSignBytesFunc, sig *signing.MultiSignatureData) bool { + bitarray := sig.BitArray + sigs := sig.Signatures + size := bitarray.Size() // ensure bit array is the correct size if len(pk.PubKeys) != size { return false } // ensure size of signature list - if len(sig.Sigs) < int(pk.K) || len(sig.Sigs) > size { + if len(sigs) < int(pk.K) || len(sigs) > size { return false } // ensure at least k signatures are set - if sig.BitArray.NumTrueBitsBefore(size) < int(pk.K) { + if bitarray.NumTrueBitsBefore(size) < int(pk.K) { return false } // index in the list of signatures which we are concerned with. sigIndex := 0 for i := 0; i < size; i++ { - if sig.BitArray.GetIndex(i) { - if !pk.PubKeys[i].VerifyBytes(msg, sig.Sigs[sigIndex]) { + if bitarray.GetIndex(i) { + si := sig.Signatures[sigIndex] + switch si := si.(type) { + case *signing.SingleSignatureData: + msg, err := getSignBytes(si.SignMode) + if err != nil { + return false + } + if !pk.PubKeys[i].VerifyBytes(msg, si.Signature) { + return false + } + case *signing.MultiSignatureData: + nestedMultisigPk, ok := pk.PubKeys[i].(MultisigPubKey) + if !ok { + return false + } + if !nestedMultisigPk.VerifyMultisignature(getSignBytes, si) { + return false + } + default: return false } sigIndex++ @@ -67,12 +87,16 @@ func (pk PubKeyMultisigThreshold) VerifyBytes(msg []byte, marshalledSig []byte) return true } +func (pk PubKeyMultisigThreshold) GetPubKeys() []crypto.PubKey { + return pk.PubKeys +} + // Bytes returns the amino encoded version of the PubKeyMultisigThreshold func (pk PubKeyMultisigThreshold) Bytes() []byte { return cdc.MustMarshalBinaryBare(pk) } -// Address returns tmhash(PubKey.Bytes()) +// Address returns tmhash(PubKeyMultisigThreshold.Bytes()) func (pk PubKeyMultisigThreshold) Address() crypto.Address { return crypto.AddressHash(pk.Bytes()) } diff --git a/crypto/types/multisig/threshold_pubkey_test.go b/crypto/multisig/threshold_pubkey_test.go similarity index 68% rename from crypto/types/multisig/threshold_pubkey_test.go rename to crypto/multisig/threshold_pubkey_test.go index cc4aa780b27a..c7a924c282b6 100644 --- a/crypto/types/multisig/threshold_pubkey_test.go +++ b/crypto/multisig/threshold_pubkey_test.go @@ -4,6 +4,8 @@ import ( "math/rand" "testing" + "github.com/cosmos/cosmos-sdk/types/tx/signing" + "github.com/stretchr/testify/require" "github.com/tendermint/tendermint/crypto" @@ -18,11 +20,11 @@ func TestThresholdMultisigValidCases(t *testing.T) { pkSet1, sigSet1 := generatePubKeysAndSignatures(5, []byte{1, 2, 3, 4}) cases := []struct { msg []byte - k int + k uint32 pubkeys []crypto.PubKey signingIndices []int // signatures should be the same size as signingIndices. - signatures [][]byte + signatures []signing.SignatureData passAfterKSignatures []bool }{ { @@ -37,73 +39,73 @@ func TestThresholdMultisigValidCases(t *testing.T) { for tcIndex, tc := range cases { multisigKey := NewPubKeyMultisigThreshold(tc.k, tc.pubkeys) multisignature := NewMultisig(len(tc.pubkeys)) + signBytesFn := func(mode signing.SignMode) ([]byte, error) { return tc.msg, nil } - for i := 0; i < tc.k-1; i++ { + for i := uint32(0); i < tc.k-1; i++ { signingIndex := tc.signingIndices[i] require.NoError( t, - multisignature.AddSignatureFromPubKey(tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), + AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), ) - bz := multisignature.Marshal() require.False( t, - multisigKey.VerifyBytes(tc.msg, bz), + multisigKey.VerifyMultisignature(signBytesFn, multisignature), "multisig passed when i < k, tc %d, i %d", tcIndex, i, ) require.NoError( t, - multisignature.AddSignatureFromPubKey(tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), + AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), ) require.Equal( t, - i+1, - len(multisignature.Sigs), + int(i+1), + len(multisignature.Signatures), "adding a signature for the same pubkey twice increased signature count by 2, tc %d", tcIndex, ) } - bz := multisignature.Marshal() require.False( t, - multisigKey.VerifyBytes(tc.msg, bz), + multisigKey.VerifyMultisignature(signBytesFn, multisignature), "multisig passed with k - 1 sigs, tc %d", tcIndex, ) require.NoError( t, - multisignature.AddSignatureFromPubKey( + AddSignatureFromPubKey( + multisignature, tc.signatures[tc.signingIndices[tc.k]], tc.pubkeys[tc.signingIndices[tc.k]], tc.pubkeys, ), ) - bz = multisignature.Marshal() require.True( t, - multisigKey.VerifyBytes(tc.msg, bz), + multisigKey.VerifyMultisignature(signBytesFn, multisignature), "multisig failed after k good signatures, tc %d", tcIndex, ) - for i := tc.k + 1; i < len(tc.signingIndices); i++ { + for i := int(tc.k) + 1; i < len(tc.signingIndices); i++ { signingIndex := tc.signingIndices[i] require.NoError( t, - multisignature.AddSignatureFromPubKey(tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), + AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), ) - bz := multisignature.Marshal() require.Equal( t, - tc.passAfterKSignatures[i-tc.k-1], - multisigKey.VerifyBytes(tc.msg, bz), + tc.passAfterKSignatures[i-int(tc.k)-1], + multisigKey.VerifyMultisignature(func(mode signing.SignMode) ([]byte, error) { + return tc.msg, nil + }, multisignature), "multisig didn't verify as expected after k sigs, tc %d, i %d", tcIndex, i, ) require.NoError( t, - multisignature.AddSignatureFromPubKey(tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), + AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), ) require.Equal( t, i+1, - len(multisignature.Sigs), + len(multisignature.Signatures), "adding a signature for the same pubkey twice increased signature count by 2, tc %d", tcIndex, ) } @@ -116,13 +118,13 @@ func TestThresholdMultisigDuplicateSignatures(t *testing.T) { pubkeys, sigs := generatePubKeysAndSignatures(5, msg) multisigKey := NewPubKeyMultisigThreshold(2, pubkeys) multisignature := NewMultisig(5) - bz := multisignature.Marshal() + signBytesFn := func(mode signing.SignMode) ([]byte, error) { return msg, nil } - require.False(t, multisigKey.VerifyBytes(msg, bz)) - multisignature.AddSignatureFromPubKey(sigs[0], pubkeys[0], pubkeys) + require.False(t, multisigKey.VerifyMultisignature(signBytesFn, multisignature)) + AddSignatureFromPubKey(multisignature, sigs[0], pubkeys[0], pubkeys) // Add second signature manually - multisignature.Sigs = append(multisignature.Sigs, sigs[0]) - require.False(t, multisigKey.VerifyBytes(msg, bz)) + multisignature.Signatures = append(multisignature.Signatures, sigs[0]) + require.False(t, multisigKey.VerifyMultisignature(signBytesFn, multisignature)) } // TODO: Fully replace this test with table driven tests @@ -157,8 +159,8 @@ func TestPubKeyMultisigThresholdAminoToIface(t *testing.T) { ab, err := cdc.MarshalBinaryLengthPrefixed(multisigKey) require.NoError(t, err) - // like other crypto.Pubkey implementations (e.g. ed25519.PubKey), - // PubKey should be deserializable into a crypto.PubKey: + // like other crypto.Pubkey implementations (e.g. ed25519.PubKeyMultisigThreshold), + // PubKeyMultisigThreshold should be deserializable into a crypto.PubKeyMultisigThreshold: var pubKey crypto.PubKey err = cdc.UnmarshalBinaryLengthPrefixed(ab, &pubKey) require.NoError(t, err) @@ -166,9 +168,9 @@ func TestPubKeyMultisigThresholdAminoToIface(t *testing.T) { require.Equal(t, multisigKey, pubKey) } -func generatePubKeysAndSignatures(n int, msg []byte) (pubkeys []crypto.PubKey, signatures [][]byte) { +func generatePubKeysAndSignatures(n int, msg []byte) (pubkeys []crypto.PubKey, signatures []signing.SignatureData) { pubkeys = make([]crypto.PubKey, n) - signatures = make([][]byte, n) + signatures = make([]signing.SignatureData, n) for i := 0; i < n; i++ { var privkey crypto.PrivKey switch rand.Int63() % 3 { @@ -180,7 +182,8 @@ func generatePubKeysAndSignatures(n int, msg []byte) (pubkeys []crypto.PubKey, s privkey = sr25519.GenPrivKey() } pubkeys[i] = privkey.PubKey() - signatures[i], _ = privkey.Sign(msg) + sig, _ := privkey.Sign(msg) + signatures[i] = &signing.SingleSignatureData{Signature: sig} } return } diff --git a/go.sum b/go.sum index f3859f33641e..3bae58262634 100644 --- a/go.sum +++ b/go.sum @@ -78,6 +78,7 @@ github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDk github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc= github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa/go.mod h1:zn76sxSg3SzpJ0PPJaLDCu+Bu0Lg3sKTORVIj19EIF8= github.com/codahale/hdrhistogram v0.0.0-20161010025455-3a0bb77429bd/go.mod h1:sE/e/2PUdi/liOCUjSTXgM1o87ZssimdTWN964YiIeI= +github.com/confio/ics23 v0.6.0 h1:bQsi55t2+xjW6EWDl83IBF1VWurplbUu+OT6pukeiEo= github.com/confio/ics23-iavl v0.6.0 h1:vVRCuVaP38FCw1kTeEdFuGuiY+2vAGTBQoH7Zxkq/ws= github.com/confio/ics23-iavl v0.6.0/go.mod h1:mmXAxD1vWoO0VP8YHu6mM1QHGv71NQqa1iSVm4HeKcY= github.com/confio/ics23/go v0.0.0-20200323120010-7d9a00f0a2fa/go.mod h1:W1I3XC8d9N8OTu/ct5VJ84ylcOunZwMXsWkd27nvVts= @@ -466,6 +467,8 @@ github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UV github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= github.com/stretchr/testify v1.5.1 h1:nOGnQDM7FYENwehXlg/kFVnos3rEvtKTjRvOWSzb6H4= github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= +github.com/stretchr/testify v1.6.0 h1:jlIyCplCJFULU/01vCkhKuTyc3OorI3bJFuw6obfgho= +github.com/stretchr/testify v1.6.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/stretchr/testify v1.6.1 h1:hDPOHmpOpP40lSULcqw7IrRb/u7w6RpDC9399XyoNd0= github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/subosito/gotenv v1.2.0 h1:Slr1R9HxAlEKefgq5jn9U+DnETlIUa6HfgEzj0g5d7s= diff --git a/types/tx/interface.go b/types/tx/interface.go deleted file mode 100644 index 77e036b56b55..000000000000 --- a/types/tx/interface.go +++ /dev/null @@ -1,38 +0,0 @@ -package types - -import ( - sdk "github.com/cosmos/cosmos-sdk/types" -) - -type ProtoTx interface { - sdk.Tx - FeeTx - TxWithMemo - SigTx - - GetBody() *TxBody - GetAuthInfo() *AuthInfo - GetSignatures() [][]byte - - GetBodyBytes() []byte - GetAuthInfoBytes() []byte -} - -// FeeTx defines the interface to be implemented by Tx to use the FeeDecorators -type FeeTx interface { - sdk.Tx - GetGas() uint64 - GetFee() sdk.Coins - FeePayer() sdk.AccAddress -} - -// Tx must have GetMemo() method to use ValidateMemoDecorator -type TxWithMemo interface { - sdk.Tx - GetMemo() string -} - -type SigTx interface { - sdk.Tx - GetSignaturesV2() ([]SignatureV2, error) -} diff --git a/types/tx/signature.go b/types/tx/signature.go deleted file mode 100644 index 9c7db87978de..000000000000 --- a/types/tx/signature.go +++ /dev/null @@ -1,64 +0,0 @@ -package types - -import ( - "github.com/cosmos/cosmos-sdk/crypto/types" - "github.com/tendermint/tendermint/crypto" -) - -type SignatureV2 struct { - PubKey crypto.PubKey - Data SignatureData -} - -type SignatureData interface { - isSignatureData() -} - -type SingleSignatureData struct { - SignMode SignMode - Signature []byte -} - -type MultiSignatureData struct { - BitArray *types.CompactBitArray - Signatures []SignatureData -} - -var _, _ SignatureData = &SingleSignatureData{}, &MultiSignatureData{} - -func (m *SingleSignatureData) isSignatureData() {} -func (m *MultiSignatureData) isSignatureData() {} - -func ModeInfoToSignatureData(modeInfo *ModeInfo, sig []byte) (SignatureData, error) { - switch modeInfo := modeInfo.Sum.(type) { - case *ModeInfo_Single_: - return &SingleSignatureData{ - SignMode: modeInfo.Single.Mode, - Signature: sig, - }, nil - - case *ModeInfo_Multi_: - multi := modeInfo.Multi - - sigs, err := types.DecodeMultisignatures(sig) - if err != nil { - return nil, err - } - - sigData := make([]SignatureData, len(sigs)) - for i, mi := range multi.ModeInfos { - sigData[i], err = ModeInfoToSignatureData(mi, sigs[i]) - if err != nil { - return nil, err - } - } - - return &MultiSignatureData{ - BitArray: multi.Bitarray, - Signatures: sigData, - }, nil - - default: - panic("unexpected case") - } -} diff --git a/types/tx/signing/signature.go b/types/tx/signing/signature.go new file mode 100644 index 000000000000..27bf9580be38 --- /dev/null +++ b/types/tx/signing/signature.go @@ -0,0 +1,8 @@ +package signing + +import "github.com/tendermint/tendermint/crypto" + +type SignatureV2 struct { + PubKey crypto.PubKey + Data SignatureData +} diff --git a/types/tx/signing/signature_data.go b/types/tx/signing/signature_data.go new file mode 100644 index 000000000000..ffb87d45678c --- /dev/null +++ b/types/tx/signing/signature_data.go @@ -0,0 +1,24 @@ +package signing + +import ( + "github.com/cosmos/cosmos-sdk/crypto/types" +) + +type SignatureData interface { + isSignatureData() +} + +type SingleSignatureData struct { + SignMode SignMode + Signature []byte +} + +type MultiSignatureData struct { + BitArray *types.CompactBitArray + Signatures []SignatureData +} + +var _, _ SignatureData = &SingleSignatureData{}, &MultiSignatureData{} + +func (m *SingleSignatureData) isSignatureData() {} +func (m *MultiSignatureData) isSignatureData() {} diff --git a/types/tx/signing/types.pb.go b/types/tx/signing/types.pb.go new file mode 100644 index 000000000000..4207f12ad27f --- /dev/null +++ b/types/tx/signing/types.pb.go @@ -0,0 +1,84 @@ +// Code generated by protoc-gen-gogo. DO NOT EDIT. +// source: types/tx/signing/types.proto + +package signing + +import ( + fmt "fmt" + proto "github.com/gogo/protobuf/proto" + math "math" +) + +// Reference imports to suppress errors if they are not otherwise used. +var _ = proto.Marshal +var _ = fmt.Errorf +var _ = math.Inf + +// This is a compile-time assertion to ensure that this generated file +// is compatible with the proto package it is being compiled against. +// A compilation error at this line likely means your copy of the +// proto package needs to be updated. +const _ = proto.GoGoProtoPackageIsVersion3 // please upgrade the proto package + +// SignMode represents a signing mode with its own security guarantees +type SignMode int32 + +const ( + // SIGN_MODE_UNSPECIFIED specifies an unknown signing mode and will be rejected + SignMode_SIGN_MODE_UNSPECIFIED SignMode = 0 + // SIGN_MODE_DIRECT specifies a signing mode which uses SignDoc and is verified + // with raw bytes from Tx + SignMode_SIGN_MODE_DIRECT SignMode = 1 + // SIGN_MODE_TEXTUAL is a future signing mode that will verify some human-readable + // textual representation on top of the binary representation from SIGN_MODE_DIRECT + SignMode_SIGN_MODE_TEXTUAL SignMode = 2 + // SIGN_MODE_LEGACY_AMINO_JSON is a backwards compatibility mode which uses + // Amino JSON and will be removed in the future + SignMode_SIGN_MODE_LEGACY_AMINO_JSON SignMode = 127 +) + +var SignMode_name = map[int32]string{ + 0: "SIGN_MODE_UNSPECIFIED", + 1: "SIGN_MODE_DIRECT", + 2: "SIGN_MODE_TEXTUAL", + 127: "SIGN_MODE_LEGACY_AMINO_JSON", +} + +var SignMode_value = map[string]int32{ + "SIGN_MODE_UNSPECIFIED": 0, + "SIGN_MODE_DIRECT": 1, + "SIGN_MODE_TEXTUAL": 2, + "SIGN_MODE_LEGACY_AMINO_JSON": 127, +} + +func (x SignMode) String() string { + return proto.EnumName(SignMode_name, int32(x)) +} + +func (SignMode) EnumDescriptor() ([]byte, []int) { + return fileDescriptor_52d5d5e2efced9ba, []int{0} +} + +func init() { + proto.RegisterEnum("cosmos_sdk.tx.signing.v1.SignMode", SignMode_name, SignMode_value) +} + +func init() { proto.RegisterFile("types/tx/signing/types.proto", fileDescriptor_52d5d5e2efced9ba) } + +var fileDescriptor_52d5d5e2efced9ba = []byte{ + // 222 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xe2, 0x92, 0x29, 0xa9, 0x2c, 0x48, + 0x2d, 0xd6, 0x2f, 0xa9, 0xd0, 0x2f, 0xce, 0x4c, 0xcf, 0xcb, 0xcc, 0x4b, 0xd7, 0x07, 0x0b, 0xe8, + 0x15, 0x14, 0xe5, 0x97, 0xe4, 0x0b, 0x49, 0x24, 0xe7, 0x17, 0xe7, 0xe6, 0x17, 0xc7, 0x17, 0xa7, + 0x64, 0xeb, 0x95, 0x54, 0xe8, 0x41, 0x95, 0xe8, 0x95, 0x19, 0x6a, 0x15, 0x73, 0x71, 0x04, 0x67, + 0xa6, 0xe7, 0xf9, 0xe6, 0xa7, 0xa4, 0x0a, 0x49, 0x72, 0x89, 0x06, 0x7b, 0xba, 0xfb, 0xc5, 0xfb, + 0xfa, 0xbb, 0xb8, 0xc6, 0x87, 0xfa, 0x05, 0x07, 0xb8, 0x3a, 0x7b, 0xba, 0x79, 0xba, 0xba, 0x08, + 0x30, 0x08, 0x89, 0x70, 0x09, 0x20, 0xa4, 0x5c, 0x3c, 0x83, 0x5c, 0x9d, 0x43, 0x04, 0x18, 0x85, + 0x44, 0xb9, 0x04, 0x11, 0xa2, 0x21, 0xae, 0x11, 0x21, 0xa1, 0x8e, 0x3e, 0x02, 0x4c, 0x42, 0xf2, + 0x5c, 0xd2, 0x08, 0x61, 0x1f, 0x57, 0x77, 0x47, 0xe7, 0xc8, 0x78, 0x47, 0x5f, 0x4f, 0x3f, 0xff, + 0x78, 0xaf, 0x60, 0x7f, 0x3f, 0x81, 0x7a, 0x27, 0xf7, 0x13, 0x8f, 0xe4, 0x18, 0x2f, 0x3c, 0x92, + 0x63, 0x7c, 0xf0, 0x48, 0x8e, 0x71, 0xc2, 0x63, 0x39, 0x86, 0x0b, 0x8f, 0xe5, 0x18, 0x6e, 0x3c, + 0x96, 0x63, 0x88, 0xd2, 0x4d, 0xcf, 0x2c, 0xc9, 0x28, 0x4d, 0xd2, 0x4b, 0xce, 0xcf, 0xd5, 0x87, + 0xb8, 0x19, 0x4a, 0xe9, 0x16, 0xa7, 0x64, 0xeb, 0xa3, 0xfb, 0x31, 0x89, 0x0d, 0xec, 0x3d, 0x63, + 0x40, 0x00, 0x00, 0x00, 0xff, 0xff, 0xa0, 0x11, 0xdd, 0x92, 0xfe, 0x00, 0x00, 0x00, +} diff --git a/types/tx/signing/types.proto b/types/tx/signing/types.proto new file mode 100644 index 000000000000..d015f8cc1ef0 --- /dev/null +++ b/types/tx/signing/types.proto @@ -0,0 +1,22 @@ +syntax = "proto3"; +package cosmos_sdk.tx.signing.v1; + +option go_package = "github.com/cosmos/cosmos-sdk/types/tx/signing"; + +// SignMode represents a signing mode with its own security guarantees +enum SignMode { + // SIGN_MODE_UNSPECIFIED specifies an unknown signing mode and will be rejected + SIGN_MODE_UNSPECIFIED = 0; + + // SIGN_MODE_DIRECT specifies a signing mode which uses SignDoc and is verified + // with raw bytes from Tx + SIGN_MODE_DIRECT = 1; + + // SIGN_MODE_TEXTUAL is a future signing mode that will verify some human-readable + // textual representation on top of the binary representation from SIGN_MODE_DIRECT + SIGN_MODE_TEXTUAL = 2; + + // SIGN_MODE_LEGACY_AMINO_JSON is a backwards compatibility mode which uses + // Amino JSON and will be removed in the future + SIGN_MODE_LEGACY_AMINO_JSON = 127; +} diff --git a/types/tx/tx.go b/types/tx/tx.go deleted file mode 100644 index aae11e4f8103..000000000000 --- a/types/tx/tx.go +++ /dev/null @@ -1,174 +0,0 @@ -package types - -import ( - "github.com/tendermint/tendermint/crypto" - - codectypes "github.com/cosmos/cosmos-sdk/codec/types" - sdk "github.com/cosmos/cosmos-sdk/types" - sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" -) - -var _ ProtoTx = &Tx{} - -func NewTx() *Tx { - return &Tx{ - Body: &TxBody{}, - AuthInfo: &AuthInfo{ - SignerInfos: nil, - Fee: &Fee{}, - }, - Signatures: nil, - } -} - -func (tx *Tx) GetMsgs() []sdk.Msg { - anys := tx.Body.Messages - res := make([]sdk.Msg, len(anys)) - for i, any := range anys { - msg := any.GetCachedValue().(sdk.Msg) - res[i] = msg - } - return res -} - -func (tx *Tx) ValidateBasic() error { - sigs := tx.GetSignatures() - - if tx.GetGas() > MaxGasWanted { - return sdkerrors.Wrapf( - sdkerrors.ErrInvalidRequest, - "invalid gas supplied; %d > %d", tx.GetGas(), MaxGasWanted, - ) - } - if tx.GetFee().IsAnyNegative() { - return sdkerrors.Wrapf( - sdkerrors.ErrInsufficientFee, - "invalid fee provided: %s", tx.GetFee(), - ) - } - if len(sigs) == 0 { - return sdkerrors.ErrNoSignatures - } - if len(sigs) != len(tx.GetSigners()) { - return sdkerrors.Wrapf( - sdkerrors.ErrUnauthorized, - "wrong number of signers; expected %d, got %d", tx.GetSigners(), len(sigs), - ) - } - - return nil -} - -func (m *Tx) GetGas() uint64 { - return m.AuthInfo.Fee.GasLimit -} - -func (m *Tx) GetFee() sdk.Coins { - return m.AuthInfo.Fee.Amount -} - -func (m *Tx) FeePayer() sdk.AccAddress { - signers := m.GetSigners() - if signers != nil { - return signers[0] - } - return sdk.AccAddress{} -} - -func (m *Tx) GetMemo() string { - if m.Body == nil { - return "" - } - return m.Body.Memo -} - -func (m *Tx) GetSigners() []sdk.AccAddress { - var signers []sdk.AccAddress - seen := map[string]bool{} - - for _, msg := range m.GetMsgs() { - for _, addr := range msg.GetSigners() { - if !seen[addr.String()] { - signers = append(signers, addr) - seen[addr.String()] = true - } - } - } - return signers -} - -func (m *Tx) GetPubKeys() []crypto.PubKey { - signerInfos := m.AuthInfo.SignerInfos - res := make([]crypto.PubKey, len(signerInfos)) - for i, si := range signerInfos { - res[i] = si.PublicKey.GetCachedPubKey() - } - return res -} - -func (m *Tx) GetBodyBytes() []byte { - bz, err := m.Body.Marshal() - if err != nil { - panic(err) - } - return bz -} - -func (m *Tx) GetAuthInfoBytes() []byte { - bz, err := m.AuthInfo.Marshal() - if err != nil { - panic(err) - } - return bz -} - -var _ codectypes.UnpackInterfacesMessage = &Tx{} -var _ codectypes.UnpackInterfacesMessage = &TxBody{} -var _ codectypes.UnpackInterfacesMessage = &SignDoc{} - -func (m *Tx) UnpackInterfaces(unpacker codectypes.AnyUnpacker) error { - if m.Body != nil { - return m.Body.UnpackInterfaces(unpacker) - } - return nil -} - -func (m *SignDoc) UnpackInterfaces(unpacker codectypes.AnyUnpacker) error { - return m.Body.UnpackInterfaces(unpacker) -} - -func (m *TxBody) UnpackInterfaces(unpacker codectypes.AnyUnpacker) error { - for _, any := range m.Messages { - var msg sdk.Msg - err := unpacker.UnpackAny(any, &msg) - if err != nil { - return err - } - } - return nil -} - -func (m *Tx) GetSignaturesV2() ([]SignatureV2, error) { - signerInfos := m.AuthInfo.SignerInfos - sigs := m.Signatures - n := len(signerInfos) - res := make([]SignatureV2, n) - - for i, si := range signerInfos { - var err error - - data, err := ModeInfoToSignatureData(si.ModeInfo, sigs[i]) - if err != nil { - return nil, err - } - - pubKey := si.PublicKey.GetCachedPubKey() - - res[i] = SignatureV2{ - PubKey: pubKey, - Data: data, - } - } - - return res, nil -} diff --git a/types/tx/types.pb.go b/types/tx/types.pb.go index 16e2ac453b56..770cc3610778 100644 --- a/types/tx/types.pb.go +++ b/types/tx/types.pb.go @@ -9,6 +9,7 @@ import ( types1 "github.com/cosmos/cosmos-sdk/crypto/types" github_com_cosmos_cosmos_sdk_types "github.com/cosmos/cosmos-sdk/types" types2 "github.com/cosmos/cosmos-sdk/types" + signing "github.com/cosmos/cosmos-sdk/types/tx/signing" _ "github.com/gogo/protobuf/gogoproto" proto "github.com/gogo/protobuf/proto" io "io" @@ -27,45 +28,6 @@ var _ = math.Inf // proto package needs to be updated. const _ = proto.GoGoProtoPackageIsVersion3 // please upgrade the proto package -// SignMode represents a signing mode with its own security guarantees -type SignMode int32 - -const ( - // SIGN_MODE_UNSPECIFIED specifies an unknown signing mode and will be rejected - SignMode_SIGN_MODE_UNSPECIFIED SignMode = 0 - // SIGN_MODE_DIRECT specifies a signing mode which uses SignDoc and is verified - // with raw bytes from Tx - SignMode_SIGN_MODE_DIRECT SignMode = 1 - // SIGN_MODE_TEXTUAL is a future signing mode that will verify some human-readable - // textual representation on top of the binary representation from SIGN_MODE_DIRECT - SignMode_SIGN_MODE_TEXTUAL SignMode = 2 - // SIGN_MODE_LEGACY_AMINO_JSON is a backwards compatibility mode which uses - // Amino JSON and will be removed in the future - SignMode_SIGN_MODE_LEGACY_AMINO_JSON SignMode = 127 -) - -var SignMode_name = map[int32]string{ - 0: "SIGN_MODE_UNSPECIFIED", - 1: "SIGN_MODE_DIRECT", - 2: "SIGN_MODE_TEXTUAL", - 127: "SIGN_MODE_LEGACY_AMINO_JSON", -} - -var SignMode_value = map[string]int32{ - "SIGN_MODE_UNSPECIFIED": 0, - "SIGN_MODE_DIRECT": 1, - "SIGN_MODE_TEXTUAL": 2, - "SIGN_MODE_LEGACY_AMINO_JSON": 127, -} - -func (x SignMode) String() string { - return proto.EnumName(SignMode_name, int32(x)) -} - -func (SignMode) EnumDescriptor() ([]byte, []int) { - return fileDescriptor_1c6ac8fa65877134, []int{0} -} - // Tx is the standard type used for broadcasting transactions type Tx struct { // body is the processable content of the transaction @@ -511,7 +473,7 @@ func (*ModeInfo) XXX_OneofWrappers() []interface{} { // to allow for additional fields such as locale for SIGN_MODE_TEXTUAL in the future type ModeInfo_Single struct { // mode is the signing mode of the single signer - Mode SignMode `protobuf:"varint,1,opt,name=mode,proto3,enum=cosmos_sdk.tx.v1.SignMode" json:"mode,omitempty"` + Mode signing.SignMode `protobuf:"varint,1,opt,name=mode,proto3,enum=cosmos_sdk.tx.signing.v1.SignMode" json:"mode,omitempty"` } func (m *ModeInfo_Single) Reset() { *m = ModeInfo_Single{} } @@ -547,11 +509,11 @@ func (m *ModeInfo_Single) XXX_DiscardUnknown() { var xxx_messageInfo_ModeInfo_Single proto.InternalMessageInfo -func (m *ModeInfo_Single) GetMode() SignMode { +func (m *ModeInfo_Single) GetMode() signing.SignMode { if m != nil { return m.Mode } - return SignMode_SIGN_MODE_UNSPECIFIED + return signing.SignMode_SIGN_MODE_UNSPECIFIED } // Multi is the mode info for a multisig public key @@ -669,7 +631,6 @@ func (m *Fee) GetGasLimit() uint64 { } func init() { - proto.RegisterEnum("cosmos_sdk.tx.v1.SignMode", SignMode_name, SignMode_value) proto.RegisterType((*Tx)(nil), "cosmos_sdk.tx.v1.Tx") proto.RegisterType((*SignDoc)(nil), "cosmos_sdk.tx.v1.SignDoc") proto.RegisterType((*TxBody)(nil), "cosmos_sdk.tx.v1.TxBody") @@ -684,60 +645,56 @@ func init() { func init() { proto.RegisterFile("types/tx/types.proto", fileDescriptor_1c6ac8fa65877134) } var fileDescriptor_1c6ac8fa65877134 = []byte{ - // 842 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x55, 0x4d, 0x6f, 0xe3, 0x44, - 0x18, 0x8e, 0x93, 0x34, 0x4d, 0xde, 0xee, 0x47, 0x3a, 0xb4, 0x92, 0x9b, 0xa2, 0x34, 0x44, 0x2a, - 0x04, 0x04, 0xce, 0xb2, 0x7b, 0x60, 0x11, 0x87, 0x55, 0x92, 0xa6, 0xdb, 0x40, 0x9b, 0xa2, 0x49, - 0x56, 0x82, 0x95, 0x90, 0xe5, 0xd8, 0x53, 0x67, 0xd4, 0x78, 0x26, 0x78, 0xc6, 0x28, 0xe1, 0x82, - 0x38, 0x70, 0xe2, 0xc2, 0x85, 0x3f, 0xc1, 0x2f, 0x59, 0x71, 0xda, 0x23, 0x17, 0x3e, 0xd4, 0xfe, - 0x10, 0x90, 0xc7, 0xe3, 0xa4, 0x6a, 0x4a, 0xb8, 0x71, 0xca, 0xeb, 0xc7, 0xcf, 0xf3, 0xcc, 0xfb, - 0x95, 0x31, 0xec, 0xc8, 0xf9, 0x94, 0x88, 0xa6, 0x9c, 0x35, 0x55, 0x60, 0x4d, 0x43, 0x2e, 0x39, - 0x2a, 0xbb, 0x5c, 0x04, 0x5c, 0xd8, 0xc2, 0xbb, 0xb4, 0xe4, 0xcc, 0xfa, 0xe6, 0xc3, 0xca, 0xdb, - 0x72, 0x4c, 0x43, 0xcf, 0x9e, 0x3a, 0xa1, 0x9c, 0x37, 0x15, 0xa9, 0xe9, 0x73, 0x9f, 0x2f, 0xa3, - 0x44, 0x59, 0x31, 0xdd, 0x70, 0x3e, 0x95, 0xbc, 0xa9, 0x6d, 0x97, 0x9e, 0x95, 0xed, 0x55, 0x68, - 0xcf, 0xe7, 0xdc, 0x9f, 0x90, 0xc4, 0x6f, 0x14, 0x5d, 0x34, 0x1d, 0x36, 0x4f, 0x5e, 0xd5, 0x7f, - 0x34, 0x20, 0x3b, 0x9c, 0xa1, 0xf7, 0x21, 0x3f, 0xe2, 0xde, 0xdc, 0x34, 0x6a, 0x46, 0x63, 0xeb, - 0xb1, 0x69, 0xdd, 0xce, 0xcb, 0x1a, 0xce, 0xda, 0xdc, 0x9b, 0x63, 0xc5, 0x42, 0x1f, 0x41, 0xc9, - 0x89, 0xe4, 0xd8, 0xa6, 0xec, 0x82, 0x9b, 0x59, 0x25, 0xa9, 0xac, 0x4a, 0x5a, 0x91, 0x1c, 0xf7, - 0xd8, 0x05, 0xc7, 0x45, 0x47, 0x47, 0xa8, 0x0a, 0x20, 0xa8, 0xcf, 0x1c, 0x19, 0x85, 0x44, 0x98, - 0xb9, 0x5a, 0xae, 0x71, 0x0f, 0xdf, 0x40, 0xea, 0xbf, 0x1b, 0xb0, 0x39, 0xa0, 0x3e, 0x3b, 0xe2, - 0xee, 0xff, 0x95, 0xd2, 0x1e, 0x14, 0xdd, 0xb1, 0x43, 0x99, 0x4d, 0x3d, 0x33, 0x57, 0x33, 0x1a, - 0x25, 0xbc, 0xa9, 0x9e, 0x7b, 0x1e, 0x3a, 0x84, 0x07, 0x8e, 0xeb, 0xf2, 0x88, 0x49, 0x9b, 0x45, - 0xc1, 0x88, 0x84, 0x66, 0xbe, 0x66, 0x34, 0xf2, 0xf8, 0xbe, 0x46, 0xfb, 0x0a, 0x44, 0xef, 0x42, - 0x39, 0xa5, 0x09, 0xf2, 0x75, 0x44, 0x98, 0x4b, 0xcc, 0x0d, 0x45, 0x7c, 0xa8, 0xf1, 0x81, 0x86, - 0xeb, 0x3f, 0x67, 0xa1, 0x90, 0xa4, 0x8d, 0x1e, 0x41, 0x31, 0x20, 0x42, 0x38, 0x3e, 0x11, 0xa6, - 0x51, 0xcb, 0x35, 0xb6, 0x1e, 0xef, 0x58, 0xc9, 0x98, 0xac, 0x74, 0x4c, 0x56, 0x8b, 0xcd, 0xf1, - 0x82, 0x85, 0x10, 0xe4, 0x03, 0x12, 0x24, 0xd5, 0x95, 0xb0, 0x8a, 0xe3, 0x14, 0x25, 0x0d, 0x08, - 0x8f, 0xa4, 0x3d, 0x26, 0xd4, 0x1f, 0x4b, 0x55, 0x43, 0x0e, 0xdf, 0xd7, 0xe8, 0x89, 0x02, 0x51, - 0x1b, 0xb6, 0xc9, 0x4c, 0x12, 0x26, 0x28, 0x67, 0x36, 0x9f, 0x4a, 0xca, 0x99, 0x30, 0xff, 0xde, - 0x5c, 0x73, 0x6c, 0x79, 0xc1, 0x3f, 0x4f, 0xe8, 0xe8, 0x25, 0x54, 0x19, 0x67, 0xb6, 0x1b, 0x52, - 0x49, 0x5d, 0x67, 0x62, 0xdf, 0x61, 0xf8, 0x70, 0x8d, 0xe1, 0x3e, 0xe3, 0xac, 0xa3, 0xb5, 0xdd, - 0x5b, 0xde, 0x75, 0x09, 0xc5, 0x74, 0x34, 0xe8, 0x19, 0xdc, 0x8b, 0x37, 0x82, 0x84, 0x6a, 0x96, - 0x69, 0x73, 0xde, 0x5c, 0x1d, 0xe6, 0x40, 0xb1, 0xd4, 0x38, 0xb7, 0xc4, 0x22, 0x16, 0xe8, 0x1d, - 0xc8, 0x5d, 0x10, 0xa2, 0x97, 0x60, 0x77, 0x55, 0x77, 0x4c, 0x08, 0x8e, 0x19, 0xf5, 0x6f, 0x01, - 0x96, 0x1e, 0xe8, 0x09, 0xc0, 0x34, 0x1a, 0x4d, 0xa8, 0x6b, 0x5f, 0x92, 0x74, 0xeb, 0xee, 0x2e, - 0xa5, 0x94, 0xf0, 0x3e, 0x23, 0x6a, 0xed, 0x02, 0xee, 0x91, 0xff, 0x58, 0xbb, 0x33, 0xee, 0x91, - 0x64, 0xed, 0x02, 0x1d, 0xd5, 0x7f, 0xcd, 0x42, 0x31, 0x85, 0xd1, 0x27, 0x50, 0x10, 0x94, 0xf9, - 0x13, 0xa2, 0x8f, 0x7d, 0xeb, 0xdf, 0x2d, 0xac, 0x81, 0x22, 0x9e, 0x64, 0xb0, 0x96, 0xa0, 0xa7, - 0xb0, 0x11, 0x44, 0x13, 0x49, 0xf5, 0xf1, 0xb5, 0x35, 0xda, 0xb3, 0x98, 0x77, 0x92, 0xc1, 0x89, - 0xa0, 0xf2, 0x14, 0x0a, 0x89, 0x1b, 0xb2, 0x20, 0x1f, 0x67, 0xa6, 0x8e, 0x7f, 0x70, 0x57, 0x05, - 0x71, 0x9f, 0x62, 0x1b, 0xac, 0x78, 0x95, 0x1f, 0x0c, 0xd8, 0x50, 0x66, 0xa8, 0x05, 0xc5, 0x11, - 0x95, 0x4e, 0x18, 0x3a, 0x69, 0xcf, 0x0e, 0x6f, 0xaa, 0x93, 0x5b, 0x2a, 0x76, 0xe8, 0xf0, 0x60, - 0xea, 0xb8, 0xb2, 0x4d, 0x65, 0x2b, 0x26, 0xe3, 0x85, 0x0c, 0x7d, 0x0c, 0xb0, 0xe8, 0xa1, 0x30, - 0xb3, 0x6a, 0xdc, 0xeb, 0x9a, 0x58, 0x4a, 0x9b, 0x28, 0xda, 0x1b, 0x90, 0x13, 0x51, 0x50, 0xff, - 0xde, 0x80, 0xdc, 0x31, 0x21, 0xe8, 0x2b, 0x28, 0x38, 0x41, 0xfc, 0x87, 0xd3, 0x4b, 0xf3, 0xc6, - 0x4d, 0x17, 0x95, 0x03, 0x65, 0xed, 0x47, 0xaf, 0xfe, 0x38, 0xc8, 0xfc, 0xf2, 0xe7, 0x41, 0xc3, - 0xa7, 0x72, 0x1c, 0x8d, 0x2c, 0x97, 0x07, 0xcd, 0x84, 0xa6, 0x7f, 0x3e, 0x10, 0xde, 0xa5, 0xbe, - 0x3e, 0x63, 0x81, 0xc0, 0xda, 0x14, 0xed, 0x43, 0xc9, 0x77, 0x84, 0x3d, 0xa1, 0x01, 0x95, 0xaa, - 0xdb, 0x79, 0x5c, 0xf4, 0x1d, 0x71, 0x1a, 0x3f, 0xbf, 0x27, 0xa0, 0x98, 0x36, 0x09, 0xed, 0xc1, - 0xee, 0xa0, 0xf7, 0xbc, 0x6f, 0x9f, 0x9d, 0x1f, 0x75, 0xed, 0x17, 0xfd, 0xc1, 0xe7, 0xdd, 0x4e, - 0xef, 0xb8, 0xd7, 0x3d, 0x2a, 0x67, 0xd0, 0x0e, 0x94, 0x97, 0xaf, 0x8e, 0x7a, 0xb8, 0xdb, 0x19, - 0x96, 0x0d, 0xb4, 0x0b, 0xdb, 0x4b, 0x74, 0xd8, 0xfd, 0x62, 0xf8, 0xa2, 0x75, 0x5a, 0xce, 0xa2, - 0x03, 0xd8, 0x5f, 0xc2, 0xa7, 0xdd, 0xe7, 0xad, 0xce, 0x97, 0x76, 0xeb, 0xac, 0xd7, 0x3f, 0xb7, - 0x3f, 0x1d, 0x9c, 0xf7, 0xcb, 0xdf, 0xb5, 0x9f, 0xbd, 0xba, 0xaa, 0x1a, 0xaf, 0xaf, 0xaa, 0xc6, - 0x5f, 0x57, 0x55, 0xe3, 0xa7, 0xeb, 0x6a, 0xe6, 0xf5, 0x75, 0x35, 0xf3, 0xdb, 0x75, 0x35, 0xf3, - 0xf2, 0x70, 0x7d, 0x75, 0xfa, 0x33, 0x34, 0x2a, 0xa8, 0xc5, 0x7e, 0xf2, 0x4f, 0x00, 0x00, 0x00, - 0xff, 0xff, 0x28, 0x03, 0x76, 0x89, 0x9f, 0x06, 0x00, 0x00, + // 774 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xbc, 0x55, 0x3d, 0x6f, 0xe3, 0x46, + 0x10, 0x15, 0x45, 0x49, 0x96, 0xc6, 0xdf, 0x1b, 0x07, 0xa0, 0x65, 0x83, 0x56, 0x08, 0x38, 0x51, + 0x80, 0x84, 0x72, 0x6c, 0x20, 0x1f, 0x48, 0xe1, 0x48, 0x4e, 0x0c, 0x1b, 0x89, 0x13, 0x80, 0x72, + 0x65, 0x20, 0x20, 0x28, 0x72, 0x45, 0x2d, 0x2c, 0xee, 0x2a, 0xdc, 0x65, 0x20, 0xa5, 0x4b, 0x91, + 0x2a, 0x4d, 0x9a, 0xfc, 0x89, 0xfb, 0x25, 0x2e, 0x8d, 0xab, 0xae, 0xb9, 0x0f, 0xd8, 0x3f, 0xe4, + 0x0e, 0x5c, 0x2e, 0x65, 0x9f, 0xe5, 0xd3, 0x75, 0x57, 0x69, 0xf8, 0xf8, 0xde, 0x9b, 0xd9, 0x99, + 0xd1, 0x12, 0x36, 0xc4, 0x64, 0x84, 0x79, 0x4b, 0x8c, 0x5b, 0x32, 0xb0, 0x47, 0x31, 0x13, 0x0c, + 0xad, 0xf9, 0x8c, 0x47, 0x8c, 0xbb, 0x3c, 0xb8, 0xb4, 0xc5, 0xd8, 0xfe, 0xf3, 0xab, 0xfa, 0xa7, + 0x62, 0x40, 0xe2, 0xc0, 0x1d, 0x79, 0xb1, 0x98, 0xb4, 0x24, 0xa9, 0x15, 0xb2, 0x90, 0xdd, 0x45, + 0x99, 0xb2, 0x6e, 0xf8, 0xf1, 0x64, 0x24, 0x58, 0x4b, 0xd9, 0xde, 0x79, 0xd6, 0xd7, 0x67, 0xa1, + 0xed, 0x69, 0x72, 0x4e, 0x42, 0x4a, 0x68, 0xf8, 0xd6, 0xdb, 0xcd, 0x90, 0xb1, 0x70, 0x88, 0xb3, + 0x6c, 0xbd, 0xa4, 0xdf, 0xf2, 0xe8, 0x24, 0x7b, 0x65, 0xfd, 0xab, 0x41, 0xf1, 0x7c, 0x8c, 0xbe, + 0x80, 0x52, 0x8f, 0x05, 0x13, 0x43, 0x6b, 0x68, 0xcd, 0xc5, 0x7d, 0xc3, 0x7e, 0x58, 0xb5, 0x7d, + 0x3e, 0xee, 0xb0, 0x60, 0xe2, 0x48, 0x16, 0xfa, 0x06, 0x6a, 0x5e, 0x22, 0x06, 0x2e, 0xa1, 0x7d, + 0x66, 0x14, 0xa5, 0xa4, 0x3e, 0x2b, 0x69, 0x27, 0x62, 0x70, 0x4a, 0xfb, 0xcc, 0xa9, 0x7a, 0x2a, + 0x42, 0x26, 0x40, 0x5a, 0x9f, 0x27, 0x92, 0x18, 0x73, 0x43, 0x6f, 0xe8, 0xcd, 0x25, 0xe7, 0x1e, + 0x62, 0x3d, 0xd7, 0x60, 0xa1, 0x4b, 0x42, 0xfa, 0x23, 0xf3, 0x3f, 0x54, 0x49, 0x9b, 0x50, 0xf5, + 0x07, 0x1e, 0xa1, 0x2e, 0x09, 0x0c, 0xbd, 0xa1, 0x35, 0x6b, 0xce, 0x82, 0x7c, 0x3e, 0x0d, 0xd0, + 0x2e, 0xac, 0x78, 0xbe, 0xcf, 0x12, 0x2a, 0x5c, 0x9a, 0x44, 0x3d, 0x1c, 0x1b, 0xa5, 0x86, 0xd6, + 0x2c, 0x39, 0xcb, 0x0a, 0xfd, 0x55, 0x82, 0xe8, 0x73, 0x58, 0xcb, 0x69, 0x1c, 0xff, 0x91, 0x60, + 0xea, 0x63, 0xa3, 0x2c, 0x89, 0xab, 0x0a, 0xef, 0x2a, 0xd8, 0xfa, 0xbf, 0x08, 0x95, 0xac, 0x6c, + 0xb4, 0x07, 0xd5, 0x08, 0x73, 0xee, 0x85, 0x98, 0x1b, 0x5a, 0x43, 0x6f, 0x2e, 0xee, 0x6f, 0xd8, + 0xd9, 0x98, 0xec, 0x7c, 0x4c, 0x76, 0x9b, 0x4e, 0x9c, 0x29, 0x0b, 0x21, 0x28, 0x45, 0x38, 0xca, + 0x4e, 0x57, 0x73, 0x64, 0x9c, 0x96, 0x28, 0x48, 0x84, 0x59, 0x22, 0xdc, 0x01, 0x26, 0xe1, 0x40, + 0xc8, 0x33, 0xe8, 0xce, 0xb2, 0x42, 0x4f, 0x24, 0x88, 0x3a, 0xb0, 0x8e, 0xc7, 0x02, 0x53, 0x4e, + 0x18, 0x75, 0xd9, 0x48, 0x10, 0x46, 0xb9, 0xf1, 0x7a, 0x61, 0x4e, 0xda, 0xb5, 0x29, 0xff, 0xb7, + 0x8c, 0x8e, 0x2e, 0xc0, 0xa4, 0x8c, 0xba, 0x7e, 0x4c, 0x04, 0xf1, 0xbd, 0xa1, 0xfb, 0x88, 0xe1, + 0xea, 0x1c, 0xc3, 0x2d, 0xca, 0xe8, 0x91, 0xd2, 0xfe, 0xf4, 0xc0, 0xdb, 0x12, 0x50, 0xcd, 0x47, + 0x83, 0x0e, 0x61, 0x29, 0xdd, 0x08, 0x1c, 0xcb, 0x59, 0xe6, 0xcd, 0xd9, 0x9e, 0x1d, 0x66, 0x57, + 0xb2, 0xe4, 0x38, 0x17, 0xf9, 0x34, 0xe6, 0xe8, 0x33, 0xd0, 0xfb, 0x18, 0xab, 0x25, 0xf8, 0x78, + 0x56, 0x77, 0x8c, 0xb1, 0x93, 0x32, 0xac, 0xbf, 0x00, 0xee, 0x3c, 0xd0, 0x01, 0xc0, 0x28, 0xe9, + 0x0d, 0x89, 0xef, 0x5e, 0xe2, 0x7c, 0xeb, 0x1e, 0x3f, 0x4a, 0x2d, 0xe3, 0xfd, 0x8c, 0xe5, 0xda, + 0x45, 0x2c, 0xc0, 0xef, 0x59, 0xbb, 0x33, 0x16, 0xe0, 0x6c, 0xed, 0x22, 0x15, 0x59, 0x4f, 0x8b, + 0x50, 0xcd, 0x61, 0xf4, 0x3d, 0x54, 0x38, 0xa1, 0xe1, 0x10, 0xab, 0xb4, 0x9f, 0xbc, 0xdb, 0xc2, + 0xee, 0x4a, 0xe2, 0x49, 0xc1, 0x51, 0x12, 0xf4, 0x2d, 0x94, 0xa3, 0x64, 0x28, 0x88, 0x4a, 0xdf, + 0x98, 0xa3, 0x3d, 0x4b, 0x79, 0x27, 0x05, 0x27, 0x13, 0xd4, 0x7f, 0x80, 0x4a, 0xe6, 0x86, 0xbe, + 0x86, 0x52, 0x5a, 0x99, 0x4c, 0xbf, 0xb2, 0x6f, 0x3d, 0xb0, 0x50, 0x57, 0x4a, 0xde, 0xf3, 0xd4, + 0xce, 0x91, 0xfc, 0xfa, 0x3f, 0x1a, 0x94, 0xa5, 0x29, 0x6a, 0x43, 0xb5, 0x47, 0x84, 0x17, 0xc7, + 0x5e, 0xde, 0xbb, 0xdd, 0xfb, 0x2e, 0xd9, 0x5d, 0x96, 0x3a, 0x1c, 0xb1, 0x68, 0xe4, 0xf9, 0xa2, + 0x43, 0x44, 0x3b, 0x25, 0x3b, 0x53, 0x19, 0xfa, 0x0e, 0x60, 0xda, 0x4b, 0x6e, 0x14, 0xe5, 0xd8, + 0xe7, 0x35, 0xb3, 0x96, 0x37, 0x93, 0x77, 0xca, 0xa0, 0xf3, 0x24, 0xb2, 0xfe, 0xd6, 0x40, 0x3f, + 0xc6, 0x18, 0xfd, 0x0e, 0x15, 0x2f, 0x4a, 0xff, 0x78, 0x6a, 0x79, 0x3e, 0xba, 0xef, 0x22, 0x6b, + 0x20, 0xb4, 0xb3, 0x77, 0xf5, 0x62, 0xa7, 0xf0, 0xe4, 0xe5, 0x4e, 0x33, 0x24, 0x62, 0x90, 0xf4, + 0x6c, 0x9f, 0x45, 0xad, 0x8c, 0xa6, 0x7e, 0xbe, 0xe4, 0xc1, 0xa5, 0xba, 0x46, 0x53, 0x01, 0x77, + 0x94, 0x29, 0xda, 0x82, 0x5a, 0xe8, 0x71, 0x77, 0x48, 0x22, 0x22, 0x64, 0xd7, 0x4b, 0x4e, 0x35, + 0xf4, 0xf8, 0x2f, 0xe9, 0x73, 0xe7, 0xf0, 0xea, 0xc6, 0xd4, 0xae, 0x6f, 0x4c, 0xed, 0xd5, 0x8d, + 0xa9, 0xfd, 0x77, 0x6b, 0x16, 0xae, 0x6f, 0xcd, 0xc2, 0xb3, 0x5b, 0xb3, 0x70, 0xb1, 0x3b, 0x3f, + 0x91, 0xfa, 0x6e, 0xf4, 0x2a, 0x72, 0xd7, 0x0e, 0xde, 0x04, 0x00, 0x00, 0xff, 0xff, 0x03, 0x5c, + 0xe0, 0x71, 0x50, 0x06, 0x00, 0x00, } func (m *Tx) Marshal() (dAtA []byte, err error) { @@ -2424,7 +2381,7 @@ func (m *ModeInfo_Single) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - m.Mode |= SignMode(b&0x7F) << shift + m.Mode |= signing.SignMode(b&0x7F) << shift if b < 0x80 { break } diff --git a/types/tx/types.proto b/types/tx/types.proto index 51ec4da84390..9aa2f64a8a1e 100644 --- a/types/tx/types.proto +++ b/types/tx/types.proto @@ -4,6 +4,7 @@ package cosmos_sdk.tx.v1; import "third_party/proto/gogoproto/gogo.proto"; import "crypto/types/types.proto"; import "types/types.proto"; +import "types/tx/signing/types.proto"; import "google/protobuf/any.proto"; option go_package = "github.com/cosmos/cosmos-sdk/tx/types"; @@ -104,7 +105,7 @@ message ModeInfo { // to allow for additional fields such as locale for SIGN_MODE_TEXTUAL in the future message Single { // mode is the signing mode of the single signer - SignMode mode = 1; + cosmos_sdk.tx.signing.v1.SignMode mode = 1; } // Multi is the mode info for a multisig public key @@ -118,24 +119,6 @@ message ModeInfo { } } -// SignMode represents a signing mode with its own security guarantees -enum SignMode { - // SIGN_MODE_UNSPECIFIED specifies an unknown signing mode and will be rejected - SIGN_MODE_UNSPECIFIED = 0; - - // SIGN_MODE_DIRECT specifies a signing mode which uses SignDoc and is verified - // with raw bytes from Tx - SIGN_MODE_DIRECT = 1; - - // SIGN_MODE_TEXTUAL is a future signing mode that will verify some human-readable - // textual representation on top of the binary representation from SIGN_MODE_DIRECT - SIGN_MODE_TEXTUAL = 2; - - // SIGN_MODE_LEGACY_AMINO_JSON is a backwards compatibility mode which uses - // Amino JSON and will be removed in the future - SIGN_MODE_LEGACY_AMINO_JSON = 127; -} - // Fee includes the amount of coins paid in fees and the maximum // gas to be used by the transaction. The ratio yields an effective "gasprice", // which must be above some miminum to be accepted into the mempool. diff --git a/x/auth/ante/ante_test.go b/x/auth/ante/ante_test.go index bff57793df30..e3335a569f49 100644 --- a/x/auth/ante/ante_test.go +++ b/x/auth/ante/ante_test.go @@ -13,7 +13,7 @@ import ( "github.com/tendermint/tendermint/crypto/ed25519" "github.com/tendermint/tendermint/crypto/secp256k1" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" sdk "github.com/cosmos/cosmos-sdk/types" sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" "github.com/cosmos/cosmos-sdk/x/auth/ante" diff --git a/x/auth/ante/basic.go b/x/auth/ante/basic.go index b1ed1e8d3691..1e086dc5ea96 100644 --- a/x/auth/ante/basic.go +++ b/x/auth/ante/basic.go @@ -4,7 +4,7 @@ import ( "github.com/tendermint/tendermint/crypto" "github.com/cosmos/cosmos-sdk/codec/legacy" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" sdk "github.com/cosmos/cosmos-sdk/types" sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" "github.com/cosmos/cosmos-sdk/x/auth/types" diff --git a/x/auth/ante/sigverify.go b/x/auth/ante/sigverify.go index 762d53f8c7c0..249c0ecc080f 100644 --- a/x/auth/ante/sigverify.go +++ b/x/auth/ante/sigverify.go @@ -9,7 +9,7 @@ import ( "github.com/tendermint/tendermint/crypto/secp256k1" "github.com/cosmos/cosmos-sdk/codec/legacy" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" sdk "github.com/cosmos/cosmos-sdk/types" sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" "github.com/cosmos/cosmos-sdk/x/auth/types" @@ -306,7 +306,7 @@ func DefaultSigVerificationGasConsumer( return nil case multisig.PubKeyMultisigThreshold: - var multisignature multisig.Multisignature + var multisignature multisig.AminoMultisignature legacy.Cdc.MustUnmarshalBinaryBare(sig, &multisignature) ConsumeMultisignatureVerificationGas(meter, multisignature, pubkey, params) @@ -319,7 +319,7 @@ func DefaultSigVerificationGasConsumer( // ConsumeMultisignatureVerificationGas consumes gas from a GasMeter for verifying a multisig pubkey signature func ConsumeMultisignatureVerificationGas( - meter sdk.GasMeter, sig multisig.Multisignature, pubkey multisig.PubKeyMultisigThreshold, params types.Params, + meter sdk.GasMeter, sig multisig.AminoMultisignature, pubkey multisig.PubKeyMultisigThreshold, params types.Params, ) { size := sig.BitArray.Size() diff --git a/x/auth/ante/sigverify_test.go b/x/auth/ante/sigverify_test.go index 0c69dba9d3d2..fc827feb44cc 100644 --- a/x/auth/ante/sigverify_test.go +++ b/x/auth/ante/sigverify_test.go @@ -4,12 +4,14 @@ import ( "fmt" "testing" + "github.com/cosmos/cosmos-sdk/simapp" + "github.com/stretchr/testify/require" "github.com/tendermint/tendermint/crypto" "github.com/tendermint/tendermint/crypto/ed25519" "github.com/tendermint/tendermint/crypto/secp256k1" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/x/auth/ante" "github.com/cosmos/cosmos-sdk/x/auth/types" @@ -58,15 +60,21 @@ func TestSetPubKey(t *testing.T) { func TestConsumeSignatureVerificationGas(t *testing.T) { params := types.DefaultParams() msg := []byte{1, 2, 3, 4} + _, cdc := simapp.MakeCodecs() pkSet1, sigSet1 := generatePubKeysAndSignatures(5, msg, false) multisigKey1 := multisig.NewPubKeyMultisigThreshold(2, pkSet1) multisignature1 := multisig.NewMultisig(len(pkSet1)) expectedCost1 := expectedGasCostByKeys(pkSet1) for i := 0; i < len(pkSet1); i++ { - err := multisignature1.AddSignatureFromPubKey(sigSet1[i], pkSet1[i], pkSet1) + stdSig := types.StdSignature{PubKey: pkSet1[i].Bytes(), Signature: sigSet1[i]} + sigV2, err := types.StdSignatureToSignatureV2(cdc, stdSig) + require.NoError(t, err) + err = multisig.AddSignatureV2(multisignature1, sigV2, pkSet1) require.NoError(t, err) } + aminoMultisignature1, err := types.SignatureDataToAminoSignature(cdc, multisignature1) + require.NoError(t, err) type args struct { meter sdk.GasMeter @@ -82,7 +90,7 @@ func TestConsumeSignatureVerificationGas(t *testing.T) { }{ {"PubKeyEd25519", args{sdk.NewInfiniteGasMeter(), nil, ed25519.GenPrivKey().PubKey(), params}, types.DefaultSigVerifyCostED25519, true}, {"PubKeySecp256k1", args{sdk.NewInfiniteGasMeter(), nil, secp256k1.GenPrivKey().PubKey(), params}, types.DefaultSigVerifyCostSecp256k1, false}, - {"Multisig", args{sdk.NewInfiniteGasMeter(), multisignature1.Marshal(), multisigKey1, params}, expectedCost1, false}, + {"Multisig", args{sdk.NewInfiniteGasMeter(), aminoMultisignature1, multisigKey1, params}, expectedCost1, false}, {"unknown key", args{sdk.NewInfiniteGasMeter(), nil, nil, params}, 0, true}, } for _, tt := range tests { diff --git a/x/auth/client/cli/tx_multisign.go b/x/auth/client/cli/tx_multisign.go index 58002e4a1244..5263d4c0f706 100644 --- a/x/auth/client/cli/tx_multisign.go +++ b/x/auth/client/cli/tx_multisign.go @@ -14,7 +14,7 @@ import ( "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/codec" "github.com/cosmos/cosmos-sdk/crypto/keyring" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/version" authclient "github.com/cosmos/cosmos-sdk/x/auth/client" @@ -107,7 +107,13 @@ func makeMultiSignCmd(cdc *codec.Codec) func(cmd *cobra.Command, args []string) if ok := stdSig.GetPubKey().VerifyBytes(sigBytes, stdSig.Signature); !ok { return fmt.Errorf("couldn't verify signature") } - if err := multisigSig.AddSignatureFromPubKey(stdSig.Signature, stdSig.GetPubKey(), multisigPub.PubKeys); err != nil { + + sigV2, err := types.StdSignatureToSignatureV2(cdc, stdSig) + if err != nil { + return nil + } + + if err := multisig.AddSignatureV2(multisigSig, sigV2, multisigPub.PubKeys); err != nil { return err } } diff --git a/x/auth/client/cli/validate_sigs.go b/x/auth/client/cli/validate_sigs.go index 7782021a78bf..a6facd0d785e 100644 --- a/x/auth/client/cli/validate_sigs.go +++ b/x/auth/client/cli/validate_sigs.go @@ -10,7 +10,7 @@ import ( "github.com/cosmos/cosmos-sdk/client" "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/codec" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" sdk "github.com/cosmos/cosmos-sdk/types" authclient "github.com/cosmos/cosmos-sdk/x/auth/client" "github.com/cosmos/cosmos-sdk/x/auth/types" @@ -108,7 +108,7 @@ func printAndValidateSigs( multiPK, ok := sig.GetPubKey().(multisig.PubKeyMultisigThreshold) if ok { - var multiSig multisig.Multisignature + var multiSig multisig.AminoMultisignature clientCtx.Codec.MustUnmarshalBinaryBare(sig.Signature, &multiSig) var b strings.Builder diff --git a/x/auth/signing/amino/amino.go b/x/auth/signing/amino/amino.go index 5788fca75494..f9efc3d91ae5 100644 --- a/x/auth/signing/amino/amino.go +++ b/x/auth/signing/amino/amino.go @@ -4,7 +4,7 @@ import ( "fmt" sdk "github.com/cosmos/cosmos-sdk/types" - types "github.com/cosmos/cosmos-sdk/types/tx" + signingtypes "github.com/cosmos/cosmos-sdk/types/tx/signing" "github.com/cosmos/cosmos-sdk/x/auth/ante" "github.com/cosmos/cosmos-sdk/x/auth/signing" authtypes "github.com/cosmos/cosmos-sdk/x/auth/types" @@ -16,19 +16,19 @@ type LegacyAminoJSONHandler struct{} var _ signing.SignModeHandler = LegacyAminoJSONHandler{} // DefaultMode implements SignModeHandler.DefaultMode -func (h LegacyAminoJSONHandler) DefaultMode() types.SignMode { - return types.SignMode_SIGN_MODE_LEGACY_AMINO_JSON +func (h LegacyAminoJSONHandler) DefaultMode() signingtypes.SignMode { + return signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON } // Modes implements SignModeHandler.Modes -func (LegacyAminoJSONHandler) Modes() []types.SignMode { - return []types.SignMode{types.SignMode_SIGN_MODE_LEGACY_AMINO_JSON} +func (LegacyAminoJSONHandler) Modes() []signingtypes.SignMode { + return []signingtypes.SignMode{signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON} } // DefaultMode implements SignModeHandler.GetSignBytes -func (LegacyAminoJSONHandler) GetSignBytes(mode types.SignMode, data signing.SignerData, tx sdk.Tx) ([]byte, error) { - if mode != types.SignMode_SIGN_MODE_LEGACY_AMINO_JSON { - return nil, fmt.Errorf("expected %s, got %s", types.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, mode) +func (LegacyAminoJSONHandler) GetSignBytes(mode signingtypes.SignMode, data signing.SignerData, tx sdk.Tx) ([]byte, error) { + if mode != signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON { + return nil, fmt.Errorf("expected %s, got %s", signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, mode) } feeTx, ok := tx.(ante.FeeTx) diff --git a/x/auth/signing/amino/amino_test.go b/x/auth/signing/amino/amino_test.go index b72eaaffb576..a88ae268d9c7 100644 --- a/x/auth/signing/amino/amino_test.go +++ b/x/auth/signing/amino/amino_test.go @@ -3,12 +3,13 @@ package amino_test import ( "testing" + signingtypes "github.com/cosmos/cosmos-sdk/types/tx/signing" + "github.com/stretchr/testify/require" "github.com/tendermint/tendermint/crypto/secp256k1" sdk "github.com/cosmos/cosmos-sdk/types" - txtypes "github.com/cosmos/cosmos-sdk/types/tx" "github.com/cosmos/cosmos-sdk/x/auth" "github.com/cosmos/cosmos-sdk/x/auth/signing" "github.com/cosmos/cosmos-sdk/x/auth/signing/amino" @@ -55,7 +56,7 @@ func TestLegacyAminoJSONHandler_GetSignBytes(t *testing.T) { AccountNumber: accNum, AccountSequence: seqNum, } - signBz, err := handler.GetSignBytes(txtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, signingData, tx) + signBz, err := handler.GetSignBytes(signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, signingData, tx) require.NoError(t, err) expectedSignBz := auth.StdSignBytes(chainId, accNum, seqNum, fee, msgs, memo) @@ -63,16 +64,16 @@ func TestLegacyAminoJSONHandler_GetSignBytes(t *testing.T) { require.Equal(t, expectedSignBz, signBz) // expect error with wrong sign mode - _, err = handler.GetSignBytes(txtypes.SignMode_SIGN_MODE_DIRECT, signingData, tx) + _, err = handler.GetSignBytes(signingtypes.SignMode_SIGN_MODE_DIRECT, signingData, tx) require.Error(t, err) } func TestLegacyAminoJSONHandler_DefaultMode(t *testing.T) { handler := amino.LegacyAminoJSONHandler{} - require.Equal(t, txtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, handler.DefaultMode()) + require.Equal(t, signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, handler.DefaultMode()) } func TestLegacyAminoJSONHandler_Modes(t *testing.T) { handler := amino.LegacyAminoJSONHandler{} - require.Equal(t, []txtypes.SignMode{txtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON}, handler.Modes()) + require.Equal(t, []signingtypes.SignMode{signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON}, handler.Modes()) } diff --git a/x/auth/signing/handler_map.go b/x/auth/signing/handler_map.go index 90421db94304..936de47da5db 100644 --- a/x/auth/signing/handler_map.go +++ b/x/auth/signing/handler_map.go @@ -3,24 +3,25 @@ package signing import ( "fmt" + "github.com/cosmos/cosmos-sdk/types/tx/signing" + sdk "github.com/cosmos/cosmos-sdk/types" - types "github.com/cosmos/cosmos-sdk/types/tx" ) // SignModeHandlerMap is SignModeHandler that aggregates multiple SignModeHandler's into // a single handler type SignModeHandlerMap struct { - defaultMode types.SignMode - modes []types.SignMode - signModeHandlers map[types.SignMode]SignModeHandler + defaultMode signing.SignMode + modes []signing.SignMode + signModeHandlers map[signing.SignMode]SignModeHandler } var _ SignModeHandler = SignModeHandlerMap{} // NewSignModeHandlerMap returns a new SignModeHandlerMap with the provided defaultMode and handlers -func NewSignModeHandlerMap(defaultMode types.SignMode, handlers []SignModeHandler) SignModeHandlerMap { - handlerMap := make(map[types.SignMode]SignModeHandler) - var modes []types.SignMode +func NewSignModeHandlerMap(defaultMode signing.SignMode, handlers []SignModeHandler) SignModeHandlerMap { + handlerMap := make(map[signing.SignMode]SignModeHandler) + var modes []signing.SignMode for _, h := range handlers { for _, m := range h.Modes() { @@ -40,17 +41,17 @@ func NewSignModeHandlerMap(defaultMode types.SignMode, handlers []SignModeHandle } // DefaultMode implements SignModeHandler.DefaultMode -func (h SignModeHandlerMap) DefaultMode() types.SignMode { +func (h SignModeHandlerMap) DefaultMode() signing.SignMode { return h.defaultMode } // Modes implements SignModeHandler.Modes -func (h SignModeHandlerMap) Modes() []types.SignMode { +func (h SignModeHandlerMap) Modes() []signing.SignMode { return h.modes } // DefaultMode implements SignModeHandler.GetSignBytes -func (h SignModeHandlerMap) GetSignBytes(mode types.SignMode, data SignerData, tx sdk.Tx) ([]byte, error) { +func (h SignModeHandlerMap) GetSignBytes(mode signing.SignMode, data SignerData, tx sdk.Tx) ([]byte, error) { handler, found := h.signModeHandlers[mode] if !found { return nil, fmt.Errorf("can't verify sign mode %s", mode.String()) diff --git a/x/auth/signing/handler_map_test.go b/x/auth/signing/handler_map_test.go index 0133c38a1df6..d69c7979133f 100644 --- a/x/auth/signing/handler_map_test.go +++ b/x/auth/signing/handler_map_test.go @@ -3,12 +3,13 @@ package signing_test import ( "testing" + signingtypes "github.com/cosmos/cosmos-sdk/types/tx/signing" + "github.com/stretchr/testify/require" "github.com/tendermint/tendermint/crypto/secp256k1" sdk "github.com/cosmos/cosmos-sdk/types" - txtypes "github.com/cosmos/cosmos-sdk/types/tx" "github.com/cosmos/cosmos-sdk/x/auth/signing" "github.com/cosmos/cosmos-sdk/x/auth/signing/amino" authtypes "github.com/cosmos/cosmos-sdk/x/auth/types" @@ -17,7 +18,7 @@ import ( func MakeTestHandlerMap() signing.SignModeHandler { return signing.NewSignModeHandlerMap( - txtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, + signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, []signing.SignModeHandler{ amino.LegacyAminoJSONHandler{}, }, @@ -66,27 +67,27 @@ func TestHandlerMap_GetSignBytes(t *testing.T) { AccountNumber: accNum, AccountSequence: seqNum, } - signBz, err := handler.GetSignBytes(txtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, signingData, tx) + signBz, err := handler.GetSignBytes(signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, signingData, tx) require.NoError(t, err) - expectedSignBz, err := aminoJSONHandler.GetSignBytes(txtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, signingData, tx) + expectedSignBz, err := aminoJSONHandler.GetSignBytes(signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, signingData, tx) require.NoError(t, err) require.Equal(t, expectedSignBz, signBz) // expect error with wrong sign mode - _, err = aminoJSONHandler.GetSignBytes(txtypes.SignMode_SIGN_MODE_DIRECT, signingData, tx) + _, err = aminoJSONHandler.GetSignBytes(signingtypes.SignMode_SIGN_MODE_DIRECT, signingData, tx) require.Error(t, err) } func TestHandlerMap_DefaultMode(t *testing.T) { handler := MakeTestHandlerMap() - require.Equal(t, txtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, handler.DefaultMode()) + require.Equal(t, signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, handler.DefaultMode()) } func TestHandlerMap_Modes(t *testing.T) { handler := MakeTestHandlerMap() modes := handler.Modes() - require.Contains(t, modes, txtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON) + require.Contains(t, modes, signingtypes.SignMode_SIGN_MODE_LEGACY_AMINO_JSON) require.Len(t, modes, 1) } diff --git a/x/auth/signing/sign_mode_handler.go b/x/auth/signing/sign_mode_handler.go index 2ad40e31a2ee..31ddcdd51850 100644 --- a/x/auth/signing/sign_mode_handler.go +++ b/x/auth/signing/sign_mode_handler.go @@ -2,7 +2,7 @@ package signing import ( sdk "github.com/cosmos/cosmos-sdk/types" - txtypes "github.com/cosmos/cosmos-sdk/types/tx" + "github.com/cosmos/cosmos-sdk/types/tx/signing" ) // SignModeHandler defines a interface to be implemented by types which will handle @@ -10,14 +10,14 @@ import ( type SignModeHandler interface { // DefaultMode is the default mode that is to be used with this handler if no // other mode is specified. This can be useful for testing and CLI usage - DefaultMode() txtypes.SignMode + DefaultMode() signing.SignMode // Modes is the list of modes supporting by this handler - Modes() []txtypes.SignMode + Modes() []signing.SignMode // GetSignBytes returns the sign bytes for the provided SignMode, SignerData and Tx, // or an error - GetSignBytes(mode txtypes.SignMode, data SignerData, tx sdk.Tx) ([]byte, error) + GetSignBytes(mode signing.SignMode, data SignerData, tx sdk.Tx) ([]byte, error) } // SignerData is the specific information needed to sign a transaction that generally diff --git a/x/auth/types/stdtx.go b/x/auth/types/stdtx.go index 6b6f8ac51030..f403f3602e15 100644 --- a/x/auth/types/stdtx.go +++ b/x/auth/types/stdtx.go @@ -4,13 +4,15 @@ import ( "encoding/json" "fmt" + "github.com/cosmos/cosmos-sdk/types/tx/signing" + "github.com/tendermint/tendermint/crypto" yaml "gopkg.in/yaml.v2" "github.com/cosmos/cosmos-sdk/codec" "github.com/cosmos/cosmos-sdk/codec/legacy" codectypes "github.com/cosmos/cosmos-sdk/codec/types" - "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + "github.com/cosmos/cosmos-sdk/crypto/multisig" sdk "github.com/cosmos/cosmos-sdk/types" sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" ) @@ -356,3 +358,93 @@ func (tx StdTx) UnpackInterfaces(unpacker codectypes.AnyUnpacker) error { } return nil } + +func StdSignatureToSignatureV2(cdc *codec.Codec, sig StdSignature) (signing.SignatureV2, error) { + pk := sig.GetPubKey() + data, err := pubKeySigToSigData(cdc, pk, sig.Signature) + if err != nil { + return signing.SignatureV2{}, err + } + + return signing.SignatureV2{ + PubKey: pk, + Data: data, + }, nil +} + +func pubKeySigToSigData(cdc *codec.Codec, key crypto.PubKey, sig []byte) (signing.SignatureData, error) { + if multiPK, ok := key.(multisig.MultisigPubKey); ok { + var multiSig multisig.AminoMultisignature + err := cdc.UnmarshalBinaryBare(sig, &multiSig) + if err != nil { + return nil, err + } + + sigs := multiSig.Sigs + sigDatas := make([]signing.SignatureData, len(sigs)) + pubKeys := multiPK.GetPubKeys() + bitArray := multiSig.BitArray + n := multiSig.BitArray.Size() + sigIdx := 0 + + for i := 0; i < n; i++ { + if bitArray.GetIndex(i) { + data, err := pubKeySigToSigData(cdc, pubKeys[i], multiSig.Sigs[sigIdx]) + if err != nil { + return nil, err + } + + sigDatas[sigIdx] = data + sigIdx++ + } + } + + return &signing.MultiSignatureData{ + BitArray: bitArray, + Signatures: sigDatas, + }, nil + } else { + return &signing.SingleSignatureData{ + SignMode: signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, + Signature: sig, + }, nil + } +} + +func MultiSignatureDataToAminoMultisignature(cdc *codec.Codec, mSig *signing.MultiSignatureData) (multisig.AminoMultisignature, error) { + n := len(mSig.Signatures) + sigs := make([][]byte, n) + + for i := 0; i < n; i++ { + var err error + sigs[i], err = SignatureDataToAminoSignature(cdc, mSig.Signatures[i]) + if err != nil { + return multisig.AminoMultisignature{}, err + } + } + + return multisig.AminoMultisignature{ + BitArray: mSig.BitArray, + Sigs: sigs, + }, nil +} + +func SignatureDataToAminoSignature(cdc *codec.Codec, data signing.SignatureData) ([]byte, error) { + switch data := data.(type) { + case *signing.SingleSignatureData: + if data.SignMode != signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON { + return nil, fmt.Errorf("expected %s, got %s", signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, data.SignMode) + } + + return data.Signature, nil + case *signing.MultiSignatureData: + aminoMSig, err := MultiSignatureDataToAminoMultisignature(cdc, data) + if err != nil { + return nil, err + } + + return cdc.MarshalBinaryBare(aminoMSig) + default: + return nil, fmt.Errorf("unexpected case") + } +} From 29299bdc0dbc543bb2c94ff81e2bb269fccce5ad Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 15:08:43 -0400 Subject: [PATCH 08/23] Undo move --- client/keys/add.go | 4 ++-- client/keys/show.go | 4 ++-- client/keys/show_test.go | 2 +- crypto/codec/amino.go | 2 +- crypto/keyring/info.go | 2 +- crypto/keyring/keyring_test.go | 2 +- crypto/keyring/output_test.go | 2 +- crypto/{ => types}/multisig/amino.go | 3 ++- crypto/{ => types}/multisig/multisig_pubkey.go | 2 +- crypto/{ => types}/multisig/multisignature.go | 0 crypto/{ => types}/multisig/threshold_pubkey.go | 13 +++++++------ .../{ => types}/multisig/threshold_pubkey_test.go | 4 ++-- go.sum | 3 --- x/auth/ante/ante_test.go | 2 +- x/auth/ante/basic.go | 2 +- x/auth/ante/sigverify.go | 2 +- x/auth/ante/sigverify_test.go | 2 +- x/auth/client/cli/tx_multisign.go | 2 +- x/auth/client/cli/validate_sigs.go | 2 +- x/auth/types/stdtx.go | 2 +- 20 files changed, 28 insertions(+), 29 deletions(-) rename crypto/{ => types}/multisig/amino.go (99%) rename crypto/{ => types}/multisig/multisig_pubkey.go (94%) rename crypto/{ => types}/multisig/multisignature.go (100%) rename crypto/{ => types}/multisig/threshold_pubkey.go (92%) rename crypto/{ => types}/multisig/threshold_pubkey_test.go (98%) diff --git a/client/keys/add.go b/client/keys/add.go index 3f433ecd7705..1159148edc35 100644 --- a/client/keys/add.go +++ b/client/keys/add.go @@ -14,7 +14,7 @@ import ( "github.com/cosmos/cosmos-sdk/client/input" "github.com/cosmos/cosmos-sdk/crypto/hd" "github.com/cosmos/cosmos-sdk/crypto/keyring" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/spf13/cobra" @@ -169,7 +169,7 @@ func RunAddCmd(cmd *cobra.Command, args []string, kb keyring.Keyring, inBuf *buf }) } - pk := multisig.NewPubKeyMultisigThreshold(uint32(multisigThreshold), pks) + pk := multisig.NewPubKeyMultisigThreshold(multisigThreshold, pks) if _, err := kb.SaveMultisig(name, pk); err != nil { return err } diff --git a/client/keys/show.go b/client/keys/show.go index 217efb163a5b..465aa0007a89 100644 --- a/client/keys/show.go +++ b/client/keys/show.go @@ -13,7 +13,7 @@ import ( "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/crypto" "github.com/cosmos/cosmos-sdk/crypto/keyring" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" sdk "github.com/cosmos/cosmos-sdk/types" ) @@ -83,7 +83,7 @@ func runShowCmd(cmd *cobra.Command, args []string) (err error) { return err } - multikey := multisig.NewPubKeyMultisigThreshold(uint32(multisigThreshold), pks) + multikey := multisig.NewPubKeyMultisigThreshold(multisigThreshold, pks) info = keyring.NewMultiInfo(defaultMultiSigKeyName, multikey) } diff --git a/client/keys/show_test.go b/client/keys/show_test.go index 13958b67baac..079e56b4a7c5 100644 --- a/client/keys/show_test.go +++ b/client/keys/show_test.go @@ -12,7 +12,7 @@ import ( "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/crypto/hd" "github.com/cosmos/cosmos-sdk/crypto/keyring" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" "github.com/cosmos/cosmos-sdk/tests" sdk "github.com/cosmos/cosmos-sdk/types" ) diff --git a/crypto/codec/amino.go b/crypto/codec/amino.go index 825ab500d0a4..9ef14fe93d8d 100644 --- a/crypto/codec/amino.go +++ b/crypto/codec/amino.go @@ -7,7 +7,7 @@ import ( "github.com/tendermint/tendermint/crypto/sr25519" "github.com/cosmos/cosmos-sdk/codec" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" ) var amino *codec.Codec diff --git a/crypto/keyring/info.go b/crypto/keyring/info.go index cf504204d95e..1587ec2b02b4 100644 --- a/crypto/keyring/info.go +++ b/crypto/keyring/info.go @@ -6,7 +6,7 @@ import ( "github.com/tendermint/tendermint/crypto" "github.com/cosmos/cosmos-sdk/crypto/hd" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" "github.com/cosmos/cosmos-sdk/types" ) diff --git a/crypto/keyring/keyring_test.go b/crypto/keyring/keyring_test.go index 2bac99dc82f4..55646c1e3af6 100644 --- a/crypto/keyring/keyring_test.go +++ b/crypto/keyring/keyring_test.go @@ -14,7 +14,7 @@ import ( "github.com/cosmos/cosmos-sdk/crypto" "github.com/cosmos/cosmos-sdk/crypto/hd" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" "github.com/cosmos/cosmos-sdk/tests" sdk "github.com/cosmos/cosmos-sdk/types" ) diff --git a/crypto/keyring/output_test.go b/crypto/keyring/output_test.go index 33b7d09dc3cf..150a546b589f 100644 --- a/crypto/keyring/output_test.go +++ b/crypto/keyring/output_test.go @@ -7,7 +7,7 @@ import ( "github.com/tendermint/tendermint/crypto" "github.com/tendermint/tendermint/crypto/secp256k1" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" sdk "github.com/cosmos/cosmos-sdk/types" ) diff --git a/crypto/multisig/amino.go b/crypto/types/multisig/amino.go similarity index 99% rename from crypto/multisig/amino.go rename to crypto/types/multisig/amino.go index e76711f9c475..d51e4fb47441 100644 --- a/crypto/multisig/amino.go +++ b/crypto/types/multisig/amino.go @@ -1,9 +1,10 @@ package multisig import ( - "github.com/cosmos/cosmos-sdk/crypto/types" amino "github.com/tendermint/go-amino" + "github.com/cosmos/cosmos-sdk/crypto/types" + "github.com/tendermint/tendermint/crypto" "github.com/tendermint/tendermint/crypto/ed25519" "github.com/tendermint/tendermint/crypto/secp256k1" diff --git a/crypto/multisig/multisig_pubkey.go b/crypto/types/multisig/multisig_pubkey.go similarity index 94% rename from crypto/multisig/multisig_pubkey.go rename to crypto/types/multisig/multisig_pubkey.go index da5dfe529a3f..31e26742789a 100644 --- a/crypto/multisig/multisig_pubkey.go +++ b/crypto/types/multisig/multisig_pubkey.go @@ -13,5 +13,5 @@ type MultisigPubKey interface { VerifyMultisignature(getSignBytes GetSignBytesFunc, sig *signing.MultiSignatureData) bool GetPubKeys() []crypto.PubKey - Threshold() uint32 + Threshold() uint } diff --git a/crypto/multisig/multisignature.go b/crypto/types/multisig/multisignature.go similarity index 100% rename from crypto/multisig/multisignature.go rename to crypto/types/multisig/multisignature.go diff --git a/crypto/multisig/threshold_pubkey.go b/crypto/types/multisig/threshold_pubkey.go similarity index 92% rename from crypto/multisig/threshold_pubkey.go rename to crypto/types/multisig/threshold_pubkey.go index d5c51b9385ee..c572fedf4ad3 100644 --- a/crypto/multisig/threshold_pubkey.go +++ b/crypto/types/multisig/threshold_pubkey.go @@ -1,17 +1,18 @@ package multisig import ( - "github.com/cosmos/cosmos-sdk/types/tx/signing" "github.com/tendermint/tendermint/crypto" + + "github.com/cosmos/cosmos-sdk/types/tx/signing" ) // PubKeyMultisigThreshold implements a K of N threshold multisig. type PubKeyMultisigThreshold struct { - K uint32 `json:"threshold"` + K uint `json:"threshold"` PubKeys []crypto.PubKey `json:"pubkeys"` } -func (pk PubKeyMultisigThreshold) Threshold() uint32 { +func (pk PubKeyMultisigThreshold) Threshold() uint { return pk.K } @@ -19,11 +20,11 @@ var _ MultisigPubKey = PubKeyMultisigThreshold{} // NewPubKeyMultisigThreshold returns a new PubKeyMultisigThreshold. // Panics if len(pubkeys) < k or 0 >= k. -func NewPubKeyMultisigThreshold(k uint32, pubkeys []crypto.PubKey) MultisigPubKey { +func NewPubKeyMultisigThreshold(k int, pubkeys []crypto.PubKey) MultisigPubKey { if k <= 0 { panic("threshold k of n multisignature: k <= 0") } - if len(pubkeys) < int(k) { + if len(pubkeys) < k { panic("threshold k of n multisignature: len(pubkeys) < k") } for _, pubkey := range pubkeys { @@ -31,7 +32,7 @@ func NewPubKeyMultisigThreshold(k uint32, pubkeys []crypto.PubKey) MultisigPubKe panic("nil pubkey") } } - return PubKeyMultisigThreshold{k, pubkeys} + return PubKeyMultisigThreshold{uint(k), pubkeys} } // VerifyBytes should not be used with this PubKeyMultisigThreshold, instead VerifyMultisignature diff --git a/crypto/multisig/threshold_pubkey_test.go b/crypto/types/multisig/threshold_pubkey_test.go similarity index 98% rename from crypto/multisig/threshold_pubkey_test.go rename to crypto/types/multisig/threshold_pubkey_test.go index c7a924c282b6..103ba38a44ff 100644 --- a/crypto/multisig/threshold_pubkey_test.go +++ b/crypto/types/multisig/threshold_pubkey_test.go @@ -20,7 +20,7 @@ func TestThresholdMultisigValidCases(t *testing.T) { pkSet1, sigSet1 := generatePubKeysAndSignatures(5, []byte{1, 2, 3, 4}) cases := []struct { msg []byte - k uint32 + k int pubkeys []crypto.PubKey signingIndices []int // signatures should be the same size as signingIndices. @@ -41,7 +41,7 @@ func TestThresholdMultisigValidCases(t *testing.T) { multisignature := NewMultisig(len(tc.pubkeys)) signBytesFn := func(mode signing.SignMode) ([]byte, error) { return tc.msg, nil } - for i := uint32(0); i < tc.k-1; i++ { + for i := 0; i < tc.k-1; i++ { signingIndex := tc.signingIndices[i] require.NoError( t, diff --git a/go.sum b/go.sum index 3bae58262634..f3859f33641e 100644 --- a/go.sum +++ b/go.sum @@ -78,7 +78,6 @@ github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDk github.com/cncf/udpa/go v0.0.0-20191209042840-269d4d468f6f/go.mod h1:M8M6+tZqaGXZJjfX53e64911xZQV5JYwmTeXPW+k8Sc= github.com/cockroachdb/datadriven v0.0.0-20190809214429-80d97fb3cbaa/go.mod h1:zn76sxSg3SzpJ0PPJaLDCu+Bu0Lg3sKTORVIj19EIF8= github.com/codahale/hdrhistogram v0.0.0-20161010025455-3a0bb77429bd/go.mod h1:sE/e/2PUdi/liOCUjSTXgM1o87ZssimdTWN964YiIeI= -github.com/confio/ics23 v0.6.0 h1:bQsi55t2+xjW6EWDl83IBF1VWurplbUu+OT6pukeiEo= github.com/confio/ics23-iavl v0.6.0 h1:vVRCuVaP38FCw1kTeEdFuGuiY+2vAGTBQoH7Zxkq/ws= github.com/confio/ics23-iavl v0.6.0/go.mod h1:mmXAxD1vWoO0VP8YHu6mM1QHGv71NQqa1iSVm4HeKcY= github.com/confio/ics23/go v0.0.0-20200323120010-7d9a00f0a2fa/go.mod h1:W1I3XC8d9N8OTu/ct5VJ84ylcOunZwMXsWkd27nvVts= @@ -467,8 +466,6 @@ github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UV github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= github.com/stretchr/testify v1.5.1 h1:nOGnQDM7FYENwehXlg/kFVnos3rEvtKTjRvOWSzb6H4= github.com/stretchr/testify v1.5.1/go.mod h1:5W2xD1RspED5o8YsWQXVCued0rvSQ+mT+I5cxcmMvtA= -github.com/stretchr/testify v1.6.0 h1:jlIyCplCJFULU/01vCkhKuTyc3OorI3bJFuw6obfgho= -github.com/stretchr/testify v1.6.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/stretchr/testify v1.6.1 h1:hDPOHmpOpP40lSULcqw7IrRb/u7w6RpDC9399XyoNd0= github.com/stretchr/testify v1.6.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= github.com/subosito/gotenv v1.2.0 h1:Slr1R9HxAlEKefgq5jn9U+DnETlIUa6HfgEzj0g5d7s= diff --git a/x/auth/ante/ante_test.go b/x/auth/ante/ante_test.go index e3335a569f49..bff57793df30 100644 --- a/x/auth/ante/ante_test.go +++ b/x/auth/ante/ante_test.go @@ -13,7 +13,7 @@ import ( "github.com/tendermint/tendermint/crypto/ed25519" "github.com/tendermint/tendermint/crypto/secp256k1" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" sdk "github.com/cosmos/cosmos-sdk/types" sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" "github.com/cosmos/cosmos-sdk/x/auth/ante" diff --git a/x/auth/ante/basic.go b/x/auth/ante/basic.go index 1e086dc5ea96..b1ed1e8d3691 100644 --- a/x/auth/ante/basic.go +++ b/x/auth/ante/basic.go @@ -4,7 +4,7 @@ import ( "github.com/tendermint/tendermint/crypto" "github.com/cosmos/cosmos-sdk/codec/legacy" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" sdk "github.com/cosmos/cosmos-sdk/types" sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" "github.com/cosmos/cosmos-sdk/x/auth/types" diff --git a/x/auth/ante/sigverify.go b/x/auth/ante/sigverify.go index 249c0ecc080f..29a561479fee 100644 --- a/x/auth/ante/sigverify.go +++ b/x/auth/ante/sigverify.go @@ -9,7 +9,7 @@ import ( "github.com/tendermint/tendermint/crypto/secp256k1" "github.com/cosmos/cosmos-sdk/codec/legacy" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" sdk "github.com/cosmos/cosmos-sdk/types" sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" "github.com/cosmos/cosmos-sdk/x/auth/types" diff --git a/x/auth/ante/sigverify_test.go b/x/auth/ante/sigverify_test.go index fc827feb44cc..33781020af06 100644 --- a/x/auth/ante/sigverify_test.go +++ b/x/auth/ante/sigverify_test.go @@ -11,7 +11,7 @@ import ( "github.com/tendermint/tendermint/crypto/ed25519" "github.com/tendermint/tendermint/crypto/secp256k1" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/x/auth/ante" "github.com/cosmos/cosmos-sdk/x/auth/types" diff --git a/x/auth/client/cli/tx_multisign.go b/x/auth/client/cli/tx_multisign.go index 5263d4c0f706..b20ff1800c70 100644 --- a/x/auth/client/cli/tx_multisign.go +++ b/x/auth/client/cli/tx_multisign.go @@ -14,7 +14,7 @@ import ( "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/codec" "github.com/cosmos/cosmos-sdk/crypto/keyring" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/version" authclient "github.com/cosmos/cosmos-sdk/x/auth/client" diff --git a/x/auth/client/cli/validate_sigs.go b/x/auth/client/cli/validate_sigs.go index a6facd0d785e..630085da1297 100644 --- a/x/auth/client/cli/validate_sigs.go +++ b/x/auth/client/cli/validate_sigs.go @@ -10,7 +10,7 @@ import ( "github.com/cosmos/cosmos-sdk/client" "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/codec" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" sdk "github.com/cosmos/cosmos-sdk/types" authclient "github.com/cosmos/cosmos-sdk/x/auth/client" "github.com/cosmos/cosmos-sdk/x/auth/types" diff --git a/x/auth/types/stdtx.go b/x/auth/types/stdtx.go index f403f3602e15..8349e1d923e2 100644 --- a/x/auth/types/stdtx.go +++ b/x/auth/types/stdtx.go @@ -12,7 +12,7 @@ import ( "github.com/cosmos/cosmos-sdk/codec" "github.com/cosmos/cosmos-sdk/codec/legacy" codectypes "github.com/cosmos/cosmos-sdk/codec/types" - "github.com/cosmos/cosmos-sdk/crypto/multisig" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" sdk "github.com/cosmos/cosmos-sdk/types" sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" ) From d2e16a21ec3621d2224abdb6a95f3666bbbfb110 Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 15:09:13 -0400 Subject: [PATCH 09/23] remove func --- crypto/types/types.go | 19 ------------------- 1 file changed, 19 deletions(-) delete mode 100644 crypto/types/types.go diff --git a/crypto/types/types.go b/crypto/types/types.go deleted file mode 100644 index d61619e5dcbe..000000000000 --- a/crypto/types/types.go +++ /dev/null @@ -1,19 +0,0 @@ -package types - -import ( - "fmt" -) - -func DecodeMultisignatures(bz []byte) ([][]byte, error) { - multisig := MultiSignature{} - err := multisig.Unmarshal(bz) - if err != nil { - return nil, err - } - // unrecognized fields must be discarded because otherwise this would present a transaction malleability issue - // which could allow transactions to be bloated with arbitrary bytes - if len(multisig.XXX_unrecognized) > 0 { - return nil, fmt.Errorf("rejecting unrecognized fields found in MultiSignature") - } - return multisig.Signatures, nil -} From 2f46b952b96be0c95ccd64f97a415916f20d317b Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 15:10:43 -0400 Subject: [PATCH 10/23] undo --- crypto/keyring/info.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crypto/keyring/info.go b/crypto/keyring/info.go index 1587ec2b02b4..74bb62d774f2 100644 --- a/crypto/keyring/info.go +++ b/crypto/keyring/info.go @@ -202,7 +202,7 @@ func NewMultiInfo(name string, pub crypto.PubKey) Info { return &multiInfo{ Name: name, PubKey: pub, - Threshold: uint(multiPK.K), + Threshold: multiPK.K, PubKeys: pubKeys, } } From bdcd4ec14b34640c9cbba8ea86adaaba1fccd2e5 Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 15:17:01 -0400 Subject: [PATCH 11/23] godocs --- types/tx/signing/signature.go | 10 +++++++++- types/tx/signing/signature_data.go | 16 ++++++++++++++-- 2 files changed, 23 insertions(+), 3 deletions(-) diff --git a/types/tx/signing/signature.go b/types/tx/signing/signature.go index 27bf9580be38..1ad1711439b8 100644 --- a/types/tx/signing/signature.go +++ b/types/tx/signing/signature.go @@ -2,7 +2,15 @@ package signing import "github.com/tendermint/tendermint/crypto" +// SignatureV2 is a convenience type that is easier to use in application logic +// than the protobuf SignerInfo's and raw signature bytes. It goes beyond the +// first sdk.Signature types by supporting sign modes and explicitly nested +// multi-signatures. type SignatureV2 struct { + // PubKey is the public key to use for verifying the signature PubKey crypto.PubKey - Data SignatureData + + // Data is the actual data of the signature which includes SignMode's and + // the signatures themselves for either single or multi-signatures. + Data SignatureData } diff --git a/types/tx/signing/signature_data.go b/types/tx/signing/signature_data.go index ffb87d45678c..06e6b6edb22e 100644 --- a/types/tx/signing/signature_data.go +++ b/types/tx/signing/signature_data.go @@ -4,17 +4,29 @@ import ( "github.com/cosmos/cosmos-sdk/crypto/types" ) +// SignatureData represents either a *SingleSignatureData or *MultiSignatureData. +// It is a convenience type that is easier to use in buiness logic than the encoded +// protobuf ModeInfo's and raw signatures. type SignatureData interface { isSignatureData() } +// SingleSignatureData represents the signature and SignMode of a single (non-multisig) signer type SingleSignatureData struct { - SignMode SignMode + // SignMode represents the SignMode of the signature + SignMode SignMode + + // SignMode represents the SignMode of the signature Signature []byte } +// SingleSignatureData represents the nested SignatureData of a multisig signature type MultiSignatureData struct { - BitArray *types.CompactBitArray + // BitArray is a compact way of indicating which signers from the multisig key + // have signed + BitArray *types.CompactBitArray + + // Signatures is the nested SignatureData's for each signer Signatures []SignatureData } From 038a472fc2ac0807bf706d7dec5f360dc2a6ed04 Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 15:25:02 -0400 Subject: [PATCH 12/23] godocs, cleanup --- crypto/types/multisig/amino.go | 3 ++- crypto/types/multisig/multisig_pubkey.go | 17 --------------- crypto/types/multisig/pubkey.go | 25 +++++++++++++++++++++++ crypto/types/multisig/threshold_pubkey.go | 12 +++++------ x/auth/types/stdtx.go | 2 +- 5 files changed, 33 insertions(+), 26 deletions(-) delete mode 100644 crypto/types/multisig/multisig_pubkey.go create mode 100644 crypto/types/multisig/pubkey.go diff --git a/crypto/types/multisig/amino.go b/crypto/types/multisig/amino.go index d51e4fb47441..1ebdbe4b504e 100644 --- a/crypto/types/multisig/amino.go +++ b/crypto/types/multisig/amino.go @@ -31,7 +31,8 @@ func init() { secp256k1.PubKeyAminoName, nil) } -// AminoMultisignature is used to represent the signature object used in the multisigs. +// AminoMultisignature is used to represent amino multi-signatures for StdTx's. +// It is assumed that all signatures were made with SIGN_MODE_LEGACY_AMINO_JSON. // Sigs is a list of signatures, sorted by corresponding index. type AminoMultisignature struct { BitArray *types.CompactBitArray diff --git a/crypto/types/multisig/multisig_pubkey.go b/crypto/types/multisig/multisig_pubkey.go deleted file mode 100644 index 31e26742789a..000000000000 --- a/crypto/types/multisig/multisig_pubkey.go +++ /dev/null @@ -1,17 +0,0 @@ -package multisig - -import ( - "github.com/tendermint/tendermint/crypto" - - "github.com/cosmos/cosmos-sdk/types/tx/signing" -) - -type GetSignBytesFunc func(mode signing.SignMode) ([]byte, error) - -type MultisigPubKey interface { - crypto.PubKey - - VerifyMultisignature(getSignBytes GetSignBytesFunc, sig *signing.MultiSignatureData) bool - GetPubKeys() []crypto.PubKey - Threshold() uint -} diff --git a/crypto/types/multisig/pubkey.go b/crypto/types/multisig/pubkey.go new file mode 100644 index 000000000000..42101f35b1de --- /dev/null +++ b/crypto/types/multisig/pubkey.go @@ -0,0 +1,25 @@ +package multisig + +import ( + "github.com/tendermint/tendermint/crypto" + + "github.com/cosmos/cosmos-sdk/types/tx/signing" +) + +// PubKey defines a type which supports multi-signature verification via MultiSignatureData +// which supports multiple SignMode's. +type PubKey interface { + crypto.PubKey + + // VerifyMultisignature verifies the provide multi-signature represented by MultiSignatureData + // using getSignBytes to retrieve the sign bytes to verify against for the provided mode. + VerifyMultisignature(getSignBytes GetSignBytesFunc, sig *signing.MultiSignatureData) bool + + // GetPubKeys returns the crypto.PubKey's nested within the multi-sig PubKey + GetPubKeys() []crypto.PubKey +} + +// GetSignBytesFunc defines a function type which returns sign bytes for a given SignMode or an error. +// It will generally be implemented as a closure which wraps whatever signable object signatures are +// being verified against. +type GetSignBytesFunc func(mode signing.SignMode) ([]byte, error) diff --git a/crypto/types/multisig/threshold_pubkey.go b/crypto/types/multisig/threshold_pubkey.go index c572fedf4ad3..90d33b9abed1 100644 --- a/crypto/types/multisig/threshold_pubkey.go +++ b/crypto/types/multisig/threshold_pubkey.go @@ -12,15 +12,11 @@ type PubKeyMultisigThreshold struct { PubKeys []crypto.PubKey `json:"pubkeys"` } -func (pk PubKeyMultisigThreshold) Threshold() uint { - return pk.K -} - -var _ MultisigPubKey = PubKeyMultisigThreshold{} +var _ PubKey = PubKeyMultisigThreshold{} // NewPubKeyMultisigThreshold returns a new PubKeyMultisigThreshold. // Panics if len(pubkeys) < k or 0 >= k. -func NewPubKeyMultisigThreshold(k int, pubkeys []crypto.PubKey) MultisigPubKey { +func NewPubKeyMultisigThreshold(k int, pubkeys []crypto.PubKey) PubKey { if k <= 0 { panic("threshold k of n multisignature: k <= 0") } @@ -41,6 +37,7 @@ func (pk PubKeyMultisigThreshold) VerifyBytes([]byte, []byte) bool { return false } +// VerifyMultisignature implements the PubKey.VerifyMultisignature method func (pk PubKeyMultisigThreshold) VerifyMultisignature(getSignBytes GetSignBytesFunc, sig *signing.MultiSignatureData) bool { bitarray := sig.BitArray sigs := sig.Signatures @@ -72,7 +69,7 @@ func (pk PubKeyMultisigThreshold) VerifyMultisignature(getSignBytes GetSignBytes return false } case *signing.MultiSignatureData: - nestedMultisigPk, ok := pk.PubKeys[i].(MultisigPubKey) + nestedMultisigPk, ok := pk.PubKeys[i].(PubKey) if !ok { return false } @@ -88,6 +85,7 @@ func (pk PubKeyMultisigThreshold) VerifyMultisignature(getSignBytes GetSignBytes return true } +// GetPubKeys implements the PubKey.GetPubKeys method func (pk PubKeyMultisigThreshold) GetPubKeys() []crypto.PubKey { return pk.PubKeys } diff --git a/x/auth/types/stdtx.go b/x/auth/types/stdtx.go index 8349e1d923e2..7bf64c0ea6ff 100644 --- a/x/auth/types/stdtx.go +++ b/x/auth/types/stdtx.go @@ -373,7 +373,7 @@ func StdSignatureToSignatureV2(cdc *codec.Codec, sig StdSignature) (signing.Sign } func pubKeySigToSigData(cdc *codec.Codec, key crypto.PubKey, sig []byte) (signing.SignatureData, error) { - if multiPK, ok := key.(multisig.MultisigPubKey); ok { + if multiPK, ok := key.(multisig.PubKey); ok { var multiSig multisig.AminoMultisignature err := cdc.UnmarshalBinaryBare(sig, &multiSig) if err != nil { From 42d97fb0c854fa4d7d824d0f2f0838d4075cebcc Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 15:33:43 -0400 Subject: [PATCH 13/23] Cleanup --- crypto/types/multisig/{amino.go => codec.go} | 10 ---------- crypto/types/multisig/multisignature.go | 11 +++++++++-- 2 files changed, 9 insertions(+), 12 deletions(-) rename crypto/types/multisig/{amino.go => codec.go} (70%) diff --git a/crypto/types/multisig/amino.go b/crypto/types/multisig/codec.go similarity index 70% rename from crypto/types/multisig/amino.go rename to crypto/types/multisig/codec.go index 1ebdbe4b504e..9fedd111b1c5 100644 --- a/crypto/types/multisig/amino.go +++ b/crypto/types/multisig/codec.go @@ -3,8 +3,6 @@ package multisig import ( amino "github.com/tendermint/go-amino" - "github.com/cosmos/cosmos-sdk/crypto/types" - "github.com/tendermint/tendermint/crypto" "github.com/tendermint/tendermint/crypto/ed25519" "github.com/tendermint/tendermint/crypto/secp256k1" @@ -30,11 +28,3 @@ func init() { cdc.RegisterConcrete(secp256k1.PubKeySecp256k1{}, secp256k1.PubKeyAminoName, nil) } - -// AminoMultisignature is used to represent amino multi-signatures for StdTx's. -// It is assumed that all signatures were made with SIGN_MODE_LEGACY_AMINO_JSON. -// Sigs is a list of signatures, sorted by corresponding index. -type AminoMultisignature struct { - BitArray *types.CompactBitArray - Sigs [][]byte -} diff --git a/crypto/types/multisig/multisignature.go b/crypto/types/multisig/multisignature.go index d04e95c3bcc1..b127b41c4d9c 100644 --- a/crypto/types/multisig/multisignature.go +++ b/crypto/types/multisig/multisignature.go @@ -4,13 +4,20 @@ import ( "fmt" "strings" - "github.com/cosmos/cosmos-sdk/types/tx/signing" - "github.com/tendermint/tendermint/crypto" "github.com/cosmos/cosmos-sdk/crypto/types" + "github.com/cosmos/cosmos-sdk/types/tx/signing" ) +// AminoMultisignature is used to represent amino multi-signatures for StdTx's. +// It is assumed that all signatures were made with SIGN_MODE_LEGACY_AMINO_JSON. +// Sigs is a list of signatures, sorted by corresponding index. +type AminoMultisignature struct { + BitArray *types.CompactBitArray + Sigs [][]byte +} + // NewMultisig returns a new MultiSignatureData func NewMultisig(n int) *signing.MultiSignatureData { return &signing.MultiSignatureData{BitArray: types.NewCompactBitArray(n), Signatures: make([]signing.SignatureData, 0, n)} From 61cc024aa8d1083cf69eddb6173f9c6acdd11c1d Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 15:53:08 -0400 Subject: [PATCH 14/23] godocs, tests --- types/tx/signing/signature.go | 3 +- x/auth/types/stdtx.go | 5 +++ x/auth/types/stdtx_test.go | 60 +++++++++++++++++++++++++++++++++++ 3 files changed, 67 insertions(+), 1 deletion(-) diff --git a/types/tx/signing/signature.go b/types/tx/signing/signature.go index 1ad1711439b8..47744de28433 100644 --- a/types/tx/signing/signature.go +++ b/types/tx/signing/signature.go @@ -5,7 +5,8 @@ import "github.com/tendermint/tendermint/crypto" // SignatureV2 is a convenience type that is easier to use in application logic // than the protobuf SignerInfo's and raw signature bytes. It goes beyond the // first sdk.Signature types by supporting sign modes and explicitly nested -// multi-signatures. +// multi-signatures. It is intended to be used for both building and verifying +// signatures. type SignatureV2 struct { // PubKey is the public key to use for verifying the signature PubKey crypto.PubKey diff --git a/x/auth/types/stdtx.go b/x/auth/types/stdtx.go index 7bf64c0ea6ff..14ef8f2a03c9 100644 --- a/x/auth/types/stdtx.go +++ b/x/auth/types/stdtx.go @@ -359,6 +359,7 @@ func (tx StdTx) UnpackInterfaces(unpacker codectypes.AnyUnpacker) error { return nil } +// StdSignatureToSignatureV2 converts a StdSignature to a SignatureV2 func StdSignatureToSignatureV2(cdc *codec.Codec, sig StdSignature) (signing.SignatureV2, error) { pk := sig.GetPubKey() data, err := pubKeySigToSigData(cdc, pk, sig.Signature) @@ -411,6 +412,8 @@ func pubKeySigToSigData(cdc *codec.Codec, key crypto.PubKey, sig []byte) (signin } } +// MultiSignatureDataToAminoMultisignature converts a MultiSignatureData to an AminoMultisignature. +// Only SIGN_MODE_LEGACY_AMINO_JSON is supported. func MultiSignatureDataToAminoMultisignature(cdc *codec.Codec, mSig *signing.MultiSignatureData) (multisig.AminoMultisignature, error) { n := len(mSig.Signatures) sigs := make([][]byte, n) @@ -429,6 +432,8 @@ func MultiSignatureDataToAminoMultisignature(cdc *codec.Codec, mSig *signing.Mul }, nil } +// SignatureDataToAminoSignature converts a SignatureData to amino-encoded signature bytes. +// Only SIGN_MODE_LEGACY_AMINO_JSON is supported. func SignatureDataToAminoSignature(cdc *codec.Codec, data signing.SignatureData) ([]byte, error) { switch data := data.(type) { case *signing.SingleSignatureData: diff --git a/x/auth/types/stdtx_test.go b/x/auth/types/stdtx_test.go index 09230d03eec6..df43ccda9268 100644 --- a/x/auth/types/stdtx_test.go +++ b/x/auth/types/stdtx_test.go @@ -4,6 +4,11 @@ import ( "fmt" "testing" + "github.com/cosmos/cosmos-sdk/crypto/types" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" + + "github.com/cosmos/cosmos-sdk/types/tx/signing" + "github.com/stretchr/testify/require" abci "github.com/tendermint/tendermint/abci/types" "github.com/tendermint/tendermint/crypto" @@ -167,3 +172,58 @@ func TestStdSignatureMarshalYAML(t *testing.T) { require.Equal(t, tc.output, string(bz), "test case #%d", i) } } + +func TestSignatureV2Conversions(t *testing.T) { + _, pubKey, _ := KeyTestPubAddr() + cdc := codec.New() + sdk.RegisterCodec(cdc) + RegisterCodec(cdc) + dummy := []byte("dummySig") + sig := StdSignature{PubKey: pubKey.Bytes(), Signature: dummy} + + sigV2, err := StdSignatureToSignatureV2(cdc, sig) + require.NoError(t, err) + require.Equal(t, pubKey, sigV2.PubKey) + require.Equal(t, &signing.SingleSignatureData{ + SignMode: signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, + Signature: dummy, + }, sigV2.Data) + + sigBz, err := SignatureDataToAminoSignature(cdc, sigV2.Data) + require.NoError(t, err) + require.Equal(t, dummy, sigBz) + + // multisigs + _, pubKey2, _ := KeyTestPubAddr() + multiPK := multisig.NewPubKeyMultisigThreshold(1, []crypto.PubKey{ + pubKey, pubKey2, + }) + dummy2 := []byte("dummySig2") + bitArray := types.NewCompactBitArray(2) + bitArray.SetIndex(0, true) + bitArray.SetIndex(1, true) + msigData := &signing.MultiSignatureData{ + BitArray: bitArray, + Signatures: []signing.SignatureData{ + &signing.SingleSignatureData{ + SignMode: signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, + Signature: dummy, + }, + &signing.SingleSignatureData{ + SignMode: signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, + Signature: dummy2, + }, + }, + } + + msig, err := SignatureDataToAminoSignature(cdc, msigData) + require.NoError(t, err) + + sigV2, err = StdSignatureToSignatureV2(cdc, StdSignature{ + PubKey: multiPK.Bytes(), + Signature: msig, + }) + require.NoError(t, err) + require.Equal(t, multiPK, sigV2.PubKey) + require.Equal(t, msigData, sigV2.Data) +} From 19453424fc2754ba5bdd3d1c13935e772a48d521 Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 15:55:47 -0400 Subject: [PATCH 15/23] lint --- x/auth/types/stdtx.go | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/x/auth/types/stdtx.go b/x/auth/types/stdtx.go index 14ef8f2a03c9..cb786a625e51 100644 --- a/x/auth/types/stdtx.go +++ b/x/auth/types/stdtx.go @@ -404,12 +404,12 @@ func pubKeySigToSigData(cdc *codec.Codec, key crypto.PubKey, sig []byte) (signin BitArray: bitArray, Signatures: sigDatas, }, nil - } else { - return &signing.SingleSignatureData{ - SignMode: signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, - Signature: sig, - }, nil } + + return &signing.SingleSignatureData{ + SignMode: signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, + Signature: sig, + }, nil } // MultiSignatureDataToAminoMultisignature converts a MultiSignatureData to an AminoMultisignature. From a9ad3be1dbbdd2f55c023d7c44a1dac65c1b4fd3 Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Tue, 9 Jun 2020 16:21:53 -0400 Subject: [PATCH 16/23] Re-enable VerifyBytes --- crypto/types/multisig/threshold_pubkey.go | 43 ++++++++++++++++++++--- x/auth/client/cli/tx_multisign.go | 9 +++-- 2 files changed, 46 insertions(+), 6 deletions(-) diff --git a/crypto/types/multisig/threshold_pubkey.go b/crypto/types/multisig/threshold_pubkey.go index 90d33b9abed1..250c237f0976 100644 --- a/crypto/types/multisig/threshold_pubkey.go +++ b/crypto/types/multisig/threshold_pubkey.go @@ -31,10 +31,45 @@ func NewPubKeyMultisigThreshold(k int, pubkeys []crypto.PubKey) PubKey { return PubKeyMultisigThreshold{uint(k), pubkeys} } -// VerifyBytes should not be used with this PubKeyMultisigThreshold, instead VerifyMultisignature -// must be used -func (pk PubKeyMultisigThreshold) VerifyBytes([]byte, []byte) bool { - return false +// VerifyBytes expects sig to be an amino encoded version of a MultiSignature. +// Returns true iff the multisignature contains k or more signatures +// for the correct corresponding keys, +// and all signatures are valid. (Not just k of the signatures) +// The multisig uses a bitarray, so multiple signatures for the same key is not +// a concern. +// +// NOTE: VerifyMultisignature should preferred to VerifyBytes which only works +// with amino multisignatures. +func (pk PubKeyMultisigThreshold) VerifyBytes(msg []byte, marshalledSig []byte) bool { + var sig AminoMultisignature + err := cdc.UnmarshalBinaryBare(marshalledSig, &sig) + if err != nil { + return false + } + size := sig.BitArray.Size() + // ensure bit array is the correct size + if len(pk.PubKeys) != size { + return false + } + // ensure size of signature list + if len(sig.Sigs) < int(pk.K) || len(sig.Sigs) > size { + return false + } + // ensure at least k signatures are set + if sig.BitArray.NumTrueBitsBefore(size) < int(pk.K) { + return false + } + // index in the list of signatures which we are concerned with. + sigIndex := 0 + for i := 0; i < size; i++ { + if sig.BitArray.GetIndex(i) { + if !pk.PubKeys[i].VerifyBytes(msg, sig.Sigs[sigIndex]) { + return false + } + sigIndex++ + } + } + return true } // VerifyMultisignature implements the PubKey.VerifyMultisignature method diff --git a/x/auth/client/cli/tx_multisign.go b/x/auth/client/cli/tx_multisign.go index b20ff1800c70..c0af04548fb5 100644 --- a/x/auth/client/cli/tx_multisign.go +++ b/x/auth/client/cli/tx_multisign.go @@ -118,8 +118,13 @@ func makeMultiSignCmd(cdc *codec.Codec) func(cmd *cobra.Command, args []string) } } - newStdSig := types.StdSignature{Signature: cdc.MustMarshalBinaryBare(multisigSig), PubKey: multisigPub.Bytes()} //nolint:staticcheck - newTx := types.NewStdTx(stdTx.GetMsgs(), stdTx.Fee, []types.StdSignature{newStdSig}, stdTx.GetMemo()) //nolint:staticcheck + sigBz, err := types.SignatureDataToAminoSignature(cdc, multisigSig) + if err != nil { + return err + } + + newStdSig := types.StdSignature{Signature: sigBz, PubKey: multisigPub.Bytes()} //nolint:staticcheck + newTx := types.NewStdTx(stdTx.GetMsgs(), stdTx.Fee, []types.StdSignature{newStdSig}, stdTx.GetMemo()) //nolint:staticcheck sigOnly := viper.GetBool(flagSigOnly) var json []byte From 8f7b0be941efcd9250de38e22141385722380dca Mon Sep 17 00:00:00 2001 From: sahith-narahari Date: Thu, 11 Jun 2020 03:23:41 +0530 Subject: [PATCH 17/23] Address comments --- crypto/types/multisig/multisignature.go | 10 +++ crypto/types/multisig/pubkey.go | 2 +- crypto/types/multisig/threshold_pubkey.go | 23 +++---- .../types/multisig/threshold_pubkey_test.go | 36 ++++++++--- x/auth/signing/amino/amino_test.go | 3 +- x/auth/signing/handler_map_test.go | 3 +- x/auth/types/stdtx.go | 63 +++++++++---------- 7 files changed, 84 insertions(+), 56 deletions(-) diff --git a/crypto/types/multisig/multisignature.go b/crypto/types/multisig/multisignature.go index b127b41c4d9c..e5a68fa285d4 100644 --- a/crypto/types/multisig/multisignature.go +++ b/crypto/types/multisig/multisignature.go @@ -58,6 +58,16 @@ func AddSignature(mSig *signing.MultiSignatureData, sig signing.SignatureData, i // AddSignatureFromPubKey adds a signature to the multisig, at the index in // keys corresponding to the provided pubkey. func AddSignatureFromPubKey(mSig *signing.MultiSignatureData, sig signing.SignatureData, pubkey crypto.PubKey, keys []crypto.PubKey) error { + if mSig == nil { + return fmt.Errorf("value of mSig is nil %v", mSig) + } + if sig == nil { + return fmt.Errorf("value of sig is nil %v", mSig) + } + + if pubkey == nil || keys == nil { + return fmt.Errorf("pubkey or keys can't be nil %v %v", pubkey, keys) + } index := getIndex(pubkey, keys) if index == -1 { keysStr := make([]string, len(keys)) diff --git a/crypto/types/multisig/pubkey.go b/crypto/types/multisig/pubkey.go index 42101f35b1de..a3935a4bb4d4 100644 --- a/crypto/types/multisig/pubkey.go +++ b/crypto/types/multisig/pubkey.go @@ -13,7 +13,7 @@ type PubKey interface { // VerifyMultisignature verifies the provide multi-signature represented by MultiSignatureData // using getSignBytes to retrieve the sign bytes to verify against for the provided mode. - VerifyMultisignature(getSignBytes GetSignBytesFunc, sig *signing.MultiSignatureData) bool + VerifyMultisignature(getSignBytes GetSignBytesFunc, sig *signing.MultiSignatureData) error // GetPubKeys returns the crypto.PubKey's nested within the multi-sig PubKey GetPubKeys() []crypto.PubKey diff --git a/crypto/types/multisig/threshold_pubkey.go b/crypto/types/multisig/threshold_pubkey.go index 250c237f0976..b229a5ba6f04 100644 --- a/crypto/types/multisig/threshold_pubkey.go +++ b/crypto/types/multisig/threshold_pubkey.go @@ -1,6 +1,7 @@ package multisig import ( + "fmt" "github.com/tendermint/tendermint/crypto" "github.com/cosmos/cosmos-sdk/types/tx/signing" @@ -73,21 +74,21 @@ func (pk PubKeyMultisigThreshold) VerifyBytes(msg []byte, marshalledSig []byte) } // VerifyMultisignature implements the PubKey.VerifyMultisignature method -func (pk PubKeyMultisigThreshold) VerifyMultisignature(getSignBytes GetSignBytesFunc, sig *signing.MultiSignatureData) bool { +func (pk PubKeyMultisigThreshold) VerifyMultisignature(getSignBytes GetSignBytesFunc, sig *signing.MultiSignatureData) error { bitarray := sig.BitArray sigs := sig.Signatures size := bitarray.Size() // ensure bit array is the correct size if len(pk.PubKeys) != size { - return false + return fmt.Errorf("bit array size is incorrect %d", len(pk.PubKeys)) } // ensure size of signature list if len(sigs) < int(pk.K) || len(sigs) > size { - return false + return fmt.Errorf("signature size is incorrect %d", len(sigs)) } // ensure at least k signatures are set if bitarray.NumTrueBitsBefore(size) < int(pk.K) { - return false + return fmt.Errorf("") } // index in the list of signatures which we are concerned with. sigIndex := 0 @@ -98,26 +99,26 @@ func (pk PubKeyMultisigThreshold) VerifyMultisignature(getSignBytes GetSignBytes case *signing.SingleSignatureData: msg, err := getSignBytes(si.SignMode) if err != nil { - return false + return err } if !pk.PubKeys[i].VerifyBytes(msg, si.Signature) { - return false + return err } case *signing.MultiSignatureData: nestedMultisigPk, ok := pk.PubKeys[i].(PubKey) if !ok { - return false + return fmt.Errorf("unable to parse pubkey of index %d", i) } - if !nestedMultisigPk.VerifyMultisignature(getSignBytes, si) { - return false + if err := nestedMultisigPk.VerifyMultisignature(getSignBytes, si); err != nil { + return err } default: - return false + return fmt.Errorf("improper signature data type for index %d", sigIndex) } sigIndex++ } } - return true + return nil } // GetPubKeys implements the PubKey.GetPubKeys method diff --git a/crypto/types/multisig/threshold_pubkey_test.go b/crypto/types/multisig/threshold_pubkey_test.go index 103ba38a44ff..bf5195919731 100644 --- a/crypto/types/multisig/threshold_pubkey_test.go +++ b/crypto/types/multisig/threshold_pubkey_test.go @@ -47,7 +47,7 @@ func TestThresholdMultisigValidCases(t *testing.T) { t, AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), ) - require.False( + require.Error( t, multisigKey.VerifyMultisignature(signBytesFn, multisignature), "multisig passed when i < k, tc %d, i %d", tcIndex, i, @@ -58,12 +58,12 @@ func TestThresholdMultisigValidCases(t *testing.T) { ) require.Equal( t, - int(i+1), + i+1, len(multisignature.Signatures), "adding a signature for the same pubkey twice increased signature count by 2, tc %d", tcIndex, ) } - require.False( + require.Error( t, multisigKey.VerifyMultisignature(signBytesFn, multisignature), "multisig passed with k - 1 sigs, tc %d", tcIndex, @@ -77,13 +77,13 @@ func TestThresholdMultisigValidCases(t *testing.T) { tc.pubkeys, ), ) - require.True( + require.NoError( t, multisigKey.VerifyMultisignature(signBytesFn, multisignature), "multisig failed after k good signatures, tc %d", tcIndex, ) - for i := int(tc.k) + 1; i < len(tc.signingIndices); i++ { + for i := tc.k + 1; i < len(tc.signingIndices); i++ { signingIndex := tc.signingIndices[i] require.NoError( @@ -92,7 +92,7 @@ func TestThresholdMultisigValidCases(t *testing.T) { ) require.Equal( t, - tc.passAfterKSignatures[i-int(tc.k)-1], + tc.passAfterKSignatures[i-(tc.k)-1], multisigKey.VerifyMultisignature(func(mode signing.SignMode) ([]byte, error) { return tc.msg, nil }, multisignature), @@ -120,11 +120,11 @@ func TestThresholdMultisigDuplicateSignatures(t *testing.T) { multisignature := NewMultisig(5) signBytesFn := func(mode signing.SignMode) ([]byte, error) { return msg, nil } - require.False(t, multisigKey.VerifyMultisignature(signBytesFn, multisignature)) + require.Error(t, multisigKey.VerifyMultisignature(signBytesFn, multisignature)) AddSignatureFromPubKey(multisignature, sigs[0], pubkeys[0], pubkeys) // Add second signature manually multisignature.Signatures = append(multisignature.Signatures, sigs[0]) - require.False(t, multisigKey.VerifyMultisignature(signBytesFn, multisignature)) + require.Error(t, multisigKey.VerifyMultisignature(signBytesFn, multisignature)) } // TODO: Fully replace this test with table driven tests @@ -168,6 +168,26 @@ func TestPubKeyMultisigThresholdAminoToIface(t *testing.T) { require.Equal(t, multisigKey, pubKey) } +func TestAddSignatureFromPubKeyNilCheck(t *testing.T) { + pkSet, sigs := generatePubKeysAndSignatures(5, []byte{1, 2, 3, 4}) + multisignature := NewMultisig(5) + + //verify no error is returned with all non-nil values + err := AddSignatureFromPubKey(multisignature, sigs[0], pkSet[0], pkSet) + require.NoError(t, err) + //verify error is returned when key value is nil + err = AddSignatureFromPubKey(multisignature, sigs[0], pkSet[0], nil) + require.Error(t, err) + //verify error is returned when pubkey value is nil + err = AddSignatureFromPubKey(multisignature, sigs[0], nil, pkSet) + require.Error(t, err) + //verify error is returned when signature value is nil + err = AddSignatureFromPubKey(multisignature, nil, pkSet[0], pkSet) + require.Error(t, err) + //verify error is returned when multisignature value is nil + err = AddSignatureFromPubKey(nil, sigs[0], pkSet[0], pkSet) + require.Error(t, err) +} func generatePubKeysAndSignatures(n int, msg []byte) (pubkeys []crypto.PubKey, signatures []signing.SignatureData) { pubkeys = make([]crypto.PubKey, n) signatures = make([]signing.SignatureData, n) diff --git a/x/auth/signing/amino/amino_test.go b/x/auth/signing/amino/amino_test.go index a88ae268d9c7..3e073ae881af 100644 --- a/x/auth/signing/amino/amino_test.go +++ b/x/auth/signing/amino/amino_test.go @@ -3,13 +3,12 @@ package amino_test import ( "testing" - signingtypes "github.com/cosmos/cosmos-sdk/types/tx/signing" - "github.com/stretchr/testify/require" "github.com/tendermint/tendermint/crypto/secp256k1" sdk "github.com/cosmos/cosmos-sdk/types" + signingtypes "github.com/cosmos/cosmos-sdk/types/tx/signing" "github.com/cosmos/cosmos-sdk/x/auth" "github.com/cosmos/cosmos-sdk/x/auth/signing" "github.com/cosmos/cosmos-sdk/x/auth/signing/amino" diff --git a/x/auth/signing/handler_map_test.go b/x/auth/signing/handler_map_test.go index d69c7979133f..9c8d516eebed 100644 --- a/x/auth/signing/handler_map_test.go +++ b/x/auth/signing/handler_map_test.go @@ -3,13 +3,12 @@ package signing_test import ( "testing" - signingtypes "github.com/cosmos/cosmos-sdk/types/tx/signing" - "github.com/stretchr/testify/require" "github.com/tendermint/tendermint/crypto/secp256k1" sdk "github.com/cosmos/cosmos-sdk/types" + signingtypes "github.com/cosmos/cosmos-sdk/types/tx/signing" "github.com/cosmos/cosmos-sdk/x/auth/signing" "github.com/cosmos/cosmos-sdk/x/auth/signing/amino" authtypes "github.com/cosmos/cosmos-sdk/x/auth/types" diff --git a/x/auth/types/stdtx.go b/x/auth/types/stdtx.go index cb786a625e51..3d0dbaeaaa0b 100644 --- a/x/auth/types/stdtx.go +++ b/x/auth/types/stdtx.go @@ -374,41 +374,40 @@ func StdSignatureToSignatureV2(cdc *codec.Codec, sig StdSignature) (signing.Sign } func pubKeySigToSigData(cdc *codec.Codec, key crypto.PubKey, sig []byte) (signing.SignatureData, error) { - if multiPK, ok := key.(multisig.PubKey); ok { - var multiSig multisig.AminoMultisignature - err := cdc.UnmarshalBinaryBare(sig, &multiSig) - if err != nil { - return nil, err - } + multiPK, ok := key.(multisig.PubKey) + if !ok { + return &signing.SingleSignatureData{ + SignMode: signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, + Signature: sig, + }, nil + } + var multiSig multisig.AminoMultisignature + err := cdc.UnmarshalBinaryBare(sig, &multiSig) + if err != nil { + return nil, err + } - sigs := multiSig.Sigs - sigDatas := make([]signing.SignatureData, len(sigs)) - pubKeys := multiPK.GetPubKeys() - bitArray := multiSig.BitArray - n := multiSig.BitArray.Size() - sigIdx := 0 - - for i := 0; i < n; i++ { - if bitArray.GetIndex(i) { - data, err := pubKeySigToSigData(cdc, pubKeys[i], multiSig.Sigs[sigIdx]) - if err != nil { - return nil, err - } - - sigDatas[sigIdx] = data - sigIdx++ + sigs := multiSig.Sigs + sigDatas := make([]signing.SignatureData, len(sigs)) + pubKeys := multiPK.GetPubKeys() + bitArray := multiSig.BitArray + n := multiSig.BitArray.Size() + sigIdx := 0 + for i := 0; i < n; i++ { + if bitArray.GetIndex(i) { + data, err := pubKeySigToSigData(cdc, pubKeys[i], multiSig.Sigs[sigIdx]) + if err != nil { + return nil, sdkerrors.Wrapf(err, "Unable to convert Signature to SigData %d", sigIdx) } - } - return &signing.MultiSignatureData{ - BitArray: bitArray, - Signatures: sigDatas, - }, nil + sigDatas[sigIdx] = data + sigIdx++ + } } - return &signing.SingleSignatureData{ - SignMode: signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, - Signature: sig, + return &signing.MultiSignatureData{ + BitArray: bitArray, + Signatures: sigDatas, }, nil } @@ -422,7 +421,7 @@ func MultiSignatureDataToAminoMultisignature(cdc *codec.Codec, mSig *signing.Mul var err error sigs[i], err = SignatureDataToAminoSignature(cdc, mSig.Signatures[i]) if err != nil { - return multisig.AminoMultisignature{}, err + return multisig.AminoMultisignature{}, sdkerrors.Wrapf(err, "Unable to convert Signature Data to signature %d", i) } } @@ -450,6 +449,6 @@ func SignatureDataToAminoSignature(cdc *codec.Codec, data signing.SignatureData) return cdc.MarshalBinaryBare(aminoMSig) default: - return nil, fmt.Errorf("unexpected case") + return nil, fmt.Errorf("unexpected signature data %T", data) } } From 8f0a957461ffc75438bde441655ef7a0dfe17359 Mon Sep 17 00:00:00 2001 From: sahith-narahari Date: Thu, 11 Jun 2020 03:29:03 +0530 Subject: [PATCH 18/23] Fix imports --- crypto/types/multisig/threshold_pubkey.go | 1 + 1 file changed, 1 insertion(+) diff --git a/crypto/types/multisig/threshold_pubkey.go b/crypto/types/multisig/threshold_pubkey.go index b229a5ba6f04..0e7be74bb821 100644 --- a/crypto/types/multisig/threshold_pubkey.go +++ b/crypto/types/multisig/threshold_pubkey.go @@ -2,6 +2,7 @@ package multisig import ( "fmt" + "github.com/tendermint/tendermint/crypto" "github.com/cosmos/cosmos-sdk/types/tx/signing" From 6c6103619edf69a46810571f07d5a78aa59e1ca6 Mon Sep 17 00:00:00 2001 From: Federico Kunze <31522760+fedekunze@users.noreply.github.com> Date: Thu, 11 Jun 2020 09:13:18 +0200 Subject: [PATCH 19/23] Update crypto/types/multisig/multisignature.go --- crypto/types/multisig/multisignature.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crypto/types/multisig/multisignature.go b/crypto/types/multisig/multisignature.go index e5a68fa285d4..7f5465ede5af 100644 --- a/crypto/types/multisig/multisignature.go +++ b/crypto/types/multisig/multisignature.go @@ -62,7 +62,7 @@ func AddSignatureFromPubKey(mSig *signing.MultiSignatureData, sig signing.Signat return fmt.Errorf("value of mSig is nil %v", mSig) } if sig == nil { - return fmt.Errorf("value of sig is nil %v", mSig) + return fmt.Errorf("value of sig is nil %v", sig) } if pubkey == nil || keys == nil { From 383cd766fb4ed8de344e08e81d5f72034deb2356 Mon Sep 17 00:00:00 2001 From: sahith-narahari Date: Thu, 11 Jun 2020 22:19:29 +0530 Subject: [PATCH 20/23] Add test for MultiSignatureData --- crypto/types/multisig/threshold_pubkey.go | 2 +- .../types/multisig/threshold_pubkey_test.go | 37 +++++++++++++++++++ types/tx/signing/signature_data.go | 2 +- 3 files changed, 39 insertions(+), 2 deletions(-) diff --git a/crypto/types/multisig/threshold_pubkey.go b/crypto/types/multisig/threshold_pubkey.go index 0e7be74bb821..ab2abddc9a83 100644 --- a/crypto/types/multisig/threshold_pubkey.go +++ b/crypto/types/multisig/threshold_pubkey.go @@ -89,7 +89,7 @@ func (pk PubKeyMultisigThreshold) VerifyMultisignature(getSignBytes GetSignBytes } // ensure at least k signatures are set if bitarray.NumTrueBitsBefore(size) < int(pk.K) { - return fmt.Errorf("") + return fmt.Errorf("minimum number of signatures not set %d", int(pk.K)) } // index in the list of signatures which we are concerned with. sigIndex := 0 diff --git a/crypto/types/multisig/threshold_pubkey_test.go b/crypto/types/multisig/threshold_pubkey_test.go index bf5195919731..5c4dc023e5b0 100644 --- a/crypto/types/multisig/threshold_pubkey_test.go +++ b/crypto/types/multisig/threshold_pubkey_test.go @@ -1,6 +1,7 @@ package multisig import ( + "github.com/cosmos/cosmos-sdk/crypto/types" "math/rand" "testing" @@ -168,6 +169,17 @@ func TestPubKeyMultisigThresholdAminoToIface(t *testing.T) { require.Equal(t, multisigKey, pubKey) } +func TestMultiSignature(t *testing.T) { + msg := []byte{1, 2, 3, 4} + pkSet, sigs := generatePubKeysAndMultiSignatures(2, msg) + multisignature := NewMultisig(1) + signBytesFn := func(mode signing.SignMode) ([]byte, error) { return msg, nil } + t.Logf("this is multisignature %v", multisignature) + multisigKey := NewPubKeyMultisigThreshold(1, pkSet) + err := multisigKey.VerifyMultisignature(signBytesFn, &sigs[0]) + require.NoError(t, err) +} + func TestAddSignatureFromPubKeyNilCheck(t *testing.T) { pkSet, sigs := generatePubKeysAndSignatures(5, []byte{1, 2, 3, 4}) multisignature := NewMultisig(5) @@ -188,6 +200,7 @@ func TestAddSignatureFromPubKeyNilCheck(t *testing.T) { err = AddSignatureFromPubKey(nil, sigs[0], pkSet[0], pkSet) require.Error(t, err) } + func generatePubKeysAndSignatures(n int, msg []byte) (pubkeys []crypto.PubKey, signatures []signing.SignatureData) { pubkeys = make([]crypto.PubKey, n) signatures = make([]signing.SignatureData, n) @@ -207,3 +220,27 @@ func generatePubKeysAndSignatures(n int, msg []byte) (pubkeys []crypto.PubKey, s } return } + +func generatePubKeysAndMultiSignatures(n int, msg []byte) (pubkeys []crypto.PubKey, signatures []signing.MultiSignatureData) { + pubkeys = make([]crypto.PubKey, n) + signatures = make([]signing.MultiSignatureData, n) + for i := 0; i < n; i++ { + var privkey crypto.PrivKey + switch rand.Int63() % 3 { + case 0: + privkey = ed25519.GenPrivKey() + case 1: + privkey = secp256k1.GenPrivKey() + case 2: + privkey = sr25519.GenPrivKey() + } + pubkeys[i] = privkey.PubKey() + sig, _ := privkey.Sign(msg) + var multisignature signing.SignatureData + cdc.UnmarshalBinaryBare(sig, &multisignature) + signatures[i].BitArray = types.NewCompactBitArray(n) + signatures[i].BitArray.SetIndex(i, true) + signatures[i].Signatures = append(signatures[i].Signatures, multisignature) + } + return +} diff --git a/types/tx/signing/signature_data.go b/types/tx/signing/signature_data.go index 06e6b6edb22e..174902ac106e 100644 --- a/types/tx/signing/signature_data.go +++ b/types/tx/signing/signature_data.go @@ -20,7 +20,7 @@ type SingleSignatureData struct { Signature []byte } -// SingleSignatureData represents the nested SignatureData of a multisig signature +// MultiSignatureData represents the nested SignatureData of a multisig signature type MultiSignatureData struct { // BitArray is a compact way of indicating which signers from the multisig key // have signed From 6ad9c634eb17cf8611ec2cecec38607ca771d7a7 Mon Sep 17 00:00:00 2001 From: Aaron Craelius Date: Thu, 11 Jun 2020 14:26:23 -0400 Subject: [PATCH 21/23] Add nested multisig case --- crypto/types/multisig/threshold_pubkey.go | 2 +- .../types/multisig/threshold_pubkey_test.go | 48 +++++++++---------- 2 files changed, 24 insertions(+), 26 deletions(-) diff --git a/crypto/types/multisig/threshold_pubkey.go b/crypto/types/multisig/threshold_pubkey.go index ab2abddc9a83..1eee32d2e0a2 100644 --- a/crypto/types/multisig/threshold_pubkey.go +++ b/crypto/types/multisig/threshold_pubkey.go @@ -89,7 +89,7 @@ func (pk PubKeyMultisigThreshold) VerifyMultisignature(getSignBytes GetSignBytes } // ensure at least k signatures are set if bitarray.NumTrueBitsBefore(size) < int(pk.K) { - return fmt.Errorf("minimum number of signatures not set %d", int(pk.K)) + return fmt.Errorf("minimum number of signatures not set, have %d, expected %d", bitarray.NumTrueBitsBefore(size), int(pk.K)) } // index in the list of signatures which we are concerned with. sigIndex := 0 diff --git a/crypto/types/multisig/threshold_pubkey_test.go b/crypto/types/multisig/threshold_pubkey_test.go index 5c4dc023e5b0..cad62c460205 100644 --- a/crypto/types/multisig/threshold_pubkey_test.go +++ b/crypto/types/multisig/threshold_pubkey_test.go @@ -1,10 +1,11 @@ package multisig import ( - "github.com/cosmos/cosmos-sdk/crypto/types" "math/rand" "testing" + "github.com/cosmos/cosmos-sdk/crypto/types" + "github.com/cosmos/cosmos-sdk/types/tx/signing" "github.com/stretchr/testify/require" @@ -171,12 +172,9 @@ func TestPubKeyMultisigThresholdAminoToIface(t *testing.T) { func TestMultiSignature(t *testing.T) { msg := []byte{1, 2, 3, 4} - pkSet, sigs := generatePubKeysAndMultiSignatures(2, msg) - multisignature := NewMultisig(1) + pk, sig := generateNestedMultiSignature(3, msg) signBytesFn := func(mode signing.SignMode) ([]byte, error) { return msg, nil } - t.Logf("this is multisignature %v", multisignature) - multisigKey := NewPubKeyMultisigThreshold(1, pkSet) - err := multisigKey.VerifyMultisignature(signBytesFn, &sigs[0]) + err := pk.VerifyMultisignature(signBytesFn, sig) require.NoError(t, err) } @@ -221,26 +219,26 @@ func generatePubKeysAndSignatures(n int, msg []byte) (pubkeys []crypto.PubKey, s return } -func generatePubKeysAndMultiSignatures(n int, msg []byte) (pubkeys []crypto.PubKey, signatures []signing.MultiSignatureData) { - pubkeys = make([]crypto.PubKey, n) - signatures = make([]signing.MultiSignatureData, n) +func generateNestedMultiSignature(n int, msg []byte) (PubKey, *signing.MultiSignatureData) { + pubkeys := make([]crypto.PubKey, n) + signatures := make([]signing.SignatureData, n) + bitArray := types.NewCompactBitArray(n) for i := 0; i < n; i++ { - var privkey crypto.PrivKey - switch rand.Int63() % 3 { - case 0: - privkey = ed25519.GenPrivKey() - case 1: - privkey = secp256k1.GenPrivKey() - case 2: - privkey = sr25519.GenPrivKey() + nestedPks, nestedSigs := generatePubKeysAndSignatures(5, msg) + nestedBitArray := types.NewCompactBitArray(5) + for j := 0; j < 5; j++ { + nestedBitArray.SetIndex(j, true) } - pubkeys[i] = privkey.PubKey() - sig, _ := privkey.Sign(msg) - var multisignature signing.SignatureData - cdc.UnmarshalBinaryBare(sig, &multisignature) - signatures[i].BitArray = types.NewCompactBitArray(n) - signatures[i].BitArray.SetIndex(i, true) - signatures[i].Signatures = append(signatures[i].Signatures, multisignature) + nestedSig := &signing.MultiSignatureData{ + BitArray: nestedBitArray, + Signatures: nestedSigs, + } + signatures[i] = nestedSig + pubkeys[i] = NewPubKeyMultisigThreshold(5, nestedPks) + bitArray.SetIndex(i, true) + } + return NewPubKeyMultisigThreshold(n, pubkeys), &signing.MultiSignatureData{ + BitArray: bitArray, + Signatures: signatures, } - return } From a75cce621ce14896bb8857643205f3acdf750bb7 Mon Sep 17 00:00:00 2001 From: sahith-narahari Date: Fri, 12 Jun 2020 04:56:12 +0530 Subject: [PATCH 22/23] Add test for AddSignatureV2 --- crypto/types/multisig/codec.go | 16 ++-- crypto/types/multisig/threshold_pubkey.go | 4 +- .../types/multisig/threshold_pubkey_test.go | 87 ++++++++++++------- 3 files changed, 66 insertions(+), 41 deletions(-) diff --git a/crypto/types/multisig/codec.go b/crypto/types/multisig/codec.go index 9fedd111b1c5..052b4f855666 100644 --- a/crypto/types/multisig/codec.go +++ b/crypto/types/multisig/codec.go @@ -1,7 +1,7 @@ package multisig import ( - amino "github.com/tendermint/go-amino" + "github.com/tendermint/go-amino" "github.com/tendermint/tendermint/crypto" "github.com/tendermint/tendermint/crypto/ed25519" @@ -10,21 +10,21 @@ import ( ) // TODO: Figure out API for others to either add their own pubkey types, or -// to make verify / marshal accept a cdc. +// to make verify / marshal accept a Cdc. const ( PubKeyAminoRoute = "tendermint/PubKeyMultisigThreshold" ) -var cdc = amino.NewCodec() +var Cdc = amino.NewCodec() func init() { - cdc.RegisterInterface((*crypto.PubKey)(nil), nil) - cdc.RegisterConcrete(PubKeyMultisigThreshold{}, + Cdc.RegisterInterface((*crypto.PubKey)(nil), nil) + Cdc.RegisterConcrete(PubKeyMultisigThreshold{}, PubKeyAminoRoute, nil) - cdc.RegisterConcrete(ed25519.PubKeyEd25519{}, + Cdc.RegisterConcrete(ed25519.PubKeyEd25519{}, ed25519.PubKeyAminoName, nil) - cdc.RegisterConcrete(sr25519.PubKeySr25519{}, + Cdc.RegisterConcrete(sr25519.PubKeySr25519{}, sr25519.PubKeyAminoName, nil) - cdc.RegisterConcrete(secp256k1.PubKeySecp256k1{}, + Cdc.RegisterConcrete(secp256k1.PubKeySecp256k1{}, secp256k1.PubKeyAminoName, nil) } diff --git a/crypto/types/multisig/threshold_pubkey.go b/crypto/types/multisig/threshold_pubkey.go index 1eee32d2e0a2..f27f2001cc9e 100644 --- a/crypto/types/multisig/threshold_pubkey.go +++ b/crypto/types/multisig/threshold_pubkey.go @@ -44,7 +44,7 @@ func NewPubKeyMultisigThreshold(k int, pubkeys []crypto.PubKey) PubKey { // with amino multisignatures. func (pk PubKeyMultisigThreshold) VerifyBytes(msg []byte, marshalledSig []byte) bool { var sig AminoMultisignature - err := cdc.UnmarshalBinaryBare(marshalledSig, &sig) + err := Cdc.UnmarshalBinaryBare(marshalledSig, &sig) if err != nil { return false } @@ -129,7 +129,7 @@ func (pk PubKeyMultisigThreshold) GetPubKeys() []crypto.PubKey { // Bytes returns the amino encoded version of the PubKeyMultisigThreshold func (pk PubKeyMultisigThreshold) Bytes() []byte { - return cdc.MustMarshalBinaryBare(pk) + return Cdc.MustMarshalBinaryBare(pk) } // Address returns tmhash(PubKeyMultisigThreshold.Bytes()) diff --git a/crypto/types/multisig/threshold_pubkey_test.go b/crypto/types/multisig/threshold_pubkey_test.go index cad62c460205..4eaf52ffa11f 100644 --- a/crypto/types/multisig/threshold_pubkey_test.go +++ b/crypto/types/multisig/threshold_pubkey_test.go @@ -1,14 +1,16 @@ -package multisig +package multisig_test import ( "math/rand" "testing" - "github.com/cosmos/cosmos-sdk/crypto/types" + "github.com/stretchr/testify/require" + "github.com/cosmos/cosmos-sdk/codec" + "github.com/cosmos/cosmos-sdk/crypto/types" + "github.com/cosmos/cosmos-sdk/crypto/types/multisig" "github.com/cosmos/cosmos-sdk/types/tx/signing" - - "github.com/stretchr/testify/require" + authtypes "github.com/cosmos/cosmos-sdk/x/auth/types" "github.com/tendermint/tendermint/crypto" "github.com/tendermint/tendermint/crypto/ed25519" @@ -39,15 +41,15 @@ func TestThresholdMultisigValidCases(t *testing.T) { }, } for tcIndex, tc := range cases { - multisigKey := NewPubKeyMultisigThreshold(tc.k, tc.pubkeys) - multisignature := NewMultisig(len(tc.pubkeys)) + multisigKey := multisig.NewPubKeyMultisigThreshold(tc.k, tc.pubkeys) + multisignature := multisig.NewMultisig(len(tc.pubkeys)) signBytesFn := func(mode signing.SignMode) ([]byte, error) { return tc.msg, nil } for i := 0; i < tc.k-1; i++ { signingIndex := tc.signingIndices[i] require.NoError( t, - AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), + multisig.AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), ) require.Error( t, @@ -56,7 +58,7 @@ func TestThresholdMultisigValidCases(t *testing.T) { ) require.NoError( t, - AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), + multisig.AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), ) require.Equal( t, @@ -72,7 +74,7 @@ func TestThresholdMultisigValidCases(t *testing.T) { ) require.NoError( t, - AddSignatureFromPubKey( + multisig.AddSignatureFromPubKey( multisignature, tc.signatures[tc.signingIndices[tc.k]], tc.pubkeys[tc.signingIndices[tc.k]], @@ -90,7 +92,7 @@ func TestThresholdMultisigValidCases(t *testing.T) { require.NoError( t, - AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), + multisig.AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), ) require.Equal( t, @@ -102,7 +104,7 @@ func TestThresholdMultisigValidCases(t *testing.T) { ) require.NoError( t, - AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), + multisig.AddSignatureFromPubKey(multisignature, tc.signatures[signingIndex], tc.pubkeys[signingIndex], tc.pubkeys), ) require.Equal( t, @@ -118,12 +120,12 @@ func TestThresholdMultisigValidCases(t *testing.T) { func TestThresholdMultisigDuplicateSignatures(t *testing.T) { msg := []byte{1, 2, 3, 4, 5} pubkeys, sigs := generatePubKeysAndSignatures(5, msg) - multisigKey := NewPubKeyMultisigThreshold(2, pubkeys) - multisignature := NewMultisig(5) + multisigKey := multisig.NewPubKeyMultisigThreshold(2, pubkeys) + multisignature := multisig.NewMultisig(5) signBytesFn := func(mode signing.SignMode) ([]byte, error) { return msg, nil } require.Error(t, multisigKey.VerifyMultisignature(signBytesFn, multisignature)) - AddSignatureFromPubKey(multisignature, sigs[0], pubkeys[0], pubkeys) + multisig.AddSignatureFromPubKey(multisignature, sigs[0], pubkeys[0], pubkeys) // Add second signature manually multisignature.Signatures = append(multisignature.Signatures, sigs[0]) require.Error(t, multisigKey.VerifyMultisignature(signBytesFn, multisignature)) @@ -133,9 +135,9 @@ func TestThresholdMultisigDuplicateSignatures(t *testing.T) { func TestMultiSigPubKeyEquality(t *testing.T) { msg := []byte{1, 2, 3, 4} pubkeys, _ := generatePubKeysAndSignatures(5, msg) - multisigKey := NewPubKeyMultisigThreshold(2, pubkeys) - var unmarshalledMultisig PubKeyMultisigThreshold - cdc.MustUnmarshalBinaryBare(multisigKey.Bytes(), &unmarshalledMultisig) + multisigKey := multisig.NewPubKeyMultisigThreshold(2, pubkeys) + var unmarshalledMultisig multisig.PubKeyMultisigThreshold + multisig.Cdc.MustUnmarshalBinaryBare(multisigKey.Bytes(), &unmarshalledMultisig) require.True(t, multisigKey.Equals(unmarshalledMultisig)) // Ensure that reordering pubkeys is treated as a different pubkey @@ -143,28 +145,28 @@ func TestMultiSigPubKeyEquality(t *testing.T) { copy(pubkeysCpy, pubkeys) pubkeysCpy[4] = pubkeys[3] pubkeysCpy[3] = pubkeys[4] - multisigKey2 := NewPubKeyMultisigThreshold(2, pubkeysCpy) + multisigKey2 := multisig.NewPubKeyMultisigThreshold(2, pubkeysCpy) require.False(t, multisigKey.Equals(multisigKey2)) } func TestAddress(t *testing.T) { msg := []byte{1, 2, 3, 4} pubkeys, _ := generatePubKeysAndSignatures(5, msg) - multisigKey := NewPubKeyMultisigThreshold(2, pubkeys) + multisigKey := multisig.NewPubKeyMultisigThreshold(2, pubkeys) require.Len(t, multisigKey.Address().Bytes(), 20) } func TestPubKeyMultisigThresholdAminoToIface(t *testing.T) { msg := []byte{1, 2, 3, 4} pubkeys, _ := generatePubKeysAndSignatures(5, msg) - multisigKey := NewPubKeyMultisigThreshold(2, pubkeys) + multisigKey := multisig.NewPubKeyMultisigThreshold(2, pubkeys) - ab, err := cdc.MarshalBinaryLengthPrefixed(multisigKey) + ab, err := multisig.Cdc.MarshalBinaryLengthPrefixed(multisigKey) require.NoError(t, err) // like other crypto.Pubkey implementations (e.g. ed25519.PubKeyMultisigThreshold), // PubKeyMultisigThreshold should be deserializable into a crypto.PubKeyMultisigThreshold: var pubKey crypto.PubKey - err = cdc.UnmarshalBinaryLengthPrefixed(ab, &pubKey) + err = multisig.Cdc.UnmarshalBinaryLengthPrefixed(ab, &pubKey) require.NoError(t, err) require.Equal(t, multisigKey, pubKey) @@ -178,24 +180,47 @@ func TestMultiSignature(t *testing.T) { require.NoError(t, err) } +func TestMultiSigMigration(t *testing.T) { + msg := []byte{1, 2, 3, 4} + pkSet, sigs := generatePubKeysAndSignatures(2, msg) + multisignature := multisig.NewMultisig(2) + + multisigKey := multisig.NewPubKeyMultisigThreshold(2, pkSet) + signBytesFn := func(mode signing.SignMode) ([]byte, error) { return msg, nil } + + cdc := codec.New() + + err := multisig.AddSignatureFromPubKey(multisignature, sigs[0], pkSet[0], pkSet) + + // create a StdSignature for msg, and convert it to sigV2 + sig := authtypes.StdSignature{PubKey: pkSet[1].Bytes(), Signature: msg} + sigV2, err := authtypes.StdSignatureToSignatureV2(cdc, sig) + require.NoError(t, multisig.AddSignatureV2(multisignature, sigV2, pkSet)) + + require.NoError(t, err) + require.NotNil(t, sigV2) + + require.NoError(t, multisigKey.VerifyMultisignature(signBytesFn, multisignature)) +} + func TestAddSignatureFromPubKeyNilCheck(t *testing.T) { pkSet, sigs := generatePubKeysAndSignatures(5, []byte{1, 2, 3, 4}) - multisignature := NewMultisig(5) + multisignature := multisig.NewMultisig(5) //verify no error is returned with all non-nil values - err := AddSignatureFromPubKey(multisignature, sigs[0], pkSet[0], pkSet) + err := multisig.AddSignatureFromPubKey(multisignature, sigs[0], pkSet[0], pkSet) require.NoError(t, err) //verify error is returned when key value is nil - err = AddSignatureFromPubKey(multisignature, sigs[0], pkSet[0], nil) + err = multisig.AddSignatureFromPubKey(multisignature, sigs[0], pkSet[0], nil) require.Error(t, err) //verify error is returned when pubkey value is nil - err = AddSignatureFromPubKey(multisignature, sigs[0], nil, pkSet) + err = multisig.AddSignatureFromPubKey(multisignature, sigs[0], nil, pkSet) require.Error(t, err) //verify error is returned when signature value is nil - err = AddSignatureFromPubKey(multisignature, nil, pkSet[0], pkSet) + err = multisig.AddSignatureFromPubKey(multisignature, nil, pkSet[0], pkSet) require.Error(t, err) //verify error is returned when multisignature value is nil - err = AddSignatureFromPubKey(nil, sigs[0], pkSet[0], pkSet) + err = multisig.AddSignatureFromPubKey(nil, sigs[0], pkSet[0], pkSet) require.Error(t, err) } @@ -219,7 +244,7 @@ func generatePubKeysAndSignatures(n int, msg []byte) (pubkeys []crypto.PubKey, s return } -func generateNestedMultiSignature(n int, msg []byte) (PubKey, *signing.MultiSignatureData) { +func generateNestedMultiSignature(n int, msg []byte) (multisig.PubKey, *signing.MultiSignatureData) { pubkeys := make([]crypto.PubKey, n) signatures := make([]signing.SignatureData, n) bitArray := types.NewCompactBitArray(n) @@ -234,10 +259,10 @@ func generateNestedMultiSignature(n int, msg []byte) (PubKey, *signing.MultiSign Signatures: nestedSigs, } signatures[i] = nestedSig - pubkeys[i] = NewPubKeyMultisigThreshold(5, nestedPks) + pubkeys[i] = multisig.NewPubKeyMultisigThreshold(5, nestedPks) bitArray.SetIndex(i, true) } - return NewPubKeyMultisigThreshold(n, pubkeys), &signing.MultiSignatureData{ + return multisig.NewPubKeyMultisigThreshold(n, pubkeys), &signing.MultiSignatureData{ BitArray: bitArray, Signatures: signatures, } From cddcd82254169b9b89b481c542e612cd36832e50 Mon Sep 17 00:00:00 2001 From: sahith-narahari Date: Fri, 12 Jun 2020 23:14:45 +0530 Subject: [PATCH 23/23] Add changelog --- CHANGELOG.md | 1 + crypto/types/multisig/multisignature.go | 5 ++++- x/auth/types/stdtx.go | 7 +++---- 3 files changed, 8 insertions(+), 5 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 5ba6406d2ae5..b5cd33889756 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -135,6 +135,7 @@ be used to retrieve the actual proposal `Content`. Also the `NewMsgSubmitProposa * (client/lcd) [\#6290](https://github.com/cosmos/cosmos-sdk/pull/6290) `CliCtx` of struct `RestServer` in package client/lcd has been renamed to `ClientCtx`. * (types) [\#6327](https://github.com/cosmos/cosmos-sdk/pull/6327) `sdk.Msg` now inherits `proto.Message`, as a result all `sdk.Msg` types now use pointer semantics. * (codec) [\#6330](https://github.com/cosmos/cosmos-sdk/pull/6330) `codec.RegisterCrypto` has been moved to the `crypto/codec` package and the global `codec.Cdc` Amino instance has been deprecated and moved to the `codec/legacy_global` package. +* (crypto/types/multisig) [\#6373](https://github.com/cosmos/cosmos-sdk/pull/6373) `multisig.Multisignature` has been renamed to `AminoMultisignature` ### Features diff --git a/crypto/types/multisig/multisignature.go b/crypto/types/multisig/multisignature.go index 7f5465ede5af..b13072e28047 100644 --- a/crypto/types/multisig/multisignature.go +++ b/crypto/types/multisig/multisignature.go @@ -20,7 +20,10 @@ type AminoMultisignature struct { // NewMultisig returns a new MultiSignatureData func NewMultisig(n int) *signing.MultiSignatureData { - return &signing.MultiSignatureData{BitArray: types.NewCompactBitArray(n), Signatures: make([]signing.SignatureData, 0, n)} + return &signing.MultiSignatureData{ + BitArray: types.NewCompactBitArray(n), + Signatures: make([]signing.SignatureData, 0, n), + } } // GetIndex returns the index of pk in keys. Returns -1 if not found diff --git a/x/auth/types/stdtx.go b/x/auth/types/stdtx.go index 3d0dbaeaaa0b..c81c3cd91cbb 100644 --- a/x/auth/types/stdtx.go +++ b/x/auth/types/stdtx.go @@ -392,6 +392,7 @@ func pubKeySigToSigData(cdc *codec.Codec, key crypto.PubKey, sig []byte) (signin pubKeys := multiPK.GetPubKeys() bitArray := multiSig.BitArray n := multiSig.BitArray.Size() + signatures := multisig.NewMultisig(n) sigIdx := 0 for i := 0; i < n; i++ { if bitArray.GetIndex(i) { @@ -401,14 +402,12 @@ func pubKeySigToSigData(cdc *codec.Codec, key crypto.PubKey, sig []byte) (signin } sigDatas[sigIdx] = data + multisig.AddSignature(signatures, data, sigIdx) sigIdx++ } } - return &signing.MultiSignatureData{ - BitArray: bitArray, - Signatures: sigDatas, - }, nil + return signatures, nil } // MultiSignatureDataToAminoMultisignature converts a MultiSignatureData to an AminoMultisignature.