diff --git a/core/src/apps/ethereum/keychain.py b/core/src/apps/ethereum/keychain.py index a4300da31a..b0c7aecfb5 100644 --- a/core/src/apps/ethereum/keychain.py +++ b/core/src/apps/ethereum/keychain.py @@ -124,7 +124,7 @@ def with_keychain_from_path( slip44 = _slip44_from_address_n(msg.address_n) defs = _defs_from_message(msg, slip44=slip44) schemas = _schemas_from_network(patterns, defs.network) - keychain = await get_keychain(CURVE, schemas) + keychain = await get_keychain(CURVE, schemas, [[b"SLIP-0024"]]) with keychain: return await func(msg, keychain, defs) @@ -140,7 +140,7 @@ def with_keychain_from_chain_id( async def wrapper(msg: MsgInSignTx) -> MsgOut: defs = _defs_from_message(msg, chain_id=msg.chain_id) schemas = _schemas_from_network(PATTERNS_ADDRESS, defs.network) - keychain = await get_keychain(CURVE, schemas) + keychain = await get_keychain(CURVE, schemas, [[b"SLIP-0024"]]) with keychain: return await func(msg, keychain, defs) diff --git a/core/src/apps/ethereum/layout.py b/core/src/apps/ethereum/layout.py index f4e97651fd..fa30c6bfe4 100644 --- a/core/src/apps/ethereum/layout.py +++ b/core/src/apps/ethereum/layout.py @@ -28,7 +28,7 @@ if TYPE_CHECKING: async def require_confirm_tx( - to_bytes: bytes, + recipient: str | None, value: int, address_n: list[int], maximum_fee: str, @@ -40,12 +40,11 @@ async def require_confirm_tx( ) -> None: from trezor.ui.layouts import confirm_ethereum_tx - to_str = address_from_bytes(to_bytes, network) if to_bytes else None total_amount = format_ethereum_amount(value, token, network) account, account_path = get_account_and_path(address_n) await confirm_ethereum_tx( - to_str, + recipient, total_amount, account, account_path, diff --git a/core/src/apps/ethereum/sign_tx.py b/core/src/apps/ethereum/sign_tx.py index 8294b90b16..240600943e 100644 --- a/core/src/apps/ethereum/sign_tx.py +++ b/core/src/apps/ethereum/sign_tx.py @@ -7,7 +7,7 @@ from trezor.wire import DataError from apps.ethereum import staking_tx_constants as constants -from .helpers import bytes_from_address +from .helpers import address_from_bytes, bytes_from_address from .keychain import with_keychain_from_chain_id if TYPE_CHECKING: @@ -21,6 +21,7 @@ if TYPE_CHECKING: ) from apps.common.keychain import Keychain + from apps.common.payment_request import PaymentRequestVerifier from .definitions import Definitions from .keychain import MsgInSignTx @@ -67,7 +68,25 @@ async def sign_tx( gas_limit, defs.network, ) - await confirm_tx_data(msg, defs, address_bytes, maximum_fee, fee_items, data_total) + + payment_req_verifier = None + if msg.payment_req: + from apps.common.payment_request import PaymentRequestVerifier + + slip44_id = paths.unharden(msg.address_n[1]) + payment_req_verifier = PaymentRequestVerifier( + msg.payment_req, slip44_id, keychain + ) + + await confirm_tx_data( + msg, + defs, + address_bytes, + maximum_fee, + fee_items, + data_total, + payment_req_verifier, + ) progress_obj = progress(title=TR.progress__signing_transaction) progress_obj.report(30) @@ -121,6 +140,7 @@ async def confirm_tx_data( maximum_fee: str, fee_items: Iterable[tuple[str, str]], data_total_len: int, + payment_req_verifier: PaymentRequestVerifier | None, ) -> None: # function distinguishes between staking / smart contracts / regular transactions from .layout import require_confirm_other_data, require_confirm_tx @@ -131,13 +151,19 @@ async def confirm_tx_data( # Handle ERC-20, currently only 'transfer' function token, recipient, value = await _handle_erc20_transfer(msg, defs, address_bytes) + recipient_str = address_from_bytes(recipient, defs.network) if recipient else None + if msg.payment_req and payment_req_verifier: + payment_req_verifier.add_output(value, recipient_str or "") + payment_req_verifier.verify() + recipient_str = msg.payment_req.recipient_name + is_contract_interaction = token is None and data_total_len > 0 if is_contract_interaction: await require_confirm_other_data(msg.data_initial_chunk, data_total_len) await require_confirm_tx( - recipient, + recipient_str, value, msg.address_n, maximum_fee, diff --git a/core/src/apps/ethereum/sign_tx_eip1559.py b/core/src/apps/ethereum/sign_tx_eip1559.py index a4cb1d2862..cc933133da 100644 --- a/core/src/apps/ethereum/sign_tx_eip1559.py +++ b/core/src/apps/ethereum/sign_tx_eip1559.py @@ -69,7 +69,25 @@ async def sign_tx_eip1559( gas_limit, defs.network, ) - await confirm_tx_data(msg, defs, address_bytes, maximum_fee, fee_items, data_total) + + payment_req_verifier = None + if msg.payment_req: + from apps.common.payment_request import PaymentRequestVerifier + + slip44_id = paths.unharden(msg.address_n[1]) + payment_req_verifier = PaymentRequestVerifier( + msg.payment_req, slip44_id, keychain + ) + + await confirm_tx_data( + msg, + defs, + address_bytes, + maximum_fee, + fee_items, + data_total, + payment_req_verifier, + ) # transaction data confirmed, proceed with signing data = bytearray() diff --git a/python/src/trezorlib/ethereum.py b/python/src/trezorlib/ethereum.py index 9fd892f3c1..2789012257 100644 --- a/python/src/trezorlib/ethereum.py +++ b/python/src/trezorlib/ethereum.py @@ -208,6 +208,7 @@ def sign_tx( tx_type: Optional[int] = None, definitions: Optional[messages.EthereumDefinitions] = None, chunkify: bool = False, + payment_req: Optional[messages.PaymentRequest] = None, ) -> Tuple[int, bytes, bytes]: if chain_id is None: raise exceptions.TrezorException("Chain ID cannot be undefined") @@ -223,6 +224,7 @@ def sign_tx( tx_type=tx_type, definitions=definitions, chunkify=chunkify, + payment_req=payment_req, ) if data is None: @@ -269,6 +271,7 @@ def sign_tx_eip1559( access_list: Optional[List[messages.EthereumAccessList]] = None, definitions: Optional[messages.EthereumDefinitions] = None, chunkify: bool = False, + payment_req: Optional[messages.PaymentRequest] = None, ) -> Tuple[int, bytes, bytes]: length = len(data) data, chunk = data[1024:], data[:1024] @@ -286,6 +289,7 @@ def sign_tx_eip1559( data_initial_chunk=chunk, definitions=definitions, chunkify=chunkify, + payment_req=payment_req, ) response = client.call(msg)