github.com/cosmos/cosmos-sdk@v0.50.10/x/auth/migrations/legacytx/stdsign.go (about) 1 package legacytx 2 3 import ( 4 "encoding/json" 5 "fmt" 6 7 "sigs.k8s.io/yaml" 8 9 "cosmossdk.io/errors" 10 11 "github.com/cosmos/cosmos-sdk/codec" 12 "github.com/cosmos/cosmos-sdk/codec/legacy" 13 codectypes "github.com/cosmos/cosmos-sdk/codec/types" 14 cryptotypes "github.com/cosmos/cosmos-sdk/crypto/types" 15 "github.com/cosmos/cosmos-sdk/crypto/types/multisig" 16 sdk "github.com/cosmos/cosmos-sdk/types" 17 "github.com/cosmos/cosmos-sdk/types/tx/signing" 18 ) 19 20 // LegacyMsg defines the old interface a message must fulfill, 21 // containing Amino signing method. 22 // Deprecated: Please use `Msg` instead. 23 type LegacyMsg interface { 24 sdk.Msg 25 26 // Get the canonical byte representation of the Msg. 27 GetSignBytes() []byte 28 } 29 30 // StdSignDoc is replay-prevention structure. 31 // It includes the result of msg.GetSignBytes(), 32 // as well as the ChainID (prevent cross chain replay) 33 // and the Sequence numbers for each signature (prevent 34 // inchain replay and enforce tx ordering per account). 35 type StdSignDoc struct { 36 AccountNumber uint64 `json:"account_number" yaml:"account_number"` 37 Sequence uint64 `json:"sequence" yaml:"sequence"` 38 TimeoutHeight uint64 `json:"timeout_height,omitempty" yaml:"timeout_height"` 39 ChainID string `json:"chain_id" yaml:"chain_id"` 40 Memo string `json:"memo" yaml:"memo"` 41 Fee json.RawMessage `json:"fee" yaml:"fee"` 42 Msgs []json.RawMessage `json:"msgs" yaml:"msgs"` 43 } 44 45 var RegressionTestingAminoCodec *codec.LegacyAmino 46 47 // Deprecated: please delete this code eventually. 48 func mustSortJSON(bz []byte) []byte { 49 var c any 50 err := json.Unmarshal(bz, &c) 51 if err != nil { 52 panic(err) 53 } 54 js, err := json.Marshal(c) 55 if err != nil { 56 panic(err) 57 } 58 return js 59 } 60 61 // StdSignBytes returns the bytes to sign for a transaction. 62 // Deprecated: Please use x/tx/signing/aminojson instead. 63 func StdSignBytes(chainID string, accnum, sequence, timeout uint64, fee StdFee, msgs []sdk.Msg, memo string) []byte { 64 if RegressionTestingAminoCodec == nil { 65 panic(fmt.Errorf("must set RegressionTestingAminoCodec before calling StdSignBytes")) 66 } 67 msgsBytes := make([]json.RawMessage, 0, len(msgs)) 68 for _, msg := range msgs { 69 bz := RegressionTestingAminoCodec.MustMarshalJSON(msg) 70 msgsBytes = append(msgsBytes, mustSortJSON(bz)) 71 } 72 73 bz, err := legacy.Cdc.MarshalJSON(StdSignDoc{ 74 AccountNumber: accnum, 75 ChainID: chainID, 76 Fee: json.RawMessage(fee.Bytes()), 77 Memo: memo, 78 Msgs: msgsBytes, 79 Sequence: sequence, 80 TimeoutHeight: timeout, 81 }) 82 if err != nil { 83 panic(err) 84 } 85 86 return mustSortJSON(bz) 87 } 88 89 // Deprecated: StdSignature represents a sig 90 type StdSignature struct { 91 cryptotypes.PubKey `json:"pub_key" yaml:"pub_key"` // optional 92 Signature []byte `json:"signature" yaml:"signature"` 93 } 94 95 // Deprecated 96 func NewStdSignature(pk cryptotypes.PubKey, sig []byte) StdSignature { 97 return StdSignature{PubKey: pk, Signature: sig} 98 } 99 100 // GetSignature returns the raw signature bytes. 101 func (ss StdSignature) GetSignature() []byte { 102 return ss.Signature 103 } 104 105 // GetPubKey returns the public key of a signature as a cryptotypes.PubKey using the 106 // Amino codec. 107 func (ss StdSignature) GetPubKey() cryptotypes.PubKey { 108 return ss.PubKey 109 } 110 111 // MarshalYAML returns the YAML representation of the signature. 112 func (ss StdSignature) MarshalYAML() (interface{}, error) { 113 pk := "" 114 if ss.PubKey != nil { 115 pk = ss.PubKey.String() 116 } 117 118 bz, err := yaml.Marshal(struct { 119 PubKey string `json:"pub_key"` 120 Signature string `json:"signature"` 121 }{ 122 pk, 123 fmt.Sprintf("%X", ss.Signature), 124 }) 125 if err != nil { 126 return nil, err 127 } 128 129 return string(bz), err 130 } 131 132 func (ss StdSignature) UnpackInterfaces(unpacker codectypes.AnyUnpacker) error { 133 return codectypes.UnpackInterfaces(ss.PubKey, unpacker) 134 } 135 136 // StdSignatureToSignatureV2 converts a StdSignature to a SignatureV2 137 func StdSignatureToSignatureV2(cdc *codec.LegacyAmino, sig StdSignature) (signing.SignatureV2, error) { 138 pk := sig.GetPubKey() 139 data, err := pubKeySigToSigData(cdc, pk, sig.Signature) 140 if err != nil { 141 return signing.SignatureV2{}, err 142 } 143 144 return signing.SignatureV2{ 145 PubKey: pk, 146 Data: data, 147 }, nil 148 } 149 150 func pubKeySigToSigData(cdc *codec.LegacyAmino, key cryptotypes.PubKey, sig []byte) (signing.SignatureData, error) { 151 multiPK, ok := key.(multisig.PubKey) 152 if !ok { 153 return &signing.SingleSignatureData{ 154 SignMode: signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON, 155 Signature: sig, 156 }, nil 157 } 158 var multiSig multisig.AminoMultisignature 159 err := cdc.Unmarshal(sig, &multiSig) 160 if err != nil { 161 return nil, err 162 } 163 164 sigs := multiSig.Sigs 165 sigDatas := make([]signing.SignatureData, len(sigs)) 166 pubKeys := multiPK.GetPubKeys() 167 bitArray := multiSig.BitArray 168 n := multiSig.BitArray.Count() 169 signatures := multisig.NewMultisig(n) 170 sigIdx := 0 171 for i := 0; i < n; i++ { 172 if bitArray.GetIndex(i) { 173 data, err := pubKeySigToSigData(cdc, pubKeys[i], multiSig.Sigs[sigIdx]) 174 if err != nil { 175 return nil, errors.Wrapf(err, "Unable to convert Signature to SigData %d", sigIdx) 176 } 177 178 sigDatas[sigIdx] = data 179 multisig.AddSignature(signatures, data, sigIdx) 180 sigIdx++ 181 } 182 } 183 184 return signatures, nil 185 }