Skip to content

Commit 2aa6657

Browse files
author
Benoît Bleuzé
committed
Crypto: Add any digest to key generation.
1 parent 245a628 commit 2aa6657

4 files changed

Lines changed: 36 additions & 13 deletions

File tree

Crypto/include/Poco/Crypto/CipherKey.h

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,16 @@ class Crypto_API CipherKey
4747
/// std::string salt("asdff8723lasdf(**923412");
4848
/// CipherKey key("aes-256", password, salt);
4949
///
50+
/// You may also control the digest and the number of iterations used to generate the key
51+
/// by specifying the specific values. Here we create a key with the same data as before,
52+
/// except that we use 100 iterations instead of DEFAULT_ITERATION_COUNT, and sha1 instead of
53+
/// the default md5:
54+
///
55+
/// std::string password = "secret";
56+
/// std::string salt("asdff8723lasdf(**923412");
57+
/// std::string digest ("sha1");
58+
/// CipherKey key("aes-256", password, salt, 100, digest);
59+
///
5060
{
5161
public:
5262
typedef CipherKeyImpl::Mode Mode;
@@ -63,9 +73,10 @@ class Crypto_API CipherKey
6373
CipherKey(const std::string& name,
6474
const std::string& passphrase,
6575
const std::string& salt = "",
66-
int iterationCount = DEFAULT_ITERATION_COUNT);
76+
int iterationCount = DEFAULT_ITERATION_COUNT,
77+
const std::string& digest = "md5");
6778
/// Creates a new CipherKeyImpl object using the given
68-
/// cipher name, passphrase, salt value and iteration count.
79+
/// cipher name, passphrase, salt value, iteration count and digest.
6980

7081
CipherKey(const std::string& name,
7182
const ByteVec& key,

Crypto/include/Poco/Crypto/CipherKeyImpl.h

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -53,17 +53,19 @@ class CipherKeyImpl: public RefCountedObject
5353
MODE_OFB /// Output feedback
5454
};
5555

56-
CipherKeyImpl(const std::string& name,
57-
const std::string& passphrase,
56+
CipherKeyImpl(const std::string& name,
57+
const std::string& passphrase,
5858
const std::string& salt,
59-
int iterationCount);
59+
int iterationCount,
60+
const std::string &digest);
6061
/// Creates a new CipherKeyImpl object, using
6162
/// the given cipher name, passphrase, salt value
6263
/// and iteration count.
6364

6465
CipherKeyImpl(const std::string& name,
6566
const ByteVec& key,
66-
const ByteVec& iv);
67+
const ByteVec& iv
68+
);
6769
/// Creates a new CipherKeyImpl object, using the
6870
/// given cipher name, key and initialization vector.
6971

@@ -118,6 +120,7 @@ class CipherKeyImpl: public RefCountedObject
118120

119121
private:
120122
const EVP_CIPHER* _pCipher;
123+
const EVP_MD* _pDigest;
121124
std::string _name;
122125
ByteVec _key;
123126
ByteVec _iv;

Crypto/src/CipherKey.cpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,8 +21,9 @@ namespace Poco {
2121
namespace Crypto {
2222

2323

24-
CipherKey::CipherKey(const std::string& name, const std::string& passphrase, const std::string& salt, int iterationCount):
25-
_pImpl(new CipherKeyImpl(name, passphrase, salt, iterationCount))
24+
CipherKey::CipherKey(const std::string& name, const std::string& passphrase, const std::string& salt, int iterationCount,
25+
const std::string &digest):
26+
_pImpl(new CipherKeyImpl(name, passphrase, salt, iterationCount, digest))
2627
{
2728
}
2829

Crypto/src/CipherKeyImpl.cpp

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -27,11 +27,13 @@ namespace Poco {
2727
namespace Crypto {
2828

2929

30-
CipherKeyImpl::CipherKeyImpl(const std::string& name,
30+
CipherKeyImpl::CipherKeyImpl(const std::string& name,
3131
const std::string& passphrase,
3232
const std::string& salt,
33-
int iterationCount):
33+
int iterationCount,
34+
const std::string& digest):
3435
_pCipher(0),
36+
_pDigest(0),
3537
_name(name),
3638
_key(),
3739
_iv()
@@ -42,6 +44,13 @@ CipherKeyImpl::CipherKeyImpl(const std::string& name,
4244

4345
if (!_pCipher)
4446
throw Poco::NotFoundException("Cipher " + name + " was not found");
47+
48+
_pDigest = EVP_get_digestbyname(digest.c_str());
49+
50+
if (!_pDigest)
51+
throw Poco::NotFoundException("Digest " + name + " was not found");
52+
53+
4554
_key = ByteVec(keySize());
4655
_iv = ByteVec(ivSize());
4756
generateKey(passphrase, salt, iterationCount);
@@ -145,7 +154,6 @@ void CipherKeyImpl::generateKey(
145154

146155
// OpenSSL documentation specifies that the salt must be an 8-byte array.
147156
unsigned char saltBytes[8];
148-
149157
if (!salt.empty())
150158
{
151159
int len = static_cast<int>(salt.size());
@@ -156,10 +164,10 @@ void CipherKeyImpl::generateKey(
156164
saltBytes[i % 8] ^= salt.at(i);
157165
}
158166

159-
// Now create the key and IV, using the MD5 digest algorithm.
167+
// Now create the key and IV, using the digest set in the constructor.
160168
int keySize = EVP_BytesToKey(
161169
_pCipher,
162-
EVP_md5(),
170+
_pDigest,
163171
(salt.empty() ? 0 : saltBytes),
164172
reinterpret_cast<const unsigned char*>(password.data()),
165173
static_cast<int>(password.size()),

0 commit comments

Comments
 (0)