...
Run Format

Source file src/encoding/asn1/asn1_test.go

Documentation: encoding/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@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@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  

View as plain text