Merge #13437: wallet: Erase wtxOrderd wtx pointer on removeprunedfunds

faa18ca046e9043b2cf68cb1bd17cc8c60fe26d9 wallet: Erase wtxOrderd wtx pointer on removeprunedfunds (MarcoFalke)

Pull request description:

  This prevents segfaults, when reading from the freed memory.

Tree-SHA512: 04f8190dea7901cf1cc298d5db98c83b02858f27114c5ef4da738accd176d6647d6b81f3dc39f3d5912b1a981cf0599370fd391c4154ffbde97afc1fac389123
This commit is contained in:
Wladimir J. van der Laan 2018-06-18 17:27:11 +02:00 committed by Pasta
parent 15fb6dbf05
commit 23704daaf0
2 changed files with 13 additions and 7 deletions

View File

@ -1063,11 +1063,10 @@ bool CWallet::AddToWallet(const CWalletTx& wtxIn, bool fFlushOnClose)
CWalletTx& wtx = (*ret.first).second; CWalletTx& wtx = (*ret.first).second;
wtx.BindWallet(this); wtx.BindWallet(this);
bool fInsertedNew = ret.second; bool fInsertedNew = ret.second;
if (fInsertedNew) if (fInsertedNew) {
{
wtx.nTimeReceived = GetAdjustedTime(); wtx.nTimeReceived = GetAdjustedTime();
wtx.nOrderPos = IncOrderPosNext(&walletdb); wtx.nOrderPos = IncOrderPosNext(&walletdb);
wtxOrdered.insert(std::make_pair(wtx.nOrderPos, TxPair(&wtx, nullptr))); wtx.m_it_wtxOrdered = wtxOrdered.insert(std::make_pair(wtx.nOrderPos, TxPair(&wtx, nullptr)));
wtx.nTimeSmart = ComputeTimeSmart(wtx); wtx.nTimeSmart = ComputeTimeSmart(wtx);
AddToSpends(hash); AddToSpends(hash);
@ -1141,9 +1140,12 @@ bool CWallet::AddToWallet(const CWalletTx& wtxIn, bool fFlushOnClose)
bool CWallet::LoadToWallet(const CWalletTx& wtxIn) bool CWallet::LoadToWallet(const CWalletTx& wtxIn)
{ {
uint256 hash = wtxIn.GetHash(); uint256 hash = wtxIn.GetHash();
CWalletTx& wtx = mapWallet.emplace(hash, wtxIn).first->second; const auto& ins = mapWallet.emplace(hash, wtxIn);
CWalletTx& wtx = ins.first->second;
wtx.BindWallet(this); wtx.BindWallet(this);
wtxOrdered.insert(std::make_pair(wtx.nOrderPos, TxPair(&wtx, nullptr))); if (/* insertion took place */ ins.second) {
wtx.m_it_wtxOrdered = wtxOrdered.insert(std::make_pair(wtx.nOrderPos, TxPair(&wtx, nullptr)));
}
AddToSpends(hash); AddToSpends(hash);
for (const CTxIn& txin : wtx.tx->vin) { for (const CTxIn& txin : wtx.tx->vin) {
auto it = mapWallet.find(txin.prevout.hash); auto it = mapWallet.find(txin.prevout.hash);
@ -4172,8 +4174,11 @@ DBErrors CWallet::ZapSelectTx(std::vector<uint256>& vHashIn, std::vector<uint256
{ {
AssertLockHeld(cs_wallet); // mapWallet AssertLockHeld(cs_wallet); // mapWallet
DBErrors nZapSelectTxRet = CWalletDB(*dbw,"cr+").ZapSelectTx(vHashIn, vHashOut); DBErrors nZapSelectTxRet = CWalletDB(*dbw,"cr+").ZapSelectTx(vHashIn, vHashOut);
for (uint256 hash : vHashOut) for (uint256 hash : vHashOut) {
mapWallet.erase(hash); const auto& it = mapWallet.find(hash);
wtxOrdered.erase(it->second.m_it_wtxOrdered);
mapWallet.erase(it);
}
if (nZapSelectTxRet == DB_NEED_REWRITE) if (nZapSelectTxRet == DB_NEED_REWRITE)
{ {

View File

@ -331,6 +331,7 @@ public:
char fFromMe; char fFromMe;
std::string strFromAccount; std::string strFromAccount;
int64_t nOrderPos; //!< position in ordered transaction list int64_t nOrderPos; //!< position in ordered transaction list
std::multimap<int64_t, std::pair<CWalletTx*, CAccountingEntry*>>::const_iterator m_it_wtxOrdered;
// memory only // memory only
mutable bool fDebitCached; mutable bool fDebitCached;