You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

778 lines
24 KiB

  1. // Copyright 2013 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. // Package ocsp parses OCSP responses as specified in RFC 2560. OCSP responses
  5. // are signed messages attesting to the validity of a certificate for a small
  6. // period of time. This is used to manage revocation for X.509 certificates.
  7. package ocsp // import "golang.org/x/crypto/ocsp"
  8. import (
  9. "crypto"
  10. "crypto/ecdsa"
  11. "crypto/elliptic"
  12. "crypto/rand"
  13. "crypto/rsa"
  14. _ "crypto/sha1"
  15. _ "crypto/sha256"
  16. _ "crypto/sha512"
  17. "crypto/x509"
  18. "crypto/x509/pkix"
  19. "encoding/asn1"
  20. "errors"
  21. "fmt"
  22. "math/big"
  23. "strconv"
  24. "time"
  25. )
  26. var idPKIXOCSPBasic = asn1.ObjectIdentifier([]int{1, 3, 6, 1, 5, 5, 7, 48, 1, 1})
  27. // ResponseStatus contains the result of an OCSP request. See
  28. // https://tools.ietf.org/html/rfc6960#section-2.3
  29. type ResponseStatus int
  30. const (
  31. Success ResponseStatus = 0
  32. Malformed ResponseStatus = 1
  33. InternalError ResponseStatus = 2
  34. TryLater ResponseStatus = 3
  35. // Status code four is unused in OCSP. See
  36. // https://tools.ietf.org/html/rfc6960#section-4.2.1
  37. SignatureRequired ResponseStatus = 5
  38. Unauthorized ResponseStatus = 6
  39. )
  40. func (r ResponseStatus) String() string {
  41. switch r {
  42. case Success:
  43. return "success"
  44. case Malformed:
  45. return "malformed"
  46. case InternalError:
  47. return "internal error"
  48. case TryLater:
  49. return "try later"
  50. case SignatureRequired:
  51. return "signature required"
  52. case Unauthorized:
  53. return "unauthorized"
  54. default:
  55. return "unknown OCSP status: " + strconv.Itoa(int(r))
  56. }
  57. }
  58. // ResponseError is an error that may be returned by ParseResponse to indicate
  59. // that the response itself is an error, not just that its indicating that a
  60. // certificate is revoked, unknown, etc.
  61. type ResponseError struct {
  62. Status ResponseStatus
  63. }
  64. func (r ResponseError) Error() string {
  65. return "ocsp: error from server: " + r.Status.String()
  66. }
  67. // These are internal structures that reflect the ASN.1 structure of an OCSP
  68. // response. See RFC 2560, section 4.2.
  69. type certID struct {
  70. HashAlgorithm pkix.AlgorithmIdentifier
  71. NameHash []byte
  72. IssuerKeyHash []byte
  73. SerialNumber *big.Int
  74. }
  75. // https://tools.ietf.org/html/rfc2560#section-4.1.1
  76. type ocspRequest struct {
  77. TBSRequest tbsRequest
  78. }
  79. type tbsRequest struct {
  80. Version int `asn1:"explicit,tag:0,default:0,optional"`
  81. RequestorName pkix.RDNSequence `asn1:"explicit,tag:1,optional"`
  82. RequestList []request
  83. }
  84. type request struct {
  85. Cert certID
  86. }
  87. type responseASN1 struct {
  88. Status asn1.Enumerated
  89. Response responseBytes `asn1:"explicit,tag:0,optional"`
  90. }
  91. type responseBytes struct {
  92. ResponseType asn1.ObjectIdentifier
  93. Response []byte
  94. }
  95. type basicResponse struct {
  96. TBSResponseData responseData
  97. SignatureAlgorithm pkix.AlgorithmIdentifier
  98. Signature asn1.BitString
  99. Certificates []asn1.RawValue `asn1:"explicit,tag:0,optional"`
  100. }
  101. type responseData struct {
  102. Raw asn1.RawContent
  103. Version int `asn1:"optional,default:0,explicit,tag:0"`
  104. RawResponderID asn1.RawValue
  105. ProducedAt time.Time `asn1:"generalized"`
  106. Responses []singleResponse
  107. }
  108. type singleResponse struct {
  109. CertID certID
  110. Good asn1.Flag `asn1:"tag:0,optional"`
  111. Revoked revokedInfo `asn1:"tag:1,optional"`
  112. Unknown asn1.Flag `asn1:"tag:2,optional"`
  113. ThisUpdate time.Time `asn1:"generalized"`
  114. NextUpdate time.Time `asn1:"generalized,explicit,tag:0,optional"`
  115. SingleExtensions []pkix.Extension `asn1:"explicit,tag:1,optional"`
  116. }
  117. type revokedInfo struct {
  118. RevocationTime time.Time `asn1:"generalized"`
  119. Reason asn1.Enumerated `asn1:"explicit,tag:0,optional"`
  120. }
  121. var (
  122. oidSignatureMD2WithRSA = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 1, 2}
  123. oidSignatureMD5WithRSA = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 1, 4}
  124. oidSignatureSHA1WithRSA = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 1, 5}
  125. oidSignatureSHA256WithRSA = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 1, 11}
  126. oidSignatureSHA384WithRSA = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 1, 12}
  127. oidSignatureSHA512WithRSA = asn1.ObjectIdentifier{1, 2, 840, 113549, 1, 1, 13}
  128. oidSignatureDSAWithSHA1 = asn1.ObjectIdentifier{1, 2, 840, 10040, 4, 3}
  129. oidSignatureDSAWithSHA256 = asn1.ObjectIdentifier{2, 16, 840, 1, 101, 3, 4, 3, 2}
  130. oidSignatureECDSAWithSHA1 = asn1.ObjectIdentifier{1, 2, 840, 10045, 4, 1}
  131. oidSignatureECDSAWithSHA256 = asn1.ObjectIdentifier{1, 2, 840, 10045, 4, 3, 2}
  132. oidSignatureECDSAWithSHA384 = asn1.ObjectIdentifier{1, 2, 840, 10045, 4, 3, 3}
  133. oidSignatureECDSAWithSHA512 = asn1.ObjectIdentifier{1, 2, 840, 10045, 4, 3, 4}
  134. )
  135. var hashOIDs = map[crypto.Hash]asn1.ObjectIdentifier{
  136. crypto.SHA1: asn1.ObjectIdentifier([]int{1, 3, 14, 3, 2, 26}),
  137. crypto.SHA256: asn1.ObjectIdentifier([]int{2, 16, 840, 1, 101, 3, 4, 2, 1}),
  138. crypto.SHA384: asn1.ObjectIdentifier([]int{2, 16, 840, 1, 101, 3, 4, 2, 2}),
  139. crypto.SHA512: asn1.ObjectIdentifier([]int{2, 16, 840, 1, 101, 3, 4, 2, 3}),
  140. }
  141. // TODO(rlb): This is also from crypto/x509, so same comment as AGL's below
  142. var signatureAlgorithmDetails = []struct {
  143. algo x509.SignatureAlgorithm
  144. oid asn1.ObjectIdentifier
  145. pubKeyAlgo x509.PublicKeyAlgorithm
  146. hash crypto.Hash
  147. }{
  148. {x509.MD2WithRSA, oidSignatureMD2WithRSA, x509.RSA, crypto.Hash(0) /* no value for MD2 */},
  149. {x509.MD5WithRSA, oidSignatureMD5WithRSA, x509.RSA, crypto.MD5},
  150. {x509.SHA1WithRSA, oidSignatureSHA1WithRSA, x509.RSA, crypto.SHA1},
  151. {x509.SHA256WithRSA, oidSignatureSHA256WithRSA, x509.RSA, crypto.SHA256},
  152. {x509.SHA384WithRSA, oidSignatureSHA384WithRSA, x509.RSA, crypto.SHA384},
  153. {x509.SHA512WithRSA, oidSignatureSHA512WithRSA, x509.RSA, crypto.SHA512},
  154. {x509.DSAWithSHA1, oidSignatureDSAWithSHA1, x509.DSA, crypto.SHA1},
  155. {x509.DSAWithSHA256, oidSignatureDSAWithSHA256, x509.DSA, crypto.SHA256},
  156. {x509.ECDSAWithSHA1, oidSignatureECDSAWithSHA1, x509.ECDSA, crypto.SHA1},
  157. {x509.ECDSAWithSHA256, oidSignatureECDSAWithSHA256, x509.ECDSA, crypto.SHA256},
  158. {x509.ECDSAWithSHA384, oidSignatureECDSAWithSHA384, x509.ECDSA, crypto.SHA384},
  159. {x509.ECDSAWithSHA512, oidSignatureECDSAWithSHA512, x509.ECDSA, crypto.SHA512},
  160. }
  161. // TODO(rlb): This is also from crypto/x509, so same comment as AGL's below
  162. func signingParamsForPublicKey(pub interface{}, requestedSigAlgo x509.SignatureAlgorithm) (hashFunc crypto.Hash, sigAlgo pkix.AlgorithmIdentifier, err error) {
  163. var pubType x509.PublicKeyAlgorithm
  164. switch pub := pub.(type) {
  165. case *rsa.PublicKey:
  166. pubType = x509.RSA
  167. hashFunc = crypto.SHA256
  168. sigAlgo.Algorithm = oidSignatureSHA256WithRSA
  169. sigAlgo.Parameters = asn1.RawValue{
  170. Tag: 5,
  171. }
  172. case *ecdsa.PublicKey:
  173. pubType = x509.ECDSA
  174. switch pub.Curve {
  175. case elliptic.P224(), elliptic.P256():
  176. hashFunc = crypto.SHA256
  177. sigAlgo.Algorithm = oidSignatureECDSAWithSHA256
  178. case elliptic.P384():
  179. hashFunc = crypto.SHA384
  180. sigAlgo.Algorithm = oidSignatureECDSAWithSHA384
  181. case elliptic.P521():
  182. hashFunc = crypto.SHA512
  183. sigAlgo.Algorithm = oidSignatureECDSAWithSHA512
  184. default:
  185. err = errors.New("x509: unknown elliptic curve")
  186. }
  187. default:
  188. err = errors.New("x509: only RSA and ECDSA keys supported")
  189. }
  190. if err != nil {
  191. return
  192. }
  193. if requestedSigAlgo == 0 {
  194. return
  195. }
  196. found := false
  197. for _, details := range signatureAlgorithmDetails {
  198. if details.algo == requestedSigAlgo {
  199. if details.pubKeyAlgo != pubType {
  200. err = errors.New("x509: requested SignatureAlgorithm does not match private key type")
  201. return
  202. }
  203. sigAlgo.Algorithm, hashFunc = details.oid, details.hash
  204. if hashFunc == 0 {
  205. err = errors.New("x509: cannot sign with hash function requested")
  206. return
  207. }
  208. found = true
  209. break
  210. }
  211. }
  212. if !found {
  213. err = errors.New("x509: unknown SignatureAlgorithm")
  214. }
  215. return
  216. }
  217. // TODO(agl): this is taken from crypto/x509 and so should probably be exported
  218. // from crypto/x509 or crypto/x509/pkix.
  219. func getSignatureAlgorithmFromOID(oid asn1.ObjectIdentifier) x509.SignatureAlgorithm {
  220. for _, details := range signatureAlgorithmDetails {
  221. if oid.Equal(details.oid) {
  222. return details.algo
  223. }
  224. }
  225. return x509.UnknownSignatureAlgorithm
  226. }
  227. // TODO(rlb): This is not taken from crypto/x509, but it's of the same general form.
  228. func getHashAlgorithmFromOID(target asn1.ObjectIdentifier) crypto.Hash {
  229. for hash, oid := range hashOIDs {
  230. if oid.Equal(target) {
  231. return hash
  232. }
  233. }
  234. return crypto.Hash(0)
  235. }
  236. func getOIDFromHashAlgorithm(target crypto.Hash) asn1.ObjectIdentifier {
  237. for hash, oid := range hashOIDs {
  238. if hash == target {
  239. return oid
  240. }
  241. }
  242. return nil
  243. }
  244. // This is the exposed reflection of the internal OCSP structures.
  245. // The status values that can be expressed in OCSP. See RFC 6960.
  246. const (
  247. // Good means that the certificate is valid.
  248. Good = iota
  249. // Revoked means that the certificate has been deliberately revoked.
  250. Revoked
  251. // Unknown means that the OCSP responder doesn't know about the certificate.
  252. Unknown
  253. // ServerFailed is unused and was never used (see
  254. // https://go-review.googlesource.com/#/c/18944). ParseResponse will
  255. // return a ResponseError when an error response is parsed.
  256. ServerFailed
  257. )
  258. // The enumerated reasons for revoking a certificate. See RFC 5280.
  259. const (
  260. Unspecified = 0
  261. KeyCompromise = 1
  262. CACompromise = 2
  263. AffiliationChanged = 3
  264. Superseded = 4
  265. CessationOfOperation = 5
  266. CertificateHold = 6
  267. RemoveFromCRL = 8
  268. PrivilegeWithdrawn = 9
  269. AACompromise = 10
  270. )
  271. // Request represents an OCSP request. See RFC 6960.
  272. type Request struct {
  273. HashAlgorithm crypto.Hash
  274. IssuerNameHash []byte
  275. IssuerKeyHash []byte
  276. SerialNumber *big.Int
  277. }
  278. // Marshal marshals the OCSP request to ASN.1 DER encoded form.
  279. func (req *Request) Marshal() ([]byte, error) {
  280. hashAlg := getOIDFromHashAlgorithm(req.HashAlgorithm)
  281. if hashAlg == nil {
  282. return nil, errors.New("Unknown hash algorithm")
  283. }
  284. return asn1.Marshal(ocspRequest{
  285. tbsRequest{
  286. Version: 0,
  287. RequestList: []request{
  288. {
  289. Cert: certID{
  290. pkix.AlgorithmIdentifier{
  291. Algorithm: hashAlg,
  292. Parameters: asn1.RawValue{Tag: 5 /* ASN.1 NULL */},
  293. },
  294. req.IssuerNameHash,
  295. req.IssuerKeyHash,
  296. req.SerialNumber,
  297. },
  298. },
  299. },
  300. },
  301. })
  302. }
  303. // Response represents an OCSP response containing a single SingleResponse. See
  304. // RFC 6960.
  305. type Response struct {
  306. // Status is one of {Good, Revoked, Unknown}
  307. Status int
  308. SerialNumber *big.Int
  309. ProducedAt, ThisUpdate, NextUpdate, RevokedAt time.Time
  310. RevocationReason int
  311. Certificate *x509.Certificate
  312. // TBSResponseData contains the raw bytes of the signed response. If
  313. // Certificate is nil then this can be used to verify Signature.
  314. TBSResponseData []byte
  315. Signature []byte
  316. SignatureAlgorithm x509.SignatureAlgorithm
  317. // IssuerHash is the hash used to compute the IssuerNameHash and IssuerKeyHash.
  318. // Valid values are crypto.SHA1, crypto.SHA256, crypto.SHA384, and crypto.SHA512.
  319. // If zero, the default is crypto.SHA1.
  320. IssuerHash crypto.Hash
  321. // RawResponderName optionally contains the DER-encoded subject of the
  322. // responder certificate. Exactly one of RawResponderName and
  323. // ResponderKeyHash is set.
  324. RawResponderName []byte
  325. // ResponderKeyHash optionally contains the SHA-1 hash of the
  326. // responder's public key. Exactly one of RawResponderName and
  327. // ResponderKeyHash is set.
  328. ResponderKeyHash []byte
  329. // Extensions contains raw X.509 extensions from the singleExtensions field
  330. // of the OCSP response. When parsing certificates, this can be used to
  331. // extract non-critical extensions that are not parsed by this package. When
  332. // marshaling OCSP responses, the Extensions field is ignored, see
  333. // ExtraExtensions.
  334. Extensions []pkix.Extension
  335. // ExtraExtensions contains extensions to be copied, raw, into any marshaled
  336. // OCSP response (in the singleExtensions field). Values override any
  337. // extensions that would otherwise be produced based on the other fields. The
  338. // ExtraExtensions field is not populated when parsing certificates, see
  339. // Extensions.
  340. ExtraExtensions []pkix.Extension
  341. }
  342. // These are pre-serialized error responses for the various non-success codes
  343. // defined by OCSP. The Unauthorized code in particular can be used by an OCSP
  344. // responder that supports only pre-signed responses as a response to requests
  345. // for certificates with unknown status. See RFC 5019.
  346. var (
  347. MalformedRequestErrorResponse = []byte{0x30, 0x03, 0x0A, 0x01, 0x01}
  348. InternalErrorErrorResponse = []byte{0x30, 0x03, 0x0A, 0x01, 0x02}
  349. TryLaterErrorResponse = []byte{0x30, 0x03, 0x0A, 0x01, 0x03}
  350. SigRequredErrorResponse = []byte{0x30, 0x03, 0x0A, 0x01, 0x05}
  351. UnauthorizedErrorResponse = []byte{0x30, 0x03, 0x0A, 0x01, 0x06}
  352. )
  353. // CheckSignatureFrom checks that the signature in resp is a valid signature
  354. // from issuer. This should only be used if resp.Certificate is nil. Otherwise,
  355. // the OCSP response contained an intermediate certificate that created the
  356. // signature. That signature is checked by ParseResponse and only
  357. // resp.Certificate remains to be validated.
  358. func (resp *Response) CheckSignatureFrom(issuer *x509.Certificate) error {
  359. return issuer.CheckSignature(resp.SignatureAlgorithm, resp.TBSResponseData, resp.Signature)
  360. }
  361. // ParseError results from an invalid OCSP response.
  362. type ParseError string
  363. func (p ParseError) Error() string {
  364. return string(p)
  365. }
  366. // ParseRequest parses an OCSP request in DER form. It only supports
  367. // requests for a single certificate. Signed requests are not supported.
  368. // If a request includes a signature, it will result in a ParseError.
  369. func ParseRequest(bytes []byte) (*Request, error) {
  370. var req ocspRequest
  371. rest, err := asn1.Unmarshal(bytes, &req)
  372. if err != nil {
  373. return nil, err
  374. }
  375. if len(rest) > 0 {
  376. return nil, ParseError("trailing data in OCSP request")
  377. }
  378. if len(req.TBSRequest.RequestList) == 0 {
  379. return nil, ParseError("OCSP request contains no request body")
  380. }
  381. innerRequest := req.TBSRequest.RequestList[0]
  382. hashFunc := getHashAlgorithmFromOID(innerRequest.Cert.HashAlgorithm.Algorithm)
  383. if hashFunc == crypto.Hash(0) {
  384. return nil, ParseError("OCSP request uses unknown hash function")
  385. }
  386. return &Request{
  387. HashAlgorithm: hashFunc,
  388. IssuerNameHash: innerRequest.Cert.NameHash,
  389. IssuerKeyHash: innerRequest.Cert.IssuerKeyHash,
  390. SerialNumber: innerRequest.Cert.SerialNumber,
  391. }, nil
  392. }
  393. // ParseResponse parses an OCSP response in DER form. It only supports
  394. // responses for a single certificate. If the response contains a certificate
  395. // then the signature over the response is checked. If issuer is not nil then
  396. // it will be used to validate the signature or embedded certificate.
  397. //
  398. // Invalid responses and parse failures will result in a ParseError.
  399. // Error responses will result in a ResponseError.
  400. func ParseResponse(bytes []byte, issuer *x509.Certificate) (*Response, error) {
  401. return ParseResponseForCert(bytes, nil, issuer)
  402. }
  403. // ParseResponseForCert parses an OCSP response in DER form and searches for a
  404. // Response relating to cert. If such a Response is found and the OCSP response
  405. // contains a certificate then the signature over the response is checked. If
  406. // issuer is not nil then it will be used to validate the signature or embedded
  407. // certificate.
  408. //
  409. // Invalid responses and parse failures will result in a ParseError.
  410. // Error responses will result in a ResponseError.
  411. func ParseResponseForCert(bytes []byte, cert, issuer *x509.Certificate) (*Response, error) {
  412. var resp responseASN1
  413. rest, err := asn1.Unmarshal(bytes, &resp)
  414. if err != nil {
  415. return nil, err
  416. }
  417. if len(rest) > 0 {
  418. return nil, ParseError("trailing data in OCSP response")
  419. }
  420. if status := ResponseStatus(resp.Status); status != Success {
  421. return nil, ResponseError{status}
  422. }
  423. if !resp.Response.ResponseType.Equal(idPKIXOCSPBasic) {
  424. return nil, ParseError("bad OCSP response type")
  425. }
  426. var basicResp basicResponse
  427. rest, err = asn1.Unmarshal(resp.Response.Response, &basicResp)
  428. if err != nil {
  429. return nil, err
  430. }
  431. if len(basicResp.Certificates) > 1 {
  432. return nil, ParseError("OCSP response contains bad number of certificates")
  433. }
  434. if n := len(basicResp.TBSResponseData.Responses); n == 0 || cert == nil && n > 1 {
  435. return nil, ParseError("OCSP response contains bad number of responses")
  436. }
  437. var singleResp singleResponse
  438. if cert == nil {
  439. singleResp = basicResp.TBSResponseData.Responses[0]
  440. } else {
  441. match := false
  442. for _, resp := range basicResp.TBSResponseData.Responses {
  443. if cert.SerialNumber.Cmp(resp.CertID.SerialNumber) == 0 {
  444. singleResp = resp
  445. match = true
  446. break
  447. }
  448. }
  449. if !match {
  450. return nil, ParseError("no response matching the supplied certificate")
  451. }
  452. }
  453. ret := &Response{
  454. TBSResponseData: basicResp.TBSResponseData.Raw,
  455. Signature: basicResp.Signature.RightAlign(),
  456. SignatureAlgorithm: getSignatureAlgorithmFromOID(basicResp.SignatureAlgorithm.Algorithm),
  457. Extensions: singleResp.SingleExtensions,
  458. SerialNumber: singleResp.CertID.SerialNumber,
  459. ProducedAt: basicResp.TBSResponseData.ProducedAt,
  460. ThisUpdate: singleResp.ThisUpdate,
  461. NextUpdate: singleResp.NextUpdate,
  462. }
  463. // Handle the ResponderID CHOICE tag. ResponderID can be flattened into
  464. // TBSResponseData once https://go-review.googlesource.com/34503 has been
  465. // released.
  466. rawResponderID := basicResp.TBSResponseData.RawResponderID
  467. switch rawResponderID.Tag {
  468. case 1: // Name
  469. var rdn pkix.RDNSequence
  470. if rest, err := asn1.Unmarshal(rawResponderID.Bytes, &rdn); err != nil || len(rest) != 0 {
  471. return nil, ParseError("invalid responder name")
  472. }
  473. ret.RawResponderName = rawResponderID.Bytes
  474. case 2: // KeyHash
  475. if rest, err := asn1.Unmarshal(rawResponderID.Bytes, &ret.ResponderKeyHash); err != nil || len(rest) != 0 {
  476. return nil, ParseError("invalid responder key hash")
  477. }
  478. default:
  479. return nil, ParseError("invalid responder id tag")
  480. }
  481. if len(basicResp.Certificates) > 0 {
  482. ret.Certificate, err = x509.ParseCertificate(basicResp.Certificates[0].FullBytes)
  483. if err != nil {
  484. return nil, err
  485. }
  486. if err := ret.CheckSignatureFrom(ret.Certificate); err != nil {
  487. return nil, ParseError("bad signature on embedded certificate: " + err.Error())
  488. }
  489. if issuer != nil {
  490. if err := issuer.CheckSignature(ret.Certificate.SignatureAlgorithm, ret.Certificate.RawTBSCertificate, ret.Certificate.Signature); err != nil {
  491. return nil, ParseError("bad OCSP signature: " + err.Error())
  492. }
  493. }
  494. } else if issuer != nil {
  495. if err := ret.CheckSignatureFrom(issuer); err != nil {
  496. return nil, ParseError("bad OCSP signature: " + err.Error())
  497. }
  498. }
  499. for _, ext := range singleResp.SingleExtensions {
  500. if ext.Critical {
  501. return nil, ParseError("unsupported critical extension")
  502. }
  503. }
  504. for h, oid := range hashOIDs {
  505. if singleResp.CertID.HashAlgorithm.Algorithm.Equal(oid) {
  506. ret.IssuerHash = h
  507. break
  508. }
  509. }
  510. if ret.IssuerHash == 0 {
  511. return nil, ParseError("unsupported issuer hash algorithm")
  512. }
  513. switch {
  514. case bool(singleResp.Good):
  515. ret.Status = Good
  516. case bool(singleResp.Unknown):
  517. ret.Status = Unknown
  518. default:
  519. ret.Status = Revoked
  520. ret.RevokedAt = singleResp.Revoked.RevocationTime
  521. ret.RevocationReason = int(singleResp.Revoked.Reason)
  522. }
  523. return ret, nil
  524. }
  525. // RequestOptions contains options for constructing OCSP requests.
  526. type RequestOptions struct {
  527. // Hash contains the hash function that should be used when
  528. // constructing the OCSP request. If zero, SHA-1 will be used.
  529. Hash crypto.Hash
  530. }
  531. func (opts *RequestOptions) hash() crypto.Hash {
  532. if opts == nil || opts.Hash == 0 {
  533. // SHA-1 is nearly universally used in OCSP.
  534. return crypto.SHA1
  535. }
  536. return opts.Hash
  537. }
  538. // CreateRequest returns a DER-encoded, OCSP request for the status of cert. If
  539. // opts is nil then sensible defaults are used.
  540. func CreateRequest(cert, issuer *x509.Certificate, opts *RequestOptions) ([]byte, error) {
  541. hashFunc := opts.hash()
  542. // OCSP seems to be the only place where these raw hash identifiers are
  543. // used. I took the following from
  544. // http://msdn.microsoft.com/en-us/library/ff635603.aspx
  545. _, ok := hashOIDs[hashFunc]
  546. if !ok {
  547. return nil, x509.ErrUnsupportedAlgorithm
  548. }
  549. if !hashFunc.Available() {
  550. return nil, x509.ErrUnsupportedAlgorithm
  551. }
  552. h := opts.hash().New()
  553. var publicKeyInfo struct {
  554. Algorithm pkix.AlgorithmIdentifier
  555. PublicKey asn1.BitString
  556. }
  557. if _, err := asn1.Unmarshal(issuer.RawSubjectPublicKeyInfo, &publicKeyInfo); err != nil {
  558. return nil, err
  559. }
  560. h.Write(publicKeyInfo.PublicKey.RightAlign())
  561. issuerKeyHash := h.Sum(nil)
  562. h.Reset()
  563. h.Write(issuer.RawSubject)
  564. issuerNameHash := h.Sum(nil)
  565. req := &Request{
  566. HashAlgorithm: hashFunc,
  567. IssuerNameHash: issuerNameHash,
  568. IssuerKeyHash: issuerKeyHash,
  569. SerialNumber: cert.SerialNumber,
  570. }
  571. return req.Marshal()
  572. }
  573. // CreateResponse returns a DER-encoded OCSP response with the specified contents.
  574. // The fields in the response are populated as follows:
  575. //
  576. // The responder cert is used to populate the responder's name field, and the
  577. // certificate itself is provided alongside the OCSP response signature.
  578. //
  579. // The issuer cert is used to puplate the IssuerNameHash and IssuerKeyHash fields.
  580. //
  581. // The template is used to populate the SerialNumber, Status, RevokedAt,
  582. // RevocationReason, ThisUpdate, and NextUpdate fields.
  583. //
  584. // If template.IssuerHash is not set, SHA1 will be used.
  585. //
  586. // The ProducedAt date is automatically set to the current date, to the nearest minute.
  587. func CreateResponse(issuer, responderCert *x509.Certificate, template Response, priv crypto.Signer) ([]byte, error) {
  588. var publicKeyInfo struct {
  589. Algorithm pkix.AlgorithmIdentifier
  590. PublicKey asn1.BitString
  591. }
  592. if _, err := asn1.Unmarshal(issuer.RawSubjectPublicKeyInfo, &publicKeyInfo); err != nil {
  593. return nil, err
  594. }
  595. if template.IssuerHash == 0 {
  596. template.IssuerHash = crypto.SHA1
  597. }
  598. hashOID := getOIDFromHashAlgorithm(template.IssuerHash)
  599. if hashOID == nil {
  600. return nil, errors.New("unsupported issuer hash algorithm")
  601. }
  602. if !template.IssuerHash.Available() {
  603. return nil, fmt.Errorf("issuer hash algorithm %v not linked into binary", template.IssuerHash)
  604. }
  605. h := template.IssuerHash.New()
  606. h.Write(publicKeyInfo.PublicKey.RightAlign())
  607. issuerKeyHash := h.Sum(nil)
  608. h.Reset()
  609. h.Write(issuer.RawSubject)
  610. issuerNameHash := h.Sum(nil)
  611. innerResponse := singleResponse{
  612. CertID: certID{
  613. HashAlgorithm: pkix.AlgorithmIdentifier{
  614. Algorithm: hashOID,
  615. Parameters: asn1.RawValue{Tag: 5 /* ASN.1 NULL */},
  616. },
  617. NameHash: issuerNameHash,
  618. IssuerKeyHash: issuerKeyHash,
  619. SerialNumber: template.SerialNumber,
  620. },
  621. ThisUpdate: template.ThisUpdate.UTC(),
  622. NextUpdate: template.NextUpdate.UTC(),
  623. SingleExtensions: template.ExtraExtensions,
  624. }
  625. switch template.Status {
  626. case Good:
  627. innerResponse.Good = true
  628. case Unknown:
  629. innerResponse.Unknown = true
  630. case Revoked:
  631. innerResponse.Revoked = revokedInfo{
  632. RevocationTime: template.RevokedAt.UTC(),
  633. Reason: asn1.Enumerated(template.RevocationReason),
  634. }
  635. }
  636. rawResponderID := asn1.RawValue{
  637. Class: 2, // context-specific
  638. Tag: 1, // Name (explicit tag)
  639. IsCompound: true,
  640. Bytes: responderCert.RawSubject,
  641. }
  642. tbsResponseData := responseData{
  643. Version: 0,
  644. RawResponderID: rawResponderID,
  645. ProducedAt: time.Now().Truncate(time.Minute).UTC(),
  646. Responses: []singleResponse{innerResponse},
  647. }
  648. tbsResponseDataDER, err := asn1.Marshal(tbsResponseData)
  649. if err != nil {
  650. return nil, err
  651. }
  652. hashFunc, signatureAlgorithm, err := signingParamsForPublicKey(priv.Public(), template.SignatureAlgorithm)
  653. if err != nil {
  654. return nil, err
  655. }
  656. responseHash := hashFunc.New()
  657. responseHash.Write(tbsResponseDataDER)
  658. signature, err := priv.Sign(rand.Reader, responseHash.Sum(nil), hashFunc)
  659. if err != nil {
  660. return nil, err
  661. }
  662. response := basicResponse{
  663. TBSResponseData: tbsResponseData,
  664. SignatureAlgorithm: signatureAlgorithm,
  665. Signature: asn1.BitString{
  666. Bytes: signature,
  667. BitLength: 8 * len(signature),
  668. },
  669. }
  670. if template.Certificate != nil {
  671. response.Certificates = []asn1.RawValue{
  672. {FullBytes: template.Certificate.Raw},
  673. }
  674. }
  675. responseDER, err := asn1.Marshal(response)
  676. if err != nil {
  677. return nil, err
  678. }
  679. return asn1.Marshal(responseASN1{
  680. Status: asn1.Enumerated(Success),
  681. Response: responseBytes{
  682. ResponseType: idPKIXOCSPBasic,
  683. Response: responseDER,
  684. },
  685. })
  686. }