Solve chainActive-related locking issues

- In wallet and GUI code LOCK cs_main as well as cs_wallet when
  necessary
- In main.cpp SendMessages move the TRY_LOCK(cs_main) up, to encompass the call
  to IsInitialBlockDownload.
- Make ActivateBestChain, AddToBlockIndex, IsInitialBlockDownload,
  InitBlockIndex acquire the cs_main lock

Fixes #3997
This commit is contained in:
Wladimir J. van der Laan
2014-04-15 17:38:25 +02:00
parent e07c943ce8
commit 55a1db4fa2
7 changed files with 269 additions and 272 deletions

View File

@@ -98,11 +98,21 @@ void WalletModel::updateStatus()
void WalletModel::pollBalanceChanged()
{
if(chainActive.Height() != cachedNumBlocks)
bool heightChanged = false;
{
LOCK(cs_main);
if(chainActive.Height() != cachedNumBlocks)
{
// Balance and number of transactions might have changed
cachedNumBlocks = chainActive.Height();
heightChanged = true;
}
}
if(heightChanged)
{
// Balance and number of transactions might have changed
cachedNumBlocks = chainActive.Height();
checkBalanceChanged();
if(transactionTableModel)
transactionTableModel->updateConfirmations();
}
}
@@ -520,7 +530,7 @@ bool WalletModel::getPubKey(const CKeyID &address, CPubKey& vchPubKeyOut) const
// returns a list of COutputs from COutPoints
void WalletModel::getOutputs(const std::vector<COutPoint>& vOutpoints, std::vector<COutput>& vOutputs)
{
LOCK(wallet->cs_wallet);
LOCK2(cs_main, wallet->cs_wallet);
BOOST_FOREACH(const COutPoint& outpoint, vOutpoints)
{
if (!wallet->mapWallet.count(outpoint.hash)) continue;
@@ -533,7 +543,7 @@ void WalletModel::getOutputs(const std::vector<COutPoint>& vOutpoints, std::vect
bool WalletModel::isSpent(const COutPoint& outpoint) const
{
LOCK(wallet->cs_wallet);
LOCK2(cs_main, wallet->cs_wallet);
return wallet->IsSpent(outpoint.hash, outpoint.n);
}
@@ -543,7 +553,7 @@ void WalletModel::listCoins(std::map<QString, std::vector<COutput> >& mapCoins)
std::vector<COutput> vCoins;
wallet->AvailableCoins(vCoins);
LOCK(wallet->cs_wallet); // ListLockedCoins, mapWallet
LOCK2(cs_main, wallet->cs_wallet); // ListLockedCoins, mapWallet
std::vector<COutPoint> vLockedCoins;
wallet->ListLockedCoins(vLockedCoins);
@@ -575,25 +585,25 @@ void WalletModel::listCoins(std::map<QString, std::vector<COutput> >& mapCoins)
bool WalletModel::isLockedCoin(uint256 hash, unsigned int n) const
{
LOCK(wallet->cs_wallet);
LOCK2(cs_main, wallet->cs_wallet);
return wallet->IsLockedCoin(hash, n);
}
void WalletModel::lockCoin(COutPoint& output)
{
LOCK(wallet->cs_wallet);
LOCK2(cs_main, wallet->cs_wallet);
wallet->LockCoin(output);
}
void WalletModel::unlockCoin(COutPoint& output)
{
LOCK(wallet->cs_wallet);
LOCK2(cs_main, wallet->cs_wallet);
wallet->UnlockCoin(output);
}
void WalletModel::listLockedCoins(std::vector<COutPoint>& vOutpts)
{
LOCK(wallet->cs_wallet);
LOCK2(cs_main, wallet->cs_wallet);
wallet->ListLockedCoins(vOutpts);
}