TEST(WebCryptoRsaSsaTest, ImportExportSpki) {
// Passing case: Import a valid RSA key in SPKI format.
- blink::WebCryptoKey key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey key;
ASSERT_EQ(Status::Success(),
ImportKey(blink::WebCryptoKeyFormatSpki,
CryptoData(HexStringToBytes(kPublicKeySpkiDerHex)),
"010001",
CryptoData(key.algorithm().rsaHashedParams()->publicExponent()));
- // Failing case: Empty SPKI data
- EXPECT_EQ(
- Status::ErrorImportEmptyKeyData(),
- ImportKey(blink::WebCryptoKeyFormatSpki,
- CryptoData(std::vector<uint8_t>()),
- CreateAlgorithm(blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5),
- true,
- blink::WebCryptoKeyUsageVerify,
- &key));
-
- // Failing case: Bad DER encoding.
- EXPECT_EQ(
- Status::DataError(),
- ImportKey(blink::WebCryptoKeyFormatSpki,
- CryptoData(HexStringToBytes("618333c4cb")),
- CreateAlgorithm(blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5),
- true,
- blink::WebCryptoKeyUsageVerify,
- &key));
-
// Failing case: Import RSA key but provide an inconsistent input algorithm.
EXPECT_EQ(Status::ErrorUnsupportedImportKeyFormat(),
ImportKey(blink::WebCryptoKeyFormatSpki,
return;
// Passing case: Import a valid RSA key in PKCS#8 format.
- blink::WebCryptoKey key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey key;
ASSERT_EQ(Status::Success(),
ImportKey(blink::WebCryptoKeyFormatPkcs8,
CryptoData(HexStringToBytes(kPrivateKeyPkcs8DerHex)),
ExportKey(blink::WebCryptoKeyFormatPkcs8, key, &exported_key));
EXPECT_BYTES_EQ_HEX(kPrivateKeyPkcs8DerHex, exported_key);
- // Failing case: Empty PKCS#8 data
- EXPECT_EQ(Status::ErrorImportEmptyKeyData(),
- ImportKey(blink::WebCryptoKeyFormatPkcs8,
- CryptoData(std::vector<uint8_t>()),
- CreateRsaHashedImportAlgorithm(
- blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
- blink::WebCryptoAlgorithmIdSha1),
- true,
- blink::WebCryptoKeyUsageSign,
- &key));
-
- // Failing case: Bad DER encoding.
- EXPECT_EQ(
- Status::DataError(),
- ImportKey(blink::WebCryptoKeyFormatPkcs8,
- CryptoData(HexStringToBytes("618333c4cb")),
- CreateAlgorithm(blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5),
- true,
- blink::WebCryptoKeyUsageSign,
- &key));
-
// Failing case: Import RSA key but provide an inconsistent input algorithm
// and usage. Several issues here:
// * AES-CBC doesn't support PKCS8 key format
&key));
}
-// Tests importing of PKCS8 data that does not define a valid RSA key.
-TEST(WebCryptoRsaSsaTest, ImportInvalidPkcs8) {
- if (!SupportsRsaPrivateKeyImport())
- return;
-
- // kPrivateKeyPkcs8DerHex defines an RSA private key in PKCS8 format, whose
- // parameters appear at the following offsets:
- //
- // n: (offset=36, len=129)
- // e: (offset=167, len=3)
- // d: (offset=173, len=128)
- // p: (offset=303, len=65)
- // q: (offset=370, len=65)
- // dp: (offset=437, len=64)
- // dq; (offset=503, len=64)
- // qi: (offset=569, len=64)
-
- // Do several tests, each of which invert a single byte within the input.
- const unsigned int kOffsetsToCorrupt[] = {
- 50, // inside n
- 168, // inside e
- 175, // inside d
- 333, // inside p
- 373, // inside q
- 450, // inside dp
- 550, // inside dq
- 600, // inside qi
- };
-
- for (size_t test_index = 0; test_index < arraysize(kOffsetsToCorrupt);
- ++test_index) {
- SCOPED_TRACE(test_index);
-
- unsigned int i = kOffsetsToCorrupt[test_index];
- std::vector<uint8_t> corrupted_data =
- HexStringToBytes(kPrivateKeyPkcs8DerHex);
- corrupted_data[i] = ~corrupted_data[i];
-
- blink::WebCryptoKey key = blink::WebCryptoKey::createNull();
- EXPECT_EQ(Status::DataError(),
- ImportKey(blink::WebCryptoKeyFormatPkcs8,
- CryptoData(corrupted_data),
- CreateRsaHashedImportAlgorithm(
- blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
- blink::WebCryptoAlgorithmIdSha1),
- true,
- blink::WebCryptoKeyUsageSign,
- &key));
- }
-}
-
// Tests JWK import and export by doing a roundtrip key conversion and ensuring
// it was lossless:
//
if (!SupportsRsaPrivateKeyImport())
return;
- blink::WebCryptoKey key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey key;
ASSERT_EQ(Status::Success(),
ImportKey(blink::WebCryptoKeyFormatPkcs8,
CryptoData(HexStringToBytes(kPrivateKeyPkcs8DerHex)),
int modulus_length_bits = 0;
ASSERT_TRUE(key_values->GetInteger("modulusLength", &modulus_length_bits));
- blink::WebCryptoKey private_key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey private_key;
// Import the key from JWK.
ASSERT_EQ(
base::DictionaryValue* key1_jwk;
ASSERT_TRUE(key1_props->GetDictionary("jwk", &key1_jwk));
- blink::WebCryptoKey key1 = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey key1;
ASSERT_EQ(Status::Success(),
ImportKeyJwkFromDict(*key1_jwk,
CreateRsaHashedImportAlgorithm(
// 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();
+ blink::WebCryptoKey key2;
ASSERT_EQ(Status::OperationError(),
ImportKeyJwkFromDict(*key2_jwk,
CreateRsaHashedImportAlgorithm(
&key2));
}
-// Import a JWK RSA private key with some optional parameters missing (q, dp,
-// dq, qi).
-//
-// The only optional parameter included is "p".
-//
-// This fails because JWA says that producers must include either ALL optional
-// parameters or NONE.
-TEST(WebCryptoRsaSsaTest, ImportRsaPrivateKeyJwkMissingOptionalParams) {
- blink::WebCryptoKey key = blink::WebCryptoKey::createNull();
-
- base::DictionaryValue dict;
- dict.SetString("kty", "RSA");
- dict.SetString("alg", "RS1");
-
- dict.SetString(
- "n",
- "pW5KDnAQF1iaUYfcfqhB0Vby7A42rVKkTf6x5h962ZHYxRBW_-2xYrTA8oOhKoijlN_"
- "1JqtykcuzB86r_OCx39XNlQgJbVsri2311nHvY3fAkhyyPCcKcOJZjm_4nRnxBazC0_"
- "DLNfKSgOE4a29kxO8i4eHyDQzoz_siSb2aITc");
- dict.SetString("e", "AQAB");
- dict.SetString(
- "d",
- "M6UEKpCyfU9UUcqbu9C0R3GhAa-IQ0Cu-YhfKku-"
- "kuiUpySsPFaMj5eFOtB8AmbIxqPKCSnx6PESMYhEKfxNmuVf7olqEM5wfD7X5zTkRyejlXRQ"
- "GlMmgxCcKrrKuig8MbS9L1PD7jfjUs7jT55QO9gMBiKtecbc7og1R8ajsyU");
-
- dict.SetString("p",
- "5-"
- "iUJyCod1Fyc6NWBT6iobwMlKpy1VxuhilrLfyWeUjApyy8zKfqyzVwbgmh31W"
- "hU1vZs8w0Fgs7bc0-2o5kQw");
-
- ASSERT_EQ(Status::ErrorJwkPropertyMissing("q"),
- ImportKeyJwkFromDict(dict,
- CreateRsaHashedImportAlgorithm(
- blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
- blink::WebCryptoAlgorithmIdSha1),
- true,
- blink::WebCryptoKeyUsageSign,
- &key));
-}
-
-// Import a JWK RSA private key, without any of the optional parameters.
-//
-// According to JWA, such keys are valid, but applications SHOULD
-// include all the parameters when sending, and recipients MAY
-// accept them, but are not required to. Chromium's WebCrypto does
-// not allow such degenerate keys.
-TEST(WebCryptoRsaSsaTest, ImportRsaPrivateKeyJwkIncorrectOptionalEmpty) {
- if (!SupportsRsaPrivateKeyImport())
- return;
-
- blink::WebCryptoKey key = blink::WebCryptoKey::createNull();
-
- base::DictionaryValue dict;
- dict.SetString("kty", "RSA");
- dict.SetString("alg", "RS1");
-
- dict.SetString(
- "n",
- "pW5KDnAQF1iaUYfcfqhB0Vby7A42rVKkTf6x5h962ZHYxRBW_-2xYrTA8oOhKoijlN_"
- "1JqtykcuzB86r_OCx39XNlQgJbVsri2311nHvY3fAkhyyPCcKcOJZjm_4nRnxBazC0_"
- "DLNfKSgOE4a29kxO8i4eHyDQzoz_siSb2aITc");
- dict.SetString("e", "AQAB");
- dict.SetString(
- "d",
- "M6UEKpCyfU9UUcqbu9C0R3GhAa-IQ0Cu-YhfKku-"
- "kuiUpySsPFaMj5eFOtB8AmbIxqPKCSnx6PESMYhEKfxNmuVf7olqEM5wfD7X5zTkRyejlXRQ"
- "GlMmgxCcKrrKuig8MbS9L1PD7jfjUs7jT55QO9gMBiKtecbc7og1R8ajsyU");
-
- ASSERT_EQ(Status::ErrorJwkPropertyMissing("p"),
- ImportKeyJwkFromDict(dict,
- CreateRsaHashedImportAlgorithm(
- blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
- blink::WebCryptoAlgorithmIdSha1),
- true,
- blink::WebCryptoKeyUsageSign,
- &key));
-}
-
-// Tries importing a public RSA key whose exponent contains leading zeros.
-TEST(WebCryptoRsaSsaTest, ImportJwkRsaNonMinimalExponent) {
- base::DictionaryValue dict;
-
- dict.SetString("kty", "RSA");
- dict.SetString("e", "AAEAAQ"); // 00 01 00 01
- dict.SetString(
- "n",
- "qLOyhK-OtQs4cDSoYPFGxJGfMYdjzWxVmMiuSBGh4KvEx-CwgtaTpef87Wdc9GaFEncsDLxk"
- "p0LGxjD1M8jMcvYq6DPEC_JYQumEu3i9v5fAEH1VvbZi9cTg-rmEXLUUjvc5LdOq_5OuHmtm"
- "e7PUJHYW1PW6ENTP0ibeiNOfFvs");
-
- blink::WebCryptoKey key = blink::WebCryptoKey::createNull();
-
- EXPECT_EQ(Status::ErrorJwkBigIntegerHasLeadingZero("e"),
- ImportKeyJwkFromDict(dict,
- CreateRsaHashedImportAlgorithm(
- blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
- blink::WebCryptoAlgorithmIdSha256),
- false,
- blink::WebCryptoKeyUsageVerify,
- &key));
-}
-
TEST(WebCryptoRsaSsaTest, GenerateKeyPairRsa) {
// Note: using unrealistic short key lengths here to avoid bogging down tests.
modulus_length,
public_exponent);
bool extractable = true;
- const blink::WebCryptoKeyUsageMask usage_mask = 0;
- blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
- blink::WebCryptoKey private_key = blink::WebCryptoKey::createNull();
+ const blink::WebCryptoKeyUsageMask usages = 0;
+ blink::WebCryptoKey public_key;
+ blink::WebCryptoKey private_key;
EXPECT_EQ(Status::Success(),
GenerateKeyPair(
- algorithm, extractable, usage_mask, &public_key, &private_key));
+ algorithm, extractable, usages, &public_key, &private_key));
EXPECT_FALSE(public_key.isNull());
EXPECT_FALSE(private_key.isNull());
EXPECT_EQ(blink::WebCryptoKeyTypePublic, public_key.type());
private_key.algorithm().rsaHashedParams()->hash().id());
EXPECT_TRUE(public_key.extractable());
EXPECT_EQ(extractable, private_key.extractable());
- EXPECT_EQ(usage_mask, public_key.usages());
- EXPECT_EQ(usage_mask, private_key.usages());
+ EXPECT_EQ(usages, public_key.usages());
+ EXPECT_EQ(usages, private_key.usages());
// Try exporting the generated key pair, and then re-importing to verify that
// the exported data was valid.
blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
blink::WebCryptoAlgorithmIdSha256),
true,
- usage_mask,
+ usages,
&public_key));
EXPECT_EQ(modulus_length,
public_key.algorithm().rsaHashedParams()->modulusLengthBits());
blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
blink::WebCryptoAlgorithmIdSha256),
true,
- usage_mask,
+ usages,
&private_key));
EXPECT_EQ(modulus_length,
private_key.algorithm().rsaHashedParams()->modulusLengthBits());
public_exponent);
EXPECT_EQ(Status::ErrorGenerateRsaUnsupportedModulus(),
GenerateKeyPair(
- algorithm, extractable, usage_mask, &public_key, &private_key));
+ algorithm, extractable, usages, &public_key, &private_key));
// Fail with bad exponent: larger than unsigned long.
unsigned int exponent_length = sizeof(unsigned long) + 1; // NOLINT
long_exponent);
EXPECT_EQ(Status::ErrorGenerateKeyPublicExponent(),
GenerateKeyPair(
- algorithm, extractable, usage_mask, &public_key, &private_key));
+ algorithm, extractable, usages, &public_key, &private_key));
// Fail with bad exponent: empty.
const std::vector<uint8_t> empty_exponent;
empty_exponent);
EXPECT_EQ(Status::ErrorGenerateKeyPublicExponent(),
GenerateKeyPair(
- algorithm, extractable, usage_mask, &public_key, &private_key));
+ algorithm, extractable, usages, &public_key, &private_key));
// Fail with bad exponent: all zeros.
std::vector<uint8_t> exponent_with_leading_zeros(15, 0x00);
exponent_with_leading_zeros);
EXPECT_EQ(Status::ErrorGenerateKeyPublicExponent(),
GenerateKeyPair(
- algorithm, extractable, usage_mask, &public_key, &private_key));
+ algorithm, extractable, usages, &public_key, &private_key));
// Key generation success using exponent with leading zeros.
exponent_with_leading_zeros.insert(exponent_with_leading_zeros.end(),
exponent_with_leading_zeros);
EXPECT_EQ(Status::Success(),
GenerateKeyPair(
- algorithm, extractable, usage_mask, &public_key, &private_key));
+ algorithm, extractable, usages, &public_key, &private_key));
EXPECT_FALSE(public_key.isNull());
EXPECT_FALSE(private_key.isNull());
EXPECT_EQ(blink::WebCryptoKeyTypePublic, public_key.type());
EXPECT_EQ(blink::WebCryptoKeyTypePrivate, private_key.type());
EXPECT_TRUE(public_key.extractable());
EXPECT_EQ(extractable, private_key.extractable());
- EXPECT_EQ(usage_mask, public_key.usages());
- EXPECT_EQ(usage_mask, private_key.usages());
+ EXPECT_EQ(usages, public_key.usages());
+ EXPECT_EQ(usages, private_key.usages());
// Successful WebCryptoAlgorithmIdRsaSsaPkcs1v1_5 key generation (sha1)
algorithm =
public_exponent);
EXPECT_EQ(
Status::Success(),
- GenerateKeyPair(algorithm, false, usage_mask, &public_key, &private_key));
+ GenerateKeyPair(algorithm, false, usages, &public_key, &private_key));
EXPECT_FALSE(public_key.isNull());
EXPECT_FALSE(private_key.isNull());
EXPECT_EQ(blink::WebCryptoKeyTypePublic, public_key.type());
// extractable.
EXPECT_TRUE(public_key.extractable());
EXPECT_FALSE(private_key.extractable());
- EXPECT_EQ(usage_mask, public_key.usages());
- EXPECT_EQ(usage_mask, private_key.usages());
+ EXPECT_EQ(usages, public_key.usages());
+ EXPECT_EQ(usages, private_key.usages());
// Exporting a private key as SPKI format doesn't make sense. However this
// will first fail because the key is not extractable.
// This should fail since spki is for public keys.
EXPECT_EQ(
Status::Success(),
- GenerateKeyPair(algorithm, true, usage_mask, &public_key, &private_key));
+ GenerateKeyPair(algorithm, true, usages, &public_key, &private_key));
EXPECT_EQ(Status::ErrorUnexpectedKeyType(),
ExportKey(blink::WebCryptoKeyFormatSpki, private_key, &output));
}
modulus_length_bits,
public_exponent);
bool extractable = true;
- const blink::WebCryptoKeyUsageMask usage_mask = 0;
- blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
- blink::WebCryptoKey private_key = blink::WebCryptoKey::createNull();
+ const blink::WebCryptoKeyUsageMask usages = 0;
+ blink::WebCryptoKey public_key;
+ blink::WebCryptoKey private_key;
- EXPECT_EQ(
- Status::ErrorGenerateRsaUnsupportedModulus(),
- GenerateKeyPair(
- algorithm, extractable, usage_mask, &public_key, &private_key));
+ EXPECT_EQ(Status::ErrorGenerateRsaUnsupportedModulus(),
+ GenerateKeyPair(
+ algorithm, extractable, usages, &public_key, &private_key));
}
}
modulus_length,
HexStringToBytes(kPublicExponents[i]));
- blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
- blink::WebCryptoKey private_key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey public_key;
+ blink::WebCryptoKey private_key;
EXPECT_EQ(Status::ErrorGenerateKeyPublicExponent(),
GenerateKeyPair(algorithm, true, 0, &public_key, &private_key));
blink::WebCryptoAlgorithm import_algorithm =
CreateRsaHashedImportAlgorithm(blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
blink::WebCryptoAlgorithmIdSha1);
- blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
- blink::WebCryptoKey private_key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey public_key;
+ blink::WebCryptoKey private_key;
ASSERT_NO_FATAL_FAILURE(
ImportRsaKeyPair(HexStringToBytes(kPublicKeySpkiDerHex),
HexStringToBytes(kPrivateKeyPkcs8DerHex),
CryptoData(data),
&signature));
- blink::WebCryptoKey public_key_256 = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey public_key_256;
EXPECT_EQ(Status::Success(),
ImportKey(blink::WebCryptoKeyFormatSpki,
CryptoData(HexStringToBytes(kPublicKeySpkiDerHex)),
blink::WebCryptoAlgorithm import_algorithm =
CreateRsaHashedImportAlgorithm(blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
blink::WebCryptoAlgorithmIdSha1);
- blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
- blink::WebCryptoKey private_key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey public_key;
+ blink::WebCryptoKey private_key;
ASSERT_NO_FATAL_FAILURE(
ImportRsaKeyPair(HexStringToBytes(kPublicKeySpkiDerHex),
HexStringToBytes(kPrivateKeyPkcs8DerHex),
for (size_t i = 0; i < arraysize(bad_usages); ++i) {
SCOPED_TRACE(i);
- blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey public_key;
ASSERT_EQ(Status::ErrorCreateKeyBadUsages(),
ImportKey(blink::WebCryptoKeyFormatSpki,
CryptoData(HexStringToBytes(kPublicKeySpkiDerHex)),
for (size_t i = 0; i < arraysize(bad_usages); ++i) {
SCOPED_TRACE(i);
- blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey public_key;
ASSERT_EQ(Status::ErrorCreateKeyBadUsages(),
ImportKeyJwkFromDict(
dict, algorithm, false, bad_usages[i], &public_key));
for (size_t i = 0; i < arraysize(bad_usages); ++i) {
SCOPED_TRACE(i);
- blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
- blink::WebCryptoKey private_key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey public_key;
+ blink::WebCryptoKey private_key;
ASSERT_EQ(Status::ErrorCreateKeyBadUsages(),
GenerateKeyPair(CreateRsaHashedKeyGenAlgorithm(
const unsigned int modulus_length = 256;
const std::vector<uint8_t> public_exponent = HexStringToBytes("010001");
- blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
- blink::WebCryptoKey private_key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey public_key;
+ blink::WebCryptoKey private_key;
ASSERT_EQ(Status::Success(),
GenerateKeyPair(
{blink::WebCryptoAlgorithmIdSha512, blink::WebCryptoKeyUsageVerify,
"RS512"}};
- for (size_t test_index = 0; test_index < ARRAYSIZE_UNSAFE(kTests);
- ++test_index) {
+ for (size_t test_index = 0; test_index < arraysize(kTests); ++test_index) {
SCOPED_TRACE(test_index);
const TestCase& test = kTests[test_index];
blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5, test.hash);
// Import the spki to create a public key
- blink::WebCryptoKey public_key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey public_key;
ASSERT_EQ(Status::Success(),
ImportKey(blink::WebCryptoKeyFormatSpki,
CryptoData(HexStringToBytes(kPublicKeySpkiDerHex)),
test.usage));
// Import the JWK back in to create a new key
- blink::WebCryptoKey public_key2 = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKey public_key2;
ASSERT_EQ(Status::Success(),
ImportKey(blink::WebCryptoKeyFormatJwk,
CryptoData(jwk),
blink::WebCryptoAlgorithm algorithm =
CreateRsaHashedImportAlgorithm(blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
blink::WebCryptoAlgorithmIdSha256);
- blink::WebCryptoKeyUsageMask usage_mask = blink::WebCryptoKeyUsageVerify;
- blink::WebCryptoKey key = blink::WebCryptoKey::createNull();
+ blink::WebCryptoKeyUsageMask usages = blink::WebCryptoKeyUsageVerify;
+ blink::WebCryptoKey key;
// An RSA public key JWK _must_ have an "n" (modulus) and an "e" (exponent)
// entry, while an RSA private key must have those plus at least a "d"
// Baseline pass.
EXPECT_EQ(Status::Success(),
- ImportKeyJwkFromDict(dict, algorithm, false, usage_mask, &key));
+ ImportKeyJwkFromDict(dict, algorithm, false, usages, &key));
EXPECT_EQ(algorithm.id(), key.algorithm().id());
EXPECT_FALSE(key.extractable());
EXPECT_EQ(blink::WebCryptoKeyUsageVerify, key.usages());
// Fail if either "n" or "e" is not present or malformed.
const std::string kKtyParmName[] = {"n", "e"};
- for (size_t idx = 0; idx < ARRAYSIZE_UNSAFE(kKtyParmName); ++idx) {
+ for (size_t idx = 0; idx < arraysize(kKtyParmName); ++idx) {
// Fail on missing parameter.
dict.Remove(kKtyParmName[idx], NULL);
EXPECT_NE(Status::Success(),
- ImportKeyJwkFromDict(dict, algorithm, false, usage_mask, &key));
+ ImportKeyJwkFromDict(dict, algorithm, false, usages, &key));
RestoreJwkRsaDictionary(&dict);
// Fail on bad b64 parameter encoding.
dict.SetString(kKtyParmName[idx], "Qk3f0DsytU8lfza2au #$% Htaw2xpop9yTuH0");
EXPECT_NE(Status::Success(),
- ImportKeyJwkFromDict(dict, algorithm, false, usage_mask, &key));
+ ImportKeyJwkFromDict(dict, algorithm, false, usages, &key));
RestoreJwkRsaDictionary(&dict);
// Fail on empty parameter.
dict.SetString(kKtyParmName[idx], "");
EXPECT_EQ(Status::ErrorJwkEmptyBigInteger(kKtyParmName[idx]),
- ImportKeyJwkFromDict(dict, algorithm, false, usage_mask, &key));
+ ImportKeyJwkFromDict(dict, algorithm, false, usages, &key));
RestoreJwkRsaDictionary(&dict);
}
}
+// Try importing an RSA-SSA key from JWK format, having specified both Sign and
+// Verify usage, and an invalid JWK.
+//
+// The test must fail with a usage error BEFORE attempting to read the JWK data.
+// Although both Sign and Verify are valid usages for RSA-SSA keys, it is
+// invalid to have them both at the same time for one key (since Sign applies to
+// private keys, whereas Verify applies to public keys).
+//
+// If the implementation does not fail fast, this test will crash dereferencing
+// invalid memory.
+TEST(WebCryptoRsaSsaTest, ImportRsaSsaJwkBadUsageFailFast) {
+ CryptoData bad_data(NULL, 128); // Invalid buffer of length 128.
+
+ blink::WebCryptoKey key;
+ ASSERT_EQ(
+ Status::ErrorCreateKeyBadUsages(),
+ ImportKey(blink::WebCryptoKeyFormatJwk,
+ bad_data,
+ CreateRsaHashedImportAlgorithm(
+ blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
+ blink::WebCryptoAlgorithmIdSha256),
+ true,
+ blink::WebCryptoKeyUsageVerify | blink::WebCryptoKeyUsageSign,
+ &key));
+}
+
+// Imports invalid JWK/SPKI/PKCS8 data and verifies that it fails as expected.
+TEST(WebCryptoRsaSsaTest, ImportInvalidKeyData) {
+ if (!SupportsRsaPrivateKeyImport())
+ return;
+
+ scoped_ptr<base::ListValue> tests;
+ ASSERT_TRUE(ReadJsonTestFileToList("bad_rsa_keys.json", &tests));
+
+ for (size_t test_index = 0; test_index < tests->GetSize(); ++test_index) {
+ SCOPED_TRACE(test_index);
+
+ const base::DictionaryValue* test;
+ ASSERT_TRUE(tests->GetDictionary(test_index, &test));
+
+ blink::WebCryptoKeyFormat key_format = GetKeyFormatFromJsonTestCase(test);
+ std::vector<uint8_t> key_data =
+ GetKeyDataFromJsonTestCase(test, key_format);
+ std::string test_error;
+ ASSERT_TRUE(test->GetString("error", &test_error));
+
+ blink::WebCryptoKey key;
+ Status status = ImportKey(key_format, CryptoData(key_data),
+ CreateRsaHashedImportAlgorithm(
+ blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5,
+ blink::WebCryptoAlgorithmIdSha256),
+ true, 0, &key);
+ EXPECT_EQ(test_error, StatusToString(status));
+ }
+}
+
} // namespace
} // namespace webcrypto