OLD | NEW |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "content/child/webcrypto/platform_crypto.h" | 5 #include "content/child/webcrypto/platform_crypto.h" |
6 | 6 |
7 #include <cryptohi.h> | 7 #include <cryptohi.h> |
8 #include <pk11pub.h> | 8 #include <pk11pub.h> |
9 #include <secerr.h> | 9 #include <secerr.h> |
10 #include <sechash.h> | 10 #include <sechash.h> |
(...skipping 259 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
270 explicit PrivateKey(crypto::ScopedSECKEYPrivateKey key) : key_(key.Pass()) {} | 270 explicit PrivateKey(crypto::ScopedSECKEYPrivateKey key) : key_(key.Pass()) {} |
271 | 271 |
272 crypto::ScopedSECKEYPrivateKey key_; | 272 crypto::ScopedSECKEYPrivateKey key_; |
273 std::vector<uint8> serialized_key_; | 273 std::vector<uint8> serialized_key_; |
274 | 274 |
275 DISALLOW_COPY_AND_ASSIGN(PrivateKey); | 275 DISALLOW_COPY_AND_ASSIGN(PrivateKey); |
276 }; | 276 }; |
277 | 277 |
278 namespace { | 278 namespace { |
279 | 279 |
280 Status NssSupportsAesGcm() { | |
281 if (g_nss_runtime_support.Get().IsAesGcmSupported()) | |
282 return Status::Success(); | |
283 return Status::ErrorUnsupported( | |
284 "NSS version doesn't support AES-GCM. Try using version 3.15 or later"); | |
285 } | |
286 | |
287 Status NssSupportsRsaOaep() { | |
288 if (g_nss_runtime_support.Get().IsRsaOaepSupported()) | |
289 return Status::Success(); | |
290 return Status::ErrorUnsupported( | |
291 "NSS version doesn't support RSA-OAEP. Try using version 3.16.2 or " | |
292 "later"); | |
293 } | |
294 | |
295 // Creates a SECItem for the data in |buffer|. This does NOT make a copy, so | 280 // Creates a SECItem for the data in |buffer|. This does NOT make a copy, so |
296 // |buffer| should outlive the SECItem. | 281 // |buffer| should outlive the SECItem. |
297 SECItem MakeSECItemForBuffer(const CryptoData& buffer) { | 282 SECItem MakeSECItemForBuffer(const CryptoData& buffer) { |
298 SECItem item = { | 283 SECItem item = { |
299 siBuffer, | 284 siBuffer, |
300 // NSS requires non-const data even though it is just for input. | 285 // NSS requires non-const data even though it is just for input. |
301 const_cast<unsigned char*>(buffer.bytes()), buffer.byte_length()}; | 286 const_cast<unsigned char*>(buffer.bytes()), buffer.byte_length()}; |
302 return item; | 287 return item; |
303 } | 288 } |
304 | 289 |
(...skipping 151 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
456 // Helper to either encrypt or decrypt for AES-GCM. The result of encryption is | 441 // Helper to either encrypt or decrypt for AES-GCM. The result of encryption is |
457 // the concatenation of the ciphertext and the authentication tag. Similarly, | 442 // the concatenation of the ciphertext and the authentication tag. Similarly, |
458 // this is the expectation for the input to decryption. | 443 // this is the expectation for the input to decryption. |
459 Status AesGcmEncryptDecrypt(EncryptOrDecrypt mode, | 444 Status AesGcmEncryptDecrypt(EncryptOrDecrypt mode, |
460 SymKey* key, | 445 SymKey* key, |
461 const CryptoData& data, | 446 const CryptoData& data, |
462 const CryptoData& iv, | 447 const CryptoData& iv, |
463 const CryptoData& additional_data, | 448 const CryptoData& additional_data, |
464 unsigned int tag_length_bits, | 449 unsigned int tag_length_bits, |
465 std::vector<uint8>* buffer) { | 450 std::vector<uint8>* buffer) { |
466 Status status = NssSupportsAesGcm(); | 451 if (!g_nss_runtime_support.Get().IsAesGcmSupported()) |
467 if (status.IsError()) | 452 return Status::ErrorUnsupported(); |
468 return status; | |
469 | 453 |
470 unsigned int tag_length_bytes = tag_length_bits / 8; | 454 unsigned int tag_length_bytes = tag_length_bits / 8; |
471 | 455 |
472 CK_GCM_PARAMS gcm_params = {0}; | 456 CK_GCM_PARAMS gcm_params = {0}; |
473 gcm_params.pIv = const_cast<unsigned char*>(iv.bytes()); | 457 gcm_params.pIv = const_cast<unsigned char*>(iv.bytes()); |
474 gcm_params.ulIvLen = iv.byte_length(); | 458 gcm_params.ulIvLen = iv.byte_length(); |
475 | 459 |
476 gcm_params.pAAD = const_cast<unsigned char*>(additional_data.bytes()); | 460 gcm_params.pAAD = const_cast<unsigned char*>(additional_data.bytes()); |
477 gcm_params.ulAADLen = additional_data.byte_length(); | 461 gcm_params.ulAADLen = additional_data.byte_length(); |
478 | 462 |
(...skipping 127 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
606 *mechanism = CKM_AES_CBC; | 590 *mechanism = CKM_AES_CBC; |
607 *flags = CKF_ENCRYPT | CKF_DECRYPT; | 591 *flags = CKF_ENCRYPT | CKF_DECRYPT; |
608 return Status::Success(); | 592 return Status::Success(); |
609 } | 593 } |
610 case blink::WebCryptoAlgorithmIdAesKw: { | 594 case blink::WebCryptoAlgorithmIdAesKw: { |
611 *mechanism = CKM_NSS_AES_KEY_WRAP; | 595 *mechanism = CKM_NSS_AES_KEY_WRAP; |
612 *flags = CKF_WRAP | CKF_WRAP; | 596 *flags = CKF_WRAP | CKF_WRAP; |
613 return Status::Success(); | 597 return Status::Success(); |
614 } | 598 } |
615 case blink::WebCryptoAlgorithmIdAesGcm: { | 599 case blink::WebCryptoAlgorithmIdAesGcm: { |
616 Status status = NssSupportsAesGcm(); | 600 if (!g_nss_runtime_support.Get().IsAesGcmSupported()) |
617 if (status.IsError()) | 601 return Status::ErrorUnsupported(); |
618 return status; | |
619 *mechanism = CKM_AES_GCM; | 602 *mechanism = CKM_AES_GCM; |
620 *flags = CKF_ENCRYPT | CKF_DECRYPT; | 603 *flags = CKF_ENCRYPT | CKF_DECRYPT; |
621 return Status::Success(); | 604 return Status::Success(); |
622 } | 605 } |
623 default: | 606 default: |
624 return Status::ErrorUnsupported(); | 607 return Status::ErrorUnsupported(); |
625 } | 608 } |
626 } | 609 } |
627 | 610 |
628 Status DoUnwrapSymKeyAesKw(const CryptoData& wrapped_key_data, | 611 Status DoUnwrapSymKeyAesKw(const CryptoData& wrapped_key_data, |
(...skipping 618 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1247 | 1230 |
1248 // ----------------------------------- | 1231 // ----------------------------------- |
1249 // RsaOaep | 1232 // RsaOaep |
1250 // ----------------------------------- | 1233 // ----------------------------------- |
1251 | 1234 |
1252 Status EncryptRsaOaep(PublicKey* key, | 1235 Status EncryptRsaOaep(PublicKey* key, |
1253 const blink::WebCryptoAlgorithm& hash, | 1236 const blink::WebCryptoAlgorithm& hash, |
1254 const CryptoData& label, | 1237 const CryptoData& label, |
1255 const CryptoData& data, | 1238 const CryptoData& data, |
1256 std::vector<uint8>* buffer) { | 1239 std::vector<uint8>* buffer) { |
1257 Status status = NssSupportsRsaOaep(); | 1240 if (!g_nss_runtime_support.Get().IsRsaOaepSupported()) |
1258 if (status.IsError()) | 1241 return Status::ErrorUnsupported(); |
1259 return status; | |
1260 | 1242 |
1261 CK_RSA_PKCS_OAEP_PARAMS oaep_params = {0}; | 1243 CK_RSA_PKCS_OAEP_PARAMS oaep_params = {0}; |
1262 if (!InitializeRsaOaepParams(hash, label, &oaep_params)) | 1244 if (!InitializeRsaOaepParams(hash, label, &oaep_params)) |
1263 return Status::ErrorUnsupported(); | 1245 return Status::ErrorUnsupported(); |
1264 | 1246 |
1265 SECItem param; | 1247 SECItem param; |
1266 param.type = siBuffer; | 1248 param.type = siBuffer; |
1267 param.data = reinterpret_cast<unsigned char*>(&oaep_params); | 1249 param.data = reinterpret_cast<unsigned char*>(&oaep_params); |
1268 param.len = sizeof(oaep_params); | 1250 param.len = sizeof(oaep_params); |
1269 | 1251 |
(...skipping 15 matching lines...) Expand all Loading... |
1285 DCHECK_LE(output_len, buffer->size()); | 1267 DCHECK_LE(output_len, buffer->size()); |
1286 buffer->resize(output_len); | 1268 buffer->resize(output_len); |
1287 return Status::Success(); | 1269 return Status::Success(); |
1288 } | 1270 } |
1289 | 1271 |
1290 Status DecryptRsaOaep(PrivateKey* key, | 1272 Status DecryptRsaOaep(PrivateKey* key, |
1291 const blink::WebCryptoAlgorithm& hash, | 1273 const blink::WebCryptoAlgorithm& hash, |
1292 const CryptoData& label, | 1274 const CryptoData& label, |
1293 const CryptoData& data, | 1275 const CryptoData& data, |
1294 std::vector<uint8>* buffer) { | 1276 std::vector<uint8>* buffer) { |
1295 Status status = NssSupportsRsaOaep(); | 1277 if (!g_nss_runtime_support.Get().IsRsaOaepSupported()) |
1296 if (status.IsError()) | 1278 return Status::ErrorUnsupported(); |
1297 return status; | |
1298 | 1279 |
1299 CK_RSA_PKCS_OAEP_PARAMS oaep_params = {0}; | 1280 CK_RSA_PKCS_OAEP_PARAMS oaep_params = {0}; |
1300 if (!InitializeRsaOaepParams(hash, label, &oaep_params)) | 1281 if (!InitializeRsaOaepParams(hash, label, &oaep_params)) |
1301 return Status::ErrorUnsupported(); | 1282 return Status::ErrorUnsupported(); |
1302 | 1283 |
1303 SECItem param; | 1284 SECItem param; |
1304 param.type = siBuffer; | 1285 param.type = siBuffer; |
1305 param.data = reinterpret_cast<unsigned char*>(&oaep_params); | 1286 param.data = reinterpret_cast<unsigned char*>(&oaep_params); |
1306 param.len = sizeof(oaep_params); | 1287 param.len = sizeof(oaep_params); |
1307 | 1288 |
(...skipping 127 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1435 // ----------------------------------- | 1416 // ----------------------------------- |
1436 | 1417 |
1437 Status GenerateRsaKeyPair(const blink::WebCryptoAlgorithm& algorithm, | 1418 Status GenerateRsaKeyPair(const blink::WebCryptoAlgorithm& algorithm, |
1438 bool extractable, | 1419 bool extractable, |
1439 blink::WebCryptoKeyUsageMask public_key_usage_mask, | 1420 blink::WebCryptoKeyUsageMask public_key_usage_mask, |
1440 blink::WebCryptoKeyUsageMask private_key_usage_mask, | 1421 blink::WebCryptoKeyUsageMask private_key_usage_mask, |
1441 unsigned int modulus_length_bits, | 1422 unsigned int modulus_length_bits, |
1442 unsigned long public_exponent, | 1423 unsigned long public_exponent, |
1443 blink::WebCryptoKey* public_key, | 1424 blink::WebCryptoKey* public_key, |
1444 blink::WebCryptoKey* private_key) { | 1425 blink::WebCryptoKey* private_key) { |
1445 if (algorithm.id() == blink::WebCryptoAlgorithmIdRsaOaep) { | 1426 if (algorithm.id() == blink::WebCryptoAlgorithmIdRsaOaep && |
1446 Status status = NssSupportsRsaOaep(); | 1427 !g_nss_runtime_support.Get().IsRsaOaepSupported()) { |
1447 if (status.IsError()) | 1428 return Status::ErrorUnsupported(); |
1448 return status; | |
1449 } | 1429 } |
1450 | 1430 |
1451 crypto::ScopedPK11Slot slot(PK11_GetInternalKeySlot()); | 1431 crypto::ScopedPK11Slot slot(PK11_GetInternalKeySlot()); |
1452 if (!slot) | 1432 if (!slot) |
1453 return Status::OperationError(); | 1433 return Status::OperationError(); |
1454 | 1434 |
1455 PK11RSAGenParams rsa_gen_params; | 1435 PK11RSAGenParams rsa_gen_params; |
1456 rsa_gen_params.keySizeInBits = modulus_length_bits; | 1436 rsa_gen_params.keySizeInBits = modulus_length_bits; |
1457 rsa_gen_params.pe = public_exponent; | 1437 rsa_gen_params.pe = public_exponent; |
1458 | 1438 |
(...skipping 409 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1868 std::vector<uint8>* buffer) { | 1848 std::vector<uint8>* buffer) { |
1869 return mode == ENCRYPT ? EncryptAesKw(wrapping_key, data, buffer) | 1849 return mode == ENCRYPT ? EncryptAesKw(wrapping_key, data, buffer) |
1870 : DecryptAesKw(wrapping_key, data, buffer); | 1850 : DecryptAesKw(wrapping_key, data, buffer); |
1871 } | 1851 } |
1872 | 1852 |
1873 } // namespace platform | 1853 } // namespace platform |
1874 | 1854 |
1875 } // namespace webcrypto | 1855 } // namespace webcrypto |
1876 | 1856 |
1877 } // namespace content | 1857 } // namespace content |
OLD | NEW |