security/pkix/lib/pkixutil.h

changeset 0
6474c204b198
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/security/pkix/lib/pkixutil.h	Wed Dec 31 06:09:35 2014 +0100
     1.3 @@ -0,0 +1,148 @@
     1.4 +/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
     1.5 +/* vim: set ts=8 sts=2 et sw=2 tw=80: */
     1.6 +/* Copyright 2013 Mozilla Foundation
     1.7 + *
     1.8 + * Licensed under the Apache License, Version 2.0 (the "License");
     1.9 + * you may not use this file except in compliance with the License.
    1.10 + * You may obtain a copy of the License at
    1.11 + *
    1.12 + *     http://www.apache.org/licenses/LICENSE-2.0
    1.13 + *
    1.14 + * Unless required by applicable law or agreed to in writing, software
    1.15 + * distributed under the License is distributed on an "AS IS" BASIS,
    1.16 + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    1.17 + * See the License for the specific language governing permissions and
    1.18 + * limitations under the License.
    1.19 + */
    1.20 +
    1.21 +#ifndef mozilla_pkix__pkixutil_h
    1.22 +#define mozilla_pkix__pkixutil_h
    1.23 +
    1.24 +#include "pkix/pkixtypes.h"
    1.25 +#include "prerror.h"
    1.26 +#include "seccomon.h"
    1.27 +#include "secerr.h"
    1.28 +
    1.29 +namespace mozilla { namespace pkix {
    1.30 +
    1.31 +enum Result
    1.32 +{
    1.33 +  Success = 0,
    1.34 +  FatalError = -1,      // An error was encountered that caused path building
    1.35 +                        // to stop immediately. example: out-of-memory.
    1.36 +  RecoverableError = -2 // an error that will cause path building to continue
    1.37 +                        // searching for alternative paths. example: expired
    1.38 +                        // certificate.
    1.39 +};
    1.40 +
    1.41 +// When returning errors, use this function instead of calling PR_SetError
    1.42 +// directly. This helps ensure that we always call PR_SetError when we return
    1.43 +// an error code. This is a useful place to set a breakpoint when a debugging
    1.44 +// a certificate verification failure.
    1.45 +inline Result
    1.46 +Fail(Result result, PRErrorCode errorCode)
    1.47 +{
    1.48 +  PR_ASSERT(result != Success);
    1.49 +  PR_SetError(errorCode, 0);
    1.50 +  return result;
    1.51 +}
    1.52 +
    1.53 +inline Result
    1.54 +MapSECStatus(SECStatus srv)
    1.55 +{
    1.56 +  if (srv == SECSuccess) {
    1.57 +    return Success;
    1.58 +  }
    1.59 +
    1.60 +  PRErrorCode error = PORT_GetError();
    1.61 +  switch (error) {
    1.62 +    case SEC_ERROR_EXTENSION_NOT_FOUND:
    1.63 +      return RecoverableError;
    1.64 +
    1.65 +    case PR_INVALID_STATE_ERROR:
    1.66 +    case SEC_ERROR_LIBRARY_FAILURE:
    1.67 +    case SEC_ERROR_NO_MEMORY:
    1.68 +      return FatalError;
    1.69 +  }
    1.70 +
    1.71 +  // TODO: PORT_Assert(false); // we haven't classified the error yet
    1.72 +  return RecoverableError;
    1.73 +}
    1.74 +
    1.75 +// During path building and verification, we build a linked list of BackCerts
    1.76 +// from the current cert toward the end-entity certificate. The linked list
    1.77 +// is used to verify properties that aren't local to the current certificate
    1.78 +// and/or the direct link between the current certificate and its issuer,
    1.79 +// such as name constraints.
    1.80 +//
    1.81 +// Each BackCert contains pointers to all the given certificate's extensions
    1.82 +// so that we can parse the extension block once and then process the
    1.83 +// extensions in an order that may be different than they appear in the cert.
    1.84 +class BackCert
    1.85 +{
    1.86 +public:
    1.87 +  // ExcludeCN means that GetConstrainedNames won't include the subject CN in
    1.88 +  // its results. IncludeCN means that GetConstrainedNames will include the
    1.89 +  // subject CN in its results.
    1.90 +  enum ConstrainedNameOptions { ExcludeCN = 0, IncludeCN = 1 };
    1.91 +
    1.92 +  // nssCert and childCert must be valid for the lifetime of BackCert
    1.93 +  BackCert(CERTCertificate* nssCert, BackCert* childCert,
    1.94 +           ConstrainedNameOptions cnOptions)
    1.95 +    : encodedBasicConstraints(nullptr)
    1.96 +    , encodedCertificatePolicies(nullptr)
    1.97 +    , encodedExtendedKeyUsage(nullptr)
    1.98 +    , encodedKeyUsage(nullptr)
    1.99 +    , encodedNameConstraints(nullptr)
   1.100 +    , encodedInhibitAnyPolicy(nullptr)
   1.101 +    , childCert(childCert)
   1.102 +    , nssCert(nssCert)
   1.103 +    , constrainedNames(nullptr)
   1.104 +    , cnOptions(cnOptions)
   1.105 +  {
   1.106 +  }
   1.107 +
   1.108 +  Result Init();
   1.109 +
   1.110 +  const SECItem* encodedBasicConstraints;
   1.111 +  const SECItem* encodedCertificatePolicies;
   1.112 +  const SECItem* encodedExtendedKeyUsage;
   1.113 +  const SECItem* encodedKeyUsage;
   1.114 +  const SECItem* encodedNameConstraints;
   1.115 +  const SECItem* encodedInhibitAnyPolicy;
   1.116 +
   1.117 +  BackCert* const childCert;
   1.118 +
   1.119 +  // Only non-const so that we can pass this to TrustDomain::IsRevoked,
   1.120 +  // which only takes a non-const pointer because VerifyEncodedOCSPResponse
   1.121 +  // requires it, and that is only because the implementation of
   1.122 +  // VerifyEncodedOCSPResponse does a CERT_DupCertificate. TODO: get rid
   1.123 +  // of that CERT_DupCertificate so that we can make all these things const.
   1.124 +  /*const*/ CERTCertificate* GetNSSCert() const { return nssCert; }
   1.125 +
   1.126 +  // Returns the names that should be considered when evaluating name
   1.127 +  // constraints. The list is constructed lazily and cached. The result is a
   1.128 +  // weak reference; do not try to free it, and do not hold long-lived
   1.129 +  // references to it.
   1.130 +  Result GetConstrainedNames(/*out*/ const CERTGeneralName** result);
   1.131 +
   1.132 +  // This is the only place where we should be dealing with non-const
   1.133 +  // CERTCertificates.
   1.134 +  Result PrependNSSCertToList(CERTCertList* results);
   1.135 +
   1.136 +  PLArenaPool* GetArena();
   1.137 +
   1.138 +private:
   1.139 +  CERTCertificate* nssCert;
   1.140 +
   1.141 +  ScopedPLArenaPool arena;
   1.142 +  CERTGeneralName* constrainedNames;
   1.143 +  ConstrainedNameOptions cnOptions;
   1.144 +
   1.145 +  BackCert(const BackCert&) /* = delete */;
   1.146 +  void operator=(const BackCert&); /* = delete */;
   1.147 +};
   1.148 +
   1.149 +} } // namespace mozilla::pkix
   1.150 +
   1.151 +#endif // mozilla_pkix__pkixutil_h

mercurial