Skip to content

Commit

Permalink
wallet: let ListWalletDir do not iterate trough our blocksdata.
Browse files Browse the repository at this point in the history
When WalletDir == DataDir we would have iterate trough our own node files
to find wallets, that consumes time and could cause an unresponsive node.
  • Loading branch information
Saibato committed Oct 17, 2020
1 parent 80c8a02 commit c730c7a
Showing 1 changed file with 47 additions and 17 deletions.
64 changes: 47 additions & 17 deletions src/wallet/walletutil.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@

#include <wallet/walletutil.h>

#include <algorithm>

#include <logging.h>
#include <util/system.h>

Expand Down Expand Up @@ -35,36 +37,64 @@ fs::path GetWalletDir()
std::vector<fs::path> ListWalletDir()
{
const fs::path wallet_dir = GetWalletDir();
const fs::path data_dir = GetDataDir();
const fs::path blocks_dir = GetBlocksDir();

const size_t offset = wallet_dir.string().size() + 1;
std::vector<fs::path> paths;
boost::system::error_code ec;

// Here we place the top level dirs we want to skip in case walletdir is datadir or blocksdir
// Those directories are referenced in doc/files.md
const std::set<fs::path> ignore_paths = {
blocks_dir,
data_dir / "blktree",
data_dir / "blocks",
data_dir / "chainstate",
data_dir / "coins",
data_dir / "database",
data_dir / "indexes",
data_dir / "regtest",
data_dir / "signet",
data_dir / "testnet3"
};

for (auto it = fs::recursive_directory_iterator(wallet_dir, ec); it != fs::recursive_directory_iterator(); it.increment(ec)) {
if (ec) {
LogPrintf("%s: %s %s\n", __func__, ec.message(), it->path().string());
continue;
}

// Get wallet path relative to walletdir by removing walletdir from the wallet path.
// This can be replaced by boost::filesystem::lexically_relative once boost is bumped to 1.60.
const fs::path path = it->path().string().substr(offset);
// We don't want to iterate through those special node dirs
if (ignore_paths.count(it->path())) {
it.no_push();
continue;
}

try {
// Get wallet path relative to walletdir by removing walletdir from the wallet path.
// This can be replaced by boost::filesystem::lexically_relative once boost is bumped to 1.60.
const fs::path path = it->path().string().substr(offset);

if (it->status().type() == fs::directory_file &&
(ExistsBerkeleyDatabase(it->path()) || ExistsSQLiteDatabase(it->path()))) {
// Found a directory which contains wallet.dat btree file, add it as a wallet.
paths.emplace_back(path);
} else if (it.level() == 0 && it->symlink_status().type() == fs::regular_file && ExistsBerkeleyDatabase(it->path())) {
if (it->path().filename() == "wallet.dat") {
// Found top-level wallet.dat btree file, add top level directory ""
// as a wallet.
paths.emplace_back();
} else {
// Found top-level btree file not called wallet.dat. Current bitcoin
// software will never create these files but will allow them to be
// opened in a shared database environment for backwards compatibility.
// Add it to the list of available wallets.
if (it->status().type() == fs::directory_file &&
(ExistsBerkeleyDatabase(it->path()) || ExistsSQLiteDatabase(it->path()))) {
// Found a directory which contains wallet.dat btree file, add it as a wallet.
paths.emplace_back(path);
} else if (it.level() == 0 && it->symlink_status().type() == fs::regular_file && ExistsBerkeleyDatabase(it->path())) {
if (it->path().filename() == "wallet.dat") {
// Found top-level wallet.dat btree file, add top level directory ""
// as a wallet.
paths.emplace_back();
} else {
// Found top-level btree file not called wallet.dat. Current bitcoin
// software will never create these files but will allow them to be
// opened in a shared database environment for backwards compatibility.
// Add it to the list of available wallets.
paths.emplace_back(path);
}
}
} catch (const std::exception& e) {
LogPrintf("%s: Error scanning %s: %s\n", __func__, it->path().string(), e.what());
}
}

Expand Down

0 comments on commit c730c7a

Please sign in to comment.