laconicd-deprecated/rpc/backend/sign_tx.go
Ramiro Carlucho 71e51aabf6
chore (deps): Update geth version to v1.10.25 (#1413)
* build(deps): bump github.com/ethereum/go-ethereum

Bumps [github.com/ethereum/go-ethereum](https://github.com/ethereum/go-ethereum) from 1.10.19 to 1.10.25.
- [Release notes](https://github.com/ethereum/go-ethereum/releases)
- [Commits](https://github.com/ethereum/go-ethereum/compare/v1.10.19...v1.10.25)

---
updated-dependencies:
- dependency-name: github.com/ethereum/go-ethereum
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>

* wip geth update

* fix geth init flag order

* add chainId to getTransaction. fix types comparison. update expected values on tests

* wip add tracer config

* tracers test

* update tests

* update to v1.10.25

* fix linter python

* ignore error

* fix lint

* additional changes from diff

* fix issues

* solve lint issues

* fix tests

* fix flake

* wrap types comparison in integration tests

* fix integration tests

* fix flake

* update changelog

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Federico Kunze Küllmer <31522760+fedekunze@users.noreply.github.com>
Co-authored-by: Freddy Caceres <facs95@gmail.com>
2022-11-16 12:59:12 -05:00

153 lines
5.1 KiB
Go

package backend
import (
"errors"
"fmt"
"math/big"
errorsmod "cosmossdk.io/errors"
"github.com/cosmos/cosmos-sdk/client/flags"
sdk "github.com/cosmos/cosmos-sdk/types"
"github.com/ethereum/go-ethereum/accounts/keystore"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/common/hexutil"
ethtypes "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/signer/core/apitypes"
evmtypes "github.com/evmos/ethermint/x/evm/types"
)
// SendTransaction sends transaction based on received args using Node's key to sign it
func (b *Backend) SendTransaction(args evmtypes.TransactionArgs) (common.Hash, error) {
// Look up the wallet containing the requested signer
_, err := b.clientCtx.Keyring.KeyByAddress(sdk.AccAddress(args.GetFrom().Bytes()))
if err != nil {
b.logger.Error("failed to find key in keyring", "address", args.GetFrom(), "error", err.Error())
return common.Hash{}, fmt.Errorf("%s; %s", keystore.ErrNoMatch, err.Error())
}
if args.ChainID != nil && (b.chainID).Cmp((*big.Int)(args.ChainID)) != 0 {
return common.Hash{}, fmt.Errorf("chainId does not match node's (have=%v, want=%v)", args.ChainID, (*hexutil.Big)(b.chainID))
}
args, err = b.SetTxDefaults(args)
if err != nil {
return common.Hash{}, err
}
msg := args.ToTransaction()
if err := msg.ValidateBasic(); err != nil {
b.logger.Debug("tx failed basic validation", "error", err.Error())
return common.Hash{}, err
}
bn, err := b.BlockNumber()
if err != nil {
b.logger.Debug("failed to fetch latest block number", "error", err.Error())
return common.Hash{}, err
}
signer := ethtypes.MakeSigner(b.ChainConfig(), new(big.Int).SetUint64(uint64(bn)))
// Sign transaction
if err := msg.Sign(signer, b.clientCtx.Keyring); err != nil {
b.logger.Debug("failed to sign tx", "error", err.Error())
return common.Hash{}, err
}
// Query params to use the EVM denomination
res, err := b.queryClient.QueryClient.Params(b.ctx, &evmtypes.QueryParamsRequest{})
if err != nil {
b.logger.Error("failed to query evm params", "error", err.Error())
return common.Hash{}, err
}
// Assemble transaction from fields
tx, err := msg.BuildTx(b.clientCtx.TxConfig.NewTxBuilder(), res.Params.EvmDenom)
if err != nil {
b.logger.Error("build cosmos tx failed", "error", err.Error())
return common.Hash{}, err
}
// Encode transaction by default Tx encoder
txEncoder := b.clientCtx.TxConfig.TxEncoder()
txBytes, err := txEncoder(tx)
if err != nil {
b.logger.Error("failed to encode eth tx using default encoder", "error", err.Error())
return common.Hash{}, err
}
ethTx := msg.AsTransaction()
// check the local node config in case unprotected txs are disabled
if !b.UnprotectedAllowed() && !ethTx.Protected() {
// Ensure only eip155 signed transactions are submitted if EIP155Required is set.
return common.Hash{}, errors.New("only replay-protected (EIP-155) transactions allowed over RPC")
}
txHash := ethTx.Hash()
// Broadcast transaction in sync mode (default)
// NOTE: If error is encountered on the node, the broadcast will not return an error
syncCtx := b.clientCtx.WithBroadcastMode(flags.BroadcastSync)
rsp, err := syncCtx.BroadcastTx(txBytes)
if rsp != nil && rsp.Code != 0 {
err = errorsmod.ABCIError(rsp.Codespace, rsp.Code, rsp.RawLog)
}
if err != nil {
b.logger.Error("failed to broadcast tx", "error", err.Error())
return txHash, err
}
// Return transaction hash
return txHash, nil
}
// Sign signs the provided data using the private key of address via Geth's signature standard.
func (b *Backend) Sign(address common.Address, data hexutil.Bytes) (hexutil.Bytes, error) {
from := sdk.AccAddress(address.Bytes())
_, err := b.clientCtx.Keyring.KeyByAddress(from)
if err != nil {
b.logger.Error("failed to find key in keyring", "address", address.String())
return nil, fmt.Errorf("%s; %s", keystore.ErrNoMatch, err.Error())
}
// Sign the requested hash with the wallet
signature, _, err := b.clientCtx.Keyring.SignByAddress(from, data)
if err != nil {
b.logger.Error("keyring.SignByAddress failed", "address", address.Hex())
return nil, err
}
signature[crypto.RecoveryIDOffset] += 27 // Transform V from 0/1 to 27/28 according to the yellow paper
return signature, nil
}
// SignTypedData signs EIP-712 conformant typed data
func (b *Backend) SignTypedData(address common.Address, typedData apitypes.TypedData) (hexutil.Bytes, error) {
from := sdk.AccAddress(address.Bytes())
_, err := b.clientCtx.Keyring.KeyByAddress(from)
if err != nil {
b.logger.Error("failed to find key in keyring", "address", address.String())
return nil, fmt.Errorf("%s; %s", keystore.ErrNoMatch, err.Error())
}
sigHash, _, err := apitypes.TypedDataAndHash(typedData)
if err != nil {
return nil, err
}
// Sign the requested hash with the wallet
signature, _, err := b.clientCtx.Keyring.SignByAddress(from, sigHash)
if err != nil {
b.logger.Error("keyring.SignByAddress failed", "address", address.Hex())
return nil, err
}
signature[crypto.RecoveryIDOffset] += 27 // Transform V from 0/1 to 27/28 according to the yellow paper
return signature, nil
}