mirror of
https://github.com/trezor/trezor-firmware.git
synced 2025-05-15 05:18:46 +00:00
legacy/signing: Ask user to confirm custom nLockTime.
This commit is contained in:
parent
146ee7af89
commit
ae71735e62
@ -8,6 +8,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
|
|||||||
|
|
||||||
### Added
|
### Added
|
||||||
- XVG support. [#1165]
|
- XVG support. [#1165]
|
||||||
|
- Ask user to confirm custom nLockTime.
|
||||||
|
|
||||||
### Changed
|
### Changed
|
||||||
- Print inverted question mark for non-printable characters.
|
- Print inverted question mark for non-printable characters.
|
||||||
|
@ -37,6 +37,8 @@
|
|||||||
#include "timer.h"
|
#include "timer.h"
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
|
|
||||||
|
#define LOCKTIME_TIMESTAMP_MIN_VALUE 500000000
|
||||||
|
|
||||||
#if !BITCOIN_ONLY
|
#if !BITCOIN_ONLY
|
||||||
|
|
||||||
static const char *slip44_extras(uint32_t coin_type) {
|
static const char *slip44_extras(uint32_t coin_type) {
|
||||||
@ -450,6 +452,25 @@ void layoutChangeCountOverThreshold(uint32_t change_count) {
|
|||||||
_("Continue?"), NULL);
|
_("Continue?"), NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void layoutConfirmNondefaultLockTime(uint32_t lock_time,
|
||||||
|
bool lock_time_disabled) {
|
||||||
|
if (lock_time_disabled) {
|
||||||
|
layoutDialogSwipe(&bmp_icon_question, _("Cancel"), _("Confirm"), NULL,
|
||||||
|
_("Warning!"), _("Locktime is set but"),
|
||||||
|
_("will have no effect."), NULL, _("Continue?"), NULL);
|
||||||
|
|
||||||
|
} else {
|
||||||
|
char str_locktime[11] = {0};
|
||||||
|
snprintf(str_locktime, sizeof(str_locktime), "%" PRIu32, lock_time);
|
||||||
|
char *str_type = (lock_time < LOCKTIME_TIMESTAMP_MIN_VALUE) ? "blockheight:"
|
||||||
|
: "timestamp:";
|
||||||
|
|
||||||
|
layoutDialogSwipe(&bmp_icon_question, _("Cancel"), _("Confirm"), NULL,
|
||||||
|
_("Locktime for this"), _("transaction is set to"),
|
||||||
|
str_type, str_locktime, _("Continue?"), NULL);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void layoutSignMessage(const uint8_t *msg, uint32_t len) {
|
void layoutSignMessage(const uint8_t *msg, uint32_t len) {
|
||||||
const char **str = NULL;
|
const char **str = NULL;
|
||||||
if (!is_valid_ascii(msg, len)) {
|
if (!is_valid_ascii(msg, len)) {
|
||||||
|
@ -53,6 +53,8 @@ void layoutConfirmTx(const CoinInfo *coin, uint64_t amount_out,
|
|||||||
uint64_t amount_fee);
|
uint64_t amount_fee);
|
||||||
void layoutFeeOverThreshold(const CoinInfo *coin, uint64_t fee);
|
void layoutFeeOverThreshold(const CoinInfo *coin, uint64_t fee);
|
||||||
void layoutChangeCountOverThreshold(uint32_t change_count);
|
void layoutChangeCountOverThreshold(uint32_t change_count);
|
||||||
|
void layoutConfirmNondefaultLockTime(uint32_t lock_time,
|
||||||
|
bool lock_time_disabled);
|
||||||
void layoutSignMessage(const uint8_t *msg, uint32_t len);
|
void layoutSignMessage(const uint8_t *msg, uint32_t len);
|
||||||
void layoutVerifyAddress(const CoinInfo *coin, const char *address);
|
void layoutVerifyAddress(const CoinInfo *coin, const char *address);
|
||||||
void layoutVerifyMessage(const uint8_t *msg, uint32_t len);
|
void layoutVerifyMessage(const uint8_t *msg, uint32_t len);
|
||||||
|
@ -75,6 +75,7 @@ static uint32_t lock_time = 0;
|
|||||||
static uint32_t expiry = 0;
|
static uint32_t expiry = 0;
|
||||||
static uint32_t version_group_id = 0;
|
static uint32_t version_group_id = 0;
|
||||||
static uint32_t timestamp = 0;
|
static uint32_t timestamp = 0;
|
||||||
|
static uint32_t min_sequence = 0;
|
||||||
#if !BITCOIN_ONLY
|
#if !BITCOIN_ONLY
|
||||||
static uint32_t branch_id = 0;
|
static uint32_t branch_id = 0;
|
||||||
#endif
|
#endif
|
||||||
@ -107,6 +108,10 @@ static uint32_t tx_weight;
|
|||||||
/* The maximum number of change-outputs allowed without user confirmation. */
|
/* The maximum number of change-outputs allowed without user confirmation. */
|
||||||
#define MAX_SILENT_CHANGE_COUNT 2
|
#define MAX_SILENT_CHANGE_COUNT 2
|
||||||
|
|
||||||
|
/* Setting nSequence to this value for every input in a transaction disables
|
||||||
|
nLockTime. */
|
||||||
|
#define SEQUENCE_FINAL 0xffffffff
|
||||||
|
|
||||||
enum {
|
enum {
|
||||||
SIGHASH_ALL = 1,
|
SIGHASH_ALL = 1,
|
||||||
SIGHASH_FORKID = 0x40,
|
SIGHASH_FORKID = 0x40,
|
||||||
@ -497,6 +502,7 @@ void signing_init(const SignTx *msg, const CoinInfo *_coin,
|
|||||||
memcpy(&root, _root, sizeof(HDNode));
|
memcpy(&root, _root, sizeof(HDNode));
|
||||||
version = msg->version;
|
version = msg->version;
|
||||||
lock_time = msg->lock_time;
|
lock_time = msg->lock_time;
|
||||||
|
min_sequence = SEQUENCE_FINAL;
|
||||||
|
|
||||||
if (!coin->overwintered) {
|
if (!coin->overwintered) {
|
||||||
if (msg->has_version_group_id) {
|
if (msg->has_version_group_id) {
|
||||||
@ -782,12 +788,18 @@ static bool signing_check_input(const TxInputType *txinput) {
|
|||||||
} else { // single signature
|
} else { // single signature
|
||||||
multisig_fp_mismatch = true;
|
multisig_fp_mismatch = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
// remember the input bip32 path
|
// remember the input bip32 path
|
||||||
// change addresses must use the same bip32 path as all inputs
|
// change addresses must use the same bip32 path as all inputs
|
||||||
extract_input_bip32_path(txinput);
|
extract_input_bip32_path(txinput);
|
||||||
|
|
||||||
|
// remember the minimum nSequence value
|
||||||
|
if (txinput->sequence < min_sequence) min_sequence = txinput->sequence;
|
||||||
|
|
||||||
// compute segwit hashPrevouts & hashSequence
|
// compute segwit hashPrevouts & hashSequence
|
||||||
tx_prevout_hash(&hasher_prevouts, txinput);
|
tx_prevout_hash(&hasher_prevouts, txinput);
|
||||||
tx_sequence_hash(&hasher_sequence, txinput);
|
tx_sequence_hash(&hasher_sequence, txinput);
|
||||||
|
|
||||||
#if !BITCOIN_ONLY
|
#if !BITCOIN_ONLY
|
||||||
if (coin->decred) {
|
if (coin->decred) {
|
||||||
// serialize Decred prefix in Phase 1
|
// serialize Decred prefix in Phase 1
|
||||||
@ -800,6 +812,7 @@ static bool signing_check_input(const TxInputType *txinput) {
|
|||||||
tx_serialize_input_hash(&ti, txinput);
|
tx_serialize_input_hash(&ti, txinput);
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// hash prevout and script type to check it later (relevant for fee
|
// hash prevout and script type to check it later (relevant for fee
|
||||||
// computation)
|
// computation)
|
||||||
tx_prevout_hash(&hasher_check, txinput);
|
tx_prevout_hash(&hasher_check, txinput);
|
||||||
@ -914,6 +927,7 @@ static bool signing_confirm_tx(void) {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
uint64_t fee = 0;
|
uint64_t fee = 0;
|
||||||
if (spending <= to_spend) {
|
if (spending <= to_spend) {
|
||||||
fee = to_spend - spending;
|
fee = to_spend - spending;
|
||||||
@ -939,6 +953,16 @@ static bool signing_confirm_tx(void) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (lock_time != 0) {
|
||||||
|
bool lock_time_disabled = (min_sequence == SEQUENCE_FINAL);
|
||||||
|
layoutConfirmNondefaultLockTime(lock_time, lock_time_disabled);
|
||||||
|
if (!protectButton(ButtonRequestType_ButtonRequest_SignTx, false)) {
|
||||||
|
fsm_sendFailure(FailureType_Failure_ActionCancelled, NULL);
|
||||||
|
signing_abort();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// last confirmation
|
// last confirmation
|
||||||
layoutConfirmTx(coin, to_spend - change_spend, fee);
|
layoutConfirmTx(coin, to_spend - change_spend, fee);
|
||||||
if (!protectButton(ButtonRequestType_ButtonRequest_SignTx, false)) {
|
if (!protectButton(ButtonRequestType_ButtonRequest_SignTx, false)) {
|
||||||
|
@ -60,7 +60,6 @@ class TestMsgSigntxKomodo:
|
|||||||
script_type=proto.OutputScriptType.PAYTOADDRESS,
|
script_type=proto.OutputScriptType.PAYTOADDRESS,
|
||||||
)
|
)
|
||||||
|
|
||||||
trezor_core = client.features.model != "1"
|
|
||||||
with client:
|
with client:
|
||||||
client.set_expected_responses(
|
client.set_expected_responses(
|
||||||
[
|
[
|
||||||
@ -71,7 +70,7 @@ class TestMsgSigntxKomodo:
|
|||||||
request_extra_data(0, 11, TXHASH_2807c),
|
request_extra_data(0, 11, TXHASH_2807c),
|
||||||
request_output(0),
|
request_output(0),
|
||||||
proto.ButtonRequest(code=B.ConfirmOutput),
|
proto.ButtonRequest(code=B.ConfirmOutput),
|
||||||
(trezor_core, proto.ButtonRequest(code=B.SignTx)),
|
proto.ButtonRequest(code=B.SignTx),
|
||||||
proto.ButtonRequest(code=B.SignTx),
|
proto.ButtonRequest(code=B.SignTx),
|
||||||
request_input(0),
|
request_input(0),
|
||||||
request_output(0),
|
request_output(0),
|
||||||
@ -120,7 +119,6 @@ class TestMsgSigntxKomodo:
|
|||||||
script_type=proto.OutputScriptType.PAYTOADDRESS,
|
script_type=proto.OutputScriptType.PAYTOADDRESS,
|
||||||
)
|
)
|
||||||
|
|
||||||
trezor_core = client.features.model != "1"
|
|
||||||
with client:
|
with client:
|
||||||
client.set_expected_responses(
|
client.set_expected_responses(
|
||||||
[
|
[
|
||||||
@ -133,7 +131,7 @@ class TestMsgSigntxKomodo:
|
|||||||
proto.ButtonRequest(code=B.ConfirmOutput),
|
proto.ButtonRequest(code=B.ConfirmOutput),
|
||||||
request_output(1),
|
request_output(1),
|
||||||
proto.ButtonRequest(code=B.ConfirmOutput),
|
proto.ButtonRequest(code=B.ConfirmOutput),
|
||||||
(trezor_core, proto.ButtonRequest(code=B.SignTx)),
|
proto.ButtonRequest(code=B.SignTx),
|
||||||
proto.ButtonRequest(code=B.SignTx),
|
proto.ButtonRequest(code=B.SignTx),
|
||||||
request_input(0),
|
request_input(0),
|
||||||
request_output(0),
|
request_output(0),
|
||||||
|
Loading…
Reference in New Issue
Block a user