diff --git a/CHANGELOG.md b/CHANGELOG.md index b837f2dbd8..4ea4f82189 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -34,6 +34,7 @@ ### BUG FIXES +- [\#1193](https://github.com/cosmos/evm/pull/1193) Remove the nonexistent vesting static precompile from defaults and migrate existing EVM params to strip its legacy address. - [\#1047](https://github.com/cosmos/evm/pull/1047) Resolve EthTxIndex -1 sentinel before uint cast in ReceiptsFromCometBlock, preventing transactionIndex overflow to MaxUint64. - [\#965](https://github.com/cosmos/evm/pull/965) Fix gas double charging on EVM calls in IBCOnTimeoutPacketCallback. - [\#869](https://github.com/cosmos/evm/pull/869) Fix erc20 IBC callbacks to check for native token transfer before parsing recipient. diff --git a/local_node.sh b/local_node.sh index b0725efb4c..f4c1f88cfc 100755 --- a/local_node.sh +++ b/local_node.sh @@ -240,7 +240,7 @@ if [[ $overwrite == "y" || $overwrite == "Y" ]]; then jq '.app_state["bank"]["denom_metadata"]=[{"description":"The native staking token for evmd.","denom_units":[{"denom":"atest","exponent":0,"aliases":["attotest"]},{"denom":"test","exponent":18,"aliases":[]}],"base":"atest","display":"test","name":"Test Token","symbol":"TEST","uri":"","uri_hash":""}]' "$GENESIS" >"$TMP_GENESIS" && mv "$TMP_GENESIS" "$GENESIS" - jq '.app_state["evm"]["params"]["active_static_precompiles"]=["0x0000000000000000000000000000000000000100","0x0000000000000000000000000000000000000400","0x0000000000000000000000000000000000000800","0x0000000000000000000000000000000000000801","0x0000000000000000000000000000000000000802","0x0000000000000000000000000000000000000803","0x0000000000000000000000000000000000000804","0x0000000000000000000000000000000000000805", "0x0000000000000000000000000000000000000806", "0x0000000000000000000000000000000000000807"]' "$GENESIS" >"$TMP_GENESIS" && mv "$TMP_GENESIS" "$GENESIS" + jq '.app_state["evm"]["params"]["active_static_precompiles"]=["0x0000000000000000000000000000000000000100","0x0000000000000000000000000000000000000400","0x0000000000000000000000000000000000000800","0x0000000000000000000000000000000000000801","0x0000000000000000000000000000000000000802","0x0000000000000000000000000000000000000804","0x0000000000000000000000000000000000000805", "0x0000000000000000000000000000000000000806", "0x0000000000000000000000000000000000000807"]' "$GENESIS" >"$TMP_GENESIS" && mv "$TMP_GENESIS" "$GENESIS" jq '.app_state["evm"]["params"]["evm_denom"]="atest"' "$GENESIS" >"$TMP_GENESIS" && mv "$TMP_GENESIS" "$GENESIS" diff --git a/tests/jsonrpc/scripts/evmd/start-evmd.sh b/tests/jsonrpc/scripts/evmd/start-evmd.sh index 4d7f5286a0..96c48e667d 100755 --- a/tests/jsonrpc/scripts/evmd/start-evmd.sh +++ b/tests/jsonrpc/scripts/evmd/start-evmd.sh @@ -103,7 +103,7 @@ jq '.app_state["mint"]["params"]["mint_denom"]="atest"' "$DATA_DIR/config/genesi jq '.app_state["bank"]["denom_metadata"]=[{"description":"The native staking token for evmd.","denom_units":[{"denom":"atest","exponent":0,"aliases":["attotest"]},{"denom":"test","exponent":18,"aliases":[]}],"base":"atest","display":"test","name":"Test Token","symbol":"TEST","uri":"","uri_hash":""}]' "$DATA_DIR/config/genesis.json" > "$DATA_DIR/config/tmp_genesis.json" && mv "$DATA_DIR/config/tmp_genesis.json" "$DATA_DIR/config/genesis.json" # Enable precompiles in EVM params -jq '.app_state["evm"]["params"]["active_static_precompiles"]=["0x0000000000000000000000000000000000000100","0x0000000000000000000000000000000000000400","0x0000000000000000000000000000000000000800","0x0000000000000000000000000000000000000801","0x0000000000000000000000000000000000000802","0x0000000000000000000000000000000000000803","0x0000000000000000000000000000000000000804","0x0000000000000000000000000000000000000805", "0x0000000000000000000000000000000000000806", "0x0000000000000000000000000000000000000807"]' "$DATA_DIR/config/genesis.json" > "$DATA_DIR/config/tmp_genesis.json" && mv "$DATA_DIR/config/tmp_genesis.json" "$DATA_DIR/config/genesis.json" +jq '.app_state["evm"]["params"]["active_static_precompiles"]=["0x0000000000000000000000000000000000000100","0x0000000000000000000000000000000000000400","0x0000000000000000000000000000000000000800","0x0000000000000000000000000000000000000801","0x0000000000000000000000000000000000000802","0x0000000000000000000000000000000000000804","0x0000000000000000000000000000000000000805", "0x0000000000000000000000000000000000000806", "0x0000000000000000000000000000000000000807"]' "$DATA_DIR/config/genesis.json" > "$DATA_DIR/config/tmp_genesis.json" && mv "$DATA_DIR/config/tmp_genesis.json" "$DATA_DIR/config/genesis.json" # Set EVM config jq '.app_state["evm"]["params"]["evm_denom"]="atest"' "$DATA_DIR/config/genesis.json" > "$DATA_DIR/config/tmp_genesis.json" && mv "$DATA_DIR/config/tmp_genesis.json" "$DATA_DIR/config/genesis.json" diff --git a/x/vm/migrations/v2/store.go b/x/vm/migrations/v2/store.go new file mode 100644 index 0000000000..593cbdc3af --- /dev/null +++ b/x/vm/migrations/v2/store.go @@ -0,0 +1,25 @@ +package v2 + +import ( + "slices" + + "github.com/cosmos/evm/x/vm/keeper" + + sdk "github.com/cosmos/cosmos-sdk/types" +) + +const vestingPrecompileAddress = "0x0000000000000000000000000000000000000803" + +// MigrateStore removes the legacy vesting precompile from active EVM params. +func MigrateStore(ctx sdk.Context, k *keeper.Keeper) error { + params := k.GetParams(ctx) + activePrecompiles := slices.DeleteFunc(params.ActiveStaticPrecompiles, func(address string) bool { + return address == vestingPrecompileAddress + }) + if len(activePrecompiles) == len(params.ActiveStaticPrecompiles) { + return nil + } + + params.ActiveStaticPrecompiles = activePrecompiles + return k.SetParams(ctx, params) +} diff --git a/x/vm/migrations/v2/store_test.go b/x/vm/migrations/v2/store_test.go new file mode 100644 index 0000000000..980a534f2b --- /dev/null +++ b/x/vm/migrations/v2/store_test.go @@ -0,0 +1,83 @@ +package v2 + +import ( + "testing" + + cmtproto "github.com/cometbft/cometbft/proto/tendermint/types" + cmttime "github.com/cometbft/cometbft/types/time" + "github.com/stretchr/testify/require" + + "github.com/cosmos/evm/testutil/constants" + vmkeeper "github.com/cosmos/evm/x/vm/keeper" + vmtypes "github.com/cosmos/evm/x/vm/types" + "github.com/cosmos/evm/x/vm/types/mocks" + + storetypes "github.com/cosmos/cosmos-sdk/store/v2/types" + "github.com/cosmos/cosmos-sdk/testutil" + sdk "github.com/cosmos/cosmos-sdk/types" + moduletestutil "github.com/cosmos/cosmos-sdk/types/module/testutil" +) + +func TestMigrateStoreRemovesVestingPrecompile(t *testing.T) { + ctx, keeper := setupKeeper(t) + params := vmtypes.DefaultParams() + params.ActiveStaticPrecompiles = append([]string{ + vmtypes.P256PrecompileAddress, + vmtypes.Bech32PrecompileAddress, + vmtypes.StakingPrecompileAddress, + vmtypes.DistributionPrecompileAddress, + vmtypes.ICS20PrecompileAddress, + vestingPrecompileAddress, + }, vmtypes.AvailableStaticPrecompiles[5:]...) + require.NoError(t, keeper.SetParams(ctx, params)) + + require.NoError(t, MigrateStore(ctx, keeper)) + + require.Equal(t, vmtypes.AvailableStaticPrecompiles, keeper.GetParams(ctx).ActiveStaticPrecompiles) +} + +func TestMigrateStoreNoopsWithoutVestingPrecompile(t *testing.T) { + ctx, keeper := setupKeeper(t) + params := vmtypes.DefaultParams() + params.ActiveStaticPrecompiles = append([]string(nil), vmtypes.AvailableStaticPrecompiles...) + require.NoError(t, keeper.SetParams(ctx, params)) + + require.NoError(t, MigrateStore(ctx, keeper)) + + require.Equal(t, params, keeper.GetParams(ctx)) +} + +func setupKeeper(t *testing.T) (sdk.Context, *vmkeeper.Keeper) { + t.Helper() + + key := storetypes.NewKVStoreKey(vmtypes.StoreKey) + oKey := storetypes.NewObjectStoreKey(vmtypes.ObjectKey) + ctx := testutil.DefaultContextWithObjectStore( + t, + key, + storetypes.NewTransientStoreKey("store_test"), + oKey, + ).Ctx.WithBlockHeader(cmtproto.Header{Time: cmttime.Now()}) + + accountKeeper := mocks.NewAccountKeeper(t) + accountKeeper.On("GetModuleAddress", vmtypes.ModuleName).Return(sdk.AccAddress("evm")) + + encCfg := moduletestutil.MakeTestEncodingConfig() + keeper := vmkeeper.NewKeeper( + encCfg.Codec, + key, + oKey, + []storetypes.StoreKey{key, oKey}, + sdk.AccAddress("foobar"), + accountKeeper, + mocks.NewBankKeeper(t), + mocks.NewStakingKeeper(t), + mocks.NewFeeMarketKeeper(t), + mocks.NewConsensusParamsKeeper(t), + mocks.NewErc20Keeper(t), + constants.EighteenDecimalsChainID, + "", + ) + + return ctx, keeper +} diff --git a/x/vm/module.go b/x/vm/module.go index 27106cf379..44a4bc5c13 100644 --- a/x/vm/module.go +++ b/x/vm/module.go @@ -14,6 +14,7 @@ import ( "github.com/cosmos/evm/x/vm/client/cli" "github.com/cosmos/evm/x/vm/keeper" + v2 "github.com/cosmos/evm/x/vm/migrations/v2" "github.com/cosmos/evm/x/vm/types" "cosmossdk.io/core/address" @@ -29,7 +30,7 @@ import ( ) // consensusVersion defines the current x/evm module consensus version. -const consensusVersion = 1 +const consensusVersion = 2 var ( _ module.AppModuleBasic = AppModuleBasic{} @@ -134,6 +135,12 @@ func (AppModule) Name() string { func (am AppModule) RegisterServices(cfg module.Configurator) { types.RegisterMsgServer(cfg.MsgServer(), am.keeper) types.RegisterQueryServer(cfg.QueryServer(), am.keeper) + + if err := cfg.RegisterMigration(types.ModuleName, 1, func(ctx sdk.Context) error { + return v2.MigrateStore(ctx, am.keeper) + }); err != nil { + panic(fmt.Sprintf("failed to register x/%s migration: %s", types.ModuleName, err.Error())) + } } // HydrateGlobals restores global EVM variables from KV store after a node restart (post-genesis). diff --git a/x/vm/types/precompiles.go b/x/vm/types/precompiles.go index a7e058ac85..41897931e3 100644 --- a/x/vm/types/precompiles.go +++ b/x/vm/types/precompiles.go @@ -9,7 +9,6 @@ const ( StakingPrecompileAddress = "0x0000000000000000000000000000000000000800" DistributionPrecompileAddress = "0x0000000000000000000000000000000000000801" ICS20PrecompileAddress = "0x0000000000000000000000000000000000000802" - VestingPrecompileAddress = "0x0000000000000000000000000000000000000803" BankPrecompileAddress = "0x0000000000000000000000000000000000000804" GovPrecompileAddress = "0x0000000000000000000000000000000000000805" SlashingPrecompileAddress = "0x0000000000000000000000000000000000000806" @@ -26,7 +25,6 @@ var AvailableStaticPrecompiles = []string{ StakingPrecompileAddress, DistributionPrecompileAddress, ICS20PrecompileAddress, - VestingPrecompileAddress, BankPrecompileAddress, GovPrecompileAddress, SlashingPrecompileAddress,