Skip to content

Commit

Permalink
Fix dyncomm ante handler (#448)
Browse files Browse the repository at this point in the history
Co-authored-by: Till Ziegler <[email protected]>
  • Loading branch information
StrathCole and fragwuerdig authored Apr 23, 2024
1 parent 2312f78 commit dc4cfb9
Show file tree
Hide file tree
Showing 4 changed files with 159 additions and 4 deletions.
1 change: 1 addition & 0 deletions app/app.go
Original file line number Diff line number Diff line change
Expand Up @@ -216,6 +216,7 @@ func NewTerraApp(
TXCounterStoreKey: app.GetKey(wasm.StoreKey),
DyncommKeeper: app.DyncommKeeper,
StakingKeeper: app.StakingKeeper,
Cdc: app.appCodec,
},
)
if err != nil {
Expand Down
4 changes: 3 additions & 1 deletion custom/auth/ante/ante.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package ante
import (
dyncommante "github.com/classic-terra/core/v2/x/dyncomm/ante"
dyncommkeeper "github.com/classic-terra/core/v2/x/dyncomm/keeper"
"github.com/cosmos/cosmos-sdk/codec"
stakingkeeper "github.com/cosmos/cosmos-sdk/x/staking/keeper"
ibcante "github.com/cosmos/ibc-go/v6/modules/core/ante"
ibckeeper "github.com/cosmos/ibc-go/v6/modules/core/keeper"
Expand Down Expand Up @@ -36,6 +37,7 @@ type HandlerOptions struct {
TXCounterStoreKey storetypes.StoreKey
DyncommKeeper dyncommkeeper.Keeper
StakingKeeper stakingkeeper.Keeper
Cdc codec.BinaryCodec
}

// NewAnteHandler returns an AnteHandler that checks and increments sequence
Expand Down Expand Up @@ -84,7 +86,7 @@ func NewAnteHandler(options HandlerOptions) (sdk.AnteHandler, error) {
NewMinInitialDepositDecorator(options.GovKeeper, options.TreasuryKeeper),
ante.NewConsumeGasForTxSizeDecorator(options.AccountKeeper),
NewFeeDecorator(options.AccountKeeper, options.BankKeeper, options.FeegrantKeeper, options.TreasuryKeeper),
dyncommante.NewDyncommDecorator(options.DyncommKeeper, options.StakingKeeper),
dyncommante.NewDyncommDecorator(options.Cdc, options.DyncommKeeper, options.StakingKeeper),

// Do not add any other decorators below this point unless explicitly explain.
ante.NewSetPubKeyDecorator(options.AccountKeeper), // SetPubKeyDecorator must be called before all signature verification decorators
Expand Down
28 changes: 26 additions & 2 deletions x/dyncomm/ante/ante.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,23 +4,29 @@ import (
"fmt"

dyncommkeeper "github.com/classic-terra/core/v2/x/dyncomm/keeper"
"github.com/cosmos/cosmos-sdk/codec"
sdk "github.com/cosmos/cosmos-sdk/types"
sdkerrors "github.com/cosmos/cosmos-sdk/types/errors"
authz "github.com/cosmos/cosmos-sdk/x/authz"
stakingkeeper "github.com/cosmos/cosmos-sdk/x/staking/keeper"
stakingtypes "github.com/cosmos/cosmos-sdk/x/staking/types"
icatypes "github.com/cosmos/ibc-go/v6/modules/apps/27-interchain-accounts/types"
channeltypes "github.com/cosmos/ibc-go/v6/modules/core/04-channel/types"
)

// DyncommDecorator checks for EditValidator and rejects
// edits that do not conform with dyncomm
type DyncommDecorator struct {
dyncommKeeper dyncommkeeper.Keeper
stakingKeeper stakingkeeper.Keeper
cdc codec.BinaryCodec
}

func NewDyncommDecorator(dk dyncommkeeper.Keeper, sk stakingkeeper.Keeper) DyncommDecorator {
func NewDyncommDecorator(cdc codec.BinaryCodec, dk dyncommkeeper.Keeper, sk stakingkeeper.Keeper) DyncommDecorator {
return DyncommDecorator{
dyncommKeeper: dk,
stakingKeeper: sk,
cdc: cdc,
}
}

Expand All @@ -41,9 +47,27 @@ func (dd DyncommDecorator) AnteHandle(ctx sdk.Context, tx sdk.Tx, simulate bool,
func (dd DyncommDecorator) FilterMsgsAndProcessMsgs(ctx sdk.Context, msgs ...sdk.Msg) (err error) {
for _, msg := range msgs {

switch msg.(type) {
switch msg := msg.(type) {
case *stakingtypes.MsgEditValidator:
err = dd.ProcessEditValidator(ctx, msg)
case *authz.MsgExec:
messages, msgerr := msg.GetMessages()
if msgerr == nil {
err = dd.FilterMsgsAndProcessMsgs(ctx, messages...)
}
case *channeltypes.MsgRecvPacket:
var data icatypes.InterchainAccountPacketData
err = icatypes.ModuleCdc.UnmarshalJSON(msg.Packet.GetData(), &data)
if err != nil {
continue
}
if data.Type != icatypes.EXECUTE_TX {
continue
}
messages, msgerr := icatypes.DeserializeCosmosTx(dd.cdc, data.Data)
if msgerr == nil {
err = dd.FilterMsgsAndProcessMsgs(ctx, messages...)
}
default:
continue
}
Expand Down
130 changes: 129 additions & 1 deletion x/dyncomm/ante/ante_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import (
"cosmossdk.io/math"
"github.com/classic-terra/core/v2/app"
core "github.com/classic-terra/core/v2/types"
"github.com/gogo/protobuf/proto"
"github.com/stretchr/testify/suite"

"github.com/cosmos/cosmos-sdk/client"
Expand All @@ -21,7 +22,11 @@ import (
apptesting "github.com/classic-terra/core/v2/app/testing"
dyncommante "github.com/classic-terra/core/v2/x/dyncomm/ante"
authtypes "github.com/cosmos/cosmos-sdk/x/auth/types"
authz "github.com/cosmos/cosmos-sdk/x/authz"
stakingtypes "github.com/cosmos/cosmos-sdk/x/staking/types"
icatypes "github.com/cosmos/ibc-go/v6/modules/apps/27-interchain-accounts/types"
clienttypes "github.com/cosmos/ibc-go/v6/modules/core/02-client/types"
channeltypes "github.com/cosmos/ibc-go/v6/modules/core/04-channel/types"

abci "github.com/tendermint/tendermint/abci/types"
)
Expand Down Expand Up @@ -173,7 +178,7 @@ func (suite *AnteTestSuite) TestAnte_EnsureDynCommissionIsMinComm() {
suite.CreateValidator(50_000_000_000)
suite.App.DyncommKeeper.UpdateAllBondedValidatorRates(suite.Ctx)

mfd := dyncommante.NewDyncommDecorator(suite.App.DyncommKeeper, suite.App.StakingKeeper)
mfd := dyncommante.NewDyncommDecorator(suite.App.AppCodec(), suite.App.DyncommKeeper, suite.App.StakingKeeper)
antehandler := sdk.ChainAnteDecorators(mfd)

dyncomm := suite.App.DyncommKeeper.CalculateDynCommission(suite.Ctx, val1)
Expand Down Expand Up @@ -205,6 +210,129 @@ func (suite *AnteTestSuite) TestAnte_EnsureDynCommissionIsMinComm() {
suite.Require().NoError(err)
}

func (suite *AnteTestSuite) TestAnte_EnsureDynCommissionIsMinCommAuthz() {
suite.SetupTest() // setup
suite.txBuilder = suite.clientCtx.TxConfig.NewTxBuilder()
suite.txBuilder.SetGasLimit(400_000)
suite.Ctx = suite.Ctx.WithIsCheckTx(false)

_, _, val1, _ := suite.CreateValidator(50_000_000_000)
priv2, _, acc2 := testdata.KeyTestPubAddr()
suite.CreateValidator(50_000_000_000)
suite.App.DyncommKeeper.UpdateAllBondedValidatorRates(suite.Ctx)

mfd := dyncommante.NewDyncommDecorator(suite.App.AppCodec(), suite.App.DyncommKeeper, suite.App.StakingKeeper)
antehandler := sdk.ChainAnteDecorators(mfd)

dyncomm := suite.App.DyncommKeeper.CalculateDynCommission(suite.Ctx, val1)
invalidtarget := dyncomm.Mul(sdk.NewDecWithPrec(9, 1))
validtarget := dyncomm.Mul(sdk.NewDecWithPrec(11, 1))

// invalid tx fails
editmsg := stakingtypes.NewMsgEditValidator(
val1.GetOperator(),
val1.Description, &invalidtarget, &val1.MinSelfDelegation,
)

execmsg := authz.NewMsgExec(acc2, []sdk.Msg{editmsg})

err := suite.txBuilder.SetMsgs(&execmsg)
suite.Require().NoError(err)
tx, err := suite.CreateTestTx([]cryptotypes.PrivKey{priv2}, []uint64{0}, []uint64{0}, suite.Ctx.ChainID())
suite.Require().NoError(err)
_, err = antehandler(suite.Ctx, tx, false)
suite.Require().Error(err)

// valid tx passes
editmsg = stakingtypes.NewMsgEditValidator(
val1.GetOperator(),
val1.Description, &validtarget, &val1.MinSelfDelegation,
)
execmsg = authz.NewMsgExec(acc2, []sdk.Msg{editmsg})

err = suite.txBuilder.SetMsgs(editmsg)
suite.Require().NoError(err)
tx, err = suite.CreateTestTx([]cryptotypes.PrivKey{priv2}, []uint64{0}, []uint64{0}, suite.Ctx.ChainID())
suite.Require().NoError(err)
_, err = antehandler(suite.Ctx, tx, false)
suite.Require().NoError(err)
}

func (suite *AnteTestSuite) TestAnte_EnsureDynCommissionIsMinCommICA() {
suite.SetupTest() // setup
suite.txBuilder = suite.clientCtx.TxConfig.NewTxBuilder()
suite.txBuilder.SetGasLimit(400_000)
suite.Ctx = suite.Ctx.WithIsCheckTx(false)

_, _, val1, _ := suite.CreateValidator(50_000_000_000)
priv2, _, _ := testdata.KeyTestPubAddr()
suite.CreateValidator(50_000_000_000)
suite.App.DyncommKeeper.UpdateAllBondedValidatorRates(suite.Ctx)

mfd := dyncommante.NewDyncommDecorator(suite.App.AppCodec(), suite.App.DyncommKeeper, suite.App.StakingKeeper)
antehandler := sdk.ChainAnteDecorators(mfd)

dyncomm := suite.App.DyncommKeeper.CalculateDynCommission(suite.Ctx, val1)
invalidtarget := dyncomm.Mul(sdk.NewDecWithPrec(9, 1))
validtarget := dyncomm.Mul(sdk.NewDecWithPrec(11, 1))

// prepare invalid tx -> expect it fails
editmsg := stakingtypes.NewMsgEditValidator(
val1.GetOperator(),
val1.Description, &invalidtarget, &val1.MinSelfDelegation,
)
data, err := icatypes.SerializeCosmosTx(suite.App.AppCodec(), []proto.Message{editmsg})
suite.Require().NoError(err)
icaPacketData := icatypes.InterchainAccountPacketData{
Type: icatypes.EXECUTE_TX,
Data: data,
}
packetData := icaPacketData.GetBytes()
packet := channeltypes.NewPacket(
packetData, 1, "source-port", "source-channel",
"dest-port", "dest-channel",
clienttypes.NewHeight(1, 1), 0,
)
recvmsg := channeltypes.NewMsgRecvPacket(
packet, []byte{}, clienttypes.NewHeight(1, 1), "signer",
)

err = suite.txBuilder.SetMsgs(recvmsg)
suite.Require().NoError(err)
tx, err := suite.CreateTestTx([]cryptotypes.PrivKey{priv2}, []uint64{0}, []uint64{0}, suite.Ctx.ChainID())
suite.Require().NoError(err)
_, err = antehandler(suite.Ctx, tx, false)
suite.Require().Error(err)

// prepare valid tx -> expect it passes
editmsg = stakingtypes.NewMsgEditValidator(
val1.GetOperator(),
val1.Description, &validtarget, &val1.MinSelfDelegation,
)
data, err = icatypes.SerializeCosmosTx(suite.App.AppCodec(), []proto.Message{editmsg})
suite.Require().NoError(err)
icaPacketData = icatypes.InterchainAccountPacketData{
Type: icatypes.EXECUTE_TX,
Data: data,
}
packetData = icaPacketData.GetBytes()
packet = channeltypes.NewPacket(
packetData, 1, "source-port", "source-channel",
"dest-port", "dest-channel",
clienttypes.NewHeight(1, 1), 0,
)
recvmsg = channeltypes.NewMsgRecvPacket(
packet, []byte{}, clienttypes.NewHeight(1, 1), "signer",
)

err = suite.txBuilder.SetMsgs(recvmsg)
suite.Require().NoError(err)
tx, err = suite.CreateTestTx([]cryptotypes.PrivKey{priv2}, []uint64{0}, []uint64{0}, suite.Ctx.ChainID())
suite.Require().NoError(err)
_, err = antehandler(suite.Ctx, tx, false)
suite.Require().NoError(err)
}

// go test -v -run ^TestAnteTestSuite/TestAnte_EditValidatorAccountSequence$ github.com/classic-terra/core/v2/x/dyncomm/ante
// check that account keeper sequence no longer increases when editing validator unsuccessfully
func (suite *AnteTestSuite) TestAnte_EditValidatorAccountSequence() {
Expand Down

0 comments on commit dc4cfb9

Please sign in to comment.