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

Side by Side Diff: extensions/common/cast/cast_cert_validator_nss.cc

Issue 853663003: Revert of Refactoring of Cast-related crypto code (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 5 years, 11 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 unified diff | Download patch
OLDNEW
(Empty)
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
3 // found in the LICENSE file.
4
5 #include "extensions/common/cast/cast_cert_validator.h"
6
7 #include <cert.h>
8 #include <cryptohi.h>
9 #include <pk11pub.h>
10 #include <seccomon.h>
11
12 #include "base/logging.h"
13 #include "base/memory/scoped_ptr.h"
14 #include "base/strings/string_number_conversions.h"
15 #include "crypto/nss_util.h"
16 #include "crypto/scoped_nss_types.h"
17 #include "extensions/browser/api/cast_channel/cast_auth_ica.h"
18
19 namespace extensions {
20 namespace core_api {
21 namespace cast_crypto {
22
23 namespace {
24
25 typedef scoped_ptr<
26 CERTCertificate,
27 crypto::NSSDestroyer<CERTCertificate, CERT_DestroyCertificate>>
28 ScopedCERTCertificate;
29
30 class CertVerificationContextNSS : public CertVerificationContext {
31 public:
32 explicit CertVerificationContextNSS(CERTCertificate* certificate)
33 : certificate_(certificate) {}
34
35 VerificationResult VerifySignatureOverData(
36 const base::StringPiece& signature,
37 const base::StringPiece& data) const override {
38 // Retrieve public key object
39 crypto::ScopedSECKEYPublicKey public_key_obj(
40 CERT_ExtractPublicKey(certificate_.get()));
41 if (!public_key_obj.get()) {
42 return VerificationResult(
43 "Failed to extract device certificate public key.",
44 VerificationResult::ERROR_CERT_INVALID);
45 }
46 // Verify signature.
47 SECItem signature_item;
48 signature_item.type = siBuffer;
49 signature_item.data =
50 reinterpret_cast<unsigned char*>(const_cast<char*>(signature.data()));
51 signature_item.len = signature.length();
52 if (VFY_VerifyDataDirect(
53 reinterpret_cast<unsigned char*>(const_cast<char*>(data.data())),
54 data.size(), public_key_obj.get(), &signature_item,
55 SEC_OID_PKCS1_RSA_ENCRYPTION, SEC_OID_SHA1, NULL,
56 NULL) != SECSuccess) {
57 return VerificationResult("Signature verification failed.",
58 VerificationResult::ERROR_SIGNATURE_INVALID,
59 PORT_GetError());
60 }
61 return VerificationResult();
62 }
63
64 std::string GetCommonName() const override {
65 char* common_name = CERT_GetCommonName(&certificate_->subject);
66 if (!common_name)
67 return std::string();
68
69 std::string result(common_name);
70 PORT_Free(common_name);
71 return result;
72 }
73
74 private:
75 ScopedCERTCertificate certificate_;
76 };
77
78 } // namespace
79
80 VerificationResult VerifyDeviceCert(
81 const base::StringPiece& device_cert,
82 const std::vector<std::string>& ica_certs,
83 scoped_ptr<CertVerificationContext>* context) {
84 crypto::EnsureNSSInit();
85
86 // If the list of intermediates is empty then use kPublicKeyICA1 as
87 // the trusted CA (legacy case).
88 // Otherwise, use the first intermediate in the list as long as it
89 // is in the allowed list of intermediates.
90 base::StringPiece ica_public_key_der =
91 (ica_certs.size() == 0)
92 ? cast_channel::GetDefaultTrustedICAPublicKey()
93 : cast_channel::GetTrustedICAPublicKey(ica_certs[0]);
94
95 if (ica_public_key_der.empty()) {
96 return VerificationResult(
97 "Device certificate is not signed by a trusted CA",
98 VerificationResult::ERROR_CERT_UNTRUSTED);
99 }
100 // Initialize the ICA public key.
101 SECItem ica_public_key_der_item;
102 ica_public_key_der_item.type = SECItemType::siDERCertBuffer;
103 ica_public_key_der_item.data = const_cast<uint8_t*>(
104 reinterpret_cast<const uint8_t*>(ica_public_key_der.data()));
105 ica_public_key_der_item.len = ica_public_key_der.size();
106
107 crypto::ScopedSECKEYPublicKey ica_public_key_obj(
108 SECKEY_ImportDERPublicKey(&ica_public_key_der_item, CKK_RSA));
109 if (!ica_public_key_obj) {
110 return VerificationResult("Failed to import trusted public key.",
111 VerificationResult::ERROR_INTERNAL,
112 PORT_GetError());
113 }
114 SECItem device_cert_der_item;
115 device_cert_der_item.type = siDERCertBuffer;
116 // Make a copy of certificate string so it is safe to type cast.
117 device_cert_der_item.data =
118 reinterpret_cast<unsigned char*>(const_cast<char*>(device_cert.data()));
119 device_cert_der_item.len = device_cert.length();
120
121 // Parse into a certificate structure.
122 ScopedCERTCertificate device_cert_obj(CERT_NewTempCertificate(
123 CERT_GetDefaultCertDB(), &device_cert_der_item, NULL, PR_FALSE, PR_TRUE));
124 if (!device_cert_obj.get()) {
125 return VerificationResult("Failed to parse device certificate.",
126 VerificationResult::ERROR_CERT_INVALID,
127 PORT_GetError());
128 }
129 if (CERT_VerifySignedDataWithPublicKey(&device_cert_obj->signatureWrap,
130 ica_public_key_obj.get(),
131 NULL) != SECSuccess) {
132 return VerificationResult("Signature verification failed.",
133 VerificationResult::ERROR_SIGNATURE_INVALID,
134 PORT_GetError());
135 }
136 if (context) {
137 scoped_ptr<CertVerificationContext> tmp_context(
138 new CertVerificationContextNSS(device_cert_obj.release()));
139 tmp_context.swap(*context);
140 }
141
142 return VerificationResult();
143 }
144
145 std::string VerificationResult::GetLogString() const {
146 std::string nssError = "NSS Error Code: ";
147 nssError += base::IntToString(library_error_code);
148 return error_message.size()
149 ? std::string("Error: ") + error_message + ", " + nssError
150 : nssError;
151 }
152
153 } // namespace cast_crypto
154 } // namespace core_api
155 } // namespace extensions
OLDNEW
« no previous file with comments | « extensions/common/cast/cast_cert_validator.cc ('k') | extensions/common/cast/cast_cert_validator_openssl.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698