OLD | NEW |
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 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/renderer/webcrypto/webcrypto_impl.h" | 5 #include "content/renderer/webcrypto/webcrypto_impl.h" |
6 | 6 |
7 #include <string> | 7 #include <string> |
8 #include <vector> | 8 #include <vector> |
9 | 9 |
10 #include "base/basictypes.h" | 10 #include "base/basictypes.h" |
(...skipping 135 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
146 WebKit::WebCryptoKey* public_key, | 146 WebKit::WebCryptoKey* public_key, |
147 WebKit::WebCryptoKey* private_key) { | 147 WebKit::WebCryptoKey* private_key) { |
148 return crypto_.GenerateKeyPairInternal( | 148 return crypto_.GenerateKeyPairInternal( |
149 algorithm, extractable, usage_mask, public_key, private_key); | 149 algorithm, extractable, usage_mask, public_key, private_key); |
150 } | 150 } |
151 | 151 |
152 bool ImportKeyInternal( | 152 bool ImportKeyInternal( |
153 WebKit::WebCryptoKeyFormat format, | 153 WebKit::WebCryptoKeyFormat format, |
154 const std::vector<uint8>& key_data, | 154 const std::vector<uint8>& key_data, |
155 const WebKit::WebCryptoAlgorithm& algorithm, | 155 const WebKit::WebCryptoAlgorithm& algorithm, |
| 156 bool extractable, |
156 WebKit::WebCryptoKeyUsageMask usage_mask, | 157 WebKit::WebCryptoKeyUsageMask usage_mask, |
157 WebKit::WebCryptoKey* key) { | 158 WebKit::WebCryptoKey* key) { |
158 bool extractable = true; | |
159 return crypto_.ImportKeyInternal(format, | 159 return crypto_.ImportKeyInternal(format, |
160 Start(key_data), | 160 Start(key_data), |
161 key_data.size(), | 161 key_data.size(), |
162 algorithm, | 162 algorithm, |
163 extractable, | 163 extractable, |
164 usage_mask, | 164 usage_mask, |
165 key); | 165 key); |
166 } | 166 } |
167 | 167 |
| 168 bool ExportKeyInternal( |
| 169 WebKit::WebCryptoKeyFormat format, |
| 170 const WebKit::WebCryptoKey& key, |
| 171 WebKit::WebArrayBuffer* buffer) { |
| 172 return crypto_.ExportKeyInternal(format, key, buffer); |
| 173 } |
| 174 |
168 bool SignInternal( | 175 bool SignInternal( |
169 const WebKit::WebCryptoAlgorithm& algorithm, | 176 const WebKit::WebCryptoAlgorithm& algorithm, |
170 const WebKit::WebCryptoKey& key, | 177 const WebKit::WebCryptoKey& key, |
171 const std::vector<uint8>& data, | 178 const std::vector<uint8>& data, |
172 WebKit::WebArrayBuffer* buffer) { | 179 WebKit::WebArrayBuffer* buffer) { |
173 return crypto_.SignInternal( | 180 return crypto_.SignInternal( |
174 algorithm, key, Start(data), data.size(), buffer); | 181 algorithm, key, Start(data), data.size(), buffer); |
175 } | 182 } |
176 | 183 |
177 bool VerifySignatureInternal( | 184 bool VerifySignatureInternal( |
(...skipping 319 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
497 | 504 |
498 // Fail importing the key (too few bytes specified) | 505 // Fail importing the key (too few bytes specified) |
499 { | 506 { |
500 std::vector<uint8> key_raw(1); | 507 std::vector<uint8> key_raw(1); |
501 std::vector<uint8> iv(16); | 508 std::vector<uint8> iv(16); |
502 | 509 |
503 WebKit::WebCryptoKey key = WebKit::WebCryptoKey::createNull(); | 510 WebKit::WebCryptoKey key = WebKit::WebCryptoKey::createNull(); |
504 EXPECT_FALSE(ImportKeyInternal(WebKit::WebCryptoKeyFormatRaw, | 511 EXPECT_FALSE(ImportKeyInternal(WebKit::WebCryptoKeyFormatRaw, |
505 key_raw, | 512 key_raw, |
506 CreateAesCbcAlgorithm(iv), | 513 CreateAesCbcAlgorithm(iv), |
| 514 true, |
507 WebKit::WebCryptoKeyUsageDecrypt, | 515 WebKit::WebCryptoKeyUsageDecrypt, |
508 &key)); | 516 &key)); |
509 } | 517 } |
| 518 |
| 519 // Fail exporting the key in SPKI format (SPKI export not allowed for secret |
| 520 // keys) |
| 521 EXPECT_FALSE(ExportKeyInternal(WebKit::WebCryptoKeyFormatSpki, key, &output)); |
510 } | 522 } |
511 | 523 |
512 TEST_F(WebCryptoImplTest, AesCbcSampleSets) { | 524 TEST_F(WebCryptoImplTest, AesCbcSampleSets) { |
513 struct TestCase { | 525 struct TestCase { |
514 const char* key; | 526 const char* key; |
515 const char* iv; | 527 const char* iv; |
516 const char* plain_text; | 528 const char* plain_text; |
517 const char* cipher_text; | 529 const char* cipher_text; |
518 }; | 530 }; |
519 | 531 |
(...skipping 155 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
675 } | 687 } |
676 | 688 |
677 TEST_F(WebCryptoImplTest, ImportSecretKeyNoAlgorithm) { | 689 TEST_F(WebCryptoImplTest, ImportSecretKeyNoAlgorithm) { |
678 WebKit::WebCryptoKey key = WebKit::WebCryptoKey::createNull(); | 690 WebKit::WebCryptoKey key = WebKit::WebCryptoKey::createNull(); |
679 | 691 |
680 // This fails because the algorithm is null. | 692 // This fails because the algorithm is null. |
681 EXPECT_FALSE(ImportKeyInternal( | 693 EXPECT_FALSE(ImportKeyInternal( |
682 WebKit::WebCryptoKeyFormatRaw, | 694 WebKit::WebCryptoKeyFormatRaw, |
683 HexStringToBytes("00000000000000000000"), | 695 HexStringToBytes("00000000000000000000"), |
684 WebKit::WebCryptoAlgorithm::createNull(), | 696 WebKit::WebCryptoAlgorithm::createNull(), |
| 697 true, |
685 WebKit::WebCryptoKeyUsageSign, | 698 WebKit::WebCryptoKeyUsageSign, |
686 &key)); | 699 &key)); |
687 } | 700 } |
688 | 701 |
689 #if !defined(USE_OPENSSL) | 702 #if !defined(USE_OPENSSL) |
690 | 703 |
| 704 TEST_F(WebCryptoImplTest, ImportExportSpki) { |
| 705 // openssl genrsa -out pair.pem 2048 |
| 706 // openssl rsa -in pair.pem -out pubkey.der -outform DER -pubout |
| 707 // xxd -p pubkey.der |
| 708 const std::string hex_rsa_spki_der = |
| 709 "30820122300d06092a864886f70d01010105000382010f003082010a0282" |
| 710 "010100f19e40f94e3780858701577a571cca000cb9795db89ddf8e98ab0e" |
| 711 "5eecfa47516cb08dc591cae5ab7fa43d6db402e95991d4a2de52e7cd3a66" |
| 712 "4f58284be2eb4675d5a849a2582c585d2b3c6c225a8f2c53a0414d5dbd06" |
| 713 "172371cefdf953e9ec3000fc9ad000743023f74e82d12aa93917a2c9b832" |
| 714 "696085ee0711154cf98a6d098f44cee00ea3b7584236503a5483ba8b6792" |
| 715 "fee588d1a8f4a0618333c4cb3447d760b43d5a0d9ed6ef79763df670cd8b" |
| 716 "5eb869a20833f1e3e6d8b88240a5d4335c73fd20487f2a7d112af8692357" |
| 717 "6425e44a273e5ad2e93d6b50a28e65f9e133958e4f0c7d12e0adc90fedd4" |
| 718 "f6b6848e7b6900666642a08b520a6534a35d4f0203010001"; |
| 719 |
| 720 // Passing case: Import a valid RSA key in SPKI format. |
| 721 WebKit::WebCryptoKey key = WebKit::WebCryptoKey::createNull(); |
| 722 ASSERT_TRUE(ImportKeyInternal( |
| 723 WebKit::WebCryptoKeyFormatSpki, |
| 724 HexStringToBytes(hex_rsa_spki_der), |
| 725 CreateAlgorithm(WebKit::WebCryptoAlgorithmIdRsaEsPkcs1v1_5), |
| 726 true, |
| 727 WebKit::WebCryptoKeyUsageEncrypt, |
| 728 &key)); |
| 729 EXPECT_TRUE(key.handle()); |
| 730 EXPECT_EQ(WebKit::WebCryptoKeyTypePublic, key.type()); |
| 731 EXPECT_TRUE(key.extractable()); |
| 732 EXPECT_EQ(WebKit::WebCryptoKeyUsageEncrypt, key.usages()); |
| 733 |
| 734 // Failing case: Empty SPKI data |
| 735 EXPECT_FALSE(ImportKeyInternal( |
| 736 WebKit::WebCryptoKeyFormatSpki, |
| 737 std::vector<uint8>(), |
| 738 WebKit::WebCryptoAlgorithm::createNull(), |
| 739 true, |
| 740 WebKit::WebCryptoKeyUsageEncrypt, |
| 741 &key)); |
| 742 |
| 743 // Failing case: Import RSA key with NULL input algorithm. This is not |
| 744 // allowed because the SPKI ASN.1 format for RSA keys is not specific enough |
| 745 // to map to a Web Crypto algorithm. |
| 746 EXPECT_FALSE(ImportKeyInternal( |
| 747 WebKit::WebCryptoKeyFormatSpki, |
| 748 HexStringToBytes(hex_rsa_spki_der), |
| 749 WebKit::WebCryptoAlgorithm::createNull(), |
| 750 true, |
| 751 WebKit::WebCryptoKeyUsageEncrypt, |
| 752 &key)); |
| 753 |
| 754 // Failing case: Bad DER encoding. |
| 755 EXPECT_FALSE(ImportKeyInternal( |
| 756 WebKit::WebCryptoKeyFormatSpki, |
| 757 HexStringToBytes("618333c4cb"), |
| 758 CreateAlgorithm(WebKit::WebCryptoAlgorithmIdRsaEsPkcs1v1_5), |
| 759 true, |
| 760 WebKit::WebCryptoKeyUsageEncrypt, |
| 761 &key)); |
| 762 |
| 763 // Failing case: Import RSA key but provide an inconsistent input algorithm. |
| 764 EXPECT_FALSE(ImportKeyInternal( |
| 765 WebKit::WebCryptoKeyFormatSpki, |
| 766 HexStringToBytes(hex_rsa_spki_der), |
| 767 CreateAlgorithm(WebKit::WebCryptoAlgorithmIdAesCbc), |
| 768 true, |
| 769 WebKit::WebCryptoKeyUsageEncrypt, |
| 770 &key)); |
| 771 |
| 772 // Passing case: Export a previously imported RSA public key in SPKI format |
| 773 // and compare to original data. |
| 774 WebKit::WebArrayBuffer output; |
| 775 ASSERT_TRUE(ExportKeyInternal(WebKit::WebCryptoKeyFormatSpki, key, &output)); |
| 776 ExpectArrayBufferMatchesHex(hex_rsa_spki_der, output); |
| 777 |
| 778 // Failing case: Try to export a non-extractable key |
| 779 ASSERT_TRUE(ImportKeyInternal( |
| 780 WebKit::WebCryptoKeyFormatSpki, |
| 781 HexStringToBytes(hex_rsa_spki_der), |
| 782 CreateAlgorithm(WebKit::WebCryptoAlgorithmIdRsaEsPkcs1v1_5), |
| 783 false, |
| 784 WebKit::WebCryptoKeyUsageEncrypt, |
| 785 &key)); |
| 786 EXPECT_TRUE(key.handle()); |
| 787 EXPECT_FALSE(key.extractable()); |
| 788 EXPECT_FALSE(ExportKeyInternal(WebKit::WebCryptoKeyFormatSpki, key, &output)); |
| 789 |
| 790 // TODO(padolph): Import a RSA SPKI key and verify it works with an operation. |
| 791 } |
| 792 |
691 TEST_F(WebCryptoImplTest, GenerateKeyPairRsa) { | 793 TEST_F(WebCryptoImplTest, GenerateKeyPairRsa) { |
692 // Note: using unrealistic short key lengths here to avoid bogging down tests. | 794 // Note: using unrealistic short key lengths here to avoid bogging down tests. |
693 | 795 |
694 // Successful WebCryptoAlgorithmIdRsaEsPkcs1v1_5 key generation. | 796 // Successful WebCryptoAlgorithmIdRsaEsPkcs1v1_5 key generation. |
695 const unsigned modulus_length = 256; | 797 const unsigned modulus_length = 256; |
696 const std::vector<uint8> public_exponent = HexStringToBytes("010001"); | 798 const std::vector<uint8> public_exponent = HexStringToBytes("010001"); |
697 WebKit::WebCryptoAlgorithm algorithm = | 799 WebKit::WebCryptoAlgorithm algorithm = |
698 CreateRsaAlgorithm(WebKit::WebCryptoAlgorithmIdRsaEsPkcs1v1_5, | 800 CreateRsaAlgorithm(WebKit::WebCryptoAlgorithmIdRsaEsPkcs1v1_5, |
699 modulus_length, | 801 modulus_length, |
700 public_exponent); | 802 public_exponent); |
701 bool extractable = false; | 803 bool extractable = true; |
702 const WebKit::WebCryptoKeyUsageMask usage_mask = 0; | 804 const WebKit::WebCryptoKeyUsageMask usage_mask = 0; |
703 WebKit::WebCryptoKey public_key = WebKit::WebCryptoKey::createNull(); | 805 WebKit::WebCryptoKey public_key = WebKit::WebCryptoKey::createNull(); |
704 WebKit::WebCryptoKey private_key = WebKit::WebCryptoKey::createNull(); | 806 WebKit::WebCryptoKey private_key = WebKit::WebCryptoKey::createNull(); |
705 EXPECT_TRUE(GenerateKeyPairInternal( | 807 EXPECT_TRUE(GenerateKeyPairInternal( |
706 algorithm, extractable, usage_mask, &public_key, &private_key)); | 808 algorithm, extractable, usage_mask, &public_key, &private_key)); |
707 EXPECT_FALSE(public_key.isNull()); | 809 EXPECT_FALSE(public_key.isNull()); |
708 EXPECT_FALSE(private_key.isNull()); | 810 EXPECT_FALSE(private_key.isNull()); |
709 EXPECT_EQ(WebKit::WebCryptoKeyTypePublic, public_key.type()); | 811 EXPECT_EQ(WebKit::WebCryptoKeyTypePublic, public_key.type()); |
710 EXPECT_EQ(WebKit::WebCryptoKeyTypePrivate, private_key.type()); | 812 EXPECT_EQ(WebKit::WebCryptoKeyTypePrivate, private_key.type()); |
711 EXPECT_EQ(extractable, public_key.extractable()); | 813 EXPECT_EQ(extractable, public_key.extractable()); |
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
783 EXPECT_TRUE(GenerateKeyPairInternal( | 885 EXPECT_TRUE(GenerateKeyPairInternal( |
784 algorithm, extractable, usage_mask, &public_key, &private_key)); | 886 algorithm, extractable, usage_mask, &public_key, &private_key)); |
785 EXPECT_FALSE(public_key.isNull()); | 887 EXPECT_FALSE(public_key.isNull()); |
786 EXPECT_FALSE(private_key.isNull()); | 888 EXPECT_FALSE(private_key.isNull()); |
787 EXPECT_EQ(WebKit::WebCryptoKeyTypePublic, public_key.type()); | 889 EXPECT_EQ(WebKit::WebCryptoKeyTypePublic, public_key.type()); |
788 EXPECT_EQ(WebKit::WebCryptoKeyTypePrivate, private_key.type()); | 890 EXPECT_EQ(WebKit::WebCryptoKeyTypePrivate, private_key.type()); |
789 EXPECT_EQ(extractable, public_key.extractable()); | 891 EXPECT_EQ(extractable, public_key.extractable()); |
790 EXPECT_EQ(extractable, private_key.extractable()); | 892 EXPECT_EQ(extractable, private_key.extractable()); |
791 EXPECT_EQ(usage_mask, public_key.usages()); | 893 EXPECT_EQ(usage_mask, public_key.usages()); |
792 EXPECT_EQ(usage_mask, private_key.usages()); | 894 EXPECT_EQ(usage_mask, private_key.usages()); |
| 895 |
| 896 // Fail SPKI export of private key. This is an ExportKey test, but do it here |
| 897 // since it is expensive to generate an RSA key pair and we already have a |
| 898 // private key here. |
| 899 WebKit::WebArrayBuffer output; |
| 900 EXPECT_FALSE( |
| 901 ExportKeyInternal(WebKit::WebCryptoKeyFormatSpki, private_key, &output)); |
793 } | 902 } |
794 | 903 |
795 #endif // #if !defined(USE_OPENSSL) | 904 #endif // #if !defined(USE_OPENSSL) |
796 | 905 |
797 } // namespace content | 906 } // namespace content |
OLD | NEW |