Home | History | Annotate | Download | only in asn1
      1 // Copyright 2009 The Go Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style
      3 // license that can be found in the LICENSE file.
      4 
      5 package asn1
      6 
      7 import (
      8 	"bytes"
      9 	"fmt"
     10 	"math"
     11 	"math/big"
     12 	"reflect"
     13 	"strings"
     14 	"testing"
     15 	"time"
     16 )
     17 
     18 type boolTest struct {
     19 	in  []byte
     20 	ok  bool
     21 	out bool
     22 }
     23 
     24 var boolTestData = []boolTest{
     25 	{[]byte{0x00}, true, false},
     26 	{[]byte{0xff}, true, true},
     27 	{[]byte{0x00, 0x00}, false, false},
     28 	{[]byte{0xff, 0xff}, false, false},
     29 	{[]byte{0x01}, false, false},
     30 }
     31 
     32 func TestParseBool(t *testing.T) {
     33 	for i, test := range boolTestData {
     34 		ret, err := parseBool(test.in)
     35 		if (err == nil) != test.ok {
     36 			t.Errorf("#%d: Incorrect error result (did fail? %v, expected: %v)", i, err == nil, test.ok)
     37 		}
     38 		if test.ok && ret != test.out {
     39 			t.Errorf("#%d: Bad result: %v (expected %v)", i, ret, test.out)
     40 		}
     41 	}
     42 }
     43 
     44 type int64Test struct {
     45 	in  []byte
     46 	ok  bool
     47 	out int64
     48 }
     49 
     50 var int64TestData = []int64Test{
     51 	{[]byte{0x00}, true, 0},
     52 	{[]byte{0x7f}, true, 127},
     53 	{[]byte{0x00, 0x80}, true, 128},
     54 	{[]byte{0x01, 0x00}, true, 256},
     55 	{[]byte{0x80}, true, -128},
     56 	{[]byte{0xff, 0x7f}, true, -129},
     57 	{[]byte{0xff}, true, -1},
     58 	{[]byte{0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, true, -9223372036854775808},
     59 	{[]byte{0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, false, 0},
     60 	{[]byte{}, false, 0},
     61 	{[]byte{0x00, 0x7f}, false, 0},
     62 	{[]byte{0xff, 0xf0}, false, 0},
     63 }
     64 
     65 func TestParseInt64(t *testing.T) {
     66 	for i, test := range int64TestData {
     67 		ret, err := parseInt64(test.in)
     68 		if (err == nil) != test.ok {
     69 			t.Errorf("#%d: Incorrect error result (did fail? %v, expected: %v)", i, err == nil, test.ok)
     70 		}
     71 		if test.ok && ret != test.out {
     72 			t.Errorf("#%d: Bad result: %v (expected %v)", i, ret, test.out)
     73 		}
     74 	}
     75 }
     76 
     77 type int32Test struct {
     78 	in  []byte
     79 	ok  bool
     80 	out int32
     81 }
     82 
     83 var int32TestData = []int32Test{
     84 	{[]byte{0x00}, true, 0},
     85 	{[]byte{0x7f}, true, 127},
     86 	{[]byte{0x00, 0x80}, true, 128},
     87 	{[]byte{0x01, 0x00}, true, 256},
     88 	{[]byte{0x80}, true, -128},
     89 	{[]byte{0xff, 0x7f}, true, -129},
     90 	{[]byte{0xff}, true, -1},
     91 	{[]byte{0x80, 0x00, 0x00, 0x00}, true, -2147483648},
     92 	{[]byte{0x80, 0x00, 0x00, 0x00, 0x00}, false, 0},
     93 	{[]byte{}, false, 0},
     94 	{[]byte{0x00, 0x7f}, false, 0},
     95 	{[]byte{0xff, 0xf0}, false, 0},
     96 }
     97 
     98 func TestParseInt32(t *testing.T) {
     99 	for i, test := range int32TestData {
    100 		ret, err := parseInt32(test.in)
    101 		if (err == nil) != test.ok {
    102 			t.Errorf("#%d: Incorrect error result (did fail? %v, expected: %v)", i, err == nil, test.ok)
    103 		}
    104 		if test.ok && int32(ret) != test.out {
    105 			t.Errorf("#%d: Bad result: %v (expected %v)", i, ret, test.out)
    106 		}
    107 	}
    108 }
    109 
    110 var bigIntTests = []struct {
    111 	in     []byte
    112 	ok     bool
    113 	base10 string
    114 }{
    115 	{[]byte{0xff}, true, "-1"},
    116 	{[]byte{0x00}, true, "0"},
    117 	{[]byte{0x01}, true, "1"},
    118 	{[]byte{0x00, 0xff}, true, "255"},
    119 	{[]byte{0xff, 0x00}, true, "-256"},
    120 	{[]byte{0x01, 0x00}, true, "256"},
    121 	{[]byte{}, false, ""},
    122 	{[]byte{0x00, 0x7f}, false, ""},
    123 	{[]byte{0xff, 0xf0}, false, ""},
    124 }
    125 
    126 func TestParseBigInt(t *testing.T) {
    127 	for i, test := range bigIntTests {
    128 		ret, err := parseBigInt(test.in)
    129 		if (err == nil) != test.ok {
    130 			t.Errorf("#%d: Incorrect error result (did fail? %v, expected: %v)", i, err == nil, test.ok)
    131 		}
    132 		if test.ok {
    133 			if ret.String() != test.base10 {
    134 				t.Errorf("#%d: bad result from %x, got %s want %s", i, test.in, ret.String(), test.base10)
    135 			}
    136 			e, err := makeBigInt(ret)
    137 			if err != nil {
    138 				t.Errorf("%d: err=%q", i, err)
    139 				continue
    140 			}
    141 			result := make([]byte, e.Len())
    142 			e.Encode(result)
    143 			if !bytes.Equal(result, test.in) {
    144 				t.Errorf("#%d: got %x from marshaling %s, want %x", i, result, ret, test.in)
    145 			}
    146 		}
    147 	}
    148 }
    149 
    150 type bitStringTest struct {
    151 	in        []byte
    152 	ok        bool
    153 	out       []byte
    154 	bitLength int
    155 }
    156 
    157 var bitStringTestData = []bitStringTest{
    158 	{[]byte{}, false, []byte{}, 0},
    159 	{[]byte{0x00}, true, []byte{}, 0},
    160 	{[]byte{0x07, 0x00}, true, []byte{0x00}, 1},
    161 	{[]byte{0x07, 0x01}, false, []byte{}, 0},
    162 	{[]byte{0x07, 0x40}, false, []byte{}, 0},
    163 	{[]byte{0x08, 0x00}, false, []byte{}, 0},
    164 }
    165 
    166 func TestBitString(t *testing.T) {
    167 	for i, test := range bitStringTestData {
    168 		ret, err := parseBitString(test.in)
    169 		if (err == nil) != test.ok {
    170 			t.Errorf("#%d: Incorrect error result (did fail? %v, expected: %v)", i, err == nil, test.ok)
    171 		}
    172 		if err == nil {
    173 			if test.bitLength != ret.BitLength || !bytes.Equal(ret.Bytes, test.out) {
    174 				t.Errorf("#%d: Bad result: %v (expected %v %v)", i, ret, test.out, test.bitLength)
    175 			}
    176 		}
    177 	}
    178 }
    179 
    180 func TestBitStringAt(t *testing.T) {
    181 	bs := BitString{[]byte{0x82, 0x40}, 16}
    182 	if bs.At(0) != 1 {
    183 		t.Error("#1: Failed")
    184 	}
    185 	if bs.At(1) != 0 {
    186 		t.Error("#2: Failed")
    187 	}
    188 	if bs.At(6) != 1 {
    189 		t.Error("#3: Failed")
    190 	}
    191 	if bs.At(9) != 1 {
    192 		t.Error("#4: Failed")
    193 	}
    194 	if bs.At(-1) != 0 {
    195 		t.Error("#5: Failed")
    196 	}
    197 	if bs.At(17) != 0 {
    198 		t.Error("#6: Failed")
    199 	}
    200 }
    201 
    202 type bitStringRightAlignTest struct {
    203 	in    []byte
    204 	inlen int
    205 	out   []byte
    206 }
    207 
    208 var bitStringRightAlignTests = []bitStringRightAlignTest{
    209 	{[]byte{0x80}, 1, []byte{0x01}},
    210 	{[]byte{0x80, 0x80}, 9, []byte{0x01, 0x01}},
    211 	{[]byte{}, 0, []byte{}},
    212 	{[]byte{0xce}, 8, []byte{0xce}},
    213 	{[]byte{0xce, 0x47}, 16, []byte{0xce, 0x47}},
    214 	{[]byte{0x34, 0x50}, 12, []byte{0x03, 0x45}},
    215 }
    216 
    217 func TestBitStringRightAlign(t *testing.T) {
    218 	for i, test := range bitStringRightAlignTests {
    219 		bs := BitString{test.in, test.inlen}
    220 		out := bs.RightAlign()
    221 		if !bytes.Equal(out, test.out) {
    222 			t.Errorf("#%d got: %x want: %x", i, out, test.out)
    223 		}
    224 	}
    225 }
    226 
    227 type objectIdentifierTest struct {
    228 	in  []byte
    229 	ok  bool
    230 	out []int
    231 }
    232 
    233 var objectIdentifierTestData = []objectIdentifierTest{
    234 	{[]byte{}, false, []int{}},
    235 	{[]byte{85}, true, []int{2, 5}},
    236 	{[]byte{85, 0x02}, true, []int{2, 5, 2}},
    237 	{[]byte{85, 0x02, 0xc0, 0x00}, true, []int{2, 5, 2, 0x2000}},
    238 	{[]byte{0x81, 0x34, 0x03}, true, []int{2, 100, 3}},
    239 	{[]byte{85, 0x02, 0xc0, 0x80, 0x80, 0x80, 0x80}, false, []int{}},
    240 }
    241 
    242 func TestObjectIdentifier(t *testing.T) {
    243 	for i, test := range objectIdentifierTestData {
    244 		ret, err := parseObjectIdentifier(test.in)
    245 		if (err == nil) != test.ok {
    246 			t.Errorf("#%d: Incorrect error result (did fail? %v, expected: %v)", i, err == nil, test.ok)
    247 		}
    248 		if err == nil {
    249 			if !reflect.DeepEqual(test.out, ret) {
    250 				t.Errorf("#%d: Bad result: %v (expected %v)", i, ret, test.out)
    251 			}
    252 		}
    253 	}
    254 
    255 	if s := ObjectIdentifier([]int{1, 2, 3, 4}).String(); s != "1.2.3.4" {
    256 		t.Errorf("bad ObjectIdentifier.String(). Got %s, want 1.2.3.4", s)
    257 	}
    258 }
    259 
    260 type timeTest struct {
    261 	in  string
    262 	ok  bool
    263 	out time.Time
    264 }
    265 
    266 var utcTestData = []timeTest{
    267 	{"910506164540-0700", true, time.Date(1991, 05, 06, 16, 45, 40, 0, time.FixedZone("", -7*60*60))},
    268 	{"910506164540+0730", true, time.Date(1991, 05, 06, 16, 45, 40, 0, time.FixedZone("", 7*60*60+30*60))},
    269 	{"910506234540Z", true, time.Date(1991, 05, 06, 23, 45, 40, 0, time.UTC)},
    270 	{"9105062345Z", true, time.Date(1991, 05, 06, 23, 45, 0, 0, time.UTC)},
    271 	{"5105062345Z", true, time.Date(1951, 05, 06, 23, 45, 0, 0, time.UTC)},
    272 	{"a10506234540Z", false, time.Time{}},
    273 	{"91a506234540Z", false, time.Time{}},
    274 	{"9105a6234540Z", false, time.Time{}},
    275 	{"910506a34540Z", false, time.Time{}},
    276 	{"910506334a40Z", false, time.Time{}},
    277 	{"91050633444aZ", false, time.Time{}},
    278 	{"910506334461Z", false, time.Time{}},
    279 	{"910506334400Za", false, time.Time{}},
    280 	/* These are invalid times. However, the time package normalises times
    281 	 * and they were accepted in some versions. See #11134. */
    282 	{"000100000000Z", false, time.Time{}},
    283 	{"101302030405Z", false, time.Time{}},
    284 	{"100002030405Z", false, time.Time{}},
    285 	{"100100030405Z", false, time.Time{}},
    286 	{"100132030405Z", false, time.Time{}},
    287 	{"100231030405Z", false, time.Time{}},
    288 	{"100102240405Z", false, time.Time{}},
    289 	{"100102036005Z", false, time.Time{}},
    290 	{"100102030460Z", false, time.Time{}},
    291 	{"-100102030410Z", false, time.Time{}},
    292 	{"10-0102030410Z", false, time.Time{}},
    293 	{"10-0002030410Z", false, time.Time{}},
    294 	{"1001-02030410Z", false, time.Time{}},
    295 	{"100102-030410Z", false, time.Time{}},
    296 	{"10010203-0410Z", false, time.Time{}},
    297 	{"1001020304-10Z", false, time.Time{}},
    298 }
    299 
    300 func TestUTCTime(t *testing.T) {
    301 	for i, test := range utcTestData {
    302 		ret, err := parseUTCTime([]byte(test.in))
    303 		if err != nil {
    304 			if test.ok {
    305 				t.Errorf("#%d: parseUTCTime(%q) = error %v", i, test.in, err)
    306 			}
    307 			continue
    308 		}
    309 		if !test.ok {
    310 			t.Errorf("#%d: parseUTCTime(%q) succeeded, should have failed", i, test.in)
    311 			continue
    312 		}
    313 		const format = "Jan _2 15:04:05 -0700 2006" // ignore zone name, just offset
    314 		have := ret.Format(format)
    315 		want := test.out.Format(format)
    316 		if have != want {
    317 			t.Errorf("#%d: parseUTCTime(%q) = %s, want %s", i, test.in, have, want)
    318 		}
    319 	}
    320 }
    321 
    322 var generalizedTimeTestData = []timeTest{
    323 	{"20100102030405Z", true, time.Date(2010, 01, 02, 03, 04, 05, 0, time.UTC)},
    324 	{"20100102030405", false, time.Time{}},
    325 	{"20100102030405+0607", true, time.Date(2010, 01, 02, 03, 04, 05, 0, time.FixedZone("", 6*60*60+7*60))},
    326 	{"20100102030405-0607", true, time.Date(2010, 01, 02, 03, 04, 05, 0, time.FixedZone("", -6*60*60-7*60))},
    327 	/* These are invalid times. However, the time package normalises times
    328 	 * and they were accepted in some versions. See #11134. */
    329 	{"00000100000000Z", false, time.Time{}},
    330 	{"20101302030405Z", false, time.Time{}},
    331 	{"20100002030405Z", false, time.Time{}},
    332 	{"20100100030405Z", false, time.Time{}},
    333 	{"20100132030405Z", false, time.Time{}},
    334 	{"20100231030405Z", false, time.Time{}},
    335 	{"20100102240405Z", false, time.Time{}},
    336 	{"20100102036005Z", false, time.Time{}},
    337 	{"20100102030460Z", false, time.Time{}},
    338 	{"-20100102030410Z", false, time.Time{}},
    339 	{"2010-0102030410Z", false, time.Time{}},
    340 	{"2010-0002030410Z", false, time.Time{}},
    341 	{"201001-02030410Z", false, time.Time{}},
    342 	{"20100102-030410Z", false, time.Time{}},
    343 	{"2010010203-0410Z", false, time.Time{}},
    344 	{"201001020304-10Z", false, time.Time{}},
    345 }
    346 
    347 func TestGeneralizedTime(t *testing.T) {
    348 	for i, test := range generalizedTimeTestData {
    349 		ret, err := parseGeneralizedTime([]byte(test.in))
    350 		if (err == nil) != test.ok {
    351 			t.Errorf("#%d: Incorrect error result (did fail? %v, expected: %v)", i, err == nil, test.ok)
    352 		}
    353 		if err == nil {
    354 			if !reflect.DeepEqual(test.out, ret) {
    355 				t.Errorf("#%d: Bad result: %q  %v (expected %v)", i, test.in, ret, test.out)
    356 			}
    357 		}
    358 	}
    359 }
    360 
    361 type tagAndLengthTest struct {
    362 	in  []byte
    363 	ok  bool
    364 	out tagAndLength
    365 }
    366 
    367 var tagAndLengthData = []tagAndLengthTest{
    368 	{[]byte{0x80, 0x01}, true, tagAndLength{2, 0, 1, false}},
    369 	{[]byte{0xa0, 0x01}, true, tagAndLength{2, 0, 1, true}},
    370 	{[]byte{0x02, 0x00}, true, tagAndLength{0, 2, 0, false}},
    371 	{[]byte{0xfe, 0x00}, true, tagAndLength{3, 30, 0, true}},
    372 	{[]byte{0x1f, 0x1f, 0x00}, true, tagAndLength{0, 31, 0, false}},
    373 	{[]byte{0x1f, 0x81, 0x00, 0x00}, true, tagAndLength{0, 128, 0, false}},
    374 	{[]byte{0x1f, 0x81, 0x80, 0x01, 0x00}, true, tagAndLength{0, 0x4001, 0, false}},
    375 	{[]byte{0x00, 0x81, 0x80}, true, tagAndLength{0, 0, 128, false}},
    376 	{[]byte{0x00, 0x82, 0x01, 0x00}, true, tagAndLength{0, 0, 256, false}},
    377 	{[]byte{0x00, 0x83, 0x01, 0x00}, false, tagAndLength{}},
    378 	{[]byte{0x1f, 0x85}, false, tagAndLength{}},
    379 	{[]byte{0x30, 0x80}, false, tagAndLength{}},
    380 	// Superfluous zeros in the length should be an error.
    381 	{[]byte{0xa0, 0x82, 0x00, 0xff}, false, tagAndLength{}},
    382 	// Lengths up to the maximum size of an int should work.
    383 	{[]byte{0xa0, 0x84, 0x7f, 0xff, 0xff, 0xff}, true, tagAndLength{2, 0, 0x7fffffff, true}},
    384 	// Lengths that would overflow an int should be rejected.
    385 	{[]byte{0xa0, 0x84, 0x80, 0x00, 0x00, 0x00}, false, tagAndLength{}},
    386 	// Long length form may not be used for lengths that fit in short form.
    387 	{[]byte{0xa0, 0x81, 0x7f}, false, tagAndLength{}},
    388 	// Tag numbers which would overflow int32 are rejected. (The value below is 2^31.)
    389 	{[]byte{0x1f, 0x88, 0x80, 0x80, 0x80, 0x00, 0x00}, false, tagAndLength{}},
    390 	// Tag numbers that fit in an int32 are valid. (The value below is 2^31 - 1.)
    391 	{[]byte{0x1f, 0x87, 0xFF, 0xFF, 0xFF, 0x7F, 0x00}, true, tagAndLength{tag: math.MaxInt32}},
    392 	// Long tag number form may not be used for tags that fit in short form.
    393 	{[]byte{0x1f, 0x1e, 0x00}, false, tagAndLength{}},
    394 }
    395 
    396 func TestParseTagAndLength(t *testing.T) {
    397 	for i, test := range tagAndLengthData {
    398 		tagAndLength, _, err := parseTagAndLength(test.in, 0)
    399 		if (err == nil) != test.ok {
    400 			t.Errorf("#%d: Incorrect error result (did pass? %v, expected: %v)", i, err == nil, test.ok)
    401 		}
    402 		if err == nil && !reflect.DeepEqual(test.out, tagAndLength) {
    403 			t.Errorf("#%d: Bad result: %v (expected %v)", i, tagAndLength, test.out)
    404 		}
    405 	}
    406 }
    407 
    408 type parseFieldParametersTest struct {
    409 	in  string
    410 	out fieldParameters
    411 }
    412 
    413 func newInt(n int) *int { return &n }
    414 
    415 func newInt64(n int64) *int64 { return &n }
    416 
    417 func newString(s string) *string { return &s }
    418 
    419 func newBool(b bool) *bool { return &b }
    420 
    421 var parseFieldParametersTestData []parseFieldParametersTest = []parseFieldParametersTest{
    422 	{"", fieldParameters{}},
    423 	{"ia5", fieldParameters{stringType: TagIA5String}},
    424 	{"generalized", fieldParameters{timeType: TagGeneralizedTime}},
    425 	{"utc", fieldParameters{timeType: TagUTCTime}},
    426 	{"printable", fieldParameters{stringType: TagPrintableString}},
    427 	{"numeric", fieldParameters{stringType: TagNumericString}},
    428 	{"optional", fieldParameters{optional: true}},
    429 	{"explicit", fieldParameters{explicit: true, tag: new(int)}},
    430 	{"application", fieldParameters{application: true, tag: new(int)}},
    431 	{"optional,explicit", fieldParameters{optional: true, explicit: true, tag: new(int)}},
    432 	{"default:42", fieldParameters{defaultValue: newInt64(42)}},
    433 	{"tag:17", fieldParameters{tag: newInt(17)}},
    434 	{"optional,explicit,default:42,tag:17", fieldParameters{optional: true, explicit: true, defaultValue: newInt64(42), tag: newInt(17)}},
    435 	{"optional,explicit,default:42,tag:17,rubbish1", fieldParameters{true, true, false, newInt64(42), newInt(17), 0, 0, false, false}},
    436 	{"set", fieldParameters{set: true}},
    437 }
    438 
    439 func TestParseFieldParameters(t *testing.T) {
    440 	for i, test := range parseFieldParametersTestData {
    441 		f := parseFieldParameters(test.in)
    442 		if !reflect.DeepEqual(f, test.out) {
    443 			t.Errorf("#%d: Bad result: %v (expected %v)", i, f, test.out)
    444 		}
    445 	}
    446 }
    447 
    448 type TestObjectIdentifierStruct struct {
    449 	OID ObjectIdentifier
    450 }
    451 
    452 type TestContextSpecificTags struct {
    453 	A int `asn1:"tag:1"`
    454 }
    455 
    456 type TestContextSpecificTags2 struct {
    457 	A int `asn1:"explicit,tag:1"`
    458 	B int
    459 }
    460 
    461 type TestContextSpecificTags3 struct {
    462 	S string `asn1:"tag:1,utf8"`
    463 }
    464 
    465 type TestElementsAfterString struct {
    466 	S    string
    467 	A, B int
    468 }
    469 
    470 type TestBigInt struct {
    471 	X *big.Int
    472 }
    473 
    474 type TestSet struct {
    475 	Ints []int `asn1:"set"`
    476 }
    477 
    478 var unmarshalTestData = []struct {
    479 	in  []byte
    480 	out interface{}
    481 }{
    482 	{[]byte{0x02, 0x01, 0x42}, newInt(0x42)},
    483 	{[]byte{0x05, 0x00}, &RawValue{0, 5, false, []byte{}, []byte{0x05, 0x00}}},
    484 	{[]byte{0x30, 0x08, 0x06, 0x06, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d}, &TestObjectIdentifierStruct{[]int{1, 2, 840, 113549}}},
    485 	{[]byte{0x03, 0x04, 0x06, 0x6e, 0x5d, 0xc0}, &BitString{[]byte{110, 93, 192}, 18}},
    486 	{[]byte{0x30, 0x09, 0x02, 0x01, 0x01, 0x02, 0x01, 0x02, 0x02, 0x01, 0x03}, &[]int{1, 2, 3}},
    487 	{[]byte{0x02, 0x01, 0x10}, newInt(16)},
    488 	{[]byte{0x13, 0x04, 't', 'e', 's', 't'}, newString("test")},
    489 	{[]byte{0x16, 0x04, 't', 'e', 's', 't'}, newString("test")},
    490 	// Ampersand is allowed in PrintableString due to mistakes by major CAs.
    491 	{[]byte{0x13, 0x05, 't', 'e', 's', 't', '&'}, newString("test&")},
    492 	{[]byte{0x16, 0x04, 't', 'e', 's', 't'}, &RawValue{0, 22, false, []byte("test"), []byte("\x16\x04test")}},
    493 	{[]byte{0x04, 0x04, 1, 2, 3, 4}, &RawValue{0, 4, false, []byte{1, 2, 3, 4}, []byte{4, 4, 1, 2, 3, 4}}},
    494 	{[]byte{0x30, 0x03, 0x81, 0x01, 0x01}, &TestContextSpecificTags{1}},
    495 	{[]byte{0x30, 0x08, 0xa1, 0x03, 0x02, 0x01, 0x01, 0x02, 0x01, 0x02}, &TestContextSpecificTags2{1, 2}},
    496 	{[]byte{0x30, 0x03, 0x81, 0x01, '@'}, &TestContextSpecificTags3{"@"}},
    497 	{[]byte{0x01, 0x01, 0x00}, newBool(false)},
    498 	{[]byte{0x01, 0x01, 0xff}, newBool(true)},
    499 	{[]byte{0x30, 0x0b, 0x13, 0x03, 0x66, 0x6f, 0x6f, 0x02, 0x01, 0x22, 0x02, 0x01, 0x33}, &TestElementsAfterString{"foo", 0x22, 0x33}},
    500 	{[]byte{0x30, 0x05, 0x02, 0x03, 0x12, 0x34, 0x56}, &TestBigInt{big.NewInt(0x123456)}},
    501 	{[]byte{0x30, 0x0b, 0x31, 0x09, 0x02, 0x01, 0x01, 0x02, 0x01, 0x02, 0x02, 0x01, 0x03}, &TestSet{Ints: []int{1, 2, 3}}},
    502 	{[]byte{0x12, 0x0b, '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', ' '}, newString("0123456789 ")},
    503 }
    504 
    505 func TestUnmarshal(t *testing.T) {
    506 	for i, test := range unmarshalTestData {
    507 		pv := reflect.New(reflect.TypeOf(test.out).Elem())
    508 		val := pv.Interface()
    509 		_, err := Unmarshal(test.in, val)
    510 		if err != nil {
    511 			t.Errorf("Unmarshal failed at index %d %v", i, err)
    512 		}
    513 		if !reflect.DeepEqual(val, test.out) {
    514 			t.Errorf("#%d:\nhave %#v\nwant %#v", i, val, test.out)
    515 		}
    516 	}
    517 }
    518 
    519 type Certificate struct {
    520 	TBSCertificate     TBSCertificate
    521 	SignatureAlgorithm AlgorithmIdentifier
    522 	SignatureValue     BitString
    523 }
    524 
    525 type TBSCertificate struct {
    526 	Version            int `asn1:"optional,explicit,default:0,tag:0"`
    527 	SerialNumber       RawValue
    528 	SignatureAlgorithm AlgorithmIdentifier
    529 	Issuer             RDNSequence
    530 	Validity           Validity
    531 	Subject            RDNSequence
    532 	PublicKey          PublicKeyInfo
    533 }
    534 
    535 type AlgorithmIdentifier struct {
    536 	Algorithm ObjectIdentifier
    537 }
    538 
    539 type RDNSequence []RelativeDistinguishedNameSET
    540 
    541 type RelativeDistinguishedNameSET []AttributeTypeAndValue
    542 
    543 type AttributeTypeAndValue struct {
    544 	Type  ObjectIdentifier
    545 	Value interface{}
    546 }
    547 
    548 type Validity struct {
    549 	NotBefore, NotAfter time.Time
    550 }
    551 
    552 type PublicKeyInfo struct {
    553 	Algorithm AlgorithmIdentifier
    554 	PublicKey BitString
    555 }
    556 
    557 func TestCertificate(t *testing.T) {
    558 	// This is a minimal, self-signed certificate that should parse correctly.
    559 	var cert Certificate
    560 	if _, err := Unmarshal(derEncodedSelfSignedCertBytes, &cert); err != nil {
    561 		t.Errorf("Unmarshal failed: %v", err)
    562 	}
    563 	if !reflect.DeepEqual(cert, derEncodedSelfSignedCert) {
    564 		t.Errorf("Bad result:\ngot: %+v\nwant: %+v", cert, derEncodedSelfSignedCert)
    565 	}
    566 }
    567 
    568 func TestCertificateWithNUL(t *testing.T) {
    569 	// This is the paypal NUL-hack certificate. It should fail to parse because
    570 	// NUL isn't a permitted character in a PrintableString.
    571 
    572 	var cert Certificate
    573 	if _, err := Unmarshal(derEncodedPaypalNULCertBytes, &cert); err == nil {
    574 		t.Error("Unmarshal succeeded, should not have")
    575 	}
    576 }
    577 
    578 type rawStructTest struct {
    579 	Raw RawContent
    580 	A   int
    581 }
    582 
    583 func TestRawStructs(t *testing.T) {
    584 	var s rawStructTest
    585 	input := []byte{0x30, 0x03, 0x02, 0x01, 0x50}
    586 
    587 	rest, err := Unmarshal(input, &s)
    588 	if len(rest) != 0 {
    589 		t.Errorf("incomplete parse: %x", rest)
    590 		return
    591 	}
    592 	if err != nil {
    593 		t.Error(err)
    594 		return
    595 	}
    596 	if s.A != 0x50 {
    597 		t.Errorf("bad value for A: got %d want %d", s.A, 0x50)
    598 	}
    599 	if !bytes.Equal([]byte(s.Raw), input) {
    600 		t.Errorf("bad value for Raw: got %x want %x", s.Raw, input)
    601 	}
    602 }
    603 
    604 type oiEqualTest struct {
    605 	first  ObjectIdentifier
    606 	second ObjectIdentifier
    607 	same   bool
    608 }
    609 
    610 var oiEqualTests = []oiEqualTest{
    611 	{
    612 		ObjectIdentifier{1, 2, 3},
    613 		ObjectIdentifier{1, 2, 3},
    614 		true,
    615 	},
    616 	{
    617 		ObjectIdentifier{1},
    618 		ObjectIdentifier{1, 2, 3},
    619 		false,
    620 	},
    621 	{
    622 		ObjectIdentifier{1, 2, 3},
    623 		ObjectIdentifier{10, 11, 12},
    624 		false,
    625 	},
    626 }
    627 
    628 func TestObjectIdentifierEqual(t *testing.T) {
    629 	for _, o := range oiEqualTests {
    630 		if s := o.first.Equal(o.second); s != o.same {
    631 			t.Errorf("ObjectIdentifier.Equal: got: %t want: %t", s, o.same)
    632 		}
    633 	}
    634 }
    635 
    636 var derEncodedSelfSignedCert = Certificate{
    637 	TBSCertificate: TBSCertificate{
    638 		Version:            0,
    639 		SerialNumber:       RawValue{Class: 0, Tag: 2, IsCompound: false, Bytes: []uint8{0x0, 0x8c, 0xc3, 0x37, 0x92, 0x10, 0xec, 0x2c, 0x98}, FullBytes: []byte{2, 9, 0x0, 0x8c, 0xc3, 0x37, 0x92, 0x10, 0xec, 0x2c, 0x98}},
    640 		SignatureAlgorithm: AlgorithmIdentifier{Algorithm: ObjectIdentifier{1, 2, 840, 113549, 1, 1, 5}},
    641 		Issuer: RDNSequence{
    642 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{2, 5, 4, 6}, Value: "XX"}},
    643 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{2, 5, 4, 8}, Value: "Some-State"}},
    644 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{2, 5, 4, 7}, Value: "City"}},
    645 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{2, 5, 4, 10}, Value: "Internet Widgits Pty Ltd"}},
    646 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{2, 5, 4, 3}, Value: "false.example.com"}},
    647 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{1, 2, 840, 113549, 1, 9, 1}, Value: "false (a] example.com"}},
    648 		},
    649 		Validity: Validity{
    650 			NotBefore: time.Date(2009, 10, 8, 00, 25, 53, 0, time.UTC),
    651 			NotAfter:  time.Date(2010, 10, 8, 00, 25, 53, 0, time.UTC),
    652 		},
    653 		Subject: RDNSequence{
    654 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{2, 5, 4, 6}, Value: "XX"}},
    655 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{2, 5, 4, 8}, Value: "Some-State"}},
    656 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{2, 5, 4, 7}, Value: "City"}},
    657 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{2, 5, 4, 10}, Value: "Internet Widgits Pty Ltd"}},
    658 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{2, 5, 4, 3}, Value: "false.example.com"}},
    659 			RelativeDistinguishedNameSET{AttributeTypeAndValue{Type: ObjectIdentifier{1, 2, 840, 113549, 1, 9, 1}, Value: "false (a] example.com"}},
    660 		},
    661 		PublicKey: PublicKeyInfo{
    662 			Algorithm: AlgorithmIdentifier{Algorithm: ObjectIdentifier{1, 2, 840, 113549, 1, 1, 1}},
    663 			PublicKey: BitString{
    664 				Bytes: []uint8{
    665 					0x30, 0x48, 0x2, 0x41, 0x0, 0xcd, 0xb7,
    666 					0x63, 0x9c, 0x32, 0x78, 0xf0, 0x6, 0xaa, 0x27, 0x7f, 0x6e, 0xaf, 0x42,
    667 					0x90, 0x2b, 0x59, 0x2d, 0x8c, 0xbc, 0xbe, 0x38, 0xa1, 0xc9, 0x2b, 0xa4,
    668 					0x69, 0x5a, 0x33, 0x1b, 0x1d, 0xea, 0xde, 0xad, 0xd8, 0xe9, 0xa5, 0xc2,
    669 					0x7e, 0x8c, 0x4c, 0x2f, 0xd0, 0xa8, 0x88, 0x96, 0x57, 0x72, 0x2a, 0x4f,
    670 					0x2a, 0xf7, 0x58, 0x9c, 0xf2, 0xc7, 0x70, 0x45, 0xdc, 0x8f, 0xde, 0xec,
    671 					0x35, 0x7d, 0x2, 0x3, 0x1, 0x0, 0x1,
    672 				},
    673 				BitLength: 592,
    674 			},
    675 		},
    676 	},
    677 	SignatureAlgorithm: AlgorithmIdentifier{Algorithm: ObjectIdentifier{1, 2, 840, 113549, 1, 1, 5}},
    678 	SignatureValue: BitString{
    679 		Bytes: []uint8{
    680 			0xa6, 0x7b, 0x6, 0xec, 0x5e, 0xce,
    681 			0x92, 0x77, 0x2c, 0xa4, 0x13, 0xcb, 0xa3, 0xca, 0x12, 0x56, 0x8f, 0xdc, 0x6c,
    682 			0x7b, 0x45, 0x11, 0xcd, 0x40, 0xa7, 0xf6, 0x59, 0x98, 0x4, 0x2, 0xdf, 0x2b,
    683 			0x99, 0x8b, 0xb9, 0xa4, 0xa8, 0xcb, 0xeb, 0x34, 0xc0, 0xf0, 0xa7, 0x8c, 0xf8,
    684 			0xd9, 0x1e, 0xde, 0x14, 0xa5, 0xed, 0x76, 0xbf, 0x11, 0x6f, 0xe3, 0x60, 0xaa,
    685 			0xfa, 0x88, 0x21, 0x49, 0x4, 0x35,
    686 		},
    687 		BitLength: 512,
    688 	},
    689 }
    690 
    691 var derEncodedSelfSignedCertBytes = []byte{
    692 	0x30, 0x82, 0x02, 0x18, 0x30,
    693 	0x82, 0x01, 0xc2, 0x02, 0x09, 0x00, 0x8c, 0xc3, 0x37, 0x92, 0x10, 0xec, 0x2c,
    694 	0x98, 0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01,
    695 	0x05, 0x05, 0x00, 0x30, 0x81, 0x92, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55,
    696 	0x04, 0x06, 0x13, 0x02, 0x58, 0x58, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55,
    697 	0x04, 0x08, 0x13, 0x0a, 0x53, 0x6f, 0x6d, 0x65, 0x2d, 0x53, 0x74, 0x61, 0x74,
    698 	0x65, 0x31, 0x0d, 0x30, 0x0b, 0x06, 0x03, 0x55, 0x04, 0x07, 0x13, 0x04, 0x43,
    699 	0x69, 0x74, 0x79, 0x31, 0x21, 0x30, 0x1f, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x13,
    700 	0x18, 0x49, 0x6e, 0x74, 0x65, 0x72, 0x6e, 0x65, 0x74, 0x20, 0x57, 0x69, 0x64,
    701 	0x67, 0x69, 0x74, 0x73, 0x20, 0x50, 0x74, 0x79, 0x20, 0x4c, 0x74, 0x64, 0x31,
    702 	0x1a, 0x30, 0x18, 0x06, 0x03, 0x55, 0x04, 0x03, 0x13, 0x11, 0x66, 0x61, 0x6c,
    703 	0x73, 0x65, 0x2e, 0x65, 0x78, 0x61, 0x6d, 0x70, 0x6c, 0x65, 0x2e, 0x63, 0x6f,
    704 	0x6d, 0x31, 0x20, 0x30, 0x1e, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d,
    705 	0x01, 0x09, 0x01, 0x16, 0x11, 0x66, 0x61, 0x6c, 0x73, 0x65, 0x40, 0x65, 0x78,
    706 	0x61, 0x6d, 0x70, 0x6c, 0x65, 0x2e, 0x63, 0x6f, 0x6d, 0x30, 0x1e, 0x17, 0x0d,
    707 	0x30, 0x39, 0x31, 0x30, 0x30, 0x38, 0x30, 0x30, 0x32, 0x35, 0x35, 0x33, 0x5a,
    708 	0x17, 0x0d, 0x31, 0x30, 0x31, 0x30, 0x30, 0x38, 0x30, 0x30, 0x32, 0x35, 0x35,
    709 	0x33, 0x5a, 0x30, 0x81, 0x92, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04,
    710 	0x06, 0x13, 0x02, 0x58, 0x58, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04,
    711 	0x08, 0x13, 0x0a, 0x53, 0x6f, 0x6d, 0x65, 0x2d, 0x53, 0x74, 0x61, 0x74, 0x65,
    712 	0x31, 0x0d, 0x30, 0x0b, 0x06, 0x03, 0x55, 0x04, 0x07, 0x13, 0x04, 0x43, 0x69,
    713 	0x74, 0x79, 0x31, 0x21, 0x30, 0x1f, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x13, 0x18,
    714 	0x49, 0x6e, 0x74, 0x65, 0x72, 0x6e, 0x65, 0x74, 0x20, 0x57, 0x69, 0x64, 0x67,
    715 	0x69, 0x74, 0x73, 0x20, 0x50, 0x74, 0x79, 0x20, 0x4c, 0x74, 0x64, 0x31, 0x1a,
    716 	0x30, 0x18, 0x06, 0x03, 0x55, 0x04, 0x03, 0x13, 0x11, 0x66, 0x61, 0x6c, 0x73,
    717 	0x65, 0x2e, 0x65, 0x78, 0x61, 0x6d, 0x70, 0x6c, 0x65, 0x2e, 0x63, 0x6f, 0x6d,
    718 	0x31, 0x20, 0x30, 0x1e, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01,
    719 	0x09, 0x01, 0x16, 0x11, 0x66, 0x61, 0x6c, 0x73, 0x65, 0x40, 0x65, 0x78, 0x61,
    720 	0x6d, 0x70, 0x6c, 0x65, 0x2e, 0x63, 0x6f, 0x6d, 0x30, 0x5c, 0x30, 0x0d, 0x06,
    721 	0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00, 0x03,
    722 	0x4b, 0x00, 0x30, 0x48, 0x02, 0x41, 0x00, 0xcd, 0xb7, 0x63, 0x9c, 0x32, 0x78,
    723 	0xf0, 0x06, 0xaa, 0x27, 0x7f, 0x6e, 0xaf, 0x42, 0x90, 0x2b, 0x59, 0x2d, 0x8c,
    724 	0xbc, 0xbe, 0x38, 0xa1, 0xc9, 0x2b, 0xa4, 0x69, 0x5a, 0x33, 0x1b, 0x1d, 0xea,
    725 	0xde, 0xad, 0xd8, 0xe9, 0xa5, 0xc2, 0x7e, 0x8c, 0x4c, 0x2f, 0xd0, 0xa8, 0x88,
    726 	0x96, 0x57, 0x72, 0x2a, 0x4f, 0x2a, 0xf7, 0x58, 0x9c, 0xf2, 0xc7, 0x70, 0x45,
    727 	0xdc, 0x8f, 0xde, 0xec, 0x35, 0x7d, 0x02, 0x03, 0x01, 0x00, 0x01, 0x30, 0x0d,
    728 	0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x05, 0x05, 0x00,
    729 	0x03, 0x41, 0x00, 0xa6, 0x7b, 0x06, 0xec, 0x5e, 0xce, 0x92, 0x77, 0x2c, 0xa4,
    730 	0x13, 0xcb, 0xa3, 0xca, 0x12, 0x56, 0x8f, 0xdc, 0x6c, 0x7b, 0x45, 0x11, 0xcd,
    731 	0x40, 0xa7, 0xf6, 0x59, 0x98, 0x04, 0x02, 0xdf, 0x2b, 0x99, 0x8b, 0xb9, 0xa4,
    732 	0xa8, 0xcb, 0xeb, 0x34, 0xc0, 0xf0, 0xa7, 0x8c, 0xf8, 0xd9, 0x1e, 0xde, 0x14,
    733 	0xa5, 0xed, 0x76, 0xbf, 0x11, 0x6f, 0xe3, 0x60, 0xaa, 0xfa, 0x88, 0x21, 0x49,
    734 	0x04, 0x35,
    735 }
    736 
    737 var derEncodedPaypalNULCertBytes = []byte{
    738 	0x30, 0x82, 0x06, 0x44, 0x30,
    739 	0x82, 0x05, 0xad, 0xa0, 0x03, 0x02, 0x01, 0x02, 0x02, 0x03, 0x00, 0xf0, 0x9b,
    740 	0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x05,
    741 	0x05, 0x00, 0x30, 0x82, 0x01, 0x12, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55,
    742 	0x04, 0x06, 0x13, 0x02, 0x45, 0x53, 0x31, 0x12, 0x30, 0x10, 0x06, 0x03, 0x55,
    743 	0x04, 0x08, 0x13, 0x09, 0x42, 0x61, 0x72, 0x63, 0x65, 0x6c, 0x6f, 0x6e, 0x61,
    744 	0x31, 0x12, 0x30, 0x10, 0x06, 0x03, 0x55, 0x04, 0x07, 0x13, 0x09, 0x42, 0x61,
    745 	0x72, 0x63, 0x65, 0x6c, 0x6f, 0x6e, 0x61, 0x31, 0x29, 0x30, 0x27, 0x06, 0x03,
    746 	0x55, 0x04, 0x0a, 0x13, 0x20, 0x49, 0x50, 0x53, 0x20, 0x43, 0x65, 0x72, 0x74,
    747 	0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x41, 0x75, 0x74,
    748 	0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x20, 0x73, 0x2e, 0x6c, 0x2e, 0x31, 0x2e,
    749 	0x30, 0x2c, 0x06, 0x03, 0x55, 0x04, 0x0a, 0x14, 0x25, 0x67, 0x65, 0x6e, 0x65,
    750 	0x72, 0x61, 0x6c, 0x40, 0x69, 0x70, 0x73, 0x63, 0x61, 0x2e, 0x63, 0x6f, 0x6d,
    751 	0x20, 0x43, 0x2e, 0x49, 0x2e, 0x46, 0x2e, 0x20, 0x20, 0x42, 0x2d, 0x42, 0x36,
    752 	0x32, 0x32, 0x31, 0x30, 0x36, 0x39, 0x35, 0x31, 0x2e, 0x30, 0x2c, 0x06, 0x03,
    753 	0x55, 0x04, 0x0b, 0x13, 0x25, 0x69, 0x70, 0x73, 0x43, 0x41, 0x20, 0x43, 0x4c,
    754 	0x41, 0x53, 0x45, 0x41, 0x31, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69,
    755 	0x63, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72,
    756 	0x69, 0x74, 0x79, 0x31, 0x2e, 0x30, 0x2c, 0x06, 0x03, 0x55, 0x04, 0x03, 0x13,
    757 	0x25, 0x69, 0x70, 0x73, 0x43, 0x41, 0x20, 0x43, 0x4c, 0x41, 0x53, 0x45, 0x41,
    758 	0x31, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74, 0x69,
    759 	0x6f, 0x6e, 0x20, 0x41, 0x75, 0x74, 0x68, 0x6f, 0x72, 0x69, 0x74, 0x79, 0x31,
    760 	0x20, 0x30, 0x1e, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09,
    761 	0x01, 0x16, 0x11, 0x67, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x6c, 0x40, 0x69, 0x70,
    762 	0x73, 0x63, 0x61, 0x2e, 0x63, 0x6f, 0x6d, 0x30, 0x1e, 0x17, 0x0d, 0x30, 0x39,
    763 	0x30, 0x32, 0x32, 0x34, 0x32, 0x33, 0x30, 0x34, 0x31, 0x37, 0x5a, 0x17, 0x0d,
    764 	0x31, 0x31, 0x30, 0x32, 0x32, 0x34, 0x32, 0x33, 0x30, 0x34, 0x31, 0x37, 0x5a,
    765 	0x30, 0x81, 0x94, 0x31, 0x0b, 0x30, 0x09, 0x06, 0x03, 0x55, 0x04, 0x06, 0x13,
    766 	0x02, 0x55, 0x53, 0x31, 0x13, 0x30, 0x11, 0x06, 0x03, 0x55, 0x04, 0x08, 0x13,
    767 	0x0a, 0x43, 0x61, 0x6c, 0x69, 0x66, 0x6f, 0x72, 0x6e, 0x69, 0x61, 0x31, 0x16,
    768 	0x30, 0x14, 0x06, 0x03, 0x55, 0x04, 0x07, 0x13, 0x0d, 0x53, 0x61, 0x6e, 0x20,
    769 	0x46, 0x72, 0x61, 0x6e, 0x63, 0x69, 0x73, 0x63, 0x6f, 0x31, 0x11, 0x30, 0x0f,
    770 	0x06, 0x03, 0x55, 0x04, 0x0a, 0x13, 0x08, 0x53, 0x65, 0x63, 0x75, 0x72, 0x69,
    771 	0x74, 0x79, 0x31, 0x14, 0x30, 0x12, 0x06, 0x03, 0x55, 0x04, 0x0b, 0x13, 0x0b,
    772 	0x53, 0x65, 0x63, 0x75, 0x72, 0x65, 0x20, 0x55, 0x6e, 0x69, 0x74, 0x31, 0x2f,
    773 	0x30, 0x2d, 0x06, 0x03, 0x55, 0x04, 0x03, 0x13, 0x26, 0x77, 0x77, 0x77, 0x2e,
    774 	0x70, 0x61, 0x79, 0x70, 0x61, 0x6c, 0x2e, 0x63, 0x6f, 0x6d, 0x00, 0x73, 0x73,
    775 	0x6c, 0x2e, 0x73, 0x65, 0x63, 0x75, 0x72, 0x65, 0x63, 0x6f, 0x6e, 0x6e, 0x65,
    776 	0x63, 0x74, 0x69, 0x6f, 0x6e, 0x2e, 0x63, 0x63, 0x30, 0x81, 0x9f, 0x30, 0x0d,
    777 	0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01, 0x05, 0x00,
    778 	0x03, 0x81, 0x8d, 0x00, 0x30, 0x81, 0x89, 0x02, 0x81, 0x81, 0x00, 0xd2, 0x69,
    779 	0xfa, 0x6f, 0x3a, 0x00, 0xb4, 0x21, 0x1b, 0xc8, 0xb1, 0x02, 0xd7, 0x3f, 0x19,
    780 	0xb2, 0xc4, 0x6d, 0xb4, 0x54, 0xf8, 0x8b, 0x8a, 0xcc, 0xdb, 0x72, 0xc2, 0x9e,
    781 	0x3c, 0x60, 0xb9, 0xc6, 0x91, 0x3d, 0x82, 0xb7, 0x7d, 0x99, 0xff, 0xd1, 0x29,
    782 	0x84, 0xc1, 0x73, 0x53, 0x9c, 0x82, 0xdd, 0xfc, 0x24, 0x8c, 0x77, 0xd5, 0x41,
    783 	0xf3, 0xe8, 0x1e, 0x42, 0xa1, 0xad, 0x2d, 0x9e, 0xff, 0x5b, 0x10, 0x26, 0xce,
    784 	0x9d, 0x57, 0x17, 0x73, 0x16, 0x23, 0x38, 0xc8, 0xd6, 0xf1, 0xba, 0xa3, 0x96,
    785 	0x5b, 0x16, 0x67, 0x4a, 0x4f, 0x73, 0x97, 0x3a, 0x4d, 0x14, 0xa4, 0xf4, 0xe2,
    786 	0x3f, 0x8b, 0x05, 0x83, 0x42, 0xd1, 0xd0, 0xdc, 0x2f, 0x7a, 0xe5, 0xb6, 0x10,
    787 	0xb2, 0x11, 0xc0, 0xdc, 0x21, 0x2a, 0x90, 0xff, 0xae, 0x97, 0x71, 0x5a, 0x49,
    788 	0x81, 0xac, 0x40, 0xf3, 0x3b, 0xb8, 0x59, 0xb2, 0x4f, 0x02, 0x03, 0x01, 0x00,
    789 	0x01, 0xa3, 0x82, 0x03, 0x21, 0x30, 0x82, 0x03, 0x1d, 0x30, 0x09, 0x06, 0x03,
    790 	0x55, 0x1d, 0x13, 0x04, 0x02, 0x30, 0x00, 0x30, 0x11, 0x06, 0x09, 0x60, 0x86,
    791 	0x48, 0x01, 0x86, 0xf8, 0x42, 0x01, 0x01, 0x04, 0x04, 0x03, 0x02, 0x06, 0x40,
    792 	0x30, 0x0b, 0x06, 0x03, 0x55, 0x1d, 0x0f, 0x04, 0x04, 0x03, 0x02, 0x03, 0xf8,
    793 	0x30, 0x13, 0x06, 0x03, 0x55, 0x1d, 0x25, 0x04, 0x0c, 0x30, 0x0a, 0x06, 0x08,
    794 	0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x03, 0x01, 0x30, 0x1d, 0x06, 0x03, 0x55,
    795 	0x1d, 0x0e, 0x04, 0x16, 0x04, 0x14, 0x61, 0x8f, 0x61, 0x34, 0x43, 0x55, 0x14,
    796 	0x7f, 0x27, 0x09, 0xce, 0x4c, 0x8b, 0xea, 0x9b, 0x7b, 0x19, 0x25, 0xbc, 0x6e,
    797 	0x30, 0x1f, 0x06, 0x03, 0x55, 0x1d, 0x23, 0x04, 0x18, 0x30, 0x16, 0x80, 0x14,
    798 	0x0e, 0x07, 0x60, 0xd4, 0x39, 0xc9, 0x1b, 0x5b, 0x5d, 0x90, 0x7b, 0x23, 0xc8,
    799 	0xd2, 0x34, 0x9d, 0x4a, 0x9a, 0x46, 0x39, 0x30, 0x09, 0x06, 0x03, 0x55, 0x1d,
    800 	0x11, 0x04, 0x02, 0x30, 0x00, 0x30, 0x1c, 0x06, 0x03, 0x55, 0x1d, 0x12, 0x04,
    801 	0x15, 0x30, 0x13, 0x81, 0x11, 0x67, 0x65, 0x6e, 0x65, 0x72, 0x61, 0x6c, 0x40,
    802 	0x69, 0x70, 0x73, 0x63, 0x61, 0x2e, 0x63, 0x6f, 0x6d, 0x30, 0x72, 0x06, 0x09,
    803 	0x60, 0x86, 0x48, 0x01, 0x86, 0xf8, 0x42, 0x01, 0x0d, 0x04, 0x65, 0x16, 0x63,
    804 	0x4f, 0x72, 0x67, 0x61, 0x6e, 0x69, 0x7a, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x20,
    805 	0x49, 0x6e, 0x66, 0x6f, 0x72, 0x6d, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x20, 0x4e,
    806 	0x4f, 0x54, 0x20, 0x56, 0x41, 0x4c, 0x49, 0x44, 0x41, 0x54, 0x45, 0x44, 0x2e,
    807 	0x20, 0x43, 0x4c, 0x41, 0x53, 0x45, 0x41, 0x31, 0x20, 0x53, 0x65, 0x72, 0x76,
    808 	0x65, 0x72, 0x20, 0x43, 0x65, 0x72, 0x74, 0x69, 0x66, 0x69, 0x63, 0x61, 0x74,
    809 	0x65, 0x20, 0x69, 0x73, 0x73, 0x75, 0x65, 0x64, 0x20, 0x62, 0x79, 0x20, 0x68,
    810 	0x74, 0x74, 0x70, 0x73, 0x3a, 0x2f, 0x2f, 0x77, 0x77, 0x77, 0x2e, 0x69, 0x70,
    811 	0x73, 0x63, 0x61, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x30, 0x2f, 0x06, 0x09, 0x60,
    812 	0x86, 0x48, 0x01, 0x86, 0xf8, 0x42, 0x01, 0x02, 0x04, 0x22, 0x16, 0x20, 0x68,
    813 	0x74, 0x74, 0x70, 0x73, 0x3a, 0x2f, 0x2f, 0x77, 0x77, 0x77, 0x2e, 0x69, 0x70,
    814 	0x73, 0x63, 0x61, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x69, 0x70, 0x73, 0x63, 0x61,
    815 	0x32, 0x30, 0x30, 0x32, 0x2f, 0x30, 0x43, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01,
    816 	0x86, 0xf8, 0x42, 0x01, 0x04, 0x04, 0x36, 0x16, 0x34, 0x68, 0x74, 0x74, 0x70,
    817 	0x73, 0x3a, 0x2f, 0x2f, 0x77, 0x77, 0x77, 0x2e, 0x69, 0x70, 0x73, 0x63, 0x61,
    818 	0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x69, 0x70, 0x73, 0x63, 0x61, 0x32, 0x30, 0x30,
    819 	0x32, 0x2f, 0x69, 0x70, 0x73, 0x63, 0x61, 0x32, 0x30, 0x30, 0x32, 0x43, 0x4c,
    820 	0x41, 0x53, 0x45, 0x41, 0x31, 0x2e, 0x63, 0x72, 0x6c, 0x30, 0x46, 0x06, 0x09,
    821 	0x60, 0x86, 0x48, 0x01, 0x86, 0xf8, 0x42, 0x01, 0x03, 0x04, 0x39, 0x16, 0x37,
    822 	0x68, 0x74, 0x74, 0x70, 0x73, 0x3a, 0x2f, 0x2f, 0x77, 0x77, 0x77, 0x2e, 0x69,
    823 	0x70, 0x73, 0x63, 0x61, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x69, 0x70, 0x73, 0x63,
    824 	0x61, 0x32, 0x30, 0x30, 0x32, 0x2f, 0x72, 0x65, 0x76, 0x6f, 0x63, 0x61, 0x74,
    825 	0x69, 0x6f, 0x6e, 0x43, 0x4c, 0x41, 0x53, 0x45, 0x41, 0x31, 0x2e, 0x68, 0x74,
    826 	0x6d, 0x6c, 0x3f, 0x30, 0x43, 0x06, 0x09, 0x60, 0x86, 0x48, 0x01, 0x86, 0xf8,
    827 	0x42, 0x01, 0x07, 0x04, 0x36, 0x16, 0x34, 0x68, 0x74, 0x74, 0x70, 0x73, 0x3a,
    828 	0x2f, 0x2f, 0x77, 0x77, 0x77, 0x2e, 0x69, 0x70, 0x73, 0x63, 0x61, 0x2e, 0x63,
    829 	0x6f, 0x6d, 0x2f, 0x69, 0x70, 0x73, 0x63, 0x61, 0x32, 0x30, 0x30, 0x32, 0x2f,
    830 	0x72, 0x65, 0x6e, 0x65, 0x77, 0x61, 0x6c, 0x43, 0x4c, 0x41, 0x53, 0x45, 0x41,
    831 	0x31, 0x2e, 0x68, 0x74, 0x6d, 0x6c, 0x3f, 0x30, 0x41, 0x06, 0x09, 0x60, 0x86,
    832 	0x48, 0x01, 0x86, 0xf8, 0x42, 0x01, 0x08, 0x04, 0x34, 0x16, 0x32, 0x68, 0x74,
    833 	0x74, 0x70, 0x73, 0x3a, 0x2f, 0x2f, 0x77, 0x77, 0x77, 0x2e, 0x69, 0x70, 0x73,
    834 	0x63, 0x61, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x69, 0x70, 0x73, 0x63, 0x61, 0x32,
    835 	0x30, 0x30, 0x32, 0x2f, 0x70, 0x6f, 0x6c, 0x69, 0x63, 0x79, 0x43, 0x4c, 0x41,
    836 	0x53, 0x45, 0x41, 0x31, 0x2e, 0x68, 0x74, 0x6d, 0x6c, 0x30, 0x81, 0x83, 0x06,
    837 	0x03, 0x55, 0x1d, 0x1f, 0x04, 0x7c, 0x30, 0x7a, 0x30, 0x39, 0xa0, 0x37, 0xa0,
    838 	0x35, 0x86, 0x33, 0x68, 0x74, 0x74, 0x70, 0x3a, 0x2f, 0x2f, 0x77, 0x77, 0x77,
    839 	0x2e, 0x69, 0x70, 0x73, 0x63, 0x61, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x69, 0x70,
    840 	0x73, 0x63, 0x61, 0x32, 0x30, 0x30, 0x32, 0x2f, 0x69, 0x70, 0x73, 0x63, 0x61,
    841 	0x32, 0x30, 0x30, 0x32, 0x43, 0x4c, 0x41, 0x53, 0x45, 0x41, 0x31, 0x2e, 0x63,
    842 	0x72, 0x6c, 0x30, 0x3d, 0xa0, 0x3b, 0xa0, 0x39, 0x86, 0x37, 0x68, 0x74, 0x74,
    843 	0x70, 0x3a, 0x2f, 0x2f, 0x77, 0x77, 0x77, 0x62, 0x61, 0x63, 0x6b, 0x2e, 0x69,
    844 	0x70, 0x73, 0x63, 0x61, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x69, 0x70, 0x73, 0x63,
    845 	0x61, 0x32, 0x30, 0x30, 0x32, 0x2f, 0x69, 0x70, 0x73, 0x63, 0x61, 0x32, 0x30,
    846 	0x30, 0x32, 0x43, 0x4c, 0x41, 0x53, 0x45, 0x41, 0x31, 0x2e, 0x63, 0x72, 0x6c,
    847 	0x30, 0x32, 0x06, 0x08, 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x01, 0x01, 0x04,
    848 	0x26, 0x30, 0x24, 0x30, 0x22, 0x06, 0x08, 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07,
    849 	0x30, 0x01, 0x86, 0x16, 0x68, 0x74, 0x74, 0x70, 0x3a, 0x2f, 0x2f, 0x6f, 0x63,
    850 	0x73, 0x70, 0x2e, 0x69, 0x70, 0x73, 0x63, 0x61, 0x2e, 0x63, 0x6f, 0x6d, 0x2f,
    851 	0x30, 0x0d, 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x05,
    852 	0x05, 0x00, 0x03, 0x81, 0x81, 0x00, 0x68, 0xee, 0x79, 0x97, 0x97, 0xdd, 0x3b,
    853 	0xef, 0x16, 0x6a, 0x06, 0xf2, 0x14, 0x9a, 0x6e, 0xcd, 0x9e, 0x12, 0xf7, 0xaa,
    854 	0x83, 0x10, 0xbd, 0xd1, 0x7c, 0x98, 0xfa, 0xc7, 0xae, 0xd4, 0x0e, 0x2c, 0x9e,
    855 	0x38, 0x05, 0x9d, 0x52, 0x60, 0xa9, 0x99, 0x0a, 0x81, 0xb4, 0x98, 0x90, 0x1d,
    856 	0xae, 0xbb, 0x4a, 0xd7, 0xb9, 0xdc, 0x88, 0x9e, 0x37, 0x78, 0x41, 0x5b, 0xf7,
    857 	0x82, 0xa5, 0xf2, 0xba, 0x41, 0x25, 0x5a, 0x90, 0x1a, 0x1e, 0x45, 0x38, 0xa1,
    858 	0x52, 0x58, 0x75, 0x94, 0x26, 0x44, 0xfb, 0x20, 0x07, 0xba, 0x44, 0xcc, 0xe5,
    859 	0x4a, 0x2d, 0x72, 0x3f, 0x98, 0x47, 0xf6, 0x26, 0xdc, 0x05, 0x46, 0x05, 0x07,
    860 	0x63, 0x21, 0xab, 0x46, 0x9b, 0x9c, 0x78, 0xd5, 0x54, 0x5b, 0x3d, 0x0c, 0x1e,
    861 	0xc8, 0x64, 0x8c, 0xb5, 0x50, 0x23, 0x82, 0x6f, 0xdb, 0xb8, 0x22, 0x1c, 0x43,
    862 	0x96, 0x07, 0xa8, 0xbb,
    863 }
    864 
    865 var stringSliceTestData = [][]string{
    866 	{"foo", "bar"},
    867 	{"foo", "\\bar"},
    868 	{"foo", "\"bar\""},
    869 	{"foo", ""},
    870 }
    871 
    872 func TestStringSlice(t *testing.T) {
    873 	for _, test := range stringSliceTestData {
    874 		bs, err := Marshal(test)
    875 		if err != nil {
    876 			t.Error(err)
    877 		}
    878 
    879 		var res []string
    880 		_, err = Unmarshal(bs, &res)
    881 		if err != nil {
    882 			t.Error(err)
    883 		}
    884 
    885 		if fmt.Sprintf("%v", res) != fmt.Sprintf("%v", test) {
    886 			t.Errorf("incorrect marshal/unmarshal; %v != %v", res, test)
    887 		}
    888 	}
    889 }
    890 
    891 type explicitTaggedTimeTest struct {
    892 	Time time.Time `asn1:"explicit,tag:0"`
    893 }
    894 
    895 var explicitTaggedTimeTestData = []struct {
    896 	in  []byte
    897 	out explicitTaggedTimeTest
    898 }{
    899 	{[]byte{0x30, 0x11, 0xa0, 0xf, 0x17, 0xd, '9', '1', '0', '5', '0', '6', '1', '6', '4', '5', '4', '0', 'Z'},
    900 		explicitTaggedTimeTest{time.Date(1991, 05, 06, 16, 45, 40, 0, time.UTC)}},
    901 	{[]byte{0x30, 0x17, 0xa0, 0xf, 0x18, 0x13, '2', '0', '1', '0', '0', '1', '0', '2', '0', '3', '0', '4', '0', '5', '+', '0', '6', '0', '7'},
    902 		explicitTaggedTimeTest{time.Date(2010, 01, 02, 03, 04, 05, 0, time.FixedZone("", 6*60*60+7*60))}},
    903 }
    904 
    905 func TestExplicitTaggedTime(t *testing.T) {
    906 	// Test that a time.Time will match either tagUTCTime or
    907 	// tagGeneralizedTime.
    908 	for i, test := range explicitTaggedTimeTestData {
    909 		var got explicitTaggedTimeTest
    910 		_, err := Unmarshal(test.in, &got)
    911 		if err != nil {
    912 			t.Errorf("Unmarshal failed at index %d %v", i, err)
    913 		}
    914 		if !got.Time.Equal(test.out.Time) {
    915 			t.Errorf("#%d: got %v, want %v", i, got.Time, test.out.Time)
    916 		}
    917 	}
    918 }
    919 
    920 type implicitTaggedTimeTest struct {
    921 	Time time.Time `asn1:"tag:24"`
    922 }
    923 
    924 func TestImplicitTaggedTime(t *testing.T) {
    925 	// An implicitly tagged time value, that happens to have an implicit
    926 	// tag equal to a GENERALIZEDTIME, should still be parsed as a UTCTime.
    927 	// (There's no "timeType" in fieldParameters to determine what type of
    928 	// time should be expected when implicitly tagged.)
    929 	der := []byte{0x30, 0x0f, 0x80 | 24, 0xd, '9', '1', '0', '5', '0', '6', '1', '6', '4', '5', '4', '0', 'Z'}
    930 	var result implicitTaggedTimeTest
    931 	if _, err := Unmarshal(der, &result); err != nil {
    932 		t.Fatalf("Error while parsing: %s", err)
    933 	}
    934 	if expected := time.Date(1991, 05, 06, 16, 45, 40, 0, time.UTC); !result.Time.Equal(expected) {
    935 		t.Errorf("Wrong result. Got %v, want %v", result.Time, expected)
    936 	}
    937 }
    938 
    939 type truncatedExplicitTagTest struct {
    940 	Test int `asn1:"explicit,tag:0"`
    941 }
    942 
    943 func TestTruncatedExplicitTag(t *testing.T) {
    944 	// This crashed Unmarshal in the past. See #11154.
    945 	der := []byte{
    946 		0x30, // SEQUENCE
    947 		0x02, // two bytes long
    948 		0xa0, // context-specific, tag 0
    949 		0x30, // 48 bytes long
    950 	}
    951 
    952 	var result truncatedExplicitTagTest
    953 	if _, err := Unmarshal(der, &result); err == nil {
    954 		t.Error("Unmarshal returned without error")
    955 	}
    956 }
    957 
    958 type invalidUTF8Test struct {
    959 	Str string `asn1:"utf8"`
    960 }
    961 
    962 func TestUnmarshalInvalidUTF8(t *testing.T) {
    963 	data := []byte("0\x05\f\x03a\xc9c")
    964 	var result invalidUTF8Test
    965 	_, err := Unmarshal(data, &result)
    966 
    967 	const expectedSubstring = "UTF"
    968 	if err == nil {
    969 		t.Fatal("Successfully unmarshaled invalid UTF-8 data")
    970 	} else if !strings.Contains(err.Error(), expectedSubstring) {
    971 		t.Fatalf("Expected error to mention %q but error was %q", expectedSubstring, err.Error())
    972 	}
    973 }
    974 
    975 func TestMarshalNilValue(t *testing.T) {
    976 	nilValueTestData := []interface{}{
    977 		nil,
    978 		struct{ V interface{} }{},
    979 	}
    980 	for i, test := range nilValueTestData {
    981 		if _, err := Marshal(test); err == nil {
    982 			t.Fatalf("#%d: successfully marshaled nil value", i)
    983 		}
    984 	}
    985 }
    986 
    987 type unexported struct {
    988 	X int
    989 	y int
    990 }
    991 
    992 type exported struct {
    993 	X int
    994 	Y int
    995 }
    996 
    997 func TestUnexportedStructField(t *testing.T) {
    998 	want := StructuralError{"struct contains unexported fields"}
    999 
   1000 	_, err := Marshal(unexported{X: 5, y: 1})
   1001 	if err != want {
   1002 		t.Errorf("got %v, want %v", err, want)
   1003 	}
   1004 
   1005 	bs, err := Marshal(exported{X: 5, Y: 1})
   1006 	if err != nil {
   1007 		t.Fatal(err)
   1008 	}
   1009 	var u unexported
   1010 	_, err = Unmarshal(bs, &u)
   1011 	if err != want {
   1012 		t.Errorf("got %v, want %v", err, want)
   1013 	}
   1014 }
   1015 
   1016 func TestNull(t *testing.T) {
   1017 	marshaled, err := Marshal(NullRawValue)
   1018 	if err != nil {
   1019 		t.Fatal(err)
   1020 	}
   1021 	if !bytes.Equal(NullBytes, marshaled) {
   1022 		t.Errorf("Expected Marshal of NullRawValue to yield %x, got %x", NullBytes, marshaled)
   1023 	}
   1024 
   1025 	unmarshaled := RawValue{}
   1026 	if _, err := Unmarshal(NullBytes, &unmarshaled); err != nil {
   1027 		t.Fatal(err)
   1028 	}
   1029 
   1030 	unmarshaled.FullBytes = NullRawValue.FullBytes
   1031 	if len(unmarshaled.Bytes) == 0 {
   1032 		// DeepEqual considers a nil slice and an empty slice to be different.
   1033 		unmarshaled.Bytes = NullRawValue.Bytes
   1034 	}
   1035 
   1036 	if !reflect.DeepEqual(NullRawValue, unmarshaled) {
   1037 		t.Errorf("Expected Unmarshal of NullBytes to yield %v, got %v", NullRawValue, unmarshaled)
   1038 	}
   1039 }
   1040 
   1041 func TestExplicitTagRawValueStruct(t *testing.T) {
   1042 	type foo struct {
   1043 		A RawValue `asn1:"optional,explicit,tag:5"`
   1044 		B []byte   `asn1:"optional,explicit,tag:6"`
   1045 	}
   1046 	before := foo{B: []byte{1, 2, 3}}
   1047 	derBytes, err := Marshal(before)
   1048 	if err != nil {
   1049 		t.Fatal(err)
   1050 	}
   1051 
   1052 	var after foo
   1053 	if rest, err := Unmarshal(derBytes, &after); err != nil || len(rest) != 0 {
   1054 		t.Fatal(err)
   1055 	}
   1056 
   1057 	got := fmt.Sprintf("%#v", after)
   1058 	want := fmt.Sprintf("%#v", before)
   1059 	if got != want {
   1060 		t.Errorf("got %s, want %s (DER: %x)", got, want, derBytes)
   1061 	}
   1062 }
   1063 
   1064 func TestTaggedRawValue(t *testing.T) {
   1065 	type taggedRawValue struct {
   1066 		A RawValue `asn1:"tag:5"`
   1067 	}
   1068 	type untaggedRawValue struct {
   1069 		A RawValue
   1070 	}
   1071 	const isCompound = 0x20
   1072 	const tag = 5
   1073 
   1074 	tests := []struct {
   1075 		shouldMatch bool
   1076 		derBytes    []byte
   1077 	}{
   1078 		{false, []byte{0x30, 3, TagInteger, 1, 1}},
   1079 		{true, []byte{0x30, 3, (ClassContextSpecific << 6) | tag, 1, 1}},
   1080 		{true, []byte{0x30, 3, (ClassContextSpecific << 6) | tag | isCompound, 1, 1}},
   1081 		{false, []byte{0x30, 3, (ClassApplication << 6) | tag | isCompound, 1, 1}},
   1082 	}
   1083 
   1084 	for i, test := range tests {
   1085 		var tagged taggedRawValue
   1086 		if _, err := Unmarshal(test.derBytes, &tagged); (err == nil) != test.shouldMatch {
   1087 			t.Errorf("#%d: unexpected result parsing %x: %s", i, test.derBytes, err)
   1088 		}
   1089 
   1090 		// An untagged RawValue should accept anything.
   1091 		var untagged untaggedRawValue
   1092 		if _, err := Unmarshal(test.derBytes, &untagged); err != nil {
   1093 			t.Errorf("#%d: unexpected failure parsing %x with untagged RawValue: %s", i, test.derBytes, err)
   1094 		}
   1095 	}
   1096 }
   1097