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

Side by Side Diff: net/cert/asn1_util.cc

Issue 2436233002: Record UMA metrics for Must-Staple certificates on private roots (Closed)
Patch Set: ... and to README Created 4 years, 2 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
« no previous file with comments | « net/cert/asn1_util.h ('k') | net/cert/cert_verify_proc.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 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 "net/cert/asn1_util.h" 5 #include "net/cert/asn1_util.h"
6 6
7 #include "net/der/input.h" 7 #include "net/der/input.h"
8 #include "net/der/parser.h" 8 #include "net/der/parser.h"
9 9
10 namespace net { 10 namespace net {
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after
63 return false; 63 return false;
64 // validity 64 // validity
65 if (!tbs_certificate->SkipTag(der::kSequence)) 65 if (!tbs_certificate->SkipTag(der::kSequence))
66 return false; 66 return false;
67 // subject 67 // subject
68 if (!tbs_certificate->SkipTag(der::kSequence)) 68 if (!tbs_certificate->SkipTag(der::kSequence))
69 return false; 69 return false;
70 return true; 70 return true;
71 } 71 }
72 72
73 // Parses input |in| which should point to the beginning of a
74 // Certificate. If parsing fails, this function returns false, with
75 // |*extensions_present| and |*extensions_parser| left in an undefined
76 // state. If parsing succeeds and extensions are present, this function
77 // sets |*extensions_present| to true and sets |*extensions_parser|
78 // ready to parse the Extensions. If extensions are not present, it sets
79 // |*extensions_present| to false and |*extensions_parser| is left in an
80 // undefined state.
81 bool SeekToExtensions(der::Input in,
82 bool* extensions_present,
83 der::Parser* extensions_parser) {
84 bool present;
85 der::Parser tbs_cert_parser;
86 if (!SeekToSPKI(in, &tbs_cert_parser))
87 return false;
88
89 // From RFC 5280, section 4.1
90 // TBSCertificate ::= SEQUENCE {
91 // ...
92 // subjectPublicKeyInfo SubjectPublicKeyInfo,
93 // issuerUniqueID [1] IMPLICIT UniqueIdentifier OPTIONAL,
94 // subjectUniqueID [2] IMPLICIT UniqueIdentifier OPTIONAL,
95 // extensions [3] EXPLICIT Extensions OPTIONAL }
96
97 // subjectPublicKeyInfo
98 if (!tbs_cert_parser.SkipTag(der::kSequence))
99 return false;
100 // issuerUniqueID
101 if (!tbs_cert_parser.SkipOptionalTag(
102 der::kTagConstructed | der::kTagContextSpecific | 1, &present)) {
103 return false;
104 }
105 // subjectUniqueID
106 if (!tbs_cert_parser.SkipOptionalTag(
107 der::kTagConstructed | der::kTagContextSpecific | 2, &present)) {
108 return false;
109 }
110
111 der::Input extensions;
112 if (!tbs_cert_parser.ReadOptionalTag(
113 der::kTagConstructed | der::kTagContextSpecific | 3, &extensions,
114 &present)) {
115 return false;
116 }
117
118 if (!present) {
119 *extensions_present = false;
120 return true;
121 }
122
123 // Extensions ::= SEQUENCE SIZE (1..MAX) OF Extension
124 // Extension ::= SEQUENCE {
125 // extnID OBJECT IDENTIFIER,
126 // critical BOOLEAN DEFAULT FALSE,
127 // extnValue OCTET STRING }
128
129 // |extensions| was EXPLICITly tagged, so we still need to remove the
130 // ASN.1 SEQUENCE header.
131 der::Parser explicit_extensions_parser(extensions);
132 if (!explicit_extensions_parser.ReadSequence(extensions_parser))
133 return false;
134
135 if (explicit_extensions_parser.HasMore())
136 return false;
137
138 *extensions_present = true;
139 return true;
140 }
141
73 } // namespace 142 } // namespace
74 143
75 bool ExtractSPKIFromDERCert(base::StringPiece cert, 144 bool ExtractSPKIFromDERCert(base::StringPiece cert,
76 base::StringPiece* spki_out) { 145 base::StringPiece* spki_out) {
77 der::Parser parser; 146 der::Parser parser;
78 if (!SeekToSPKI(der::Input(cert), &parser)) 147 if (!SeekToSPKI(der::Input(cert), &parser))
79 return false; 148 return false;
80 der::Input spki; 149 der::Input spki;
81 if (!parser.ReadRawTLV(&spki)) 150 if (!parser.ReadRawTLV(&spki))
82 return false; 151 return false;
(...skipping 28 matching lines...) Expand all
111 return false; 180 return false;
112 *spk_out = spk.AsStringPiece(); 181 *spk_out = spk.AsStringPiece();
113 return true; 182 return true;
114 } 183 }
115 184
116 185
117 bool ExtractCRLURLsFromDERCert(base::StringPiece cert, 186 bool ExtractCRLURLsFromDERCert(base::StringPiece cert,
118 std::vector<base::StringPiece>* urls_out) { 187 std::vector<base::StringPiece>* urls_out) {
119 urls_out->clear(); 188 urls_out->clear();
120 std::vector<base::StringPiece> tmp_urls_out; 189 std::vector<base::StringPiece> tmp_urls_out;
121
122 bool present; 190 bool present;
123 der::Parser tbs_cert_parser; 191 der::Parser extensions_parser;
124 if (!SeekToSPKI(der::Input(cert), &tbs_cert_parser)) 192 if (!SeekToExtensions(der::Input(cert), &present, &extensions_parser))
125 return false; 193 return false;
126 194
127 // From RFC 5280, section 4.1
128 // TBSCertificate ::= SEQUENCE {
129 // ...
130 // subjectPublicKeyInfo SubjectPublicKeyInfo,
131 // issuerUniqueID [1] IMPLICIT UniqueIdentifier OPTIONAL,
132 // subjectUniqueID [2] IMPLICIT UniqueIdentifier OPTIONAL,
133 // extensions [3] EXPLICIT Extensions OPTIONAL }
134
135 // subjectPublicKeyInfo
136 if (!tbs_cert_parser.SkipTag(der::kSequence))
137 return false;
138 // issuerUniqueID
139 if (!tbs_cert_parser.SkipOptionalTag(
140 der::kTagConstructed | der::kTagContextSpecific | 1, &present)) {
141 return false;
142 }
143 // subjectUniqueID
144 if (!tbs_cert_parser.SkipOptionalTag(
145 der::kTagConstructed | der::kTagContextSpecific | 2, &present)) {
146 return false;
147 }
148
149 der::Input extensions;
150 if (!tbs_cert_parser.ReadOptionalTag(
151 der::kTagConstructed | der::kTagContextSpecific | 3, &extensions,
152 &present)) {
153 return false;
154 }
155
156 if (!present) 195 if (!present)
157 return true; 196 return true;
158 197
159 // Extensions ::= SEQUENCE SIZE (1..MAX) OF Extension
160 // Extension ::= SEQUENCE {
161 // extnID OBJECT IDENTIFIER,
162 // critical BOOLEAN DEFAULT FALSE,
163 // extnValue OCTET STRING }
164
165 // |extensions| was EXPLICITly tagged, so we still need to remove the
166 // ASN.1 SEQUENCE header.
167 der::Parser explicit_extensions_parser(extensions);
168 der::Parser extensions_parser;
169 if (!explicit_extensions_parser.ReadSequence(&extensions_parser))
170 return false;
171
172 if (explicit_extensions_parser.HasMore())
173 return false;
174
175 while (extensions_parser.HasMore()) { 198 while (extensions_parser.HasMore()) {
176 der::Parser extension_parser; 199 der::Parser extension_parser;
177 if (!extensions_parser.ReadSequence(&extension_parser)) 200 if (!extensions_parser.ReadSequence(&extension_parser))
178 return false; 201 return false;
179 202
180 der::Input oid; 203 der::Input oid;
181 if (!extension_parser.ReadTag(der::kOid, &oid)) 204 if (!extension_parser.ReadTag(der::kOid, &oid))
182 return false; 205 return false;
183 206
184 // kCRLDistributionPointsOID is the DER encoding of the OID for the X.509 207 // kCRLDistributionPointsOID is the DER encoding of the OID for the X.509
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after
282 } 305 }
283 } 306 }
284 } 307 }
285 } 308 }
286 } 309 }
287 310
288 urls_out->swap(tmp_urls_out); 311 urls_out->swap(tmp_urls_out);
289 return true; 312 return true;
290 } 313 }
291 314
315 bool HasTLSFeatureExtension(base::StringPiece cert) {
316 bool present;
317 der::Parser extensions_parser;
318 if (!SeekToExtensions(der::Input(cert), &present, &extensions_parser))
319 return false;
320 if (!present)
321 return false;
322
323 while (extensions_parser.HasMore()) {
324 der::Parser extension_parser;
325 if (!extensions_parser.ReadSequence(&extension_parser))
326 return false;
327
328 der::Input oid;
329 if (!extension_parser.ReadTag(der::kOid, &oid))
330 return false;
331
332 // kTLSFeatureExtensionOID is the DER encoding of the OID for the
333 // X.509 TLS Feature Extension.
334 static const uint8_t kTLSFeatureExtensionOID[] = {0x2B, 0x06, 0x01, 0x05,
335 0x05, 0x07, 0x01, 0x18};
336 if (oid == der::Input(kTLSFeatureExtensionOID))
337 return true;
338 }
339
340 return false;
341 }
342
292 } // namespace asn1 343 } // namespace asn1
293 344
294 } // namespace net 345 } // namespace net
OLDNEW
« no previous file with comments | « net/cert/asn1_util.h ('k') | net/cert/cert_verify_proc.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698