Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

R4R: Validator unbonding state #2163

Merged
merged 18 commits into from
Sep 1, 2018
Merged
Show file tree
Hide file tree
Changes from 12 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions PENDING.md
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,8 @@ BREAKING CHANGES
* [x/stake] \#1901 Validator type's Owner field renamed to Operator; Validator's GetOwner() renamed accordingly to comply with the SDK's Validator interface.
* [docs] [#2001](https://github.com/cosmos/cosmos-sdk/pull/2001) Update slashing spec for slashing period
* [x/stake, x/slashing] [#1305](https://github.com/cosmos/cosmos-sdk/issues/1305) - Rename "revoked" to "jailed"
* [x/stake] [#1676] Revoked and jailed validators put into the unbonding state
* [x/stake] [#1877] Redelegations/unbonding-delegation from unbonding validator have reduced time

* SDK
* [core] \#1807 Switch from use of rational to decimal
Expand Down
6 changes: 3 additions & 3 deletions x/slashing/keeper_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -114,7 +114,7 @@ func TestHandleAbsentValidator(t *testing.T) {

// validator should have been jailed
validator, _ = sk.GetValidatorByPubKey(ctx, val)
require.Equal(t, sdk.Unbonded, validator.GetStatus())
require.Equal(t, sdk.Unbonding, validator.GetStatus())

// unrevocation should fail prior to jail expiration
got = slh(ctx, NewMsgUnjail(addr))
Expand Down Expand Up @@ -161,7 +161,7 @@ func TestHandleAbsentValidator(t *testing.T) {
keeper.handleValidatorSignature(ctx, val.Address(), amtInt, false)
}
validator, _ = sk.GetValidatorByPubKey(ctx, val)
require.Equal(t, sdk.Unbonded, validator.GetStatus())
require.Equal(t, sdk.Unbonding, validator.GetStatus())
}

// Test a new validator entering the validator set
Expand Down Expand Up @@ -230,7 +230,7 @@ func TestHandleAlreadyJailed(t *testing.T) {

// validator should have been jailed and slashed
validator, _ := sk.GetValidatorByPubKey(ctx, val)
require.Equal(t, sdk.Unbonded, validator.GetStatus())
require.Equal(t, sdk.Unbonding, validator.GetStatus())

// validator should have been slashed
require.Equal(t, int64(amtInt-1), validator.GetTokens().RoundInt64())
Expand Down
2 changes: 1 addition & 1 deletion x/slashing/tick_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -80,5 +80,5 @@ func TestBeginBlocker(t *testing.T) {
// validator should be jailed
validator, found := sk.GetValidatorByPubKey(ctx, pk)
require.True(t, found)
require.Equal(t, sdk.Unbonded, validator.GetStatus())
require.Equal(t, sdk.Unbonding, validator.GetStatus())
}
4 changes: 2 additions & 2 deletions x/stake/handler_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -85,8 +85,8 @@ func TestValidatorByPowerIndex(t *testing.T) {
keeper.Jail(ctx, keep.PKs[0])
validator, found = keeper.GetValidator(ctx, validatorAddr)
require.True(t, found)
require.Equal(t, sdk.Unbonded, validator.Status) // ensure is unbonded
require.Equal(t, int64(500000), validator.Tokens.RoundInt64()) // ensure is unbonded
require.Equal(t, sdk.Unbonding, validator.Status) // ensure is unbonding
require.Equal(t, int64(500000), validator.Tokens.RoundInt64()) // ensure tokens slashed

// the old power record should have been deleted as the power changed
require.False(t, keep.ValidatorByPowerIndexExists(ctx, keeper, power))
Expand Down
46 changes: 44 additions & 2 deletions x/stake/keeper/delegation.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package keeper

import (
"bytes"
"time"

sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/cosmos/cosmos-sdk/x/stake/types"
Expand Down Expand Up @@ -311,6 +312,32 @@ func (k Keeper) unbond(ctx sdk.Context, delegatorAddr, validatorAddr sdk.AccAddr

//______________________________________________________________________________________________________

// get info for begin functions: MinTime and CreationHeight
func (k Keeper) getBeginInfo(ctx sdk.Context, params types.Params, validatorSrcAddr sdk.AccAddress) (
minTime time.Time, height int64, completeNow bool) {

validator, found := k.GetValidator(ctx, validatorSrcAddr)
switch {
case !found || validator.Status == sdk.Bonded:

// the longest wait - just unbonding period from now
minTime = ctx.BlockHeader().Time.Add(params.UnbondingTime)
height = ctx.BlockHeader().Height
return minTime, height, false

case validator.IsUnbonded(ctx):
return minTime, height, true

case validator.Status == sdk.Unbonding:
minTime = validator.UnbondingMinTime
height = validator.UnbondingHeight
return minTime, height, false

default:
panic("unknown validator status")
}
}

// complete unbonding an unbonding record
func (k Keeper) BeginUnbonding(ctx sdk.Context, delegatorAddr, validatorAddr sdk.AccAddress, sharesAmount sdk.Dec) sdk.Error {

Expand All @@ -327,12 +354,22 @@ func (k Keeper) BeginUnbonding(ctx sdk.Context, delegatorAddr, validatorAddr sdk

// create the unbonding delegation
params := k.GetParams(ctx)
minTime := ctx.BlockHeader().Time.Add(params.UnbondingTime)
minTime, height, completeNow := k.getBeginInfo(ctx, params, validatorAddr)
balance := sdk.Coin{params.BondDenom, returnAmount.RoundInt()}

// no need to create the ubd object just complete now
if completeNow {
_, _, err := k.coinKeeper.AddCoins(ctx, delegatorAddr, sdk.Coins{balance})
if err != nil {
return err
}
return nil
}

ubd := types.UnbondingDelegation{
DelegatorAddr: delegatorAddr,
ValidatorAddr: validatorAddr,
CreationHeight: height,
MinTime: minTime,
Balance: balance,
InitialBalance: balance,
Expand Down Expand Up @@ -389,12 +426,17 @@ func (k Keeper) BeginRedelegation(ctx sdk.Context, delegatorAddr, validatorSrcAd
}

// create the unbonding delegation
minTime := ctx.BlockHeader().Time.Add(params.UnbondingTime)
minTime, height, completeNow := k.getBeginInfo(ctx, params, validatorSrcAddr)

if completeNow { // no need to create the redelegation object
return nil
}

red := types.Redelegation{
DelegatorAddr: delegatorAddr,
ValidatorSrcAddr: validatorSrcAddr,
ValidatorDstAddr: validatorDstAddr,
CreationHeight: height,
MinTime: minTime,
SharesDst: sharesCreated,
SharesSrc: sharesAmount,
Expand Down
Loading