Bitcoin Core  0.20.99
P2P Digital Currency
load.cpp
Go to the documentation of this file.
1 // Copyright (c) 2009-2010 Satoshi Nakamoto
2 // Copyright (c) 2009-2020 The Bitcoin Core developers
3 // Distributed under the MIT software license, see the accompanying
4 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
5 
6 #include <wallet/load.h>
7 
8 #include <interfaces/chain.h>
9 #include <scheduler.h>
10 #include <util/string.h>
11 #include <util/system.h>
12 #include <util/translation.h>
13 #include <wallet/wallet.h>
14 
15 bool VerifyWallets(interfaces::Chain& chain, const std::vector<std::string>& wallet_files)
16 {
17  if (gArgs.IsArgSet("-walletdir")) {
18  fs::path wallet_dir = gArgs.GetArg("-walletdir", "");
19  boost::system::error_code error;
20  // The canonical path cleans the path, preventing >1 Berkeley environment instances for the same directory
21  fs::path canonical_wallet_dir = fs::canonical(wallet_dir, error);
22  if (error || !fs::exists(wallet_dir)) {
23  chain.initError(strprintf(_("Specified -walletdir \"%s\" does not exist"), wallet_dir.string()));
24  return false;
25  } else if (!fs::is_directory(wallet_dir)) {
26  chain.initError(strprintf(_("Specified -walletdir \"%s\" is not a directory"), wallet_dir.string()));
27  return false;
28  // The canonical path transforms relative paths into absolute ones, so we check the non-canonical version
29  } else if (!wallet_dir.is_absolute()) {
30  chain.initError(strprintf(_("Specified -walletdir \"%s\" is a relative path"), wallet_dir.string()));
31  return false;
32  }
33  gArgs.ForceSetArg("-walletdir", canonical_wallet_dir.string());
34  }
35 
36  LogPrintf("Using wallet directory %s\n", GetWalletDir().string());
37 
38  chain.initMessage(_("Verifying wallet(s)...").translated);
39 
40  // Parameter interaction code should have thrown an error if -salvagewallet
41  // was enabled with more than wallet file, so the wallet_files size check
42  // here should have no effect.
43  bool salvage_wallet = gArgs.GetBoolArg("-salvagewallet", false) && wallet_files.size() <= 1;
44 
45  // Keep track of each wallet absolute path to detect duplicates.
46  std::set<fs::path> wallet_paths;
47 
48  for (const auto& wallet_file : wallet_files) {
49  WalletLocation location(wallet_file);
50 
51  if (!wallet_paths.insert(location.GetPath()).second) {
52  chain.initError(strprintf(_("Error loading wallet %s. Duplicate -wallet filename specified."), wallet_file));
53  return false;
54  }
55 
56  bilingual_str error_string;
57  std::vector<bilingual_str> warnings;
58  bool verify_success = CWallet::Verify(chain, location, salvage_wallet, error_string, warnings);
59  if (!warnings.empty()) chain.initWarning(Join(warnings, Untranslated("\n")));
60  if (!verify_success) {
61  chain.initError(error_string);
62  return false;
63  }
64  }
65 
66  return true;
67 }
68 
69 bool LoadWallets(interfaces::Chain& chain, const std::vector<std::string>& wallet_files)
70 {
71  try {
72  for (const std::string& walletFile : wallet_files) {
74  std::vector<bilingual_str> warnings;
75  std::shared_ptr<CWallet> pwallet = CWallet::CreateWalletFromFile(chain, WalletLocation(walletFile), error, warnings);
76  if (!warnings.empty()) chain.initWarning(Join(warnings, Untranslated("\n")));
77  if (!pwallet) {
78  chain.initError(error);
79  return false;
80  }
81  AddWallet(pwallet);
82  }
83  return true;
84  } catch (const std::runtime_error& e) {
85  chain.initError(Untranslated(e.what()));
86  return false;
87  }
88 }
89 
90 void StartWallets(CScheduler& scheduler)
91 {
92  for (const std::shared_ptr<CWallet>& pwallet : GetWallets()) {
93  pwallet->postInitProcess();
94  }
95 
96  // Schedule periodic wallet flushes and tx rebroadcasts
97  scheduler.scheduleEvery(MaybeCompactWalletDB, std::chrono::milliseconds{500});
98  scheduler.scheduleEvery(MaybeResendWalletTxs, std::chrono::milliseconds{1000});
99 }
100 
102 {
103  for (const std::shared_ptr<CWallet>& pwallet : GetWallets()) {
104  pwallet->Flush(false);
105  }
106 }
107 
109 {
110  for (const std::shared_ptr<CWallet>& pwallet : GetWallets()) {
111  pwallet->Flush(true);
112  }
113 }
114 
116 {
117  auto wallets = GetWallets();
118  while (!wallets.empty()) {
119  auto wallet = wallets.back();
120  wallets.pop_back();
121  RemoveWallet(wallet);
122  UnloadWallet(std::move(wallet));
123  }
124 }
const fs::path & GetPath() const
Get wallet absolute path.
Definition: walletutil.h:84
bool IsArgSet(const std::string &strArg) const
Return true if the given argument has been manually set.
Definition: system.cpp:369
std::vector< std::shared_ptr< CWallet > > GetWallets()
Definition: dummywallet.cpp:71
void UnloadWallet(std::shared_ptr< CWallet > &&wallet)
Explicitly unload and delete the wallet.
Definition: wallet.cpp:129
void scheduleEvery(Function f, std::chrono::milliseconds delta)
Repeat f until the scheduler is stopped.
Definition: scheduler.cpp:123
Bilingual messages:
Definition: translation.h:16
auto Join(const std::vector< T > &list, const BaseType &separator, UnaryOp unary_op) -> decltype(unary_op(list.at(0)))
Join a list of items.
Definition: string.h:34
#define strprintf
Format arguments and return the string or write to given std::ostream (see tinyformat::format doc for...
Definition: tinyformat.h:1164
bool AddWallet(const std::shared_ptr< CWallet > &wallet)
Definition: wallet.cpp:56
static std::shared_ptr< CWallet > CreateWalletFromFile(interfaces::Chain &chain, const WalletLocation &location, bilingual_str &error, std::vector< bilingual_str > &warnings, uint64_t wallet_creation_flags=0)
Definition: wallet.cpp:3705
bilingual_str Untranslated(std::string original)
Mark a bilingual_str as untranslated.
Definition: translation.h:35
static void LogPrintf(const char *fmt, const Args &... args)
Definition: logging.h:164
void MaybeResendWalletTxs()
Called periodically by the schedule thread.
Definition: wallet.cpp:2009
bool GetBoolArg(const std::string &strArg, bool fDefault) const
Return boolean argument or default value.
Definition: system.cpp:391
bool LoadWallets(interfaces::Chain &chain, const std::vector< std::string > &wallet_files)
Load wallet databases.
Definition: load.cpp:69
void ForceSetArg(const std::string &strArg, const std::string &strValue)
Definition: system.cpp:413
void StartWallets(CScheduler &scheduler)
Complete startup of wallets.
Definition: load.cpp:90
void StopWallets()
Stop all wallets. Wallets will be flushed first.
Definition: load.cpp:108
bilingual_str _(const char *psz)
Translation function.
Definition: translation.h:52
void MaybeCompactWalletDB()
Compacts BDB state so that wallet.dat is self-contained (if there are changes)
Definition: walletdb.cpp:949
void FlushWallets()
Flush all wallets in preparation for shutdown.
Definition: load.cpp:101
virtual void initWarning(const bilingual_str &message)=0
Send init warning.
Interface giving clients (wallet processes, maybe other analysis tools in the future) ability to acce...
Definition: chain.h:79
std::string GetArg(const std::string &strArg, const std::string &strDefault) const
Return string argument or default value.
Definition: system.cpp:379
virtual void initMessage(const std::string &message)=0
Send init message.
bool RemoveWallet(const std::shared_ptr< CWallet > &wallet)
Definition: wallet.cpp:67
ArgsManager gArgs
Definition: system.cpp:76
fs::path GetWalletDir()
Get the path of the wallet directory.
Definition: dummywallet.cpp:61
The WalletLocation class provides wallet information.
Definition: walletutil.h:71
void UnloadWallets()
Close all wallets.
Definition: load.cpp:115
static bool Verify(interfaces::Chain &chain, const WalletLocation &location, bool salvage_wallet, bilingual_str &error_string, std::vector< bilingual_str > &warnings)
Verify wallet naming and perform salvage on the wallet if required.
Definition: wallet.cpp:3653
bool VerifyWallets(interfaces::Chain &chain, const std::vector< std::string > &wallet_files)
Responsible for reading and validating the -wallet arguments and verifying the wallet database...
Definition: load.cpp:15
virtual void initError(const bilingual_str &message)=0
Send init error.
bool error(const char *fmt, const Args &... args)
Definition: system.h:49