diff options
author | Dusan Klinec <dusan.klinec@gmail.com> | 2018-11-11 20:07:25 +0100 |
---|---|---|
committer | Dusan Klinec <dusan.klinec@gmail.com> | 2018-11-29 04:33:41 +0100 |
commit | 318cc78457136ec778d6dff43b36f9447d95a43d (patch) | |
tree | 940b10195714d689ac6eb0feebd6b18757f0f57f /src/wallet | |
parent | Merge pull request #4821 (diff) | |
download | monero-318cc78457136ec778d6dff43b36f9447d95a43d.tar.xz |
device/trezor: passphrase entry on host
- simple device callback object added. Device can request passphrase/PIN entry via the callback or notify user some action is required
- callback is routed to wallet2, which routes the callback to i_wallet_callback so CLI or GUI wallets can support passphrase entry for HW tokens
- wallet: device open needs wallet callback first - passphrase protected device needs wallet callback so user can enter passphrase
Diffstat (limited to 'src/wallet')
-rw-r--r-- | src/wallet/wallet2.cpp | 52 | ||||
-rw-r--r-- | src/wallet/wallet2.h | 22 | ||||
-rw-r--r-- | src/wallet/wallet_errors.h | 8 |
3 files changed, 79 insertions, 3 deletions
diff --git a/src/wallet/wallet2.cpp b/src/wallet/wallet2.cpp index 49aef4350..ae6ed0937 100644 --- a/src/wallet/wallet2.cpp +++ b/src/wallet/wallet2.cpp @@ -818,6 +818,24 @@ wallet_keys_unlocker::~wallet_keys_unlocker() w.encrypt_keys(key); } +void wallet_device_callback::on_button_request() +{ + if (wallet) + wallet->on_button_request(); +} + +void wallet_device_callback::on_pin_request(epee::wipeable_string & pin) +{ + if (wallet) + wallet->on_pin_request(pin); +} + +void wallet_device_callback::on_passphrase_request(bool on_device, epee::wipeable_string & passphrase) +{ + if (wallet) + wallet->on_passphrase_request(on_device, passphrase); +} + wallet2::wallet2(network_type nettype, uint64_t kdf_rounds, bool unattended): m_multisig_rescan_info(NULL), m_multisig_rescan_k(NULL), @@ -929,7 +947,7 @@ std::pair<std::unique_ptr<wallet2>, password_container> wallet2::make_from_file( return {nullptr, password_container{}}; } auto wallet = make_basic(vm, unattended, opts, password_prompter); - if (wallet) + if (wallet && !wallet_file.empty()) { wallet->load(wallet_file, pwd->password()); } @@ -1071,15 +1089,16 @@ bool wallet2::reconnect_device() hw::device &hwdev = lookup_device(m_device_name); hwdev.set_name(m_device_name); hwdev.set_network_type(m_nettype); + hwdev.set_callback(get_device_callback()); r = hwdev.init(); if (!r){ - LOG_PRINT_L2("Could not init device"); + MERROR("Could not init device"); return false; } r = hwdev.connect(); if (!r){ - LOG_PRINT_L2("Could not connect to the device"); + MERROR("Could not connect to the device"); return false; } @@ -3441,6 +3460,7 @@ bool wallet2::load_keys(const std::string& keys_file_name, const epee::wipeable_ hw::device &hwdev = lookup_device(m_device_name); THROW_WALLET_EXCEPTION_IF(!hwdev.set_name(m_device_name), error::wallet_internal_error, "Could not set device name " + m_device_name); hwdev.set_network_type(m_nettype); + hwdev.set_callback(get_device_callback()); THROW_WALLET_EXCEPTION_IF(!hwdev.init(), error::wallet_internal_error, "Could not initialize the device " + m_device_name); THROW_WALLET_EXCEPTION_IF(!hwdev.connect(), error::wallet_internal_error, "Could not connect to the device " + m_device_name); m_account.set_device(hwdev); @@ -3947,6 +3967,7 @@ void wallet2::restore(const std::string& wallet_, const epee::wipeable_string& p auto &hwdev = lookup_device(device_name); hwdev.set_name(device_name); hwdev.set_network_type(m_nettype); + hwdev.set_callback(get_device_callback()); m_account.create_from_device(hwdev); m_key_device_type = m_account.get_device().get_type(); @@ -11940,4 +11961,29 @@ uint64_t wallet2::get_segregation_fork_height() const void wallet2::generate_genesis(cryptonote::block& b) const { cryptonote::generate_genesis_block(b, get_config(m_nettype).GENESIS_TX, get_config(m_nettype).GENESIS_NONCE); } +//---------------------------------------------------------------------------------------------------- +wallet_device_callback * wallet2::get_device_callback() +{ + if (!m_device_callback){ + m_device_callback.reset(new wallet_device_callback(this)); + } + return m_device_callback.get(); +}//---------------------------------------------------------------------------------------------------- +void wallet2::on_button_request() +{ + if (0 != m_callback) + m_callback->on_button_request(); +} +//---------------------------------------------------------------------------------------------------- +void wallet2::on_pin_request(epee::wipeable_string & pin) +{ + if (0 != m_callback) + m_callback->on_pin_request(pin); +} +//---------------------------------------------------------------------------------------------------- +void wallet2::on_passphrase_request(bool on_device, epee::wipeable_string & passphrase) +{ + if (0 != m_callback) + m_callback->on_passphrase_request(on_device, passphrase); +} } diff --git a/src/wallet/wallet2.h b/src/wallet/wallet2.h index eb0763131..c07054177 100644 --- a/src/wallet/wallet2.h +++ b/src/wallet/wallet2.h @@ -98,11 +98,26 @@ namespace tools virtual void on_lw_money_received(uint64_t height, const crypto::hash &txid, uint64_t amount) {} virtual void on_lw_unconfirmed_money_received(uint64_t height, const crypto::hash &txid, uint64_t amount) {} virtual void on_lw_money_spent(uint64_t height, const crypto::hash &txid, uint64_t amount) {} + // Device callbacks + virtual void on_button_request() {} + virtual void on_pin_request(epee::wipeable_string & pin) {} + virtual void on_passphrase_request(bool on_device, epee::wipeable_string & passphrase) {} // Common callbacks virtual void on_pool_tx_removed(const crypto::hash &txid) {} virtual ~i_wallet2_callback() {} }; + class wallet_device_callback : public hw::i_device_callback + { + public: + wallet_device_callback(wallet2 * wallet): wallet(wallet) {}; + void on_button_request() override; + void on_pin_request(epee::wipeable_string & pin) override; + void on_passphrase_request(bool on_device, epee::wipeable_string & passphrase) override; + private: + wallet2 * wallet; + }; + struct tx_dust_policy { uint64_t dust_threshold; @@ -154,6 +169,7 @@ namespace tools { friend class ::Serialization_portability_wallet_Test; friend class wallet_keys_unlocker; + friend class wallet_device_callback; public: static constexpr const std::chrono::seconds rpc_timeout = std::chrono::minutes(3) + std::chrono::seconds(30); @@ -1285,6 +1301,11 @@ namespace tools void setup_new_blockchain(); void create_keys_file(const std::string &wallet_, bool watch_only, const epee::wipeable_string &password, bool create_address_file); + wallet_device_callback * get_device_callback(); + void on_button_request(); + void on_pin_request(epee::wipeable_string & pin); + void on_passphrase_request(bool on_device, epee::wipeable_string & passphrase); + cryptonote::account_base m_account; boost::optional<epee::net_utils::http::login> m_daemon_login; std::string m_daemon_address; @@ -1396,6 +1417,7 @@ namespace tools bool m_devices_registered; std::shared_ptr<tools::Notify> m_tx_notify; + std::unique_ptr<wallet_device_callback> m_device_callback; }; } BOOST_CLASS_VERSION(tools::wallet2, 26) diff --git a/src/wallet/wallet_errors.h b/src/wallet/wallet_errors.h index b3141985d..e2caee5d2 100644 --- a/src/wallet/wallet_errors.h +++ b/src/wallet/wallet_errors.h @@ -219,6 +219,14 @@ namespace tools } }; //---------------------------------------------------------------------------------------------------- + struct password_entry_failed : public wallet_runtime_error + { + explicit password_entry_failed(std::string&& loc, const std::string &msg = "Password entry failed") + : wallet_runtime_error(std::move(loc), msg) + { + } + }; + //---------------------------------------------------------------------------------------------------- const char* const file_error_messages[] = { "file already exists", "file not found", |