mirror of
https://github.com/trezor/trezor-firmware.git
synced 2025-07-20 05:28:14 +00:00
feat(core): Implement payment requests in Ethereum signing.
This commit is contained in:
parent
00fb041452
commit
5dd2405a86
@ -124,7 +124,7 @@ def with_keychain_from_path(
|
|||||||
slip44 = _slip44_from_address_n(msg.address_n)
|
slip44 = _slip44_from_address_n(msg.address_n)
|
||||||
defs = _defs_from_message(msg, slip44=slip44)
|
defs = _defs_from_message(msg, slip44=slip44)
|
||||||
schemas = _schemas_from_network(patterns, defs.network)
|
schemas = _schemas_from_network(patterns, defs.network)
|
||||||
keychain = await get_keychain(CURVE, schemas)
|
keychain = await get_keychain(CURVE, schemas, [[b"SLIP-0024"]])
|
||||||
with keychain:
|
with keychain:
|
||||||
return await func(msg, keychain, defs)
|
return await func(msg, keychain, defs)
|
||||||
|
|
||||||
@ -140,7 +140,7 @@ def with_keychain_from_chain_id(
|
|||||||
async def wrapper(msg: MsgInSignTx) -> MsgOut:
|
async def wrapper(msg: MsgInSignTx) -> MsgOut:
|
||||||
defs = _defs_from_message(msg, chain_id=msg.chain_id)
|
defs = _defs_from_message(msg, chain_id=msg.chain_id)
|
||||||
schemas = _schemas_from_network(PATTERNS_ADDRESS, defs.network)
|
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:
|
with keychain:
|
||||||
return await func(msg, keychain, defs)
|
return await func(msg, keychain, defs)
|
||||||
|
|
||||||
|
@ -28,7 +28,7 @@ if TYPE_CHECKING:
|
|||||||
|
|
||||||
|
|
||||||
async def require_confirm_tx(
|
async def require_confirm_tx(
|
||||||
to_bytes: bytes,
|
recipient: str | None,
|
||||||
value: int,
|
value: int,
|
||||||
address_n: list[int],
|
address_n: list[int],
|
||||||
maximum_fee: str,
|
maximum_fee: str,
|
||||||
@ -40,12 +40,11 @@ async def require_confirm_tx(
|
|||||||
) -> None:
|
) -> None:
|
||||||
from trezor.ui.layouts import confirm_ethereum_tx
|
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)
|
total_amount = format_ethereum_amount(value, token, network)
|
||||||
account, account_path = get_account_and_path(address_n)
|
account, account_path = get_account_and_path(address_n)
|
||||||
|
|
||||||
await confirm_ethereum_tx(
|
await confirm_ethereum_tx(
|
||||||
to_str,
|
recipient,
|
||||||
total_amount,
|
total_amount,
|
||||||
account,
|
account,
|
||||||
account_path,
|
account_path,
|
||||||
|
@ -7,7 +7,7 @@ from trezor.wire import DataError
|
|||||||
|
|
||||||
from apps.ethereum import staking_tx_constants as constants
|
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
|
from .keychain import with_keychain_from_chain_id
|
||||||
|
|
||||||
if TYPE_CHECKING:
|
if TYPE_CHECKING:
|
||||||
@ -21,6 +21,7 @@ if TYPE_CHECKING:
|
|||||||
)
|
)
|
||||||
|
|
||||||
from apps.common.keychain import Keychain
|
from apps.common.keychain import Keychain
|
||||||
|
from apps.common.payment_request import PaymentRequestVerifier
|
||||||
|
|
||||||
from .definitions import Definitions
|
from .definitions import Definitions
|
||||||
from .keychain import MsgInSignTx
|
from .keychain import MsgInSignTx
|
||||||
@ -67,7 +68,25 @@ async def sign_tx(
|
|||||||
gas_limit,
|
gas_limit,
|
||||||
defs.network,
|
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 = progress(title=TR.progress__signing_transaction)
|
||||||
progress_obj.report(30)
|
progress_obj.report(30)
|
||||||
@ -121,6 +140,7 @@ async def confirm_tx_data(
|
|||||||
maximum_fee: str,
|
maximum_fee: str,
|
||||||
fee_items: Iterable[tuple[str, str]],
|
fee_items: Iterable[tuple[str, str]],
|
||||||
data_total_len: int,
|
data_total_len: int,
|
||||||
|
payment_req_verifier: PaymentRequestVerifier | None,
|
||||||
) -> None:
|
) -> None:
|
||||||
# function distinguishes between staking / smart contracts / regular transactions
|
# function distinguishes between staking / smart contracts / regular transactions
|
||||||
from .layout import require_confirm_other_data, require_confirm_tx
|
from .layout import require_confirm_other_data, require_confirm_tx
|
||||||
@ -131,13 +151,21 @@ async def confirm_tx_data(
|
|||||||
# Handle ERC-20, currently only 'transfer' function
|
# Handle ERC-20, currently only 'transfer' function
|
||||||
token, recipient, value = await _handle_erc20_transfer(msg, defs, address_bytes)
|
token, recipient, value = await _handle_erc20_transfer(msg, defs, address_bytes)
|
||||||
|
|
||||||
|
recipient_str = address_from_bytes(recipient, defs.network) if recipient else None
|
||||||
|
if payment_req_verifier is not None:
|
||||||
|
# If a payment_req_verifier is provided, then msg.payment_req must have been set.
|
||||||
|
assert msg.payment_req is not None
|
||||||
|
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
|
is_contract_interaction = token is None and data_total_len > 0
|
||||||
|
|
||||||
if is_contract_interaction:
|
if is_contract_interaction:
|
||||||
await require_confirm_other_data(msg.data_initial_chunk, data_total_len)
|
await require_confirm_other_data(msg.data_initial_chunk, data_total_len)
|
||||||
|
|
||||||
await require_confirm_tx(
|
await require_confirm_tx(
|
||||||
recipient,
|
recipient_str,
|
||||||
value,
|
value,
|
||||||
msg.address_n,
|
msg.address_n,
|
||||||
maximum_fee,
|
maximum_fee,
|
||||||
|
@ -69,7 +69,25 @@ async def sign_tx_eip1559(
|
|||||||
gas_limit,
|
gas_limit,
|
||||||
defs.network,
|
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
|
# transaction data confirmed, proceed with signing
|
||||||
data = bytearray()
|
data = bytearray()
|
||||||
|
@ -208,6 +208,7 @@ def sign_tx(
|
|||||||
tx_type: Optional[int] = None,
|
tx_type: Optional[int] = None,
|
||||||
definitions: Optional[messages.EthereumDefinitions] = None,
|
definitions: Optional[messages.EthereumDefinitions] = None,
|
||||||
chunkify: bool = False,
|
chunkify: bool = False,
|
||||||
|
payment_req: Optional[messages.PaymentRequest] = None,
|
||||||
) -> Tuple[int, bytes, bytes]:
|
) -> Tuple[int, bytes, bytes]:
|
||||||
if chain_id is None:
|
if chain_id is None:
|
||||||
raise exceptions.TrezorException("Chain ID cannot be undefined")
|
raise exceptions.TrezorException("Chain ID cannot be undefined")
|
||||||
@ -223,6 +224,7 @@ def sign_tx(
|
|||||||
tx_type=tx_type,
|
tx_type=tx_type,
|
||||||
definitions=definitions,
|
definitions=definitions,
|
||||||
chunkify=chunkify,
|
chunkify=chunkify,
|
||||||
|
payment_req=payment_req,
|
||||||
)
|
)
|
||||||
|
|
||||||
if data is None:
|
if data is None:
|
||||||
@ -269,6 +271,7 @@ def sign_tx_eip1559(
|
|||||||
access_list: Optional[List[messages.EthereumAccessList]] = None,
|
access_list: Optional[List[messages.EthereumAccessList]] = None,
|
||||||
definitions: Optional[messages.EthereumDefinitions] = None,
|
definitions: Optional[messages.EthereumDefinitions] = None,
|
||||||
chunkify: bool = False,
|
chunkify: bool = False,
|
||||||
|
payment_req: Optional[messages.PaymentRequest] = None,
|
||||||
) -> Tuple[int, bytes, bytes]:
|
) -> Tuple[int, bytes, bytes]:
|
||||||
length = len(data)
|
length = len(data)
|
||||||
data, chunk = data[1024:], data[:1024]
|
data, chunk = data[1024:], data[:1024]
|
||||||
@ -286,6 +289,7 @@ def sign_tx_eip1559(
|
|||||||
data_initial_chunk=chunk,
|
data_initial_chunk=chunk,
|
||||||
definitions=definitions,
|
definitions=definitions,
|
||||||
chunkify=chunkify,
|
chunkify=chunkify,
|
||||||
|
payment_req=payment_req,
|
||||||
)
|
)
|
||||||
|
|
||||||
response = client.call(msg)
|
response = client.call(msg)
|
||||||
|
Loading…
Reference in New Issue
Block a user