-
Notifications
You must be signed in to change notification settings - Fork 3.6k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Fix multisig LegacyAminoPubKey Amino marshaling (#8841)
* Use v034auth RegisterCrypto * Add custom amino for LegacyAminoPubKey * Fix registercrypto * Revert old PR * revert some genutil stuff * Add comment * Add changelog * Remove binary marshalling * Fix lint * Fix lint again * Fix lint, 3rd time's a charm * ignore wrong linter warning * Fix UnmarshalAmioJSON Co-authored-by: mergify[bot] <37929162+mergify[bot]@users.noreply.github.com> Co-authored-by: Alessio Treglia <[email protected]> Co-authored-by: Anil Kumar Kammari <[email protected]> (cherry picked from commit d4d27e1) # Conflicts: # CHANGELOG.md # x/auth/legacy/v040/migrate.go
- Loading branch information
1 parent
e23c0ce
commit 0253544
Showing
7 changed files
with
226 additions
and
3 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,88 @@ | ||
package multisig | ||
|
||
import ( | ||
types "github.com/cosmos/cosmos-sdk/codec/types" | ||
cryptotypes "github.com/cosmos/cosmos-sdk/crypto/types" | ||
sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" | ||
) | ||
|
||
// tmMultisig implements a K of N threshold multisig. It is used for | ||
// Amino JSON marshaling of LegacyAminoPubKey (see below for details). | ||
// | ||
// This struct is copy-pasted from: | ||
// https://github.com/tendermint/tendermint/blob/v0.33.9/crypto/multisig/threshold_pubkey.go | ||
// | ||
// This struct was used in the SDK <=0.39. In 0.40 and the switch to protobuf, | ||
// it has been converted to LegacyAminoPubKey. However, there's one difference: | ||
// the threshold field was an `uint` before, and an `uint32` after. This caused | ||
// amino marshaling to be breaking: amino marshals `uint32` as a JSON number, | ||
// and `uint` as a JSON string. | ||
// | ||
// In this file, we're overriding LegacyAminoPubKey's default JSON Amino | ||
// marshaling by using this struct. Please note that we are NOT overriding the | ||
// Amino binary marshaling, as that _might_ introduce breaking changes in the | ||
// keyring, where multisigs are amino-binary-encoded. | ||
// | ||
// ref: https://github.com/cosmos/cosmos-sdk/issues/8776 | ||
type tmMultisig struct { | ||
K uint `json:"threshold"` | ||
PubKeys []cryptotypes.PubKey `json:"pubkeys"` | ||
} | ||
|
||
// protoToTm converts a LegacyAminoPubKey into a tmMultisig. | ||
func protoToTm(protoPk *LegacyAminoPubKey) (tmMultisig, error) { | ||
var ok bool | ||
pks := make([]cryptotypes.PubKey, len(protoPk.PubKeys)) | ||
for i, pk := range protoPk.PubKeys { | ||
pks[i], ok = pk.GetCachedValue().(cryptotypes.PubKey) | ||
if !ok { | ||
return tmMultisig{}, sdkerrors.Wrapf(sdkerrors.ErrInvalidType, "expected %T, got %T", (cryptotypes.PubKey)(nil), pk.GetCachedValue()) | ||
} | ||
} | ||
|
||
return tmMultisig{ | ||
K: uint(protoPk.Threshold), | ||
PubKeys: pks, | ||
}, nil | ||
} | ||
|
||
// tmToProto converts a tmMultisig into a LegacyAminoPubKey. | ||
func tmToProto(tmPk tmMultisig) (*LegacyAminoPubKey, error) { | ||
var err error | ||
pks := make([]*types.Any, len(tmPk.PubKeys)) | ||
for i, pk := range tmPk.PubKeys { | ||
pks[i], err = types.NewAnyWithValue(pk) | ||
if err != nil { | ||
return nil, err | ||
} | ||
} | ||
|
||
return &LegacyAminoPubKey{ | ||
Threshold: uint32(tmPk.K), | ||
PubKeys: pks, | ||
}, nil | ||
} | ||
|
||
// MarshalAminoJSON overrides amino JSON unmarshaling. | ||
func (m LegacyAminoPubKey) MarshalAminoJSON() (tmMultisig, error) { //nolint:golint | ||
return protoToTm(&m) | ||
} | ||
|
||
// UnmarshalAminoJSON overrides amino JSON unmarshaling. | ||
func (m *LegacyAminoPubKey) UnmarshalAminoJSON(tmPk tmMultisig) error { | ||
protoPk, err := tmToProto(tmPk) | ||
if err != nil { | ||
return err | ||
} | ||
|
||
// Instead of just doing `*m = *protoPk`, we prefer to modify in-place the | ||
// existing Anys inside `m` (instead of allocating new Anys), as so not to | ||
// break the `.compat` fields in the existing Anys. | ||
for i := range m.PubKeys { | ||
m.PubKeys[i].TypeUrl = protoPk.PubKeys[i].TypeUrl | ||
m.PubKeys[i].Value = protoPk.PubKeys[i].Value | ||
} | ||
m.Threshold = protoPk.Threshold | ||
|
||
return nil | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters