Putting initial password entry as a background task so startup is more responsive.

This commit is contained in:
clemahieu 2015-01-22 01:37:17 -06:00
commit 329246a74d
7 changed files with 57 additions and 8 deletions

View file

@ -34,7 +34,7 @@ TEST (node, send_unkeyed)
rai::system system (24000, 1);
rai::keypair key2;
system.wallet (0)->store.insert (rai::test_genesis_key.prv);
system.wallet (0)->store.password.value_set (rai::uint256_union (0));
system.wallet (0)->store.password.value_set (rai::uint256_union (1));
ASSERT_TRUE (system.wallet (0)->send (key2.pub, 1000));
}

View file

@ -419,6 +419,14 @@ TEST (rpc, wallet_password_change)
TEST (rpc, wallet_password_enter)
{
rai::system system (24000, 1);
auto iterations (0);
while (system.wallet (0)->store.password.value () == 0)
{
system.service->poll_one ();
system.processor.poll_one ();
++iterations;
ASSERT_LT (iterations, 200);
}
auto pool (boost::make_shared <boost::network::utils::thread_pool> ());
rai::rpc rpc (system.service, pool, boost::asio::ip::address_v6::loopback (), 25000, *system.nodes [0], true);
boost::network::http::server <rai::rpc>::request request;

View file

@ -189,7 +189,7 @@ TEST (wallet, rekey)
bool init;
rai::wallet_store wallet (init, rai::unique_path ());
ASSERT_FALSE (init);
ASSERT_EQ (wallet.password.value (), wallet.derive_key (""));
ASSERT_TRUE (wallet.password.value ().is_zero ());
ASSERT_FALSE (init);
rai::keypair key1;
wallet.insert (key1.prv);
@ -299,13 +299,14 @@ TEST (wallet, already_open)
ASSERT_TRUE (init);
}
TEST (wallet, repoen_default_password)
TEST (wallet, reopen_default_password)
{
auto path (rai::unique_path ());
{
bool init;
rai::wallet_store wallet (init, path);
ASSERT_FALSE (init);
wallet.rekey ("");
ASSERT_TRUE (wallet.valid_password ());
}
{

View file

@ -25,6 +25,14 @@ TEST (wallets, open_existing)
auto wallet (wallets.create (id));
ASSERT_NE (nullptr, wallet);
ASSERT_EQ (wallet, wallets.open (id));
auto iterations (0);
while (wallet->store.password.value () == 0)
{
system.service->poll_one ();
system.processor.poll_one ();
++iterations;
ASSERT_LT (iterations, 200);
}
}
{
rai::wallets wallets (*system.nodes [0], path);

View file

@ -613,7 +613,7 @@ password (0, 1024)
auto status4 (handle->Get (leveldb::ReadOptions (), leveldb::Slice (representative_special.chars.data (), representative_special.chars.size ()), &junk));
if (status4.ok ())
{
enter_password ("");
password.value_set (0);
}
else
{
@ -663,10 +663,9 @@ password (0, 1024)
// Wallet key is a fixed random key that encrypts all entries
rai::uint256_union wallet_key;
random_pool.GenerateBlock (wallet_key.bytes.data (), sizeof (wallet_key.bytes));
auto password_l (derive_key (""));
password.value_set (password_l);
password.value_set (0);
// Wallet key is encrypted by the user's password
rai::uint256_union encrypted (wallet_key, password_l, salt_l.owords [0]);
rai::uint256_union encrypted (wallet_key, 0, salt_l.owords [0]);
auto status1 (handle->Put (leveldb::WriteOptions (), leveldb::Slice (wallet_key_special.chars.data (), wallet_key_special.chars.size ()), leveldb::Slice (encrypted.chars.data (), encrypted.chars.size ())));
assert (status1.ok ());
rai::uint256_union zero (0);
@ -674,7 +673,6 @@ password (0, 1024)
auto status3 (handle->Put (leveldb::WriteOptions (), leveldb::Slice (check_special.chars.data (), check_special.chars.size ()), leveldb::Slice (check.chars.data (), check.chars.size ())));
assert (status3.ok ());
wallet_key.clear ();
password_l.clear ();
auto status4 (handle->Put (leveldb::WriteOptions (), leveldb::Slice (representative_special.chars.data (), representative_special.chars.size ()), leveldb::Slice (rai::genesis_account.chars.data (), rai::genesis_account.chars.size ())));
assert (status4.ok ());
}
@ -831,6 +829,23 @@ node (node_a)
{
}
void rai::wallet::enter_initial_password ()
{
std::lock_guard <std::mutex> lock (mutex);
if (store.password.value ().is_zero ())
{
if (store.valid_password ())
{
// Newly created wallets have a zero key
store.rekey ("");
}
else
{
store.enter_password ("");
}
}
}
void rai::wallet::insert (rai::private_key const & key_a)
{
std::lock_guard <std::mutex> lock (mutex);
@ -1024,6 +1039,10 @@ node (node_a)
auto wallet (std::make_shared <rai::wallet> (error, node_a, i->path ()));
if (!error)
{
node_a.service.add (std::chrono::system_clock::now (), [wallet] ()
{
wallet->enter_initial_password ();
});
items [id] = wallet;
}
else
@ -1064,6 +1083,10 @@ std::shared_ptr <rai::wallet> rai::wallets::create (rai::uint256_union const & i
auto wallet (std::make_shared <rai::wallet> (error, node, path / id));
if (!error)
{
node.service.add (std::chrono::system_clock::now (), [wallet] ()
{
wallet->enter_initial_password ();
});
items [id_a] = wallet;
result = wallet;
}

View file

@ -323,6 +323,7 @@ class wallet : public std::enable_shared_from_this <rai::wallet>
public:
wallet (bool &, rai::node &, boost::filesystem::path const &);
wallet (bool &, rai::node &, boost::filesystem::path const &, std::string const &);
void enter_initial_password ();
void insert (rai::private_key const &);
bool receive (rai::send_block const &, rai::private_key const &, rai::account const &);
bool send (rai::account const &, rai::uint128_t const &);

View file

@ -80,6 +80,14 @@ TEST (client, password_nochange)
rai_qt::wallet wallet (application, *system.nodes [0], system.wallet (0), system.account (0));
QTest::mouseClick (wallet.show_advanced, Qt::LeftButton);
QTest::mouseClick (wallet.advanced.change_password, Qt::LeftButton);
auto iterations (0);
while (system.wallet (0)->store.password.value () == 0)
{
system.service->poll_one ();
system.processor.poll_one ();
++iterations;
ASSERT_LT (iterations, 200);
}
ASSERT_EQ (system.wallet (0)->store.derive_key (""), system.wallet (0)->store.password.value ());
QTest::keyClicks (wallet.password_change.password, "1");
QTest::keyClicks (wallet.password_change.retype, "2");