forked from cerc-io/laconicd-deprecated
release: v0.20.0-rc1 cherry pick and changelog (#1422)
* Revert "feat(eip712): Create LedgerPreprocessHook to reformat EIP-712 payloads (#1277)"
This reverts commit 723443abc7
.
* release: upadte changelog
This commit is contained in:
parent
a8ea4eceb6
commit
92c0f558c1
@ -36,7 +36,7 @@ Ref: https://keepachangelog.com/en/1.0.0/
|
|||||||
|
|
||||||
# Changelog
|
# Changelog
|
||||||
|
|
||||||
## Unreleased
|
## [v0.20.0-rc1] - 2022-11-02
|
||||||
|
|
||||||
### State Machine Breaking
|
### State Machine Breaking
|
||||||
|
|
||||||
@ -58,7 +58,6 @@ Ref: https://keepachangelog.com/en/1.0.0/
|
|||||||
* (cli) [#1226](https://github.com/evmos/ethermint/pull/1226) Add custom app db backend flag.
|
* (cli) [#1226](https://github.com/evmos/ethermint/pull/1226) Add custom app db backend flag.
|
||||||
* (ante) [#1289](https://github.com/evmos/ethermint/pull/1289) Change the fallback tx priority mechanism to be based on gas price.
|
* (ante) [#1289](https://github.com/evmos/ethermint/pull/1289) Change the fallback tx priority mechanism to be based on gas price.
|
||||||
* (test) [#1311](https://github.com/evmos/ethermint/pull/1311) Add integration test for the `rollback` cmd
|
* (test) [#1311](https://github.com/evmos/ethermint/pull/1311) Add integration test for the `rollback` cmd
|
||||||
* (ledger) [#1277](https://github.com/evmos/ethermint/pull/1277) Add Ledger preprocessing transaction hook for EIP-712-signed Cosmos payloads.
|
|
||||||
* (rpc) [#1296](https://github.com/evmos/ethermint/pull/1296) Add RPC Backend unit tests.
|
* (rpc) [#1296](https://github.com/evmos/ethermint/pull/1296) Add RPC Backend unit tests.
|
||||||
* (rpc) [#1352](https://github.com/evmos/ethermint/pull/1352) Make the grpc queries run concurrently, don't block the consensus state machine.
|
* (rpc) [#1352](https://github.com/evmos/ethermint/pull/1352) Make the grpc queries run concurrently, don't block the consensus state machine.
|
||||||
* (cli) [#1360](https://github.com/evmos/ethermint/pull/1360) Introduce a new `grpc-only` flag, such that when enabled, will start the node in a query-only mode. Note, gRPC MUST be enabled with this flag.
|
* (cli) [#1360](https://github.com/evmos/ethermint/pull/1360) Introduce a new `grpc-only` flag, such that when enabled, will start the node in a query-only mode. Note, gRPC MUST be enabled with this flag.
|
||||||
|
@ -1,83 +0,0 @@
|
|||||||
package eip712
|
|
||||||
|
|
||||||
import (
|
|
||||||
"fmt"
|
|
||||||
|
|
||||||
"github.com/cosmos/cosmos-sdk/client"
|
|
||||||
codectypes "github.com/cosmos/cosmos-sdk/codec/types"
|
|
||||||
cosmoskr "github.com/cosmos/cosmos-sdk/crypto/keyring"
|
|
||||||
"github.com/cosmos/cosmos-sdk/types/tx/signing"
|
|
||||||
authtx "github.com/cosmos/cosmos-sdk/x/auth/tx"
|
|
||||||
"github.com/evmos/ethermint/types"
|
|
||||||
)
|
|
||||||
|
|
||||||
// PreprocessLedgerTx reformats Ledger-signed Cosmos transactions to match the fork expected by Ethermint
|
|
||||||
// by including the signature in a Web3Tx extension and sending a blank signature in the body.
|
|
||||||
func PreprocessLedgerTx(chainID string, keyType cosmoskr.KeyType, txBuilder client.TxBuilder) error {
|
|
||||||
// Only process Ledger transactions
|
|
||||||
if keyType != cosmoskr.TypeLedger {
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// Init extension builder to set Web3 extension
|
|
||||||
extensionBuilder, ok := txBuilder.(authtx.ExtensionOptionsTxBuilder)
|
|
||||||
if !ok {
|
|
||||||
return fmt.Errorf("cannot cast TxBuilder to ExtensionOptionsTxBuilder")
|
|
||||||
}
|
|
||||||
|
|
||||||
// Get signatures from TxBuilder
|
|
||||||
sigs, err := txBuilder.GetTx().GetSignaturesV2()
|
|
||||||
if err != nil {
|
|
||||||
return fmt.Errorf("could not get signatures: %w", err)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Verify single-signer
|
|
||||||
if len(sigs) != 1 {
|
|
||||||
return fmt.Errorf("invalid number of signatures, expected 1 and got %v", len(sigs))
|
|
||||||
}
|
|
||||||
|
|
||||||
signature := sigs[0]
|
|
||||||
sigData, ok := signature.Data.(*signing.SingleSignatureData)
|
|
||||||
if !ok {
|
|
||||||
return fmt.Errorf("unexpected signature type, expected SingleSignatureData")
|
|
||||||
}
|
|
||||||
sigBytes := sigData.Signature
|
|
||||||
|
|
||||||
// Parse Chain ID as big.Int
|
|
||||||
chainIDInt, err := types.ParseChainID(chainID)
|
|
||||||
if err != nil {
|
|
||||||
return fmt.Errorf("could not parse chain id: %w", err)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Add ExtensionOptionsWeb3Tx extension with signature
|
|
||||||
var option *codectypes.Any
|
|
||||||
option, err = codectypes.NewAnyWithValue(&types.ExtensionOptionsWeb3Tx{
|
|
||||||
FeePayer: txBuilder.GetTx().FeePayer().String(),
|
|
||||||
TypedDataChainID: chainIDInt.Uint64(),
|
|
||||||
FeePayerSig: sigBytes,
|
|
||||||
})
|
|
||||||
if err != nil {
|
|
||||||
return fmt.Errorf("could not set extension as any: %w", err)
|
|
||||||
}
|
|
||||||
|
|
||||||
extensionBuilder.SetExtensionOptions(option)
|
|
||||||
|
|
||||||
// Set blank signature with Amino Sign Type
|
|
||||||
// (Regardless of input signMode, Evmos requires Amino signature type for Ledger)
|
|
||||||
blankSig := signing.SingleSignatureData{
|
|
||||||
SignMode: signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON,
|
|
||||||
Signature: nil,
|
|
||||||
}
|
|
||||||
sig := signing.SignatureV2{
|
|
||||||
PubKey: signature.PubKey,
|
|
||||||
Data: &blankSig,
|
|
||||||
Sequence: signature.Sequence,
|
|
||||||
}
|
|
||||||
|
|
||||||
err = txBuilder.SetSignatures(sig)
|
|
||||||
if err != nil {
|
|
||||||
return fmt.Errorf("unable to set signatures on payload: %w", err)
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
|
||||||
}
|
|
@ -1,222 +0,0 @@
|
|||||||
package eip712_test
|
|
||||||
|
|
||||||
import (
|
|
||||||
"encoding/hex"
|
|
||||||
"strings"
|
|
||||||
"testing"
|
|
||||||
|
|
||||||
"cosmossdk.io/math"
|
|
||||||
"github.com/cosmos/cosmos-sdk/client"
|
|
||||||
codectypes "github.com/cosmos/cosmos-sdk/codec/types"
|
|
||||||
"github.com/cosmos/cosmos-sdk/crypto/keyring"
|
|
||||||
sdk "github.com/cosmos/cosmos-sdk/types"
|
|
||||||
"github.com/cosmos/cosmos-sdk/types/tx/signing"
|
|
||||||
"github.com/cosmos/cosmos-sdk/x/auth/ante"
|
|
||||||
banktypes "github.com/cosmos/cosmos-sdk/x/bank/types"
|
|
||||||
"github.com/evmos/ethermint/app"
|
|
||||||
"github.com/evmos/ethermint/encoding"
|
|
||||||
"github.com/evmos/ethermint/ethereum/eip712"
|
|
||||||
"github.com/evmos/ethermint/tests"
|
|
||||||
"github.com/evmos/ethermint/types"
|
|
||||||
evmtypes "github.com/evmos/ethermint/x/evm/types"
|
|
||||||
"github.com/stretchr/testify/require"
|
|
||||||
)
|
|
||||||
|
|
||||||
// Testing Constants
|
|
||||||
var (
|
|
||||||
chainId = "ethermint_9000-1"
|
|
||||||
ctx = client.Context{}.WithTxConfig(
|
|
||||||
encoding.MakeConfig(app.ModuleBasics).TxConfig,
|
|
||||||
)
|
|
||||||
)
|
|
||||||
var feePayerAddress = "ethm17xpfvakm2amg962yls6f84z3kell8c5lthdzgl"
|
|
||||||
|
|
||||||
type TestCaseStruct struct {
|
|
||||||
txBuilder client.TxBuilder
|
|
||||||
expectedFeePayer string
|
|
||||||
expectedGas uint64
|
|
||||||
expectedFee math.Int
|
|
||||||
expectedMemo string
|
|
||||||
expectedMsg string
|
|
||||||
expectedSignatureBytes []byte
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestLedgerPreprocessing(t *testing.T) {
|
|
||||||
// Update bech32 prefix
|
|
||||||
sdk.GetConfig().SetBech32PrefixForAccount("ethm", "")
|
|
||||||
|
|
||||||
testCases := []TestCaseStruct{
|
|
||||||
createBasicTestCase(t),
|
|
||||||
createPopulatedTestCase(t),
|
|
||||||
}
|
|
||||||
|
|
||||||
for _, tc := range testCases {
|
|
||||||
// Run pre-processing
|
|
||||||
err := eip712.PreprocessLedgerTx(
|
|
||||||
chainId,
|
|
||||||
keyring.TypeLedger,
|
|
||||||
tc.txBuilder,
|
|
||||||
)
|
|
||||||
|
|
||||||
require.NoError(t, err)
|
|
||||||
|
|
||||||
// Verify Web3 extension matches expected
|
|
||||||
hasExtOptsTx, ok := tc.txBuilder.(ante.HasExtensionOptionsTx)
|
|
||||||
require.True(t, ok)
|
|
||||||
require.True(t, len(hasExtOptsTx.GetExtensionOptions()) == 1)
|
|
||||||
|
|
||||||
expectedExt := types.ExtensionOptionsWeb3Tx{
|
|
||||||
TypedDataChainID: 9000,
|
|
||||||
FeePayer: feePayerAddress,
|
|
||||||
FeePayerSig: tc.expectedSignatureBytes,
|
|
||||||
}
|
|
||||||
|
|
||||||
expectedExtAny, err := codectypes.NewAnyWithValue(&expectedExt)
|
|
||||||
require.NoError(t, err)
|
|
||||||
|
|
||||||
actualExtAny := hasExtOptsTx.GetExtensionOptions()[0]
|
|
||||||
require.Equal(t, expectedExtAny, actualExtAny)
|
|
||||||
|
|
||||||
// Verify signature type matches expected
|
|
||||||
signatures, err := tc.txBuilder.GetTx().GetSignaturesV2()
|
|
||||||
require.NoError(t, err)
|
|
||||||
require.Equal(t, len(signatures), 1)
|
|
||||||
|
|
||||||
txSig := signatures[0].Data.(*signing.SingleSignatureData)
|
|
||||||
require.Equal(t, txSig.SignMode, signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON)
|
|
||||||
|
|
||||||
// Verify signature is blank
|
|
||||||
require.Equal(t, len(txSig.Signature), 0)
|
|
||||||
|
|
||||||
// Verify tx fields are unchanged
|
|
||||||
tx := tc.txBuilder.GetTx()
|
|
||||||
|
|
||||||
require.Equal(t, tx.FeePayer().String(), tc.expectedFeePayer)
|
|
||||||
require.Equal(t, tx.GetGas(), tc.expectedGas)
|
|
||||||
require.Equal(t, tx.GetFee().AmountOf(evmtypes.DefaultParams().EvmDenom), tc.expectedFee)
|
|
||||||
require.Equal(t, tx.GetMemo(), tc.expectedMemo)
|
|
||||||
|
|
||||||
// Verify message is unchanged
|
|
||||||
if tc.expectedMsg != "" {
|
|
||||||
require.Equal(t, len(tx.GetMsgs()), 1)
|
|
||||||
require.Equal(t, tx.GetMsgs()[0].String(), tc.expectedMsg)
|
|
||||||
} else {
|
|
||||||
require.Equal(t, len(tx.GetMsgs()), 0)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestBlankTxBuilder(t *testing.T) {
|
|
||||||
txBuilder := ctx.TxConfig.NewTxBuilder()
|
|
||||||
|
|
||||||
err := eip712.PreprocessLedgerTx(
|
|
||||||
chainId,
|
|
||||||
keyring.TypeLedger,
|
|
||||||
txBuilder,
|
|
||||||
)
|
|
||||||
|
|
||||||
require.Error(t, err)
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestNonLedgerTxBuilder(t *testing.T) {
|
|
||||||
txBuilder := ctx.TxConfig.NewTxBuilder()
|
|
||||||
|
|
||||||
err := eip712.PreprocessLedgerTx(
|
|
||||||
chainId,
|
|
||||||
keyring.TypeLocal,
|
|
||||||
txBuilder,
|
|
||||||
)
|
|
||||||
|
|
||||||
require.NoError(t, err)
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestInvalidChainId(t *testing.T) {
|
|
||||||
txBuilder := ctx.TxConfig.NewTxBuilder()
|
|
||||||
|
|
||||||
err := eip712.PreprocessLedgerTx(
|
|
||||||
"invalid-chain-id",
|
|
||||||
keyring.TypeLedger,
|
|
||||||
txBuilder,
|
|
||||||
)
|
|
||||||
|
|
||||||
require.Error(t, err)
|
|
||||||
}
|
|
||||||
|
|
||||||
func createBasicTestCase(t *testing.T) TestCaseStruct {
|
|
||||||
t.Helper()
|
|
||||||
txBuilder := ctx.TxConfig.NewTxBuilder()
|
|
||||||
|
|
||||||
feePayer, err := sdk.AccAddressFromBech32(feePayerAddress)
|
|
||||||
require.NoError(t, err)
|
|
||||||
|
|
||||||
txBuilder.SetFeePayer(feePayer)
|
|
||||||
|
|
||||||
// Create signature unrelated to payload for testing
|
|
||||||
signatureHex := strings.Repeat("01", 65)
|
|
||||||
signatureBytes, err := hex.DecodeString(signatureHex)
|
|
||||||
require.NoError(t, err)
|
|
||||||
|
|
||||||
_, privKey := tests.NewAddrKey()
|
|
||||||
sigsV2 := signing.SignatureV2{
|
|
||||||
PubKey: privKey.PubKey(), // Use unrelated public key for testing
|
|
||||||
Data: &signing.SingleSignatureData{
|
|
||||||
SignMode: signing.SignMode_SIGN_MODE_DIRECT,
|
|
||||||
Signature: signatureBytes,
|
|
||||||
},
|
|
||||||
Sequence: 0,
|
|
||||||
}
|
|
||||||
|
|
||||||
txBuilder.SetSignatures(sigsV2)
|
|
||||||
return TestCaseStruct{
|
|
||||||
txBuilder: txBuilder,
|
|
||||||
expectedFeePayer: feePayer.String(),
|
|
||||||
expectedGas: 0,
|
|
||||||
expectedFee: math.NewInt(0),
|
|
||||||
expectedMemo: "",
|
|
||||||
expectedMsg: "",
|
|
||||||
expectedSignatureBytes: signatureBytes,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func createPopulatedTestCase(t *testing.T) TestCaseStruct {
|
|
||||||
t.Helper()
|
|
||||||
basicTestCase := createBasicTestCase(t)
|
|
||||||
txBuilder := basicTestCase.txBuilder
|
|
||||||
|
|
||||||
gasLimit := uint64(200000)
|
|
||||||
memo := ""
|
|
||||||
denom := evmtypes.DefaultParams().EvmDenom
|
|
||||||
feeAmount := math.NewInt(2000)
|
|
||||||
|
|
||||||
txBuilder.SetFeeAmount(sdk.NewCoins(
|
|
||||||
sdk.NewCoin(
|
|
||||||
denom,
|
|
||||||
feeAmount,
|
|
||||||
)))
|
|
||||||
|
|
||||||
txBuilder.SetGasLimit(gasLimit)
|
|
||||||
txBuilder.SetMemo(memo)
|
|
||||||
|
|
||||||
msgSend := banktypes.MsgSend{
|
|
||||||
FromAddress: feePayerAddress,
|
|
||||||
ToAddress: "ethm12luku6uxehhak02py4rcz65zu0swh7wjun6msa",
|
|
||||||
Amount: sdk.NewCoins(
|
|
||||||
sdk.NewCoin(
|
|
||||||
evmtypes.DefaultParams().EvmDenom,
|
|
||||||
math.NewInt(10000000),
|
|
||||||
),
|
|
||||||
),
|
|
||||||
}
|
|
||||||
|
|
||||||
txBuilder.SetMsgs(&msgSend)
|
|
||||||
|
|
||||||
return TestCaseStruct{
|
|
||||||
txBuilder: txBuilder,
|
|
||||||
expectedFeePayer: basicTestCase.expectedFeePayer,
|
|
||||||
expectedGas: gasLimit,
|
|
||||||
expectedFee: feeAmount,
|
|
||||||
expectedMemo: memo,
|
|
||||||
expectedMsg: msgSend.String(),
|
|
||||||
expectedSignatureBytes: basicTestCase.expectedSignatureBytes,
|
|
||||||
}
|
|
||||||
}
|
|
Loading…
Reference in New Issue
Block a user