From 72e26947c341ecdfcec3ed68dfad41469d4c6f1f Mon Sep 17 00:00:00 2001 From: Alexandre Paillier Date: Fri, 8 Mar 2024 14:36:10 +0100 Subject: [PATCH 1/5] Fix blind-signing TX refusal Would refuse the APDU but then start a empty signature flow on the device Which would crash the device when accepted or rejected --- src_features/signTx/logic_signTx.c | 24 +++++++++++++----------- 1 file changed, 13 insertions(+), 11 deletions(-) diff --git a/src_features/signTx/logic_signTx.c b/src_features/signTx/logic_signTx.c index b1ca0654a..bdacd7684 100644 --- a/src_features/signTx/logic_signTx.c +++ b/src_features/signTx/logic_signTx.c @@ -316,15 +316,13 @@ static int strcasecmp_workaround(const char *str1, const char *str2) { return 0; } -__attribute__((noinline)) static void finalize_parsing_helper(bool direct, bool *use_standard_UI) { +__attribute__((noinline)) static bool finalize_parsing_helper(bool direct, bool *use_standard_UI) { char displayBuffer[50]; uint8_t decimals = WEI_TO_ETHER; uint64_t chain_id = get_tx_chain_id(); const char *ticker = get_displayable_ticker(&chain_id, chainConfig); ethPluginFinalize_t pluginFinalize; - *use_standard_UI = true; - // Verify the chain if (chainConfig->chainId != ETHEREUM_MAINNET_CHAINID) { uint64_t id = get_tx_chain_id(); @@ -334,7 +332,7 @@ __attribute__((noinline)) static void finalize_parsing_helper(bool direct, bool reset_app_context(); reportFinalizeError(direct); if (!direct) { - return; + return false; } } } @@ -358,7 +356,7 @@ __attribute__((noinline)) static void finalize_parsing_helper(bool direct, bool PRINTF("Plugin finalize call failed\n"); reportFinalizeError(direct); if (!direct) { - return; + return false; } } // Lookup tokens if requested @@ -384,7 +382,7 @@ __attribute__((noinline)) static void finalize_parsing_helper(bool direct, bool PRINTF("Plugin provide token call failed\n"); reportFinalizeError(direct); if (!direct) { - return; + return false; } } pluginFinalize.result = pluginProvideInfo.result; @@ -409,7 +407,7 @@ __attribute__((noinline)) static void finalize_parsing_helper(bool direct, bool PRINTF("Incorrect amount/address set by plugin\n"); reportFinalizeError(direct); if (!direct) { - return; + return false; } } memmove(tmpContent.txContent.value.value, pluginFinalize.amount, 32); @@ -425,7 +423,7 @@ __attribute__((noinline)) static void finalize_parsing_helper(bool direct, bool PRINTF("ui type %d not supported\n", pluginFinalize.uiType); reportFinalizeError(direct); if (!direct) { - return; + return false; } } } @@ -450,7 +448,7 @@ __attribute__((noinline)) static void finalize_parsing_helper(bool direct, bool reportFinalizeError(direct); ui_warning_contract_data(); if (!direct) { - return; + return false; } } @@ -530,12 +528,16 @@ __attribute__((noinline)) static void finalize_parsing_helper(bool direct, bool // Prepare network field get_network_as_string(strings.common.network_name, sizeof(strings.common.network_name)); PRINTF("Network: %s\n", strings.common.network_name); + return true; } void finalizeParsing(bool direct) { - bool use_standard_UI; + bool use_standard_UI = true; bool no_consent_check; - finalize_parsing_helper(direct, &use_standard_UI); + + if (!finalize_parsing_helper(direct, &use_standard_UI)) { + return; + } // If called from swap, the user has already validated a standard transaction // And we have already checked the fields of this transaction above no_consent_check = G_called_from_swap && use_standard_UI; From 5715827addbbe98e5d71772949c24febf43be8b0 Mon Sep 17 00:00:00 2001 From: Alexandre Paillier Date: Fri, 8 Mar 2024 17:39:18 +0100 Subject: [PATCH 2/5] New basic signature (+ verification) ragger tests --- tests/ragger/test_sign.py | 67 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 67 insertions(+) create mode 100644 tests/ragger/test_sign.py diff --git a/tests/ragger/test_sign.py b/tests/ragger/test_sign.py new file mode 100644 index 000000000..401be19a0 --- /dev/null +++ b/tests/ragger/test_sign.py @@ -0,0 +1,67 @@ +from ragger.backend import BackendInterface +from ragger.firmware import Firmware +from ragger.navigator import Navigator, NavInsID +from ledger_app_clients.ethereum.client import EthAppClient +import ledger_app_clients.ethereum.response_parser as ResponseParser +from ledger_app_clients.ethereum.utils import recover_transaction +from web3 import Web3 + + +# Values used across all tests +CHAIN_ID = 1 +ADDR = bytes.fromhex("0011223344556677889900112233445566778899") +BIP32_PATH = "m/44'/60'/0'/0/0" +NONCE = 21 +GAS_PRICE = 13 +GAS_LIMIT = 21000 +AMOUNT = 1.22 + + +def common(fw: Firmware, + back: BackendInterface, + nav: Navigator, + tx_params: dict): + app_client = EthAppClient(back) + + with app_client.get_public_addr(display=False): + pass + _, DEVICE_ADDR, _ = ResponseParser.pk_addr(app_client.response().data) + + with app_client.sign(BIP32_PATH, tx_params): + if fw.device.startswith("nano"): + next_action = NavInsID.RIGHT_CLICK + confirm_action = NavInsID.BOTH_CLICK + end_text = "Accept" + else: + next_action = NavInsID.USE_CASE_REVIEW_TAP + confirm_action = NavInsID.USE_CASE_REVIEW_CONFIRM + end_text = "Sign" + nav.navigate_until_text(next_action, [confirm_action], end_text) + + # verify signature + vrs = ResponseParser.signature(app_client.response().data) + addr = recover_transaction(tx_params, vrs) + assert addr == DEVICE_ADDR + + +def test_legacy(firmware: Firmware, backend: BackendInterface, navigator: Navigator): + common(firmware, backend, navigator, { + "nonce": NONCE, + "gasPrice": Web3.to_wei(GAS_PRICE, "gwei"), + "gas": GAS_LIMIT, + "to": ADDR, + "value": Web3.to_wei(AMOUNT, "ether"), + "chainId": CHAIN_ID + }) + + +def test_1559(firmware: Firmware, backend: BackendInterface, navigator: Navigator): + common(firmware, backend, navigator, { + "nonce": NONCE, + "maxFeePerGas": Web3.to_wei(145, "gwei"), + "maxPriorityFeePerGas": Web3.to_wei(1.5, "gwei"), + "gas": GAS_LIMIT, + "to": ADDR, + "value": Web3.to_wei(AMOUNT, "ether"), + "chainId": CHAIN_ID + }) From 6414890b2f3516c15632cd0a4c3b955e85f8e701 Mon Sep 17 00:00:00 2001 From: Alexandre Paillier Date: Fri, 8 Mar 2024 18:00:28 +0100 Subject: [PATCH 3/5] Added ERC-20 ABI & fixed indentation on other ABIs --- tests/ragger/abis/erc1155.json | 548 ++++++++++++++++----------------- tests/ragger/abis/erc20.json | 135 ++++++++ tests/ragger/abis/erc721.json | 532 ++++++++++++++++---------------- 3 files changed, 675 insertions(+), 540 deletions(-) create mode 100644 tests/ragger/abis/erc20.json diff --git a/tests/ragger/abis/erc1155.json b/tests/ragger/abis/erc1155.json index 3c53ad8c2..6f8e6ab25 100644 --- a/tests/ragger/abis/erc1155.json +++ b/tests/ragger/abis/erc1155.json @@ -1,276 +1,276 @@ [ - { - "anonymous" : false, - "inputs" : [ - { - "indexed" : true, - "internalType" : "address", - "name" : "_owner", - "type" : "address" - }, - { - "indexed" : true, - "internalType" : "address", - "name" : "_operator", - "type" : "address" - }, - { - "indexed" : false, - "internalType" : "bool", - "name" : "_approved", - "type" : "bool" - } - ], - "name" : "ApprovalForAll", - "type" : "event" - }, - { - "anonymous" : false, - "inputs" : [ - { - "indexed" : true, - "internalType" : "address", - "name" : "_operator", - "type" : "address" - }, - { - "indexed" : true, - "internalType" : "address", - "name" : "_from", - "type" : "address" - }, - { - "indexed" : true, - "internalType" : "address", - "name" : "_to", - "type" : "address" - }, - { - "indexed" : false, - "internalType" : "uint256[]", - "name" : "_ids", - "type" : "uint256[]" - }, - { - "indexed" : false, - "internalType" : "uint256[]", - "name" : "_values", - "type" : "uint256[]" - } - ], - "name" : "TransferBatch", - "type" : "event" - }, - { - "anonymous" : false, - "inputs" : [ - { - "indexed" : true, - "internalType" : "address", - "name" : "_operator", - "type" : "address" - }, - { - "indexed" : true, - "internalType" : "address", - "name" : "_from", - "type" : "address" - }, - { - "indexed" : true, - "internalType" : "address", - "name" : "_to", - "type" : "address" - }, - { - "indexed" : false, - "internalType" : "uint256", - "name" : "_id", - "type" : "uint256" - }, - { - "indexed" : false, - "internalType" : "uint256", - "name" : "_value", - "type" : "uint256" - } - ], - "name" : "TransferSingle", - "type" : "event" - }, - { - "anonymous" : false, - "inputs" : [ - { - "indexed" : false, - "internalType" : "string", - "name" : "_value", - "type" : "string" - }, - { - "indexed" : true, - "internalType" : "uint256", - "name" : "_id", - "type" : "uint256" - } - ], - "name" : "URI", - "type" : "event" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_owner", - "type" : "address" - }, - { - "internalType" : "uint256", - "name" : "_id", - "type" : "uint256" - } - ], - "name" : "balanceOf", - "outputs" : [ - { - "internalType" : "uint256", - "name" : "", - "type" : "uint256" - } - ], - "stateMutability" : "view", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "address[]", - "name" : "_owners", - "type" : "address[]" - }, - { - "internalType" : "uint256[]", - "name" : "_ids", - "type" : "uint256[]" - } - ], - "name" : "balanceOfBatch", - "outputs" : [ - { - "internalType" : "uint256[]", - "name" : "", - "type" : "uint256[]" - } - ], - "stateMutability" : "view", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_owner", - "type" : "address" - }, - { - "internalType" : "address", - "name" : "_operator", - "type" : "address" - } - ], - "name" : "isApprovedForAll", - "outputs" : [ - { - "internalType" : "bool", - "name" : "", - "type" : "bool" - } - ], - "stateMutability" : "view", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_from", - "type" : "address" - }, - { - "internalType" : "address", - "name" : "_to", - "type" : "address" - }, - { - "internalType" : "uint256[]", - "name" : "_ids", - "type" : "uint256[]" - }, - { - "internalType" : "uint256[]", - "name" : "_values", - "type" : "uint256[]" - }, - { - "internalType" : "bytes", - "name" : "_data", - "type" : "bytes" - } - ], - "name" : "safeBatchTransferFrom", - "outputs" : [], - "stateMutability" : "nonpayable", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_from", - "type" : "address" - }, - { - "internalType" : "address", - "name" : "_to", - "type" : "address" - }, - { - "internalType" : "uint256", - "name" : "_id", - "type" : "uint256" - }, - { - "internalType" : "uint256", - "name" : "_value", - "type" : "uint256" - }, - { - "internalType" : "bytes", - "name" : "_data", - "type" : "bytes" - } - ], - "name" : "safeTransferFrom", - "outputs" : [], - "stateMutability" : "nonpayable", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_operator", - "type" : "address" - }, - { - "internalType" : "bool", - "name" : "_approved", - "type" : "bool" - } - ], - "name" : "setApprovalForAll", - "outputs" : [], - "stateMutability" : "nonpayable", - "type" : "function" - } + { + "anonymous" : false, + "inputs" : [ + { + "indexed" : true, + "internalType" : "address", + "name" : "_owner", + "type" : "address" + }, + { + "indexed" : true, + "internalType" : "address", + "name" : "_operator", + "type" : "address" + }, + { + "indexed" : false, + "internalType" : "bool", + "name" : "_approved", + "type" : "bool" + } + ], + "name" : "ApprovalForAll", + "type" : "event" + }, + { + "anonymous" : false, + "inputs" : [ + { + "indexed" : true, + "internalType" : "address", + "name" : "_operator", + "type" : "address" + }, + { + "indexed" : true, + "internalType" : "address", + "name" : "_from", + "type" : "address" + }, + { + "indexed" : true, + "internalType" : "address", + "name" : "_to", + "type" : "address" + }, + { + "indexed" : false, + "internalType" : "uint256[]", + "name" : "_ids", + "type" : "uint256[]" + }, + { + "indexed" : false, + "internalType" : "uint256[]", + "name" : "_values", + "type" : "uint256[]" + } + ], + "name" : "TransferBatch", + "type" : "event" + }, + { + "anonymous" : false, + "inputs" : [ + { + "indexed" : true, + "internalType" : "address", + "name" : "_operator", + "type" : "address" + }, + { + "indexed" : true, + "internalType" : "address", + "name" : "_from", + "type" : "address" + }, + { + "indexed" : true, + "internalType" : "address", + "name" : "_to", + "type" : "address" + }, + { + "indexed" : false, + "internalType" : "uint256", + "name" : "_id", + "type" : "uint256" + }, + { + "indexed" : false, + "internalType" : "uint256", + "name" : "_value", + "type" : "uint256" + } + ], + "name" : "TransferSingle", + "type" : "event" + }, + { + "anonymous" : false, + "inputs" : [ + { + "indexed" : false, + "internalType" : "string", + "name" : "_value", + "type" : "string" + }, + { + "indexed" : true, + "internalType" : "uint256", + "name" : "_id", + "type" : "uint256" + } + ], + "name" : "URI", + "type" : "event" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_owner", + "type" : "address" + }, + { + "internalType" : "uint256", + "name" : "_id", + "type" : "uint256" + } + ], + "name" : "balanceOf", + "outputs" : [ + { + "internalType" : "uint256", + "name" : "", + "type" : "uint256" + } + ], + "stateMutability" : "view", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address[]", + "name" : "_owners", + "type" : "address[]" + }, + { + "internalType" : "uint256[]", + "name" : "_ids", + "type" : "uint256[]" + } + ], + "name" : "balanceOfBatch", + "outputs" : [ + { + "internalType" : "uint256[]", + "name" : "", + "type" : "uint256[]" + } + ], + "stateMutability" : "view", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_owner", + "type" : "address" + }, + { + "internalType" : "address", + "name" : "_operator", + "type" : "address" + } + ], + "name" : "isApprovedForAll", + "outputs" : [ + { + "internalType" : "bool", + "name" : "", + "type" : "bool" + } + ], + "stateMutability" : "view", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_from", + "type" : "address" + }, + { + "internalType" : "address", + "name" : "_to", + "type" : "address" + }, + { + "internalType" : "uint256[]", + "name" : "_ids", + "type" : "uint256[]" + }, + { + "internalType" : "uint256[]", + "name" : "_values", + "type" : "uint256[]" + }, + { + "internalType" : "bytes", + "name" : "_data", + "type" : "bytes" + } + ], + "name" : "safeBatchTransferFrom", + "outputs" : [], + "stateMutability" : "nonpayable", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_from", + "type" : "address" + }, + { + "internalType" : "address", + "name" : "_to", + "type" : "address" + }, + { + "internalType" : "uint256", + "name" : "_id", + "type" : "uint256" + }, + { + "internalType" : "uint256", + "name" : "_value", + "type" : "uint256" + }, + { + "internalType" : "bytes", + "name" : "_data", + "type" : "bytes" + } + ], + "name" : "safeTransferFrom", + "outputs" : [], + "stateMutability" : "nonpayable", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_operator", + "type" : "address" + }, + { + "internalType" : "bool", + "name" : "_approved", + "type" : "bool" + } + ], + "name" : "setApprovalForAll", + "outputs" : [], + "stateMutability" : "nonpayable", + "type" : "function" + } ] diff --git a/tests/ragger/abis/erc20.json b/tests/ragger/abis/erc20.json new file mode 100644 index 000000000..301b94656 --- /dev/null +++ b/tests/ragger/abis/erc20.json @@ -0,0 +1,135 @@ +[ + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_owner", + "type" : "address" + }, + { + "internalType" : "address", + "name" : "_spender", + "type" : "address" + } + ], + "name" : "allowance", + "outputs" : [ + { + "internalType" : "uint256", + "name" : "remaining", + "type" : "uint256" + } + ], + "stateMutability" : "view", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_spender", + "type" : "address" + }, + { + "internalType" : "uint256", + "name" : "_value", + "type" : "uint256" + } + ], + "name" : "approve", + "outputs" : [ + { + "internalType" : "bool", + "name" : "success", + "type" : "bool" + } + ], + "stateMutability" : "nonpayable", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_owner", + "type" : "address" + } + ], + "name" : "balanceOf", + "outputs" : [ + { + "internalType" : "uint256", + "name" : "balance", + "type" : "uint256" + } + ], + "stateMutability" : "view", + "type" : "function" + }, + { + "inputs" : [], + "name" : "totalSupply", + "outputs" : [ + { + "internalType" : "uint256", + "name" : "", + "type" : "uint256" + } + ], + "stateMutability" : "view", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_to", + "type" : "address" + }, + { + "internalType" : "uint256", + "name" : "_value", + "type" : "uint256" + } + ], + "name" : "transfer", + "outputs" : [ + { + "internalType" : "bool", + "name" : "success", + "type" : "bool" + } + ], + "stateMutability" : "nonpayable", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_from", + "type" : "address" + }, + { + "internalType" : "address", + "name" : "_to", + "type" : "address" + }, + { + "internalType" : "uint256", + "name" : "_value", + "type" : "uint256" + } + ], + "name" : "transferFrom", + "outputs" : [ + { + "internalType" : "bool", + "name" : "success", + "type" : "bool" + } + ], + "stateMutability" : "nonpayable", + "type" : "function" + } +] diff --git a/tests/ragger/abis/erc721.json b/tests/ragger/abis/erc721.json index e00d5ca3f..b6f583563 100644 --- a/tests/ragger/abis/erc721.json +++ b/tests/ragger/abis/erc721.json @@ -1,268 +1,268 @@ [ - { - "anonymous" : false, - "inputs" : [ - { - "indexed" : true, - "internalType" : "address", - "name" : "_owner", - "type" : "address" - }, - { - "indexed" : true, - "internalType" : "address", - "name" : "_approved", - "type" : "address" - }, - { - "indexed" : true, - "internalType" : "uint256", - "name" : "_tokenId", - "type" : "uint256" - } - ], - "name" : "Approval", - "type" : "event" - }, - { - "anonymous" : false, - "inputs" : [ - { - "indexed" : true, - "internalType" : "address", - "name" : "_owner", - "type" : "address" - }, - { - "indexed" : true, - "internalType" : "address", - "name" : "_operator", - "type" : "address" - }, - { - "indexed" : false, - "internalType" : "bool", - "name" : "_approved", - "type" : "bool" - } - ], - "name" : "ApprovalForAll", - "type" : "event" - }, - { - "anonymous" : false, - "inputs" : [ - { - "indexed" : true, - "internalType" : "address", - "name" : "_from", - "type" : "address" - }, - { - "indexed" : true, - "internalType" : "address", - "name" : "_to", - "type" : "address" - }, - { - "indexed" : true, - "internalType" : "uint256", - "name" : "_tokenId", - "type" : "uint256" - } - ], - "name" : "Transfer", - "type" : "event" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_approved", - "type" : "address" - }, - { - "internalType" : "uint256", - "name" : "_tokenId", - "type" : "uint256" - } - ], - "name" : "approve", - "outputs" : [], - "stateMutability" : "payable", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_owner", - "type" : "address" - } - ], - "name" : "balanceOf", - "outputs" : [ - { - "internalType" : "uint256", - "name" : "", - "type" : "uint256" - } - ], - "stateMutability" : "view", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "uint256", - "name" : "_tokenId", - "type" : "uint256" - } - ], - "name" : "getApproved", - "outputs" : [ - { - "internalType" : "address", - "name" : "", - "type" : "address" - } - ], - "stateMutability" : "view", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_owner", - "type" : "address" - }, - { - "internalType" : "address", - "name" : "_operator", - "type" : "address" - } - ], - "name" : "isApprovedForAll", - "outputs" : [ - { - "internalType" : "bool", - "name" : "", - "type" : "bool" - } - ], - "stateMutability" : "view", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "uint256", - "name" : "_tokenId", - "type" : "uint256" - } - ], - "name" : "ownerOf", - "outputs" : [ - { - "internalType" : "address", - "name" : "", - "type" : "address" - } - ], - "stateMutability" : "view", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_from", - "type" : "address" - }, - { - "internalType" : "address", - "name" : "_to", - "type" : "address" - }, - { - "internalType" : "uint256", - "name" : "_tokenId", - "type" : "uint256" - } - ], - "name" : "safeTransferFrom", - "outputs" : [], - "stateMutability" : "payable", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_from", - "type" : "address" - }, - { - "internalType" : "address", - "name" : "_to", - "type" : "address" - }, - { - "internalType" : "uint256", - "name" : "_tokenId", - "type" : "uint256" - }, - { - "internalType" : "bytes", - "name" : "data", - "type" : "bytes" - } - ], - "name" : "safeTransferFrom", - "outputs" : [], - "stateMutability" : "payable", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_operator", - "type" : "address" - }, - { - "internalType" : "bool", - "name" : "_approved", - "type" : "bool" - } - ], - "name" : "setApprovalForAll", - "outputs" : [], - "stateMutability" : "nonpayable", - "type" : "function" - }, - { - "inputs" : [ - { - "internalType" : "address", - "name" : "_from", - "type" : "address" - }, - { - "internalType" : "address", - "name" : "_to", - "type" : "address" - }, - { - "internalType" : "uint256", - "name" : "_tokenId", - "type" : "uint256" - } - ], - "name" : "transferFrom", - "outputs" : [], - "stateMutability" : "payable", - "type" : "function" - } + { + "anonymous" : false, + "inputs" : [ + { + "indexed" : true, + "internalType" : "address", + "name" : "_owner", + "type" : "address" + }, + { + "indexed" : true, + "internalType" : "address", + "name" : "_approved", + "type" : "address" + }, + { + "indexed" : true, + "internalType" : "uint256", + "name" : "_tokenId", + "type" : "uint256" + } + ], + "name" : "Approval", + "type" : "event" + }, + { + "anonymous" : false, + "inputs" : [ + { + "indexed" : true, + "internalType" : "address", + "name" : "_owner", + "type" : "address" + }, + { + "indexed" : true, + "internalType" : "address", + "name" : "_operator", + "type" : "address" + }, + { + "indexed" : false, + "internalType" : "bool", + "name" : "_approved", + "type" : "bool" + } + ], + "name" : "ApprovalForAll", + "type" : "event" + }, + { + "anonymous" : false, + "inputs" : [ + { + "indexed" : true, + "internalType" : "address", + "name" : "_from", + "type" : "address" + }, + { + "indexed" : true, + "internalType" : "address", + "name" : "_to", + "type" : "address" + }, + { + "indexed" : true, + "internalType" : "uint256", + "name" : "_tokenId", + "type" : "uint256" + } + ], + "name" : "Transfer", + "type" : "event" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_approved", + "type" : "address" + }, + { + "internalType" : "uint256", + "name" : "_tokenId", + "type" : "uint256" + } + ], + "name" : "approve", + "outputs" : [], + "stateMutability" : "payable", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_owner", + "type" : "address" + } + ], + "name" : "balanceOf", + "outputs" : [ + { + "internalType" : "uint256", + "name" : "", + "type" : "uint256" + } + ], + "stateMutability" : "view", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "uint256", + "name" : "_tokenId", + "type" : "uint256" + } + ], + "name" : "getApproved", + "outputs" : [ + { + "internalType" : "address", + "name" : "", + "type" : "address" + } + ], + "stateMutability" : "view", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_owner", + "type" : "address" + }, + { + "internalType" : "address", + "name" : "_operator", + "type" : "address" + } + ], + "name" : "isApprovedForAll", + "outputs" : [ + { + "internalType" : "bool", + "name" : "", + "type" : "bool" + } + ], + "stateMutability" : "view", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "uint256", + "name" : "_tokenId", + "type" : "uint256" + } + ], + "name" : "ownerOf", + "outputs" : [ + { + "internalType" : "address", + "name" : "", + "type" : "address" + } + ], + "stateMutability" : "view", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_from", + "type" : "address" + }, + { + "internalType" : "address", + "name" : "_to", + "type" : "address" + }, + { + "internalType" : "uint256", + "name" : "_tokenId", + "type" : "uint256" + } + ], + "name" : "safeTransferFrom", + "outputs" : [], + "stateMutability" : "payable", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_from", + "type" : "address" + }, + { + "internalType" : "address", + "name" : "_to", + "type" : "address" + }, + { + "internalType" : "uint256", + "name" : "_tokenId", + "type" : "uint256" + }, + { + "internalType" : "bytes", + "name" : "data", + "type" : "bytes" + } + ], + "name" : "safeTransferFrom", + "outputs" : [], + "stateMutability" : "payable", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_operator", + "type" : "address" + }, + { + "internalType" : "bool", + "name" : "_approved", + "type" : "bool" + } + ], + "name" : "setApprovalForAll", + "outputs" : [], + "stateMutability" : "nonpayable", + "type" : "function" + }, + { + "inputs" : [ + { + "internalType" : "address", + "name" : "_from", + "type" : "address" + }, + { + "internalType" : "address", + "name" : "_to", + "type" : "address" + }, + { + "internalType" : "uint256", + "name" : "_tokenId", + "type" : "uint256" + } + ], + "name" : "transferFrom", + "outputs" : [], + "stateMutability" : "payable", + "type" : "function" + } ] From c193362d56053ab2a815772b7496b0f82dc7aab5 Mon Sep 17 00:00:00 2001 From: Alexandre Paillier Date: Fri, 8 Mar 2024 17:47:55 +0100 Subject: [PATCH 4/5] New blind-sign ragger test --- tests/ragger/constants.py | 2 + .../nanos/blind-signed_approval/00000.png | Bin 0 -> 428 bytes .../nanos/blind-signed_approval/00001.png | Bin 0 -> 419 bytes .../nanos/blind-signed_approval/00002.png | Bin 0 -> 349 bytes .../nanosp/blind-signed_approval/00000.png | Bin 0 -> 587 bytes .../nanosp/blind-signed_approval/00001.png | Bin 0 -> 381 bytes .../nanox/blind-signed_approval/00000.png | Bin 0 -> 587 bytes .../nanox/blind-signed_approval/00001.png | Bin 0 -> 381 bytes .../stax/blind-signed_approval/00000.png | Bin 0 -> 13105 bytes .../stax/blind-signed_approval/00001.png | Bin 0 -> 10883 bytes tests/ragger/test_blind_sign.py | 55 ++++++++++++++++++ tests/ragger/test_nft.py | 5 +- 12 files changed, 58 insertions(+), 4 deletions(-) create mode 100644 tests/ragger/snapshots/nanos/blind-signed_approval/00000.png create mode 100644 tests/ragger/snapshots/nanos/blind-signed_approval/00001.png create mode 100644 tests/ragger/snapshots/nanos/blind-signed_approval/00002.png create mode 100644 tests/ragger/snapshots/nanosp/blind-signed_approval/00000.png create mode 100644 tests/ragger/snapshots/nanosp/blind-signed_approval/00001.png create mode 100644 tests/ragger/snapshots/nanox/blind-signed_approval/00000.png create mode 100644 tests/ragger/snapshots/nanox/blind-signed_approval/00001.png create mode 100644 tests/ragger/snapshots/stax/blind-signed_approval/00000.png create mode 100644 tests/ragger/snapshots/stax/blind-signed_approval/00001.png create mode 100644 tests/ragger/test_blind_sign.py diff --git a/tests/ragger/constants.py b/tests/ragger/constants.py index 86b6304ee..0f375a71f 100644 --- a/tests/ragger/constants.py +++ b/tests/ragger/constants.py @@ -1,3 +1,5 @@ from pathlib import Path +import os ROOT_SNAPSHOT_PATH = Path(__file__).parent +ABIS_FOLDER = "%s/abis" % (os.path.dirname(__file__)) diff --git a/tests/ragger/snapshots/nanos/blind-signed_approval/00000.png b/tests/ragger/snapshots/nanos/blind-signed_approval/00000.png new file mode 100644 index 0000000000000000000000000000000000000000..c2420afe1d5b2ea19c999ee43f90c67f120d4f5b GIT binary patch literal 428 zcmV;d0aN~oP)CI>TUk!C8`c(mGx8WRa z!xd`|I)kHai-|mfH_EU=@WQ<8?vt;iutXgsJ7fsT#RT=*@-kDbFv|(3aIfXRyfj@+?msfv|9!ih8`J$fW)Vn zz~CO>;T|BN_mLd%e%vjPJ%D;eMaiRY#At6&Lsw*_J&nWB{N+Jii(`R~LM#+7vH7^1 zF{YKPgOW#*A8m0f)G#fTs8dpVu7-&qzkS-3oiTU-^*<9k78P5Y>WHD!W4f~aS-%if z=ZR@VlnSwV`CZM!$c^HXr@$^f3+e?K9T@e1AEk+s4NtSE;t^;oLOod9f%9u_+g!V> zg-|*Hr>)vEHnNj9aru-OX(LJU#UxzW#2tv5bk|2oN7xMoGovT4Cs$JRS3(FO58w+7 Wi7X{&VtL~L0000&Y zgBND@G|SJC_g~fqbc0^sIaWU`>wufAelSi!%!3qtam)=vPiZv&K!Fpv#O{SmfokLJ zp87upO%wsYQqK)YLE>ZPF2NT+9(#mV<19*cgK44&97!^oMk`-llLWqi3*b+7J6;)f#rg;Z6 zj%lA#1coqYV>KeY%+@-9sUzLLDq<^u`9V=p&V$8RXc!x+7OAG zw)^arJc+=D-0$)sldm|!=|2NF`s5CFA)bPavHM@p0`xf59mjD7@&#R+4xnH^xfuWe N002ovPDHLkV1g%Zy?y`y literal 0 HcmV?d00001 diff --git a/tests/ragger/snapshots/nanos/blind-signed_approval/00002.png b/tests/ragger/snapshots/nanos/blind-signed_approval/00002.png new file mode 100644 index 0000000000000000000000000000000000000000..ce795f34e8569e986af689fded3b59c9a8af2961 GIT binary patch literal 349 zcmV-j0iyniP)O41}p;-~WL<=z+0=1Om1tEU@3H#qtw22}5*_5JCvCo4!52c$FXo$VhXU?0M$^Bekqgf%Ka;M*^X|4 zEs9YCQ(xfJKmNC#+8dY%2&wT+>D^<3C%}_*k1^mvtO~`RE00000NkvXXu0mjf-kqOA literal 0 HcmV?d00001 diff --git a/tests/ragger/snapshots/nanosp/blind-signed_approval/00000.png b/tests/ragger/snapshots/nanosp/blind-signed_approval/00000.png new file mode 100644 index 0000000000000000000000000000000000000000..11ea8a56bc60bd449386bb9fca08e76fedf58e0e GIT binary patch literal 587 zcmV-R0<`^!P)S}D{b#1o0q#G`|wuQS5382)wtbsZ$x!T z8b7$9HnG=lzlVLFx<${P6!qgz(YnI4qx6{=X_;q@`%ClIMm7U(NG4Lm_Q&#J1ZZ3e zyXyH$BR&LW=)3%m+QHAV#7M(%)%mQ=lVY6Ov82SGvAkBByJ8GzOnN}LRoi1@c3Sd@ zL)eHhZS?cAU9F$w-_DX#Mxd#s0eK$qpLo}IL8C3j{YD5OgsdbZV@<^j`&rM9)YB+7 zYZH)Z)TncR&?8brFCy+mswCOpR2L`emdEhH)?%IhOMz3CwxUy->rLA(r-*3Ow~Z_@ zEARM~*Qt|!hyA2_K(bE$kty;OzTxY+fMyp-fU^ztj3sY2!02En$sw;X-IP*99945Y ztDBzg0sh&>qbwR`mngtaky5_P{U4`s1;0 z?{f>9Zfbf|_00eLCwPudd#p2Mzfg8-=Z~Y&(Z3(6-dSPln_e}2 z&8bJe=5=w3_V0Wxpw!uqXV@ zTyg#0l&4R7|Ayyoo}1J3WZRs6lez;p_x-s3`O4ERHjEo5Zk@S4@1z`Oka)v{pj(C~ z>TB;CrkB0D2@>;k^>bP0l+XkKqsFS~ literal 0 HcmV?d00001 diff --git a/tests/ragger/snapshots/nanox/blind-signed_approval/00000.png b/tests/ragger/snapshots/nanox/blind-signed_approval/00000.png new file mode 100644 index 0000000000000000000000000000000000000000..11ea8a56bc60bd449386bb9fca08e76fedf58e0e GIT binary patch literal 587 zcmV-R0<`^!P)S}D{b#1o0q#G`|wuQS5382)wtbsZ$x!T z8b7$9HnG=lzlVLFx<${P6!qgz(YnI4qx6{=X_;q@`%ClIMm7U(NG4Lm_Q&#J1ZZ3e zyXyH$BR&LW=)3%m+QHAV#7M(%)%mQ=lVY6Ov82SGvAkBByJ8GzOnN}LRoi1@c3Sd@ zL)eHhZS?cAU9F$w-_DX#Mxd#s0eK$qpLo}IL8C3j{YD5OgsdbZV@<^j`&rM9)YB+7 zYZH)Z)TncR&?8brFCy+mswCOpR2L`emdEhH)?%IhOMz3CwxUy->rLA(r-*3Ow~Z_@ zEARM~*Qt|!hyA2_K(bE$kty;OzTxY+fMyp-fU^ztj3sY2!02En$sw;X-IP*99945Y ztDBzg0sh&>qbwR`mngtaky5_P{U4`s1;0 z?{f>9Zfbf|_00eLCwPudd#p2Mzfg8-=Z~Y&(Z3(6-dSPln_e}2 z&8bJe=5=w3_V0Wxpw!uqXV@ zTyg#0l&4R7|Ayyoo}1J3WZRs6lez;p_x-s3`O4ERHjEo5Zk@S4@1z`Oka)v{pj(C~ z>TB;CrkB0D2@>;k^>bP0l+XkKqsFS~ literal 0 HcmV?d00001 diff --git a/tests/ragger/snapshots/stax/blind-signed_approval/00000.png b/tests/ragger/snapshots/stax/blind-signed_approval/00000.png new file mode 100644 index 0000000000000000000000000000000000000000..7c13332b6ebd5b2edae1533c8fbb661eb1ff81b4 GIT binary patch literal 13105 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 literal 0 HcmV?d00001 diff --git a/tests/ragger/snapshots/stax/blind-signed_approval/00001.png b/tests/ragger/snapshots/stax/blind-signed_approval/00001.png new file mode 100644 index 0000000000000000000000000000000000000000..b1ff1b3ab3f4dd6e51e46f9c6e0a2b36b8dd1f7b GIT binary patch literal 10883 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 Ldb{=}?D2mCKHFqS literal 0 HcmV?d00001 diff --git a/tests/ragger/test_blind_sign.py b/tests/ragger/test_blind_sign.py new file mode 100644 index 000000000..a4ed7679c --- /dev/null +++ b/tests/ragger/test_blind_sign.py @@ -0,0 +1,55 @@ +import json +from ragger.backend import BackendInterface +from ragger.firmware import Firmware +from ragger.navigator import Navigator, NavInsID +from ragger.error import ExceptionRAPDU +from ledger_app_clients.ethereum.client import EthAppClient +from web3 import Web3 +from constants import ROOT_SNAPSHOT_PATH, ABIS_FOLDER + + +# Token approval, would require loading the "internal plugin" & +# providing the token metadata from the CAL +def test_blind_sign(firmware: Firmware, + backend: BackendInterface, + navigator: Navigator): + app_client = EthAppClient(backend) + + with open("%s/erc20.json" % (ABIS_FOLDER)) as file: + contract = Web3().eth.contract( + abi=json.load(file), + address=None + ) + data = contract.encodeABI("approve", [ + # Uniswap Protocol: Permit2 + bytes.fromhex("000000000022d473030f116ddee9f6b43ac78ba3"), + Web3.to_wei("2", "ether") + ]) + tx_params = { + "nonce": 235, + "maxFeePerGas": Web3.to_wei(100, "gwei"), + "maxPriorityFeePerGas": Web3.to_wei(10, "gwei"), + "gas": 44001, + # Maker: Dai Stablecoin + "to": bytes.fromhex("6b175474e89094c44da98b954eedeac495271d0f"), + "data": data, + "chainId": 1 + } + try: + with app_client.sign("m/44'/60'/0'/0/0", tx_params): + pass + except ExceptionRAPDU: + pass + else: + assert False + + moves = list() + if firmware.device.startswith("nano"): + if firmware.device == "nanos": + moves += [NavInsID.RIGHT_CLICK] + moves += [NavInsID.BOTH_CLICK] + else: + moves += [NavInsID.USE_CASE_CHOICE_CONFIRM] + navigator.navigate_and_compare(ROOT_SNAPSHOT_PATH, + "blind-signed_approval", + moves) diff --git a/tests/ragger/test_nft.py b/tests/ragger/test_nft.py index 87c1ac0c4..fd3987122 100644 --- a/tests/ragger/test_nft.py +++ b/tests/ragger/test_nft.py @@ -11,12 +11,9 @@ from ledger_app_clients.ethereum.utils import get_selector_from_data, recover_transaction from web3 import Web3 import json -import os -from constants import ROOT_SNAPSHOT_PATH +from constants import ROOT_SNAPSHOT_PATH, ABIS_FOLDER -ABIS_FOLDER = "%s/abis" % (os.path.dirname(__file__)) - BIP32_PATH = "m/44'/60'/0'/0/0" NONCE = 21 GAS_PRICE = 13 From 30067d6f7cd3a239910af7de7fccd65aee363577 Mon Sep 17 00:00:00 2001 From: Alexandre Paillier Date: Fri, 8 Mar 2024 17:51:27 +0100 Subject: [PATCH 5/5] Updated release date in changelog --- CHANGELOG.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 0bfabaaa0..9b3afd163 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,7 +5,7 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](http://keepachangelog.com/) and this project adheres to [Semantic Versioning](http://semver.org/). -## [1.10.4](https://github.com/ledgerhq/app-ethereum/compare/1.10.3...1.10.4) - 2023-02-16 +## [1.10.4](https://github.com/ledgerhq/app-ethereum/compare/1.10.3...1.10.4) - 2023-03-08 ### Added