diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/cryptonote_basic/verification_context.h | 1 | ||||
-rw-r--r-- | src/cryptonote_core/cryptonote_core.cpp | 2 | ||||
-rw-r--r-- | src/device/device_ledger.cpp | 70 | ||||
-rw-r--r-- | src/device/device_ledger.hpp | 44 | ||||
-rw-r--r-- | src/p2p/net_node.inl | 10 | ||||
-rw-r--r-- | src/rpc/core_rpc_server.cpp | 2 | ||||
-rw-r--r-- | src/rpc/core_rpc_server_commands_defs.h | 2 | ||||
-rw-r--r-- | src/rpc/daemon_handler.cpp | 5 | ||||
-rw-r--r-- | src/wallet/api/wallet.cpp | 6 | ||||
-rw-r--r-- | src/wallet/api/wallet.h | 2 | ||||
-rw-r--r-- | src/wallet/api/wallet2_api.h | 4 | ||||
-rw-r--r-- | src/wallet/api/wallet_manager.cpp | 5 | ||||
-rw-r--r-- | src/wallet/api/wallet_manager.h | 3 | ||||
-rw-r--r-- | src/wallet/wallet2.cpp | 3 |
14 files changed, 133 insertions, 26 deletions
diff --git a/src/cryptonote_basic/verification_context.h b/src/cryptonote_basic/verification_context.h index f5f663464..4d49b692c 100644 --- a/src/cryptonote_basic/verification_context.h +++ b/src/cryptonote_basic/verification_context.h @@ -47,7 +47,6 @@ namespace cryptonote bool m_too_big; bool m_overspend; bool m_fee_too_low; - bool m_not_rct; bool m_too_few_outputs; }; diff --git a/src/cryptonote_core/cryptonote_core.cpp b/src/cryptonote_core/cryptonote_core.cpp index 212616af8..7fb232ad2 100644 --- a/src/cryptonote_core/cryptonote_core.cpp +++ b/src/cryptonote_core/cryptonote_core.cpp @@ -1907,7 +1907,7 @@ namespace cryptonote MDEBUG("blocks in the last " << seconds[n] / 60 << " minutes: " << b << " (probability " << p << ")"); if (p < threshold) { - MWARNING("There were " << b << (b == max_blocks_checked ? " or more" : "") << " blocks in the last " << seconds[n] / 60 << " minutes, there might be large hash rate changes, or we might be partitioned, cut off from the Monero network or under attack. Or it could be just sheer bad luck."); + MWARNING("There were " << b << (b == max_blocks_checked ? " or more" : "") << " blocks in the last " << seconds[n] / 60 << " minutes, there might be large hash rate changes, or we might be partitioned, cut off from the Monero network or under attack, or your computer's time is off. Or it could be just sheer bad luck."); std::shared_ptr<tools::Notify> block_rate_notify = m_block_rate_notify; if (block_rate_notify) diff --git a/src/device/device_ledger.cpp b/src/device/device_ledger.cpp index 49f54e5a5..eaa9f910d 100644 --- a/src/device/device_ledger.cpp +++ b/src/device/device_ledger.cpp @@ -55,7 +55,10 @@ namespace hw { } #define TRACKD MTRACE("hw") - #define ASSERT_SW(sw,ok,msk) CHECK_AND_ASSERT_THROW_MES(((sw)&(mask))==(ok), "Wrong Device Status : SW=" << std::hex << (sw) << " (EXPECT=" << std::hex << (ok) << ", MASK=" << std::hex << (mask) << ")") ; + #define ASSERT_SW(sw,ok,msk) CHECK_AND_ASSERT_THROW_MES(((sw)&(mask))==(ok), \ + "Wrong Device Status: " << "0x" << std::hex << (sw) << " (" << Status::to_string(sw) << "), " << \ + "EXPECTED 0x" << std::hex << (ok) << " (" << Status::to_string(ok) << "), " << \ + "MASK 0x" << std::hex << (mask)); #define ASSERT_T0(exp) CHECK_AND_ASSERT_THROW_MES(exp, "Protocol assert failure: "#exp ) ; #define ASSERT_X(exp,msg) CHECK_AND_ASSERT_THROW_MES(exp, msg); @@ -64,6 +67,71 @@ namespace hw { crypto::secret_key dbg_spendkey; #endif + struct Status + { + unsigned int code; + const char *string; + + constexpr operator unsigned int() const + { + return this->code; + } + + static const char *to_string(unsigned int code); + }; + + // Must be sorted in ascending order by the code + #define LEDGER_STATUS(status) {status, #status} + constexpr Status status_codes[] = { + LEDGER_STATUS(SW_BYTES_REMAINING_00), + LEDGER_STATUS(SW_WARNING_STATE_UNCHANGED), + LEDGER_STATUS(SW_STATE_TERMINATED), + LEDGER_STATUS(SW_MORE_DATA_AVAILABLE), + LEDGER_STATUS(SW_WRONG_LENGTH), + LEDGER_STATUS(SW_LOGICAL_CHANNEL_NOT_SUPPORTED), + LEDGER_STATUS(SW_SECURE_MESSAGING_NOT_SUPPORTED), + LEDGER_STATUS(SW_LAST_COMMAND_EXPECTED), + LEDGER_STATUS(SW_COMMAND_CHAINING_NOT_SUPPORTED), + LEDGER_STATUS(SW_SECURITY_LOAD_KEY), + LEDGER_STATUS(SW_SECURITY_COMMITMENT_CONTROL), + LEDGER_STATUS(SW_SECURITY_AMOUNT_CHAIN_CONTROL), + LEDGER_STATUS(SW_SECURITY_COMMITMENT_CHAIN_CONTROL), + LEDGER_STATUS(SW_SECURITY_OUTKEYS_CHAIN_CONTROL), + LEDGER_STATUS(SW_SECURITY_MAXOUTPUT_REACHED), + LEDGER_STATUS(SW_SECURITY_TRUSTED_INPUT), + LEDGER_STATUS(SW_CLIENT_NOT_SUPPORTED), + LEDGER_STATUS(SW_SECURITY_STATUS_NOT_SATISFIED), + LEDGER_STATUS(SW_FILE_INVALID), + LEDGER_STATUS(SW_PIN_BLOCKED), + LEDGER_STATUS(SW_DATA_INVALID), + LEDGER_STATUS(SW_CONDITIONS_NOT_SATISFIED), + LEDGER_STATUS(SW_COMMAND_NOT_ALLOWED), + LEDGER_STATUS(SW_APPLET_SELECT_FAILED), + LEDGER_STATUS(SW_WRONG_DATA), + LEDGER_STATUS(SW_FUNC_NOT_SUPPORTED), + LEDGER_STATUS(SW_FILE_NOT_FOUND), + LEDGER_STATUS(SW_RECORD_NOT_FOUND), + LEDGER_STATUS(SW_FILE_FULL), + LEDGER_STATUS(SW_INCORRECT_P1P2), + LEDGER_STATUS(SW_REFERENCED_DATA_NOT_FOUND), + LEDGER_STATUS(SW_WRONG_P1P2), + LEDGER_STATUS(SW_CORRECT_LENGTH_00), + LEDGER_STATUS(SW_INS_NOT_SUPPORTED), + LEDGER_STATUS(SW_CLA_NOT_SUPPORTED), + LEDGER_STATUS(SW_UNKNOWN), + LEDGER_STATUS(SW_OK), + LEDGER_STATUS(SW_ALGORITHM_UNSUPPORTED) + }; + + const char *Status::to_string(unsigned int code) + { + constexpr size_t status_codes_size = sizeof(status_codes) / sizeof(status_codes[0]); + constexpr const Status *status_codes_end = &status_codes[status_codes_size]; + + const Status *item = std::lower_bound(&status_codes[0], status_codes_end, code); + return (item == status_codes_end || code < *item) ? "UNKNOWN" : item->string; + } + /* ===================================================================== */ /* === hmacmap ==== */ /* ===================================================================== */ diff --git a/src/device/device_ledger.hpp b/src/device/device_ledger.hpp index 05a26143a..e3e30fba8 100644 --- a/src/device/device_ledger.hpp +++ b/src/device/device_ledger.hpp @@ -58,6 +58,46 @@ namespace hw { #ifdef WITH_DEVICE_LEDGER + // Origin: https://github.com/LedgerHQ/ledger-app-monero/blob/master/src/monero_types.h + #define SW_BYTES_REMAINING_00 0x6100 + #define SW_WARNING_STATE_UNCHANGED 0x6200 + #define SW_STATE_TERMINATED 0x6285 + #define SW_MORE_DATA_AVAILABLE 0x6310 + #define SW_WRONG_LENGTH 0x6700 + #define SW_LOGICAL_CHANNEL_NOT_SUPPORTED 0x6881 + #define SW_SECURE_MESSAGING_NOT_SUPPORTED 0x6882 + #define SW_LAST_COMMAND_EXPECTED 0x6883 + #define SW_COMMAND_CHAINING_NOT_SUPPORTED 0x6884 + #define SW_SECURITY_LOAD_KEY 0x6900 + #define SW_SECURITY_COMMITMENT_CONTROL 0x6911 + #define SW_SECURITY_AMOUNT_CHAIN_CONTROL 0x6912 + #define SW_SECURITY_COMMITMENT_CHAIN_CONTROL 0x6913 + #define SW_SECURITY_OUTKEYS_CHAIN_CONTROL 0x6914 + #define SW_SECURITY_MAXOUTPUT_REACHED 0x6915 + #define SW_SECURITY_TRUSTED_INPUT 0x6916 + #define SW_CLIENT_NOT_SUPPORTED 0x6930 + #define SW_SECURITY_STATUS_NOT_SATISFIED 0x6982 + #define SW_FILE_INVALID 0x6983 + #define SW_PIN_BLOCKED 0x6983 + #define SW_DATA_INVALID 0x6984 + #define SW_CONDITIONS_NOT_SATISFIED 0x6985 + #define SW_COMMAND_NOT_ALLOWED 0x6986 + #define SW_APPLET_SELECT_FAILED 0x6999 + #define SW_WRONG_DATA 0x6a80 + #define SW_FUNC_NOT_SUPPORTED 0x6a81 + #define SW_FILE_NOT_FOUND 0x6a82 + #define SW_RECORD_NOT_FOUND 0x6a83 + #define SW_FILE_FULL 0x6a84 + #define SW_INCORRECT_P1P2 0x6a86 + #define SW_REFERENCED_DATA_NOT_FOUND 0x6a88 + #define SW_WRONG_P1P2 0x6b00 + #define SW_CORRECT_LENGTH_00 0x6c00 + #define SW_INS_NOT_SUPPORTED 0x6d00 + #define SW_CLA_NOT_SUPPORTED 0x6e00 + #define SW_UNKNOWN 0x6f00 + #define SW_OK 0x9000 + #define SW_ALGORITHM_UNSUPPORTED 0x9484 + namespace { bool apdu_verbose =true; } @@ -128,8 +168,8 @@ namespace hw { unsigned int id; void logCMD(void); void logRESP(void); - unsigned int exchange(unsigned int ok=0x9000, unsigned int mask=0xFFFF); - unsigned int exchange_wait_on_input(unsigned int ok=0x9000, unsigned int mask=0xFFFF); + unsigned int exchange(unsigned int ok=SW_OK, unsigned int mask=0xFFFF); + unsigned int exchange_wait_on_input(unsigned int ok=SW_OK, unsigned int mask=0xFFFF); void reset_buffer(void); int set_command_header(unsigned char ins, unsigned char p1 = 0x00, unsigned char p2 = 0x00); int set_command_header_noopt(unsigned char ins, unsigned char p1 = 0x00, unsigned char p2 = 0x00); diff --git a/src/p2p/net_node.inl b/src/p2p/net_node.inl index 9b6358dee..dcd16e5c1 100644 --- a/src/p2p/net_node.inl +++ b/src/p2p/net_node.inl @@ -1013,15 +1013,18 @@ namespace nodetool epee::simple_event ev; std::atomic<bool> hsh_result(false); + bool timeout = false; bool r = epee::net_utils::async_invoke_remote_command2<typename COMMAND_HANDSHAKE::response>(context_, COMMAND_HANDSHAKE::ID, arg, zone.m_net_server.get_config_object(), - [this, &pi, &ev, &hsh_result, &just_take_peerlist, &context_](int code, const typename COMMAND_HANDSHAKE::response& rsp, p2p_connection_context& context) + [this, &pi, &ev, &hsh_result, &just_take_peerlist, &context_, &timeout](int code, const typename COMMAND_HANDSHAKE::response& rsp, p2p_connection_context& context) { epee::misc_utils::auto_scope_leave_caller scope_exit_handler = epee::misc_utils::create_scope_leave_handler([&](){ev.raise();}); if(code < 0) { LOG_WARNING_CC(context, "COMMAND_HANDSHAKE invoke failed. (" << code << ", " << epee::levin::get_err_descr(code) << ")"); + if (code == LEVIN_ERROR_CONNECTION_TIMEDOUT || code == LEVIN_ERROR_CONNECTION_DESTROYED) + timeout = true; return; } @@ -1079,7 +1082,8 @@ namespace nodetool if(!hsh_result) { LOG_WARNING_CC(context_, "COMMAND_HANDSHAKE Failed"); - m_network_zones.at(context_.m_remote_address.get_zone()).m_net_server.get_config_object().close(context_.m_connection_id); + if (!timeout) + zone.m_net_server.get_config_object().close(context_.m_connection_id); } else if (!just_take_peerlist) { @@ -1266,7 +1270,6 @@ namespace nodetool LOG_PRINT_CC_PRIORITY_NODE(is_priority, *con, "Failed to HANDSHAKE with peer " << na.str() /*<< ", try " << try_count*/); - zone.m_net_server.get_config_object().close(con->m_connection_id); record_addr_failed(na); return false; } @@ -1330,7 +1333,6 @@ namespace nodetool bool is_priority = is_priority_node(na); LOG_PRINT_CC_PRIORITY_NODE(is_priority, *con, "Failed to HANDSHAKE with peer " << na.str()); - zone.m_net_server.get_config_object().close(con->m_connection_id); record_addr_failed(na); return false; } diff --git a/src/rpc/core_rpc_server.cpp b/src/rpc/core_rpc_server.cpp index 8e5207e82..d33dbd16a 100644 --- a/src/rpc/core_rpc_server.cpp +++ b/src/rpc/core_rpc_server.cpp @@ -1134,8 +1134,6 @@ namespace cryptonote add_reason(reason, "overspend"); if ((res.fee_too_low = tvc.m_fee_too_low)) add_reason(reason, "fee too low"); - if ((res.not_rct = tvc.m_not_rct)) - add_reason(reason, "tx is not ringct"); if ((res.too_few_outputs = tvc.m_too_few_outputs)) add_reason(reason, "too few outputs"); const std::string punctuation = reason.empty() ? "" : ": "; diff --git a/src/rpc/core_rpc_server_commands_defs.h b/src/rpc/core_rpc_server_commands_defs.h index dbb1d4472..a3c187c24 100644 --- a/src/rpc/core_rpc_server_commands_defs.h +++ b/src/rpc/core_rpc_server_commands_defs.h @@ -588,7 +588,6 @@ namespace cryptonote bool too_big; bool overspend; bool fee_too_low; - bool not_rct; bool too_few_outputs; bool sanity_check_failed; @@ -603,7 +602,6 @@ namespace cryptonote KV_SERIALIZE(too_big) KV_SERIALIZE(overspend) KV_SERIALIZE(fee_too_low) - KV_SERIALIZE(not_rct) KV_SERIALIZE(too_few_outputs) KV_SERIALIZE(sanity_check_failed) END_KV_SERIALIZE_MAP() diff --git a/src/rpc/daemon_handler.cpp b/src/rpc/daemon_handler.cpp index 125688ba5..7292176b4 100644 --- a/src/rpc/daemon_handler.cpp +++ b/src/rpc/daemon_handler.cpp @@ -410,11 +410,6 @@ namespace rpc if (!res.error_details.empty()) res.error_details += " and "; res.error_details += "fee too low"; } - if (tvc.m_not_rct) - { - if (!res.error_details.empty()) res.error_details += " and "; - res.error_details += "tx is not ringct"; - } if (tvc.m_too_few_outputs) { if (!res.error_details.empty()) res.error_details += " and "; diff --git a/src/wallet/api/wallet.cpp b/src/wallet/api/wallet.cpp index 33047f703..4612b0397 100644 --- a/src/wallet/api/wallet.cpp +++ b/src/wallet/api/wallet.cpp @@ -725,7 +725,7 @@ bool WalletImpl::recover(const std::string &path, const std::string &seed) return recover(path, "", seed); } -bool WalletImpl::recover(const std::string &path, const std::string &password, const std::string &seed) +bool WalletImpl::recover(const std::string &path, const std::string &password, const std::string &seed, const std::string &seed_offset/* = {}*/) { clearStatus(); m_errorString.clear(); @@ -743,6 +743,10 @@ bool WalletImpl::recover(const std::string &path, const std::string &password, c setStatusError(tr("Electrum-style word list failed verification")); return false; } + if (!seed_offset.empty()) + { + recovery_key = cryptonote::decrypt_key(recovery_key, seed_offset); + } if (old_language == crypto::ElectrumWords::old_language_name) old_language = Language::English().get_language_name(); diff --git a/src/wallet/api/wallet.h b/src/wallet/api/wallet.h index e46a62340..66eeb0e73 100644 --- a/src/wallet/api/wallet.h +++ b/src/wallet/api/wallet.h @@ -60,7 +60,7 @@ public: const std::string &language) const override; bool open(const std::string &path, const std::string &password); bool recover(const std::string &path,const std::string &password, - const std::string &seed); + const std::string &seed, const std::string &seed_offset = {}); bool recoverFromKeysWithPassword(const std::string &path, const std::string &password, const std::string &language, diff --git a/src/wallet/api/wallet2_api.h b/src/wallet/api/wallet2_api.h index 3945e55c9..09c64106e 100644 --- a/src/wallet/api/wallet2_api.h +++ b/src/wallet/api/wallet2_api.h @@ -1093,10 +1093,12 @@ struct WalletManager * \param nettype Network type * \param restoreHeight restore from start height * \param kdf_rounds Number of rounds for key derivation function + * \param seed_offset Seed offset passphrase (optional) * \return Wallet instance (Wallet::status() needs to be called to check if recovered successfully) */ virtual Wallet * recoveryWallet(const std::string &path, const std::string &password, const std::string &mnemonic, - NetworkType nettype = MAINNET, uint64_t restoreHeight = 0, uint64_t kdf_rounds = 1) = 0; + NetworkType nettype = MAINNET, uint64_t restoreHeight = 0, uint64_t kdf_rounds = 1, + const std::string &seed_offset = {}) = 0; Wallet * recoveryWallet(const std::string &path, const std::string &password, const std::string &mnemonic, bool testnet = false, uint64_t restoreHeight = 0) // deprecated { diff --git a/src/wallet/api/wallet_manager.cpp b/src/wallet/api/wallet_manager.cpp index d589dcc75..44a184304 100644 --- a/src/wallet/api/wallet_manager.cpp +++ b/src/wallet/api/wallet_manager.cpp @@ -93,13 +93,14 @@ Wallet *WalletManagerImpl::recoveryWallet(const std::string &path, const std::string &mnemonic, NetworkType nettype, uint64_t restoreHeight, - uint64_t kdf_rounds) + uint64_t kdf_rounds, + const std::string &seed_offset/* = {}*/) { WalletImpl * wallet = new WalletImpl(nettype, kdf_rounds); if(restoreHeight > 0){ wallet->setRefreshFromBlockHeight(restoreHeight); } - wallet->recover(path, password, mnemonic); + wallet->recover(path, password, mnemonic, seed_offset); return wallet; } diff --git a/src/wallet/api/wallet_manager.h b/src/wallet/api/wallet_manager.h index 537fc5ba6..0595b8327 100644 --- a/src/wallet/api/wallet_manager.h +++ b/src/wallet/api/wallet_manager.h @@ -46,7 +46,8 @@ public: const std::string &mnemonic, NetworkType nettype, uint64_t restoreHeight, - uint64_t kdf_rounds = 1) override; + uint64_t kdf_rounds = 1, + const std::string &seed_offset = {}) override; virtual Wallet * createWalletFromKeys(const std::string &path, const std::string &password, const std::string &language, diff --git a/src/wallet/wallet2.cpp b/src/wallet/wallet2.cpp index 90682e60c..70ceddad3 100644 --- a/src/wallet/wallet2.cpp +++ b/src/wallet/wallet2.cpp @@ -236,8 +236,6 @@ namespace add_reason(reason, "overspend"); if (res.fee_too_low) add_reason(reason, "fee too low"); - if (res.not_rct) - add_reason(reason, "tx is not ringct"); if (res.sanity_check_failed) add_reason(reason, "tx sanity check failed"); if (res.not_relayed) @@ -437,6 +435,7 @@ std::unique_ptr<tools::wallet2> make_basic(const boost::program_options::variabl verification_required && !ssl_options.has_strong_verification(real_daemon), tools::error::wallet_internal_error, tools::wallet2::tr("Enabling --") + std::string{use_proxy ? opts.proxy.name : opts.daemon_ssl.name} + tools::wallet2::tr(" requires --") + + opts.daemon_ssl_allow_any_cert.name + tools::wallet2::tr(" or --") + opts.daemon_ssl_ca_certificates.name + tools::wallet2::tr(" or --") + opts.daemon_ssl_allowed_fingerprints.name + tools::wallet2::tr(" or use of a .onion/.i2p domain") ); } |