|
|
@ -5,6 +5,7 @@ |
|
|
|
#include "crypter.h" |
|
|
|
#include "crypter.h" |
|
|
|
|
|
|
|
|
|
|
|
#include "crypto/aes.h" |
|
|
|
#include "crypto/aes.h" |
|
|
|
|
|
|
|
#include "crypto/sha512.h" |
|
|
|
#include "script/script.h" |
|
|
|
#include "script/script.h" |
|
|
|
#include "script/standard.h" |
|
|
|
#include "script/standard.h" |
|
|
|
#include "util.h" |
|
|
|
#include "util.h" |
|
|
@ -12,8 +13,33 @@ |
|
|
|
#include <string> |
|
|
|
#include <string> |
|
|
|
#include <vector> |
|
|
|
#include <vector> |
|
|
|
#include <boost/foreach.hpp> |
|
|
|
#include <boost/foreach.hpp> |
|
|
|
#include <openssl/aes.h> |
|
|
|
|
|
|
|
#include <openssl/evp.h> |
|
|
|
int CCrypter::BytesToKeySHA512AES(const std::vector<unsigned char>& chSalt, const SecureString& strKeyData, int count, unsigned char *key,unsigned char *iv) const |
|
|
|
|
|
|
|
{ |
|
|
|
|
|
|
|
// This mimics the behavior of openssl's EVP_BytesToKey with an aes256cbc
|
|
|
|
|
|
|
|
// cipher and sha512 message digest. Because sha512's output size (64b) is
|
|
|
|
|
|
|
|
// greater than the aes256 block size (16b) + aes256 key size (32b),
|
|
|
|
|
|
|
|
// there's no need to process more than once (D_0).
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if(!count || !key || !iv) |
|
|
|
|
|
|
|
return 0; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
unsigned char buf[CSHA512::OUTPUT_SIZE]; |
|
|
|
|
|
|
|
CSHA512 di; |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
di.Write((const unsigned char*)strKeyData.c_str(), strKeyData.size()); |
|
|
|
|
|
|
|
if(chSalt.size()) |
|
|
|
|
|
|
|
di.Write(&chSalt[0], chSalt.size()); |
|
|
|
|
|
|
|
di.Finalize(buf); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
for(int i = 0; i != count - 1; i++) |
|
|
|
|
|
|
|
di.Reset().Write(buf, sizeof(buf)).Finalize(buf); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
memcpy(key, buf, WALLET_CRYPTO_KEY_SIZE); |
|
|
|
|
|
|
|
memcpy(iv, buf + WALLET_CRYPTO_KEY_SIZE, WALLET_CRYPTO_IV_SIZE); |
|
|
|
|
|
|
|
memory_cleanse(buf, sizeof(buf)); |
|
|
|
|
|
|
|
return WALLET_CRYPTO_KEY_SIZE; |
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
bool CCrypter::SetKeyFromPassphrase(const SecureString& strKeyData, const std::vector<unsigned char>& chSalt, const unsigned int nRounds, const unsigned int nDerivationMethod) |
|
|
|
bool CCrypter::SetKeyFromPassphrase(const SecureString& strKeyData, const std::vector<unsigned char>& chSalt, const unsigned int nRounds, const unsigned int nDerivationMethod) |
|
|
|
{ |
|
|
|
{ |
|
|
@ -22,8 +48,7 @@ bool CCrypter::SetKeyFromPassphrase(const SecureString& strKeyData, const std::v |
|
|
|
|
|
|
|
|
|
|
|
int i = 0; |
|
|
|
int i = 0; |
|
|
|
if (nDerivationMethod == 0) |
|
|
|
if (nDerivationMethod == 0) |
|
|
|
i = EVP_BytesToKey(EVP_aes_256_cbc(), EVP_sha512(), &chSalt[0], |
|
|
|
i = BytesToKeySHA512AES(chSalt, strKeyData, nRounds, chKey, chIV); |
|
|
|
(unsigned char *)&strKeyData[0], strKeyData.size(), nRounds, chKey, chIV); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
if (i != (int)WALLET_CRYPTO_KEY_SIZE) |
|
|
|
if (i != (int)WALLET_CRYPTO_KEY_SIZE) |
|
|
|
{ |
|
|
|
{ |
|
|
|