tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

pkix.h (7965B)


      1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
      2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
      3 /* This code is made available to you under your choice of the following sets
      4 * of licensing terms:
      5 */
      6 /* This Source Code Form is subject to the terms of the Mozilla Public
      7 * License, v. 2.0. If a copy of the MPL was not distributed with this
      8 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
      9 */
     10 /* Copyright 2013 Mozilla Contributors
     11 *
     12 * Licensed under the Apache License, Version 2.0 (the "License");
     13 * you may not use this file except in compliance with the License.
     14 * You may obtain a copy of the License at
     15 *
     16 *     http://www.apache.org/licenses/LICENSE-2.0
     17 *
     18 * Unless required by applicable law or agreed to in writing, software
     19 * distributed under the License is distributed on an "AS IS" BASIS,
     20 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     21 * See the License for the specific language governing permissions and
     22 * limitations under the License.
     23 */
     24 
     25 #ifndef mozilla_pkix_pkix_h
     26 #define mozilla_pkix_pkix_h
     27 
     28 #include "mozpkix/pkixtypes.h"
     29 
     30 namespace mozilla {
     31 namespace pkix {
     32 
     33 // ----------------------------------------------------------------------------
     34 // LIMITED SUPPORT FOR CERTIFICATE POLICIES
     35 //
     36 // If SEC_OID_X509_ANY_POLICY is passed as the value of the requiredPolicy
     37 // parameter then all policy validation will be skipped. Otherwise, path
     38 // building and validation will be done for the given policy.
     39 //
     40 // In RFC 5280 terms:
     41 //
     42 //    * user-initial-policy-set = { requiredPolicy }.
     43 //    * initial-explicit-policy = true
     44 //    * initial-any-policy-inhibit = false
     45 //
     46 // We allow intermediate cerificates to use this extension but since
     47 // we do not process the inhibit anyPolicy extesion we will fail if this
     48 // extension is present. TODO(bug 989051)
     49 // Because we force explicit policy and because we prohibit policy mapping, we
     50 // do not bother processing the policy mapping, or policy constraint.
     51 //
     52 // ----------------------------------------------------------------------------
     53 // ERROR RANKING
     54 //
     55 // BuildCertChain prioritizes certain checks ahead of others so that when a
     56 // certificate chain has multiple errors, the "most serious" error is
     57 // returned. In practice, this ranking of seriousness is tied directly to how
     58 // Firefox's certificate error override mechanism.
     59 //
     60 // The ranking is:
     61 //
     62 //    1. Active distrust (Result::ERROR_UNTRUSTED_CERT).
     63 //    2. Problems with issuer-independent properties for CA certificates.
     64 //    3. Unknown issuer (Result::ERROR_UNKNOWN_ISSUER).
     65 //    4. Problems with issuer-independent properties for EE certificates.
     66 //    5. Revocation.
     67 //
     68 // In particular, if BuildCertChain returns Result::ERROR_UNKNOWN_ISSUER then
     69 // the caller can call CERT_CheckCertValidTimes to determine if the certificate
     70 // is ALSO expired.
     71 //
     72 // It would be better if revocation were prioritized above expiration and
     73 // unknown issuer. However, it is impossible to do revocation checking without
     74 // knowing the issuer, since the issuer information is needed to validate the
     75 // revocation information. Also, generally revocation checking only works
     76 // during the validity period of the certificate.
     77 //
     78 // In general, when path building fails, BuildCertChain will return
     79 // Result::ERROR_UNKNOWN_ISSUER. However, if all attempted paths resulted in
     80 // the same error (which is trivially true when there is only one potential
     81 // path), more specific errors will be returned.
     82 //
     83 // ----------------------------------------------------------------------------
     84 // Meanings of specific error codes can be found in Result.h
     85 
     86 // This function attempts to find a trustworthy path from the supplied
     87 // certificate to a trust anchor. In the event that no trusted path is found,
     88 // the method returns an error result; the error ranking is described above.
     89 //
     90 // Parameters:
     91 //  time:
     92 //         Timestamp for which the chain should be valid; this is useful to
     93 //         analyze whether a record was trustworthy when it was made.
     94 //  requiredKeyUsageIfPresent:
     95 //         What key usage bits must be set, if the extension is present at all,
     96 //         to be considered a valid chain. Multiple values should be OR'd
     97 //         together. If you don't want to specify anything, use
     98 //         KeyUsage::noParticularKeyUsageRequired.
     99 //  requiredEKUIfPresent:
    100 //         What extended key usage bits must be set, if the EKU extension
    101 //         exists, to be considered a valid chain. Multiple values should be
    102 //         OR'd together. If you don't want to specify anything, use
    103 //         KeyPurposeId::anyExtendedKeyUsage.
    104 //  requiredPolicy:
    105 //         This is the policy to apply; typically included in EV certificates.
    106 //         If there is no policy, pass in CertPolicyId::anyPolicy.
    107 Result BuildCertChain(TrustDomain& trustDomain, Input cert, Time time,
    108                      EndEntityOrCA endEntityOrCA,
    109                      KeyUsage requiredKeyUsageIfPresent,
    110                      KeyPurposeId requiredEKUIfPresent,
    111                      const CertPolicyId& requiredPolicy,
    112                      /*optional*/ const Input* stapledOCSPResponse);
    113 
    114 // Verify that the given end-entity cert, which is assumed to have been already
    115 // validated with BuildCertChain, is valid for the given hostname. The matching
    116 // function attempts to implement RFC 6125 with a couple of differences:
    117 // - IP addresses are out of scope of RFC 6125, but this method accepts them for
    118 //   backward compatibility (see SearchNames in pkixnames.cpp)
    119 // - A wildcard in a DNS-ID may only appear as the entirety of the first label.
    120 // If the NameMatchingPolicy is omitted, a StrictNameMatchingPolicy is used.
    121 Result CheckCertHostname(Input cert, Input hostname);
    122 Result CheckCertHostname(Input cert, Input hostname,
    123                         NameMatchingPolicy& nameMatchingPolicy);
    124 
    125 // Construct an RFC-6960-encoded OCSP request, ready for submission to a
    126 // responder, for the provided CertID. The request has no extensions.
    127 static const size_t OCSP_REQUEST_MAX_LENGTH = 127;
    128 Result CreateEncodedOCSPRequest(TrustDomain& trustDomain, const CertID& certID,
    129                                /*out*/ uint8_t (&out)[OCSP_REQUEST_MAX_LENGTH],
    130                                /*out*/ size_t& outLen);
    131 
    132 // The out parameter expired will be true if the response has expired. If the
    133 // response also indicates a revoked or unknown certificate, that error
    134 // will be returned. Otherwise, Result::ERROR_OCSP_OLD_RESPONSE will be
    135 // returned for an expired response.
    136 //
    137 // The optional parameter thisUpdate will be the thisUpdate value of
    138 // the encoded response if it is considered trustworthy. Only
    139 // good, unknown, or revoked responses that verify correctly are considered
    140 // trustworthy. If the response is not trustworthy, thisUpdate will be 0.
    141 // Similarly, the optional parameter validThrough will be the time through
    142 // which the encoded response is considered trustworthy (that is, as long as
    143 // the given time at which to validate is less than or equal to validThrough,
    144 // the response will be considered trustworthy).
    145 Result VerifyEncodedOCSPResponse(
    146    TrustDomain& trustDomain, const CertID& certID, Time time,
    147    uint16_t maxLifetimeInDays, Input encodedResponse,
    148    /* out */ bool& expired,
    149    /* optional out */ Time* thisUpdate = nullptr,
    150    /* optional out */ Time* validThrough = nullptr);
    151 
    152 // Check that the TLSFeature extensions in a given end-entity cert (which is
    153 // assumed to have been already validated with BuildCertChain) are satisfied.
    154 // The only feature which we cancurrently process a requirement for is
    155 // status_request (OCSP stapling) so we reject any extension that specifies a
    156 // requirement for another value. Empty extensions are also rejected.
    157 Result CheckTLSFeaturesAreSatisfied(Input& cert,
    158                                    const Input* stapledOCSPResponse);
    159 }  // namespace pkix
    160 }  // namespace mozilla
    161 
    162 #endif  // mozilla_pkix_pkix_h