Skip to content

Commit

Permalink
Merge PR #4400: Release v0.34.5 - RC1
Browse files Browse the repository at this point in the history
* Cherry Pick PR #4345: Upgrade ledger-cosmos-go

* Cherry Pick PR #4336: Fix AppendTags usage error

* Update modules

* Cherry Pick PR #4265: CacheKVStore keep sorted items

* Cherry Pick #4227: Adding support for Ledger Cosmos App v1.5

* Cherry Pick #4395: Improve sig verification error message

* Cherry Pick PR #4140: Fix Failed Simulation Seeds
  • Loading branch information
alexanderbez authored May 23, 2019
1 parent 62fa99e commit c7c8bbd
Show file tree
Hide file tree
Showing 22 changed files with 439 additions and 123 deletions.
23 changes: 22 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,13 +1,34 @@
# Changelog

## 0.34.5

### Bug Fixes

#### SDK

* [\#4273](https://github.com/cosmos/cosmos-sdk/issues/4273) Fix usage of `AppendTags` in x/staking/handler.go

### Improvements

### SDK

* [\#2286](https://github.com/cosmos/cosmos-sdk/issues/2286) Improve performance of `CacheKVStore` iterator.
* [\#3655](https://github.com/cosmos/cosmos-sdk/issues/3655) Improve signature verification failure error message.

#### Gaia CLI

* [\#4227](https://github.com/cosmos/cosmos-sdk/issues/4227) Support for Ledger App v1.5.
* [#4345](https://github.com/cosmos/cosmos-sdk/pull/4345) Update `ledger-cosmos-go`
to v0.10.3.

## 0.34.4

### Bug Fixes

#### SDK

* [#4234](https://github.com/cosmos/cosmos-sdk/pull/4234) Allow `tx send --generate-only` to
actually work offline.
actually work offline.

#### Gaia

Expand Down
5 changes: 3 additions & 2 deletions client/keys/add.go
Original file line number Diff line number Diff line change
Expand Up @@ -171,9 +171,10 @@ func runAddCmd(_ *cobra.Command, args []string) error {
account := uint32(viper.GetInt(flagAccount))
index := uint32(viper.GetInt(flagIndex))

// If we're using ledger, only thing we need is the path. So generate key and we're done.
// If we're using ledger, only thing we need is the path and the bech32 prefix.
if viper.GetBool(client.FlagUseLedger) {
info, err := kb.CreateLedger(name, keys.Secp256k1, account, index)
bech32PrefixAccAddr := sdk.GetConfig().GetBech32AccountAddrPrefix()
info, err := kb.CreateLedger(name, keys.Secp256k1, bech32PrefixAccAddr, account, index)
if err != nil {
return err
}
Expand Down
4 changes: 2 additions & 2 deletions client/keys/show.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ const (
FlagPublicKey = "pubkey"
// FlagBechPrefix defines a desired Bech32 prefix encoding for a key.
FlagBechPrefix = "bech"
// FlagBechPrefix defines a desired Bech32 prefix encoding for a key.
// FlagDevice indicates that the information should be shown in the device
FlagDevice = "device"

flagMultiSigThreshold = "multisig-threshold"
Expand All @@ -47,7 +47,7 @@ consisting of all the keys provided by name and multisig threshold.`,
cmd.Flags().String(FlagBechPrefix, sdk.PrefixAccount, "The Bech32 prefix encoding for a key (acc|val|cons)")
cmd.Flags().BoolP(FlagAddress, "a", false, "Output the address only (overrides --output)")
cmd.Flags().BoolP(FlagPublicKey, "p", false, "Output the public key only (overrides --output)")
cmd.Flags().BoolP(FlagDevice, "d", false, "Output the address in the device")
cmd.Flags().BoolP(FlagDevice, "d", false, "Output the address in a ledger device")
cmd.Flags().Uint(flagMultiSigThreshold, 1, "K out of N required signatures")
cmd.Flags().BoolP(flagShowMultiSig, "m", false, "Output multisig pubkey constituents, threshold, and weights")
cmd.Flags().Bool(client.FlagIndentResponse, false, "Add indent to JSON response")
Expand Down
32 changes: 16 additions & 16 deletions cmd/gaia/app/sim_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -119,23 +119,27 @@ func appStateRandomizedFn(r *rand.Rand, accs []simulation.Account, genesisTimest
if int64(i) > numInitiallyBonded && r.Intn(100) < 50 {
var (
vacc auth.VestingAccount
endTime int
endTime int64
)

startTime := genesisTimestamp.Unix()

// Allow for some vesting accounts to vest very quickly while others very
// slowly.
if r.Intn(100) < 50 {
endTime = randIntBetween(r, int(startTime), int(startTime+(60*60*24*30)))
endTime = int64(simulation.RandIntBetween(r, int(startTime), int(startTime+(60*60*24*30))))
} else {
endTime = randIntBetween(r, int(startTime), int(startTime+(60*60*12)))
endTime = int64(simulation.RandIntBetween(r, int(startTime), int(startTime+(60*60*12))))
}

if startTime == endTime {
endTime += 1
}

if r.Intn(100) < 50 {
vacc = auth.NewContinuousVestingAccount(&bacc, startTime, int64(endTime))
vacc = auth.NewContinuousVestingAccount(&bacc, startTime, endTime)
} else {
vacc = auth.NewDelayedVestingAccount(&bacc, int64(endTime))
vacc = auth.NewDelayedVestingAccount(&bacc, endTime)
}

gacc = NewGenesisAccountI(vacc)
Expand All @@ -148,11 +152,11 @@ func appStateRandomizedFn(r *rand.Rand, accs []simulation.Account, genesisTimest

authGenesis := auth.GenesisState{
Params: auth.Params{
MaxMemoCharacters: uint64(randIntBetween(r, 100, 200)),
MaxMemoCharacters: uint64(simulation.RandIntBetween(r, 100, 200)),
TxSigLimit: uint64(r.Intn(7) + 1),
TxSizeCostPerByte: uint64(randIntBetween(r, 5, 15)),
SigVerifyCostED25519: uint64(randIntBetween(r, 500, 1000)),
SigVerifyCostSecp256k1: uint64(randIntBetween(r, 500, 1000)),
TxSizeCostPerByte: uint64(simulation.RandIntBetween(r, 5, 15)),
SigVerifyCostED25519: uint64(simulation.RandIntBetween(r, 500, 1000)),
SigVerifyCostSecp256k1: uint64(simulation.RandIntBetween(r, 500, 1000)),
},
}
fmt.Printf("Selected randomly generated auth parameters:\n\t%+v\n", authGenesis)
Expand Down Expand Up @@ -182,7 +186,7 @@ func appStateRandomizedFn(r *rand.Rand, accs []simulation.Account, genesisTimest
stakingGenesis := staking.GenesisState{
Pool: staking.InitialPool(),
Params: staking.Params{
UnbondingTime: time.Duration(randIntBetween(r, 60, 60*60*24*3*2)) * time.Second,
UnbondingTime: time.Duration(simulation.RandIntBetween(r, 60, 60*60*24*3*2)) * time.Second,
MaxValidators: uint16(r.Intn(250) + 1),
BondDenom: sdk.DefaultBondDenom,
},
Expand All @@ -192,9 +196,9 @@ func appStateRandomizedFn(r *rand.Rand, accs []simulation.Account, genesisTimest
slashingGenesis := slashing.GenesisState{
Params: slashing.Params{
MaxEvidenceAge: stakingGenesis.Params.UnbondingTime,
SignedBlocksWindow: int64(randIntBetween(r, 10, 1000)),
SignedBlocksWindow: int64(simulation.RandIntBetween(r, 10, 1000)),
MinSignedPerWindow: sdk.NewDecWithPrec(int64(r.Intn(10)), 1),
DowntimeJailDuration: time.Duration(randIntBetween(r, 60, 60*60*24)) * time.Second,
DowntimeJailDuration: time.Duration(simulation.RandIntBetween(r, 60, 60*60*24)) * time.Second,
SlashFractionDoubleSign: sdk.NewDec(1).Quo(sdk.NewDec(int64(r.Intn(50) + 1))),
SlashFractionDowntime: sdk.NewDec(1).Quo(sdk.NewDec(int64(r.Intn(200) + 1))),
},
Expand Down Expand Up @@ -269,10 +273,6 @@ func appStateFn(r *rand.Rand, accs []simulation.Account, genesisTimestamp time.T
return appStateRandomizedFn(r, accs, genesisTimestamp)
}

func randIntBetween(r *rand.Rand, min, max int) int {
return r.Intn(max-min) + min
}

func testAndRunTxs(app *GaiaApp) []simulation.WeightedOperation {
return []simulation.WeightedOperation{
{5, authsim.SimulateDeductFee(app.accountKeeper, app.feeCollectionKeeper)},
Expand Down
7 changes: 4 additions & 3 deletions crypto/keys/keybase.go
Original file line number Diff line number Diff line change
Expand Up @@ -137,18 +137,19 @@ func (kb dbKeybase) Derive(name, mnemonic, bip39Passphrase, encryptPasswd string

// CreateLedger creates a new locally-stored reference to a Ledger keypair
// It returns the created key info and an error if the Ledger could not be queried
func (kb dbKeybase) CreateLedger(name string, algo SigningAlgo, account uint32, index uint32) (Info, error) {
func (kb dbKeybase) CreateLedger(name string, algo SigningAlgo, hrp string, account, index uint32) (Info, error) {
if algo != Secp256k1 {
return nil, ErrUnsupportedSigningAlgo
}

hdPath := hd.NewFundraiserParams(account, index)
priv, err := crypto.NewPrivKeyLedgerSecp256k1(*hdPath)
priv, _, err := crypto.NewPrivKeyLedgerSecp256k1(*hdPath, hrp)
if err != nil {
return nil, err
}
pub := priv.PubKey()

// Note: Once Cosmos App v1.3.1 is compulsory, it could be possible to check that pubkey and addr match
return kb.writeLedgerKey(name, pub, *hdPath), nil
}

Expand Down Expand Up @@ -246,7 +247,7 @@ func (kb dbKeybase) Sign(name, passphrase string, msg []byte) (sig []byte, pub t

case ledgerInfo:
linfo := info.(ledgerInfo)
priv, err = crypto.NewPrivKeyLedgerSecp256k1(linfo.Path)
priv, err = crypto.NewPrivKeyLedgerSecp256k1Unsafe(linfo.Path)
if err != nil {
return
}
Expand Down
4 changes: 2 additions & 2 deletions crypto/keys/keybase_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ func TestCreateAccountInvalidMnemonic(t *testing.T) {

func TestCreateLedgerUnsupportedAlgo(t *testing.T) {
kb := NewInMemory()
_, err := kb.CreateLedger("some_account", Ed25519, 0, 1)
_, err := kb.CreateLedger("some_account", Ed25519, "cosmos", 0, 1)
assert.Error(t, err)
assert.Equal(t, "unsupported signing algo: only secp256k1 is supported", err.Error())
}
Expand All @@ -49,7 +49,7 @@ func TestCreateLedger(t *testing.T) {
// test_cover does not compile some dependencies so ledger is disabled
// test_unit may add a ledger mock
// both cases are acceptable
ledger, err := kb.CreateLedger("some_account", Secp256k1, 3, 1)
ledger, err := kb.CreateLedger("some_account", Secp256k1, "cosmos", 3, 1)

if err != nil {
assert.Error(t, err)
Expand Down
4 changes: 2 additions & 2 deletions crypto/keys/lazy_keybase.go
Original file line number Diff line number Diff line change
Expand Up @@ -106,14 +106,14 @@ func (lkb lazyKeybase) Derive(name, mnemonic, bip39Passwd, encryptPasswd string,
return newDbKeybase(db).Derive(name, mnemonic, bip39Passwd, encryptPasswd, params)
}

func (lkb lazyKeybase) CreateLedger(name string, algo SigningAlgo, account uint32, index uint32) (info Info, err error) {
func (lkb lazyKeybase) CreateLedger(name string, algo SigningAlgo, hrp string, account, index uint32) (info Info, err error) {
db, err := sdk.NewLevelDB(lkb.name, lkb.dir)
if err != nil {
return nil, err
}
defer db.Close()

return newDbKeybase(db).CreateLedger(name, algo, account, index)
return newDbKeybase(db).CreateLedger(name, algo, hrp, account, index)
}

func (lkb lazyKeybase) CreateOffline(name string, pubkey crypto.PubKey) (info Info, err error) {
Expand Down
2 changes: 1 addition & 1 deletion crypto/keys/types.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ type Keybase interface {
Derive(name, mnemonic, bip39Passwd, encryptPasswd string, params hd.BIP44Params) (Info, error)

// CreateLedger creates, stores, and returns a new Ledger key reference
CreateLedger(name string, algo SigningAlgo, account uint32, index uint32) (info Info, err error)
CreateLedger(name string, algo SigningAlgo, hrp string, account, index uint32) (info Info, err error)

// CreateOffline creates, stores, and returns a new offline key reference
CreateOffline(name string, pubkey crypto.PubKey) (info Info, err error)
Expand Down
33 changes: 30 additions & 3 deletions crypto/ledger_mock.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,17 @@ package crypto

import (
"fmt"

"github.com/btcsuite/btcd/btcec"
"github.com/pkg/errors"

"github.com/cosmos/cosmos-sdk/crypto/keys/hd"
"github.com/cosmos/cosmos-sdk/tests"
bip39 "github.com/cosmos/go-bip39"
"github.com/pkg/errors"
"github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/go-bip39"

secp256k1 "github.com/tendermint/btcd/btcec"
"github.com/tendermint/tendermint/crypto"
tmsecp256k1 "github.com/tendermint/tendermint/crypto/secp256k1"
)

// If ledger support (build tag) has been enabled, which implies a CGO dependency,
Expand All @@ -30,6 +33,8 @@ func (mock LedgerSECP256K1Mock) Close() error {
return nil
}

// GetPublicKeySECP256K1 mocks a ledger device
// as per the original API, it returns an uncompressed key
func (mock LedgerSECP256K1Mock) GetPublicKeySECP256K1(derivationPath []uint32) ([]byte, error) {
if derivationPath[0] != 44 {
return nil, errors.New("Invalid derivation path")
Expand All @@ -55,6 +60,28 @@ func (mock LedgerSECP256K1Mock) GetPublicKeySECP256K1(derivationPath []uint32) (
return pubkeyObject.SerializeUncompressed(), nil
}

// GetAddressPubKeySECP256K1 mocks a ledger device
// as per the original API, it returns a compressed key and a bech32 address
func (mock LedgerSECP256K1Mock) GetAddressPubKeySECP256K1(derivationPath []uint32, hrp string) ([]byte, string, error) {
pk, err := mock.GetPublicKeySECP256K1(derivationPath)
if err != nil {
return nil, "", err
}

// re-serialize in the 33-byte compressed format
cmp, err := btcec.ParsePubKey(pk[:], btcec.S256())
if err != nil {
return nil, "", fmt.Errorf("error parsing public key: %v", err)
}

var compressedPublicKey tmsecp256k1.PubKeySecp256k1
copy(compressedPublicKey[:], cmp.SerializeCompressed())

// Generate the bech32 addr using existing tmcrypto/etc.
addr := types.AccAddress(compressedPublicKey.Address()).String()
return pk, addr, err
}

func (mock LedgerSECP256K1Mock) SignSECP256K1(derivationPath []uint32, message []byte) ([]byte, error) {
path := hd.NewParams(derivationPath[0], derivationPath[1], derivationPath[2], derivationPath[3] != 0, derivationPath[4])
seed, err := bip39.NewSeedWithErrorChecking(tests.TestMnemonic, "")
Expand Down
Loading

0 comments on commit c7c8bbd

Please sign in to comment.