1 package main
2
3 import (
4 "crypto/ecdsa"
5 "crypto/elliptic"
6 "crypto/rand"
7 "crypto/x509"
8 "crypto/x509/pkix"
9 "math/big"
10 "testing"
11 "time"
12
13 "github.com/letsencrypt/boulder/test"
14 )
15
16 func TestGenerateOCSPResponse(t *testing.T) {
17 kA, err := ecdsa.GenerateKey(elliptic.P256(), rand.Reader)
18 test.AssertNotError(t, err, "failed to generate test key")
19 kB, err := ecdsa.GenerateKey(elliptic.P256(), rand.Reader)
20 test.AssertNotError(t, err, "failed to generate test key")
21 kC, err := ecdsa.GenerateKey(elliptic.P256(), rand.Reader)
22 test.AssertNotError(t, err, "failed to generate test key")
23
24 template := &x509.Certificate{
25 SerialNumber: big.NewInt(9),
26 Subject: pkix.Name{
27 CommonName: "cn",
28 },
29 KeyUsage: x509.KeyUsageCertSign,
30 BasicConstraintsValid: true,
31 IsCA: true,
32 NotBefore: time.Time{}.Add(time.Hour * 10),
33 NotAfter: time.Time{}.Add(time.Hour * 20),
34 }
35 issuerBytes, err := x509.CreateCertificate(rand.Reader, template, template, kA.Public(), kA)
36 test.AssertNotError(t, err, "failed to create test issuer")
37 issuer, err := x509.ParseCertificate(issuerBytes)
38 test.AssertNotError(t, err, "failed to parse test issuer")
39 delegatedIssuerBytes, err := x509.CreateCertificate(rand.Reader, template, issuer, kB.Public(), kA)
40 test.AssertNotError(t, err, "failed to create test delegated issuer")
41 badDelegatedIssuer, err := x509.ParseCertificate(delegatedIssuerBytes)
42 test.AssertNotError(t, err, "failed to parse test delegated issuer")
43 template.ExtKeyUsage = []x509.ExtKeyUsage{x509.ExtKeyUsageOCSPSigning}
44 delegatedIssuerBytes, err = x509.CreateCertificate(rand.Reader, template, issuer, kB.Public(), kA)
45 test.AssertNotError(t, err, "failed to create test delegated issuer")
46 goodDelegatedIssuer, err := x509.ParseCertificate(delegatedIssuerBytes)
47 test.AssertNotError(t, err, "failed to parse test delegated issuer")
48 template.BasicConstraintsValid, template.IsCA = false, false
49 certBytes, err := x509.CreateCertificate(rand.Reader, template, issuer, kC.Public(), kA)
50 test.AssertNotError(t, err, "failed to create test cert")
51 cert, err := x509.ParseCertificate(certBytes)
52 test.AssertNotError(t, err, "failed to parse test cert")
53
54 cases := []struct {
55 name string
56 issuer *x509.Certificate
57 delegatedIssuer *x509.Certificate
58 cert *x509.Certificate
59 thisUpdate time.Time
60 nextUpdate time.Time
61 expectedError string
62 }{
63 {
64 name: "invalid signature from issuer on certificate",
65 issuer: &x509.Certificate{},
66 cert: &x509.Certificate{},
67 expectedError: "invalid signature on certificate from issuer: x509: cannot verify signature: algorithm unimplemented",
68 },
69 {
70 name: "nextUpdate before thisUpdate",
71 issuer: issuer,
72 cert: cert,
73 thisUpdate: time.Time{}.Add(time.Hour),
74 nextUpdate: time.Time{},
75 expectedError: "thisUpdate must be before nextUpdate",
76 },
77 {
78 name: "thisUpdate before signer notBefore",
79 issuer: issuer,
80 cert: cert,
81 thisUpdate: time.Time{},
82 nextUpdate: time.Time{}.Add(time.Hour),
83 expectedError: "thisUpdate is before signing certificate's notBefore",
84 },
85 {
86 name: "nextUpdate after signer notAfter",
87 issuer: issuer,
88 cert: cert,
89 thisUpdate: time.Time{}.Add(time.Hour * 11),
90 nextUpdate: time.Time{}.Add(time.Hour * 21),
91 expectedError: "nextUpdate is after signing certificate's notAfter",
92 },
93 {
94 name: "bad delegated issuer signature",
95 issuer: issuer,
96 cert: cert,
97 delegatedIssuer: &x509.Certificate{},
98 expectedError: "invalid signature on delegated issuer from issuer: x509: cannot verify signature: algorithm unimplemented",
99 },
100 {
101 name: "good",
102 issuer: issuer,
103 cert: cert,
104 thisUpdate: time.Time{}.Add(time.Hour * 11),
105 nextUpdate: time.Time{}.Add(time.Hour * 12),
106 },
107 {
108 name: "bad delegated issuer without EKU",
109 issuer: issuer,
110 cert: cert,
111 delegatedIssuer: badDelegatedIssuer,
112 expectedError: "delegated issuer certificate doesn't contain OCSPSigning extended key usage",
113 },
114 {
115 name: "good delegated issuer",
116 issuer: issuer,
117 cert: cert,
118 delegatedIssuer: goodDelegatedIssuer,
119 thisUpdate: time.Time{}.Add(time.Hour * 11),
120 nextUpdate: time.Time{}.Add(time.Hour * 12),
121 },
122 }
123
124 for _, tc := range cases {
125 t.Run(tc.name, func(t *testing.T) {
126 _, err := generateOCSPResponse(kA, tc.issuer, tc.delegatedIssuer, tc.cert, tc.thisUpdate, tc.nextUpdate, 0)
127 if err != nil {
128 if tc.expectedError != "" && tc.expectedError != err.Error() {
129 t.Errorf("unexpected error: got %q, want %q", err.Error(), tc.expectedError)
130 } else if tc.expectedError == "" {
131 t.Errorf("unexpected error: %s", err)
132 }
133 } else if tc.expectedError != "" {
134 t.Errorf("expected error: %s", tc.expectedError)
135 }
136 })
137 }
138 }
139
View as plain text