1 /* Copyright (c) 2014, Google Inc.
2  *
3  * Permission to use, copy, modify, and/or distribute this software for any
4  * purpose with or without fee is hereby granted, provided that the above
5  * copyright notice and this permission notice appear in all copies.
6  *
7  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
8  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
9  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
10  * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
11  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
12  * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
13  * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */
14 
15 #if !defined(__STDC_CONSTANT_MACROS)
16 #define __STDC_CONSTANT_MACROS
17 #endif
18 
19 #include <stdio.h>
20 #include <stdlib.h>
21 #include <string.h>
22 
23 #include <vector>
24 
25 #include <openssl/bytestring.h>
26 #include <openssl/crypto.h>
27 
28 #include "internal.h"
29 #include "../internal.h"
30 
31 
TestSkip()32 static bool TestSkip() {
33   static const uint8_t kData[] = {1, 2, 3};
34   CBS data;
35 
36   CBS_init(&data, kData, sizeof(kData));
37   return CBS_len(&data) == 3 &&
38       CBS_skip(&data, 1) &&
39       CBS_len(&data) == 2 &&
40       CBS_skip(&data, 2) &&
41       CBS_len(&data) == 0 &&
42       !CBS_skip(&data, 1);
43 }
44 
TestGetUint()45 static bool TestGetUint() {
46   static const uint8_t kData[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11};
47   uint8_t u8;
48   uint16_t u16;
49   uint32_t u32;
50   CBS data;
51 
52   CBS_init(&data, kData, sizeof(kData));
53   return CBS_get_u8(&data, &u8) &&
54     u8 == 1 &&
55     CBS_get_u16(&data, &u16) &&
56     u16 == 0x203 &&
57     CBS_get_u24(&data, &u32) &&
58     u32 == 0x40506 &&
59     CBS_get_u32(&data, &u32) &&
60     u32 == 0x708090a &&
61     CBS_get_last_u8(&data, &u8) &&
62     u8 == 0xb &&
63     !CBS_get_u8(&data, &u8) &&
64     !CBS_get_last_u8(&data, &u8);
65 }
66 
TestGetPrefixed()67 static bool TestGetPrefixed() {
68   static const uint8_t kData[] = {1, 2, 0, 2, 3, 4, 0, 0, 3, 3, 2, 1};
69   uint8_t u8;
70   uint16_t u16;
71   uint32_t u32;
72   CBS data, prefixed;
73 
74   CBS_init(&data, kData, sizeof(kData));
75   return CBS_get_u8_length_prefixed(&data, &prefixed) &&
76     CBS_len(&prefixed) == 1 &&
77     CBS_get_u8(&prefixed, &u8) &&
78     u8 == 2 &&
79     CBS_get_u16_length_prefixed(&data, &prefixed) &&
80     CBS_len(&prefixed) == 2 &&
81     CBS_get_u16(&prefixed, &u16) &&
82     u16 == 0x304 &&
83     CBS_get_u24_length_prefixed(&data, &prefixed) &&
84     CBS_len(&prefixed) == 3 &&
85     CBS_get_u24(&prefixed, &u32) &&
86     u32 == 0x30201;
87 }
88 
TestGetPrefixedBad()89 static bool TestGetPrefixedBad() {
90   static const uint8_t kData1[] = {2, 1};
91   static const uint8_t kData2[] = {0, 2, 1};
92   static const uint8_t kData3[] = {0, 0, 2, 1};
93   CBS data, prefixed;
94 
95   CBS_init(&data, kData1, sizeof(kData1));
96   if (CBS_get_u8_length_prefixed(&data, &prefixed)) {
97     return false;
98   }
99 
100   CBS_init(&data, kData2, sizeof(kData2));
101   if (CBS_get_u16_length_prefixed(&data, &prefixed)) {
102     return false;
103   }
104 
105   CBS_init(&data, kData3, sizeof(kData3));
106   if (CBS_get_u24_length_prefixed(&data, &prefixed)) {
107     return false;
108   }
109 
110   return true;
111 }
112 
TestGetASN1()113 static bool TestGetASN1() {
114   static const uint8_t kData1[] = {0x30, 2, 1, 2};
115   static const uint8_t kData2[] = {0x30, 3, 1, 2};
116   static const uint8_t kData3[] = {0x30, 0x80};
117   static const uint8_t kData4[] = {0x30, 0x81, 1, 1};
118   static const uint8_t kData5[4 + 0x80] = {0x30, 0x82, 0, 0x80};
119   static const uint8_t kData6[] = {0xa1, 3, 0x4, 1, 1};
120   static const uint8_t kData7[] = {0xa1, 3, 0x4, 2, 1};
121   static const uint8_t kData8[] = {0xa1, 3, 0x2, 1, 1};
122   static const uint8_t kData9[] = {0xa1, 3, 0x2, 1, 0xff};
123 
124   CBS data, contents;
125   int present;
126   uint64_t value;
127 
128   CBS_init(&data, kData1, sizeof(kData1));
129   if (CBS_peek_asn1_tag(&data, 0x1) ||
130       !CBS_peek_asn1_tag(&data, 0x30)) {
131     return false;
132   }
133   if (!CBS_get_asn1(&data, &contents, 0x30) ||
134       CBS_len(&contents) != 2 ||
135       OPENSSL_memcmp(CBS_data(&contents), "\x01\x02", 2) != 0) {
136     return false;
137   }
138 
139   CBS_init(&data, kData2, sizeof(kData2));
140   // data is truncated
141   if (CBS_get_asn1(&data, &contents, 0x30)) {
142     return false;
143   }
144 
145   CBS_init(&data, kData3, sizeof(kData3));
146   // zero byte length of length
147   if (CBS_get_asn1(&data, &contents, 0x30)) {
148     return false;
149   }
150 
151   CBS_init(&data, kData4, sizeof(kData4));
152   // long form mistakenly used.
153   if (CBS_get_asn1(&data, &contents, 0x30)) {
154     return false;
155   }
156 
157   CBS_init(&data, kData5, sizeof(kData5));
158   // length takes too many bytes.
159   if (CBS_get_asn1(&data, &contents, 0x30)) {
160     return false;
161   }
162 
163   CBS_init(&data, kData1, sizeof(kData1));
164   // wrong tag.
165   if (CBS_get_asn1(&data, &contents, 0x31)) {
166     return false;
167   }
168 
169   CBS_init(&data, NULL, 0);
170   // peek at empty data.
171   if (CBS_peek_asn1_tag(&data, 0x30)) {
172     return false;
173   }
174 
175   CBS_init(&data, NULL, 0);
176   // optional elements at empty data.
177   if (!CBS_get_optional_asn1(&data, &contents, &present, 0xa0) ||
178       present ||
179       !CBS_get_optional_asn1_octet_string(&data, &contents, &present, 0xa0) ||
180       present ||
181       CBS_len(&contents) != 0 ||
182       !CBS_get_optional_asn1_octet_string(&data, &contents, NULL, 0xa0) ||
183       CBS_len(&contents) != 0 ||
184       !CBS_get_optional_asn1_uint64(&data, &value, 0xa0, 42) ||
185       value != 42) {
186     return false;
187   }
188 
189   CBS_init(&data, kData6, sizeof(kData6));
190   // optional element.
191   if (!CBS_get_optional_asn1(&data, &contents, &present, 0xa0) ||
192       present ||
193       !CBS_get_optional_asn1(&data, &contents, &present, 0xa1) ||
194       !present ||
195       CBS_len(&contents) != 3 ||
196       OPENSSL_memcmp(CBS_data(&contents), "\x04\x01\x01", 3) != 0) {
197     return false;
198   }
199 
200   CBS_init(&data, kData6, sizeof(kData6));
201   // optional octet string.
202   if (!CBS_get_optional_asn1_octet_string(&data, &contents, &present, 0xa0) ||
203       present ||
204       CBS_len(&contents) != 0 ||
205       !CBS_get_optional_asn1_octet_string(&data, &contents, &present, 0xa1) ||
206       !present ||
207       CBS_len(&contents) != 1 ||
208       CBS_data(&contents)[0] != 1) {
209     return false;
210   }
211 
212   CBS_init(&data, kData7, sizeof(kData7));
213   // invalid optional octet string.
214   if (CBS_get_optional_asn1_octet_string(&data, &contents, &present, 0xa1)) {
215     return false;
216   }
217 
218   CBS_init(&data, kData8, sizeof(kData8));
219   // optional octet string.
220   if (!CBS_get_optional_asn1_uint64(&data, &value, 0xa0, 42) ||
221       value != 42 ||
222       !CBS_get_optional_asn1_uint64(&data, &value, 0xa1, 42) ||
223       value != 1) {
224     return false;
225   }
226 
227   CBS_init(&data, kData9, sizeof(kData9));
228   // invalid optional integer.
229   if (CBS_get_optional_asn1_uint64(&data, &value, 0xa1, 42)) {
230     return false;
231   }
232 
233   unsigned tag;
234   CBS_init(&data, kData1, sizeof(kData1));
235   if (!CBS_get_any_asn1(&data, &contents, &tag) ||
236       tag != CBS_ASN1_SEQUENCE ||
237       CBS_len(&contents) != 2 ||
238       OPENSSL_memcmp(CBS_data(&contents), "\x01\x02", 2) != 0) {
239     return false;
240   }
241 
242   size_t header_len;
243   CBS_init(&data, kData1, sizeof(kData1));
244   if (!CBS_get_any_asn1_element(&data, &contents, &tag, &header_len) ||
245       tag != CBS_ASN1_SEQUENCE ||
246       header_len != 2 ||
247       CBS_len(&contents) != 4 ||
248       OPENSSL_memcmp(CBS_data(&contents), "\x30\x02\x01\x02", 2) != 0) {
249     return false;
250   }
251 
252   return true;
253 }
254 
TestGetOptionalASN1Bool()255 static bool TestGetOptionalASN1Bool() {
256   static const uint8_t kTrue[] = {0x0a, 3, CBS_ASN1_BOOLEAN, 1, 0xff};
257   static const uint8_t kFalse[] = {0x0a, 3, CBS_ASN1_BOOLEAN, 1, 0x00};
258   static const uint8_t kInvalid[] = {0x0a, 3, CBS_ASN1_BOOLEAN, 1, 0x01};
259 
260   CBS data;
261   CBS_init(&data, NULL, 0);
262   int val = 2;
263   if (!CBS_get_optional_asn1_bool(&data, &val, 0x0a, 0) ||
264       val != 0) {
265     return false;
266   }
267 
268   CBS_init(&data, kTrue, sizeof(kTrue));
269   val = 2;
270   if (!CBS_get_optional_asn1_bool(&data, &val, 0x0a, 0) ||
271       val != 1) {
272     return false;
273   }
274 
275   CBS_init(&data, kFalse, sizeof(kFalse));
276   val = 2;
277   if (!CBS_get_optional_asn1_bool(&data, &val, 0x0a, 1) ||
278       val != 0) {
279     return false;
280   }
281 
282   CBS_init(&data, kInvalid, sizeof(kInvalid));
283   if (CBS_get_optional_asn1_bool(&data, &val, 0x0a, 1)) {
284     return false;
285   }
286 
287   return true;
288 }
289 
TestCBBBasic()290 static bool TestCBBBasic() {
291   static const uint8_t kExpected[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 0xa, 0xb, 0xc};
292   uint8_t *buf;
293   size_t buf_len;
294   CBB cbb;
295 
296   if (!CBB_init(&cbb, 100)) {
297     return false;
298   }
299   CBB_cleanup(&cbb);
300 
301   if (!CBB_init(&cbb, 0)) {
302     return false;
303   }
304   if (!CBB_add_u8(&cbb, 1) ||
305       !CBB_add_u16(&cbb, 0x203) ||
306       !CBB_add_u24(&cbb, 0x40506) ||
307       !CBB_add_u32(&cbb, 0x708090a) ||
308       !CBB_add_bytes(&cbb, (const uint8_t*) "\x0b\x0c", 2) ||
309       !CBB_finish(&cbb, &buf, &buf_len)) {
310     CBB_cleanup(&cbb);
311     return false;
312   }
313 
314   bssl::UniquePtr<uint8_t> scoper(buf);
315   return buf_len == sizeof(kExpected) &&
316          OPENSSL_memcmp(buf, kExpected, buf_len) == 0;
317 }
318 
TestCBBFixed()319 static bool TestCBBFixed() {
320   bssl::ScopedCBB cbb;
321   uint8_t buf[1];
322   uint8_t *out_buf;
323   size_t out_size;
324 
325   if (!CBB_init_fixed(cbb.get(), NULL, 0) ||
326       !CBB_finish(cbb.get(), &out_buf, &out_size) ||
327       out_buf != NULL ||
328       out_size != 0) {
329     return false;
330   }
331 
332   cbb.Reset();
333   if (!CBB_init_fixed(cbb.get(), buf, 1) ||
334       !CBB_add_u8(cbb.get(), 1) ||
335       !CBB_finish(cbb.get(), &out_buf, &out_size) ||
336       out_buf != buf ||
337       out_size != 1 ||
338       buf[0] != 1) {
339     return false;
340   }
341 
342   cbb.Reset();
343   if (!CBB_init_fixed(cbb.get(), buf, 1) ||
344       !CBB_add_u8(cbb.get(), 1) ||
345       CBB_add_u8(cbb.get(), 2)) {
346     return false;
347   }
348 
349   return true;
350 }
351 
TestCBBFinishChild()352 static bool TestCBBFinishChild() {
353   CBB cbb, child;
354   uint8_t *out_buf;
355   size_t out_size;
356 
357   if (!CBB_init(&cbb, 16)) {
358     return false;
359   }
360   if (!CBB_add_u8_length_prefixed(&cbb, &child) ||
361       CBB_finish(&child, &out_buf, &out_size) ||
362       !CBB_finish(&cbb, &out_buf, &out_size)) {
363     CBB_cleanup(&cbb);
364     return false;
365   }
366   bssl::UniquePtr<uint8_t> scoper(out_buf);
367   return out_size == 1 && out_buf[0] == 0;
368 }
369 
TestCBBPrefixed()370 static bool TestCBBPrefixed() {
371   static const uint8_t kExpected[] = {0, 1, 1, 0, 2, 2, 3, 0, 0, 3,
372                                       4, 5, 6, 5, 4, 1, 0, 1, 2};
373   uint8_t *buf;
374   size_t buf_len;
375   CBB cbb, contents, inner_contents, inner_inner_contents;
376 
377   if (!CBB_init(&cbb, 0) ||
378       CBB_len(&cbb) != 0 ||
379       !CBB_add_u8_length_prefixed(&cbb, &contents) ||
380       !CBB_add_u8_length_prefixed(&cbb, &contents) ||
381       !CBB_add_u8(&contents, 1) ||
382       CBB_len(&contents) != 1 ||
383       !CBB_flush(&cbb) ||
384       CBB_len(&cbb) != 3 ||
385       !CBB_add_u16_length_prefixed(&cbb, &contents) ||
386       !CBB_add_u16(&contents, 0x203) ||
387       !CBB_add_u24_length_prefixed(&cbb, &contents) ||
388       !CBB_add_u24(&contents, 0x40506) ||
389       !CBB_add_u8_length_prefixed(&cbb, &contents) ||
390       !CBB_add_u8_length_prefixed(&contents, &inner_contents) ||
391       !CBB_add_u8(&inner_contents, 1) ||
392       !CBB_add_u16_length_prefixed(&inner_contents, &inner_inner_contents) ||
393       !CBB_add_u8(&inner_inner_contents, 2) ||
394       !CBB_finish(&cbb, &buf, &buf_len)) {
395     CBB_cleanup(&cbb);
396     return false;
397   }
398 
399   bssl::UniquePtr<uint8_t> scoper(buf);
400   return buf_len == sizeof(kExpected) &&
401          OPENSSL_memcmp(buf, kExpected, buf_len) == 0;
402 }
403 
TestCBBDiscardChild()404 static bool TestCBBDiscardChild() {
405   bssl::ScopedCBB cbb;
406   CBB contents, inner_contents, inner_inner_contents;
407 
408   if (!CBB_init(cbb.get(), 0) ||
409       !CBB_add_u8(cbb.get(), 0xaa)) {
410     return false;
411   }
412 
413   // Discarding |cbb|'s children preserves the byte written.
414   CBB_discard_child(cbb.get());
415 
416   if (!CBB_add_u8_length_prefixed(cbb.get(), &contents) ||
417       !CBB_add_u8_length_prefixed(cbb.get(), &contents) ||
418       !CBB_add_u8(&contents, 0xbb) ||
419       !CBB_add_u16_length_prefixed(cbb.get(), &contents) ||
420       !CBB_add_u16(&contents, 0xcccc) ||
421       !CBB_add_u24_length_prefixed(cbb.get(), &contents) ||
422       !CBB_add_u24(&contents, 0xdddddd) ||
423       !CBB_add_u8_length_prefixed(cbb.get(), &contents) ||
424       !CBB_add_u8(&contents, 0xff) ||
425       !CBB_add_u8_length_prefixed(&contents, &inner_contents) ||
426       !CBB_add_u8(&inner_contents, 0x42) ||
427       !CBB_add_u16_length_prefixed(&inner_contents, &inner_inner_contents) ||
428       !CBB_add_u8(&inner_inner_contents, 0x99)) {
429     return false;
430   }
431 
432   // Discard everything from |inner_contents| down.
433   CBB_discard_child(&contents);
434 
435   uint8_t *buf;
436   size_t buf_len;
437   if (!CBB_finish(cbb.get(), &buf, &buf_len)) {
438     return false;
439   }
440   bssl::UniquePtr<uint8_t> scoper(buf);
441 
442   static const uint8_t kExpected[] = {
443         0xaa,
444         0,
445         1, 0xbb,
446         0, 2, 0xcc, 0xcc,
447         0, 0, 3, 0xdd, 0xdd, 0xdd,
448         1, 0xff,
449   };
450   return buf_len == sizeof(kExpected) &&
451          OPENSSL_memcmp(buf, kExpected, buf_len) == 0;
452 }
453 
TestCBBMisuse()454 static bool TestCBBMisuse() {
455   CBB cbb, child, contents;
456   uint8_t *buf;
457   size_t buf_len;
458 
459   if (!CBB_init(&cbb, 0)) {
460     return false;
461   }
462   if (!CBB_add_u8_length_prefixed(&cbb, &child) ||
463       !CBB_add_u8(&child, 1) ||
464       !CBB_add_u8(&cbb, 2)) {
465     CBB_cleanup(&cbb);
466     return false;
467   }
468 
469   // Since we wrote to |cbb|, |child| is now invalid and attempts to write to
470   // it should fail.
471   if (CBB_add_u8(&child, 1) ||
472       CBB_add_u16(&child, 1) ||
473       CBB_add_u24(&child, 1) ||
474       CBB_add_u8_length_prefixed(&child, &contents) ||
475       CBB_add_u16_length_prefixed(&child, &contents) ||
476       CBB_add_asn1(&child, &contents, 1) ||
477       CBB_add_bytes(&child, (const uint8_t*) "a", 1)) {
478     fprintf(stderr, "CBB operation on invalid CBB did not fail.\n");
479     CBB_cleanup(&cbb);
480     return false;
481   }
482 
483   if (!CBB_finish(&cbb, &buf, &buf_len)) {
484     CBB_cleanup(&cbb);
485     return false;
486   }
487   bssl::UniquePtr<uint8_t> scoper(buf);
488 
489   if (buf_len != 3 ||
490       OPENSSL_memcmp(buf, "\x01\x01\x02", 3) != 0) {
491     return false;
492   }
493   return true;
494 }
495 
TestCBBASN1()496 static bool TestCBBASN1() {
497   static const uint8_t kExpected[] = {0x30, 3, 1, 2, 3};
498   uint8_t *buf;
499   size_t buf_len;
500   CBB cbb, contents, inner_contents;
501 
502   if (!CBB_init(&cbb, 0)) {
503     return false;
504   }
505   if (!CBB_add_asn1(&cbb, &contents, 0x30) ||
506       !CBB_add_bytes(&contents, (const uint8_t*) "\x01\x02\x03", 3) ||
507       !CBB_finish(&cbb, &buf, &buf_len)) {
508     CBB_cleanup(&cbb);
509     return false;
510   }
511   bssl::UniquePtr<uint8_t> scoper(buf);
512 
513   if (buf_len != sizeof(kExpected) ||
514       OPENSSL_memcmp(buf, kExpected, buf_len) != 0) {
515     return false;
516   }
517 
518   std::vector<uint8_t> test_data(100000, 0x42);
519 
520   if (!CBB_init(&cbb, 0)) {
521     return false;
522   }
523   if (!CBB_add_asn1(&cbb, &contents, 0x30) ||
524       !CBB_add_bytes(&contents, test_data.data(), 130) ||
525       !CBB_finish(&cbb, &buf, &buf_len)) {
526     CBB_cleanup(&cbb);
527     return false;
528   }
529   scoper.reset(buf);
530 
531   if (buf_len != 3 + 130 ||
532       OPENSSL_memcmp(buf, "\x30\x81\x82", 3) != 0 ||
533       OPENSSL_memcmp(buf + 3, test_data.data(), 130) != 0) {
534     return false;
535   }
536 
537   if (!CBB_init(&cbb, 0)) {
538     return false;
539   }
540   if (!CBB_add_asn1(&cbb, &contents, 0x30) ||
541       !CBB_add_bytes(&contents, test_data.data(), 1000) ||
542       !CBB_finish(&cbb, &buf, &buf_len)) {
543     CBB_cleanup(&cbb);
544     return false;
545   }
546   scoper.reset(buf);
547 
548   if (buf_len != 4 + 1000 ||
549       OPENSSL_memcmp(buf, "\x30\x82\x03\xe8", 4) != 0 ||
550       OPENSSL_memcmp(buf + 4, test_data.data(), 1000)) {
551     return false;
552   }
553 
554   if (!CBB_init(&cbb, 0)) {
555     return false;
556   }
557   if (!CBB_add_asn1(&cbb, &contents, 0x30) ||
558       !CBB_add_asn1(&contents, &inner_contents, 0x30) ||
559       !CBB_add_bytes(&inner_contents, test_data.data(), 100000) ||
560       !CBB_finish(&cbb, &buf, &buf_len)) {
561     CBB_cleanup(&cbb);
562     return false;
563   }
564   scoper.reset(buf);
565 
566   if (buf_len != 5 + 5 + 100000 ||
567       OPENSSL_memcmp(buf, "\x30\x83\x01\x86\xa5\x30\x83\x01\x86\xa0", 10) !=
568           0 ||
569       OPENSSL_memcmp(buf + 10, test_data.data(), 100000)) {
570     return false;
571   }
572 
573   return true;
574 }
575 
DoBerConvert(const char * name,const uint8_t * der_expected,size_t der_len,const uint8_t * ber,size_t ber_len)576 static bool DoBerConvert(const char *name,
577                          const uint8_t *der_expected, size_t der_len,
578                          const uint8_t *ber, size_t ber_len) {
579   CBS in;
580   uint8_t *out;
581   size_t out_len;
582 
583   CBS_init(&in, ber, ber_len);
584   if (!CBS_asn1_ber_to_der(&in, &out, &out_len)) {
585     fprintf(stderr, "%s: CBS_asn1_ber_to_der failed.\n", name);
586     return false;
587   }
588   bssl::UniquePtr<uint8_t> scoper(out);
589 
590   if (out == NULL) {
591     if (ber_len != der_len ||
592         OPENSSL_memcmp(der_expected, ber, ber_len) != 0) {
593       fprintf(stderr, "%s: incorrect unconverted result.\n", name);
594       return false;
595     }
596 
597     return true;
598   }
599 
600   if (out_len != der_len ||
601       OPENSSL_memcmp(out, der_expected, der_len) != 0) {
602     fprintf(stderr, "%s: incorrect converted result.\n", name);
603     return false;
604   }
605 
606   return true;
607 }
608 
TestBerConvert()609 static bool TestBerConvert() {
610   static const uint8_t kSimpleBER[] = {0x01, 0x01, 0x00};
611 
612   // kIndefBER contains a SEQUENCE with an indefinite length.
613   static const uint8_t kIndefBER[] = {0x30, 0x80, 0x01, 0x01, 0x02, 0x00, 0x00};
614   static const uint8_t kIndefDER[] = {0x30, 0x03, 0x01, 0x01, 0x02};
615 
616   // kOctetStringBER contains an indefinite length OCTET STRING with two parts.
617   // These parts need to be concatenated in DER form.
618   static const uint8_t kOctetStringBER[] = {0x24, 0x80, 0x04, 0x02, 0,    1,
619                                             0x04, 0x02, 2,    3,    0x00, 0x00};
620   static const uint8_t kOctetStringDER[] = {0x04, 0x04, 0, 1, 2, 3};
621 
622   // kNSSBER is part of a PKCS#12 message generated by NSS that uses indefinite
623   // length elements extensively.
624   static const uint8_t kNSSBER[] = {
625       0x30, 0x80, 0x02, 0x01, 0x03, 0x30, 0x80, 0x06, 0x09, 0x2a, 0x86, 0x48,
626       0x86, 0xf7, 0x0d, 0x01, 0x07, 0x01, 0xa0, 0x80, 0x24, 0x80, 0x04, 0x04,
627       0x01, 0x02, 0x03, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x39,
628       0x30, 0x21, 0x30, 0x09, 0x06, 0x05, 0x2b, 0x0e, 0x03, 0x02, 0x1a, 0x05,
629       0x00, 0x04, 0x14, 0x84, 0x98, 0xfc, 0x66, 0x33, 0xee, 0xba, 0xe7, 0x90,
630       0xc1, 0xb6, 0xe8, 0x8f, 0xfe, 0x1d, 0xc5, 0xa5, 0x97, 0x93, 0x3e, 0x04,
631       0x10, 0x38, 0x62, 0xc6, 0x44, 0x12, 0xd5, 0x30, 0x00, 0xf8, 0xf2, 0x1b,
632       0xf0, 0x6e, 0x10, 0x9b, 0xb8, 0x02, 0x02, 0x07, 0xd0, 0x00, 0x00,
633   };
634 
635   static const uint8_t kNSSDER[] = {
636       0x30, 0x53, 0x02, 0x01, 0x03, 0x30, 0x13, 0x06, 0x09, 0x2a, 0x86,
637       0x48, 0x86, 0xf7, 0x0d, 0x01, 0x07, 0x01, 0xa0, 0x06, 0x04, 0x04,
638       0x01, 0x02, 0x03, 0x04, 0x30, 0x39, 0x30, 0x21, 0x30, 0x09, 0x06,
639       0x05, 0x2b, 0x0e, 0x03, 0x02, 0x1a, 0x05, 0x00, 0x04, 0x14, 0x84,
640       0x98, 0xfc, 0x66, 0x33, 0xee, 0xba, 0xe7, 0x90, 0xc1, 0xb6, 0xe8,
641       0x8f, 0xfe, 0x1d, 0xc5, 0xa5, 0x97, 0x93, 0x3e, 0x04, 0x10, 0x38,
642       0x62, 0xc6, 0x44, 0x12, 0xd5, 0x30, 0x00, 0xf8, 0xf2, 0x1b, 0xf0,
643       0x6e, 0x10, 0x9b, 0xb8, 0x02, 0x02, 0x07, 0xd0,
644   };
645 
646   // kConstructedStringBER contains a deeply-nested constructed OCTET STRING.
647   // The BER conversion collapses this to one level deep, but not completely.
648   static const uint8_t kConstructedStringBER[] = {
649       0xa0, 0x10, 0x24, 0x06, 0x04, 0x01, 0x00, 0x04, 0x01,
650       0x01, 0x24, 0x06, 0x04, 0x01, 0x02, 0x04, 0x01, 0x03,
651   };
652   static const uint8_t kConstructedStringDER[] = {
653       0xa0, 0x08, 0x04, 0x02, 0x00, 0x01, 0x04, 0x02, 0x02, 0x03,
654   };
655 
656   return DoBerConvert("kSimpleBER", kSimpleBER, sizeof(kSimpleBER),
657                       kSimpleBER, sizeof(kSimpleBER)) &&
658          DoBerConvert("kIndefBER", kIndefDER, sizeof(kIndefDER), kIndefBER,
659                       sizeof(kIndefBER)) &&
660          DoBerConvert("kOctetStringBER", kOctetStringDER,
661                       sizeof(kOctetStringDER), kOctetStringBER,
662                       sizeof(kOctetStringBER)) &&
663          DoBerConvert("kNSSBER", kNSSDER, sizeof(kNSSDER), kNSSBER,
664                       sizeof(kNSSBER)) &&
665          DoBerConvert("kConstructedStringBER", kConstructedStringDER,
666                       sizeof(kConstructedStringDER), kConstructedStringBER,
667                       sizeof(kConstructedStringBER));
668 }
669 
670 struct ImplicitStringTest {
671   const char *in;
672   size_t in_len;
673   bool ok;
674   const char *out;
675   size_t out_len;
676 };
677 
678 static const ImplicitStringTest kImplicitStringTests[] = {
679     // A properly-encoded string.
680     {"\x80\x03\x61\x61\x61", 5, true, "aaa", 3},
681     // An implicit-tagged string.
682     {"\xa0\x09\x04\x01\x61\x04\x01\x61\x04\x01\x61", 11, true, "aaa", 3},
683     // |CBS_get_asn1_implicit_string| only accepts one level deep of nesting.
684     {"\xa0\x0b\x24\x06\x04\x01\x61\x04\x01\x61\x04\x01\x61", 13, false, nullptr,
685      0},
686     // The outer tag must match.
687     {"\x81\x03\x61\x61\x61", 5, false, nullptr, 0},
688     {"\xa1\x09\x04\x01\x61\x04\x01\x61\x04\x01\x61", 11, false, nullptr, 0},
689     // The inner tag must match.
690     {"\xa1\x09\x0c\x01\x61\x0c\x01\x61\x0c\x01\x61", 11, false, nullptr, 0},
691 };
692 
TestImplicitString()693 static bool TestImplicitString() {
694   for (const auto &test : kImplicitStringTests) {
695     uint8_t *storage = nullptr;
696     CBS in, out;
697     CBS_init(&in, reinterpret_cast<const uint8_t *>(test.in), test.in_len);
698     int ok = CBS_get_asn1_implicit_string(&in, &out, &storage,
699                                           CBS_ASN1_CONTEXT_SPECIFIC | 0,
700                                           CBS_ASN1_OCTETSTRING);
701     bssl::UniquePtr<uint8_t> scoper(storage);
702 
703     if (static_cast<bool>(ok) != test.ok) {
704       fprintf(stderr, "CBS_get_asn1_implicit_string unexpectedly %s\n",
705               ok ? "succeeded" : "failed");
706       return false;
707     }
708 
709     if (ok && (CBS_len(&out) != test.out_len ||
710                OPENSSL_memcmp(CBS_data(&out), test.out, test.out_len) != 0)) {
711       fprintf(stderr, "CBS_get_asn1_implicit_string gave the wrong output\n");
712       return false;
713     }
714   }
715 
716   return true;
717 }
718 
719 struct ASN1Uint64Test {
720   uint64_t value;
721   const char *encoding;
722   size_t encoding_len;
723 };
724 
725 static const ASN1Uint64Test kASN1Uint64Tests[] = {
726     {0, "\x02\x01\x00", 3},
727     {1, "\x02\x01\x01", 3},
728     {127, "\x02\x01\x7f", 3},
729     {128, "\x02\x02\x00\x80", 4},
730     {0xdeadbeef, "\x02\x05\x00\xde\xad\xbe\xef", 7},
731     {UINT64_C(0x0102030405060708),
732      "\x02\x08\x01\x02\x03\x04\x05\x06\x07\x08", 10},
733     {UINT64_C(0xffffffffffffffff),
734       "\x02\x09\x00\xff\xff\xff\xff\xff\xff\xff\xff", 11},
735 };
736 
737 struct ASN1InvalidUint64Test {
738   const char *encoding;
739   size_t encoding_len;
740 };
741 
742 static const ASN1InvalidUint64Test kASN1InvalidUint64Tests[] = {
743     // Bad tag.
744     {"\x03\x01\x00", 3},
745     // Empty contents.
746     {"\x02\x00", 2},
747     // Negative number.
748     {"\x02\x01\x80", 3},
749     // Overflow.
750     {"\x02\x09\x01\x00\x00\x00\x00\x00\x00\x00\x00", 11},
751     // Leading zeros.
752     {"\x02\x02\x00\x01", 4},
753 };
754 
TestASN1Uint64()755 static bool TestASN1Uint64() {
756   for (size_t i = 0; i < OPENSSL_ARRAY_SIZE(kASN1Uint64Tests); i++) {
757     const ASN1Uint64Test *test = &kASN1Uint64Tests[i];
758     CBS cbs;
759     uint64_t value;
760     CBB cbb;
761     uint8_t *out;
762     size_t len;
763 
764     CBS_init(&cbs, (const uint8_t *)test->encoding, test->encoding_len);
765     if (!CBS_get_asn1_uint64(&cbs, &value) ||
766         CBS_len(&cbs) != 0 ||
767         value != test->value) {
768       return false;
769     }
770 
771     if (!CBB_init(&cbb, 0)) {
772       return false;
773     }
774     if (!CBB_add_asn1_uint64(&cbb, test->value) ||
775         !CBB_finish(&cbb, &out, &len)) {
776       CBB_cleanup(&cbb);
777       return false;
778     }
779     bssl::UniquePtr<uint8_t> scoper(out);
780     if (len != test->encoding_len ||
781         OPENSSL_memcmp(out, test->encoding, len) != 0) {
782       return false;
783     }
784   }
785 
786   for (size_t i = 0; i < OPENSSL_ARRAY_SIZE(kASN1InvalidUint64Tests); i++) {
787     const ASN1InvalidUint64Test *test = &kASN1InvalidUint64Tests[i];
788     CBS cbs;
789     uint64_t value;
790 
791     CBS_init(&cbs, (const uint8_t *)test->encoding, test->encoding_len);
792     if (CBS_get_asn1_uint64(&cbs, &value)) {
793       return false;
794     }
795   }
796 
797   return true;
798 }
799 
TestZero()800 static bool TestZero() {
801   CBB cbb;
802   CBB_zero(&cbb);
803   // Calling |CBB_cleanup| on a zero-state |CBB| must not crash.
804   CBB_cleanup(&cbb);
805   return true;
806 }
807 
TestCBBReserve()808 static bool TestCBBReserve() {
809   uint8_t buf[10];
810   uint8_t *ptr;
811   size_t len;
812   bssl::ScopedCBB cbb;
813   if (!CBB_init_fixed(cbb.get(), buf, sizeof(buf)) ||
814       // Too large.
815       CBB_reserve(cbb.get(), &ptr, 11)) {
816     return false;
817   }
818 
819   cbb.Reset();
820   if (!CBB_init_fixed(cbb.get(), buf, sizeof(buf)) ||
821       // Successfully reserve the entire space.
822       !CBB_reserve(cbb.get(), &ptr, 10) ||
823       ptr != buf ||
824       // Advancing under the maximum bytes is legal.
825       !CBB_did_write(cbb.get(), 5) ||
826       !CBB_finish(cbb.get(), NULL, &len) ||
827       len != 5) {
828     return false;
829   }
830   return true;
831 }
832 
TestStickyError()833 static bool TestStickyError() {
834   // Write an input that exceeds the limit for its length prefix.
835   bssl::ScopedCBB cbb;
836   CBB child;
837   static const uint8_t kZeros[256] = {0};
838   if (!CBB_init(cbb.get(), 0) ||
839       !CBB_add_u8_length_prefixed(cbb.get(), &child) ||
840       !CBB_add_bytes(&child, kZeros, sizeof(kZeros))) {
841     return false;
842   }
843 
844   if (CBB_flush(cbb.get())) {
845     fprintf(stderr, "CBB_flush unexpectedly succeeded.\n");
846     return false;
847   }
848 
849   // All future operations should fail.
850   uint8_t *ptr;
851   size_t len;
852   if (CBB_add_u8(cbb.get(), 0) ||
853       CBB_finish(cbb.get(), &ptr, &len)) {
854     fprintf(stderr, "Future operations unexpectedly succeeded.\n");
855     return false;
856   }
857 
858   // Write an input that cannot fit in a fixed CBB.
859   cbb.Reset();
860   uint8_t buf;
861   if (!CBB_init_fixed(cbb.get(), &buf, 1)) {
862     return false;
863   }
864 
865   if (CBB_add_bytes(cbb.get(), kZeros, sizeof(kZeros))) {
866     fprintf(stderr, "CBB_add_bytes unexpectedly succeeded.\n");
867     return false;
868   }
869 
870   // All future operations should fail.
871   if (CBB_add_u8(cbb.get(), 0) ||
872       CBB_finish(cbb.get(), &ptr, &len)) {
873     fprintf(stderr, "Future operations unexpectedly succeeded.\n");
874     return false;
875   }
876 
877   // Write a u32 that cannot fit in a u24.
878   cbb.Reset();
879   if (!CBB_init(cbb.get(), 0)) {
880     return false;
881   }
882 
883   if (CBB_add_u24(cbb.get(), 1u << 24)) {
884     fprintf(stderr, "CBB_add_u24 unexpectedly succeeded.\n");
885     return false;
886   }
887 
888   // All future operations should fail.
889   if (CBB_add_u8(cbb.get(), 0) ||
890       CBB_finish(cbb.get(), &ptr, &len)) {
891     fprintf(stderr, "Future operations unexpectedly succeeded.\n");
892     return false;
893   }
894 
895   return true;
896 }
897 
TestBitString()898 static bool TestBitString() {
899   static const std::vector<uint8_t> kValidBitStrings[] = {
900       {0x00},                                      // 0 bits
901       {0x07, 0x80},                                // 1 bit
902       {0x04, 0xf0},                                // 4 bits
903       {0x00, 0xff},                                // 8 bits
904       {0x06, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc0},  // 42 bits
905   };
906   for (const auto& test : kValidBitStrings) {
907     CBS cbs;
908     CBS_init(&cbs, test.data(), test.size());
909     if (!CBS_is_valid_asn1_bitstring(&cbs)) {
910       return false;
911     }
912   }
913 
914   static const std::vector<uint8_t> kInvalidBitStrings[] = {
915       // BIT STRINGs always have a leading byte.
916       std::vector<uint8_t>{},
917       // It's not possible to take an unused bit off the empty string.
918       {0x01},
919       // There can be at most 7 unused bits.
920       {0x08, 0xff},
921       {0xff, 0xff},
922       // All unused bits must be cleared.
923       {0x06, 0xff, 0xc1},
924   };
925   for (const auto& test : kInvalidBitStrings) {
926     CBS cbs;
927     CBS_init(&cbs, test.data(), test.size());
928     if (CBS_is_valid_asn1_bitstring(&cbs)) {
929       return false;
930     }
931 
932     // CBS_asn1_bitstring_has_bit returns false on invalid inputs.
933     if (CBS_asn1_bitstring_has_bit(&cbs, 0)) {
934       return false;
935     }
936   }
937 
938   static const struct {
939     std::vector<uint8_t> in;
940     unsigned bit;
941     bool bit_set;
942   } kBitTests[] = {
943       // Basic tests.
944       {{0x00}, 0, false},
945       {{0x07, 0x80}, 0, true},
946       {{0x06, 0x0f, 0x40}, 0, false},
947       {{0x06, 0x0f, 0x40}, 1, false},
948       {{0x06, 0x0f, 0x40}, 2, false},
949       {{0x06, 0x0f, 0x40}, 3, false},
950       {{0x06, 0x0f, 0x40}, 4, true},
951       {{0x06, 0x0f, 0x40}, 5, true},
952       {{0x06, 0x0f, 0x40}, 6, true},
953       {{0x06, 0x0f, 0x40}, 7, true},
954       {{0x06, 0x0f, 0x40}, 8, false},
955       {{0x06, 0x0f, 0x40}, 9, true},
956       // Out-of-bounds bits return 0.
957       {{0x06, 0x0f, 0x40}, 10, false},
958       {{0x06, 0x0f, 0x40}, 15, false},
959       {{0x06, 0x0f, 0x40}, 16, false},
960       {{0x06, 0x0f, 0x40}, 1000, false},
961   };
962   for (const auto& test : kBitTests) {
963     CBS cbs;
964     CBS_init(&cbs, test.in.data(), test.in.size());
965     if (CBS_asn1_bitstring_has_bit(&cbs, test.bit) !=
966         static_cast<int>(test.bit_set)) {
967       return false;
968     }
969   }
970 
971   return true;
972 }
973 
main()974 int main() {
975   CRYPTO_library_init();
976 
977   if (!TestSkip() ||
978       !TestGetUint() ||
979       !TestGetPrefixed() ||
980       !TestGetPrefixedBad() ||
981       !TestGetASN1() ||
982       !TestCBBBasic() ||
983       !TestCBBFixed() ||
984       !TestCBBFinishChild() ||
985       !TestCBBMisuse() ||
986       !TestCBBPrefixed() ||
987       !TestCBBDiscardChild() ||
988       !TestCBBASN1() ||
989       !TestBerConvert() ||
990       !TestImplicitString() ||
991       !TestASN1Uint64() ||
992       !TestGetOptionalASN1Bool() ||
993       !TestZero() ||
994       !TestCBBReserve() ||
995       !TestStickyError() ||
996       !TestBitString()) {
997     return 1;
998   }
999 
1000   printf("PASS\n");
1001   return 0;
1002 }
1003