Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(868)

Unified Diff: content/child/webcrypto/shared_crypto_unittest.cc

Issue 308523003: [webcrypto] Fix a bug with JWK private key import. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Rebase Created 6 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « content/child/webcrypto/platform_crypto_nss.cc ('k') | content/test/data/webcrypto/rsa_private_keys.json » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: content/child/webcrypto/shared_crypto_unittest.cc
diff --git a/content/child/webcrypto/shared_crypto_unittest.cc b/content/child/webcrypto/shared_crypto_unittest.cc
index 81877f651b1d0c65b006ed5448abb625fc618c99..a25db7760542b637480a8d077e1d5bb736771f95 100644
--- a/content/child/webcrypto/shared_crypto_unittest.cc
+++ b/content/child/webcrypto/shared_crypto_unittest.cc
@@ -90,6 +90,11 @@ bool operator==(const content::webcrypto::CryptoData& a,
memcmp(a.bytes(), b.bytes(), a.byte_length()) == 0;
}
+bool operator!=(const content::webcrypto::CryptoData& a,
+ const content::webcrypto::CryptoData& b) {
+ return !(a == b);
+}
+
namespace {
// -----------------------------------------------------------------------------
@@ -846,12 +851,12 @@ TEST_F(SharedCryptoTest, HMACSampleSets) {
blink::WebCryptoAlgorithm algorithm =
CreateAlgorithm(blink::WebCryptoAlgorithmIdHmac);
- blink::WebCryptoAlgorithm importAlgorithm =
+ blink::WebCryptoAlgorithm import_algorithm =
CreateHmacImportAlgorithm(test_hash.id());
blink::WebCryptoKey key = ImportSecretKeyFromRaw(
test_key,
- importAlgorithm,
+ import_algorithm,
blink::WebCryptoKeyUsageSign | blink::WebCryptoKeyUsageVerify);
EXPECT_EQ(test_hash.id(), key.algorithm().hmacParams()->hash().id());
@@ -2191,6 +2196,127 @@ TEST_F(SharedCryptoTest, MAYBE(ImportRsaPrivateKeyJwkToPkcs8RoundTrip)) {
CryptoData(exported_key_pkcs8));
}
+// Tests importing multiple RSA private keys from JWK, and then exporting to
+// PKCS8.
+//
+// This is a regression test for http://crbug.com/378315, for which importing
+// a sequence of keys from JWK could yield the wrong key. The first key would
+// be imported correctly, however every key after that would actually import
+// the first key.
+TEST_F(SharedCryptoTest, MAYBE(ImportMultipleRSAPrivateKeysJwk)) {
+ scoped_ptr<base::ListValue> key_list;
+ ASSERT_TRUE(ReadJsonTestFileToList("rsa_private_keys.json", &key_list));
+
+ // For this test to be meaningful the keys MUST be kept alive before importing
+ // new keys.
+ std::vector<blink::WebCryptoKey> live_keys;
+
+ for (size_t key_index = 0; key_index < key_list->GetSize(); ++key_index) {
+ SCOPED_TRACE(key_index);
+
+ base::DictionaryValue* key_values;
+ ASSERT_TRUE(key_list->GetDictionary(key_index, &key_values));
+
+ // Get the JWK representation of the key.
+ base::DictionaryValue* key_jwk;
+ ASSERT_TRUE(key_values->GetDictionary("jwk", &key_jwk));
+
+ // Get the PKCS8 representation of the key.
+ std::string pkcs8_hex_string;
+ ASSERT_TRUE(key_values->GetString("pkcs8", &pkcs8_hex_string));
+ std::vector<uint8> pkcs8_bytes = HexStringToBytes(pkcs8_hex_string);
+
+ // Get the modulus length for the key.
+ int modulus_length_bits = 0;
+ ASSERT_TRUE(key_values->GetInteger("modulusLength", &modulus_length_bits));
+
+ blink::WebCryptoKey private_key = blink::WebCryptoKey::createNull();
+
+ // Import the key from JWK.
+ ASSERT_EQ(
+ Status::Success(),
+ ImportKeyJwkFromDict(*key_jwk,
+ CreateRsaHashedImportAlgorithm(
+ blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
+ blink::WebCryptoAlgorithmIdSha256),
+ true,
+ blink::WebCryptoKeyUsageSign,
+ &private_key));
+
+ live_keys.push_back(private_key);
+
+ EXPECT_EQ(
+ modulus_length_bits,
+ static_cast<int>(
+ private_key.algorithm().rsaHashedParams()->modulusLengthBits()));
+
+ // Export to PKCS8 and verify that it matches expectation.
+ std::vector<uint8> exported_key_pkcs8;
+ ASSERT_EQ(
+ Status::Success(),
+ ExportKey(
+ blink::WebCryptoKeyFormatPkcs8, private_key, &exported_key_pkcs8));
+
+ EXPECT_BYTES_EQ(pkcs8_bytes, exported_key_pkcs8);
+ }
+}
+
+// Import an RSA private key using JWK. Next import a JWK containing the same
+// modulus, but mismatched parameters for the rest. It should NOT be possible
+// that the second import retrieves the first key. See http://crbug.com/378315
+// for how that could happen.
+TEST_F(SharedCryptoTest, MAYBE(ImportJwkExistingModulusAndInvalid)) {
+#if defined(USE_NSS)
+ if (!NSS_VersionCheck("3.16.2")) {
+ LOG(WARNING) << "Skipping test because lacks NSS support";
+ return;
+ }
+#endif
+
+ scoped_ptr<base::ListValue> key_list;
+ ASSERT_TRUE(ReadJsonTestFileToList("rsa_private_keys.json", &key_list));
+
+ // Import a 1024-bit private key.
+ base::DictionaryValue* key1_props;
+ ASSERT_TRUE(key_list->GetDictionary(1, &key1_props));
+ base::DictionaryValue* key1_jwk;
+ ASSERT_TRUE(key1_props->GetDictionary("jwk", &key1_jwk));
+
+ blink::WebCryptoKey key1 = blink::WebCryptoKey::createNull();
+ ASSERT_EQ(Status::Success(),
+ ImportKeyJwkFromDict(*key1_jwk,
+ CreateRsaHashedImportAlgorithm(
+ blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
+ blink::WebCryptoAlgorithmIdSha256),
+ true,
+ blink::WebCryptoKeyUsageSign,
+ &key1));
+
+ ASSERT_EQ(1024u, key1.algorithm().rsaHashedParams()->modulusLengthBits());
+
+ // Construct a JWK using the modulus of key1, but all the other fields from
+ // another key (also a 1024-bit private key).
+ base::DictionaryValue* key2_props;
+ ASSERT_TRUE(key_list->GetDictionary(5, &key2_props));
+ base::DictionaryValue* key2_jwk;
+ ASSERT_TRUE(key2_props->GetDictionary("jwk", &key2_jwk));
+ std::string modulus;
+ key1_jwk->GetString("n", &modulus);
+ key2_jwk->SetString("n", modulus);
+
+ // This should fail, as the n,e,d parameters are not consistent. It MUST NOT
+ // somehow return the key created earlier.
+ blink::WebCryptoKey key2 = blink::WebCryptoKey::createNull();
+ ASSERT_EQ(Status::OperationError(),
+ ImportKeyJwkFromDict(*key2_jwk,
+ CreateRsaHashedImportAlgorithm(
+ blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
+ blink::WebCryptoAlgorithmIdSha256),
+ true,
+ blink::WebCryptoKeyUsageSign,
+ &key2));
+}
+
// Import a JWK RSA private key with some optional parameters missing (q, dp,
// dq, qi).
//
@@ -2455,7 +2581,7 @@ TEST_F(SharedCryptoTest, MAYBE(GenerateKeyPairRsa)) {
TEST_F(SharedCryptoTest, MAYBE(RsaSsaSignVerifyFailures)) {
// Import a key pair.
- blink::WebCryptoAlgorithm importAlgorithm =
+ blink::WebCryptoAlgorithm import_algorithm =
CreateRsaHashedImportAlgorithm(blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
blink::WebCryptoAlgorithmIdSha1);
blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
@@ -2463,7 +2589,7 @@ TEST_F(SharedCryptoTest, MAYBE(RsaSsaSignVerifyFailures)) {
ASSERT_NO_FATAL_FAILURE(
ImportRsaKeyPair(HexStringToBytes(kPublicKeySpkiDerHex),
HexStringToBytes(kPrivateKeyPkcs8DerHex),
- importAlgorithm,
+ import_algorithm,
false,
blink::WebCryptoKeyUsageVerify,
blink::WebCryptoKeyUsageSign,
@@ -2588,7 +2714,7 @@ TEST_F(SharedCryptoTest, MAYBE(RsaSignVerifyKnownAnswer)) {
ASSERT_TRUE(ReadJsonTestFileToList("pkcs1v15_sign.json", &tests));
// Import the key pair.
- blink::WebCryptoAlgorithm importAlgorithm =
+ blink::WebCryptoAlgorithm import_algorithm =
CreateRsaHashedImportAlgorithm(blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
blink::WebCryptoAlgorithmIdSha1);
blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
@@ -2596,7 +2722,7 @@ TEST_F(SharedCryptoTest, MAYBE(RsaSignVerifyKnownAnswer)) {
ASSERT_NO_FATAL_FAILURE(
ImportRsaKeyPair(HexStringToBytes(kPublicKeySpkiDerHex),
HexStringToBytes(kPrivateKeyPkcs8DerHex),
- importAlgorithm,
+ import_algorithm,
false,
blink::WebCryptoKeyUsageVerify,
blink::WebCryptoKeyUsageSign,
« no previous file with comments | « content/child/webcrypto/platform_crypto_nss.cc ('k') | content/test/data/webcrypto/rsa_private_keys.json » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698