summaryrefslogtreecommitdiffstats
path: root/crypto
diff options
context:
space:
mode:
authorwtc@chromium.org <wtc@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-07-31 11:36:37 +0000
committerwtc@chromium.org <wtc@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-07-31 11:36:37 +0000
commit2fe8b630617b48ec4590b04dccf70b87db0a84a0 (patch)
tree8299aa8c9ffebd0de620e7fe73c3c779ec91bd10 /crypto
parentcc405e47896d2b031f8f42a93337538e162ab1e4 (diff)
downloadchromium_src-2fe8b630617b48ec4590b04dccf70b87db0a84a0.zip
chromium_src-2fe8b630617b48ec4590b04dccf70b87db0a84a0.tar.gz
chromium_src-2fe8b630617b48ec4590b04dccf70b87db0a84a0.tar.bz2
Implement QUIC key extraction.
Added a new subkey_secret output to crypto::HKDF which is saved by the forward-secure key derivation and used for a new ExportKeyingMaterial method on QuicCryptoStream. This will be used in Chromium for WebRTC on QUIC. Generated some tests by making a straightforward alternative implementation in Python. Written by Daniel Ziegler. Merge internal CL: 72073257 R=agl@chromium.org,dmziegler@chromium.org BUG= Review URL: https://codereview.chromium.org/423333002 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@286738 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'crypto')
-rw-r--r--crypto/hkdf.cc14
-rw-r--r--crypto/hkdf.h19
-rw-r--r--crypto/hkdf_unittest.cc2
3 files changed, 25 insertions, 10 deletions
diff --git a/crypto/hkdf.cc b/crypto/hkdf.cc
index 1cd8468..82aae24 100644
--- a/crypto/hkdf.cc
+++ b/crypto/hkdf.cc
@@ -5,6 +5,7 @@
#include "crypto/hkdf.h"
#include "base/logging.h"
+#include "base/memory/scoped_ptr.h"
#include "crypto/hmac.h"
namespace crypto {
@@ -15,7 +16,8 @@ HKDF::HKDF(const base::StringPiece& secret,
const base::StringPiece& salt,
const base::StringPiece& info,
size_t key_bytes_to_generate,
- size_t iv_bytes_to_generate) {
+ size_t iv_bytes_to_generate,
+ size_t subkey_secret_bytes_to_generate) {
// https://tools.ietf.org/html/rfc5869#section-2.2
base::StringPiece actual_salt = salt;
char zeros[kSHA256HashLength];
@@ -40,8 +42,9 @@ HKDF::HKDF(const base::StringPiece& secret,
// https://tools.ietf.org/html/rfc5869#section-2.3
// Perform the Expand phase to turn the pseudorandom key
// and info into the output keying material.
- const size_t material_length =
- 2*key_bytes_to_generate + 2*iv_bytes_to_generate;
+ const size_t material_length = 2 * key_bytes_to_generate +
+ 2 * iv_bytes_to_generate +
+ subkey_secret_bytes_to_generate;
const size_t n = (material_length + kSHA256HashLength-1) /
kSHA256HashLength;
DCHECK_LT(n, 256u);
@@ -90,6 +93,11 @@ HKDF::HKDF(const base::StringPiece& secret,
j += iv_bytes_to_generate;
server_write_iv_ = base::StringPiece(reinterpret_cast<char*>(&output_[j]),
iv_bytes_to_generate);
+ j += iv_bytes_to_generate;
+ }
+ if (subkey_secret_bytes_to_generate) {
+ subkey_secret_ = base::StringPiece(reinterpret_cast<char*>(&output_[j]),
+ subkey_secret_bytes_to_generate);
}
}
diff --git a/crypto/hkdf.h b/crypto/hkdf.h
index 1d7a876..e91bccf 100644
--- a/crypto/hkdf.h
+++ b/crypto/hkdf.h
@@ -8,9 +8,7 @@
#include <vector>
#include "base/basictypes.h"
-#include "base/memory/scoped_ptr.h"
#include "base/strings/string_piece.h"
-#include "build/build_config.h"
#include "crypto/crypto_export.h"
namespace crypto {
@@ -20,7 +18,7 @@ namespace crypto {
// See https://tools.ietf.org/html/rfc5869 for details.
class CRYPTO_EXPORT HKDF {
public:
- // |secret|: The input shared secret (or, from RFC 5869, the IKM).
+ // |secret|: the input shared secret (or, from RFC 5869, the IKM).
// |salt|: an (optional) public salt / non-secret random value. While
// optional, callers are strongly recommended to provide a salt. There is no
// added security value in making this larger than the SHA-256 block size of
@@ -28,13 +26,18 @@ class CRYPTO_EXPORT HKDF {
// |info|: an (optional) label to distinguish different uses of HKDF. It is
// optional context and application specific information (can be a zero-length
// string).
- // |key_bytes_to_generate|: the number of bytes of key material to generate.
- // |iv_bytes_to_generate|: the number of bytes of IV to generate.
+ // |key_bytes_to_generate|: the number of bytes of key material to generate
+ // for both client and server.
+ // |iv_bytes_to_generate|: the number of bytes of IV to generate for both
+ // client and server.
+ // |subkey_secret_bytes_to_generate|: the number of bytes of subkey secret to
+ // generate, shared between client and server.
HKDF(const base::StringPiece& secret,
const base::StringPiece& salt,
const base::StringPiece& info,
size_t key_bytes_to_generate,
- size_t iv_bytes_to_generate);
+ size_t iv_bytes_to_generate,
+ size_t subkey_secret_bytes_to_generate);
~HKDF();
base::StringPiece client_write_key() const {
@@ -49,6 +52,9 @@ class CRYPTO_EXPORT HKDF {
base::StringPiece server_write_iv() const {
return server_write_iv_;
}
+ base::StringPiece subkey_secret() const {
+ return subkey_secret_;
+ }
private:
std::vector<uint8> output_;
@@ -57,6 +63,7 @@ class CRYPTO_EXPORT HKDF {
base::StringPiece server_write_key_;
base::StringPiece client_write_iv_;
base::StringPiece server_write_iv_;
+ base::StringPiece subkey_secret_;
};
} // namespace crypto
diff --git a/crypto/hkdf_unittest.cc b/crypto/hkdf_unittest.cc
index dc369d1..bcb19c5 100644
--- a/crypto/hkdf_unittest.cc
+++ b/crypto/hkdf_unittest.cc
@@ -82,7 +82,7 @@ TEST(HKDFTest, HKDF) {
// We set the key_length to the length of the expected output and then take
// the result from the first key, which is the client write key.
- HKDF hkdf(key, salt, info, expected.size(), 0);
+ HKDF hkdf(key, salt, info, expected.size(), 0, 0);
ASSERT_EQ(expected.size(), hkdf.client_write_key().size());
EXPECT_EQ(0, memcmp(expected.data(), hkdf.client_write_key().data(),