[WIP] [wallet] dynamic loading/unloading of wallets #10740
Open
Commits
Show all changes
19 commits
Select commit
Hold shift + click to select a range
a952c04
[wallet] [tests] multiwallet test
jnewbery 5d18ee0
[wallet] [rpc] print wallet name in getwalletinfo
jnewbery 754434a
[wallet] fix comment for CWallet::Verify()
jnewbery 74882ca
[wallet] [rpc] Add listwallets RPC
jnewbery 851cf9f
[wallet] Add walletinit.cpp
jnewbery a863dc3
[wallet] move WalletParameterInteraction() to walletinit.cpp
jnewbery 3954d79
[wallet] move VerifyWallets() to walletinit.cpp
jnewbery 4ba8d57
[wallet] Allow individual wallets to be verified
jnewbery 533eb5e
[wallet] move InitLoadWallets() to walletinit.cpp
jnewbery 34d0690
fixup with Allow individual wallets to be verified
jnewbery 4c62008
[wallet] move calls to postInitProcess() to walletinit.cpp
jnewbery 10e781b
[wallet] move FlushWallets and DeleteWallets to walletinit.cpp
jnewbery 0efbd06
[wallet] add CDBEnv::Shutdown() function
jnewbery d1a1218
[wallet] call CDBEnv.shutdown() from FlushWallets()
jnewbery 267a74e
[wallet] remove early call to FlushWallets()
jnewbery d4f6a0f
[wallet] add loadwallet RPC
jnewbery 8d32ecc
[wallet] add unloadwallet rpc
jnewbery 17549a4
[wallet] add cs_wallets to protect vpwallets
jnewbery 72c3745
[wallet] [test] update multiwallet.py to use loadwallet and unloadwallet
jnewbery
Jump to file or symbol
Failed to load files and symbols.
31
src/init.cpp
| @@ -43,7 +43,7 @@ | ||
| #include "utilmoneystr.h" | ||
| #include "validationinterface.h" | ||
| #ifdef ENABLE_WALLET | ||
| -#include "wallet/wallet.h" | ||
| +#include "wallet/walletinit.h" | ||
| #endif | ||
| #include "warnings.h" | ||
| #include <stdint.h> | ||
| @@ -187,11 +187,6 @@ void Shutdown() | ||
| StopREST(); | ||
| StopRPC(); | ||
| StopHTTPServer(); | ||
| -#ifdef ENABLE_WALLET | ||
| - for (CWalletRef pwallet : vpwallets) { | ||
| - pwallet->Flush(false); | ||
| - } | ||
| -#endif | ||
| MapPort(false); | ||
| UnregisterValidationInterface(peerLogic.get()); | ||
| peerLogic.reset(); | ||
| @@ -230,9 +225,7 @@ void Shutdown() | ||
| pblocktree = NULL; | ||
| } | ||
| #ifdef ENABLE_WALLET | ||
| - for (CWalletRef pwallet : vpwallets) { | ||
| - pwallet->Flush(true); | ||
| - } | ||
| + ShutdownWallets(); | ||
| #endif | ||
| #if ENABLE_ZMQ | ||
| @@ -252,10 +245,7 @@ void Shutdown() | ||
| #endif | ||
| UnregisterAllValidationInterfaces(); | ||
| #ifdef ENABLE_WALLET | ||
| - for (CWalletRef pwallet : vpwallets) { | ||
| - delete pwallet; | ||
| - } | ||
| - vpwallets.clear(); | ||
| + DeleteWallets(); | ||
jnewbery
Member
|
||
| #endif | ||
| globalVerifyHandle.reset(); | ||
| ECC_Stop(); | ||
| @@ -404,7 +394,7 @@ std::string HelpMessage(HelpMessageMode mode) | ||
| strUsage += HelpMessageOpt("-maxuploadtarget=<n>", strprintf(_("Tries to keep outbound traffic under the given target (in MiB per 24h), 0 = no limit (default: %d)"), DEFAULT_MAX_UPLOAD_TARGET)); | ||
| #ifdef ENABLE_WALLET | ||
| - strUsage += CWallet::GetWalletHelpString(showDebug); | ||
| + strUsage += GetWalletHelpString(showDebug); | ||
| #endif | ||
| #if ENABLE_ZMQ | ||
| @@ -1052,8 +1042,7 @@ bool AppInitParameterInteraction() | ||
| nBytesPerSigOp = GetArg("-bytespersigop", nBytesPerSigOp); | ||
| #ifdef ENABLE_WALLET | ||
| - if (!CWallet::ParameterInteraction()) | ||
| - return false; | ||
| + if (!WalletParameterInteraction()) return false; | ||
| #endif | ||
| fIsBareMultisigStd = GetBoolArg("-permitbaremultisig", DEFAULT_PERMIT_BAREMULTISIG); | ||
| @@ -1219,8 +1208,7 @@ bool AppInitMain(boost::thread_group& threadGroup, CScheduler& scheduler) | ||
| // ********************************************************* Step 5: verify wallet database integrity | ||
| #ifdef ENABLE_WALLET | ||
| - if (!CWallet::Verify()) | ||
| - return false; | ||
| + if (!VerifyWallets()) return false; | ||
| #endif | ||
| // ********************************************************* Step 6: network initialization | ||
| // Note that we absolutely cannot open any actual connections | ||
| @@ -1507,8 +1495,7 @@ bool AppInitMain(boost::thread_group& threadGroup, CScheduler& scheduler) | ||
| // ********************************************************* Step 8: load wallet | ||
| #ifdef ENABLE_WALLET | ||
| - if (!CWallet::InitLoadWallet()) | ||
| - return false; | ||
| + if (!InitLoadWallets()) return false; | ||
| #else | ||
| LogPrintf("No wallet support compiled in!\n"); | ||
| #endif | ||
| @@ -1638,9 +1625,7 @@ bool AppInitMain(boost::thread_group& threadGroup, CScheduler& scheduler) | ||
| uiInterface.InitMessage(_("Done loading")); | ||
| #ifdef ENABLE_WALLET | ||
| - for (CWalletRef pwallet : vpwallets) { | ||
| - pwallet->postInitProcess(scheduler); | ||
| - } | ||
| + WalletCompleteStartup(scheduler); | ||
| #endif | ||
| return !fRequestShutdown; | ||
| @@ -227,40 +227,12 @@ bool CDB::Recover(const std::string& filename, void *callbackDataIn, bool (*reco | ||
| bool CDB::VerifyEnvironment(const std::string& walletFile, const fs::path& dataDir, std::string& errorStr) | ||
| { | ||
| - LogPrintf("Using BerkeleyDB version %s\n", DbEnv::version(0, 0, 0)); | ||
jonasschnelli
Member
|
||
| - LogPrintf("Using wallet %s\n", walletFile); | ||
| - | ||
| - // Wallet file must be a plain filename without a directory | ||
| - if (walletFile != fs::basename(walletFile) + fs::extension(walletFile)) | ||
| - { | ||
| - errorStr = strprintf(_("Wallet %s resides outside data directory %s"), walletFile, dataDir.string()); | ||
| - return false; | ||
| - } | ||
| - | ||
| - if (!bitdb.Open(dataDir)) | ||
| - { | ||
| - // try moving the database env out of the way | ||
| - fs::path pathDatabase = dataDir / "database"; | ||
| - fs::path pathDatabaseBak = dataDir / strprintf("database.%d.bak", GetTime()); | ||
| - try { | ||
| - fs::rename(pathDatabase, pathDatabaseBak); | ||
| - LogPrintf("Moved old %s to %s. Retrying.\n", pathDatabase.string(), pathDatabaseBak.string()); | ||
| - } catch (const fs::filesystem_error&) { | ||
| - // failure is ok (well, not really, but it's not worse than what we started with) | ||
| - } | ||
| - | ||
| - // try again | ||
| - if (!bitdb.Open(dataDir)) { | ||
| - // if it still fails, it probably means we can't even create the database env | ||
| - errorStr = strprintf(_("Error initializing wallet database environment %s!"), GetDataDir()); | ||
| - return false; | ||
| - } | ||
| - } | ||
| return true; | ||
| } | ||
| bool CDB::VerifyDatabaseFile(const std::string& walletFile, const fs::path& dataDir, std::string& warningStr, std::string& errorStr, CDBEnv::recoverFunc_type recoverFunc) | ||
| { | ||
| + LogPrintf("Using wallet %s\n", walletFile); | ||
| if (fs::exists(dataDir / walletFile)) | ||
| { | ||
| std::string backup_filename; | ||
| @@ -558,22 +530,32 @@ bool CDB::Rewrite(CWalletDBWrapper& dbw, const char* pszSkip) | ||
| return false; | ||
| } | ||
| +void CDBEnv::Shutdown() | ||
| +{ | ||
| + char** listp; | ||
| + if (mapFileUseCount.empty()) { | ||
| + dbenv->log_archive(&listp, DB_ARCH_REMOVE); | ||
| + Close(); | ||
| + if (!fMockDb) | ||
| + fs::remove_all(fs::path(strPath) / "database"); | ||
| + } | ||
| +} | ||
| -void CDBEnv::Flush(bool fShutdown) | ||
| +void CDBEnv::Flush(std::string strFile) | ||
| { | ||
| int64_t nStart = GetTimeMillis(); | ||
| // Flush log data to the actual data file on all files that are not in use | ||
| - LogPrint(BCLog::DB, "CDBEnv::Flush: Flush(%s)%s\n", fShutdown ? "true" : "false", fDbEnvInit ? "" : " database not started"); | ||
| + LogPrint(BCLog::DB, "CDBEnv::Flush: Flush%s\n", fDbEnvInit ? "" : " database not started"); | ||
| if (!fDbEnvInit) | ||
| return; | ||
| { | ||
| LOCK(cs_db); | ||
| std::map<std::string, int>::iterator mi = mapFileUseCount.begin(); | ||
| while (mi != mapFileUseCount.end()) { | ||
| - std::string strFile = (*mi).first; | ||
| + std::string foundStrFile = (*mi).first; | ||
| int nRefCount = (*mi).second; | ||
| - LogPrint(BCLog::DB, "CDBEnv::Flush: Flushing %s (refcount = %d)...\n", strFile, nRefCount); | ||
| - if (nRefCount == 0) { | ||
| + if (foundStrFile == strFile && nRefCount == 0) { | ||
| + LogPrint(BCLog::DB, "CDBEnv::Flush: Flushing %s (refcount = %d)...\n", strFile, nRefCount); | ||
| // Move log data to the dat file | ||
| CloseDb(strFile); | ||
| LogPrint(BCLog::DB, "CDBEnv::Flush: %s checkpoint\n", strFile); | ||
| @@ -586,16 +568,7 @@ void CDBEnv::Flush(bool fShutdown) | ||
| } else | ||
| mi++; | ||
| } | ||
| - LogPrint(BCLog::DB, "CDBEnv::Flush: Flush(%s)%s took %15dms\n", fShutdown ? "true" : "false", fDbEnvInit ? "" : " database not started", GetTimeMillis() - nStart); | ||
| - if (fShutdown) { | ||
| - char** listp; | ||
| - if (mapFileUseCount.empty()) { | ||
| - dbenv->log_archive(&listp, DB_ARCH_REMOVE); | ||
| - Close(); | ||
| - if (!fMockDb) | ||
| - fs::remove_all(fs::path(strPath) / "database"); | ||
| - } | ||
| - } | ||
| + LogPrint(BCLog::DB, "CDBEnv::Flush: Flush took %15dms\n", GetTimeMillis() - nStart); | ||
| } | ||
| } | ||
| @@ -684,9 +657,9 @@ bool CWalletDBWrapper::Backup(const std::string& strDest) | ||
| return false; | ||
| } | ||
| -void CWalletDBWrapper::Flush(bool shutdown) | ||
| +void CWalletDBWrapper::Flush() | ||
| { | ||
| if (!IsDummy()) { | ||
| - env->Flush(shutdown); | ||
| + env->Flush(strFile); | ||
| } | ||
| } | ||
Oops, something went wrong.
It'd probably call this
deallocWallets()