Browse Source

Make CCryptoKeyStore::Unlock check all keys.

CCryptoKeyStore::Unlock has a loop to attempt decrypting each key which
 only executes once, likely due to a simple mistake when the code was
 originally written.

This patch fixes the behavior by making it check all keys. It also adds
 a fatal assertion in the case some decrypt but some do not, since that
 indicates that the wallet is in some kind of really bad state.

This may make unlocking noticeably slower on wallets with many keys.
0.10
Gregory Maxwell 11 years ago committed by Matt Corallo
parent
commit
1e21c17d20
  1. 26
      src/crypter.cpp

26
src/crypter.cpp

@ -152,6 +152,8 @@ bool CCryptoKeyStore::Unlock(const CKeyingMaterial& vMasterKeyIn)
if (!SetCrypted()) if (!SetCrypted())
return false; return false;
bool keyPass = false;
bool keyFail = false;
CryptedKeyMap::const_iterator mi = mapCryptedKeys.begin(); CryptedKeyMap::const_iterator mi = mapCryptedKeys.begin();
for (; mi != mapCryptedKeys.end(); ++mi) for (; mi != mapCryptedKeys.end(); ++mi)
{ {
@ -159,15 +161,31 @@ bool CCryptoKeyStore::Unlock(const CKeyingMaterial& vMasterKeyIn)
const std::vector<unsigned char> &vchCryptedSecret = (*mi).second.second; const std::vector<unsigned char> &vchCryptedSecret = (*mi).second.second;
CKeyingMaterial vchSecret; CKeyingMaterial vchSecret;
if(!DecryptSecret(vMasterKeyIn, vchCryptedSecret, vchPubKey.GetHash(), vchSecret)) if(!DecryptSecret(vMasterKeyIn, vchCryptedSecret, vchPubKey.GetHash(), vchSecret))
return false; {
keyFail = true;
break;
}
if (vchSecret.size() != 32) if (vchSecret.size() != 32)
return false; {
keyFail = true;
break;
}
CKey key; CKey key;
key.Set(vchSecret.begin(), vchSecret.end(), vchPubKey.IsCompressed()); key.Set(vchSecret.begin(), vchSecret.end(), vchPubKey.IsCompressed());
if (key.GetPubKey() == vchPubKey) if (key.GetPubKey() != vchPubKey)
{
keyFail = true;
break; break;
return false;
} }
keyPass = true;
}
if (keyPass && keyFail)
{
LogPrintf("The wallet is probably corrupted: Some keys decrypt but not all.");
assert(false);
}
if (keyFail || !keyPass)
return false;
vMasterKey = vMasterKeyIn; vMasterKey = vMasterKeyIn;
} }
NotifyStatusChanged(this); NotifyStatusChanged(this);

Loading…
Cancel
Save