Bug 1479787 - delete mozpkix, r=mt,keeler
authorFranziskus Kiefer <franziskuskiefer@gmail.com>
Tue, 02 Oct 2018 12:40:22 +0200
changeset 494986 fd2a0cc4b40afeb46ac88965237bfefaa58702ae
parent 494985 0e43215b1975317557dff4c9a8878b1189d3e14e
child 494987 432a98e50d2bfab224328254266069aef1a474cc
push id9984
push userffxbld-merge
push dateMon, 15 Oct 2018 21:07:35 +0000
treeherdermozilla-beta@183d27ea8570 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersmt, keeler
bugs1479787
milestone64.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1479787 - delete mozpkix, r=mt,keeler Differential Revision: https://phabricator.services.mozilla.com/D2722
security/pkix/include/pkix/Input.h
security/pkix/include/pkix/Result.h
security/pkix/include/pkix/Time.h
security/pkix/include/pkix/pkix.h
security/pkix/include/pkix/pkixnss.h
security/pkix/include/pkix/pkixtypes.h
security/pkix/lib/ScopedPtr.h
security/pkix/lib/pkixbuild.cpp
security/pkix/lib/pkixcert.cpp
security/pkix/lib/pkixcheck.cpp
security/pkix/lib/pkixcheck.h
security/pkix/lib/pkixder.cpp
security/pkix/lib/pkixder.h
security/pkix/lib/pkixnames.cpp
security/pkix/lib/pkixnss.cpp
security/pkix/lib/pkixocsp.cpp
security/pkix/lib/pkixresult.cpp
security/pkix/lib/pkixtime.cpp
security/pkix/lib/pkixutil.h
security/pkix/lib/pkixverify.cpp
security/pkix/moz.build
security/pkix/test/gtest/README.txt
security/pkix/test/gtest/moz.build
security/pkix/test/gtest/pkixbuild_tests.cpp
security/pkix/test/gtest/pkixcert_extension_tests.cpp
security/pkix/test/gtest/pkixcert_signature_algorithm_tests.cpp
security/pkix/test/gtest/pkixcheck_CheckExtendedKeyUsage_tests.cpp
security/pkix/test/gtest/pkixcheck_CheckIssuer_tests.cpp
security/pkix/test/gtest/pkixcheck_CheckKeyUsage_tests.cpp
security/pkix/test/gtest/pkixcheck_CheckSignatureAlgorithm_tests.cpp
security/pkix/test/gtest/pkixcheck_CheckValidity_tests.cpp
security/pkix/test/gtest/pkixcheck_ParseValidity_tests.cpp
security/pkix/test/gtest/pkixcheck_TLSFeaturesSatisfiedInternal_tests.cpp
security/pkix/test/gtest/pkixder_input_tests.cpp
security/pkix/test/gtest/pkixder_pki_types_tests.cpp
security/pkix/test/gtest/pkixder_universal_types_tests.cpp
security/pkix/test/gtest/pkixgtest.cpp
security/pkix/test/gtest/pkixgtest.h
security/pkix/test/gtest/pkixnames_tests.cpp
security/pkix/test/gtest/pkixocsp_CreateEncodedOCSPRequest_tests.cpp
security/pkix/test/gtest/pkixocsp_VerifyEncodedOCSPResponse.cpp
security/pkix/test/lib/moz.build
security/pkix/test/lib/pkixtestalg.cpp
security/pkix/test/lib/pkixtestnss.cpp
security/pkix/test/lib/pkixtestnss.h
security/pkix/test/lib/pkixtestutil.cpp
security/pkix/test/lib/pkixtestutil.h
security/pkix/tools/DottedOIDToCode.py
security/pkix/warnings.mozbuild
deleted file mode 100644
--- a/security/pkix/include/pkix/Input.h
+++ /dev/null
@@ -1,348 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef mozilla_pkix_Input_h
-#define mozilla_pkix_Input_h
-
-#include <algorithm>
-
-#include "pkix/Result.h"
-#include "stdint.h"
-
-namespace mozilla { namespace pkix {
-
-class Reader;
-
-// An Input is a safety-oriented immutable weak reference to a array of bytes
-// of a known size. The data can only be legally accessed by constructing a
-// Reader object, which guarantees all accesses to the data are memory safe.
-// Neither Input not Reader provide any facilities for modifying the data
-// they reference.
-//
-// Inputs are small and should usually be passed by value, not by reference,
-// though for inline functions the distinction doesn't matter:
-//
-//    Result GoodExample(Input input);
-//    Result BadExample(const Input& input);
-//    Result WorseExample(const uint8_t* input, size_t len);
-//
-// Note that in the example, GoodExample has the same performance
-// characteristics as WorseExample, but with much better safety guarantees.
-class Input final
-{
-public:
-  typedef uint16_t size_type;
-
-  // This constructor is useful for inputs that are statically known to be of a
-  // fixed size, e.g.:
-  //
-  //   static const uint8_t EXPECTED_BYTES[] = { 0x00, 0x01, 0x02 };
-  //   const Input expected(EXPECTED_BYTES);
-  //
-  // This is equivalent to (and preferred over):
-  //
-  //   static const uint8_t EXPECTED_BYTES[] = { 0x00, 0x01, 0x02 };
-  //   Input expected;
-  //   Result rv = expected.Init(EXPECTED_BYTES, sizeof EXPECTED_BYTES);
-  template <size_type N>
-  explicit Input(const uint8_t (&aData)[N])
-    : data(aData)
-    , len(N)
-  {
-  }
-
-  // Construct a valid, empty, Init-able Input.
-  Input()
-    : data(nullptr)
-    , len(0u)
-  {
-  }
-
-  // This is intentionally not explicit in order to allow value semantics.
-  Input(const Input&) = default;
-
-  // Initialize the input. data must be non-null and len must be less than
-  // 65536. Init may not be called more than once.
-  Result Init(const uint8_t* aData, size_t aLen)
-  {
-    if (this->data) {
-      // already initialized
-      return Result::FATAL_ERROR_INVALID_ARGS;
-    }
-    if (!aData || aLen > 0xffffu) {
-      // input too large
-      return Result::ERROR_BAD_DER;
-    }
-
-    this->data = aData;
-    this->len = aLen;
-
-    return Success;
-  }
-
-  // Initialize the input to be equivalent to the given input. Init may not be
-  // called more than once.
-  //
-  // This is basically operator=, but it wasn't given that name because
-  // normally callers do not check the result of operator=, and normally
-  // operator= can be used multiple times.
-  Result Init(Input other)
-  {
-    return Init(other.data, other.len);
-  }
-
-  // Returns the length of the input.
-  //
-  // Having the return type be size_type instead of size_t avoids the need for
-  // callers to ensure that the result is small enough.
-  size_type GetLength() const { return static_cast<size_type>(len); }
-
-  // Don't use this. It is here because we have some "friend" functions that we
-  // don't want to declare in this header file.
-  const uint8_t* UnsafeGetData() const { return data; }
-
-private:
-  const uint8_t* data;
-  size_t len;
-
-  void operator=(const Input&) = delete; // Use Init instead.
-};
-
-inline bool
-InputsAreEqual(const Input& a, const Input& b)
-{
-  return a.GetLength() == b.GetLength() &&
-         std::equal(a.UnsafeGetData(), a.UnsafeGetData() + a.GetLength(), b.UnsafeGetData());
-}
-
-// An Reader is a cursor/iterator through the contents of an Input, designed to
-// maximize safety during parsing while minimizing the performance cost of that
-// safety. In particular, all methods do strict bounds checking to ensure
-// buffer overflows are impossible, and they are all inline so that the
-// compiler can coalesce as many of those checks together as possible.
-//
-// In general, Reader allows for one byte of lookahead and no backtracking.
-// However, the Match* functions internally may have more lookahead.
-class Reader final
-{
-public:
-  Reader()
-    : input(nullptr)
-    , end(nullptr)
-  {
-  }
-
-  explicit Reader(Input aInput)
-    : input(aInput.UnsafeGetData())
-    , end(aInput.UnsafeGetData() + aInput.GetLength())
-  {
-  }
-
-  Result Init(Input aInput)
-  {
-    if (this->input) {
-      return Result::FATAL_ERROR_INVALID_ARGS;
-    }
-    this->input = aInput.UnsafeGetData();
-    this->end = aInput.UnsafeGetData() + aInput.GetLength();
-    return Success;
-  }
-
-  bool Peek(uint8_t expectedByte) const
-  {
-    return input < end && *input == expectedByte;
-  }
-
-  Result Read(uint8_t& out)
-  {
-    Result rv = EnsureLength(1);
-    if (rv != Success) {
-      return rv;
-    }
-    out = *input++;
-    return Success;
-  }
-
-  Result Read(uint16_t& out)
-  {
-    Result rv = EnsureLength(2);
-    if (rv != Success) {
-      return rv;
-    }
-    out = *input++;
-    out <<= 8u;
-    out |= *input++;
-    return Success;
-  }
-
-  template <Input::size_type N>
-  bool MatchRest(const uint8_t (&toMatch)[N])
-  {
-    // Normally we use EnsureLength which compares (input + len < end), but
-    // here we want to be sure that there is nothing following the matched
-    // bytes
-    if (static_cast<size_t>(end - input) != N) {
-      return false;
-    }
-    if (!std::equal(input, end, toMatch)) {
-      return false;
-    }
-    input = end;
-    return true;
-  }
-
-  bool MatchRest(Input toMatch)
-  {
-    // Normally we use EnsureLength which compares (input + len < end), but
-    // here we want to be sure that there is nothing following the matched
-    // bytes
-    size_t remaining = static_cast<size_t>(end - input);
-    if (toMatch.GetLength() != remaining) {
-      return false;
-    }
-    if (!std::equal(input, end, toMatch.UnsafeGetData())) {
-      return false;
-    }
-    input = end;
-    return true;
-  }
-
-  Result Skip(Input::size_type len)
-  {
-    Result rv = EnsureLength(len);
-    if (rv != Success) {
-      return rv;
-    }
-    input += len;
-    return Success;
-  }
-
-  Result Skip(Input::size_type len, Reader& skipped)
-  {
-    Result rv = EnsureLength(len);
-    if (rv != Success) {
-      return rv;
-    }
-    rv = skipped.Init(input, len);
-    if (rv != Success) {
-      return rv;
-    }
-    input += len;
-    return Success;
-  }
-
-  Result Skip(Input::size_type len, /*out*/ Input& skipped)
-  {
-    Result rv = EnsureLength(len);
-    if (rv != Success) {
-      return rv;
-    }
-    rv = skipped.Init(input, len);
-    if (rv != Success) {
-      return rv;
-    }
-    input += len;
-    return Success;
-  }
-
-  void SkipToEnd()
-  {
-    input = end;
-  }
-
-  Result SkipToEnd(/*out*/ Input& skipped)
-  {
-    return Skip(static_cast<Input::size_type>(end - input), skipped);
-  }
-
-  Result EnsureLength(Input::size_type len)
-  {
-    if (static_cast<size_t>(end - input) < len) {
-      return Result::ERROR_BAD_DER;
-    }
-    return Success;
-  }
-
-  bool AtEnd() const { return input == end; }
-
-  class Mark final
-  {
-  public:
-    Mark(const Mark&) = default; // Intentionally not explicit.
-  private:
-    friend class Reader;
-    Mark(const Reader& aInput, const uint8_t* aMark) : input(aInput), mark(aMark) { }
-    const Reader& input;
-    const uint8_t* const mark;
-    void operator=(const Mark&) = delete;
-  };
-
-  Mark GetMark() const { return Mark(*this, input); }
-
-  Result GetInput(const Mark& mark, /*out*/ Input& item)
-  {
-    if (&mark.input != this || mark.mark > input) {
-      return NotReached("invalid mark", Result::FATAL_ERROR_INVALID_ARGS);
-    }
-    return item.Init(mark.mark,
-                     static_cast<Input::size_type>(input - mark.mark));
-  }
-
-private:
-  Result Init(const uint8_t* data, Input::size_type len)
-  {
-    if (input) {
-      // already initialized
-      return Result::FATAL_ERROR_INVALID_ARGS;
-    }
-    input = data;
-    end = data + len;
-    return Success;
-  }
-
-  const uint8_t* input;
-  const uint8_t* end;
-
-  Reader(const Reader&) = delete;
-  void operator=(const Reader&) = delete;
-};
-
-inline bool
-InputContains(const Input& input, uint8_t toFind)
-{
-  Reader reader(input);
-  for (;;) {
-    uint8_t b;
-    if (reader.Read(b) != Success) {
-      return false;
-    }
-    if (b == toFind) {
-      return true;
-    }
-  }
-}
-
-} } // namespace mozilla::pkix
-
-#endif // mozilla_pkix_Input_h
deleted file mode 100644
--- a/security/pkix/include/pkix/Result.h
+++ /dev/null
@@ -1,241 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef mozilla_pkix_Result_h
-#define mozilla_pkix_Result_h
-
-#include <cassert>
-
-namespace mozilla { namespace pkix {
-
-static const unsigned int FATAL_ERROR_FLAG = 0x800;
-
-// ----------------------------------------------------------------------------
-// SELECTED ERROR CODE EXPLANATIONS
-//
-// Result::ERROR_UNTRUSTED_CERT
-//         means that the end-entity certificate was actively distrusted.
-// Result::ERROR_UNTRUSTED_ISSUER
-//         means that path building failed because of active distrust.
-// Result::ERROR_INVALID_DER_TIME
-//         means the DER-encoded time was unexpected, such as being before the
-//         UNIX epoch (allowed by X500, but not valid here).
-// Result::ERROR_EXPIRED_CERTIFICATE
-//         means the end entity certificate expired.
-// Result::ERROR_EXPIRED_ISSUER_CERTIFICATE
-//         means the CA certificate expired.
-// Result::ERROR_UNKNOWN_ISSUER
-//         means that the CA could not be found in the root store.
-// Result::ERROR_POLICY_VALIDATION_FAILED
-//         means that an encoded policy could not be applied or wasn't present
-//         when expected. Usually this is in the context of Extended Validation.
-// Result::ERROR_BAD_CERT_DOMAIN
-//         means that the certificate's name couldn't be matched to the
-//         reference identifier.
-// Result::ERROR_CERT_NOT_IN_NAME_SPACE
-//         typically means the certificate violates name constraints applied
-//         by the issuer.
-// Result::ERROR_BAD_DER
-//         means the input was improperly encoded.
-// Result::ERROR_UNKNOWN_ERROR
-//         means that an external library (NSS) provided an error we didn't
-//         anticipate. See the map below in Result.h to add new ones.
-// Result::FATAL_ERROR_LIBRARY_FAILURE
-//         is an unexpected fatal error indicating a library had an unexpected
-//         failure, and we can't proceed.
-// Result::FATAL_ERROR_INVALID_ARGS
-//         means that we violated our own expectations on inputs and there's a
-//         bug somewhere.
-// Result::FATAL_ERROR_INVALID_STATE
-//         means that we violated our own expectations on state and there's a
-//         bug somewhere.
-// Result::FATAL_ERROR_NO_MEMORY
-//         means a memory allocation failed, prohibiting validation.
-// ----------------------------------------------------------------------------
-
-// The first argument to MOZILLA_PKIX_MAP() is used for building the mapping
-// from error code to error name in MapResultToName.
-//
-// The second argument is for defining the value for the enum literal in the
-// Result enum class.
-//
-// The third argument to MOZILLA_PKIX_MAP() is used, along with the first
-// argument, for maintaining the mapping of mozilla::pkix error codes to
-// NSS/NSPR error codes in pkixnss.cpp.
-#define MOZILLA_PKIX_MAP_LIST \
-    MOZILLA_PKIX_MAP(Success, 0, 0) \
-    MOZILLA_PKIX_MAP(ERROR_BAD_DER, 1, \
-                     SEC_ERROR_BAD_DER) \
-    MOZILLA_PKIX_MAP(ERROR_CA_CERT_INVALID, 2, \
-                     SEC_ERROR_CA_CERT_INVALID) \
-    MOZILLA_PKIX_MAP(ERROR_BAD_SIGNATURE, 3, \
-                     SEC_ERROR_BAD_SIGNATURE) \
-    MOZILLA_PKIX_MAP(ERROR_CERT_BAD_ACCESS_LOCATION, 4, \
-                     SEC_ERROR_CERT_BAD_ACCESS_LOCATION) \
-    MOZILLA_PKIX_MAP(ERROR_CERT_NOT_IN_NAME_SPACE, 5, \
-                     SEC_ERROR_CERT_NOT_IN_NAME_SPACE) \
-    MOZILLA_PKIX_MAP(ERROR_CERT_SIGNATURE_ALGORITHM_DISABLED, 6, \
-                     SEC_ERROR_CERT_SIGNATURE_ALGORITHM_DISABLED) \
-    MOZILLA_PKIX_MAP(ERROR_CONNECT_REFUSED, 7, \
-                     PR_CONNECT_REFUSED_ERROR) \
-    MOZILLA_PKIX_MAP(ERROR_EXPIRED_CERTIFICATE, 8, \
-                     SEC_ERROR_EXPIRED_CERTIFICATE) \
-    MOZILLA_PKIX_MAP(ERROR_EXTENSION_VALUE_INVALID, 9, \
-                     SEC_ERROR_EXTENSION_VALUE_INVALID) \
-    MOZILLA_PKIX_MAP(ERROR_INADEQUATE_CERT_TYPE, 10, \
-                     SEC_ERROR_INADEQUATE_CERT_TYPE) \
-    MOZILLA_PKIX_MAP(ERROR_INADEQUATE_KEY_USAGE, 11, \
-                     SEC_ERROR_INADEQUATE_KEY_USAGE) \
-    MOZILLA_PKIX_MAP(ERROR_INVALID_ALGORITHM, 12, \
-                     SEC_ERROR_INVALID_ALGORITHM) \
-    MOZILLA_PKIX_MAP(ERROR_INVALID_DER_TIME, 13, \
-                     SEC_ERROR_INVALID_TIME) \
-    MOZILLA_PKIX_MAP(ERROR_KEY_PINNING_FAILURE, 14, \
-                     MOZILLA_PKIX_ERROR_KEY_PINNING_FAILURE) \
-    MOZILLA_PKIX_MAP(ERROR_PATH_LEN_CONSTRAINT_INVALID, 15, \
-                     SEC_ERROR_PATH_LEN_CONSTRAINT_INVALID) \
-    MOZILLA_PKIX_MAP(ERROR_POLICY_VALIDATION_FAILED, 16, \
-                     SEC_ERROR_POLICY_VALIDATION_FAILED) \
-    MOZILLA_PKIX_MAP(ERROR_REVOKED_CERTIFICATE, 17, \
-                     SEC_ERROR_REVOKED_CERTIFICATE) \
-    MOZILLA_PKIX_MAP(ERROR_UNKNOWN_CRITICAL_EXTENSION, 18, \
-                     SEC_ERROR_UNKNOWN_CRITICAL_EXTENSION) \
-    MOZILLA_PKIX_MAP(ERROR_UNKNOWN_ERROR, 19, \
-                     PR_UNKNOWN_ERROR) \
-    MOZILLA_PKIX_MAP(ERROR_UNKNOWN_ISSUER, 20, \
-                     SEC_ERROR_UNKNOWN_ISSUER) \
-    MOZILLA_PKIX_MAP(ERROR_UNTRUSTED_CERT, 21, \
-                     SEC_ERROR_UNTRUSTED_CERT) \
-    MOZILLA_PKIX_MAP(ERROR_UNTRUSTED_ISSUER, 22, \
-                     SEC_ERROR_UNTRUSTED_ISSUER) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_BAD_SIGNATURE, 23, \
-                     SEC_ERROR_OCSP_BAD_SIGNATURE) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_INVALID_SIGNING_CERT, 24, \
-                     SEC_ERROR_OCSP_INVALID_SIGNING_CERT) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_MALFORMED_REQUEST, 25, \
-                     SEC_ERROR_OCSP_MALFORMED_REQUEST) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_MALFORMED_RESPONSE, 26, \
-                     SEC_ERROR_OCSP_MALFORMED_RESPONSE) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_OLD_RESPONSE, 27, \
-                     SEC_ERROR_OCSP_OLD_RESPONSE) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_REQUEST_NEEDS_SIG, 28, \
-                     SEC_ERROR_OCSP_REQUEST_NEEDS_SIG) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_RESPONDER_CERT_INVALID, 29, \
-                     SEC_ERROR_OCSP_RESPONDER_CERT_INVALID) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_SERVER_ERROR, 30, \
-                     SEC_ERROR_OCSP_SERVER_ERROR) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_TRY_SERVER_LATER, 31, \
-                     SEC_ERROR_OCSP_TRY_SERVER_LATER) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_UNAUTHORIZED_REQUEST, 32, \
-                     SEC_ERROR_OCSP_UNAUTHORIZED_REQUEST) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_UNKNOWN_RESPONSE_STATUS, 33, \
-                     SEC_ERROR_OCSP_UNKNOWN_RESPONSE_STATUS) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_UNKNOWN_CERT, 34, \
-                     SEC_ERROR_OCSP_UNKNOWN_CERT) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_FUTURE_RESPONSE, 35, \
-                     SEC_ERROR_OCSP_FUTURE_RESPONSE) \
-    MOZILLA_PKIX_MAP(ERROR_INVALID_KEY, 36, \
-                     SEC_ERROR_INVALID_KEY) \
-    MOZILLA_PKIX_MAP(ERROR_UNSUPPORTED_KEYALG, 37, \
-                     SEC_ERROR_UNSUPPORTED_KEYALG) \
-    MOZILLA_PKIX_MAP(ERROR_EXPIRED_ISSUER_CERTIFICATE, 38, \
-                     SEC_ERROR_EXPIRED_ISSUER_CERTIFICATE) \
-    MOZILLA_PKIX_MAP(ERROR_CA_CERT_USED_AS_END_ENTITY, 39, \
-                     MOZILLA_PKIX_ERROR_CA_CERT_USED_AS_END_ENTITY) \
-    MOZILLA_PKIX_MAP(ERROR_INADEQUATE_KEY_SIZE, 40, \
-                     MOZILLA_PKIX_ERROR_INADEQUATE_KEY_SIZE) \
-    MOZILLA_PKIX_MAP(ERROR_V1_CERT_USED_AS_CA, 41, \
-                     MOZILLA_PKIX_ERROR_V1_CERT_USED_AS_CA) \
-    MOZILLA_PKIX_MAP(ERROR_BAD_CERT_DOMAIN, 42, \
-                     SSL_ERROR_BAD_CERT_DOMAIN) \
-    MOZILLA_PKIX_MAP(ERROR_NO_RFC822NAME_MATCH, 43, \
-                     MOZILLA_PKIX_ERROR_NO_RFC822NAME_MATCH) \
-    MOZILLA_PKIX_MAP(ERROR_UNSUPPORTED_ELLIPTIC_CURVE, 44, \
-                     SEC_ERROR_UNSUPPORTED_ELLIPTIC_CURVE) \
-    MOZILLA_PKIX_MAP(ERROR_NOT_YET_VALID_CERTIFICATE, 45, \
-                     MOZILLA_PKIX_ERROR_NOT_YET_VALID_CERTIFICATE) \
-    MOZILLA_PKIX_MAP(ERROR_NOT_YET_VALID_ISSUER_CERTIFICATE, 46, \
-                     MOZILLA_PKIX_ERROR_NOT_YET_VALID_ISSUER_CERTIFICATE) \
-    MOZILLA_PKIX_MAP(ERROR_UNSUPPORTED_EC_POINT_FORM, 47, \
-                     SEC_ERROR_UNSUPPORTED_EC_POINT_FORM) \
-    MOZILLA_PKIX_MAP(ERROR_SIGNATURE_ALGORITHM_MISMATCH, 48, \
-                     MOZILLA_PKIX_ERROR_SIGNATURE_ALGORITHM_MISMATCH) \
-    MOZILLA_PKIX_MAP(ERROR_OCSP_RESPONSE_FOR_CERT_MISSING, 49, \
-                     MOZILLA_PKIX_ERROR_OCSP_RESPONSE_FOR_CERT_MISSING) \
-    MOZILLA_PKIX_MAP(ERROR_VALIDITY_TOO_LONG, 50, \
-                     MOZILLA_PKIX_ERROR_VALIDITY_TOO_LONG) \
-    MOZILLA_PKIX_MAP(ERROR_REQUIRED_TLS_FEATURE_MISSING, 51, \
-                     MOZILLA_PKIX_ERROR_REQUIRED_TLS_FEATURE_MISSING) \
-    MOZILLA_PKIX_MAP(ERROR_INVALID_INTEGER_ENCODING, 52, \
-                     MOZILLA_PKIX_ERROR_INVALID_INTEGER_ENCODING) \
-    MOZILLA_PKIX_MAP(ERROR_EMPTY_ISSUER_NAME, 53, \
-                     MOZILLA_PKIX_ERROR_EMPTY_ISSUER_NAME) \
-    MOZILLA_PKIX_MAP(ERROR_ADDITIONAL_POLICY_CONSTRAINT_FAILED, 54, \
-                     MOZILLA_PKIX_ERROR_ADDITIONAL_POLICY_CONSTRAINT_FAILED) \
-    MOZILLA_PKIX_MAP(ERROR_SELF_SIGNED_CERT, 55, \
-                     MOZILLA_PKIX_ERROR_SELF_SIGNED_CERT) \
-    MOZILLA_PKIX_MAP(ERROR_MITM_DETECTED, 56, \
-                     MOZILLA_PKIX_ERROR_MITM_DETECTED) \
-    MOZILLA_PKIX_MAP(FATAL_ERROR_INVALID_ARGS, FATAL_ERROR_FLAG | 1, \
-                     SEC_ERROR_INVALID_ARGS) \
-    MOZILLA_PKIX_MAP(FATAL_ERROR_INVALID_STATE, FATAL_ERROR_FLAG | 2, \
-                     PR_INVALID_STATE_ERROR) \
-    MOZILLA_PKIX_MAP(FATAL_ERROR_LIBRARY_FAILURE, FATAL_ERROR_FLAG | 3, \
-                     SEC_ERROR_LIBRARY_FAILURE) \
-    MOZILLA_PKIX_MAP(FATAL_ERROR_NO_MEMORY, FATAL_ERROR_FLAG | 4, \
-                     SEC_ERROR_NO_MEMORY) \
-    /* nothing here */
-
-enum class Result
-{
-#define MOZILLA_PKIX_MAP(name, value, nss_name) name = value,
-  MOZILLA_PKIX_MAP_LIST
-#undef MOZILLA_PKIX_MAP
-};
-
-// Returns the stringified name of the given result, e.g. "Result::Success",
-// or nullptr if result is unknown (invalid).
-const char* MapResultToName(Result result);
-
-// We write many comparisons as (x != Success), and this shortened name makes
-// those comparisons clearer, especially because the shortened name often
-// results in less line wrapping.
-static const Result Success = Result::Success;
-
-inline bool
-IsFatalError(Result rv)
-{
-  return (static_cast<unsigned int>(rv) & FATAL_ERROR_FLAG) != 0;
-}
-
-inline Result
-NotReached(const char* /*explanation*/, Result result)
-{
-  assert(false);
-  return result;
-}
-
-} } // namespace mozilla::pkix
-
-#endif // mozilla_pkix_Result_h
deleted file mode 100644
--- a/security/pkix/include/pkix/Time.h
+++ /dev/null
@@ -1,155 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2014 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef mozilla_pkix_Time_h
-#define mozilla_pkix_Time_h
-
-#include <ctime>
-#include <limits>
-#include <stdint.h>
-
-#include "pkix/Result.h"
-
-namespace mozilla { namespace pkix {
-
-// Time with a range from the first second of year 0 (AD) through at least the
-// last second of year 9999, which is the range of legal times in X.509 and
-// OCSP. This type has second-level precision. The time zone is always UTC.
-//
-// Pass by value, not by reference.
-class Time final
-{
-public:
-  // Construct an uninitialized instance.
-  //
-  // This will fail to compile because there is no default constructor:
-  //    Time x;
-  //
-  // This will succeed, leaving the time uninitialized:
-  //    Time x(Time::uninitialized);
-  enum Uninitialized { uninitialized };
-  explicit Time(Uninitialized) { }
-
-  bool operator==(const Time& other) const
-  {
-    return elapsedSecondsAD == other.elapsedSecondsAD;
-  }
-  bool operator>(const Time& other) const
-  {
-    return elapsedSecondsAD > other.elapsedSecondsAD;
-  }
-  bool operator>=(const Time& other) const
-  {
-    return elapsedSecondsAD >= other.elapsedSecondsAD;
-  }
-  bool operator<(const Time& other) const
-  {
-    return elapsedSecondsAD < other.elapsedSecondsAD;
-  }
-  bool operator<=(const Time& other) const
-  {
-    return elapsedSecondsAD <= other.elapsedSecondsAD;
-  }
-
-  Result AddSeconds(uint64_t seconds)
-  {
-    if (std::numeric_limits<uint64_t>::max() - elapsedSecondsAD
-          < seconds) {
-      return Result::FATAL_ERROR_INVALID_ARGS; // integer overflow
-    }
-    elapsedSecondsAD += seconds;
-    return Success;
-  }
-
-  Result SubtractSeconds(uint64_t seconds)
-  {
-    if (seconds > elapsedSecondsAD) {
-      return Result::FATAL_ERROR_INVALID_ARGS; // integer overflow
-    }
-    elapsedSecondsAD -= seconds;
-    return Success;
-  }
-
-  static const uint64_t ONE_DAY_IN_SECONDS
-    = UINT64_C(24) * UINT64_C(60) * UINT64_C(60);
-
-private:
-  // This constructor is hidden to prevent accidents like this:
-  //
-  //    Time foo(time_t t)
-  //    {
-  //      // WRONG! 1970-01-01-00:00:00 == time_t(0), but not Time(0)!
-  //      return Time(t);
-  //    }
-  explicit Time(uint64_t aElapsedSecondsAD)
-    : elapsedSecondsAD(aElapsedSecondsAD)
-  {
-  }
-  friend Time TimeFromElapsedSecondsAD(uint64_t);
-  friend class Duration;
-
-  uint64_t elapsedSecondsAD;
-};
-
-inline Time TimeFromElapsedSecondsAD(uint64_t aElapsedSecondsAD)
-{
-  return Time(aElapsedSecondsAD);
-}
-
-Time Now();
-
-// Note the epoch is the unix epoch (ie 00:00:00 UTC, 1 January 1970)
-Time TimeFromEpochInSeconds(uint64_t secondsSinceEpoch);
-
-class Duration final
-{
-public:
-  Duration(Time timeA, Time timeB)
-    : durationInSeconds(timeA < timeB
-                        ? timeB.elapsedSecondsAD - timeA.elapsedSecondsAD
-                        : timeA.elapsedSecondsAD - timeB.elapsedSecondsAD)
-  {
-  }
-
-  explicit Duration(uint64_t aDurationInSeconds)
-    : durationInSeconds(aDurationInSeconds)
-  {
-  }
-
-  bool operator>(const Duration& other) const
-  {
-    return durationInSeconds > other.durationInSeconds;
-  }
-  bool operator<(const Duration& other) const
-  {
-    return durationInSeconds < other.durationInSeconds;
-  }
-
-private:
-  uint64_t durationInSeconds;
-};
-
-} } // namespace mozilla::pkix
-
-#endif // mozilla_pkix_Time_h
deleted file mode 100644
--- a/security/pkix/include/pkix/pkix.h
+++ /dev/null
@@ -1,161 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef mozilla_pkix_pkix_h
-#define mozilla_pkix_pkix_h
-
-#include "pkixtypes.h"
-
-namespace mozilla { namespace pkix {
-
-// ----------------------------------------------------------------------------
-// LIMITED SUPPORT FOR CERTIFICATE POLICIES
-//
-// If SEC_OID_X509_ANY_POLICY is passed as the value of the requiredPolicy
-// parameter then all policy validation will be skipped. Otherwise, path
-// building and validation will be done for the given policy.
-//
-// In RFC 5280 terms:
-//
-//    * user-initial-policy-set = { requiredPolicy }.
-//    * initial-explicit-policy = true
-//    * initial-any-policy-inhibit = false
-//
-// We allow intermediate cerificates to use this extension but since
-// we do not process the inhibit anyPolicy extesion we will fail if this
-// extension is present. TODO(bug 989051)
-// Because we force explicit policy and because we prohibit policy mapping, we
-// do not bother processing the policy mapping, or policy constraint.
-//
-// ----------------------------------------------------------------------------
-// ERROR RANKING
-//
-// BuildCertChain prioritizes certain checks ahead of others so that when a
-// certificate chain has multiple errors, the "most serious" error is
-// returned. In practice, this ranking of seriousness is tied directly to how
-// Firefox's certificate error override mechanism.
-//
-// The ranking is:
-//
-//    1. Active distrust (Result::ERROR_UNTRUSTED_CERT).
-//    2. Problems with issuer-independent properties for CA certificates.
-//    3. Unknown issuer (Result::ERROR_UNKNOWN_ISSUER).
-//    4. Problems with issuer-independent properties for EE certificates.
-//    5. Revocation.
-//
-// In particular, if BuildCertChain returns Result::ERROR_UNKNOWN_ISSUER then
-// the caller can call CERT_CheckCertValidTimes to determine if the certificate
-// is ALSO expired.
-//
-// It would be better if revocation were prioritized above expiration and
-// unknown issuer. However, it is impossible to do revocation checking without
-// knowing the issuer, since the issuer information is needed to validate the
-// revocation information. Also, generally revocation checking only works
-// during the validity period of the certificate.
-//
-// In general, when path building fails, BuildCertChain will return
-// Result::ERROR_UNKNOWN_ISSUER. However, if all attempted paths resulted in
-// the same error (which is trivially true when there is only one potential
-// path), more specific errors will be returned.
-//
-// ----------------------------------------------------------------------------
-// Meanings of specific error codes can be found in Result.h
-
-// This function attempts to find a trustworthy path from the supplied
-// certificate to a trust anchor. In the event that no trusted path is found,
-// the method returns an error result; the error ranking is described above.
-//
-// Parameters:
-//  time:
-//         Timestamp for which the chain should be valid; this is useful to
-//         analyze whether a record was trustworthy when it was made.
-//  requiredKeyUsageIfPresent:
-//         What key usage bits must be set, if the extension is present at all,
-//         to be considered a valid chain. Multiple values should be OR'd
-//         together. If you don't want to specify anything, use
-//         KeyUsage::noParticularKeyUsageRequired.
-//  requiredEKUIfPresent:
-//         What extended key usage bits must be set, if the EKU extension
-//         exists, to be considered a valid chain. Multiple values should be
-//         OR'd together. If you don't want to specify anything, use
-//         KeyPurposeId::anyExtendedKeyUsage.
-//  requiredPolicy:
-//         This is the policy to apply; typically included in EV certificates.
-//         If there is no policy, pass in CertPolicyId::anyPolicy.
-Result BuildCertChain(TrustDomain& trustDomain, Input cert,
-                      Time time, EndEntityOrCA endEntityOrCA,
-                      KeyUsage requiredKeyUsageIfPresent,
-                      KeyPurposeId requiredEKUIfPresent,
-                      const CertPolicyId& requiredPolicy,
-                      /*optional*/ const Input* stapledOCSPResponse);
-
-// Verify that the given end-entity cert, which is assumed to have been already
-// validated with BuildCertChain, is valid for the given hostname. The matching
-// function attempts to implement RFC 6125 with a couple of differences:
-// - IP addresses are out of scope of RFC 6125, but this method accepts them for
-//   backward compatibility (see SearchNames in pkixnames.cpp)
-// - A wildcard in a DNS-ID may only appear as the entirety of the first label.
-Result CheckCertHostname(Input cert, Input hostname,
-                         NameMatchingPolicy& nameMatchingPolicy);
-
-// Construct an RFC-6960-encoded OCSP request, ready for submission to a
-// responder, for the provided CertID. The request has no extensions.
-static const size_t OCSP_REQUEST_MAX_LENGTH = 127;
-Result CreateEncodedOCSPRequest(TrustDomain& trustDomain,
-                                const CertID& certID,
-                                /*out*/ uint8_t (&out)[OCSP_REQUEST_MAX_LENGTH],
-                                /*out*/ size_t& outLen);
-
-// The out parameter expired will be true if the response has expired. If the
-// response also indicates a revoked or unknown certificate, that error
-// will be returned. Otherwise, Result::ERROR_OCSP_OLD_RESPONSE will be
-// returned for an expired response.
-//
-// The optional parameter thisUpdate will be the thisUpdate value of
-// the encoded response if it is considered trustworthy. Only
-// good, unknown, or revoked responses that verify correctly are considered
-// trustworthy. If the response is not trustworthy, thisUpdate will be 0.
-// Similarly, the optional parameter validThrough will be the time through
-// which the encoded response is considered trustworthy (that is, as long as
-// the given time at which to validate is less than or equal to validThrough,
-// the response will be considered trustworthy).
-Result VerifyEncodedOCSPResponse(TrustDomain& trustDomain,
-                                 const CertID& certID, Time time,
-                                 uint16_t maxLifetimeInDays,
-                                 Input encodedResponse,
-                       /* out */ bool& expired,
-              /* optional out */ Time* thisUpdate = nullptr,
-              /* optional out */ Time* validThrough = nullptr);
-
-// Check that the TLSFeature extensions in a given end-entity cert (which is
-// assumed to have been already validated with BuildCertChain) are satisfied.
-// The only feature which we cancurrently process a requirement for is
-// status_request (OCSP stapling) so we reject any extension that specifies a
-// requirement for another value. Empty extensions are also rejected.
-Result CheckTLSFeaturesAreSatisfied(Input& cert,
-                                    const Input* stapledOCSPResponse);
-
-} } // namespace mozilla::pkix
-
-#endif // mozilla_pkix_pkix_h
deleted file mode 100644
--- a/security/pkix/include/pkix/pkixnss.h
+++ /dev/null
@@ -1,112 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef mozilla_pkix_pkixnss_h
-#define mozilla_pkix_pkixnss_h
-
-#include "pkixtypes.h"
-#include "prerror.h"
-#include "seccomon.h"
-
-namespace mozilla { namespace pkix {
-
-// Verifies the PKCS#1.5 signature on the given data using the given RSA public
-// key.
-Result VerifyRSAPKCS1SignedDigestNSS(const SignedDigest& sd,
-                                     Input subjectPublicKeyInfo,
-                                     void* pkcs11PinArg);
-
-// Verifies the ECDSA signature on the given data using the given ECC public
-// key.
-Result VerifyECDSASignedDigestNSS(const SignedDigest& sd,
-                                  Input subjectPublicKeyInfo,
-                                  void* pkcs11PinArg);
-
-// Computes the digest of the given data using the given digest algorithm.
-//
-// item contains the data to hash.
-// digestBuf must point to a buffer to where the digest will be written.
-// digestBufLen must be the size of the buffer, which must be exactly equal
-//              to the size of the digest output (20 for SHA-1, 32 for SHA-256,
-//              etc.)
-//
-// TODO: Taking the output buffer as (uint8_t*, size_t) is counter to our
-// other, extensive, memory safety efforts in mozilla::pkix, and we should find
-// a way to provide a more-obviously-safe interface.
-Result DigestBufNSS(Input item,
-                    DigestAlgorithm digestAlg,
-                    /*out*/ uint8_t* digestBuf,
-                    size_t digestBufLen);
-
-Result MapPRErrorCodeToResult(PRErrorCode errorCode);
-PRErrorCode MapResultToPRErrorCode(Result result);
-
-// The error codes within each module must fit in 16 bits. We want these
-// errors to fit in the same module as the NSS errors but not overlap with
-// any of them. Converting an NSS SEC, NSS SSL, or PSM error to an NS error
-// involves negating the value of the error and then synthesizing an error
-// in the NS_ERROR_MODULE_SECURITY module. Hence, PSM errors will start at
-// a negative value that both doesn't overlap with the current value
-// ranges for NSS errors and that will fit in 16 bits when negated.
-static const PRErrorCode ERROR_BASE = -0x4000;
-static const PRErrorCode ERROR_LIMIT = ERROR_BASE + 1000;
-
-enum ErrorCode
-{
-  MOZILLA_PKIX_ERROR_KEY_PINNING_FAILURE = ERROR_BASE + 0,
-  MOZILLA_PKIX_ERROR_CA_CERT_USED_AS_END_ENTITY = ERROR_BASE + 1,
-  MOZILLA_PKIX_ERROR_INADEQUATE_KEY_SIZE = ERROR_BASE + 2,
-  MOZILLA_PKIX_ERROR_V1_CERT_USED_AS_CA = ERROR_BASE + 3,
-  MOZILLA_PKIX_ERROR_NO_RFC822NAME_MATCH = ERROR_BASE + 4,
-  MOZILLA_PKIX_ERROR_NOT_YET_VALID_CERTIFICATE = ERROR_BASE + 5,
-  MOZILLA_PKIX_ERROR_NOT_YET_VALID_ISSUER_CERTIFICATE = ERROR_BASE + 6,
-  MOZILLA_PKIX_ERROR_SIGNATURE_ALGORITHM_MISMATCH = ERROR_BASE + 7,
-  MOZILLA_PKIX_ERROR_OCSP_RESPONSE_FOR_CERT_MISSING = ERROR_BASE + 8,
-  MOZILLA_PKIX_ERROR_VALIDITY_TOO_LONG = ERROR_BASE + 9,
-  MOZILLA_PKIX_ERROR_REQUIRED_TLS_FEATURE_MISSING = ERROR_BASE + 10,
-  MOZILLA_PKIX_ERROR_INVALID_INTEGER_ENCODING = ERROR_BASE + 11,
-  MOZILLA_PKIX_ERROR_EMPTY_ISSUER_NAME = ERROR_BASE + 12,
-  MOZILLA_PKIX_ERROR_ADDITIONAL_POLICY_CONSTRAINT_FAILED = ERROR_BASE + 13,
-  MOZILLA_PKIX_ERROR_SELF_SIGNED_CERT = ERROR_BASE + 14,
-  MOZILLA_PKIX_ERROR_MITM_DETECTED = ERROR_BASE + 15,
-  END_OF_LIST
-};
-
-void RegisterErrorTable();
-
-inline SECItem UnsafeMapInputToSECItem(Input input)
-{
-  SECItem result = {
-    siBuffer,
-    const_cast<uint8_t*>(input.UnsafeGetData()),
-    input.GetLength()
-  };
-  static_assert(sizeof(decltype(input.GetLength())) <= sizeof(result.len),
-                "input.GetLength() must fit in a SECItem");
-  return result;
-}
-
-} } // namespace mozilla::pkix
-
-#endif // mozilla_pkix_pkixnss_h
deleted file mode 100644
--- a/security/pkix/include/pkix/pkixtypes.h
+++ /dev/null
@@ -1,411 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef mozilla_pkix_pkixtypes_h
-#define mozilla_pkix_pkixtypes_h
-
-#include "pkix/Input.h"
-#include "pkix/Time.h"
-#include "stdint.h"
-
-namespace mozilla { namespace pkix {
-
-enum class DigestAlgorithm
-{
-  sha512 = 1,
-  sha384 = 2,
-  sha256 = 3,
-  sha1 = 4,
-};
-
-enum class NamedCurve
-{
-  // secp521r1 (OID 1.3.132.0.35, RFC 5480)
-  secp521r1 = 1,
-
-  // secp384r1 (OID 1.3.132.0.34, RFC 5480)
-  secp384r1 = 2,
-
-  // secp256r1 (OID 1.2.840.10045.3.1.7, RFC 5480)
-  secp256r1 = 3,
-};
-
-struct SignedDigest final
-{
-  Input digest;
-  DigestAlgorithm digestAlgorithm;
-  Input signature;
-
-  void operator=(const SignedDigest&) = delete;
-};
-
-enum class EndEntityOrCA { MustBeEndEntity = 0, MustBeCA = 1 };
-
-enum class KeyUsage : uint8_t
-{
-  digitalSignature = 0,
-  nonRepudiation   = 1,
-  keyEncipherment  = 2,
-  dataEncipherment = 3,
-  keyAgreement     = 4,
-  keyCertSign      = 5,
-  // cRLSign       = 6,
-  // encipherOnly  = 7,
-  // decipherOnly  = 8,
-  noParticularKeyUsageRequired = 0xff,
-};
-
-enum class KeyPurposeId
-{
-  anyExtendedKeyUsage = 0,
-  id_kp_serverAuth = 1,           // id-kp-serverAuth
-  id_kp_clientAuth = 2,           // id-kp-clientAuth
-  id_kp_codeSigning = 3,          // id-kp-codeSigning
-  id_kp_emailProtection = 4,      // id-kp-emailProtection
-  id_kp_OCSPSigning = 9,          // id-kp-OCSPSigning
-};
-
-struct CertPolicyId final
-{
-  uint16_t numBytes;
-  static const uint16_t MAX_BYTES = 24;
-  uint8_t bytes[MAX_BYTES];
-
-  bool IsAnyPolicy() const;
-  bool operator==(const CertPolicyId& other) const;
-
-  static const CertPolicyId anyPolicy;
-};
-
-enum class TrustLevel
-{
-  TrustAnchor = 1,        // certificate is a trusted root CA certificate or
-                          // equivalent *for the given policy*.
-  ActivelyDistrusted = 2, // certificate is known to be bad
-  InheritsTrust = 3       // certificate must chain to a trust anchor
-};
-
-// Extensions extracted during the verification flow.
-// See TrustDomain::NoteAuxiliaryExtension.
-enum class AuxiliaryExtension
-{
-  // Certificate Transparency data, specifically Signed Certificate
-  // Timestamps (SCTs). See RFC 6962.
-
-  // SCT list embedded in the end entity certificate. Called by BuildCertChain
-  // after the certificate containing the SCTs has passed the revocation checks.
-  EmbeddedSCTList = 1,
-  // SCT list from OCSP response. Called by VerifyEncodedOCSPResponse
-  // when its result is a success and the SCT list is present.
-  SCTListFromOCSPResponse = 2
-};
-
-// CertID references the information needed to do revocation checking for the
-// certificate issued by the given issuer with the given serial number.
-//
-// issuer must be the DER-encoded issuer field from the certificate for which
-// revocation checking is being done, **NOT** the subject field of the issuer
-// certificate. (Those two fields must be equal to each other, but they may not
-// be encoded exactly the same, and the encoding matters for OCSP.)
-// issuerSubjectPublicKeyInfo is the entire DER-encoded subjectPublicKeyInfo
-// field from the issuer's certificate. serialNumber is the entire DER-encoded
-// serial number from the subject certificate (the certificate for which we are
-// checking the revocation status).
-struct CertID final
-{
-public:
-  CertID(Input aIssuer, Input aIssuerSubjectPublicKeyInfo, Input aSerialNumber)
-    : issuer(aIssuer)
-    , issuerSubjectPublicKeyInfo(aIssuerSubjectPublicKeyInfo)
-    , serialNumber(aSerialNumber)
-  {
-  }
-  const Input issuer;
-  const Input issuerSubjectPublicKeyInfo;
-  const Input serialNumber;
-
-  void operator=(const CertID&) = delete;
-};
-
-class DERArray
-{
-public:
-  // Returns the number of DER-encoded items in the array.
-  virtual size_t GetLength() const = 0;
-
-  // Returns a weak (non-owning) pointer the ith DER-encoded item in the array
-  // (0-indexed). The result is guaranteed to be non-null if i < GetLength(),
-  // and the result is guaranteed to be nullptr if i >= GetLength().
-  virtual const Input* GetDER(size_t i) const = 0;
-protected:
-  DERArray() { }
-  virtual ~DERArray() { }
-};
-
-// Applications control the behavior of path building and verification by
-// implementing the TrustDomain interface. The TrustDomain is used for all
-// cryptography and for determining which certificates are trusted or
-// distrusted.
-class TrustDomain
-{
-public:
-  virtual ~TrustDomain() { }
-
-  // Determine the level of trust in the given certificate for the given role.
-  // This will be called for every certificate encountered during path
-  // building.
-  //
-  // When policy.IsAnyPolicy(), then no policy-related checking should be done.
-  // When !policy.IsAnyPolicy(), then GetCertTrust MUST NOT return with
-  // trustLevel == TrustAnchor unless the given cert is considered a trust
-  // anchor *for that policy*. In particular, if the user has marked an
-  // intermediate certificate as trusted, but that intermediate isn't in the
-  // list of EV roots, then GetCertTrust must result in
-  // trustLevel == InheritsTrust instead of trustLevel == TrustAnchor
-  // (assuming the candidate cert is not actively distrusted).
-  virtual Result GetCertTrust(EndEntityOrCA endEntityOrCA,
-                              const CertPolicyId& policy,
-                              Input candidateCertDER,
-                              /*out*/ TrustLevel& trustLevel) = 0;
-
-  class IssuerChecker
-  {
-  public:
-    // potentialIssuerDER is the complete DER encoding of the certificate to
-    // be checked as a potential issuer.
-    //
-    // If additionalNameConstraints is not nullptr then it must point to an
-    // encoded NameConstraints extension value; in that case, those name
-    // constraints will be checked in addition to any any name constraints
-    // contained in potentialIssuerDER.
-    virtual Result Check(Input potentialIssuerDER,
-            /*optional*/ const Input* additionalNameConstraints,
-                 /*out*/ bool& keepGoing) = 0;
-  protected:
-    IssuerChecker();
-    virtual ~IssuerChecker();
-
-    IssuerChecker(const IssuerChecker&) = delete;
-    void operator=(const IssuerChecker&) = delete;
-  };
-
-  // Search for a CA certificate with the given name. The implementation must
-  // call checker.Check with the DER encoding of the potential issuer
-  // certificate. The implementation must follow these rules:
-  //
-  // * The implementation must be reentrant and must limit the amount of stack
-  //   space it uses; see the note on reentrancy and stack usage below.
-  // * When checker.Check does not return Success then immediately return its
-  //   return value.
-  // * When checker.Check returns Success and sets keepGoing = false, then
-  //   immediately return Success.
-  // * When checker.Check returns Success and sets keepGoing = true, then
-  //   call checker.Check again with a different potential issuer certificate,
-  //   if any more are available.
-  // * When no more potential issuer certificates are available, return
-  //   Success.
-  // * Don't call checker.Check with the same potential issuer certificate more
-  //   than once in a given call of FindIssuer.
-  // * The given time parameter may be used to filter out certificates that are
-  //   not valid at the given time, or it may be ignored.
-  //
-  // Note on reentrancy and stack usage: checker.Check will attempt to
-  // recursively build a certificate path from the potential issuer it is given
-  // to a trusted root, as determined by this TrustDomain. That means that
-  // checker.Check may call any/all of the methods on this TrustDomain. In
-  // particular, there will be call stacks that look like this:
-  //
-  //    BuildCertChain
-  //      [...]
-  //        TrustDomain::FindIssuer
-  //          [...]
-  //            IssuerChecker::Check
-  //              [...]
-  //                TrustDomain::FindIssuer
-  //                  [...]
-  //                    IssuerChecker::Check
-  //                      [...]
-  //
-  // checker.Check is responsible for limiting the recursion to a reasonable
-  // limit.
-  //
-  // checker.Check will verify that the subject's issuer field matches the
-  // potential issuer's subject field. It will also check that the potential
-  // issuer is valid at the given time. However, if the FindIssuer
-  // implementation has an efficient way of filtering potential issuers by name
-  // and/or validity period itself, then it is probably better for performance
-  // for it to do so.
-  virtual Result FindIssuer(Input encodedIssuerName,
-                            IssuerChecker& checker, Time time) = 0;
-
-  // Called as soon as we think we have a valid chain but before revocation
-  // checks are done. This function can be used to compute additional checks,
-  // especially checks that require the entire certificate chain. This callback
-  // can also be used to save a copy of the built certificate chain for later
-  // use.
-  //
-  // This function may be called multiple times, regardless of whether it
-  // returns success or failure. It is guaranteed that BuildCertChain will not
-  // return Success unless the last call to IsChainValid returns Success. Further,
-  // it is guaranteed that when BuildCertChain returns Success the last chain
-  // passed to IsChainValid is the valid chain that should be used for further
-  // operations that require the whole chain.
-  //
-  // Keep in mind, in particular, that if the application saves a copy of the
-  // certificate chain the last invocation of IsChainValid during a validation,
-  // it is still possible for BuildCertChain to fail, in which case the
-  // application must not assume anything about the validity of the last
-  // certificate chain passed to IsChainValid; especially, it would be very
-  // wrong to assume that the certificate chain is valid.
-  //
-  // certChain.GetDER(0) is the trust anchor.
-  virtual Result IsChainValid(const DERArray& certChain, Time time,
-                              const CertPolicyId& requiredPolicy) = 0;
-
-  virtual Result CheckRevocation(EndEntityOrCA endEntityOrCA,
-                                 const CertID& certID, Time time,
-                                 Duration validityDuration,
-                    /*optional*/ const Input* stapledOCSPresponse,
-                    /*optional*/ const Input* aiaExtension) = 0;
-
-  // Check that the given digest algorithm is acceptable for use in signatures.
-  //
-  // Return Success if the algorithm is acceptable,
-  // Result::ERROR_CERT_SIGNATURE_ALGORITHM_DISABLED if the algorithm is not
-  // acceptable, or another error code if another error occurred.
-  virtual Result CheckSignatureDigestAlgorithm(DigestAlgorithm digestAlg,
-                                               EndEntityOrCA endEntityOrCA,
-                                               Time notBefore) = 0;
-
-  // Check that the RSA public key size is acceptable.
-  //
-  // Return Success if the key size is acceptable,
-  // Result::ERROR_INADEQUATE_KEY_SIZE if the key size is not acceptable,
-  // or another error code if another error occurred.
-  virtual Result CheckRSAPublicKeyModulusSizeInBits(
-                   EndEntityOrCA endEntityOrCA,
-                   unsigned int modulusSizeInBits) = 0;
-
-  // Verify the given RSA PKCS#1.5 signature on the given digest using the
-  // given RSA public key.
-  //
-  // CheckRSAPublicKeyModulusSizeInBits will be called before calling this
-  // function, so it is not necessary to repeat those checks here. However,
-  // VerifyRSAPKCS1SignedDigest *is* responsible for doing the mathematical
-  // verification of the public key validity as specified in NIST SP 800-56A.
-  virtual Result VerifyRSAPKCS1SignedDigest(
-                   const SignedDigest& signedDigest,
-                   Input subjectPublicKeyInfo) = 0;
-
-  // Check that the given named ECC curve is acceptable for ECDSA signatures.
-  //
-  // Return Success if the curve is acceptable,
-  // Result::ERROR_UNSUPPORTED_ELLIPTIC_CURVE if the curve is not acceptable,
-  // or another error code if another error occurred.
-  virtual Result CheckECDSACurveIsAcceptable(EndEntityOrCA endEntityOrCA,
-                                             NamedCurve curve) = 0;
-
-  // Verify the given ECDSA signature on the given digest using the given ECC
-  // public key.
-  //
-  // CheckECDSACurveIsAcceptable will be called before calling this function,
-  // so it is not necessary to repeat that check here. However,
-  // VerifyECDSASignedDigest *is* responsible for doing the mathematical
-  // verification of the public key validity as specified in NIST SP 800-56A.
-  virtual Result VerifyECDSASignedDigest(const SignedDigest& signedDigest,
-                                         Input subjectPublicKeyInfo) = 0;
-
-  // Check that the validity duration is acceptable.
-  //
-  // Return Success if the validity duration is acceptable,
-  // Result::ERROR_VALIDITY_TOO_LONG if the validity duration is not acceptable,
-  // or another error code if another error occurred.
-  virtual Result CheckValidityIsAcceptable(Time notBefore, Time notAfter,
-                                           EndEntityOrCA endEntityOrCA,
-                                           KeyPurposeId keyPurpose) = 0;
-
-  // For compatibility, a CA certificate with an extended key usage that
-  // contains the id-Netscape-stepUp OID but does not contain the
-  // id-kp-serverAuth OID may be considered valid for issuing server auth
-  // certificates. This function allows TrustDomain implementations to control
-  // this setting based on the start of the validity period of the certificate
-  // in question.
-  virtual Result NetscapeStepUpMatchesServerAuth(Time notBefore,
-                                                 /*out*/ bool& matches) = 0;
-
-  // Some certificate or OCSP response extensions do not directly participate
-  // in the verification flow, but might still be of interest to the clients
-  // (notably Certificate Transparency data, RFC 6962). Such extensions are
-  // extracted and passed to this function for further processing.
-  virtual void NoteAuxiliaryExtension(AuxiliaryExtension extension,
-                                      Input extensionData) = 0;
-
-  // Compute a digest of the data in item using the given digest algorithm.
-  //
-  // item contains the data to hash.
-  // digestBuf points to a buffer to where the digest will be written.
-  // digestBufLen will be the size of the digest output (20 for SHA-1,
-  // 32 for SHA-256, etc.).
-  //
-  // TODO: Taking the output buffer as (uint8_t*, size_t) is counter to our
-  // other, extensive, memory safety efforts in mozilla::pkix, and we should
-  // find a way to provide a more-obviously-safe interface.
-  virtual Result DigestBuf(Input item,
-                           DigestAlgorithm digestAlg,
-                           /*out*/ uint8_t* digestBuf,
-                           size_t digestBufLen) = 0;
-protected:
-  TrustDomain() { }
-
-  TrustDomain(const TrustDomain&) = delete;
-  void operator=(const TrustDomain&) = delete;
-};
-
-enum class FallBackToSearchWithinSubject { No = 0, Yes = 1 };
-
-// Applications control the behavior of matching presented name information from
-// a certificate against a reference hostname by implementing the
-// NameMatchingPolicy interface. Used in concert with CheckCertHostname.
-class NameMatchingPolicy
-{
-public:
-  virtual ~NameMatchingPolicy() { }
-
-  // Given that the certificate in question has a notBefore field with the given
-  // value, should name matching fall back to searching within the subject
-  // common name field?
-  virtual Result FallBackToCommonName(
-    Time notBefore,
-    /*out*/ FallBackToSearchWithinSubject& fallBackToCommonName) = 0;
-
-protected:
-  NameMatchingPolicy() { }
-
-  NameMatchingPolicy(const NameMatchingPolicy&) = delete;
-  void operator=(const NameMatchingPolicy&) = delete;
-};
-
-} } // namespace mozilla::pkix
-
-#endif // mozilla_pkix_pkixtypes_h
deleted file mode 100644
--- a/security/pkix/lib/ScopedPtr.h
+++ /dev/null
@@ -1,83 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef mozilla_pkix_ScopedPtr_h
-#define mozilla_pkix_ScopedPtr_h
-
-namespace mozilla { namespace pkix {
-
-// A subset polyfill of std::unique_ptr that does not support move construction
-// or move assignment. This is used instead of std::unique_ptr because some
-// important toolchains still don't provide std::unique_ptr, including in
-// particular Android NDK projects with APP_STL=stlport_static or
-// ALL_STL=stlport_shared.
-template <typename T, void (&Destroyer)(T*)>
-class ScopedPtr final
-{
-public:
-  explicit ScopedPtr(T* value = nullptr) : mValue(value) { }
-
-  ScopedPtr(const ScopedPtr&) = delete;
-
-  ~ScopedPtr()
-  {
-    if (mValue) {
-      Destroyer(mValue);
-    }
-  }
-
-  void operator=(const ScopedPtr&) = delete;
-
-  T& operator*() const { return *mValue; }
-  T* operator->() const { return mValue; }
-
-  explicit operator bool() const { return mValue; }
-
-  T* get() const { return mValue; }
-
-  T* release()
-  {
-    T* result = mValue;
-    mValue = nullptr;
-    return result;
-  }
-
-  void reset(T* newValue = nullptr)
-  {
-    // The C++ standard requires std::unique_ptr to destroy the old value
-    // pointed to by mValue, if any, *after* assigning the new value to mValue.
-    T* oldValue = mValue;
-    mValue = newValue;
-    if (oldValue) {
-      Destroyer(oldValue);
-    }
-  }
-
-private:
-  T* mValue;
-};
-
-} } // namespace mozilla::pkix
-
-#endif // mozilla_pkix_ScopedPtr_h
deleted file mode 100644
--- a/security/pkix/lib/pkixbuild.cpp
+++ /dev/null
@@ -1,418 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "pkix/pkix.h"
-
-#include "pkixcheck.h"
-#include "pkixutil.h"
-
-namespace mozilla { namespace pkix {
-
-static Result BuildForward(TrustDomain& trustDomain,
-                           const BackCert& subject,
-                           Time time,
-                           KeyUsage requiredKeyUsageIfPresent,
-                           KeyPurposeId requiredEKUIfPresent,
-                           const CertPolicyId& requiredPolicy,
-                           /*optional*/ const Input* stapledOCSPResponse,
-                           unsigned int subCACount,
-                           unsigned int& buildForwardCallBudget);
-
-TrustDomain::IssuerChecker::IssuerChecker() { }
-TrustDomain::IssuerChecker::~IssuerChecker() { }
-
-// The implementation of TrustDomain::IssuerTracker is in a subclass only to
-// hide the implementation from external users.
-class PathBuildingStep final : public TrustDomain::IssuerChecker
-{
-public:
-  PathBuildingStep(TrustDomain& aTrustDomain, const BackCert& aSubject,
-                   Time aTime, KeyPurposeId aRequiredEKUIfPresent,
-                   const CertPolicyId& aRequiredPolicy,
-                   /*optional*/ const Input* aStapledOCSPResponse,
-                   unsigned int aSubCACount, Result aDeferredSubjectError,
-                   unsigned int& aBuildForwardCallBudget)
-    : trustDomain(aTrustDomain)
-    , subject(aSubject)
-    , time(aTime)
-    , requiredEKUIfPresent(aRequiredEKUIfPresent)
-    , requiredPolicy(aRequiredPolicy)
-    , stapledOCSPResponse(aStapledOCSPResponse)
-    , subCACount(aSubCACount)
-    , deferredSubjectError(aDeferredSubjectError)
-    , subjectSignaturePublicKeyAlg(der::PublicKeyAlgorithm::Uninitialized)
-    , result(Result::FATAL_ERROR_LIBRARY_FAILURE)
-    , resultWasSet(false)
-    , buildForwardCallBudget(aBuildForwardCallBudget)
-  {
-  }
-
-  Result Check(Input potentialIssuerDER,
-               /*optional*/ const Input* additionalNameConstraints,
-               /*out*/ bool& keepGoing) override;
-
-  Result CheckResult() const;
-
-private:
-  TrustDomain& trustDomain;
-  const BackCert& subject;
-  const Time time;
-  const KeyPurposeId requiredEKUIfPresent;
-  const CertPolicyId& requiredPolicy;
-  /*optional*/ Input const* const stapledOCSPResponse;
-  const unsigned int subCACount;
-  const Result deferredSubjectError;
-
-  // Initialized lazily.
-  uint8_t subjectSignatureDigestBuf[MAX_DIGEST_SIZE_IN_BYTES];
-  der::PublicKeyAlgorithm subjectSignaturePublicKeyAlg;
-  SignedDigest subjectSignature;
-
-  Result RecordResult(Result currentResult, /*out*/ bool& keepGoing);
-  Result result;
-  bool resultWasSet;
-  unsigned int& buildForwardCallBudget;
-
-  PathBuildingStep(const PathBuildingStep&) = delete;
-  void operator=(const PathBuildingStep&) = delete;
-};
-
-Result
-PathBuildingStep::RecordResult(Result newResult, /*out*/ bool& keepGoing)
-{
-  if (newResult == Result::ERROR_UNTRUSTED_CERT) {
-    newResult = Result::ERROR_UNTRUSTED_ISSUER;
-  } else if (newResult == Result::ERROR_EXPIRED_CERTIFICATE) {
-    newResult = Result::ERROR_EXPIRED_ISSUER_CERTIFICATE;
-  } else if (newResult == Result::ERROR_NOT_YET_VALID_CERTIFICATE) {
-    newResult = Result::ERROR_NOT_YET_VALID_ISSUER_CERTIFICATE;
-  }
-
-  if (resultWasSet) {
-    if (result == Success) {
-      return NotReached("RecordResult called after finding a chain",
-                        Result::FATAL_ERROR_INVALID_STATE);
-    }
-    // If every potential issuer has the same problem (e.g. expired) and/or if
-    // there is only one bad potential issuer, then return a more specific
-    // error. Otherwise, punt on trying to decide which error should be
-    // returned by returning the generic Result::ERROR_UNKNOWN_ISSUER error.
-    if (newResult != Success && newResult != result) {
-      newResult = Result::ERROR_UNKNOWN_ISSUER;
-    }
-  }
-
-  result = newResult;
-  resultWasSet = true;
-  keepGoing = result != Success;
-  return Success;
-}
-
-Result
-PathBuildingStep::CheckResult() const
-{
-  if (!resultWasSet) {
-    return Result::ERROR_UNKNOWN_ISSUER;
-  }
-  return result;
-}
-
-// The code that executes in the inner loop of BuildForward
-Result
-PathBuildingStep::Check(Input potentialIssuerDER,
-           /*optional*/ const Input* additionalNameConstraints,
-                /*out*/ bool& keepGoing)
-{
-  BackCert potentialIssuer(potentialIssuerDER, EndEntityOrCA::MustBeCA,
-                           &subject);
-  Result rv = potentialIssuer.Init();
-  if (rv != Success) {
-    return RecordResult(rv, keepGoing);
-  }
-
-  // Simple TrustDomain::FindIssuers implementations may pass in all possible
-  // CA certificates without any filtering. Because of this, we don't consider
-  // a mismatched name to be an error. Instead, we just pretend that any
-  // certificate without a matching name was never passed to us. In particular,
-  // we treat the case where the TrustDomain only asks us to check CA
-  // certificates with mismatched names as equivalent to the case where the
-  // TrustDomain never called Check() at all.
-  if (!InputsAreEqual(potentialIssuer.GetSubject(), subject.GetIssuer())) {
-    keepGoing = true;
-    return Success;
-  }
-
-  // Loop prevention, done as recommended by RFC4158 Section 5.2
-  // TODO: this doesn't account for subjectAltNames!
-  // TODO(perf): This probably can and should be optimized in some way.
-  for (const BackCert* prev = potentialIssuer.childCert; prev;
-       prev = prev->childCert) {
-    if (InputsAreEqual(potentialIssuer.GetSubjectPublicKeyInfo(),
-                       prev->GetSubjectPublicKeyInfo()) &&
-        InputsAreEqual(potentialIssuer.GetSubject(), prev->GetSubject())) {
-      // XXX: error code
-      return RecordResult(Result::ERROR_UNKNOWN_ISSUER, keepGoing);
-    }
-  }
-
-  if (potentialIssuer.GetNameConstraints()) {
-    rv = CheckNameConstraints(*potentialIssuer.GetNameConstraints(),
-                              subject, requiredEKUIfPresent);
-    if (rv != Success) {
-       return RecordResult(rv, keepGoing);
-    }
-  }
-
-  if (additionalNameConstraints) {
-    rv = CheckNameConstraints(*additionalNameConstraints, subject,
-                              requiredEKUIfPresent);
-    if (rv != Success) {
-       return RecordResult(rv, keepGoing);
-    }
-  }
-
-  rv = CheckTLSFeatures(subject, potentialIssuer);
-  if (rv != Success) {
-    return RecordResult(rv, keepGoing);
-  }
-
-  // If we've ran out of budget, stop searching.
-  if (buildForwardCallBudget == 0) {
-    Result savedRv = RecordResult(Result::ERROR_UNKNOWN_ISSUER, keepGoing);
-    keepGoing = false;
-    return savedRv;
-  }
-  buildForwardCallBudget--;
-
-  // RFC 5280, Section 4.2.1.3: "If the keyUsage extension is present, then the
-  // subject public key MUST NOT be used to verify signatures on certificates
-  // or CRLs unless the corresponding keyCertSign or cRLSign bit is set."
-  rv = BuildForward(trustDomain, potentialIssuer, time, KeyUsage::keyCertSign,
-                    requiredEKUIfPresent, requiredPolicy, nullptr, subCACount,
-                    buildForwardCallBudget);
-  if (rv != Success) {
-    return RecordResult(rv, keepGoing);
-  }
-
-  // Calculate the digest of the subject's signed data if we haven't already
-  // done so. We do this lazily to avoid doing it at all if we backtrack before
-  // getting to this point. We cache the result to avoid recalculating it if we
-  // backtrack after getting to this point.
-  if (subjectSignature.digest.GetLength() == 0) {
-    rv = DigestSignedData(trustDomain, subject.GetSignedData(),
-                          subjectSignatureDigestBuf,
-                          subjectSignaturePublicKeyAlg, subjectSignature);
-    if (rv != Success) {
-      return rv;
-    }
-  }
-
-  rv = VerifySignedDigest(trustDomain, subjectSignaturePublicKeyAlg,
-                          subjectSignature,
-                          potentialIssuer.GetSubjectPublicKeyInfo());
-  if (rv != Success) {
-    return RecordResult(rv, keepGoing);
-  }
-
-  // We avoid doing revocation checking for expired certificates because OCSP
-  // responders are allowed to forget about expired certificates, and many OCSP
-  // responders return an error when asked for the status of an expired
-  // certificate.
-  if (deferredSubjectError != Result::ERROR_EXPIRED_CERTIFICATE) {
-    CertID certID(subject.GetIssuer(), potentialIssuer.GetSubjectPublicKeyInfo(),
-                  subject.GetSerialNumber());
-    Time notBefore(Time::uninitialized);
-    Time notAfter(Time::uninitialized);
-    // This should never fail. If we're here, we've already parsed the validity
-    // and checked that the given time is in the certificate's validity period.
-    rv = ParseValidity(subject.GetValidity(), &notBefore, &notAfter);
-    if (rv != Success) {
-      return rv;
-    }
-    Duration validityDuration(notAfter, notBefore);
-    rv = trustDomain.CheckRevocation(subject.endEntityOrCA, certID, time,
-                                     validityDuration, stapledOCSPResponse,
-                                     subject.GetAuthorityInfoAccess());
-    if (rv != Success) {
-      // Since this is actually a problem with the current subject certificate
-      // (rather than the issuer), it doesn't make sense to keep going; all
-      // paths through this certificate will fail.
-      Result savedRv = RecordResult(rv, keepGoing);
-      keepGoing = false;
-      return savedRv;
-    }
-
-    if (subject.endEntityOrCA == EndEntityOrCA::MustBeEndEntity) {
-      const Input* sctExtension = subject.GetSignedCertificateTimestamps();
-      if (sctExtension) {
-        Input sctList;
-        rv = ExtractSignedCertificateTimestampListFromExtension(*sctExtension,
-                                                                sctList);
-        if (rv != Success) {
-          // Again, the problem is with this certificate, and all paths through
-          // it will fail.
-          Result savedRv = RecordResult(rv, keepGoing);
-          keepGoing = false;
-          return savedRv;
-        }
-        trustDomain.NoteAuxiliaryExtension(AuxiliaryExtension::EmbeddedSCTList,
-                                           sctList);
-      }
-    }
-  }
-
-  return RecordResult(Success, keepGoing);
-}
-
-// Recursively build the path from the given subject certificate to the root.
-//
-// Be very careful about changing the order of checks. The order is significant
-// because it affects which error we return when a certificate or certificate
-// chain has multiple problems. See the error ranking documentation in
-// pkix/pkix.h.
-static Result
-BuildForward(TrustDomain& trustDomain,
-             const BackCert& subject,
-             Time time,
-             KeyUsage requiredKeyUsageIfPresent,
-             KeyPurposeId requiredEKUIfPresent,
-             const CertPolicyId& requiredPolicy,
-             /*optional*/ const Input* stapledOCSPResponse,
-             unsigned int subCACount,
-             unsigned int& buildForwardCallBudget)
-{
-  Result rv;
-
-  TrustLevel trustLevel;
-  // If this is an end-entity and not a trust anchor, we defer reporting
-  // any error found here until after attempting to find a valid chain.
-  // See the explanation of error prioritization in pkix.h.
-  rv = CheckIssuerIndependentProperties(trustDomain, subject, time,
-                                        requiredKeyUsageIfPresent,
-                                        requiredEKUIfPresent, requiredPolicy,
-                                        subCACount, trustLevel);
-  Result deferredEndEntityError = Success;
-  if (rv != Success) {
-    if (subject.endEntityOrCA == EndEntityOrCA::MustBeEndEntity &&
-        trustLevel != TrustLevel::TrustAnchor) {
-      deferredEndEntityError = rv;
-    } else {
-      return rv;
-    }
-  }
-
-  if (trustLevel == TrustLevel::TrustAnchor) {
-    // End of the recursion.
-
-    NonOwningDERArray chain;
-    for (const BackCert* cert = &subject; cert; cert = cert->childCert) {
-      rv = chain.Append(cert->GetDER());
-      if (rv != Success) {
-        return NotReached("NonOwningDERArray::SetItem failed.", rv);
-      }
-    }
-
-    // This must be done here, after the chain is built but before any
-    // revocation checks have been done.
-    return trustDomain.IsChainValid(chain, time, requiredPolicy);
-  }
-
-  if (subject.endEntityOrCA == EndEntityOrCA::MustBeCA) {
-    // Avoid stack overflows and poor performance by limiting cert chain
-    // length.
-    static const unsigned int MAX_SUBCA_COUNT = 6;
-    static_assert(1/*end-entity*/ + MAX_SUBCA_COUNT + 1/*root*/ ==
-                  NonOwningDERArray::MAX_LENGTH,
-                  "MAX_SUBCA_COUNT and NonOwningDERArray::MAX_LENGTH mismatch.");
-    if (subCACount >= MAX_SUBCA_COUNT) {
-      return Result::ERROR_UNKNOWN_ISSUER;
-    }
-    ++subCACount;
-  } else {
-    assert(subCACount == 0);
-  }
-
-  // Find a trusted issuer.
-
-  PathBuildingStep pathBuilder(trustDomain, subject, time,
-                               requiredEKUIfPresent, requiredPolicy,
-                               stapledOCSPResponse, subCACount,
-                               deferredEndEntityError, buildForwardCallBudget);
-
-  // TODO(bug 965136): Add SKI/AKI matching optimizations
-  rv = trustDomain.FindIssuer(subject.GetIssuer(), pathBuilder, time);
-  if (rv != Success) {
-    return rv;
-  }
-
-  rv = pathBuilder.CheckResult();
-  if (rv != Success) {
-    return rv;
-  }
-
-  // If we found a valid chain but deferred reporting an error with the
-  // end-entity certificate, report it now.
-  if (deferredEndEntityError != Success) {
-    return deferredEndEntityError;
-  }
-
-  // We've built a valid chain from the subject cert up to a trusted root.
-  return Success;
-}
-
-Result
-BuildCertChain(TrustDomain& trustDomain, Input certDER,
-               Time time, EndEntityOrCA endEntityOrCA,
-               KeyUsage requiredKeyUsageIfPresent,
-               KeyPurposeId requiredEKUIfPresent,
-               const CertPolicyId& requiredPolicy,
-               /*optional*/ const Input* stapledOCSPResponse)
-{
-  // XXX: Support the legacy use of the subject CN field for indicating the
-  // domain name the certificate is valid for.
-  BackCert cert(certDER, endEntityOrCA, nullptr);
-  Result rv = cert.Init();
-  if (rv != Success) {
-    return rv;
-  }
-
-  // See bug 1056341 for context. If mozilla::pkix is being used in an
-  // environment where there are many certificates that all have the same
-  // distinguished name as their subject and issuer (but different SPKIs - see
-  // the loop prevention as per RFC4158 Section 5.2 in PathBuildingStep::Check),
-  // the space to search becomes exponential. Because it would be prohibitively
-  // expensive to explore the entire space, we introduce a budget here that,
-  // when exhausted, terminates the search with the result
-  // Result::ERROR_UNKNOWN_ISSUER. Essentially, we limit the total number of
-  // times `BuildForward` can be called. The current value appears to be a good
-  // balance between finding a path when one exists (when the space isn't too
-  // large) and timing out quickly enough when the space is too large or there
-  // is no valid path to a trust anchor.
-  unsigned int buildForwardCallBudget = 200000;
-  return BuildForward(trustDomain, cert, time, requiredKeyUsageIfPresent,
-                      requiredEKUIfPresent, requiredPolicy, stapledOCSPResponse,
-                      0/*subCACount*/, buildForwardCallBudget);
-}
-
-} } // namespace mozilla::pkix
deleted file mode 100644
--- a/security/pkix/lib/pkixcert.cpp
+++ /dev/null
@@ -1,323 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2014 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "pkixutil.h"
-
-namespace mozilla { namespace pkix {
-
-Result
-BackCert::Init()
-{
-  Result rv;
-
-  // Certificate  ::=  SEQUENCE  {
-  //         tbsCertificate       TBSCertificate,
-  //         signatureAlgorithm   AlgorithmIdentifier,
-  //         signatureValue       BIT STRING  }
-
-  Reader tbsCertificate;
-
-  // The scope of |input| and |certificate| are limited to this block so we
-  // don't accidentally confuse them for tbsCertificate later.
-  {
-    Reader certificate;
-    rv = der::ExpectTagAndGetValueAtEnd(der, der::SEQUENCE, certificate);
-    if (rv != Success) {
-      return rv;
-    }
-    rv = der::SignedData(certificate, tbsCertificate, signedData);
-    if (rv != Success) {
-      return rv;
-    }
-    rv = der::End(certificate);
-    if (rv != Success) {
-      return rv;
-    }
-  }
-
-  // TBSCertificate  ::=  SEQUENCE  {
-  //      version         [0]  EXPLICIT Version DEFAULT v1,
-  //      serialNumber         CertificateSerialNumber,
-  //      signature            AlgorithmIdentifier,
-  //      issuer               Name,
-  //      validity             Validity,
-  //      subject              Name,
-  //      subjectPublicKeyInfo SubjectPublicKeyInfo,
-  //      issuerUniqueID  [1]  IMPLICIT UniqueIdentifier OPTIONAL,
-  //                           -- If present, version MUST be v2 or v3
-  //      subjectUniqueID [2]  IMPLICIT UniqueIdentifier OPTIONAL,
-  //                           -- If present, version MUST be v2 or v3
-  //      extensions      [3]  EXPLICIT Extensions OPTIONAL
-  //                           -- If present, version MUST be v3
-  //      }
-  rv = der::OptionalVersion(tbsCertificate, version);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::CertificateSerialNumber(tbsCertificate, serialNumber);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::ExpectTagAndGetValue(tbsCertificate, der::SEQUENCE, signature);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::ExpectTagAndGetTLV(tbsCertificate, der::SEQUENCE, issuer);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::ExpectTagAndGetValue(tbsCertificate, der::SEQUENCE, validity);
-  if (rv != Success) {
-    return rv;
-  }
-  // TODO(bug XXXXXXX): We rely on the the caller of mozilla::pkix to validate
-  // that the name is syntactically valid, if they care. In Gecko we do this
-  // implicitly by parsing the certificate into a CERTCertificate object.
-  // Instead of relying on the caller to do this, we should do it ourselves.
-  rv = der::ExpectTagAndGetTLV(tbsCertificate, der::SEQUENCE, subject);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::ExpectTagAndGetTLV(tbsCertificate, der::SEQUENCE,
-                               subjectPublicKeyInfo);
-  if (rv != Success) {
-    return rv;
-  }
-
-  static const uint8_t CSC = der::CONTEXT_SPECIFIC | der::CONSTRUCTED;
-
-  // According to RFC 5280, all fields below this line are forbidden for
-  // certificate versions less than v3.  However, for compatibility reasons,
-  // we parse v1/v2 certificates in the same way as v3 certificates.  So if
-  // these fields appear in a v1 certificate, they will be used.
-
-  // Ignore issuerUniqueID if present.
-  if (tbsCertificate.Peek(CSC | 1)) {
-    rv = der::ExpectTagAndSkipValue(tbsCertificate, CSC | 1);
-    if (rv != Success) {
-      return rv;
-    }
-  }
-
-  // Ignore subjectUniqueID if present.
-  if (tbsCertificate.Peek(CSC | 2)) {
-    rv = der::ExpectTagAndSkipValue(tbsCertificate, CSC | 2);
-    if (rv != Success) {
-      return rv;
-    }
-  }
-
-  rv = der::OptionalExtensions(
-         tbsCertificate, CSC | 3,
-         [this](Reader& extnID, const Input& extnValue, bool critical,
-                /*out*/ bool& understood) {
-           return RememberExtension(extnID, extnValue, critical, understood);
-         });
-  if (rv != Success) {
-    return rv;
-  }
-
-  // The Netscape Certificate Type extension is an obsolete
-  // Netscape-proprietary mechanism that we ignore in favor of the standard
-  // extensions. However, some CAs have issued certificates with the Netscape
-  // Cert Type extension marked critical. Thus, for compatibility reasons, we
-  // "understand" this extension by ignoring it when it is not critical, and
-  // by ensuring that the equivalent standardized extensions are present when
-  // it is marked critical, based on the assumption that the information in
-  // the Netscape Cert Type extension is consistent with the information in
-  // the standard extensions.
-  //
-  // Here is a mapping between the Netscape Cert Type extension and the
-  // standard extensions:
-  //
-  // Netscape Cert Type  |  BasicConstraints.cA  |  Extended Key Usage
-  // --------------------+-----------------------+----------------------
-  // SSL Server          |  false                |  id_kp_serverAuth
-  // SSL Client          |  false                |  id_kp_clientAuth
-  // S/MIME Client       |  false                |  id_kp_emailProtection
-  // Object Signing      |  false                |  id_kp_codeSigning
-  // SSL Server CA       |  true                 |  id_kp_serverAuth
-  // SSL Client CA       |  true                 |  id_kp_clientAuth
-  // S/MIME CA           |  true                 |  id_kp_emailProtection
-  // Object Signing CA   |  true                 |  id_kp_codeSigning
-  if (criticalNetscapeCertificateType.GetLength() > 0 &&
-      (basicConstraints.GetLength() == 0 || extKeyUsage.GetLength() == 0)) {
-    return Result::ERROR_UNKNOWN_CRITICAL_EXTENSION;
-  }
-
-  return der::End(tbsCertificate);
-}
-
-Result
-BackCert::RememberExtension(Reader& extnID, Input extnValue,
-                            bool critical, /*out*/ bool& understood)
-{
-  understood = false;
-
-  // python DottedOIDToCode.py id-ce-keyUsage 2.5.29.15
-  static const uint8_t id_ce_keyUsage[] = {
-    0x55, 0x1d, 0x0f
-  };
-  // python DottedOIDToCode.py id-ce-subjectAltName 2.5.29.17
-  static const uint8_t id_ce_subjectAltName[] = {
-    0x55, 0x1d, 0x11
-  };
-  // python DottedOIDToCode.py id-ce-basicConstraints 2.5.29.19
-  static const uint8_t id_ce_basicConstraints[] = {
-    0x55, 0x1d, 0x13
-  };
-  // python DottedOIDToCode.py id-ce-nameConstraints 2.5.29.30
-  static const uint8_t id_ce_nameConstraints[] = {
-    0x55, 0x1d, 0x1e
-  };
-  // python DottedOIDToCode.py id-ce-certificatePolicies 2.5.29.32
-  static const uint8_t id_ce_certificatePolicies[] = {
-    0x55, 0x1d, 0x20
-  };
-  // python DottedOIDToCode.py id-ce-policyConstraints 2.5.29.36
-  static const uint8_t id_ce_policyConstraints[] = {
-    0x55, 0x1d, 0x24
-  };
-  // python DottedOIDToCode.py id-ce-extKeyUsage 2.5.29.37
-  static const uint8_t id_ce_extKeyUsage[] = {
-    0x55, 0x1d, 0x25
-  };
-  // python DottedOIDToCode.py id-ce-inhibitAnyPolicy 2.5.29.54
-  static const uint8_t id_ce_inhibitAnyPolicy[] = {
-    0x55, 0x1d, 0x36
-  };
-  // python DottedOIDToCode.py id-pe-authorityInfoAccess 1.3.6.1.5.5.7.1.1
-  static const uint8_t id_pe_authorityInfoAccess[] = {
-    0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x01, 0x01
-  };
-  // python DottedOIDToCode.py id-pkix-ocsp-nocheck 1.3.6.1.5.5.7.48.1.5
-  static const uint8_t id_pkix_ocsp_nocheck[] = {
-    0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x30, 0x01, 0x05
-  };
-  // python DottedOIDToCode.py Netscape-certificate-type 2.16.840.1.113730.1.1
-  static const uint8_t Netscape_certificate_type[] = {
-    0x60, 0x86, 0x48, 0x01, 0x86, 0xf8, 0x42, 0x01, 0x01
-  };
-  // python DottedOIDToCode.py id-pe-tlsfeature 1.3.6.1.5.5.7.1.24
-  static const uint8_t id_pe_tlsfeature[] = {
-    0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x01, 0x18
-  };
-  // python DottedOIDToCode.py id-embeddedSctList 1.3.6.1.4.1.11129.2.4.2
-  // See Section 3.3 of RFC 6962.
-  static const uint8_t id_embeddedSctList[] = {
-    0x2b, 0x06, 0x01, 0x04, 0x01, 0xd6, 0x79, 0x02, 0x04, 0x02
-  };
-
-  Input* out = nullptr;
-
-  // We already enforce the maximum possible constraints for policies so we
-  // can safely ignore even critical policy constraint extensions.
-  //
-  // XXX: Doing it this way won't allow us to detect duplicate
-  // policyConstraints extensions, but that's OK because (and only because) we
-  // ignore the extension.
-  Input dummyPolicyConstraints;
-
-  // We don't need to save the contents of this extension if it is present. We
-  // just need to handle its presence (it is essentially ignored right now).
-  Input dummyOCSPNocheck;
-
-  // For compatibility reasons, for some extensions we have to allow empty
-  // extension values. This would normally interfere with our duplicate
-  // extension checking code. However, as long as the extensions we allow to
-  // have empty values are also the ones we implicitly allow duplicates of,
-  // this will work fine.
-  bool emptyValueAllowed = false;
-
-  // RFC says "Conforming CAs MUST mark this extension as non-critical" for
-  // both authorityKeyIdentifier and subjectKeyIdentifier, and we do not use
-  // them for anything, so we totally ignore them here.
-
-  if (extnID.MatchRest(id_ce_keyUsage)) {
-    out = &keyUsage;
-  } else if (extnID.MatchRest(id_ce_subjectAltName)) {
-    out = &subjectAltName;
-  } else if (extnID.MatchRest(id_ce_basicConstraints)) {
-    out = &basicConstraints;
-  } else if (extnID.MatchRest(id_ce_nameConstraints)) {
-    out = &nameConstraints;
-  } else if (extnID.MatchRest(id_ce_certificatePolicies)) {
-    out = &certificatePolicies;
-  } else if (extnID.MatchRest(id_ce_policyConstraints)) {
-    out = &dummyPolicyConstraints;
-  } else if (extnID.MatchRest(id_ce_extKeyUsage)) {
-    out = &extKeyUsage;
-  } else if (extnID.MatchRest(id_ce_inhibitAnyPolicy)) {
-    out = &inhibitAnyPolicy;
-  } else if (extnID.MatchRest(id_pe_authorityInfoAccess)) {
-    out = &authorityInfoAccess;
-  } else if (extnID.MatchRest(id_pe_tlsfeature)) {
-    out = &requiredTLSFeatures;
-  } else if (extnID.MatchRest(id_embeddedSctList)) {
-    out = &signedCertificateTimestamps;
-  } else if (extnID.MatchRest(id_pkix_ocsp_nocheck) && critical) {
-    // We need to make sure we don't reject delegated OCSP response signing
-    // certificates that contain the id-pkix-ocsp-nocheck extension marked as
-    // critical when validating OCSP responses. Without this, an application
-    // that implements soft-fail OCSP might ignore a valid Revoked or Unknown
-    // response, and an application that implements hard-fail OCSP might fail
-    // to connect to a server given a valid Good response.
-    out = &dummyOCSPNocheck;
-    // We allow this extension to have an empty value.
-    // See http://comments.gmane.org/gmane.ietf.x509/30947
-    emptyValueAllowed = true;
-  } else if (extnID.MatchRest(Netscape_certificate_type) && critical) {
-    out = &criticalNetscapeCertificateType;
-  }
-
-  if (out) {
-    // Don't allow an empty value for any extension we understand. This way, we
-    // can test out->GetLength() != 0 or out->Init() to check for duplicates.
-    if (extnValue.GetLength() == 0 && !emptyValueAllowed) {
-      return Result::ERROR_EXTENSION_VALUE_INVALID;
-    }
-    if (out->Init(extnValue) != Success) {
-      // Duplicate extension
-      return Result::ERROR_EXTENSION_VALUE_INVALID;
-    }
-    understood = true;
-  }
-
-  return Success;
-}
-
-Result
-ExtractSignedCertificateTimestampListFromExtension(Input extnValue,
-                                                   Input& sctList)
-{
-  Reader decodedValue;
-  Result rv = der::ExpectTagAndGetValueAtEnd(extnValue, der::OCTET_STRING,
-                                             decodedValue);
-  if (rv != Success) {
-    return rv;
-  }
-  return decodedValue.SkipToEnd(sctList);
-}
-
-} } // namespace mozilla::pkix
deleted file mode 100644
--- a/security/pkix/lib/pkixcheck.cpp
+++ /dev/null
@@ -1,1100 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "pkixcheck.h"
-
-#include "pkixder.h"
-#include "pkixutil.h"
-
-namespace mozilla { namespace pkix {
-
-// 4.1.1.2 signatureAlgorithm
-// 4.1.2.3 signature
-
-Result
-CheckSignatureAlgorithm(TrustDomain& trustDomain,
-                        EndEntityOrCA endEntityOrCA,
-                        Time notBefore,
-                        const der::SignedDataWithSignature& signedData,
-                        Input signatureValue)
-{
-  // 4.1.1.2. signatureAlgorithm
-  der::PublicKeyAlgorithm publicKeyAlg;
-  DigestAlgorithm digestAlg;
-  Reader signatureAlgorithmReader(signedData.algorithm);
-  Result rv = der::SignatureAlgorithmIdentifierValue(signatureAlgorithmReader,
-                                                     publicKeyAlg, digestAlg);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::End(signatureAlgorithmReader);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // 4.1.2.3. Signature
-  der::PublicKeyAlgorithm signedPublicKeyAlg;
-  DigestAlgorithm signedDigestAlg;
-  Reader signedSignatureAlgorithmReader(signatureValue);
-  rv = der::SignatureAlgorithmIdentifierValue(signedSignatureAlgorithmReader,
-                                              signedPublicKeyAlg,
-                                              signedDigestAlg);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::End(signedSignatureAlgorithmReader);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // "This field MUST contain the same algorithm identifier as the
-  // signatureAlgorithm field in the sequence Certificate." However, it may
-  // be encoded differently. In particular, one of the fields may have a NULL
-  // parameter while the other one may omit the parameter field altogether, and
-  // these are considered equivalent. Some certificates generation software
-  // actually generates certificates like that, so we compare the parsed values
-  // instead of comparing the encoded values byte-for-byte.
-  //
-  // Along the same lines, we accept two different OIDs for RSA-with-SHA1, and
-  // we consider those OIDs to be equivalent here.
-  if (publicKeyAlg != signedPublicKeyAlg || digestAlg != signedDigestAlg) {
-    return Result::ERROR_SIGNATURE_ALGORITHM_MISMATCH;
-  }
-
-  // During the time of the deprecation of SHA-1 and the deprecation of RSA
-  // keys of less than 2048 bits, we will encounter many certs signed using
-  // SHA-1 and/or too-small RSA keys. With this in mind, we ask the trust
-  // domain early on if it knows it will reject the signature purely based on
-  // the digest algorithm and/or the RSA key size (if an RSA signature). This
-  // is a good optimization because it completely avoids calling
-  // trustDomain.FindIssuers (which may be slow) for such rejected certs, and
-  // more generally it short-circuits any path building with them (which, of
-  // course, is even slower).
-
-  rv = trustDomain.CheckSignatureDigestAlgorithm(digestAlg, endEntityOrCA,
-                                                 notBefore);
-  if (rv != Success) {
-    return rv;
-  }
-
-  switch (publicKeyAlg) {
-    case der::PublicKeyAlgorithm::RSA_PKCS1:
-    {
-      // The RSA computation may give a result that requires fewer bytes to
-      // encode than the public key (since it is modular arithmetic). However,
-      // the last step of generating a PKCS#1.5 signature is the I2OSP
-      // procedure, which pads any such shorter result with zeros so that it
-      // is exactly the same length as the public key.
-      unsigned int signatureSizeInBits = signedData.signature.GetLength() * 8u;
-      return trustDomain.CheckRSAPublicKeyModulusSizeInBits(
-               endEntityOrCA, signatureSizeInBits);
-    }
-
-    case der::PublicKeyAlgorithm::ECDSA:
-      // In theory, we could implement a similar early-pruning optimization for
-      // ECDSA curves. However, since there has been no similar deprecation for
-      // for any curve that we support, the chances of us encountering a curve
-      // during path building is too low to be worth bothering with.
-      break;
-    case der::PublicKeyAlgorithm::Uninitialized:
-    {
-      assert(false);
-      return Result::FATAL_ERROR_LIBRARY_FAILURE;
-    }
-    MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-  }
-
-  return Success;
-}
-
-// 4.1.2.4 Issuer
-
-Result
-CheckIssuer(Input encodedIssuer)
-{
-  // "The issuer field MUST contain a non-empty distinguished name (DN)."
-  Reader issuer(encodedIssuer);
-  Input encodedRDNs;
-  ExpectTagAndGetValue(issuer, der::SEQUENCE, encodedRDNs);
-  Reader rdns(encodedRDNs);
-  // Check that the issuer name contains at least one RDN
-  // (Note: this does not check related grammar rules, such as there being one
-  // or more AVAs in each RDN, or the values in AVAs not being empty strings)
-  if (rdns.AtEnd()) {
-    return Result::ERROR_EMPTY_ISSUER_NAME;
-  }
-  return Success;
-}
-
-// 4.1.2.5 Validity
-
-Result
-ParseValidity(Input encodedValidity,
-              /*optional out*/ Time* notBeforeOut,
-              /*optional out*/ Time* notAfterOut)
-{
-  Reader validity(encodedValidity);
-  Time notBefore(Time::uninitialized);
-  if (der::TimeChoice(validity, notBefore) != Success) {
-    return Result::ERROR_INVALID_DER_TIME;
-  }
-
-  Time notAfter(Time::uninitialized);
-  if (der::TimeChoice(validity, notAfter) != Success) {
-    return Result::ERROR_INVALID_DER_TIME;
-  }
-
-  if (der::End(validity) != Success) {
-    return Result::ERROR_INVALID_DER_TIME;
-  }
-
-  if (notBefore > notAfter) {
-    return Result::ERROR_INVALID_DER_TIME;
-  }
-
-  if (notBeforeOut) {
-    *notBeforeOut = notBefore;
-  }
-  if (notAfterOut) {
-    *notAfterOut = notAfter;
-  }
-
-  return Success;
-}
-
-Result
-CheckValidity(Time time, Time notBefore, Time notAfter)
-{
-  if (time < notBefore) {
-    return Result::ERROR_NOT_YET_VALID_CERTIFICATE;
-  }
-
-  if (time > notAfter) {
-    return Result::ERROR_EXPIRED_CERTIFICATE;
-  }
-
-  return Success;
-}
-
-// 4.1.2.7 Subject Public Key Info
-
-Result
-CheckSubjectPublicKeyInfoContents(Reader& input, TrustDomain& trustDomain,
-                                  EndEntityOrCA endEntityOrCA)
-{
-  // Here, we validate the syntax and do very basic semantic validation of the
-  // public key of the certificate. The intention here is to filter out the
-  // types of bad inputs that are most likely to trigger non-mathematical
-  // security vulnerabilities in the TrustDomain, like buffer overflows or the
-  // use of unsafe elliptic curves.
-  //
-  // We don't check (all of) the mathematical properties of the public key here
-  // because it is more efficient for the TrustDomain to do it during signature
-  // verification and/or other use of the public key. In particular, we
-  // delegate the arithmetic validation of the public key, as specified in
-  // NIST SP800-56A section 5.6.2, to the TrustDomain, at least for now.
-
-  Reader algorithm;
-  Input subjectPublicKey;
-  Result rv = der::ExpectTagAndGetValue(input, der::SEQUENCE, algorithm);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::BitStringWithNoUnusedBits(input, subjectPublicKey);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::End(input);
-  if (rv != Success) {
-    return rv;
-  }
-
-  Reader subjectPublicKeyReader(subjectPublicKey);
-
-  Reader algorithmOID;
-  rv = der::ExpectTagAndGetValue(algorithm, der::OIDTag, algorithmOID);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // RFC 3279 Section 2.3.1
-  // python DottedOIDToCode.py rsaEncryption 1.2.840.113549.1.1.1
-  static const uint8_t rsaEncryption[] = {
-    0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01
-  };
-
-  // RFC 3279 Section 2.3.5 and RFC 5480 Section 2.1.1
-  // python DottedOIDToCode.py id-ecPublicKey 1.2.840.10045.2.1
-  static const uint8_t id_ecPublicKey[] = {
-    0x2a, 0x86, 0x48, 0xce, 0x3d, 0x02, 0x01
-  };
-
-  if (algorithmOID.MatchRest(id_ecPublicKey)) {
-    // An id-ecPublicKey AlgorithmIdentifier has a parameter that identifes
-    // the curve being used. Although RFC 5480 specifies multiple forms, we
-    // only supported the NamedCurve form, where the curve is identified by an
-    // OID.
-
-    Reader namedCurveOIDValue;
-    rv = der::ExpectTagAndGetValue(algorithm, der::OIDTag,
-                                   namedCurveOIDValue);
-    if (rv != Success) {
-      return rv;
-    }
-
-    // RFC 5480
-    // python DottedOIDToCode.py secp256r1 1.2.840.10045.3.1.7
-    static const uint8_t secp256r1[] = {
-      0x2a, 0x86, 0x48, 0xce, 0x3d, 0x03, 0x01, 0x07
-    };
-
-    // RFC 5480
-    // python DottedOIDToCode.py secp384r1 1.3.132.0.34
-    static const uint8_t secp384r1[] = {
-      0x2b, 0x81, 0x04, 0x00, 0x22
-    };
-
-    // RFC 5480
-    // python DottedOIDToCode.py secp521r1 1.3.132.0.35
-    static const uint8_t secp521r1[] = {
-      0x2b, 0x81, 0x04, 0x00, 0x23
-    };
-
-    // Matching is attempted based on a rough estimate of the commonality of the
-    // elliptic curve, to minimize the number of MatchRest calls.
-    NamedCurve curve;
-    unsigned int bits;
-    if (namedCurveOIDValue.MatchRest(secp256r1)) {
-      curve = NamedCurve::secp256r1;
-      bits = 256;
-    } else if (namedCurveOIDValue.MatchRest(secp384r1)) {
-      curve = NamedCurve::secp384r1;
-      bits = 384;
-    } else if (namedCurveOIDValue.MatchRest(secp521r1)) {
-      curve = NamedCurve::secp521r1;
-      bits = 521;
-    } else {
-      return Result::ERROR_UNSUPPORTED_ELLIPTIC_CURVE;
-    }
-
-    rv = trustDomain.CheckECDSACurveIsAcceptable(endEntityOrCA, curve);
-    if (rv != Success) {
-      return rv;
-    }
-
-    // RFC 5480 Section 2.2 says that the first octet will be 0x04 to indicate
-    // an uncompressed point, which is the only encoding we support.
-    uint8_t compressedOrUncompressed;
-    rv = subjectPublicKeyReader.Read(compressedOrUncompressed);
-    if (rv != Success) {
-      return rv;
-    }
-    if (compressedOrUncompressed != 0x04) {
-      return Result::ERROR_UNSUPPORTED_EC_POINT_FORM;
-    }
-
-    // The point is encoded as two raw (not DER-encoded) integers, each padded
-    // to the bit length (rounded up to the nearest byte).
-    Input point;
-    rv = subjectPublicKeyReader.SkipToEnd(point);
-    if (rv != Success) {
-      return rv;
-    }
-    if (point.GetLength() != ((bits + 7) / 8u) * 2u) {
-      return Result::ERROR_BAD_DER;
-    }
-
-    // XXX: We defer the mathematical verification of the validity of the point
-    // until signature verification. This means that if we never verify a
-    // signature, we'll never fully check whether the public key is valid.
-  } else if (algorithmOID.MatchRest(rsaEncryption)) {
-    // RFC 3279 Section 2.3.1 says "The parameters field MUST have ASN.1 type
-    // NULL for this algorithm identifier."
-    rv = der::ExpectTagAndEmptyValue(algorithm, der::NULLTag);
-    if (rv != Success) {
-      return rv;
-    }
-
-    // RSAPublicKey :: = SEQUENCE{
-    //    modulus            INTEGER,    --n
-    //    publicExponent     INTEGER  }  --e
-    rv = der::Nested(subjectPublicKeyReader, der::SEQUENCE,
-                     [&trustDomain, endEntityOrCA](Reader& r) {
-      Input modulus;
-      Input::size_type modulusSignificantBytes;
-      Result nestedRv =
-        der::PositiveInteger(r, modulus, &modulusSignificantBytes);
-      if (nestedRv != Success) {
-        return nestedRv;
-      }
-      // XXX: Should we do additional checks of the modulus?
-      nestedRv = trustDomain.CheckRSAPublicKeyModulusSizeInBits(
-        endEntityOrCA, modulusSignificantBytes * 8u);
-      if (nestedRv != Success) {
-        return nestedRv;
-      }
-
-      // XXX: We don't allow the TrustDomain to validate the exponent.
-      // XXX: We don't do our own sanity checking of the exponent.
-      Input exponent;
-      return der::PositiveInteger(r, exponent);
-    });
-    if (rv != Success) {
-      return rv;
-    }
-  } else {
-    return Result::ERROR_UNSUPPORTED_KEYALG;
-  }
-
-  rv = der::End(algorithm);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::End(subjectPublicKeyReader);
-  if (rv != Success) {
-    return rv;
-  }
-
-  return Success;
-}
-
-Result
-CheckSubjectPublicKeyInfo(Input subjectPublicKeyInfo, TrustDomain& trustDomain,
-                          EndEntityOrCA endEntityOrCA)
-{
-  Reader spkiReader(subjectPublicKeyInfo);
-  Result rv = der::Nested(spkiReader, der::SEQUENCE, [&](Reader& r) {
-    return CheckSubjectPublicKeyInfoContents(r, trustDomain, endEntityOrCA);
-  });
-  if (rv != Success) {
-    return rv;
-  }
-  return der::End(spkiReader);
-}
-
-// 4.2.1.3. Key Usage (id-ce-keyUsage)
-
-// As explained in the comment in CheckKeyUsage, bit 0 is the most significant
-// bit and bit 7 is the least significant bit.
-inline uint8_t KeyUsageToBitMask(KeyUsage keyUsage)
-{
-  assert(keyUsage != KeyUsage::noParticularKeyUsageRequired);
-  return 0x80u >> static_cast<uint8_t>(keyUsage);
-}
-
-Result
-CheckKeyUsage(EndEntityOrCA endEntityOrCA, const Input* encodedKeyUsage,
-              KeyUsage requiredKeyUsageIfPresent)
-{
-  if (!encodedKeyUsage) {
-    // TODO(bug 970196): Reject certificates that are being used to verify
-    // certificate signatures unless the certificate is a trust anchor, to
-    // reduce the chances of an end-entity certificate being abused as a CA
-    // certificate.
-    // if (endEntityOrCA == EndEntityOrCA::MustBeCA && !isTrustAnchor) {
-    //   return Result::ERROR_INADEQUATE_KEY_USAGE;
-    // }
-    //
-    // TODO: Users may configure arbitrary certificates as trust anchors, not
-    // just roots. We should only allow a certificate without a key usage to be
-    // used as a CA when it is self-issued and self-signed.
-    return Success;
-  }
-
-  Reader input(*encodedKeyUsage);
-  Reader value;
-  if (der::ExpectTagAndGetValue(input, der::BIT_STRING, value) != Success) {
-    return Result::ERROR_INADEQUATE_KEY_USAGE;
-  }
-
-  uint8_t numberOfPaddingBits;
-  if (value.Read(numberOfPaddingBits) != Success) {
-    return Result::ERROR_INADEQUATE_KEY_USAGE;
-  }
-  if (numberOfPaddingBits > 7) {
-    return Result::ERROR_INADEQUATE_KEY_USAGE;
-  }
-
-  uint8_t bits;
-  if (value.Read(bits) != Success) {
-    // Reject empty bit masks.
-    return Result::ERROR_INADEQUATE_KEY_USAGE;
-  }
-
-  // The most significant bit is numbered 0 (digitalSignature) and the least
-  // significant bit is numbered 7 (encipherOnly), and the padding is in the
-  // least significant bits of the last byte. The numbering of bits in a byte
-  // is backwards from how we usually interpret them.
-  //
-  // For example, let's say bits is encoded in one byte with of value 0xB0 and
-  // numberOfPaddingBits == 4. Then, bits is 10110000 in binary:
-  //
-  //      bit 0  bit 3
-  //          |  |
-  //          v  v
-  //          10110000
-  //              ^^^^
-  //               |
-  //               4 padding bits
-  //
-  // Since bits is the last byte, we have to consider the padding by ensuring
-  // that the least significant 4 bits are all zero, since DER rules require
-  // all padding bits to be zero. Then we have to look at the bit N bits to the
-  // right of the most significant bit, where N is a value from the KeyUsage
-  // enumeration.
-  //
-  // Let's say we're interested in the keyCertSign (5) bit. We'd need to look
-  // at bit 5, which is zero, so keyCertSign is not asserted. (Since we check
-  // that the padding is all zeros, it is OK to read from the padding bits.)
-  //
-  // Let's say we're interested in the digitalSignature (0) bit. We'd need to
-  // look at the bit 0 (the most significant bit), which is set, so that means
-  // digitalSignature is asserted. Similarly, keyEncipherment (2) and
-  // dataEncipherment (3) are asserted.
-  //
-  // Note that since the KeyUsage enumeration is limited to values 0-7, we
-  // only ever need to examine the first byte test for
-  // requiredKeyUsageIfPresent.
-
-  if (requiredKeyUsageIfPresent != KeyUsage::noParticularKeyUsageRequired) {
-    // Check that the required key usage bit is set.
-    if ((bits & KeyUsageToBitMask(requiredKeyUsageIfPresent)) == 0) {
-      return Result::ERROR_INADEQUATE_KEY_USAGE;
-    }
-  }
-
-  // RFC 5280 says "The keyCertSign bit is asserted when the subject public
-  // key is used for verifying signatures on public key certificates. If the
-  // keyCertSign bit is asserted, then the cA bit in the basic constraints
-  // extension (Section 4.2.1.9) MUST also be asserted."
-  // However, we allow end-entity certificates (i.e. certificates without
-  // basicConstraints.cA set to TRUE) to claim keyCertSign for compatibility
-  // reasons. This does not compromise security because we only allow
-  // certificates with basicConstraints.cA set to TRUE to act as CAs.
-  if (requiredKeyUsageIfPresent == KeyUsage::keyCertSign &&
-      endEntityOrCA != EndEntityOrCA::MustBeCA) {
-    return Result::ERROR_INADEQUATE_KEY_USAGE;
-  }
-
-  // The padding applies to the last byte, so skip to the last byte.
-  while (!value.AtEnd()) {
-    if (value.Read(bits) != Success) {
-      return Result::ERROR_INADEQUATE_KEY_USAGE;
-    }
-  }
-
-  // All of the padding bits must be zero, according to DER rules.
-  uint8_t paddingMask = static_cast<uint8_t>((1 << numberOfPaddingBits) - 1);
-  if ((bits & paddingMask) != 0) {
-    return Result::ERROR_INADEQUATE_KEY_USAGE;
-  }
-
-  return Success;
-}
-
-// RFC5820 4.2.1.4. Certificate Policies
-
-// "The user-initial-policy-set contains the special value any-policy if the
-// user is not concerned about certificate policy."
-//
-// python DottedOIDToCode.py anyPolicy 2.5.29.32.0
-
-static const uint8_t anyPolicy[] = {
-  0x55, 0x1d, 0x20, 0x00
-};
-
-/*static*/ const CertPolicyId CertPolicyId::anyPolicy = {
-  4, { 0x55, 0x1d, 0x20, 0x00 }
-};
-
-bool
-CertPolicyId::IsAnyPolicy() const {
-  if (this == &CertPolicyId::anyPolicy) {
-    return true;
-  }
-  return numBytes == sizeof(::mozilla::pkix::anyPolicy) &&
-         std::equal(bytes, bytes + numBytes, ::mozilla::pkix::anyPolicy);
-}
-
-bool
-CertPolicyId::operator==(const CertPolicyId& other) const
-{
-  return numBytes == other.numBytes &&
-         std::equal(bytes, bytes + numBytes, other.bytes);
-}
-
-// certificatePolicies ::= SEQUENCE SIZE (1..MAX) OF PolicyInformation
-Result
-CheckCertificatePolicies(EndEntityOrCA endEntityOrCA,
-                         const Input* encodedCertificatePolicies,
-                         const Input* encodedInhibitAnyPolicy,
-                         TrustLevel trustLevel,
-                         const CertPolicyId& requiredPolicy)
-{
-  if (requiredPolicy.numBytes == 0 ||
-      requiredPolicy.numBytes > sizeof requiredPolicy.bytes) {
-    return Result::FATAL_ERROR_INVALID_ARGS;
-  }
-
-  bool requiredPolicyFound = requiredPolicy.IsAnyPolicy();
-  if (requiredPolicyFound) {
-    return Success;
-  }
-
-  // Bug 989051. Until we handle inhibitAnyPolicy we will fail close when
-  // inhibitAnyPolicy extension is present and we are validating for a policy.
-  if (!requiredPolicyFound && encodedInhibitAnyPolicy) {
-    return Result::ERROR_POLICY_VALIDATION_FAILED;
-  }
-
-  // The root CA certificate may omit the policies that it has been
-  // trusted for, so we cannot require the policies to be present in those
-  // certificates. Instead, the determination of which roots are trusted for
-  // which policies is made by the TrustDomain's GetCertTrust method.
-  if (trustLevel == TrustLevel::TrustAnchor &&
-      endEntityOrCA == EndEntityOrCA::MustBeCA) {
-    requiredPolicyFound = true;
-  }
-
-  Input requiredPolicyDER;
-  if (requiredPolicyDER.Init(requiredPolicy.bytes, requiredPolicy.numBytes)
-        != Success) {
-    return Result::FATAL_ERROR_INVALID_ARGS;
-  }
-
-  if (encodedCertificatePolicies) {
-    Reader extension(*encodedCertificatePolicies);
-    Reader certificatePolicies;
-    Result rv = der::ExpectTagAndGetValue(extension, der::SEQUENCE,
-                                          certificatePolicies);
-    if (rv != Success) {
-      return Result::ERROR_POLICY_VALIDATION_FAILED;
-    }
-    if (!extension.AtEnd()) {
-      return Result::ERROR_POLICY_VALIDATION_FAILED;
-    }
-
-    do {
-      // PolicyInformation ::= SEQUENCE {
-      //         policyIdentifier   CertPolicyId,
-      //         policyQualifiers   SEQUENCE SIZE (1..MAX) OF
-      //                                 PolicyQualifierInfo OPTIONAL }
-      Reader policyInformation;
-      rv = der::ExpectTagAndGetValue(certificatePolicies, der::SEQUENCE,
-                                     policyInformation);
-      if (rv != Success) {
-        return Result::ERROR_POLICY_VALIDATION_FAILED;
-      }
-
-      Reader policyIdentifier;
-      rv = der::ExpectTagAndGetValue(policyInformation, der::OIDTag,
-                                     policyIdentifier);
-      if (rv != Success) {
-        return rv;
-      }
-
-      if (policyIdentifier.MatchRest(requiredPolicyDER)) {
-        requiredPolicyFound = true;
-      } else if (endEntityOrCA == EndEntityOrCA::MustBeCA &&
-                 policyIdentifier.MatchRest(anyPolicy)) {
-        requiredPolicyFound = true;
-      }
-
-      // RFC 5280 Section 4.2.1.4 says "Optional qualifiers, which MAY be
-      // present, are not expected to change the definition of the policy." Also,
-      // it seems that Section 6, which defines validation, does not require any
-      // matching of qualifiers. Thus, doing anything with the policy qualifiers
-      // would be a waste of time and a source of potential incompatibilities, so
-      // we just ignore them.
-    } while (!requiredPolicyFound && !certificatePolicies.AtEnd());
-  }
-
-  if (!requiredPolicyFound) {
-    return Result::ERROR_POLICY_VALIDATION_FAILED;
-  }
-
-  return Success;
-}
-
-static const long UNLIMITED_PATH_LEN = -1; // must be less than zero
-
-//  BasicConstraints ::= SEQUENCE {
-//          cA                      BOOLEAN DEFAULT FALSE,
-//          pathLenConstraint       INTEGER (0..MAX) OPTIONAL }
-
-// RFC5280 4.2.1.9. Basic Constraints (id-ce-basicConstraints)
-Result
-CheckBasicConstraints(EndEntityOrCA endEntityOrCA,
-                      const Input* encodedBasicConstraints,
-                      const der::Version version, TrustLevel trustLevel,
-                      unsigned int subCACount)
-{
-  bool isCA = false;
-  long pathLenConstraint = UNLIMITED_PATH_LEN;
-
-  if (encodedBasicConstraints) {
-    Reader input(*encodedBasicConstraints);
-    Result rv = der::Nested(input, der::SEQUENCE,
-                            [&isCA, &pathLenConstraint](Reader& r) {
-      Result nestedRv = der::OptionalBoolean(r, isCA);
-      if (nestedRv != Success) {
-        return nestedRv;
-      }
-      // TODO(bug 985025): If isCA is false, pathLenConstraint
-      // MUST NOT be included (as per RFC 5280 section
-      // 4.2.1.9), but for compatibility reasons, we don't
-      // check this.
-      return der::OptionalInteger(r, UNLIMITED_PATH_LEN, pathLenConstraint);
-    });
-    if (rv != Success) {
-      return Result::ERROR_EXTENSION_VALUE_INVALID;
-    }
-    if (der::End(input) != Success) {
-      return Result::ERROR_EXTENSION_VALUE_INVALID;
-    }
-  } else {
-    // "If the basic constraints extension is not present in a version 3
-    //  certificate, or the extension is present but the cA boolean is not
-    //  asserted, then the certified public key MUST NOT be used to verify
-    //  certificate signatures."
-    //
-    // For compatibility, we must accept v1 trust anchors without basic
-    // constraints as CAs.
-    //
-    // There are devices with v1 certificates that are unlikely to be trust
-    // anchors. In order to allow applications to treat this case differently
-    // from other basic constraints violations (e.g. allowing certificate error
-    // overrides for only this case), we return a different error code.
-    //
-    // TODO: add check for self-signedness?
-    if (endEntityOrCA == EndEntityOrCA::MustBeCA && version == der::Version::v1) {
-      if (trustLevel == TrustLevel::TrustAnchor) {
-        isCA = true;
-      } else {
-        return Result::ERROR_V1_CERT_USED_AS_CA;
-      }
-    }
-  }
-
-  if (endEntityOrCA == EndEntityOrCA::MustBeEndEntity) {
-    // CA certificates are not trusted as EE certs.
-
-    if (isCA) {
-      // Note that this check prevents a delegated OCSP response signing
-      // certificate with the CA bit from successfully validating when we check
-      // it from pkixocsp.cpp, which is a good thing.
-      return Result::ERROR_CA_CERT_USED_AS_END_ENTITY;
-    }
-
-    return Success;
-  }
-
-  assert(endEntityOrCA == EndEntityOrCA::MustBeCA);
-
-  // End-entity certificates are not allowed to act as CA certs.
-  if (!isCA) {
-    return Result::ERROR_CA_CERT_INVALID;
-  }
-
-  if (pathLenConstraint >= 0 &&
-      static_cast<long>(subCACount) > pathLenConstraint) {
-    return Result::ERROR_PATH_LEN_CONSTRAINT_INVALID;
-  }
-
-  return Success;
-}
-
-// 4.2.1.12. Extended Key Usage (id-ce-extKeyUsage)
-
-static Result
-MatchEKU(Reader& value, KeyPurposeId requiredEKU,
-         EndEntityOrCA endEntityOrCA, TrustDomain& trustDomain,
-         Time notBefore, /*in/out*/ bool& found,
-         /*in/out*/ bool& foundOCSPSigning)
-{
-  // See Section 5.9 of "A Layman's Guide to a Subset of ASN.1, BER, and DER"
-  // for a description of ASN.1 DER encoding of OIDs.
-
-  // id-pkix  OBJECT IDENTIFIER  ::=
-  //            { iso(1) identified-organization(3) dod(6) internet(1)
-  //                    security(5) mechanisms(5) pkix(7) }
-  // id-kp OBJECT IDENTIFIER ::= { id-pkix 3 }
-  // id-kp-serverAuth      OBJECT IDENTIFIER ::= { id-kp 1 }
-  // id-kp-clientAuth      OBJECT IDENTIFIER ::= { id-kp 2 }
-  // id-kp-codeSigning     OBJECT IDENTIFIER ::= { id-kp 3 }
-  // id-kp-emailProtection OBJECT IDENTIFIER ::= { id-kp 4 }
-  // id-kp-OCSPSigning     OBJECT IDENTIFIER ::= { id-kp 9 }
-  static const uint8_t server[] = { (40*1)+3, 6, 1, 5, 5, 7, 3, 1 };
-  static const uint8_t client[] = { (40*1)+3, 6, 1, 5, 5, 7, 3, 2 };
-  static const uint8_t code  [] = { (40*1)+3, 6, 1, 5, 5, 7, 3, 3 };
-  static const uint8_t email [] = { (40*1)+3, 6, 1, 5, 5, 7, 3, 4 };
-  static const uint8_t ocsp  [] = { (40*1)+3, 6, 1, 5, 5, 7, 3, 9 };
-
-  // id-Netscape        OBJECT IDENTIFIER ::= { 2 16 840 1 113730 }
-  // id-Netscape-policy OBJECT IDENTIFIER ::= { id-Netscape 4 }
-  // id-Netscape-stepUp OBJECT IDENTIFIER ::= { id-Netscape-policy 1 }
-  static const uint8_t serverStepUp[] =
-    { (40*2)+16, 128+6,72, 1, 128+6,128+120,66, 4, 1 };
-
-  bool match = false;
-
-  if (!found) {
-    switch (requiredEKU) {
-      case KeyPurposeId::id_kp_serverAuth: {
-        if (value.MatchRest(server)) {
-          match = true;
-          break;
-        }
-        // Potentially treat CA certs with step-up OID as also having SSL server
-        // type. Comodo has issued certificates that require this behavior that
-        // don't expire until June 2020!
-        if (endEntityOrCA == EndEntityOrCA::MustBeCA &&
-            value.MatchRest(serverStepUp)) {
-          Result rv = trustDomain.NetscapeStepUpMatchesServerAuth(notBefore,
-                                                                  match);
-          if (rv != Success) {
-            return rv;
-          }
-        }
-        break;
-      }
-
-      case KeyPurposeId::id_kp_clientAuth:
-        match = value.MatchRest(client);
-        break;
-
-      case KeyPurposeId::id_kp_codeSigning:
-        match = value.MatchRest(code);
-        break;
-
-      case KeyPurposeId::id_kp_emailProtection:
-        match = value.MatchRest(email);
-        break;
-
-      case KeyPurposeId::id_kp_OCSPSigning:
-        match = value.MatchRest(ocsp);
-        break;
-
-      case KeyPurposeId::anyExtendedKeyUsage:
-        return NotReached("anyExtendedKeyUsage should start with found==true",
-                          Result::FATAL_ERROR_LIBRARY_FAILURE);
-    }
-  }
-
-  if (match) {
-    found = true;
-    if (requiredEKU == KeyPurposeId::id_kp_OCSPSigning) {
-      foundOCSPSigning = true;
-    }
-  } else if (value.MatchRest(ocsp)) {
-    foundOCSPSigning = true;
-  }
-
-  value.SkipToEnd(); // ignore unmatched OIDs.
-
-  return Success;
-}
-
-Result
-CheckExtendedKeyUsage(EndEntityOrCA endEntityOrCA,
-                      const Input* encodedExtendedKeyUsage,
-                      KeyPurposeId requiredEKU, TrustDomain& trustDomain,
-                      Time notBefore)
-{
-  // XXX: We're using Result::ERROR_INADEQUATE_CERT_TYPE here so that callers
-  // can distinguish EKU mismatch from KU mismatch from basic constraints
-  // mismatch. We should probably add a new error code that is more clear for
-  // this type of problem.
-
-  bool foundOCSPSigning = false;
-
-  if (encodedExtendedKeyUsage) {
-    bool found = requiredEKU == KeyPurposeId::anyExtendedKeyUsage;
-
-    Reader input(*encodedExtendedKeyUsage);
-    Result rv = der::NestedOf(input, der::SEQUENCE, der::OIDTag,
-                              der::EmptyAllowed::No, [&](Reader& r) {
-      return MatchEKU(r, requiredEKU, endEntityOrCA, trustDomain, notBefore,
-                      found, foundOCSPSigning);
-    });
-    if (rv != Success) {
-      return Result::ERROR_INADEQUATE_CERT_TYPE;
-    }
-    if (der::End(input) != Success) {
-      return Result::ERROR_INADEQUATE_CERT_TYPE;
-    }
-
-    // If the EKU extension was included, then the required EKU must be in the
-    // list.
-    if (!found) {
-      return Result::ERROR_INADEQUATE_CERT_TYPE;
-    }
-  }
-
-  // pkixocsp.cpp depends on the following additional checks.
-
-  if (endEntityOrCA == EndEntityOrCA::MustBeEndEntity) {
-    // When validating anything other than an delegated OCSP signing cert,
-    // reject any cert that also claims to be an OCSP responder, because such
-    // a cert does not make sense. For example, if an SSL certificate were to
-    // assert id-kp-OCSPSigning then it could sign OCSP responses for itself,
-    // if not for this check.
-    // That said, we accept CA certificates with id-kp-OCSPSigning because
-    // some CAs in Mozilla's CA program have issued such intermediate
-    // certificates, and because some CAs have reported some Microsoft server
-    // software wrongly requires CA certificates to have id-kp-OCSPSigning.
-    // Allowing this exception does not cause any security issues because we
-    // require delegated OCSP response signing certificates to be end-entity
-    // certificates.
-    if (foundOCSPSigning && requiredEKU != KeyPurposeId::id_kp_OCSPSigning) {
-      return Result::ERROR_INADEQUATE_CERT_TYPE;
-    }
-    // http://tools.ietf.org/html/rfc6960#section-4.2.2.2:
-    // "OCSP signing delegation SHALL be designated by the inclusion of
-    // id-kp-OCSPSigning in an extended key usage certificate extension
-    // included in the OCSP response signer's certificate."
-    //
-    // id-kp-OCSPSigning is the only EKU that isn't implicitly assumed when the
-    // EKU extension is missing from an end-entity certificate. However, any CA
-    // certificate can issue a delegated OCSP response signing certificate, so
-    // we can't require the EKU be explicitly included for CA certificates.
-    if (!foundOCSPSigning && requiredEKU == KeyPurposeId::id_kp_OCSPSigning) {
-      return Result::ERROR_INADEQUATE_CERT_TYPE;
-    }
-  }
-
-  return Success;
-}
-
-Result
-CheckTLSFeatures(const BackCert& subject, BackCert& potentialIssuer)
-{
-  const Input* issuerTLSFeatures = potentialIssuer.GetRequiredTLSFeatures();
-  if (!issuerTLSFeatures) {
-    return Success;
-  }
-
-  const Input* subjectTLSFeatures = subject.GetRequiredTLSFeatures();
-  if (issuerTLSFeatures->GetLength() == 0 ||
-      !subjectTLSFeatures ||
-      !InputsAreEqual(*issuerTLSFeatures, *subjectTLSFeatures)) {
-    return Result::ERROR_REQUIRED_TLS_FEATURE_MISSING;
-  }
-
-  return Success;
-}
-
-Result
-TLSFeaturesSatisfiedInternal(const Input* requiredTLSFeatures,
-                             const Input* stapledOCSPResponse)
-{
-  if (!requiredTLSFeatures) {
-    return Success;
-  }
-
-  // RFC 6066 10.2: ExtensionType status_request
-  const static uint8_t status_request = 5;
-  const static uint8_t status_request_bytes[] = { status_request };
-
-  Reader input(*requiredTLSFeatures);
-  return der::NestedOf(input, der::SEQUENCE, der::INTEGER,
-                       der::EmptyAllowed::No, [&](Reader& r) {
-    if (!r.MatchRest(status_request_bytes)) {
-      return Result::ERROR_REQUIRED_TLS_FEATURE_MISSING;
-    }
-
-    if (!stapledOCSPResponse) {
-      return Result::ERROR_REQUIRED_TLS_FEATURE_MISSING;
-    }
-
-    return Result::Success;
-  });
-}
-
-Result
-CheckTLSFeaturesAreSatisfied(Input& cert,
-                             const Input* stapledOCSPResponse)
-{
-  BackCert backCert(cert, EndEntityOrCA::MustBeEndEntity, nullptr);
-  Result rv = backCert.Init();
-  if (rv != Success) {
-    return rv;
-  }
-
-  return TLSFeaturesSatisfiedInternal(backCert.GetRequiredTLSFeatures(),
-                                      stapledOCSPResponse);
-}
-
-Result
-CheckIssuerIndependentProperties(TrustDomain& trustDomain,
-                                 const BackCert& cert,
-                                 Time time,
-                                 KeyUsage requiredKeyUsageIfPresent,
-                                 KeyPurposeId requiredEKUIfPresent,
-                                 const CertPolicyId& requiredPolicy,
-                                 unsigned int subCACount,
-                                 /*out*/ TrustLevel& trustLevel)
-{
-  Result rv;
-
-  const EndEntityOrCA endEntityOrCA = cert.endEntityOrCA;
-
-  // Check the cert's trust first, because we want to minimize the amount of
-  // processing we do on a distrusted cert, in case it is trying to exploit
-  // some bug in our processing.
-  rv = trustDomain.GetCertTrust(endEntityOrCA, requiredPolicy, cert.GetDER(),
-                                trustLevel);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // IMPORTANT: We parse the validity interval here, so that we can use the
-  // notBefore and notAfter values in checks for things that might be deprecated
-  // over time. However, we must not fail for semantic errors until the end of
-  // this method, in order to preserve error ranking.
-  Time notBefore(Time::uninitialized);
-  Time notAfter(Time::uninitialized);
-  rv = ParseValidity(cert.GetValidity(), &notBefore, &notAfter);
-  if (rv != Success) {
-    return rv;
-  }
-
-  if (trustLevel == TrustLevel::TrustAnchor &&
-      endEntityOrCA == EndEntityOrCA::MustBeEndEntity &&
-      requiredEKUIfPresent == KeyPurposeId::id_kp_OCSPSigning) {
-    // OCSP signer certificates can never be trust anchors, especially
-    // since we don't support designated OCSP responders. All of the checks
-    // below that are dependent on trustLevel rely on this overriding of the
-    // trust level for OCSP signers.
-    trustLevel = TrustLevel::InheritsTrust;
-  }
-
-  switch (trustLevel) {
-    case TrustLevel::InheritsTrust:
-      rv = CheckSignatureAlgorithm(trustDomain, endEntityOrCA, notBefore,
-                                   cert.GetSignedData(), cert.GetSignature());
-      if (rv != Success) {
-        return rv;
-      }
-      break;
-
-    case TrustLevel::TrustAnchor:
-      // We don't even bother checking signatureAlgorithm or signature for
-      // syntactic validity for trust anchors, because we don't use those
-      // fields for anything, and because the trust anchor might be signed
-      // with a signature algorithm we don't actually support.
-      break;
-
-    case TrustLevel::ActivelyDistrusted:
-      return Result::ERROR_UNTRUSTED_CERT;
-  }
-
-  // Check the SPKI early, because it is one of the most selective properties
-  // of the certificate due to SHA-1 deprecation and the deprecation of
-  // certificates with keys weaker than RSA 2048.
-  rv = CheckSubjectPublicKeyInfo(cert.GetSubjectPublicKeyInfo(), trustDomain,
-                                 endEntityOrCA);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // 4.1.2.4. Issuer
-  rv = CheckIssuer(cert.GetIssuer());
-  if (rv != Success) {
-    return rv;
-  }
-
-  // 4.2.1.1. Authority Key Identifier is ignored (see bug 965136).
-
-  // 4.2.1.2. Subject Key Identifier is ignored (see bug 965136).
-
-  // 4.2.1.3. Key Usage
-  rv = CheckKeyUsage(endEntityOrCA, cert.GetKeyUsage(),
-                     requiredKeyUsageIfPresent);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // 4.2.1.4. Certificate Policies
-  rv = CheckCertificatePolicies(endEntityOrCA, cert.GetCertificatePolicies(),
-                                cert.GetInhibitAnyPolicy(), trustLevel,
-                                requiredPolicy);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // 4.2.1.5. Policy Mappings are not supported; see the documentation about
-  //          policy enforcement in pkix.h.
-
-  // 4.2.1.6. Subject Alternative Name dealt with during name constraint
-  //          checking and during name verification (CERT_VerifyCertName).
-
-  // 4.2.1.7. Issuer Alternative Name is not something that needs checking.
-
-  // 4.2.1.8. Subject Directory Attributes is not something that needs
-  //          checking.
-
-  // 4.2.1.9. Basic Constraints.
-  rv = CheckBasicConstraints(endEntityOrCA, cert.GetBasicConstraints(),
-                             cert.GetVersion(), trustLevel, subCACount);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // 4.2.1.10. Name Constraints is dealt with in during path building.
-
-  // 4.2.1.11. Policy Constraints are implicitly supported; see the
-  //           documentation about policy enforcement in pkix.h.
-
-  // 4.2.1.12. Extended Key Usage
-  rv = CheckExtendedKeyUsage(endEntityOrCA, cert.GetExtKeyUsage(),
-                             requiredEKUIfPresent, trustDomain, notBefore);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // 4.2.1.13. CRL Distribution Points is not supported, though the
-  //           TrustDomain's CheckRevocation method may parse it and process it
-  //           on its own.
-
-  // 4.2.1.14. Inhibit anyPolicy is implicitly supported; see the documentation
-  //           about policy enforcement in pkix.h.
-
-  // IMPORTANT: Even though we parse validity above, we wait until this point to
-  // check it, so that error ranking works correctly.
-  rv = CheckValidity(time, notBefore, notAfter);
-  if (rv != Success) {
-    return rv;
-  }
-
-  rv = trustDomain.CheckValidityIsAcceptable(notBefore, notAfter, endEntityOrCA,
-                                             requiredEKUIfPresent);
-  if (rv != Success) {
-    return rv;
-  }
-
-  return Success;
-}
-
-} } // namespace mozilla::pkix
deleted file mode 100644
--- a/security/pkix/lib/pkixcheck.h
+++ /dev/null
@@ -1,66 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef mozilla_pkix_pkixcheck_h
-#define mozilla_pkix_pkixcheck_h
-
-#include "pkix/pkixtypes.h"
-
-namespace mozilla { namespace pkix {
-
-class BackCert;
-
-Result CheckIssuerIndependentProperties(
-          TrustDomain& trustDomain,
-          const BackCert& cert,
-          Time time,
-          KeyUsage requiredKeyUsageIfPresent,
-          KeyPurposeId requiredEKUIfPresent,
-          const CertPolicyId& requiredPolicy,
-          unsigned int subCACount,
-          /*out*/ TrustLevel& trustLevel);
-
-Result CheckNameConstraints(Input encodedNameConstraints,
-                            const BackCert& firstChild,
-                            KeyPurposeId requiredEKUIfPresent);
-
-Result CheckIssuer(Input encodedIssuer);
-
-// ParseValidity and CheckValidity are usually used together.  First you parse
-// the dates from the DER Validity sequence, then you compare them to the time
-// at which you are validating.  They are separate so that the notBefore and
-// notAfter times can be used for other things before they are checked against
-// the time of validation.
-Result ParseValidity(Input encodedValidity,
-                     /*optional out*/ Time* notBeforeOut = nullptr,
-                     /*optional out*/ Time* notAfterOut = nullptr);
-Result CheckValidity(Time time, Time notBefore, Time notAfter);
-
-// Check that a subject has TLS Feature (rfc7633) requirements that match its
-// potential issuer
-Result CheckTLSFeatures(const BackCert& subject, BackCert& potentialIssuer);
-
-} } // namespace mozilla::pkix
-
-#endif // mozilla_pkix_pkixcheck_h
deleted file mode 100644
--- a/security/pkix/lib/pkixder.cpp
+++ /dev/null
@@ -1,611 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "pkixder.h"
-
-#include "pkixutil.h"
-
-namespace mozilla { namespace pkix { namespace der {
-
-// Too complicated to be inline
-Result
-ReadTagAndGetValue(Reader& input, /*out*/ uint8_t& tag, /*out*/ Input& value)
-{
-  Result rv;
-
-  rv = input.Read(tag);
-  if (rv != Success) {
-    return rv;
-  }
-  if ((tag & 0x1F) == 0x1F) {
-    return Result::ERROR_BAD_DER; // high tag number form not allowed
-  }
-
-  uint16_t length;
-
-  // The short form of length is a single byte with the high order bit set
-  // to zero. The long form of length is one byte with the high order bit
-  // set, followed by N bytes, where N is encoded in the lowest 7 bits of
-  // the first byte.
-  uint8_t length1;
-  rv = input.Read(length1);
-  if (rv != Success) {
-    return rv;
-  }
-  if (!(length1 & 0x80)) {
-    length = length1;
-  } else if (length1 == 0x81) {
-    uint8_t length2;
-    rv = input.Read(length2);
-    if (rv != Success) {
-      return rv;
-    }
-    if (length2 < 128) {
-      // Not shortest possible encoding
-      return Result::ERROR_BAD_DER;
-    }
-    length = length2;
-  } else if (length1 == 0x82) {
-    rv = input.Read(length);
-    if (rv != Success) {
-      return rv;
-    }
-    if (length < 256) {
-      // Not shortest possible encoding
-      return Result::ERROR_BAD_DER;
-    }
-  } else {
-    // We don't support lengths larger than 2^16 - 1.
-    return Result::ERROR_BAD_DER;
-  }
-
-  return input.Skip(length, value);
-}
-
-static Result
-OptionalNull(Reader& input)
-{
-  if (input.Peek(NULLTag)) {
-    return Null(input);
-  }
-  return Success;
-}
-
-namespace {
-
-Result
-AlgorithmIdentifierValue(Reader& input, /*out*/ Reader& algorithmOIDValue)
-{
-  Result rv = ExpectTagAndGetValue(input, der::OIDTag, algorithmOIDValue);
-  if (rv != Success) {
-    return rv;
-  }
-  return OptionalNull(input);
-}
-
-} // namespace
-
-Result
-SignatureAlgorithmIdentifierValue(Reader& input,
-                                 /*out*/ PublicKeyAlgorithm& publicKeyAlgorithm,
-                                 /*out*/ DigestAlgorithm& digestAlgorithm)
-{
-  // RFC 5758 Section 3.2 (ECDSA with SHA-2), and RFC 3279 Section 2.2.3
-  // (ECDSA with SHA-1) say that parameters must be omitted.
-  //
-  // RFC 4055 Section 5 and RFC 3279 Section 2.2.1 both say that parameters for
-  // RSA must be encoded as NULL; we relax that requirement by allowing the
-  // NULL to be omitted, to match all the other signature algorithms we support
-  // and for compatibility.
-  Reader algorithmID;
-  Result rv = AlgorithmIdentifierValue(input, algorithmID);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // RFC 5758 Section 3.2 (ecdsa-with-SHA224 is intentionally excluded)
-  // python DottedOIDToCode.py ecdsa-with-SHA256 1.2.840.10045.4.3.2
-  static const uint8_t ecdsa_with_SHA256[] = {
-    0x2a, 0x86, 0x48, 0xce, 0x3d, 0x04, 0x03, 0x02
-  };
-  // python DottedOIDToCode.py ecdsa-with-SHA384 1.2.840.10045.4.3.3
-  static const uint8_t ecdsa_with_SHA384[] = {
-    0x2a, 0x86, 0x48, 0xce, 0x3d, 0x04, 0x03, 0x03
-  };
-  // python DottedOIDToCode.py ecdsa-with-SHA512 1.2.840.10045.4.3.4
-  static const uint8_t ecdsa_with_SHA512[] = {
-    0x2a, 0x86, 0x48, 0xce, 0x3d, 0x04, 0x03, 0x04
-  };
-
-  // RFC 4055 Section 5 (sha224WithRSAEncryption is intentionally excluded)
-  // python DottedOIDToCode.py sha256WithRSAEncryption 1.2.840.113549.1.1.11
-  static const uint8_t sha256WithRSAEncryption[] = {
-    0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0b
-  };
-  // python DottedOIDToCode.py sha384WithRSAEncryption 1.2.840.113549.1.1.12
-  static const uint8_t sha384WithRSAEncryption[] = {
-    0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0c
-  };
-  // python DottedOIDToCode.py sha512WithRSAEncryption 1.2.840.113549.1.1.13
-  static const uint8_t sha512WithRSAEncryption[] = {
-    0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x0d
-  };
-
-  // RFC 3279 Section 2.2.1
-  // python DottedOIDToCode.py sha-1WithRSAEncryption 1.2.840.113549.1.1.5
-  static const uint8_t sha_1WithRSAEncryption[] = {
-    0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x05
-  };
-
-  // NIST Open Systems Environment (OSE) Implementor's Workshop (OIW)
-  // http://www.oiw.org/agreements/stable/12s-9412.txt (no longer works).
-  // http://www.imc.org/ietf-pkix/old-archive-97/msg01166.html
-  // We need to support this this non-PKIX OID for compatibility.
-  // python DottedOIDToCode.py sha1WithRSASignature 1.3.14.3.2.29
-  static const uint8_t sha1WithRSASignature[] = {
-    0x2b, 0x0e, 0x03, 0x02, 0x1d
-  };
-
-  // RFC 3279 Section 2.2.3
-  // python DottedOIDToCode.py ecdsa-with-SHA1 1.2.840.10045.4.1
-  static const uint8_t ecdsa_with_SHA1[] = {
-    0x2a, 0x86, 0x48, 0xce, 0x3d, 0x04, 0x01
-  };
-
-  // Matching is attempted based on a rough estimate of the commonality of the
-  // algorithm, to minimize the number of MatchRest calls.
-  if (algorithmID.MatchRest(sha256WithRSAEncryption)) {
-    publicKeyAlgorithm = PublicKeyAlgorithm::RSA_PKCS1;
-    digestAlgorithm = DigestAlgorithm::sha256;
-  } else if (algorithmID.MatchRest(ecdsa_with_SHA256)) {
-    publicKeyAlgorithm = PublicKeyAlgorithm::ECDSA;
-    digestAlgorithm = DigestAlgorithm::sha256;
-  } else if (algorithmID.MatchRest(sha_1WithRSAEncryption)) {
-    publicKeyAlgorithm = PublicKeyAlgorithm::RSA_PKCS1;
-    digestAlgorithm = DigestAlgorithm::sha1;
-  } else if (algorithmID.MatchRest(ecdsa_with_SHA1)) {
-    publicKeyAlgorithm = PublicKeyAlgorithm::ECDSA;
-    digestAlgorithm = DigestAlgorithm::sha1;
-  } else if (algorithmID.MatchRest(ecdsa_with_SHA384)) {
-    publicKeyAlgorithm = PublicKeyAlgorithm::ECDSA;
-    digestAlgorithm = DigestAlgorithm::sha384;
-  } else if (algorithmID.MatchRest(ecdsa_with_SHA512)) {
-    publicKeyAlgorithm = PublicKeyAlgorithm::ECDSA;
-    digestAlgorithm = DigestAlgorithm::sha512;
-  } else if (algorithmID.MatchRest(sha384WithRSAEncryption)) {
-    publicKeyAlgorithm = PublicKeyAlgorithm::RSA_PKCS1;
-    digestAlgorithm = DigestAlgorithm::sha384;
-  } else if (algorithmID.MatchRest(sha512WithRSAEncryption)) {
-    publicKeyAlgorithm = PublicKeyAlgorithm::RSA_PKCS1;
-    digestAlgorithm = DigestAlgorithm::sha512;
-  } else if (algorithmID.MatchRest(sha1WithRSASignature)) {
-    // XXX(bug 1042479): recognize this old OID for compatibility.
-    publicKeyAlgorithm = PublicKeyAlgorithm::RSA_PKCS1;
-    digestAlgorithm = DigestAlgorithm::sha1;
-  } else {
-    return Result::ERROR_CERT_SIGNATURE_ALGORITHM_DISABLED;
-  }
-
-  return Success;
-}
-
-Result
-DigestAlgorithmIdentifier(Reader& input, /*out*/ DigestAlgorithm& algorithm)
-{
-  return der::Nested(input, SEQUENCE, [&algorithm](Reader& r) -> Result {
-    Reader algorithmID;
-    Result rv = AlgorithmIdentifierValue(r, algorithmID);
-    if (rv != Success) {
-      return rv;
-    }
-
-    // RFC 4055 Section 2.1
-    // python DottedOIDToCode.py id-sha1 1.3.14.3.2.26
-    static const uint8_t id_sha1[] = {
-      0x2b, 0x0e, 0x03, 0x02, 0x1a
-    };
-    // python DottedOIDToCode.py id-sha256 2.16.840.1.101.3.4.2.1
-    static const uint8_t id_sha256[] = {
-      0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x01
-    };
-    // python DottedOIDToCode.py id-sha384 2.16.840.1.101.3.4.2.2
-    static const uint8_t id_sha384[] = {
-      0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x02
-    };
-    // python DottedOIDToCode.py id-sha512 2.16.840.1.101.3.4.2.3
-    static const uint8_t id_sha512[] = {
-      0x60, 0x86, 0x48, 0x01, 0x65, 0x03, 0x04, 0x02, 0x03
-    };
-
-    // Matching is attempted based on a rough estimate of the commonality of the
-    // algorithm, to minimize the number of MatchRest calls.
-    if (algorithmID.MatchRest(id_sha1)) {
-      algorithm = DigestAlgorithm::sha1;
-    } else if (algorithmID.MatchRest(id_sha256)) {
-      algorithm = DigestAlgorithm::sha256;
-    } else if (algorithmID.MatchRest(id_sha384)) {
-      algorithm = DigestAlgorithm::sha384;
-    } else if (algorithmID.MatchRest(id_sha512)) {
-      algorithm = DigestAlgorithm::sha512;
-    } else {
-      return Result::ERROR_INVALID_ALGORITHM;
-    }
-
-    return Success;
-  });
-}
-
-Result
-SignedData(Reader& input, /*out*/ Reader& tbs,
-           /*out*/ SignedDataWithSignature& signedData)
-{
-  Reader::Mark mark(input.GetMark());
-
-  Result rv;
-  rv = ExpectTagAndGetValue(input, SEQUENCE, tbs);
-  if (rv != Success) {
-    return rv;
-  }
-
-  rv = input.GetInput(mark, signedData.data);
-  if (rv != Success) {
-    return rv;
-  }
-
-  rv = ExpectTagAndGetValue(input, der::SEQUENCE, signedData.algorithm);
-  if (rv != Success) {
-    return rv;
-  }
-
-  rv = BitStringWithNoUnusedBits(input, signedData.signature);
-  if (rv == Result::ERROR_BAD_DER) {
-    rv = Result::ERROR_BAD_SIGNATURE;
-  }
-  return rv;
-}
-
-Result
-BitStringWithNoUnusedBits(Reader& input, /*out*/ Input& value)
-{
-  Reader valueWithUnusedBits;
-  Result rv = ExpectTagAndGetValue(input, BIT_STRING, valueWithUnusedBits);
-  if (rv != Success) {
-    return rv;
-  }
-
-  uint8_t unusedBitsAtEnd;
-  if (valueWithUnusedBits.Read(unusedBitsAtEnd) != Success) {
-    return Result::ERROR_BAD_DER;
-  }
-  // XXX: Really the constraint should be that unusedBitsAtEnd must be less
-  // than 7. But, we suspect there are no real-world values in OCSP responses
-  // or certificates with non-zero unused bits. It seems like NSS assumes this
-  // in various places, so we enforce it too in order to simplify this code. If
-  // we find compatibility issues, we'll know we're wrong and we'll have to
-  // figure out how to shift the bits around.
-  if (unusedBitsAtEnd != 0) {
-    return Result::ERROR_BAD_DER;
-  }
-  return valueWithUnusedBits.SkipToEnd(value);
-}
-
-static inline Result
-ReadDigit(Reader& input, /*out*/ unsigned int& value)
-{
-  uint8_t b;
-  if (input.Read(b) != Success) {
-    return Result::ERROR_INVALID_DER_TIME;
-  }
-  if (b < '0' || b > '9') {
-    return Result::ERROR_INVALID_DER_TIME;
-  }
-  value = static_cast<unsigned int>(b - static_cast<uint8_t>('0'));
-  return Success;
-}
-
-static inline Result
-ReadTwoDigits(Reader& input, unsigned int minValue, unsigned int maxValue,
-              /*out*/ unsigned int& value)
-{
-  unsigned int hi;
-  Result rv = ReadDigit(input, hi);
-  if (rv != Success) {
-    return rv;
-  }
-  unsigned int lo;
-  rv = ReadDigit(input, lo);
-  if (rv != Success) {
-    return rv;
-  }
-  value = (hi * 10) + lo;
-  if (value < minValue || value > maxValue) {
-    return Result::ERROR_INVALID_DER_TIME;
-  }
-  return Success;
-}
-
-namespace internal {
-
-// We parse GeneralizedTime and UTCTime according to RFC 5280 and we do not
-// accept all time formats allowed in the ASN.1 spec. That is,
-// GeneralizedTime must always be in the format YYYYMMDDHHMMSSZ and UTCTime
-// must always be in the format YYMMDDHHMMSSZ. Timezone formats of the form
-// +HH:MM or -HH:MM or NOT accepted.
-Result
-TimeChoice(Reader& tagged, uint8_t expectedTag, /*out*/ Time& time)
-{
-  unsigned int days;
-
-  Reader input;
-  Result rv = ExpectTagAndGetValue(tagged, expectedTag, input);
-  if (rv != Success) {
-    return rv;
-  }
-
-  unsigned int yearHi;
-  unsigned int yearLo;
-  if (expectedTag == GENERALIZED_TIME) {
-    rv = ReadTwoDigits(input, 0, 99, yearHi);
-    if (rv != Success) {
-      return rv;
-    }
-    rv = ReadTwoDigits(input, 0, 99, yearLo);
-    if (rv != Success) {
-      return rv;
-    }
-  } else if (expectedTag == UTCTime) {
-    rv = ReadTwoDigits(input, 0, 99, yearLo);
-    if (rv != Success) {
-      return rv;
-    }
-    yearHi = yearLo >= 50u ? 19u : 20u;
-  } else {
-    return NotReached("invalid tag given to TimeChoice",
-                      Result::ERROR_INVALID_DER_TIME);
-  }
-  unsigned int year = (yearHi * 100u) + yearLo;
-  if (year < 1970u) {
-    // We don't support dates before January 1, 1970 because that is the epoch.
-    return Result::ERROR_INVALID_DER_TIME;
-  }
-  days = DaysBeforeYear(year);
-
-  unsigned int month;
-  rv = ReadTwoDigits(input, 1u, 12u, month);
-  if (rv != Success) {
-    return rv;
-  }
-  unsigned int daysInMonth;
-  static const unsigned int jan = 31u;
-  const unsigned int feb = ((year % 4u == 0u) &&
-                           ((year % 100u != 0u) || (year % 400u == 0u)))
-                         ? 29u
-                         : 28u;
-  static const unsigned int mar = 31u;
-  static const unsigned int apr = 30u;
-  static const unsigned int may = 31u;
-  static const unsigned int jun = 30u;
-  static const unsigned int jul = 31u;
-  static const unsigned int aug = 31u;
-  static const unsigned int sep = 30u;
-  static const unsigned int oct = 31u;
-  static const unsigned int nov = 30u;
-  static const unsigned int dec = 31u;
-  switch (month) {
-    case 1:  daysInMonth = jan; break;
-    case 2:  daysInMonth = feb; days += jan; break;
-    case 3:  daysInMonth = mar; days += jan + feb; break;
-    case 4:  daysInMonth = apr; days += jan + feb + mar; break;
-    case 5:  daysInMonth = may; days += jan + feb + mar + apr; break;
-    case 6:  daysInMonth = jun; days += jan + feb + mar + apr + may; break;
-    case 7:  daysInMonth = jul; days += jan + feb + mar + apr + may + jun;
-             break;
-    case 8:  daysInMonth = aug; days += jan + feb + mar + apr + may + jun +
-                                        jul;
-             break;
-    case 9:  daysInMonth = sep; days += jan + feb + mar + apr + may + jun +
-                                        jul + aug;
-             break;
-    case 10: daysInMonth = oct; days += jan + feb + mar + apr + may + jun +
-                                        jul + aug + sep;
-             break;
-    case 11: daysInMonth = nov; days += jan + feb + mar + apr + may + jun +
-                                        jul + aug + sep + oct;
-             break;
-    case 12: daysInMonth = dec; days += jan + feb + mar + apr + may + jun +
-                                        jul + aug + sep + oct + nov;
-             break;
-    default:
-      return NotReached("month already bounds-checked by ReadTwoDigits",
-                        Result::FATAL_ERROR_INVALID_STATE);
-  }
-
-  unsigned int dayOfMonth;
-  rv = ReadTwoDigits(input, 1u, daysInMonth, dayOfMonth);
-  if (rv != Success) {
-    return rv;
-  }
-  days += dayOfMonth - 1;
-
-  unsigned int hours;
-  rv = ReadTwoDigits(input, 0u, 23u, hours);
-  if (rv != Success) {
-    return rv;
-  }
-  unsigned int minutes;
-  rv = ReadTwoDigits(input, 0u, 59u, minutes);
-  if (rv != Success) {
-    return rv;
-  }
-  unsigned int seconds;
-  rv = ReadTwoDigits(input, 0u, 59u, seconds);
-  if (rv != Success) {
-    return rv;
-  }
-
-  uint8_t b;
-  if (input.Read(b) != Success) {
-    return Result::ERROR_INVALID_DER_TIME;
-  }
-  if (b != 'Z') {
-    return Result::ERROR_INVALID_DER_TIME;
-  }
-  if (End(input) != Success) {
-    return Result::ERROR_INVALID_DER_TIME;
-  }
-
-  uint64_t totalSeconds = (static_cast<uint64_t>(days) * 24u * 60u * 60u) +
-                          (static_cast<uint64_t>(hours)      * 60u * 60u) +
-                          (static_cast<uint64_t>(minutes)          * 60u) +
-                          seconds;
-
-  time = TimeFromElapsedSecondsAD(totalSeconds);
-  return Success;
-}
-
-Result
-IntegralBytes(Reader& input, uint8_t tag,
-              IntegralValueRestriction valueRestriction,
-              /*out*/ Input& value,
-              /*optional out*/ Input::size_type* significantBytes)
-{
-  Result rv = ExpectTagAndGetValue(input, tag, value);
-  if (rv != Success) {
-    return rv;
-  }
-  Reader reader(value);
-
-  // There must be at least one byte in the value. (Zero is encoded with a
-  // single 0x00 value byte.)
-  uint8_t firstByte;
-  rv = reader.Read(firstByte);
-  if (rv != Success) {
-    if (rv == Result::ERROR_BAD_DER) {
-      return Result::ERROR_INVALID_INTEGER_ENCODING;
-    }
-
-    return rv;
-  }
-
-  // If there is a byte after an initial 0x00/0xFF, then the initial byte
-  // indicates a positive/negative integer value with its high bit set/unset.
-  bool prefixed = !reader.AtEnd() && (firstByte == 0 || firstByte == 0xff);
-
-  if (prefixed) {
-    uint8_t nextByte;
-    if (reader.Read(nextByte) != Success) {
-      return NotReached("Read of one byte failed but not at end.",
-                        Result::FATAL_ERROR_LIBRARY_FAILURE);
-    }
-    if ((firstByte & 0x80) == (nextByte & 0x80)) {
-      return Result::ERROR_INVALID_INTEGER_ENCODING;
-    }
-  }
-
-  switch (valueRestriction) {
-    case IntegralValueRestriction::MustBe0To127:
-      if (value.GetLength() != 1 || (firstByte & 0x80) != 0) {
-        return Result::ERROR_INVALID_INTEGER_ENCODING;
-      }
-      break;
-
-    case IntegralValueRestriction::MustBePositive:
-      if ((value.GetLength() == 1 && firstByte == 0) ||
-          (firstByte & 0x80) != 0) {
-        return Result::ERROR_INVALID_INTEGER_ENCODING;
-      }
-      break;
-
-    case IntegralValueRestriction::NoRestriction:
-      break;
-  }
-
-  if (significantBytes) {
-    *significantBytes = value.GetLength();
-    if (prefixed) {
-      assert(*significantBytes > 1);
-      --*significantBytes;
-    }
-
-    assert(*significantBytes > 0);
-  }
-
-  return Success;
-}
-
-// This parser will only parse values between 0..127. If this range is
-// increased then callers will need to be changed.
-Result
-IntegralValue(Reader& input, uint8_t tag, /*out*/ uint8_t& value)
-{
-  // Conveniently, all the Integers that we actually have to be able to parse
-  // are positive and very small. Consequently, this parser is *much* simpler
-  // than a general Integer parser would need to be.
-  Input valueBytes;
-  Result rv = IntegralBytes(input, tag, IntegralValueRestriction::MustBe0To127,
-                            valueBytes, nullptr);
-  if (rv != Success) {
-    return rv;
-  }
-  Reader valueReader(valueBytes);
-  rv = valueReader.Read(value);
-  if (rv != Success) {
-    return NotReached("IntegralBytes already validated the value.", rv);
-  }
-  rv = End(valueReader);
-  assert(rv == Success); // guaranteed by IntegralBytes's range checks.
-  return rv;
-}
-
-} // namespace internal
-
-Result
-OptionalVersion(Reader& input, /*out*/ Version& version)
-{
-  static const uint8_t TAG = CONTEXT_SPECIFIC | CONSTRUCTED | 0;
-  if (!input.Peek(TAG)) {
-    version = Version::v1;
-    return Success;
-  }
-  return Nested(input, TAG, [&version](Reader& value) -> Result {
-    uint8_t integerValue;
-    Result rv = Integer(value, integerValue);
-    if (rv != Success) {
-      return rv;
-    }
-    // XXX(bug 1031093): We shouldn't accept an explicit encoding of v1,
-    // but we do here for compatibility reasons.
-    switch (integerValue) {
-      case static_cast<uint8_t>(Version::v3): version = Version::v3; break;
-      case static_cast<uint8_t>(Version::v2): version = Version::v2; break;
-      case static_cast<uint8_t>(Version::v1): version = Version::v1; break;
-      case static_cast<uint8_t>(Version::v4): version = Version::v4; break;
-      default:
-        return Result::ERROR_BAD_DER;
-    }
-    return Success;
-  });
-}
-
-} } } // namespace mozilla::pkix::der
deleted file mode 100644
--- a/security/pkix/lib/pkixder.h
+++ /dev/null
@@ -1,566 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef mozilla_pkix_pkixder_h
-#define mozilla_pkix_pkixder_h
-
-// Expect* functions advance the input mark and return Success if the input
-// matches the given criteria; they fail with the input mark in an undefined
-// state if the input does not match the criteria.
-//
-// Match* functions advance the input mark and return true if the input matches
-// the given criteria; they return false without changing the input mark if the
-// input does not match the criteria.
-//
-// Skip* functions unconditionally advance the input mark and return Success if
-// they are able to do so; otherwise they fail with the input mark in an
-// undefined state.
-
-#include "pkix/Input.h"
-#include "pkix/pkixtypes.h"
-
-namespace mozilla { namespace pkix { namespace der {
-
-enum Class : uint8_t
-{
-   UNIVERSAL = 0 << 6,
-// APPLICATION = 1 << 6, // unused
-   CONTEXT_SPECIFIC = 2 << 6,
-// PRIVATE = 3 << 6 // unused
-};
-
-enum Constructed
-{
-  CONSTRUCTED = 1 << 5
-};
-
-enum Tag : uint8_t
-{
-  BOOLEAN = UNIVERSAL | 0x01,
-  INTEGER = UNIVERSAL | 0x02,
-  BIT_STRING = UNIVERSAL | 0x03,
-  OCTET_STRING = UNIVERSAL | 0x04,
-  NULLTag = UNIVERSAL | 0x05,
-  OIDTag = UNIVERSAL | 0x06,
-  ENUMERATED = UNIVERSAL | 0x0a,
-  UTF8String = UNIVERSAL | 0x0c,
-  SEQUENCE = UNIVERSAL | CONSTRUCTED | 0x10, // 0x30
-  SET = UNIVERSAL | CONSTRUCTED | 0x11, // 0x31
-  PrintableString = UNIVERSAL | 0x13,
-  TeletexString = UNIVERSAL | 0x14,
-  IA5String = UNIVERSAL | 0x16,
-  UTCTime = UNIVERSAL | 0x17,
-  GENERALIZED_TIME = UNIVERSAL | 0x18,
-};
-
-enum class EmptyAllowed { No = 0, Yes = 1 };
-
-Result ReadTagAndGetValue(Reader& input, /*out*/ uint8_t& tag,
-                          /*out*/ Input& value);
-Result End(Reader& input);
-
-inline Result
-ExpectTagAndGetValue(Reader& input, uint8_t tag, /*out*/ Input& value)
-{
-  uint8_t actualTag;
-  Result rv = ReadTagAndGetValue(input, actualTag, value);
-  if (rv != Success) {
-    return rv;
-  }
-  if (tag != actualTag) {
-    return Result::ERROR_BAD_DER;
-  }
-  return Success;
-}
-
-inline Result
-ExpectTagAndGetValue(Reader& input, uint8_t tag, /*out*/ Reader& value)
-{
-  Input valueInput;
-  Result rv = ExpectTagAndGetValue(input, tag, valueInput);
-  if (rv != Success) {
-    return rv;
-  }
-  return value.Init(valueInput);
-}
-
-inline Result
-ExpectTagAndEmptyValue(Reader& input, uint8_t tag)
-{
-  Reader value;
-  Result rv = ExpectTagAndGetValue(input, tag, value);
-  if (rv != Success) {
-    return rv;
-  }
-  return End(value);
-}
-
-inline Result
-ExpectTagAndSkipValue(Reader& input, uint8_t tag)
-{
-  Input ignoredValue;
-  return ExpectTagAndGetValue(input, tag, ignoredValue);
-}
-
-// Like ExpectTagAndGetValue, except the output Input will contain the
-// encoded tag and length along with the value.
-inline Result
-ExpectTagAndGetTLV(Reader& input, uint8_t tag, /*out*/ Input& tlv)
-{
-  Reader::Mark mark(input.GetMark());
-  Result rv = ExpectTagAndSkipValue(input, tag);
-  if (rv != Success) {
-    return rv;
-  }
-  return input.GetInput(mark, tlv);
-}
-
-inline Result
-End(Reader& input)
-{
-  if (!input.AtEnd()) {
-    return Result::ERROR_BAD_DER;
-  }
-
-  return Success;
-}
-
-template <typename Decoder>
-inline Result
-Nested(Reader& input, uint8_t tag, Decoder decoder)
-{
-  Reader nested;
-  Result rv = ExpectTagAndGetValue(input, tag, nested);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = decoder(nested);
-  if (rv != Success) {
-    return rv;
-  }
-  return End(nested);
-}
-
-template <typename Decoder>
-inline Result
-Nested(Reader& input, uint8_t outerTag, uint8_t innerTag, Decoder decoder)
-{
-  Reader nestedInput;
-  Result rv = ExpectTagAndGetValue(input, outerTag, nestedInput);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = Nested(nestedInput, innerTag, decoder);
-  if (rv != Success) {
-    return rv;
-  }
-  return End(nestedInput);
-}
-
-// This can be used to decode constructs like this:
-//
-//     ...
-//     foos SEQUENCE OF Foo,
-//     ...
-//     Foo ::= SEQUENCE {
-//     }
-//
-// using code like this:
-//
-//    Result Foo(Reader& r) { /*...*/ }
-//
-//    rv = der::NestedOf(input, der::SEQEUENCE, der::SEQUENCE, Foo);
-//
-// or:
-//
-//    Result Bar(Reader& r, int value) { /*...*/ }
-//
-//    int value = /*...*/;
-//
-//    rv = der::NestedOf(input, der::SEQUENCE, [value](Reader& r) {
-//      return Bar(r, value);
-//    });
-//
-// In these examples the function will get called once for each element of
-// foos.
-//
-template <typename Decoder>
-inline Result
-NestedOf(Reader& input, uint8_t outerTag, uint8_t innerTag,
-         EmptyAllowed mayBeEmpty, Decoder decoder)
-{
-  Reader inner;
-  Result rv = ExpectTagAndGetValue(input, outerTag, inner);
-  if (rv != Success) {
-    return rv;
-  }
-
-  if (inner.AtEnd()) {
-    if (mayBeEmpty != EmptyAllowed::Yes) {
-      return Result::ERROR_BAD_DER;
-    }
-    return Success;
-  }
-
-  do {
-    rv = Nested(inner, innerTag, decoder);
-    if (rv != Success) {
-      return rv;
-    }
-  } while (!inner.AtEnd());
-
-  return Success;
-}
-
-// Often, a function will need to decode an Input or Reader that contains
-// DER-encoded data wrapped in a SEQUENCE (or similar) with nothing after it.
-// This function reduces the boilerplate necessary for stripping the outermost
-// SEQUENCE (or similar) and ensuring that nothing follows it.
-inline Result
-ExpectTagAndGetValueAtEnd(Reader& outer, uint8_t expectedTag,
-                          /*out*/ Reader& inner)
-{
-  Result rv = der::ExpectTagAndGetValue(outer, expectedTag, inner);
-  if (rv != Success) {
-    return rv;
-  }
-  return der::End(outer);
-}
-
-// Similar to the above, but takes an Input instead of a Reader&.
-inline Result
-ExpectTagAndGetValueAtEnd(Input outer, uint8_t expectedTag,
-                          /*out*/ Reader& inner)
-{
-  Reader outerReader(outer);
-  return ExpectTagAndGetValueAtEnd(outerReader, expectedTag, inner);
-}
-
-// Universal types
-
-namespace internal {
-
-enum class IntegralValueRestriction
-{
-  NoRestriction,
-  MustBePositive,
-  MustBe0To127,
-};
-
-Result IntegralBytes(Reader& input, uint8_t tag,
-                     IntegralValueRestriction valueRestriction,
-             /*out*/ Input& value,
-    /*optional out*/ Input::size_type* significantBytes = nullptr);
-
-// This parser will only parse values between 0..127. If this range is
-// increased then callers will need to be changed.
-Result IntegralValue(Reader& input, uint8_t tag, /*out*/ uint8_t& value);
-
-} // namespace internal
-
-Result
-BitStringWithNoUnusedBits(Reader& input, /*out*/ Input& value);
-
-inline Result
-Boolean(Reader& input, /*out*/ bool& value)
-{
-  Reader valueReader;
-  Result rv = ExpectTagAndGetValue(input, BOOLEAN, valueReader);
-  if (rv != Success) {
-    return rv;
-  }
-
-  uint8_t intValue;
-  rv = valueReader.Read(intValue);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = End(valueReader);
-  if (rv != Success) {
-    return rv;
-  }
-  switch (intValue) {
-    case 0: value = false; return Success;
-    case 0xFF: value = true; return Success;
-    default:
-      return Result::ERROR_BAD_DER;
-  }
-}
-
-// This is for BOOLEAN DEFAULT FALSE.
-// The standard stipulates that "The encoding of a set value or sequence value
-// shall not include an encoding for any component value which is equal to its
-// default value." However, it appears to be common that other libraries
-// incorrectly include the value of a BOOLEAN even when it's equal to the
-// default value, so we allow invalid explicit encodings here.
-inline Result
-OptionalBoolean(Reader& input, /*out*/ bool& value)
-{
-  value = false;
-  if (input.Peek(BOOLEAN)) {
-    Result rv = Boolean(input, value);
-    if (rv != Success) {
-      return rv;
-    }
-  }
-  return Success;
-}
-
-// This parser will only parse values between 0..127. If this range is
-// increased then callers will need to be changed.
-inline Result
-Enumerated(Reader& input, uint8_t& value)
-{
-  return internal::IntegralValue(input, ENUMERATED | 0, value);
-}
-
-namespace internal {
-
-// internal::TimeChoice implements the shared functionality of GeneralizedTime
-// and TimeChoice. tag must be either UTCTime or GENERALIZED_TIME.
-//
-// Only times from 1970-01-01-00:00:00 onward are accepted, in order to
-// eliminate the chance for complications in converting times to traditional
-// time formats that start at 1970.
-Result TimeChoice(Reader& input, uint8_t tag, /*out*/ Time& time);
-
-} // namespace internal
-
-// Only times from 1970-01-01-00:00:00 onward are accepted, in order to
-// eliminate the chance for complications in converting times to traditional
-// time formats that start at 1970.
-inline Result
-GeneralizedTime(Reader& input, /*out*/ Time& time)
-{
-  return internal::TimeChoice(input, GENERALIZED_TIME, time);
-}
-
-// Only times from 1970-01-01-00:00:00 onward are accepted, in order to
-// eliminate the chance for complications in converting times to traditional
-// time formats that start at 1970.
-inline Result
-TimeChoice(Reader& input, /*out*/ Time& time)
-{
-  uint8_t expectedTag = input.Peek(UTCTime) ? UTCTime : GENERALIZED_TIME;
-  return internal::TimeChoice(input, expectedTag, time);
-}
-
-// Parse a DER integer value into value. Empty values, negative values, and
-// zero are rejected. If significantBytes is not null, then it will be set to
-// the number of significant bytes in the value (the length of the value, less
-// the length of any leading padding), which is useful for key size checks.
-inline Result
-PositiveInteger(Reader& input, /*out*/ Input& value,
-                /*optional out*/ Input::size_type* significantBytes = nullptr)
-{
-  return internal::IntegralBytes(
-           input, INTEGER, internal::IntegralValueRestriction::MustBePositive,
-           value, significantBytes);
-}
-
-// This parser will only parse values between 0..127. If this range is
-// increased then callers will need to be changed.
-inline Result
-Integer(Reader& input, /*out*/ uint8_t& value)
-{
-  return internal::IntegralValue(input, INTEGER, value);
-}
-
-// This parser will only parse values between 0..127. If this range is
-// increased then callers will need to be changed. The default value must be
-// -1; defaultValue is only a parameter to make it clear in the calling code
-// what the default value is.
-inline Result
-OptionalInteger(Reader& input, long defaultValue, /*out*/ long& value)
-{
-  // If we need to support a different default value in the future, we need to
-  // test that parsedValue != defaultValue.
-  if (defaultValue != -1) {
-    return Result::FATAL_ERROR_INVALID_ARGS;
-  }
-
-  if (!input.Peek(INTEGER)) {
-    value = defaultValue;
-    return Success;
-  }
-
-  uint8_t parsedValue;
-  Result rv = Integer(input, parsedValue);
-  if (rv != Success) {
-    return rv;
-  }
-  value = parsedValue;
-  return Success;
-}
-
-inline Result
-Null(Reader& input)
-{
-  return ExpectTagAndEmptyValue(input, NULLTag);
-}
-
-template <uint8_t Len>
-Result
-OID(Reader& input, const uint8_t (&expectedOid)[Len])
-{
-  Reader value;
-  Result rv = ExpectTagAndGetValue(input, OIDTag, value);
-  if (rv != Success) {
-    return rv;
-  }
-  if (!value.MatchRest(expectedOid)) {
-    return Result::ERROR_BAD_DER;
-  }
-  return Success;
-}
-
-// PKI-specific types
-
-inline Result
-CertificateSerialNumber(Reader& input, /*out*/ Input& value)
-{
-  // http://tools.ietf.org/html/rfc5280#section-4.1.2.2:
-  //
-  // * "The serial number MUST be a positive integer assigned by the CA to
-  //   each certificate."
-  // * "Certificate users MUST be able to handle serialNumber values up to 20
-  //   octets. Conforming CAs MUST NOT use serialNumber values longer than 20
-  //   octets."
-  // * "Note: Non-conforming CAs may issue certificates with serial numbers
-  //   that are negative or zero.  Certificate users SHOULD be prepared to
-  //   gracefully handle such certificates."
-  return internal::IntegralBytes(
-           input, INTEGER, internal::IntegralValueRestriction::NoRestriction,
-           value);
-}
-
-// x.509 and OCSP both use this same version numbering scheme, though OCSP
-// only supports v1.
-enum class Version { v1 = 0, v2 = 1, v3 = 2, v4 = 3, Uninitialized = 255 };
-
-// X.509 Certificate and OCSP ResponseData both use
-// "[0] EXPLICIT Version DEFAULT v1". Although an explicit encoding of v1 is
-// illegal, we support it because some real-world OCSP responses explicitly
-// encode it.
-Result OptionalVersion(Reader& input, /*out*/ Version& version);
-
-template <typename ExtensionHandler>
-inline Result
-OptionalExtensions(Reader& input, uint8_t tag,
-                   ExtensionHandler extensionHandler)
-{
-  if (!input.Peek(tag)) {
-    return Success;
-  }
-
-  return Nested(input, tag, [extensionHandler](Reader& tagged) {
-    // Extensions ::= SEQUENCE SIZE (1..MAX) OF Extension
-    //
-    // TODO(bug 997994): According to the specification, there should never be
-    // an empty sequence of extensions but we've found OCSP responses that have
-    // that (see bug 991898).
-    return NestedOf(tagged, SEQUENCE, SEQUENCE, EmptyAllowed::Yes,
-                    [extensionHandler](Reader& extension) -> Result {
-      // Extension  ::=  SEQUENCE  {
-      //      extnID      OBJECT IDENTIFIER,
-      //      critical    BOOLEAN DEFAULT FALSE,
-      //      extnValue   OCTET STRING
-      //      }
-      Reader extnID;
-      Result rv = ExpectTagAndGetValue(extension, OIDTag, extnID);
-      if (rv != Success) {
-        return rv;
-      }
-      bool critical;
-      rv = OptionalBoolean(extension, critical);
-      if (rv != Success) {
-        return rv;
-      }
-      Input extnValue;
-      rv = ExpectTagAndGetValue(extension, OCTET_STRING, extnValue);
-      if (rv != Success) {
-        return rv;
-      }
-      bool understood = false;
-      rv = extensionHandler(extnID, extnValue, critical, understood);
-      if (rv != Success) {
-        return rv;
-      }
-      if (critical && !understood) {
-        return Result::ERROR_UNKNOWN_CRITICAL_EXTENSION;
-      }
-      return Success;
-    });
-  });
-}
-
-Result DigestAlgorithmIdentifier(Reader& input,
-                                 /*out*/ DigestAlgorithm& algorithm);
-
-enum class PublicKeyAlgorithm
-{
-  RSA_PKCS1,
-  ECDSA,
-  Uninitialized
-};
-
-Result SignatureAlgorithmIdentifierValue(
-         Reader& input,
-         /*out*/ PublicKeyAlgorithm& publicKeyAlgorithm,
-         /*out*/ DigestAlgorithm& digestAlgorithm);
-
-struct SignedDataWithSignature final
-{
-public:
-  Input data;
-  Input algorithm;
-  Input signature;
-
-  void operator=(const SignedDataWithSignature&) = delete;
-};
-
-// Parses a SEQUENCE into tbs and then parses an AlgorithmIdentifier followed
-// by a BIT STRING into signedData. This handles the commonality between
-// parsing the signed/signature fields of certificates and OCSP responses. In
-// the case of an OCSP response, the caller needs to parse the certs
-// separately.
-//
-// Note that signatureAlgorithm is NOT parsed or validated.
-//
-// Certificate  ::=  SEQUENCE  {
-//        tbsCertificate       TBSCertificate,
-//        signatureAlgorithm   AlgorithmIdentifier,
-//        signatureValue       BIT STRING  }
-//
-// BasicOCSPResponse       ::= SEQUENCE {
-//    tbsResponseData      ResponseData,
-//    signatureAlgorithm   AlgorithmIdentifier,
-//    signature            BIT STRING,
-//    certs            [0] EXPLICIT SEQUENCE OF Certificate OPTIONAL }
-Result SignedData(Reader& input, /*out*/ Reader& tbs,
-                  /*out*/ SignedDataWithSignature& signedDataWithSignature);
-
-} } } // namespace mozilla::pkix::der
-
-#endif // mozilla_pkix_pkixder_h
deleted file mode 100644
--- a/security/pkix/lib/pkixnames.cpp
+++ /dev/null
@@ -1,2050 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2014 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// This code implements RFC6125-ish name matching, RFC5280-ish name constraint
-// checking, and related things.
-//
-// In this code, identifiers are classified as either "presented" or
-// "reference" identifiers are defined in
-// http://tools.ietf.org/html/rfc6125#section-1.8. A "presented identifier" is
-// one in the subjectAltName of the certificate, or sometimes within a CN of
-// the certificate's subject. The "reference identifier" is the one we are
-// being asked to match the certificate against. When checking name
-// constraints, the reference identifier is the entire encoded name constraint
-// extension value.
-
-#include <algorithm>
-
-#include "pkixcheck.h"
-#include "pkixutil.h"
-
-namespace mozilla { namespace pkix {
-
-namespace {
-
-// GeneralName ::= CHOICE {
-//      otherName                       [0]     OtherName,
-//      rfc822Name                      [1]     IA5String,
-//      dNSName                         [2]     IA5String,
-//      x400Address                     [3]     ORAddress,
-//      directoryName                   [4]     Name,
-//      ediPartyName                    [5]     EDIPartyName,
-//      uniformResourceIdentifier       [6]     IA5String,
-//      iPAddress                       [7]     OCTET STRING,
-//      registeredID                    [8]     OBJECT IDENTIFIER }
-enum class GeneralNameType : uint8_t
-{
-  // Note that these values are NOT contiguous. Some values have the
-  // der::CONSTRUCTED bit set while others do not.
-  // (The der::CONSTRUCTED bit is for types where the value is a SEQUENCE.)
-  otherName = der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 0,
-  rfc822Name = der::CONTEXT_SPECIFIC | 1,
-  dNSName = der::CONTEXT_SPECIFIC | 2,
-  x400Address = der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 3,
-  directoryName = der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 4,
-  ediPartyName = der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 5,
-  uniformResourceIdentifier = der::CONTEXT_SPECIFIC | 6,
-  iPAddress = der::CONTEXT_SPECIFIC | 7,
-  registeredID = der::CONTEXT_SPECIFIC | 8,
-  // nameConstraints is a pseudo-GeneralName used to signify that a
-  // reference ID is actually the entire name constraint extension.
-  nameConstraints = 0xff
-};
-
-inline Result
-ReadGeneralName(Reader& reader,
-                /*out*/ GeneralNameType& generalNameType,
-                /*out*/ Input& value)
-{
-  uint8_t tag;
-  Result rv = der::ReadTagAndGetValue(reader, tag, value);
-  if (rv != Success) {
-    return rv;
-  }
-  switch (tag) {
-    case static_cast<uint8_t>(GeneralNameType::otherName):
-      generalNameType = GeneralNameType::otherName;
-      break;
-    case static_cast<uint8_t>(GeneralNameType::rfc822Name):
-      generalNameType = GeneralNameType::rfc822Name;
-      break;
-    case static_cast<uint8_t>(GeneralNameType::dNSName):
-      generalNameType = GeneralNameType::dNSName;
-      break;
-    case static_cast<uint8_t>(GeneralNameType::x400Address):
-      generalNameType = GeneralNameType::x400Address;
-      break;
-    case static_cast<uint8_t>(GeneralNameType::directoryName):
-      generalNameType = GeneralNameType::directoryName;
-      break;
-    case static_cast<uint8_t>(GeneralNameType::ediPartyName):
-      generalNameType = GeneralNameType::ediPartyName;
-      break;
-    case static_cast<uint8_t>(GeneralNameType::uniformResourceIdentifier):
-      generalNameType = GeneralNameType::uniformResourceIdentifier;
-      break;
-    case static_cast<uint8_t>(GeneralNameType::iPAddress):
-      generalNameType = GeneralNameType::iPAddress;
-      break;
-    case static_cast<uint8_t>(GeneralNameType::registeredID):
-      generalNameType = GeneralNameType::registeredID;
-      break;
-    default:
-      return Result::ERROR_BAD_DER;
-  }
-  return Success;
-}
-
-enum class MatchResult
-{
-  NoNamesOfGivenType = 0,
-  Mismatch = 1,
-  Match = 2
-};
-
-Result SearchNames(const Input* subjectAltName, Input subject,
-                   GeneralNameType referenceIDType,
-                   Input referenceID,
-                   FallBackToSearchWithinSubject fallBackToCommonName,
-                   /*out*/ MatchResult& match);
-Result SearchWithinRDN(Reader& rdn,
-                       GeneralNameType referenceIDType,
-                       Input referenceID,
-                       FallBackToSearchWithinSubject fallBackToEmailAddress,
-                       FallBackToSearchWithinSubject fallBackToCommonName,
-                       /*in/out*/ MatchResult& match);
-Result MatchAVA(Input type,
-                uint8_t valueEncodingTag,
-                Input presentedID,
-                GeneralNameType referenceIDType,
-                Input referenceID,
-                FallBackToSearchWithinSubject fallBackToEmailAddress,
-                FallBackToSearchWithinSubject fallBackToCommonName,
-                /*in/out*/ MatchResult& match);
-Result ReadAVA(Reader& rdn,
-               /*out*/ Input& type,
-               /*out*/ uint8_t& valueTag,
-               /*out*/ Input& value);
-void MatchSubjectPresentedIDWithReferenceID(GeneralNameType presentedIDType,
-                                            Input presentedID,
-                                            GeneralNameType referenceIDType,
-                                            Input referenceID,
-                                            /*in/out*/ MatchResult& match);
-
-Result MatchPresentedIDWithReferenceID(GeneralNameType presentedIDType,
-                                       Input presentedID,
-                                       GeneralNameType referenceIDType,
-                                       Input referenceID,
-                                       /*in/out*/ MatchResult& matchResult);
-Result CheckPresentedIDConformsToConstraints(GeneralNameType referenceIDType,
-                                             Input presentedID,
-                                             Input nameConstraints);
-
-uint8_t LocaleInsensitveToLower(uint8_t a);
-bool StartsWithIDNALabel(Input id);
-
-enum class IDRole
-{
-  ReferenceID = 0,
-  PresentedID = 1,
-  NameConstraint = 2,
-};
-
-enum class AllowWildcards { No = 0, Yes = 1 };
-
-// DNSName constraints implicitly allow subdomain matching when there is no
-// leading dot ("foo.example.com" matches a constraint of "example.com"), but
-// RFC822Name constraints only allow subdomain matching when there is a leading
-// dot ("foo.example.com" does not match "example.com" but does match
-// ".example.com").
-enum class AllowDotlessSubdomainMatches { No = 0, Yes = 1 };
-
-bool IsValidDNSID(Input hostname, IDRole idRole,
-                  AllowWildcards allowWildcards);
-
-Result MatchPresentedDNSIDWithReferenceDNSID(
-         Input presentedDNSID,
-         AllowWildcards allowWildcards,
-         AllowDotlessSubdomainMatches allowDotlessSubdomainMatches,
-         IDRole referenceDNSIDRole,
-         Input referenceDNSID,
-         /*out*/ bool& matches);
-
-Result MatchPresentedRFC822NameWithReferenceRFC822Name(
-         Input presentedRFC822Name, IDRole referenceRFC822NameRole,
-         Input referenceRFC822Name, /*out*/ bool& matches);
-
-} // namespace
-
-bool IsValidReferenceDNSID(Input hostname);
-bool IsValidPresentedDNSID(Input hostname);
-bool ParseIPv4Address(Input hostname, /*out*/ uint8_t (&out)[4]);
-bool ParseIPv6Address(Input hostname, /*out*/ uint8_t (&out)[16]);
-
-// This is used by the pkixnames_tests.cpp tests.
-Result
-MatchPresentedDNSIDWithReferenceDNSID(Input presentedDNSID,
-                                      Input referenceDNSID,
-                                      /*out*/ bool& matches)
-{
-  return MatchPresentedDNSIDWithReferenceDNSID(
-           presentedDNSID, AllowWildcards::Yes,
-           AllowDotlessSubdomainMatches::Yes, IDRole::ReferenceID,
-           referenceDNSID, matches);
-}
-
-// Verify that the given end-entity cert, which is assumed to have been already
-// validated with BuildCertChain, is valid for the given hostname. hostname is
-// assumed to be a string representation of an IPv4 address, an IPv6 addresss,
-// or a normalized ASCII (possibly punycode) DNS name.
-Result
-CheckCertHostname(Input endEntityCertDER, Input hostname,
-                  NameMatchingPolicy& nameMatchingPolicy)
-{
-  BackCert cert(endEntityCertDER, EndEntityOrCA::MustBeEndEntity, nullptr);
-  Result rv = cert.Init();
-  if (rv != Success) {
-    return rv;
-  }
-
-  Time notBefore(Time::uninitialized);
-  rv = ParseValidity(cert.GetValidity(), &notBefore);
-  if (rv != Success) {
-    return rv;
-  }
-  FallBackToSearchWithinSubject fallBackToSearchWithinSubject;
-  rv = nameMatchingPolicy.FallBackToCommonName(notBefore,
-                                               fallBackToSearchWithinSubject);
-  if (rv != Success) {
-    return rv;
-  }
-
-  const Input* subjectAltName(cert.GetSubjectAltName());
-  Input subject(cert.GetSubject());
-
-  // For backward compatibility with legacy certificates, we may fall back to
-  // searching for a name match in the subject common name for DNS names and
-  // IPv4 addresses. We don't do so for IPv6 addresses because we do not think
-  // there are many certificates that would need such fallback, and because
-  // comparisons of string representations of IPv6 addresses are particularly
-  // error prone due to the syntactic flexibility that IPv6 addresses have.
-  //
-  // IPv4 and IPv6 addresses are represented using the same type of GeneralName
-  // (iPAddress); they are differentiated by the lengths of the values.
-  MatchResult match;
-  uint8_t ipv6[16];
-  uint8_t ipv4[4];
-  if (IsValidReferenceDNSID(hostname)) {
-    rv = SearchNames(subjectAltName, subject, GeneralNameType::dNSName,
-                     hostname, fallBackToSearchWithinSubject, match);
-  } else if (ParseIPv6Address(hostname, ipv6)) {
-    rv = SearchNames(subjectAltName, subject, GeneralNameType::iPAddress,
-                     Input(ipv6), FallBackToSearchWithinSubject::No, match);
-  } else if (ParseIPv4Address(hostname, ipv4)) {
-    rv = SearchNames(subjectAltName, subject, GeneralNameType::iPAddress,
-                     Input(ipv4), fallBackToSearchWithinSubject, match);
-  } else {
-    return Result::ERROR_BAD_CERT_DOMAIN;
-  }
-  if (rv != Success) {
-    return rv;
-  }
-  switch (match) {
-    case MatchResult::NoNamesOfGivenType: // fall through
-    case MatchResult::Mismatch:
-      return Result::ERROR_BAD_CERT_DOMAIN;
-    case MatchResult::Match:
-      return Success;
-    MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-  }
-}
-
-// 4.2.1.10. Name Constraints
-Result
-CheckNameConstraints(Input encodedNameConstraints,
-                     const BackCert& firstChild,
-                     KeyPurposeId requiredEKUIfPresent)
-{
-  for (const BackCert* child = &firstChild; child; child = child->childCert) {
-    FallBackToSearchWithinSubject fallBackToCommonName
-      = (child->endEntityOrCA == EndEntityOrCA::MustBeEndEntity &&
-         requiredEKUIfPresent == KeyPurposeId::id_kp_serverAuth)
-      ? FallBackToSearchWithinSubject::Yes
-      : FallBackToSearchWithinSubject::No;
-
-    MatchResult match;
-    Result rv = SearchNames(child->GetSubjectAltName(), child->GetSubject(),
-                            GeneralNameType::nameConstraints,
-                            encodedNameConstraints, fallBackToCommonName,
-                            match);
-    if (rv != Success) {
-      return rv;
-    }
-    switch (match) {
-      case MatchResult::Match: // fall through
-      case MatchResult::NoNamesOfGivenType:
-        break;
-      case MatchResult::Mismatch:
-        return Result::ERROR_CERT_NOT_IN_NAME_SPACE;
-    }
-  }
-
-  return Success;
-}
-
-namespace {
-
-// SearchNames is used by CheckCertHostname and CheckNameConstraints.
-//
-// When called during name constraint checking, referenceIDType is
-// GeneralNameType::nameConstraints and referenceID is the entire encoded name
-// constraints extension value.
-//
-// The main benefit of using the exact same code paths for both is that we
-// ensure consistency between name validation and name constraint enforcement
-// regarding thing like "Which CN attributes should be considered as potential
-// CN-IDs" and "Which character sets are acceptable for CN-IDs?" If the name
-// matching and the name constraint enforcement logic were out of sync on these
-// issues (e.g. if name matching were to consider all subject CN attributes,
-// but name constraints were only enforced on the most specific subject CN),
-// trivial name constraint bypasses could result.
-
-Result
-SearchNames(/*optional*/ const Input* subjectAltName,
-            Input subject,
-            GeneralNameType referenceIDType,
-            Input referenceID,
-            FallBackToSearchWithinSubject fallBackToCommonName,
-            /*out*/ MatchResult& match)
-{
-  Result rv;
-
-  match = MatchResult::NoNamesOfGivenType;
-
-  // RFC 6125 says "A client MUST NOT seek a match for a reference identifier
-  // of CN-ID if the presented identifiers include a DNS-ID, SRV-ID, URI-ID, or
-  // any application-specific identifier types supported by the client."
-  // Accordingly, we only consider CN-IDs if there are no DNS-IDs in the
-  // subjectAltName.
-  //
-  // RFC 6125 says that IP addresses are out of scope, but for backward
-  // compatibility we accept them, by considering IP addresses to be an
-  // "application-specific identifier type supported by the client."
-  //
-  // TODO(bug XXXXXXX): Consider strengthening this check to "A client MUST NOT
-  // seek a match for a reference identifier of CN-ID if the certificate
-  // contains a subjectAltName extension."
-  //
-  // TODO(bug XXXXXXX): Consider dropping support for IP addresses as
-  // identifiers completely.
-
-  if (subjectAltName) {
-    Reader altNames;
-    rv = der::ExpectTagAndGetValueAtEnd(*subjectAltName, der::SEQUENCE,
-                                        altNames);
-    if (rv != Success) {
-      return rv;
-    }
-
-    // According to RFC 5280, "If the subjectAltName extension is present, the
-    // sequence MUST contain at least one entry." For compatibility reasons, we
-    // do not enforce this. See bug 1143085.
-    while (!altNames.AtEnd()) {
-      GeneralNameType presentedIDType;
-      Input presentedID;
-      rv = ReadGeneralName(altNames, presentedIDType, presentedID);
-      if (rv != Success) {
-        return rv;
-      }
-
-      rv = MatchPresentedIDWithReferenceID(presentedIDType, presentedID,
-                                           referenceIDType, referenceID,
-                                           match);
-      if (rv != Success) {
-        return rv;
-      }
-      if (referenceIDType != GeneralNameType::nameConstraints &&
-          match == MatchResult::Match) {
-        return Success;
-      }
-      if (presentedIDType == GeneralNameType::dNSName ||
-          presentedIDType == GeneralNameType::iPAddress) {
-        fallBackToCommonName = FallBackToSearchWithinSubject::No;
-      }
-    }
-  }
-
-  if (referenceIDType == GeneralNameType::nameConstraints) {
-    rv = CheckPresentedIDConformsToConstraints(GeneralNameType::directoryName,
-                                               subject, referenceID);
-    if (rv != Success) {
-      return rv;
-    }
-  }
-
-  FallBackToSearchWithinSubject fallBackToEmailAddress;
-  if (!subjectAltName &&
-      (referenceIDType == GeneralNameType::rfc822Name ||
-       referenceIDType == GeneralNameType::nameConstraints)) {
-    fallBackToEmailAddress = FallBackToSearchWithinSubject::Yes;
-  } else {
-    fallBackToEmailAddress = FallBackToSearchWithinSubject::No;
-  }
-
-  // Short-circuit the parsing of the subject name if we're not going to match
-  // any names in it
-  if (fallBackToEmailAddress == FallBackToSearchWithinSubject::No &&
-      fallBackToCommonName == FallBackToSearchWithinSubject::No) {
-    return Success;
-  }
-
-  // Attempt to match the reference ID against the CN-ID, which we consider to
-  // be the most-specific CN AVA in the subject field.
-  //
-  // https://tools.ietf.org/html/rfc6125#section-2.3.1 says:
-  //
-  //   To reduce confusion, in this specification we avoid such terms and
-  //   instead use the terms provided under Section 1.8; in particular, we
-  //   do not use the term "(most specific) Common Name field in the subject
-  //   field" from [HTTP-TLS] and instead state that a CN-ID is a Relative
-  //   Distinguished Name (RDN) in the certificate subject containing one
-  //   and only one attribute-type-and-value pair of type Common Name (thus
-  //   removing the possibility that an RDN might contain multiple AVAs
-  //   (Attribute Value Assertions) of type CN, one of which could be
-  //   considered "most specific").
-  //
-  // https://tools.ietf.org/html/rfc6125#section-7.4 says:
-  //
-  //   [...] Although it would be preferable to
-  //   forbid multiple CN-IDs entirely, there are several reasons at this
-  //   time why this specification states that they SHOULD NOT (instead of
-  //   MUST NOT) be included [...]
-  //
-  // Consequently, it is unclear what to do when there are multiple CNs in the
-  // subject, regardless of whether there "SHOULD NOT" be.
-  //
-  // NSS's CERT_VerifyCertName mostly follows RFC2818 in this instance, which
-  // says:
-  //
-  //   If a subjectAltName extension of type dNSName is present, that MUST
-  //   be used as the identity. Otherwise, the (most specific) Common Name
-  //   field in the Subject field of the certificate MUST be used.
-  //
-  //   [...]
-  //
-  //   In some cases, the URI is specified as an IP address rather than a
-  //   hostname. In this case, the iPAddress subjectAltName must be present
-  //   in the certificate and must exactly match the IP in the URI.
-  //
-  // (The main difference from RFC2818 is that NSS's CERT_VerifyCertName also
-  // matches IP addresses in the most-specific CN.)
-  //
-  // NSS's CERT_VerifyCertName finds the most specific CN via
-  // CERT_GetCommoName, which uses CERT_GetLastNameElement. Note that many
-  // NSS-based applications, including Gecko, also use CERT_GetCommonName. It
-  // is likely that other, non-NSS-based, applications also expect only the
-  // most specific CN to be matched against the reference ID.
-  //
-  // "A Layman's Guide to a Subset of ASN.1, BER, and DER" and other sources
-  // agree that an RDNSequence is ordered from most significant (least
-  // specific) to least significant (most specific), as do other references.
-  //
-  // However, Chromium appears to use the least-specific (first) CN instead of
-  // the most-specific; see https://crbug.com/366957. Also, MSIE and some other
-  // popular implementations apparently attempt to match the reference ID
-  // against any/all CNs in the subject. Since we're trying to phase out the
-  // use of CN-IDs, we intentionally avoid trying to match MSIE's more liberal
-  // behavior.
-
-  // Name ::= CHOICE { -- only one possibility for now --
-  //   rdnSequence  RDNSequence }
-  //
-  // RDNSequence ::= SEQUENCE OF RelativeDistinguishedName
-  //
-  // RelativeDistinguishedName ::=
-  //   SET SIZE (1..MAX) OF AttributeTypeAndValue
-  Reader subjectReader(subject);
-  return der::NestedOf(subjectReader, der::SEQUENCE, der::SET,
-                       der::EmptyAllowed::Yes, [&](Reader& r) {
-    return SearchWithinRDN(r, referenceIDType, referenceID,
-                          fallBackToEmailAddress, fallBackToCommonName, match);
-  });
-}
-
-// RelativeDistinguishedName ::=
-//   SET SIZE (1..MAX) OF AttributeTypeAndValue
-//
-// AttributeTypeAndValue ::= SEQUENCE {
-//   type     AttributeType,
-//   value    AttributeValue }
-Result
-SearchWithinRDN(Reader& rdn,
-                GeneralNameType referenceIDType,
-                Input referenceID,
-                FallBackToSearchWithinSubject fallBackToEmailAddress,
-                FallBackToSearchWithinSubject fallBackToCommonName,
-                /*in/out*/ MatchResult& match)
-{
-  do {
-    Input type;
-    uint8_t valueTag;
-    Input value;
-    Result rv = ReadAVA(rdn, type, valueTag, value);
-    if (rv != Success) {
-      return rv;
-    }
-    rv = MatchAVA(type, valueTag, value, referenceIDType, referenceID,
-                  fallBackToEmailAddress, fallBackToCommonName, match);
-    if (rv != Success) {
-      return rv;
-    }
-  } while (!rdn.AtEnd());
-
-  return Success;
-}
-
-// AttributeTypeAndValue ::= SEQUENCE {
-//   type     AttributeType,
-//   value    AttributeValue }
-//
-// AttributeType ::= OBJECT IDENTIFIER
-//
-// AttributeValue ::= ANY -- DEFINED BY AttributeType
-//
-// DirectoryString ::= CHOICE {
-//       teletexString           TeletexString (SIZE (1..MAX)),
-//       printableString         PrintableString (SIZE (1..MAX)),
-//       universalString         UniversalString (SIZE (1..MAX)),
-//       utf8String              UTF8String (SIZE (1..MAX)),
-//       bmpString               BMPString (SIZE (1..MAX)) }
-Result
-MatchAVA(Input type, uint8_t valueEncodingTag, Input presentedID,
-         GeneralNameType referenceIDType,
-         Input referenceID,
-         FallBackToSearchWithinSubject fallBackToEmailAddress,
-         FallBackToSearchWithinSubject fallBackToCommonName,
-         /*in/out*/ MatchResult& match)
-{
-  // Try to match the  CN as a DNSName or an IPAddress.
-  //
-  // id-at-commonName        AttributeType ::= { id-at 3 }
-  //
-  // -- Naming attributes of type X520CommonName:
-  // --   X520CommonName ::= DirectoryName (SIZE (1..ub-common-name))
-  // --
-  // -- Expanded to avoid parameterized type:
-  // X520CommonName ::= CHOICE {
-  //       teletexString     TeletexString   (SIZE (1..ub-common-name)),
-  //       printableString   PrintableString (SIZE (1..ub-common-name)),
-  //       universalString   UniversalString (SIZE (1..ub-common-name)),
-  //       utf8String        UTF8String      (SIZE (1..ub-common-name)),
-  //       bmpString         BMPString       (SIZE (1..ub-common-name)) }
-  //
-  // python DottedOIDToCode.py id-at-commonName 2.5.4.3
-  static const uint8_t id_at_commonName[] = {
-    0x55, 0x04, 0x03
-  };
-  if (fallBackToCommonName == FallBackToSearchWithinSubject::Yes &&
-      InputsAreEqual(type, Input(id_at_commonName))) {
-    // We might have previously found a match. Now that we've found another CN,
-    // we no longer consider that previous match to be a match, so "forget" about
-    // it.
-    match = MatchResult::NoNamesOfGivenType;
-
-    // PrintableString is a subset of ASCII that contains all the characters
-    // allowed in CN-IDs except '*'. Although '*' is illegal, there are many
-    // real-world certificates that are encoded this way, so we accept it.
-    //
-    // In the case of UTF8String, we rely on the fact that in UTF-8 the octets in
-    // a multi-byte encoding of a code point are always distinct from ASCII. Any
-    // non-ASCII byte in a UTF-8 string causes us to fail to match. We make no
-    // attempt to detect or report malformed UTF-8 (e.g. incomplete or overlong
-    // encodings of code points, or encodings of invalid code points).
-    //
-    // TeletexString is supported as long as it does not contain any escape
-    // sequences, which are not supported. We'll reject escape sequences as
-    // invalid characters in names, which means we only accept strings that are
-    // in the default character set, which is a superset of ASCII. Note that NSS
-    // actually treats TeletexString as ISO-8859-1. Many certificates that have
-    // wildcard CN-IDs (e.g. "*.example.com") use TeletexString because
-    // PrintableString is defined to not allow '*' and because, at one point in
-    // history, UTF8String was too new to use for compatibility reasons.
-    //
-    // UniversalString and BMPString are also deprecated, and they are a little
-    // harder to support because they are not single-byte ASCII superset
-    // encodings, so we don't bother.
-    if (valueEncodingTag != der::PrintableString &&
-        valueEncodingTag != der::UTF8String &&
-        valueEncodingTag != der::TeletexString) {
-      return Success;
-    }
-
-    if (IsValidPresentedDNSID(presentedID)) {
-      MatchSubjectPresentedIDWithReferenceID(GeneralNameType::dNSName,
-                                             presentedID, referenceIDType,
-                                             referenceID, match);
-    } else {
-      // We don't match CN-IDs for IPv6 addresses.
-      // MatchSubjectPresentedIDWithReferenceID ensures that it won't match an
-      // IPv4 address with an IPv6 address, so we don't need to check that
-      // referenceID is an IPv4 address here.
-      uint8_t ipv4[4];
-      if (ParseIPv4Address(presentedID, ipv4)) {
-        MatchSubjectPresentedIDWithReferenceID(GeneralNameType::iPAddress,
-                                               Input(ipv4), referenceIDType,
-                                               referenceID, match);
-      }
-    }
-
-    // Regardless of whether there was a match, we keep going in case we find
-    // another CN later. If we do find another one, then this match/mismatch
-    // will be ignored, because we only care about the most specific CN.
-
-    return Success;
-  }
-
-  // Match an email address against an emailAddress attribute in the
-  // subject.
-  //
-  // id-emailAddress      AttributeType ::= { pkcs-9 1 }
-  //
-  // EmailAddress ::=     IA5String (SIZE (1..ub-emailaddress-length))
-  //
-  // python DottedOIDToCode.py id-emailAddress 1.2.840.113549.1.9.1
-  static const uint8_t id_emailAddress[] = {
-    0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09, 0x01
-  };
-  if (fallBackToEmailAddress == FallBackToSearchWithinSubject::Yes &&
-      InputsAreEqual(type, Input(id_emailAddress))) {
-    if (referenceIDType == GeneralNameType::rfc822Name &&
-        match == MatchResult::Match) {
-      // We already found a match; we don't need to match another one
-      return Success;
-    }
-    if (valueEncodingTag != der::IA5String) {
-      return Result::ERROR_BAD_DER;
-    }
-    return MatchPresentedIDWithReferenceID(GeneralNameType::rfc822Name,
-                                           presentedID, referenceIDType,
-                                           referenceID, match);
-  }
-
-  return Success;
-}
-
-void
-MatchSubjectPresentedIDWithReferenceID(GeneralNameType presentedIDType,
-                                       Input presentedID,
-                                       GeneralNameType referenceIDType,
-                                       Input referenceID,
-                                       /*in/out*/ MatchResult& match)
-{
-  Result rv = MatchPresentedIDWithReferenceID(presentedIDType, presentedID,
-                                              referenceIDType, referenceID,
-                                              match);
-  if (rv != Success) {
-    match = MatchResult::Mismatch;
-  }
-}
-
-Result
-MatchPresentedIDWithReferenceID(GeneralNameType presentedIDType,
-                                Input presentedID,
-                                GeneralNameType referenceIDType,
-                                Input referenceID,
-                                /*out*/ MatchResult& matchResult)
-{
-  if (referenceIDType == GeneralNameType::nameConstraints) {
-    // matchResult is irrelevant when checking name constraints; only the
-    // pass/fail result of CheckPresentedIDConformsToConstraints matters.
-    return CheckPresentedIDConformsToConstraints(presentedIDType, presentedID,
-                                                 referenceID);
-  }
-
-  if (presentedIDType != referenceIDType) {
-    matchResult = MatchResult::Mismatch;
-    return Success;
-  }
-
-  Result rv;
-  bool foundMatch;
-
-  switch (referenceIDType) {
-    case GeneralNameType::dNSName:
-      rv = MatchPresentedDNSIDWithReferenceDNSID(
-             presentedID, AllowWildcards::Yes,
-             AllowDotlessSubdomainMatches::Yes, IDRole::ReferenceID,
-             referenceID, foundMatch);
-      break;
-
-    case GeneralNameType::iPAddress:
-      foundMatch = InputsAreEqual(presentedID, referenceID);
-      rv = Success;
-      break;
-
-    case GeneralNameType::rfc822Name:
-      rv = MatchPresentedRFC822NameWithReferenceRFC822Name(
-             presentedID, IDRole::ReferenceID, referenceID, foundMatch);
-      break;
-
-    case GeneralNameType::directoryName:
-      // TODO: At some point, we may add APIs for matching DirectoryNames.
-      // fall through
-
-    case GeneralNameType::otherName: // fall through
-    case GeneralNameType::x400Address: // fall through
-    case GeneralNameType::ediPartyName: // fall through
-    case GeneralNameType::uniformResourceIdentifier: // fall through
-    case GeneralNameType::registeredID: // fall through
-    case GeneralNameType::nameConstraints:
-      return NotReached("unexpected nameType for SearchType::Match",
-                        Result::FATAL_ERROR_INVALID_ARGS);
-
-    MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
- }
-
-  if (rv != Success) {
-    return rv;
-  }
-  matchResult = foundMatch ? MatchResult::Match : MatchResult::Mismatch;
-  return Success;
-}
-
-enum class NameConstraintsSubtrees : uint8_t
-{
-  permittedSubtrees = der::CONSTRUCTED | der::CONTEXT_SPECIFIC | 0,
-  excludedSubtrees  = der::CONSTRUCTED | der::CONTEXT_SPECIFIC | 1
-};
-
-Result CheckPresentedIDConformsToNameConstraintsSubtrees(
-         GeneralNameType presentedIDType,
-         Input presentedID,
-         Reader& nameConstraints,
-         NameConstraintsSubtrees subtreesType);
-Result MatchPresentedIPAddressWithConstraint(Input presentedID,
-                                             Input iPAddressConstraint,
-                                             /*out*/ bool& foundMatch);
-Result MatchPresentedDirectoryNameWithConstraint(
-         NameConstraintsSubtrees subtreesType, Input presentedID,
-         Input directoryNameConstraint, /*out*/ bool& matches);
-
-Result
-CheckPresentedIDConformsToConstraints(
-  GeneralNameType presentedIDType,
-  Input presentedID,
-  Input encodedNameConstraints)
-{
-  // NameConstraints ::= SEQUENCE {
-  //      permittedSubtrees       [0]     GeneralSubtrees OPTIONAL,
-  //      excludedSubtrees        [1]     GeneralSubtrees OPTIONAL }
-  Reader nameConstraints;
-  Result rv = der::ExpectTagAndGetValueAtEnd(encodedNameConstraints,
-                                             der::SEQUENCE, nameConstraints);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // RFC 5280 says "Conforming CAs MUST NOT issue certificates where name
-  // constraints is an empty sequence. That is, either the permittedSubtrees
-  // field or the excludedSubtrees MUST be present."
-  if (nameConstraints.AtEnd()) {
-    return Result::ERROR_BAD_DER;
-  }
-
-  rv = CheckPresentedIDConformsToNameConstraintsSubtrees(
-         presentedIDType, presentedID, nameConstraints,
-         NameConstraintsSubtrees::permittedSubtrees);
-  if (rv != Success) {
-    return rv;
-  }
-
-  rv = CheckPresentedIDConformsToNameConstraintsSubtrees(
-         presentedIDType, presentedID, nameConstraints,
-         NameConstraintsSubtrees::excludedSubtrees);
-  if (rv != Success) {
-    return rv;
-  }
-
-  return der::End(nameConstraints);
-}
-
-Result
-CheckPresentedIDConformsToNameConstraintsSubtrees(
-  GeneralNameType presentedIDType,
-  Input presentedID,
-  Reader& nameConstraints,
-  NameConstraintsSubtrees subtreesType)
-{
-  if (!nameConstraints.Peek(static_cast<uint8_t>(subtreesType))) {
-    return Success;
-  }
-
-  Reader subtrees;
-  Result rv = der::ExpectTagAndGetValue(nameConstraints,
-                                        static_cast<uint8_t>(subtreesType),
-                                        subtrees);
-  if (rv != Success) {
-    return rv;
-  }
-
-  bool hasPermittedSubtreesMatch = false;
-  bool hasPermittedSubtreesMismatch = false;
-
-  // GeneralSubtrees ::= SEQUENCE SIZE (1..MAX) OF GeneralSubtree
-  //
-  // do { ... } while(...) because subtrees isn't allowed to be empty.
-  do {
-    // GeneralSubtree ::= SEQUENCE {
-    //      base                    GeneralName,
-    //      minimum         [0]     BaseDistance DEFAULT 0,
-    //      maximum         [1]     BaseDistance OPTIONAL }
-    Reader subtree;
-    rv = ExpectTagAndGetValue(subtrees, der::SEQUENCE, subtree);
-    if (rv != Success) {
-      return rv;
-    }
-    GeneralNameType nameConstraintType;
-    Input base;
-    rv = ReadGeneralName(subtree, nameConstraintType, base);
-    if (rv != Success) {
-      return rv;
-    }
-    // http://tools.ietf.org/html/rfc5280#section-4.2.1.10: "Within this
-    // profile, the minimum and maximum fields are not used with any name
-    // forms, thus, the minimum MUST be zero, and maximum MUST be absent."
-    //
-    // Since the default value isn't allowed to be encoded according to the DER
-    // encoding rules for DEFAULT, this is equivalent to saying that neither
-    // minimum or maximum must be encoded.
-    rv = der::End(subtree);
-    if (rv != Success) {
-      return rv;
-    }
-
-    if (presentedIDType == nameConstraintType) {
-      bool matches;
-
-      switch (presentedIDType) {
-        case GeneralNameType::dNSName:
-          rv = MatchPresentedDNSIDWithReferenceDNSID(
-                 presentedID, AllowWildcards::Yes,
-                 AllowDotlessSubdomainMatches::Yes, IDRole::NameConstraint,
-                 base, matches);
-          if (rv != Success) {
-            return rv;
-          }
-          break;
-
-        case GeneralNameType::iPAddress:
-          rv = MatchPresentedIPAddressWithConstraint(presentedID, base,
-                                                     matches);
-          if (rv != Success) {
-            return rv;
-          }
-          break;
-
-        case GeneralNameType::directoryName:
-          rv = MatchPresentedDirectoryNameWithConstraint(subtreesType,
-                                                         presentedID, base,
-                                                         matches);
-          if (rv != Success) {
-            return rv;
-          }
-          break;
-
-        case GeneralNameType::rfc822Name:
-          rv = MatchPresentedRFC822NameWithReferenceRFC822Name(
-                 presentedID, IDRole::NameConstraint, base, matches);
-          if (rv != Success) {
-            return rv;
-          }
-          break;
-
-        // RFC 5280 says "Conforming CAs [...] SHOULD NOT impose name
-        // constraints on the x400Address, ediPartyName, or registeredID
-        // name forms. It also says "Applications conforming to this profile
-        // [...] SHOULD be able to process name constraints that are imposed
-        // on [...] uniformResourceIdentifier [...]", but we don't bother.
-        //
-        // TODO: Ask to have spec updated to say ""Conforming CAs [...] SHOULD
-        // NOT impose name constraints on the otherName, x400Address,
-        // ediPartyName, uniformResourceIdentifier, or registeredID name
-        // forms."
-        case GeneralNameType::otherName: // fall through
-        case GeneralNameType::x400Address: // fall through
-        case GeneralNameType::ediPartyName: // fall through
-        case GeneralNameType::uniformResourceIdentifier: // fall through
-        case GeneralNameType::registeredID: // fall through
-          return Result::ERROR_CERT_NOT_IN_NAME_SPACE;
-
-        case GeneralNameType::nameConstraints:
-          return NotReached("invalid presentedIDType",
-                            Result::FATAL_ERROR_LIBRARY_FAILURE);
-
-        MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-      }
-
-      switch (subtreesType) {
-        case NameConstraintsSubtrees::permittedSubtrees:
-          if (matches) {
-            hasPermittedSubtreesMatch = true;
-          } else {
-            hasPermittedSubtreesMismatch = true;
-          }
-          break;
-        case NameConstraintsSubtrees::excludedSubtrees:
-          if (matches) {
-            return Result::ERROR_CERT_NOT_IN_NAME_SPACE;
-          }
-          break;
-      }
-    }
-  } while (!subtrees.AtEnd());
-
-  if (hasPermittedSubtreesMismatch && !hasPermittedSubtreesMatch) {
-    // If there was any entry of the given type in permittedSubtrees, then it
-    // required that at least one of them must match. Since none of them did,
-    // we have a failure.
-    return Result::ERROR_CERT_NOT_IN_NAME_SPACE;
-  }
-
-  return Success;
-}
-
-// We do not distinguish between a syntactically-invalid presentedDNSID and one
-// that is syntactically valid but does not match referenceDNSID; in both
-// cases, the result is false.
-//
-// We assume that both presentedDNSID and referenceDNSID are encoded in such a
-// way that US-ASCII (7-bit) characters are encoded in one byte and no encoding
-// of a non-US-ASCII character contains a code point in the range 0-127. For
-// example, UTF-8 is OK but UTF-16 is not.
-//
-// RFC6125 says that a wildcard label may be of the form <x>*<y>.<DNSID>, where
-// <x> and/or <y> may be empty. However, NSS requires <y> to be empty, and we
-// follow NSS's stricter policy by accepting wildcards only of the form
-// <x>*.<DNSID>, where <x> may be empty.
-//
-// An relative presented DNS ID matches both an absolute reference ID and a
-// relative reference ID. Absolute presented DNS IDs are not supported:
-//
-//      Presented ID   Reference ID  Result
-//      -------------------------------------
-//      example.com    example.com   Match
-//      example.com.   example.com   Mismatch
-//      example.com    example.com.  Match
-//      example.com.   example.com.  Mismatch
-//
-// There are more subtleties documented inline in the code.
-//
-// Name constraints ///////////////////////////////////////////////////////////
-//
-// This is all RFC 5280 has to say about DNSName constraints:
-//
-//     DNS name restrictions are expressed as host.example.com.  Any DNS
-//     name that can be constructed by simply adding zero or more labels to
-//     the left-hand side of the name satisfies the name constraint.  For
-//     example, www.host.example.com would satisfy the constraint but
-//     host1.example.com would not.
-//
-// This lack of specificity has lead to a lot of uncertainty regarding
-// subdomain matching. In particular, the following questions have been
-// raised and answered:
-//
-//     Q: Does a presented identifier equal (case insensitive) to the name
-//        constraint match the constraint? For example, does the presented
-//        ID "host.example.com" match a "host.example.com" constraint?
-//     A: Yes. RFC5280 says "by simply adding zero or more labels" and this
-//        is the case of adding zero labels.
-//
-//     Q: When the name constraint does not start with ".", do subdomain
-//        presented identifiers match it? For example, does the presented
-//        ID "www.host.example.com" match a "host.example.com" constraint?
-//     A: Yes. RFC5280 says "by simply adding zero or more labels" and this
-//        is the case of adding more than zero labels. The example is the
-//        one from RFC 5280.
-//
-//     Q: When the name constraint does not start with ".", does a
-//        non-subdomain prefix match it? For example, does "bigfoo.bar.com"
-//        match "foo.bar.com"? [4]
-//     A: No. We interpret RFC 5280's language of "adding zero or more labels"
-//        to mean that whole labels must be prefixed.
-//
-//     (Note that the above three scenarios are the same as the RFC 6265
-//     domain matching rules [0].)
-//
-//     Q: Is a name constraint that starts with "." valid, and if so, what
-//        semantics does it have? For example, does a presented ID of
-//        "www.example.com" match a constraint of ".example.com"? Does a
-//        presented ID of "example.com" match a constraint of ".example.com"?
-//     A: This implementation, NSS[1], and SChannel[2] all support a
-//        leading ".", but OpenSSL[3] does not yet. Amongst the
-//        implementations that support it, a leading "." is legal and means
-//        the same thing as when the "." is omitted, EXCEPT that a
-//        presented identifier equal (case insensitive) to the name
-//        constraint is not matched; i.e. presented DNSName identifiers
-//        must be subdomains. Some CAs in Mozilla's CA program (e.g. HARICA)
-//        have name constraints with the leading "." in their root
-//        certificates. The name constraints imposed on DCISS by Mozilla also
-//        have the it, so supporting this is a requirement for backward
-//        compatibility, even if it is not yet standardized. So, for example, a
-//        presented ID of "www.example.com" matches a constraint of
-//        ".example.com" but a presented ID of "example.com" does not.
-//
-//     Q: Is there a way to prevent subdomain matches?
-//     A: Yes.
-//
-//        Some people have proposed that dNSName constraints that do not
-//        start with a "." should be restricted to exact (case insensitive)
-//        matches. However, such a change of semantics from what RFC5280
-//        specifies would be a non-backward-compatible change in the case of
-//        permittedSubtrees constraints, and it would be a security issue for
-//        excludedSubtrees constraints.
-//
-//        However, it can be done with a combination of permittedSubtrees and
-//        excludedSubtrees, e.g. "example.com" in permittedSubtrees and
-//        ".example.com" in excudedSubtrees.
-//
-//     Q: Are name constraints allowed to be specified as absolute names?
-//        For example, does a presented ID of "example.com" match a name
-//        constraint of "example.com." and vice versa.
-//     A: Absolute names are not supported as presented IDs or name
-//        constraints. Only reference IDs may be absolute.
-//
-//     Q: Is "" a valid DNSName constraints? If so, what does it mean?
-//     A: Yes. Any valid presented DNSName can be formed "by simply adding zero
-//        or more labels to the left-hand side" of "". In particular, an
-//        excludedSubtrees DNSName constraint of "" forbids all DNSNames.
-//
-//     Q: Is "." a valid DNSName constraints? If so, what does it mean?
-//     A: No, because absolute names are not allowed (see above).
-//
-// [0] RFC 6265 (Cookies) Domain Matching rules:
-//     http://tools.ietf.org/html/rfc6265#section-5.1.3
-// [1] NSS source code:
-//     https://mxr.mozilla.org/nss/source/lib/certdb/genname.c?rev=2a7348f013cb#1209
-// [2] Description of SChannel's behavior from Microsoft:
-//     http://www.imc.org/ietf-pkix/mail-archive/msg04668.html
-// [3] Proposal to add such support to OpenSSL:
-//     http://www.mail-archive.com/openssl-dev%40openssl.org/msg36204.html
-//     https://rt.openssl.org/Ticket/Display.html?id=3562
-// [4] Feedback on the lack of clarify in the definition that never got
-//     incorporated into the spec:
-//     https://www.ietf.org/mail-archive/web/pkix/current/msg21192.html
-Result
-MatchPresentedDNSIDWithReferenceDNSID(
-  Input presentedDNSID,
-  AllowWildcards allowWildcards,
-  AllowDotlessSubdomainMatches allowDotlessSubdomainMatches,
-  IDRole referenceDNSIDRole,
-  Input referenceDNSID,
-  /*out*/ bool& matches)
-{
-  if (!IsValidDNSID(presentedDNSID, IDRole::PresentedID, allowWildcards)) {
-    return Result::ERROR_BAD_DER;
-  }
-
-  if (!IsValidDNSID(referenceDNSID, referenceDNSIDRole, AllowWildcards::No)) {
-    return Result::ERROR_BAD_DER;
-  }
-
-  Reader presented(presentedDNSID);
-  Reader reference(referenceDNSID);
-
-  switch (referenceDNSIDRole)
-  {
-    case IDRole::ReferenceID:
-      break;
-
-    case IDRole::NameConstraint:
-    {
-      if (presentedDNSID.GetLength() > referenceDNSID.GetLength()) {
-        if (referenceDNSID.GetLength() == 0) {
-          // An empty constraint matches everything.
-          matches = true;
-          return Success;
-        }
-        // If the reference ID starts with a dot then skip the prefix of
-        // of the presented ID and start the comparison at the position of that
-        // dot. Examples:
-        //
-        //                                       Matches     Doesn't Match
-        //     -----------------------------------------------------------
-        //       original presented ID:  www.example.com    badexample.com
-        //                     skipped:  www                ba
-        //     presented ID w/o prefix:     .example.com      dexample.com
-        //                reference ID:     .example.com      .example.com
-        //
-        // If the reference ID does not start with a dot then we skip the
-        // prefix of the presented ID but also verify that the prefix ends with
-        // a dot. Examples:
-        //
-        //                                       Matches     Doesn't Match
-        //     -----------------------------------------------------------
-        //       original presented ID:  www.example.com    badexample.com
-        //                     skipped:  www                ba
-        //                 must be '.':     .                 d
-        //     presented ID w/o prefix:      example.com       example.com
-        //                reference ID:      example.com       example.com
-        //
-        if (reference.Peek('.')) {
-          if (presented.Skip(static_cast<Input::size_type>(
-                               presentedDNSID.GetLength() -
-                                 referenceDNSID.GetLength())) != Success) {
-            return NotReached("skipping subdomain failed",
-                              Result::FATAL_ERROR_LIBRARY_FAILURE);
-          }
-        } else if (allowDotlessSubdomainMatches ==
-                   AllowDotlessSubdomainMatches::Yes) {
-          if (presented.Skip(static_cast<Input::size_type>(
-                               presentedDNSID.GetLength() -
-                                 referenceDNSID.GetLength() - 1)) != Success) {
-            return NotReached("skipping subdomains failed",
-                              Result::FATAL_ERROR_LIBRARY_FAILURE);
-          }
-          uint8_t b;
-          if (presented.Read(b) != Success) {
-            return NotReached("reading from presentedDNSID failed",
-                              Result::FATAL_ERROR_LIBRARY_FAILURE);
-          }
-          if (b != '.') {
-            matches = false;
-            return Success;
-          }
-        }
-      }
-      break;
-    }
-
-    case IDRole::PresentedID: // fall through
-      return NotReached("IDRole::PresentedID is not a valid referenceDNSIDRole",
-                        Result::FATAL_ERROR_INVALID_ARGS);
-  }
-
-  // We only allow wildcard labels that consist only of '*'.
-  if (presented.Peek('*')) {
-    if (presented.Skip(1) != Success) {
-      return NotReached("Skipping '*' failed",
-                        Result::FATAL_ERROR_LIBRARY_FAILURE);
-    }
-    do {
-      // This will happen if reference is a single, relative label
-      if (reference.AtEnd()) {
-        matches = false;
-        return Success;
-      }
-      uint8_t referenceByte;
-      if (reference.Read(referenceByte) != Success) {
-        return NotReached("invalid reference ID",
-                          Result::FATAL_ERROR_INVALID_ARGS);
-      }
-    } while (!reference.Peek('.'));
-  }
-
-  for (;;) {
-    uint8_t presentedByte;
-    if (presented.Read(presentedByte) != Success) {
-      matches = false;
-      return Success;
-    }
-    uint8_t referenceByte;
-    if (reference.Read(referenceByte) != Success) {
-      matches = false;
-      return Success;
-    }
-    if (LocaleInsensitveToLower(presentedByte) !=
-        LocaleInsensitveToLower(referenceByte)) {
-      matches = false;
-      return Success;
-    }
-    if (presented.AtEnd()) {
-      // Don't allow presented IDs to be absolute.
-      if (presentedByte == '.') {
-        return Result::ERROR_BAD_DER;
-      }
-      break;
-    }
-  }
-
-  // Allow a relative presented DNS ID to match an absolute reference DNS ID,
-  // unless we're matching a name constraint.
-  if (!reference.AtEnd()) {
-    if (referenceDNSIDRole != IDRole::NameConstraint) {
-      uint8_t referenceByte;
-      if (reference.Read(referenceByte) != Success) {
-        return NotReached("read failed but not at end",
-                          Result::FATAL_ERROR_LIBRARY_FAILURE);
-      }
-      if (referenceByte != '.') {
-        matches = false;
-        return Success;
-      }
-    }
-    if (!reference.AtEnd()) {
-      matches = false;
-      return Success;
-    }
-  }
-
-  matches = true;
-  return Success;
-}
-
-// https://tools.ietf.org/html/rfc5280#section-4.2.1.10 says:
-//
-//     For IPv4 addresses, the iPAddress field of GeneralName MUST contain
-//     eight (8) octets, encoded in the style of RFC 4632 (CIDR) to represent
-//     an address range [RFC4632].  For IPv6 addresses, the iPAddress field
-//     MUST contain 32 octets similarly encoded.  For example, a name
-//     constraint for "class C" subnet 192.0.2.0 is represented as the
-//     octets C0 00 02 00 FF FF FF 00, representing the CIDR notation
-//     192.0.2.0/24 (mask 255.255.255.0).
-Result
-MatchPresentedIPAddressWithConstraint(Input presentedID,
-                                      Input iPAddressConstraint,
-                                      /*out*/ bool& foundMatch)
-{
-  if (presentedID.GetLength() != 4 && presentedID.GetLength() != 16) {
-    return Result::ERROR_BAD_DER;
-  }
-  if (iPAddressConstraint.GetLength() != 8 &&
-      iPAddressConstraint.GetLength() != 32) {
-    return Result::ERROR_BAD_DER;
-  }
-
-  // an IPv4 address never matches an IPv6 constraint, and vice versa.
-  if (presentedID.GetLength() * 2 != iPAddressConstraint.GetLength()) {
-    foundMatch = false;
-    return Success;
-  }
-
-  Reader constraint(iPAddressConstraint);
-  Reader constraintAddress;
-  Result rv = constraint.Skip(iPAddressConstraint.GetLength() / 2u,
-                              constraintAddress);
-  if (rv != Success) {
-    return rv;
-  }
-  Reader constraintMask;
-  rv = constraint.Skip(iPAddressConstraint.GetLength() / 2u, constraintMask);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::End(constraint);
-  if (rv != Success) {
-    return rv;
-  }
-
-  Reader presented(presentedID);
-  do {
-    uint8_t presentedByte;
-    rv = presented.Read(presentedByte);
-    if (rv != Success) {
-      return rv;
-    }
-    uint8_t constraintAddressByte;
-    rv = constraintAddress.Read(constraintAddressByte);
-    if (rv != Success) {
-      return rv;
-    }
-    uint8_t constraintMaskByte;
-    rv = constraintMask.Read(constraintMaskByte);
-    if (rv != Success) {
-      return rv;
-    }
-    foundMatch =
-      ((presentedByte ^ constraintAddressByte) & constraintMaskByte) == 0;
-  } while (foundMatch && !presented.AtEnd());
-
-  return Success;
-}
-
-// AttributeTypeAndValue ::= SEQUENCE {
-//   type     AttributeType,
-//   value    AttributeValue }
-//
-// AttributeType ::= OBJECT IDENTIFIER
-//
-// AttributeValue ::= ANY -- DEFINED BY AttributeType
-Result
-ReadAVA(Reader& rdn,
-        /*out*/ Input& type,
-        /*out*/ uint8_t& valueTag,
-        /*out*/ Input& value)
-{
-  return der::Nested(rdn, der::SEQUENCE, [&](Reader& ava) -> Result {
-    Result rv = der::ExpectTagAndGetValue(ava, der::OIDTag, type);
-    if (rv != Success) {
-      return rv;
-    }
-    rv = der::ReadTagAndGetValue(ava, valueTag, value);
-    if (rv != Success) {
-      return rv;
-    }
-    return Success;
-  });
-}
-
-// Names are sequences of RDNs. RDNS are sets of AVAs. That means that RDNs are
-// unordered, so in theory we should match RDNs with equivalent AVAs that are
-// in different orders. Within the AVAs are DirectoryNames that are supposed to
-// be compared according to LDAP stringprep normalization rules (e.g.
-// normalizing whitespace), consideration of different character encodings,
-// etc. Indeed, RFC 5280 says we MUST deal with all of that.
-//
-// In practice, many implementations, including NSS, only match Names in a way
-// that only meets a subset of the requirements of RFC 5280. Those
-// normalization and character encoding conversion steps appear to be
-// unnecessary for processing real-world certificates, based on experience from
-// having used NSS in Firefox for many years.
-//
-// RFC 5280 also says "CAs issuing certificates with a restriction of the form
-// directoryName SHOULD NOT rely on implementation of the full
-// ISO DN name comparison algorithm. This implies name restrictions MUST
-// be stated identically to the encoding used in the subject field or
-// subjectAltName extension." It goes on to say, in the security
-// considerations:
-//
-//     In addition, name constraints for distinguished names MUST be stated
-//     identically to the encoding used in the subject field or
-//     subjectAltName extension.  If not, then name constraints stated as
-//     excludedSubtrees will not match and invalid paths will be accepted
-//     and name constraints expressed as permittedSubtrees will not match
-//     and valid paths will be rejected.  To avoid acceptance of invalid
-//     paths, CAs SHOULD state name constraints for distinguished names as
-//     permittedSubtrees wherever possible.
-//
-// For permittedSubtrees, the MUST-level requirement is relaxed for
-// compatibility in the case of PrintableString and UTF8String. That is, if a
-// name constraint has been encoded using UTF8String and the presented ID has
-// been encoded with a PrintableString (or vice-versa), they are considered to
-// match if they are equal everywhere except for the tag identifying the
-// encoding. See bug 1150114.
-//
-// For excludedSubtrees, we simply prohibit any non-empty directoryName
-// constraint to ensure we are not being too lenient. We support empty
-// DirectoryName constraints in excludedSubtrees so that a CA can say "Do not
-// allow any DirectoryNames in issued certificates."
-Result
-MatchPresentedDirectoryNameWithConstraint(NameConstraintsSubtrees subtreesType,
-                                          Input presentedID,
-                                          Input directoryNameConstraint,
-                                          /*out*/ bool& matches)
-{
-  Reader constraintRDNs;
-  Result rv = der::ExpectTagAndGetValueAtEnd(directoryNameConstraint,
-                                             der::SEQUENCE, constraintRDNs);
-  if (rv != Success) {
-    return rv;
-  }
-  Reader presentedRDNs;
-  rv = der::ExpectTagAndGetValueAtEnd(presentedID, der::SEQUENCE,
-                                      presentedRDNs);
-  if (rv != Success) {
-    return rv;
-  }
-
-  switch (subtreesType) {
-    case NameConstraintsSubtrees::permittedSubtrees:
-      break; // dealt with below
-    case NameConstraintsSubtrees::excludedSubtrees:
-      if (!constraintRDNs.AtEnd() || !presentedRDNs.AtEnd()) {
-        return Result::ERROR_CERT_NOT_IN_NAME_SPACE;
-      }
-      matches = true;
-      return Success;
-  }
-
-  for (;;) {
-    // The AVAs have to be fully equal, but the constraint RDNs just need to be
-    // a prefix of the presented RDNs.
-    if (constraintRDNs.AtEnd()) {
-      matches = true;
-      return Success;
-    }
-    if (presentedRDNs.AtEnd()) {
-      matches = false;
-      return Success;
-    }
-    Reader constraintRDN;
-    rv = der::ExpectTagAndGetValue(constraintRDNs, der::SET, constraintRDN);
-    if (rv != Success) {
-      return rv;
-    }
-    Reader presentedRDN;
-    rv = der::ExpectTagAndGetValue(presentedRDNs, der::SET, presentedRDN);
-    if (rv != Success) {
-      return rv;
-    }
-    while (!constraintRDN.AtEnd() && !presentedRDN.AtEnd()) {
-      Input constraintType;
-      uint8_t constraintValueTag;
-      Input constraintValue;
-      rv = ReadAVA(constraintRDN, constraintType, constraintValueTag,
-                   constraintValue);
-      if (rv != Success) {
-        return rv;
-      }
-      Input presentedType;
-      uint8_t presentedValueTag;
-      Input presentedValue;
-      rv = ReadAVA(presentedRDN, presentedType, presentedValueTag,
-                   presentedValue);
-      if (rv != Success) {
-        return rv;
-      }
-      // TODO (bug 1155767): verify that if an AVA is a PrintableString it
-      // consists only of characters valid for PrintableStrings.
-      bool avasMatch =
-        InputsAreEqual(constraintType, presentedType) &&
-        InputsAreEqual(constraintValue, presentedValue) &&
-        (constraintValueTag == presentedValueTag ||
-         (constraintValueTag == der::Tag::UTF8String &&
-          presentedValueTag == der::Tag::PrintableString) ||
-         (constraintValueTag == der::Tag::PrintableString &&
-          presentedValueTag == der::Tag::UTF8String));
-      if (!avasMatch) {
-        matches = false;
-        return Success;
-      }
-    }
-    if (!constraintRDN.AtEnd() || !presentedRDN.AtEnd()) {
-      matches = false;
-      return Success;
-    }
-  }
-}
-
-// RFC 5280 says:
-//
-//     The format of an rfc822Name is a "Mailbox" as defined in Section 4.1.2
-//     of [RFC2821]. A Mailbox has the form "Local-part@Domain".  Note that a
-//     Mailbox has no phrase (such as a common name) before it, has no comment
-//     (text surrounded in parentheses) after it, and is not surrounded by "<"
-//     and ">".  Rules for encoding Internet mail addresses that include
-//     internationalized domain names are specified in Section 7.5.
-//
-// and:
-//
-//     A name constraint for Internet mail addresses MAY specify a
-//     particular mailbox, all addresses at a particular host, or all
-//     mailboxes in a domain.  To indicate a particular mailbox, the
-//     constraint is the complete mail address.  For example,
-//     "root@example.com" indicates the root mailbox on the host
-//     "example.com".  To indicate all Internet mail addresses on a
-//     particular host, the constraint is specified as the host name.  For
-//     example, the constraint "example.com" is satisfied by any mail
-//     address at the host "example.com".  To specify any address within a
-//     domain, the constraint is specified with a leading period (as with
-//     URIs).  For example, ".example.com" indicates all the Internet mail
-//     addresses in the domain "example.com", but not Internet mail
-//     addresses on the host "example.com".
-
-bool
-IsValidRFC822Name(Input input)
-{
-  Reader reader(input);
-
-  // Local-part@.
-  bool startOfAtom = true;
-  for (;;) {
-    uint8_t presentedByte;
-    if (reader.Read(presentedByte) != Success) {
-      return false;
-    }
-    switch (presentedByte) {
-      // atext is defined in https://tools.ietf.org/html/rfc2822#section-3.2.4
-      case 'A': case 'a': case 'N': case 'n': case '0': case '!': case '#':
-      case 'B': case 'b': case 'O': case 'o': case '1': case '$': case '%':
-      case 'C': case 'c': case 'P': case 'p': case '2': case '&': case '\'':
-      case 'D': case 'd': case 'Q': case 'q': case '3': case '*': case '+':
-      case 'E': case 'e': case 'R': case 'r': case '4': case '-': case '/':
-      case 'F': case 'f': case 'S': case 's': case '5': case '=': case '?':
-      case 'G': case 'g': case 'T': case 't': case '6': case '^': case '_':
-      case 'H': case 'h': case 'U': case 'u': case '7': case '`': case '{':
-      case 'I': case 'i': case 'V': case 'v': case '8': case '|': case '}':
-      case 'J': case 'j': case 'W': case 'w': case '9': case '~':
-      case 'K': case 'k': case 'X': case 'x':
-      case 'L': case 'l': case 'Y': case 'y':
-      case 'M': case 'm': case 'Z': case 'z':
-        startOfAtom = false;
-        break;
-
-      case '.':
-        if (startOfAtom) {
-          return false;
-        }
-        startOfAtom = true;
-        break;
-
-      case '@':
-      {
-        if (startOfAtom) {
-          return false;
-        }
-        Input domain;
-        if (reader.SkipToEnd(domain) != Success) {
-          return false;
-        }
-        return IsValidDNSID(domain, IDRole::PresentedID, AllowWildcards::No);
-      }
-
-      default:
-        return false;
-    }
-  }
-}
-
-Result
-MatchPresentedRFC822NameWithReferenceRFC822Name(Input presentedRFC822Name,
-                                                IDRole referenceRFC822NameRole,
-                                                Input referenceRFC822Name,
-                                                /*out*/ bool& matches)
-{
-  if (!IsValidRFC822Name(presentedRFC822Name)) {
-    return Result::ERROR_BAD_DER;
-  }
-  Reader presented(presentedRFC822Name);
-
-  switch (referenceRFC822NameRole)
-  {
-    case IDRole::PresentedID:
-      return Result::FATAL_ERROR_INVALID_ARGS;
-
-    case IDRole::ReferenceID:
-      break;
-
-    case IDRole::NameConstraint:
-    {
-      if (InputContains(referenceRFC822Name, '@')) {
-        // The constraint is of the form "Local-part@Domain".
-        break;
-      }
-
-      // The constraint is of the form "example.com" or ".example.com".
-
-      // Skip past the '@' in the presented ID.
-      for (;;) {
-        uint8_t presentedByte;
-        if (presented.Read(presentedByte) != Success) {
-          return Result::FATAL_ERROR_LIBRARY_FAILURE;
-        }
-        if (presentedByte == '@') {
-          break;
-        }
-      }
-
-      Input presentedDNSID;
-      if (presented.SkipToEnd(presentedDNSID) != Success) {
-        return Result::FATAL_ERROR_LIBRARY_FAILURE;
-      }
-
-      return MatchPresentedDNSIDWithReferenceDNSID(
-               presentedDNSID, AllowWildcards::No,
-               AllowDotlessSubdomainMatches::No, IDRole::NameConstraint,
-               referenceRFC822Name, matches);
-    }
-  }
-
-  if (!IsValidRFC822Name(referenceRFC822Name)) {
-    return Result::ERROR_BAD_DER;
-  }
-
-  Reader reference(referenceRFC822Name);
-
-  for (;;) {
-    uint8_t presentedByte;
-    if (presented.Read(presentedByte) != Success) {
-      matches = reference.AtEnd();
-      return Success;
-    }
-    uint8_t referenceByte;
-    if (reference.Read(referenceByte) != Success) {
-      matches = false;
-      return Success;
-    }
-    if (LocaleInsensitveToLower(presentedByte) !=
-        LocaleInsensitveToLower(referenceByte)) {
-      matches = false;
-      return Success;
-    }
-  }
-}
-
-// We avoid isdigit because it is locale-sensitive. See
-// http://pubs.opengroup.org/onlinepubs/009695399/functions/tolower.html.
-inline uint8_t
-LocaleInsensitveToLower(uint8_t a)
-{
-  if (a >= 'A' && a <= 'Z') { // unlikely
-    return static_cast<uint8_t>(
-             static_cast<uint8_t>(a - static_cast<uint8_t>('A')) +
-             static_cast<uint8_t>('a'));
-  }
-  return a;
-}
-
-bool
-StartsWithIDNALabel(Input id)
-{
-  static const uint8_t IDN_ALABEL_PREFIX[4] = { 'x', 'n', '-', '-' };
-  Reader input(id);
-  for (const uint8_t prefixByte : IDN_ALABEL_PREFIX) {
-    uint8_t b;
-    if (input.Read(b) != Success) {
-      return false;
-    }
-    if (b != prefixByte) {
-      return false;
-    }
-  }
-  return true;
-}
-
-bool
-ReadIPv4AddressComponent(Reader& input, bool lastComponent,
-                         /*out*/ uint8_t& valueOut)
-{
-  size_t length = 0;
-  unsigned int value = 0; // Must be larger than uint8_t.
-
-  for (;;) {
-    if (input.AtEnd() && lastComponent) {
-      break;
-    }
-
-    uint8_t b;
-    if (input.Read(b) != Success) {
-      return false;
-    }
-
-    if (b >= '0' && b <= '9') {
-      if (value == 0 && length > 0) {
-        return false; // Leading zeros are not allowed.
-      }
-      value = (value * 10) + (b - '0');
-      if (value > 255) {
-        return false; // Component's value is too large.
-      }
-      ++length;
-    } else if (!lastComponent && b == '.') {
-      break;
-    } else {
-      return false; // Invalid character.
-    }
-  }
-
-  if (length == 0) {
-    return false; // empty components not allowed
-  }
-
-  valueOut = static_cast<uint8_t>(value);
-  return true;
-}
-
-} // namespace
-
-// On Windows and maybe other platforms, OS-provided IP address parsing
-// functions might fail if the protocol (IPv4 or IPv6) has been disabled, so we
-// can't rely on them.
-bool
-ParseIPv4Address(Input hostname, /*out*/ uint8_t (&out)[4])
-{
-  Reader input(hostname);
-  return ReadIPv4AddressComponent(input, false, out[0]) &&
-         ReadIPv4AddressComponent(input, false, out[1]) &&
-         ReadIPv4AddressComponent(input, false, out[2]) &&
-         ReadIPv4AddressComponent(input, true, out[3]);
-}
-
-namespace {
-
-bool
-FinishIPv6Address(/*in/out*/ uint8_t (&address)[16], int numComponents,
-                  int contractionIndex)
-{
-  assert(numComponents >= 0);
-  assert(numComponents <= 8);
-  assert(contractionIndex >= -1);
-  assert(contractionIndex <= 8);
-  assert(contractionIndex <= numComponents);
-  if (!(numComponents >= 0 &&
-        numComponents <= 8 &&
-        contractionIndex >= -1 &&
-        contractionIndex <= 8 &&
-        contractionIndex <= numComponents)) {
-    return false;
-  }
-
-  if (contractionIndex == -1) {
-    // no contraction
-    return numComponents == 8;
-  }
-
-  if (numComponents >= 8) {
-    return false; // no room left to expand the contraction.
-  }
-
-  // Shift components that occur after the contraction over.
-  std::copy_backward(address + (2u * static_cast<size_t>(contractionIndex)),
-                     address + (2u * static_cast<size_t>(numComponents)),
-                     address + (2u * 8u));
-  // Fill in the contracted area with zeros.
-  std::fill_n(address + 2u * static_cast<size_t>(contractionIndex),
-              (8u - static_cast<size_t>(numComponents)) * 2u, static_cast<uint8_t>(0u));
-
-  return true;
-}
-
-} // namespace
-
-// On Windows and maybe other platforms, OS-provided IP address parsing
-// functions might fail if the protocol (IPv4 or IPv6) has been disabled, so we
-// can't rely on them.
-bool
-ParseIPv6Address(Input hostname, /*out*/ uint8_t (&out)[16])
-{
-  Reader input(hostname);
-
-  int currentComponentIndex = 0;
-  int contractionIndex = -1;
-
-  if (input.Peek(':')) {
-    // A valid input can only start with ':' if there is a contraction at the
-    // beginning.
-    uint8_t b;
-    if (input.Read(b) != Success || b != ':') {
-      assert(false);
-      return false;
-    }
-    if (input.Read(b) != Success) {
-      return false;
-    }
-    if (b != ':') {
-      return false;
-    }
-    contractionIndex = 0;
-  }
-
-  for (;;) {
-    // If we encounter a '.' then we'll have to backtrack to parse the input
-    // from startOfComponent to the end of the input as an IPv4 address.
-    Reader::Mark startOfComponent(input.GetMark());
-    uint16_t componentValue = 0;
-    size_t componentLength = 0;
-    while (!input.AtEnd() && !input.Peek(':')) {
-      uint8_t value;
-      uint8_t b;
-      if (input.Read(b) != Success) {
-        assert(false);
-        return false;
-      }
-      switch (b) {
-        case '0': case '1': case '2': case '3': case '4':
-        case '5': case '6': case '7': case '8': case '9':
-          value = static_cast<uint8_t>(b - static_cast<uint8_t>('0'));
-          break;
-        case 'a': case 'b': case 'c': case 'd': case 'e': case 'f':
-          value = static_cast<uint8_t>(b - static_cast<uint8_t>('a') +
-                                       UINT8_C(10));
-          break;
-        case 'A': case 'B': case 'C': case 'D': case 'E': case 'F':
-          value = static_cast<uint8_t>(b - static_cast<uint8_t>('A') +
-                                       UINT8_C(10));
-          break;
-        case '.':
-        {
-          // A dot indicates we hit a IPv4-syntax component. Backtrack, parsing
-          // the input from startOfComponent to the end of the input as an IPv4
-          // address, and then combine it with the other components.
-
-          if (currentComponentIndex > 6) {
-            return false; // Too many components before the IPv4 component
-          }
-
-          input.SkipToEnd();
-          Input ipv4Component;
-          if (input.GetInput(startOfComponent, ipv4Component) != Success) {
-            return false;
-          }
-          uint8_t (*ipv4)[4] =
-            reinterpret_cast<uint8_t(*)[4]>(&out[2 * currentComponentIndex]);
-          if (!ParseIPv4Address(ipv4Component, *ipv4)) {
-            return false;
-          }
-          assert(input.AtEnd());
-          currentComponentIndex += 2;
-
-          return FinishIPv6Address(out, currentComponentIndex,
-                                   contractionIndex);
-        }
-        default:
-          return false;
-      }
-      if (componentLength >= 4) {
-        // component too long
-        return false;
-      }
-      ++componentLength;
-      componentValue = (componentValue * 0x10u) + value;
-    }
-
-    if (currentComponentIndex >= 8) {
-      return false; // too many components
-    }
-
-    if (componentLength == 0) {
-      if (input.AtEnd() && currentComponentIndex == contractionIndex) {
-        if (contractionIndex == 0) {
-          // don't accept "::"
-          return false;
-        }
-        return FinishIPv6Address(out, currentComponentIndex,
-                                 contractionIndex);
-      }
-      return false;
-    }
-
-    out[2 * currentComponentIndex] =
-      static_cast<uint8_t>(componentValue / 0x100);
-    out[(2 * currentComponentIndex) + 1] =
-      static_cast<uint8_t>(componentValue % 0x100);
-
-    ++currentComponentIndex;
-
-    if (input.AtEnd()) {
-      return FinishIPv6Address(out, currentComponentIndex,
-                               contractionIndex);
-    }
-
-    uint8_t b;
-    if (input.Read(b) != Success || b != ':') {
-      assert(false);
-      return false;
-    }
-
-    if (input.Peek(':')) {
-      // Contraction
-      if (contractionIndex != -1) {
-        return false; // multiple contractions are not allowed.
-      }
-      if (input.Read(b) != Success || b != ':') {
-        assert(false);
-        return false;
-      }
-      contractionIndex = currentComponentIndex;
-      if (input.AtEnd()) {
-        // "::" at the end of the input.
-        return FinishIPv6Address(out, currentComponentIndex,
-                                 contractionIndex);
-      }
-    }
-  }
-}
-
-bool
-IsValidReferenceDNSID(Input hostname)
-{
-  return IsValidDNSID(hostname, IDRole::ReferenceID, AllowWildcards::No);
-}
-
-bool
-IsValidPresentedDNSID(Input hostname)
-{
-  return IsValidDNSID(hostname, IDRole::PresentedID, AllowWildcards::Yes);
-}
-
-namespace {
-
-// RFC 5280 Section 4.2.1.6 says that a dNSName "MUST be in the 'preferred name
-// syntax', as specified by Section 3.5 of [RFC1034] and as modified by Section
-// 2.1 of [RFC1123]" except "a dNSName of ' ' MUST NOT be used." Additionally,
-// we allow underscores for compatibility with existing practice.
-bool
-IsValidDNSID(Input hostname, IDRole idRole, AllowWildcards allowWildcards)
-{
-  if (hostname.GetLength() > 253) {
-    return false;
-  }
-
-  Reader input(hostname);
-
-  if (idRole == IDRole::NameConstraint && input.AtEnd()) {
-    return true;
-  }
-
-  size_t dotCount = 0;
-  size_t labelLength = 0;
-  bool labelIsAllNumeric = false;
-  bool labelEndsWithHyphen = false;
-
-  // Only presented IDs are allowed to have wildcard labels. And, like
-  // Chromium, be stricter than RFC 6125 requires by insisting that a
-  // wildcard label consist only of '*'.
-  bool isWildcard = allowWildcards == AllowWildcards::Yes && input.Peek('*');
-  bool isFirstByte = !isWildcard;
-  if (isWildcard) {
-    Result rv = input.Skip(1);
-    if (rv != Success) {
-      assert(false);
-      return false;
-    }
-
-    uint8_t b;
-    rv = input.Read(b);
-    if (rv != Success) {
-      return false;
-    }
-    if (b != '.') {
-      return false;
-    }
-    ++dotCount;
-  }
-
-  do {
-    static const size_t MAX_LABEL_LENGTH = 63;
-
-    uint8_t b;
-    if (input.Read(b) != Success) {
-      return false;
-    }
-    switch (b) {
-      case '-':
-        if (labelLength == 0) {
-          return false; // Labels must not start with a hyphen.
-        }
-        labelIsAllNumeric = false;
-        labelEndsWithHyphen = true;
-        ++labelLength;
-        if (labelLength > MAX_LABEL_LENGTH) {
-          return false;
-        }
-        break;
-
-      // We avoid isdigit because it is locale-sensitive. See
-      // http://pubs.opengroup.org/onlinepubs/009695399/functions/isdigit.html
-      case '0': case '5':
-      case '1': case '6':
-      case '2': case '7':
-      case '3': case '8':
-      case '4': case '9':
-        if (labelLength == 0) {
-          labelIsAllNumeric = true;
-        }
-        labelEndsWithHyphen = false;
-        ++labelLength;
-        if (labelLength > MAX_LABEL_LENGTH) {
-          return false;
-        }
-        break;
-
-      // We avoid using islower/isupper/tolower/toupper or similar things, to
-      // avoid any possibility of this code being locale-sensitive. See
-      // http://pubs.opengroup.org/onlinepubs/009695399/functions/isupper.html
-      case 'a': case 'A': case 'n': case 'N':
-      case 'b': case 'B': case 'o': case 'O':
-      case 'c': case 'C': case 'p': case 'P':
-      case 'd': case 'D': case 'q': case 'Q':
-      case 'e': case 'E': case 'r': case 'R':
-      case 'f': case 'F': case 's': case 'S':
-      case 'g': case 'G': case 't': case 'T':
-      case 'h': case 'H': case 'u': case 'U':
-      case 'i': case 'I': case 'v': case 'V':
-      case 'j': case 'J': case 'w': case 'W':
-      case 'k': case 'K': case 'x': case 'X':
-      case 'l': case 'L': case 'y': case 'Y':
-      case 'm': case 'M': case 'z': case 'Z':
-      // We allow underscores for compatibility with existing practices.
-      // See bug 1136616.
-      case '_':
-        labelIsAllNumeric = false;
-        labelEndsWithHyphen = false;
-        ++labelLength;
-        if (labelLength > MAX_LABEL_LENGTH) {
-          return false;
-        }
-        break;
-
-      case '.':
-        ++dotCount;
-        if (labelLength == 0 &&
-            (idRole != IDRole::NameConstraint || !isFirstByte)) {
-          return false;
-        }
-        if (labelEndsWithHyphen) {
-          return false; // Labels must not end with a hyphen.
-        }
-        labelLength = 0;
-        break;
-
-      default:
-        return false; // Invalid character.
-    }
-    isFirstByte = false;
-  } while (!input.AtEnd());
-
-  // Only reference IDs, not presented IDs or name constraints, may be
-  // absolute.
-  if (labelLength == 0 && idRole != IDRole::ReferenceID) {
-    return false;
-  }
-
-  if (labelEndsWithHyphen) {
-    return false; // Labels must not end with a hyphen.
-  }
-
-  if (labelIsAllNumeric) {
-    return false; // Last label must not be all numeric.
-  }
-
-  if (isWildcard) {
-    // If the DNS ID ends with a dot, the last dot signifies an absolute ID.
-    size_t labelCount = (labelLength == 0) ? dotCount : (dotCount + 1);
-
-    // Like NSS, require at least two labels to follow the wildcard label.
-    //
-    // TODO(bug XXXXXXX): Allow the TrustDomain to control this on a
-    // per-eTLD+1 basis, similar to Chromium. Even then, it might be better to
-    // still enforce that there are at least two labels after the wildcard.
-    if (labelCount < 3) {
-      return false;
-    }
-    // XXX: RFC6125 says that we shouldn't accept wildcards within an IDN
-    // A-Label. The consequence of this is that we effectively discriminate
-    // against users of languages that cannot be encoded with ASCII.
-    if (StartsWithIDNALabel(hostname)) {
-      return false;
-    }
-
-    // TODO(bug XXXXXXX): Wildcards are not allowed for EV certificates.
-    // Provide an option to indicate whether wildcards should be matched, for
-    // the purpose of helping the application enforce this.
-  }
-
-  return true;
-}
-
-} // namespace
-
-} } // namespace mozilla::pkix
deleted file mode 100644
--- a/security/pkix/lib/pkixnss.cpp
+++ /dev/null
@@ -1,236 +0,0 @@
-/*- *- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "pkix/pkixnss.h"
-
-#include <limits>
-
-#include "cryptohi.h"
-#include "keyhi.h"
-#include "pk11pub.h"
-#include "pkix/pkix.h"
-#include "pkixutil.h"
-#include "ScopedPtr.h"
-#include "secerr.h"
-#include "sslerr.h"
-
-namespace mozilla { namespace pkix {
-
-namespace {
-
-Result
-VerifySignedDigest(const SignedDigest& sd,
-                   Input subjectPublicKeyInfo,
-                   SECOidTag pubKeyAlg,
-                   void* pkcs11PinArg)
-{
-  SECOidTag digestAlg;
-  switch (sd.digestAlgorithm) {
-    case DigestAlgorithm::sha512: digestAlg = SEC_OID_SHA512; break;
-    case DigestAlgorithm::sha384: digestAlg = SEC_OID_SHA384; break;
-    case DigestAlgorithm::sha256: digestAlg = SEC_OID_SHA256; break;
-    case DigestAlgorithm::sha1: digestAlg = SEC_OID_SHA1; break;
-    MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-  }
-
-  SECItem subjectPublicKeyInfoSECItem =
-    UnsafeMapInputToSECItem(subjectPublicKeyInfo);
-  ScopedPtr<CERTSubjectPublicKeyInfo, SECKEY_DestroySubjectPublicKeyInfo>
-    spki(SECKEY_DecodeDERSubjectPublicKeyInfo(&subjectPublicKeyInfoSECItem));
-  if (!spki) {
-    return MapPRErrorCodeToResult(PR_GetError());
-  }
-  ScopedPtr<SECKEYPublicKey, SECKEY_DestroyPublicKey>
-    pubKey(SECKEY_ExtractPublicKey(spki.get()));
-  if (!pubKey) {
-    return MapPRErrorCodeToResult(PR_GetError());
-  }
-
-  SECItem digestSECItem(UnsafeMapInputToSECItem(sd.digest));
-  SECItem signatureSECItem(UnsafeMapInputToSECItem(sd.signature));
-  SECStatus srv = VFY_VerifyDigestDirect(&digestSECItem, pubKey.get(),
-                                         &signatureSECItem, pubKeyAlg,
-                                         digestAlg, pkcs11PinArg);
-  if (srv != SECSuccess) {
-    return MapPRErrorCodeToResult(PR_GetError());
-  }
-
-  return Success;
-}
-
-} // namespace
-
-Result
-VerifyRSAPKCS1SignedDigestNSS(const SignedDigest& sd,
-                              Input subjectPublicKeyInfo,
-                              void* pkcs11PinArg)
-{
-  return VerifySignedDigest(sd, subjectPublicKeyInfo,
-                            SEC_OID_PKCS1_RSA_ENCRYPTION, pkcs11PinArg);
-}
-
-Result
-VerifyECDSASignedDigestNSS(const SignedDigest& sd,
-                           Input subjectPublicKeyInfo,
-                           void* pkcs11PinArg)
-{
-  return VerifySignedDigest(sd, subjectPublicKeyInfo,
-                            SEC_OID_ANSIX962_EC_PUBLIC_KEY, pkcs11PinArg);
-}
-
-Result
-DigestBufNSS(Input item,
-             DigestAlgorithm digestAlg,
-             /*out*/ uint8_t* digestBuf,
-             size_t digestBufLen)
-{
-  SECOidTag oid;
-  size_t bits;
-  switch (digestAlg) {
-    case DigestAlgorithm::sha512: oid = SEC_OID_SHA512; bits = 512; break;
-    case DigestAlgorithm::sha384: oid = SEC_OID_SHA384; bits = 384; break;
-    case DigestAlgorithm::sha256: oid = SEC_OID_SHA256; bits = 256; break;
-    case DigestAlgorithm::sha1: oid = SEC_OID_SHA1; bits = 160; break;
-    MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-  }
-  if (digestBufLen != bits / 8) {
-    return Result::FATAL_ERROR_INVALID_ARGS;
-  }
-
-  SECItem itemSECItem = UnsafeMapInputToSECItem(item);
-  if (itemSECItem.len >
-        static_cast<decltype(itemSECItem.len)>(
-          std::numeric_limits<int32_t>::max())) {
-    PR_NOT_REACHED("large items should not be possible here");
-    return Result::FATAL_ERROR_INVALID_ARGS;
-  }
-  SECStatus srv = PK11_HashBuf(oid, digestBuf, itemSECItem.data,
-                               static_cast<int32_t>(itemSECItem.len));
-  if (srv != SECSuccess) {
-    return MapPRErrorCodeToResult(PR_GetError());
-  }
-  return Success;
-}
-
-Result
-MapPRErrorCodeToResult(PRErrorCode error)
-{
-  switch (error)
-  {
-#define MOZILLA_PKIX_MAP(mozilla_pkix_result, value, nss_result) \
-    case nss_result: return Result::mozilla_pkix_result;
-
-    MOZILLA_PKIX_MAP_LIST
-
-#undef MOZILLA_PKIX_MAP
-
-    default:
-      return Result::ERROR_UNKNOWN_ERROR;
-  }
-}
-
-PRErrorCode
-MapResultToPRErrorCode(Result result)
-{
-  switch (result)
-  {
-#define MOZILLA_PKIX_MAP(mozilla_pkix_result, value, nss_result) \
-    case Result::mozilla_pkix_result: return nss_result;
-
-    MOZILLA_PKIX_MAP_LIST
-
-#undef MOZILLA_PKIX_MAP
-
-    MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-  }
-}
-
-void
-RegisterErrorTable()
-{
-  // Note that these error strings are not localizable.
-  // When these strings change, update the localization information too.
-  static const PRErrorMessage ErrorTableText[] = {
-    { "MOZILLA_PKIX_ERROR_KEY_PINNING_FAILURE",
-      "The server uses key pinning (HPKP) but no trusted certificate chain "
-      "could be constructed that matches the pinset. Key pinning violations "
-      "cannot be overridden." },
-    { "MOZILLA_PKIX_ERROR_CA_CERT_USED_AS_END_ENTITY",
-      "The server uses a certificate with a basic constraints extension "
-      "identifying it as a certificate authority. For a properly-issued "
-      "certificate, this should not be the case." },
-    { "MOZILLA_PKIX_ERROR_INADEQUATE_KEY_SIZE",
-      "The server presented a certificate with a key size that is too small "
-      "to establish a secure connection." },
-    { "MOZILLA_PKIX_ERROR_V1_CERT_USED_AS_CA",
-      "An X.509 version 1 certificate that is not a trust anchor was used to "
-      "issue the server's certificate. X.509 version 1 certificates are "
-      "deprecated and should not be used to sign other certificates." },
-    { "MOZILLA_PKIX_ERROR_NO_RFC822NAME_MATCH",
-      "The certificate is not valid for the given email address." },
-    { "MOZILLA_PKIX_ERROR_NOT_YET_VALID_CERTIFICATE",
-      "The server presented a certificate that is not yet valid." },
-    { "MOZILLA_PKIX_ERROR_NOT_YET_VALID_ISSUER_CERTIFICATE",
-      "A certificate that is not yet valid was used to issue the server's "
-      "certificate." },
-    { "MOZILLA_PKIX_ERROR_SIGNATURE_ALGORITHM_MISMATCH",
-      "The signature algorithm in the signature field of the certificate does "
-      "not match the algorithm in its signatureAlgorithm field." },
-    { "MOZILLA_PKIX_ERROR_OCSP_RESPONSE_FOR_CERT_MISSING",
-      "The OCSP response does not include a status for the certificate being "
-      "verified." },
-    { "MOZILLA_PKIX_ERROR_VALIDITY_TOO_LONG",
-      "The server presented a certificate that is valid for too long." },
-    { "MOZILLA_PKIX_ERROR_REQUIRED_TLS_FEATURE_MISSING",
-      "A required TLS feature is missing." },
-    { "MOZILLA_PKIX_ERROR_INVALID_INTEGER_ENCODING",
-      "The server presented a certificate that contains an invalid encoding of "
-      "an integer. Common causes include negative serial numbers, negative RSA "
-      "moduli, and encodings that are longer than necessary." },
-    { "MOZILLA_PKIX_ERROR_EMPTY_ISSUER_NAME",
-      "The server presented a certificate with an empty issuer distinguished "
-      "name." },
-    { "MOZILLA_PKIX_ERROR_ADDITIONAL_POLICY_CONSTRAINT_FAILED",
-      "An additional policy constraint failed when validating this "
-      "certificate." },
-    { "MOZILLA_PKIX_ERROR_SELF_SIGNED_CERT",
-      "The certificate is not trusted because it is self-signed." },
-    { "MOZILLA_PKIX_ERROR_MITM_DETECTED",
-      "Your connection is being intercepted by a TLS proxy. Uninstall it if "
-      "possible or configure your device to trust its root certificate." },
-  };
-  // Note that these error strings are not localizable.
-  // When these strings change, update the localization information too.
-
-  static const PRErrorTable ErrorTable = {
-    ErrorTableText,
-    "pkixerrors",
-    ERROR_BASE,
-    PR_ARRAY_SIZE(ErrorTableText)
-  };
-
-  (void) PR_ErrorInstallTable(&ErrorTable);
-}
-
-} } // namespace mozilla::pkix
deleted file mode 100644
--- a/security/pkix/lib/pkixocsp.cpp
+++ /dev/null
@@ -1,1012 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <limits>
-
-#include "pkix/pkix.h"
-#include "pkixcheck.h"
-#include "pkixutil.h"
-
-namespace {
-
-const size_t SHA1_DIGEST_LENGTH = 160 / 8;
-
-} // namespace
-
-namespace mozilla { namespace pkix {
-
-// These values correspond to the tag values in the ASN.1 CertStatus
-enum class CertStatus : uint8_t {
-  Good = der::CONTEXT_SPECIFIC | 0,
-  Revoked = der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 1,
-  Unknown = der::CONTEXT_SPECIFIC | 2
-};
-
-class Context final
-{
-public:
-  Context(TrustDomain& aTrustDomain, const CertID& aCertID, Time aTime,
-          uint16_t aMaxLifetimeInDays, /*optional out*/ Time* aThisUpdate,
-          /*optional out*/ Time* aValidThrough)
-    : trustDomain(aTrustDomain)
-    , certID(aCertID)
-    , time(aTime)
-    , maxLifetimeInDays(aMaxLifetimeInDays)
-    , certStatus(CertStatus::Unknown)
-    , thisUpdate(aThisUpdate)
-    , validThrough(aValidThrough)
-    , expired(false)
-    , matchFound(false)
-  {
-    if (thisUpdate) {
-      *thisUpdate = TimeFromElapsedSecondsAD(0);
-    }
-    if (validThrough) {
-      *validThrough = TimeFromElapsedSecondsAD(0);
-    }
-  }
-
-  TrustDomain& trustDomain;
-  const CertID& certID;
-  const Time time;
-  const uint16_t maxLifetimeInDays;
-  CertStatus certStatus;
-  Time* thisUpdate;
-  Time* validThrough;
-  bool expired;
-
-  Input signedCertificateTimestamps;
-
-  // Keep track of whether the OCSP response contains the status of the
-  // certificate we're interested in. Responders might reply without
-  // including the status of any of the requested certs, we should
-  // indicate a server failure in those cases.
-  bool matchFound;
-
-  Context(const Context&) = delete;
-  void operator=(const Context&) = delete;
-};
-
-// Verify that potentialSigner is a valid delegated OCSP response signing cert
-// according to RFC 6960 section 4.2.2.2.
-static Result
-CheckOCSPResponseSignerCert(TrustDomain& trustDomain,
-                            BackCert& potentialSigner,
-                            Input issuerSubject,
-                            Input issuerSubjectPublicKeyInfo,
-                            Time time)
-{
-  Result rv;
-
-  // We don't need to do a complete verification of the signer (i.e. we don't
-  // have to call BuildCertChain to verify the entire chain) because we
-  // already know that the issuer is valid, since revocation checking is done
-  // from the root to the parent after we've built a complete chain that we
-  // know is otherwise valid. Rather, we just need to do a one-step validation
-  // from potentialSigner to the issuer.
-  //
-  // It seems reasonable to require the KU_DIGITAL_SIGNATURE key usage on the
-  // OCSP responder certificate if the OCSP responder certificate has a
-  // key usage extension. However, according to bug 240456, some OCSP responder
-  // certificates may have only the nonRepudiation bit set. Also, the OCSP
-  // specification (RFC 6960) does not mandate any particular key usage to be
-  // asserted for OCSP responde signers. Oddly, the CABForum Baseline
-  // Requirements v.1.1.5 do say "If the Root CA Private Key is used for
-  // signing OCSP responses, then the digitalSignature bit MUST be set."
-  //
-  // Note that CheckIssuerIndependentProperties processes
-  // SEC_OID_OCSP_RESPONDER in the way that the OCSP specification requires us
-  // to--in particular, it doesn't allow SEC_OID_OCSP_RESPONDER to be implied
-  // by a missing EKU extension, unlike other EKUs.
-  //
-  // TODO(bug 926261): If we're validating for a policy then the policy OID we
-  // are validating for should be passed to CheckIssuerIndependentProperties.
-  TrustLevel unusedTrustLevel;
-  rv = CheckIssuerIndependentProperties(trustDomain, potentialSigner, time,
-                                        KeyUsage::noParticularKeyUsageRequired,
-                                        KeyPurposeId::id_kp_OCSPSigning,
-                                        CertPolicyId::anyPolicy, 0,
-                                        unusedTrustLevel);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // It is possible that there exists a certificate with the same key as the
-  // issuer but with a different name, so we need to compare names
-  // XXX(bug 926270) XXX(bug 1008133) XXX(bug 980163): Improve name
-  // comparison.
-  // TODO: needs test
-  if (!InputsAreEqual(potentialSigner.GetIssuer(), issuerSubject)) {
-    return Result::ERROR_OCSP_RESPONDER_CERT_INVALID;
-  }
-
-  // TODO(bug 926260): check name constraints
-
-  rv = VerifySignedData(trustDomain, potentialSigner.GetSignedData(),
-                        issuerSubjectPublicKeyInfo);
-
-  // TODO: check for revocation of the OCSP responder certificate unless no-check
-  // or the caller forcing no-check. To properly support the no-check policy, we'd
-  // need to enforce policy constraints from the issuerChain.
-
-  return rv;
-}
-
-enum class ResponderIDType : uint8_t
-{
-  byName = der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 1,
-  byKey = der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 2
-};
-
-static inline Result OCSPResponse(Reader&, Context&);
-static inline Result ResponseBytes(Reader&, Context&);
-static inline Result BasicResponse(Reader&, Context&);
-static inline Result ResponseData(
-                       Reader& tbsResponseData,
-                       Context& context,
-                       const der::SignedDataWithSignature& signedResponseData,
-                       const DERArray& certs);
-static inline Result SingleResponse(Reader& input, Context& context);
-static Result ExtensionNotUnderstood(Reader& extnID, Input extnValue,
-                                     bool critical, /*out*/ bool& understood);
-static Result RememberSingleExtension(Context& context, Reader& extnID,
-                                      Input extnValue, bool critical,
-                                      /*out*/ bool& understood);
-// It is convention to name the function after the part of the data structure
-// we're parsing from the RFC (e.g. OCSPResponse, ResponseBytes).
-// But since we also have a C++ type called CertID, this function doesn't
-// follow the convention to prevent shadowing.
-static inline Result MatchCertID(Reader& input,
-                                 const Context& context,
-                                 /*out*/ bool& match);
-static Result MatchKeyHash(TrustDomain& trustDomain,
-                           Input issuerKeyHash,
-                           Input issuerSubjectPublicKeyInfo,
-                           /*out*/ bool& match);
-static Result KeyHash(TrustDomain& trustDomain,
-                      Input subjectPublicKeyInfo,
-                      /*out*/ uint8_t* hashBuf, size_t hashBufSize);
-
-static Result
-MatchResponderID(TrustDomain& trustDomain,
-                 ResponderIDType responderIDType,
-                 Input responderID,
-                 Input potentialSignerSubject,
-                 Input potentialSignerSubjectPublicKeyInfo,
-                 /*out*/ bool& match)
-{
-  match = false;
-
-  switch (responderIDType) {
-    case ResponderIDType::byName:
-      // XXX(bug 926270) XXX(bug 1008133) XXX(bug 980163): Improve name
-      // comparison.
-      match = InputsAreEqual(responderID, potentialSignerSubject);
-      return Success;
-
-    case ResponderIDType::byKey:
-    {
-      Reader input(responderID);
-      Input keyHash;
-      Result rv = der::ExpectTagAndGetValue(input, der::OCTET_STRING, keyHash);
-      if (rv != Success) {
-        return rv;
-      }
-      return MatchKeyHash(trustDomain, keyHash,
-                          potentialSignerSubjectPublicKeyInfo, match);
-    }
-
-    MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-  }
-}
-
-static Result
-VerifyOCSPSignedData(TrustDomain& trustDomain,
-                     const der::SignedDataWithSignature& signedResponseData,
-                     Input spki)
-{
-  Result rv = VerifySignedData(trustDomain, signedResponseData, spki);
-  if (rv == Result::ERROR_BAD_SIGNATURE) {
-    rv = Result::ERROR_OCSP_BAD_SIGNATURE;
-  }
-  return rv;
-}
-
-// RFC 6960 section 4.2.2.2: The OCSP responder must either be the issuer of
-// the cert or it must be a delegated OCSP response signing cert directly
-// issued by the issuer. If the OCSP responder is a delegated OCSP response
-// signer, then its certificate is (probably) embedded within the OCSP
-// response and we'll need to verify that it is a valid certificate that chains
-// *directly* to issuerCert.
-static Result
-VerifySignature(Context& context, ResponderIDType responderIDType,
-                Input responderID, const DERArray& certs,
-                const der::SignedDataWithSignature& signedResponseData)
-{
-  bool match;
-  Result rv = MatchResponderID(context.trustDomain, responderIDType,
-                               responderID, context.certID.issuer,
-                               context.certID.issuerSubjectPublicKeyInfo,
-                               match);
-  if (rv != Success) {
-    return rv;
-  }
-  if (match) {
-    return VerifyOCSPSignedData(context.trustDomain, signedResponseData,
-                                context.certID.issuerSubjectPublicKeyInfo);
-  }
-
-  size_t numCerts = certs.GetLength();
-  for (size_t i = 0; i < numCerts; ++i) {
-    BackCert cert(*certs.GetDER(i), EndEntityOrCA::MustBeEndEntity, nullptr);
-    rv = cert.Init();
-    if (rv != Success) {
-      return rv;
-    }
-    rv = MatchResponderID(context.trustDomain, responderIDType, responderID,
-                          cert.GetSubject(), cert.GetSubjectPublicKeyInfo(),
-                          match);
-    if (rv != Success) {
-      if (IsFatalError(rv)) {
-        return rv;
-      }
-      continue;
-    }
-
-    if (match) {
-      rv = CheckOCSPResponseSignerCert(context.trustDomain, cert,
-                                       context.certID.issuer,
-                                       context.certID.issuerSubjectPublicKeyInfo,
-                                       context.time);
-      if (rv != Success) {
-        if (IsFatalError(rv)) {
-          return rv;
-        }
-        continue;
-      }
-
-      return VerifyOCSPSignedData(context.trustDomain, signedResponseData,
-                                  cert.GetSubjectPublicKeyInfo());
-    }
-  }
-
-  return Result::ERROR_OCSP_INVALID_SIGNING_CERT;
-}
-
-static inline Result
-MapBadDERToMalformedOCSPResponse(Result rv)
-{
-  if (rv == Result::ERROR_BAD_DER) {
-    return Result::ERROR_OCSP_MALFORMED_RESPONSE;
-  }
-  return rv;
-}
-
-Result
-VerifyEncodedOCSPResponse(TrustDomain& trustDomain, const struct CertID& certID,
-                          Time time, uint16_t maxOCSPLifetimeInDays,
-                          Input encodedResponse,
-                          /*out*/ bool& expired,
-                          /*optional out*/ Time* thisUpdate,
-                          /*optional out*/ Time* validThrough)
-{
-  // Always initialize this to something reasonable.
-  expired = false;
-
-  Context context(trustDomain, certID, time, maxOCSPLifetimeInDays,
-                  thisUpdate, validThrough);
-
-  Reader input(encodedResponse);
-  Result rv = der::Nested(input, der::SEQUENCE, [&context](Reader& r) {
-    return OCSPResponse(r, context);
-  });
-  if (rv != Success) {
-    return MapBadDERToMalformedOCSPResponse(rv);
-  }
-  rv = der::End(input);
-  if (rv != Success) {
-    return MapBadDERToMalformedOCSPResponse(rv);
-  }
-  if (!context.matchFound) {
-    return Result::ERROR_OCSP_RESPONSE_FOR_CERT_MISSING;
-  }
-
-  expired = context.expired;
-
-  switch (context.certStatus) {
-    case CertStatus::Good:
-      if (expired) {
-        return Result::ERROR_OCSP_OLD_RESPONSE;
-      }
-      if (context.signedCertificateTimestamps.GetLength()) {
-        Input sctList;
-        rv = ExtractSignedCertificateTimestampListFromExtension(
-          context.signedCertificateTimestamps, sctList);
-        if (rv != Success) {
-          return MapBadDERToMalformedOCSPResponse(rv);
-        }
-        context.trustDomain.NoteAuxiliaryExtension(
-          AuxiliaryExtension::SCTListFromOCSPResponse, sctList);
-      }
-      return Success;
-    case CertStatus::Revoked:
-      return Result::ERROR_REVOKED_CERTIFICATE;
-    case CertStatus::Unknown:
-      return Result::ERROR_OCSP_UNKNOWN_CERT;
-     MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-  }
-}
-
-// OCSPResponse ::= SEQUENCE {
-//       responseStatus         OCSPResponseStatus,
-//       responseBytes          [0] EXPLICIT ResponseBytes OPTIONAL }
-//
-static inline Result
-OCSPResponse(Reader& input, Context& context)
-{
-  // OCSPResponseStatus ::= ENUMERATED {
-  //     successful            (0),  -- Response has valid confirmations
-  //     malformedRequest      (1),  -- Illegal confirmation request
-  //     internalError         (2),  -- Internal error in issuer
-  //     tryLater              (3),  -- Try again later
-  //                                 -- (4) is not used
-  //     sigRequired           (5),  -- Must sign the request
-  //     unauthorized          (6)   -- Request unauthorized
-  // }
-  uint8_t responseStatus;
-
-  Result rv = der::Enumerated(input, responseStatus);
-  if (rv != Success) {
-    return rv;
-  }
-  switch (responseStatus) {
-    case 0: break; // successful
-    case 1: return Result::ERROR_OCSP_MALFORMED_REQUEST;
-    case 2: return Result::ERROR_OCSP_SERVER_ERROR;
-    case 3: return Result::ERROR_OCSP_TRY_SERVER_LATER;
-    case 5: return Result::ERROR_OCSP_REQUEST_NEEDS_SIG;
-    case 6: return Result::ERROR_OCSP_UNAUTHORIZED_REQUEST;
-    default: return Result::ERROR_OCSP_UNKNOWN_RESPONSE_STATUS;
-  }
-
-  return der::Nested(input, der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 0,
-                     der::SEQUENCE, [&context](Reader& r) {
-    return ResponseBytes(r, context);
-  });
-}
-
-// ResponseBytes ::=       SEQUENCE {
-//     responseType   OBJECT IDENTIFIER,
-//     response       OCTET STRING }
-static inline Result
-ResponseBytes(Reader& input, Context& context)
-{
-  static const uint8_t id_pkix_ocsp_basic[] = {
-    0x2B, 0x06, 0x01, 0x05, 0x05, 0x07, 0x30, 0x01, 0x01
-  };
-
-  Result rv = der::OID(input, id_pkix_ocsp_basic);
-  if (rv != Success) {
-    return rv;
-  }
-
-  return der::Nested(input, der::OCTET_STRING, der::SEQUENCE,
-                     [&context](Reader& r) {
-    return BasicResponse(r, context);
-  });
-}
-
-// BasicOCSPResponse       ::= SEQUENCE {
-//    tbsResponseData      ResponseData,
-//    signatureAlgorithm   AlgorithmIdentifier,
-//    signature            BIT STRING,
-//    certs            [0] EXPLICIT SEQUENCE OF Certificate OPTIONAL }
-Result
-BasicResponse(Reader& input, Context& context)
-{
-  Reader tbsResponseData;
-  der::SignedDataWithSignature signedData;
-  Result rv = der::SignedData(input, tbsResponseData, signedData);
-  if (rv != Success) {
-    if (rv == Result::ERROR_BAD_SIGNATURE) {
-      return Result::ERROR_OCSP_BAD_SIGNATURE;
-    }
-    return rv;
-  }
-
-  // Parse certificates, if any
-  NonOwningDERArray certs;
-  if (!input.AtEnd()) {
-    rv = der::Nested(input, der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 0,
-                     der::SEQUENCE, [&certs](Reader& certsDER) -> Result {
-      while (!certsDER.AtEnd()) {
-        Input cert;
-        Result nestedRv =
-          der::ExpectTagAndGetTLV(certsDER, der::SEQUENCE, cert);
-        if (nestedRv != Success) {
-          return nestedRv;
-        }
-        nestedRv = certs.Append(cert);
-        if (nestedRv != Success) {
-          return Result::ERROR_BAD_DER; // Too many certs
-        }
-      }
-      return Success;
-    });
-    if (rv != Success) {
-      return rv;
-    }
-  }
-
-  return ResponseData(tbsResponseData, context, signedData, certs);
-}
-
-// ResponseData ::= SEQUENCE {
-//    version             [0] EXPLICIT Version DEFAULT v1,
-//    responderID             ResponderID,
-//    producedAt              GeneralizedTime,
-//    responses               SEQUENCE OF SingleResponse,
-//    responseExtensions  [1] EXPLICIT Extensions OPTIONAL }
-static inline Result
-ResponseData(Reader& input, Context& context,
-             const der::SignedDataWithSignature& signedResponseData,
-             const DERArray& certs)
-{
-  der::Version version;
-  Result rv = der::OptionalVersion(input, version);
-  if (rv != Success) {
-    return rv;
-  }
-  if (version != der::Version::v1) {
-    // TODO: more specific error code for bad version?
-    return Result::ERROR_BAD_DER;
-  }
-
-  // ResponderID ::= CHOICE {
-  //    byName              [1] Name,
-  //    byKey               [2] KeyHash }
-  Input responderID;
-  ResponderIDType responderIDType
-    = input.Peek(static_cast<uint8_t>(ResponderIDType::byName))
-    ? ResponderIDType::byName
-    : ResponderIDType::byKey;
-  rv = der::ExpectTagAndGetValue(input, static_cast<uint8_t>(responderIDType),
-                                 responderID);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // This is the soonest we can verify the signature. We verify the signature
-  // right away to follow the principal of minimizing the processing of data
-  // before verifying its signature.
-  rv = VerifySignature(context, responderIDType, responderID, certs,
-                       signedResponseData);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // TODO: Do we even need to parse this? Should we just skip it?
-  Time producedAt(Time::uninitialized);
-  rv = der::GeneralizedTime(input, producedAt);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // We don't accept an empty sequence of responses. In practice, a legit OCSP
-  // responder will never return an empty response, and handling the case of an
-  // empty response makes things unnecessarily complicated.
-  rv = der::NestedOf(input, der::SEQUENCE, der::SEQUENCE,
-                     der::EmptyAllowed::No, [&context](Reader& r) {
-    return SingleResponse(r, context);
-  });
-  if (rv != Success) {
-    return rv;
-  }
-
-  return der::OptionalExtensions(input,
-                                 der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 1,
-                                 ExtensionNotUnderstood);
-}
-
-// SingleResponse ::= SEQUENCE {
-//    certID                       CertID,
-//    certStatus                   CertStatus,
-//    thisUpdate                   GeneralizedTime,
-//    nextUpdate           [0]     EXPLICIT GeneralizedTime OPTIONAL,
-//    singleExtensions     [1]     EXPLICIT Extensions{{re-ocsp-crl |
-//                                              re-ocsp-archive-cutoff |
-//                                              CrlEntryExtensions, ...}
-//                                              } OPTIONAL }
-static inline Result
-SingleResponse(Reader& input, Context& context)
-{
-  bool match = false;
-  Result rv = der::Nested(input, der::SEQUENCE, [&context, &match](Reader& r) {
-    return MatchCertID(r, context, match);
-  });
-  if (rv != Success) {
-    return rv;
-  }
-
-  if (!match) {
-    // This response does not reference the certificate we're interested in.
-    // By consuming the rest of our input and returning successfully, we can
-    // continue processing and examine another response that might have what
-    // we want.
-    input.SkipToEnd();
-    return Success;
-  }
-
-  // We found a response for the cert we're interested in.
-  context.matchFound = true;
-
-  // CertStatus ::= CHOICE {
-  //     good        [0]     IMPLICIT NULL,
-  //     revoked     [1]     IMPLICIT RevokedInfo,
-  //     unknown     [2]     IMPLICIT UnknownInfo }
-  //
-  // In the event of multiple SingleResponses for a cert that have conflicting
-  // statuses, we use the following precedence rules:
-  //
-  // * revoked overrides good and unknown
-  // * good overrides unknown
-  if (input.Peek(static_cast<uint8_t>(CertStatus::Good))) {
-    rv = der::ExpectTagAndEmptyValue(input,
-                                     static_cast<uint8_t>(CertStatus::Good));
-    if (rv != Success) {
-      return rv;
-    }
-    if (context.certStatus != CertStatus::Revoked) {
-      context.certStatus = CertStatus::Good;
-    }
-  } else if (input.Peek(static_cast<uint8_t>(CertStatus::Revoked))) {
-    // We don't need any info from the RevokedInfo structure, so we don't even
-    // parse it. TODO: We should mention issues like this in the explanation of
-    // why we treat invalid OCSP responses equivalently to revoked for OCSP
-    // stapling.
-    rv = der::ExpectTagAndSkipValue(input,
-                                    static_cast<uint8_t>(CertStatus::Revoked));
-    if (rv != Success) {
-      return rv;
-    }
-    context.certStatus = CertStatus::Revoked;
-  } else {
-    rv = der::ExpectTagAndEmptyValue(input,
-                                     static_cast<uint8_t>(CertStatus::Unknown));
-    if (rv != Success) {
-      return rv;
-    }
-  }
-
-  // http://tools.ietf.org/html/rfc6960#section-3.2
-  // 5. The time at which the status being indicated is known to be
-  //    correct (thisUpdate) is sufficiently recent;
-  // 6. When available, the time at or before which newer information will
-  //    be available about the status of the certificate (nextUpdate) is
-  //    greater than the current time.
-
-  Time thisUpdate(Time::uninitialized);
-  rv = der::GeneralizedTime(input, thisUpdate);
-  if (rv != Success) {
-    return rv;
-  }
-
-  static const uint64_t SLOP_SECONDS = Time::ONE_DAY_IN_SECONDS;
-
-  Time timePlusSlop(context.time);
-  rv = timePlusSlop.AddSeconds(SLOP_SECONDS);
-  if (rv != Success) {
-    return rv;
-  }
-  if (thisUpdate > timePlusSlop) {
-    return Result::ERROR_OCSP_FUTURE_RESPONSE;
-  }
-
-  Time notAfter(Time::uninitialized);
-  static const uint8_t NEXT_UPDATE_TAG =
-    der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 0;
-  if (input.Peek(NEXT_UPDATE_TAG)) {
-    Time nextUpdate(Time::uninitialized);
-    rv = der::Nested(input, NEXT_UPDATE_TAG, [&nextUpdate](Reader& r) {
-      return der::GeneralizedTime(r, nextUpdate);
-    });
-    if (rv != Success) {
-      return rv;
-    }
-
-    if (nextUpdate < thisUpdate) {
-      return Result::ERROR_OCSP_MALFORMED_RESPONSE;
-    }
-    notAfter = thisUpdate;
-    if (notAfter.AddSeconds(context.maxLifetimeInDays *
-                            Time::ONE_DAY_IN_SECONDS) != Success) {
-      // This could only happen if we're dealing with times beyond the year
-      // 10,000AD.
-      return Result::ERROR_OCSP_FUTURE_RESPONSE;
-    }
-    if (nextUpdate <= notAfter) {
-      notAfter = nextUpdate;
-    }
-  } else {
-    // NSS requires all OCSP responses without a nextUpdate to be recent.
-    // Match that stricter behavior.
-    notAfter = thisUpdate;
-    if (notAfter.AddSeconds(Time::ONE_DAY_IN_SECONDS) != Success) {
-      // This could only happen if we're dealing with times beyond the year
-      // 10,000AD.
-      return Result::ERROR_OCSP_FUTURE_RESPONSE;
-    }
-  }
-
-  // Add some slop to hopefully handle clock-skew.
-  Time notAfterPlusSlop(notAfter);
-  rv = notAfterPlusSlop.AddSeconds(SLOP_SECONDS);
-  if (rv != Success) {
-    // This could only happen if we're dealing with times beyond the year
-    // 10,000AD.
-    return Result::ERROR_OCSP_FUTURE_RESPONSE;
-  }
-  if (context.time > notAfterPlusSlop) {
-    context.expired = true;
-  }
-
-  rv = der::OptionalExtensions(
-    input,
-    der::CONTEXT_SPECIFIC | der::CONSTRUCTED | 1,
-    [&context](Reader& extnID, const Input& extnValue, bool critical,
-               /*out*/ bool& understood) {
-      return RememberSingleExtension(context, extnID, extnValue, critical,
-                                     understood);
-    });
-
-  if (rv != Success) {
-    return rv;
-  }
-
-  if (context.thisUpdate) {
-    *context.thisUpdate = thisUpdate;
-  }
-  if (context.validThrough) {
-    *context.validThrough = notAfterPlusSlop;
-  }
-
-  return Success;
-}
-
-// CertID          ::=     SEQUENCE {
-//        hashAlgorithm       AlgorithmIdentifier,
-//        issuerNameHash      OCTET STRING, -- Hash of issuer's DN
-//        issuerKeyHash       OCTET STRING, -- Hash of issuer's public key
-//        serialNumber        CertificateSerialNumber }
-static inline Result
-MatchCertID(Reader& input, const Context& context, /*out*/ bool& match)
-{
-  match = false;
-
-  DigestAlgorithm hashAlgorithm;
-  Result rv = der::DigestAlgorithmIdentifier(input, hashAlgorithm);
-  if (rv != Success) {
-    if (rv == Result::ERROR_INVALID_ALGORITHM) {
-      // Skip entries that are hashed with algorithms we don't support.
-      input.SkipToEnd();
-      return Success;
-    }
-    return rv;
-  }
-
-  Input issuerNameHash;
-  rv = der::ExpectTagAndGetValue(input, der::OCTET_STRING, issuerNameHash);
-  if (rv != Success) {
-    return rv;
-  }
-
-  Input issuerKeyHash;
-  rv = der::ExpectTagAndGetValue(input, der::OCTET_STRING, issuerKeyHash);
-  if (rv != Success) {
-    return rv;
-  }
-
-  Input serialNumber;
-  rv = der::CertificateSerialNumber(input, serialNumber);
-  if (rv != Success) {
-    return rv;
-  }
-
-  if (!InputsAreEqual(serialNumber, context.certID.serialNumber)) {
-    // This does not reference the certificate we're interested in.
-    // Consume the rest of the input and return successfully to
-    // potentially continue processing other responses.
-    input.SkipToEnd();
-    return Success;
-  }
-
-  // TODO: support SHA-2 hashes.
-
-  if (hashAlgorithm != DigestAlgorithm::sha1) {
-    // Again, not interested in this response. Consume input, return success.
-    input.SkipToEnd();
-    return Success;
-  }
-
-  if (issuerNameHash.GetLength() != SHA1_DIGEST_LENGTH) {
-    return Result::ERROR_OCSP_MALFORMED_RESPONSE;
-  }
-
-  // From http://tools.ietf.org/html/rfc6960#section-4.1.1:
-  // "The hash shall be calculated over the DER encoding of the
-  // issuer's name field in the certificate being checked."
-  uint8_t hashBuf[SHA1_DIGEST_LENGTH];
-  rv = context.trustDomain.DigestBuf(context.certID.issuer,
-                                     DigestAlgorithm::sha1, hashBuf,
-                                     sizeof(hashBuf));
-  if (rv != Success) {
-    return rv;
-  }
-  Input computed(hashBuf);
-  if (!InputsAreEqual(computed, issuerNameHash)) {
-    // Again, not interested in this response. Consume input, return success.
-    input.SkipToEnd();
-    return Success;
-  }
-
-  return MatchKeyHash(context.trustDomain, issuerKeyHash,
-                      context.certID.issuerSubjectPublicKeyInfo, match);
-}
-
-// From http://tools.ietf.org/html/rfc6960#section-4.1.1:
-// "The hash shall be calculated over the value (excluding tag and length) of
-// the subject public key field in the issuer's certificate."
-//
-// From http://tools.ietf.org/html/rfc6960#appendix-B.1:
-// KeyHash ::= OCTET STRING -- SHA-1 hash of responder's public key
-//                          -- (i.e., the SHA-1 hash of the value of the
-//                          -- BIT STRING subjectPublicKey [excluding
-//                          -- the tag, length, and number of unused
-//                          -- bits] in the responder's certificate)
-static Result
-MatchKeyHash(TrustDomain& trustDomain, Input keyHash,
-             const Input subjectPublicKeyInfo, /*out*/ bool& match)
-{
-  if (keyHash.GetLength() != SHA1_DIGEST_LENGTH)  {
-    return Result::ERROR_OCSP_MALFORMED_RESPONSE;
-  }
-  uint8_t hashBuf[SHA1_DIGEST_LENGTH];
-  Result rv = KeyHash(trustDomain, subjectPublicKeyInfo, hashBuf,
-                      sizeof hashBuf);
-  if (rv != Success) {
-    return rv;
-  }
-  Input computed(hashBuf);
-  match = InputsAreEqual(computed, keyHash);
-  return Success;
-}
-
-// TODO(bug 966856): support SHA-2 hashes
-Result
-KeyHash(TrustDomain& trustDomain, const Input subjectPublicKeyInfo,
-        /*out*/ uint8_t* hashBuf, size_t hashBufSize)
-{
-  if (!hashBuf || hashBufSize != SHA1_DIGEST_LENGTH) {
-    return Result::FATAL_ERROR_LIBRARY_FAILURE;
-  }
-
-  // RFC 5280 Section 4.1
-  //
-  // SubjectPublicKeyInfo  ::=  SEQUENCE  {
-  //    algorithm            AlgorithmIdentifier,
-  //    subjectPublicKey     BIT STRING  }
-
-  Reader spki;
-  Result rv = der::ExpectTagAndGetValueAtEnd(subjectPublicKeyInfo,
-                                             der::SEQUENCE, spki);
-  if (rv != Success) {
-    return rv;
-  }
-
-  // Skip AlgorithmIdentifier
-  rv = der::ExpectTagAndSkipValue(spki, der::SEQUENCE);
-  if (rv != Success) {
-    return rv;
-  }
-
-  Input subjectPublicKey;
-  rv = der::BitStringWithNoUnusedBits(spki, subjectPublicKey);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = der::End(spki);
-  if (rv != Success) {
-    return rv;
-  }
-
-  return trustDomain.DigestBuf(subjectPublicKey, DigestAlgorithm::sha1,
-                               hashBuf, hashBufSize);
-}
-
-Result
-ExtensionNotUnderstood(Reader& /*extnID*/, Input /*extnValue*/,
-                       bool /*critical*/, /*out*/ bool& understood)
-{
-  understood = false;
-  return Success;
-}
-
-Result
-RememberSingleExtension(Context& context, Reader& extnID, Input extnValue,
-                        bool /*critical*/, /*out*/ bool& understood)
-{
-  understood = false;
-
-  // SingleExtension for Signed Certificate Timestamp List.
-  // See Section 3.3 of RFC 6962.
-  // python DottedOIDToCode.py
-  //   id_ocsp_singleExtensionSctList 1.3.6.1.4.1.11129.2.4.5
-  static const uint8_t id_ocsp_singleExtensionSctList[] = {
-    0x2b, 0x06, 0x01, 0x04, 0x01, 0xd6, 0x79, 0x02, 0x04, 0x05
-  };
-
-  if (extnID.MatchRest(id_ocsp_singleExtensionSctList)) {
-    // Empty values are not allowed for this extension. Note that
-    // we assume this later, when checking if the extension was present.
-    if (extnValue.GetLength() == 0) {
-      return Result::ERROR_EXTENSION_VALUE_INVALID;
-    }
-    if (context.signedCertificateTimestamps.Init(extnValue) != Success) {
-      // Duplicate extension.
-      return Result::ERROR_EXTENSION_VALUE_INVALID;
-    }
-    understood = true;
-  }
-
-  return Success;
-}
-
-//   1. The certificate identified in a received response corresponds to
-//      the certificate that was identified in the corresponding request;
-//   2. The signature on the response is valid;
-//   3. The identity of the signer matches the intended recipient of the
-//      request;
-//   4. The signer is currently authorized to provide a response for the
-//      certificate in question;
-//   5. The time at which the status being indicated is known to be
-//      correct (thisUpdate) is sufficiently recent;
-//   6. When available, the time at or before which newer information will
-//      be available about the status of the certificate (nextUpdate) is
-//      greater than the current time.
-//
-//   Responses whose nextUpdate value is earlier than
-//   the local system time value SHOULD be considered unreliable.
-//   Responses whose thisUpdate time is later than the local system time
-//   SHOULD be considered unreliable.
-//
-//   If nextUpdate is not set, the responder is indicating that newer
-//   revocation information is available all the time.
-//
-// http://tools.ietf.org/html/rfc5019#section-4
-
-Result
-CreateEncodedOCSPRequest(TrustDomain& trustDomain, const struct CertID& certID,
-                         /*out*/ uint8_t (&out)[OCSP_REQUEST_MAX_LENGTH],
-                         /*out*/ size_t& outLen)
-{
-  // We do not add any extensions to the request.
-
-  // RFC 6960 says "An OCSP client MAY wish to specify the kinds of response
-  // types it understands. To do so, it SHOULD use an extension with the OID
-  // id-pkix-ocsp-response." This use of MAY and SHOULD is unclear. MSIE11
-  // on Windows 8.1 does not include any extensions, whereas NSS has always
-  // included the id-pkix-ocsp-response extension. Avoiding the sending the
-  // extension is better for OCSP GET because it makes the request smaller,
-  // and thus more likely to fit within the 255 byte limit for OCSP GET that
-  // is specified in RFC 5019 Section 5.
-
-  // Bug 966856: Add the id-pkix-ocsp-pref-sig-algs extension.
-
-  // Since we don't know whether the OCSP responder supports anything other
-  // than SHA-1, we have no choice but to use SHA-1 for issuerNameHash and
-  // issuerKeyHash.
-  static const uint8_t hashAlgorithm[11] = {
-    0x30, 0x09,                               // SEQUENCE
-    0x06, 0x05, 0x2B, 0x0E, 0x03, 0x02, 0x1A, //   OBJECT IDENTIFIER id-sha1
-    0x05, 0x00,                               //   NULL
-  };
-  static const uint8_t hashLen = 160 / 8;
-
-  static const unsigned int totalLenWithoutSerialNumberData
-    = 2                             // OCSPRequest
-    + 2                             //   tbsRequest
-    + 2                             //     requestList
-    + 2                             //       Request
-    + 2                             //         reqCert (CertID)
-    + sizeof(hashAlgorithm)         //           hashAlgorithm
-    + 2 + hashLen                   //           issuerNameHash
-    + 2 + hashLen                   //           issuerKeyHash
-    + 2;                            //           serialNumber (header)
-
-  // The only way we could have a request this large is if the serialNumber was
-  // ridiculously and unreasonably large. RFC 5280 says "Conforming CAs MUST
-  // NOT use serialNumber values longer than 20 octets." With this restriction,
-  // we allow for some amount of non-conformance with that requirement while
-  // still ensuring we can encode the length values in the ASN.1 TLV structures
-  // in a single byte.
-  static_assert(totalLenWithoutSerialNumberData < OCSP_REQUEST_MAX_LENGTH,
-                "totalLenWithoutSerialNumberData too big");
-  if (certID.serialNumber.GetLength() >
-        OCSP_REQUEST_MAX_LENGTH - totalLenWithoutSerialNumberData) {
-    return Result::ERROR_BAD_DER;
-  }
-
-  outLen = totalLenWithoutSerialNumberData + certID.serialNumber.GetLength();
-
-  uint8_t totalLen = static_cast<uint8_t>(outLen);
-
-  uint8_t* d = out;
-  *d++ = 0x30; *d++ = totalLen - 2u;  // OCSPRequest (SEQUENCE)
-  *d++ = 0x30; *d++ = totalLen - 4u;  //   tbsRequest (SEQUENCE)
-  *d++ = 0x30; *d++ = totalLen - 6u;  //     requestList (SEQUENCE OF)
-  *d++ = 0x30; *d++ = totalLen - 8u;  //       Request (SEQUENCE)
-  *d++ = 0x30; *d++ = totalLen - 10u; //         reqCert (CertID SEQUENCE)
-
-  // reqCert.hashAlgorithm
-  for (const uint8_t hashAlgorithmByte : hashAlgorithm) {
-    *d++ = hashAlgorithmByte;
-  }
-
-  // reqCert.issuerNameHash (OCTET STRING)
-  *d++ = 0x04;
-  *d++ = hashLen;
-  Result rv = trustDomain.DigestBuf(certID.issuer, DigestAlgorithm::sha1, d,
-                                    hashLen);
-  if (rv != Success) {
-    return rv;
-  }
-  d += hashLen;
-
-  // reqCert.issuerKeyHash (OCTET STRING)
-  *d++ = 0x04;
-  *d++ = hashLen;
-  rv = KeyHash(trustDomain, certID.issuerSubjectPublicKeyInfo, d, hashLen);
-  if (rv != Success) {
-    return rv;
-  }
-  d += hashLen;
-
-  // reqCert.serialNumber (INTEGER)
-  *d++ = 0x02; // INTEGER
-  *d++ = static_cast<uint8_t>(certID.serialNumber.GetLength());
-  Reader serialNumber(certID.serialNumber);
-  do {
-    rv = serialNumber.Read(*d);
-    if (rv != Success) {
-      return rv;
-    }
-    ++d;
-  } while (!serialNumber.AtEnd());
-
-  assert(d == out + totalLen);
-
-  return Success;
-}
-
-} } // namespace mozilla::pkix
deleted file mode 100644
--- a/security/pkix/lib/pkixresult.cpp
+++ /dev/null
@@ -1,46 +0,0 @@
-/*- *- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "pkix/Result.h"
-#include "pkixutil.h"
-
-namespace mozilla { namespace pkix {
-
-const char*
-MapResultToName(Result result)
-{
-  switch (result)
-  {
-#define MOZILLA_PKIX_MAP(mozilla_pkix_result, value, nss_result) \
-    case Result::mozilla_pkix_result: return "Result::" #mozilla_pkix_result;
-
-    MOZILLA_PKIX_MAP_LIST
-
-#undef MOZILLA_PKIX_MAP
-
-    MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-  }
-}
-
-} } // namespace mozilla::pkix
deleted file mode 100644
--- a/security/pkix/lib/pkixtime.cpp
+++ /dev/null
@@ -1,78 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2014 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "pkix/Time.h"
-#include "pkixutil.h"
-
-#ifdef WIN32
-#ifdef _MSC_VER
-#pragma warning(push, 3)
-#endif
-#include "windows.h"
-#ifdef _MSC_VER
-#pragma warning(pop)
-#endif
-#else
-#include "sys/time.h"
-#endif
-
-namespace mozilla { namespace pkix {
-
-Time
-Now()
-{
-  uint64_t seconds;
-
-#ifdef WIN32
-  // "Contains a 64-bit value representing the number of 100-nanosecond
-  // intervals since January 1, 1601 (UTC)."
-  //   - http://msdn.microsoft.com/en-us/library/windows/desktop/ms724284(v=vs.85).aspx
-  FILETIME ft;
-  GetSystemTimeAsFileTime(&ft);
-  uint64_t ft64 = (static_cast<uint64_t>(ft.dwHighDateTime) << 32) |
-                  ft.dwLowDateTime;
-  seconds = (DaysBeforeYear(1601) * Time::ONE_DAY_IN_SECONDS) +
-            ft64 / (1000u * 1000u * 1000u / 100u);
-#else
-  // "The gettimeofday() function shall obtain the current time, expressed as
-  // seconds and microseconds since the Epoch."
-  //   - http://pubs.opengroup.org/onlinepubs/009695399/functions/gettimeofday.html
-  timeval tv;
-  (void) gettimeofday(&tv, nullptr);
-  seconds = (DaysBeforeYear(1970) * Time::ONE_DAY_IN_SECONDS) +
-            static_cast<uint64_t>(tv.tv_sec);
-#endif
-
-  return TimeFromElapsedSecondsAD(seconds);
-}
-
-Time
-TimeFromEpochInSeconds(uint64_t secondsSinceEpoch)
-{
-  uint64_t seconds = (DaysBeforeYear(1970) * Time::ONE_DAY_IN_SECONDS) +
-                     secondsSinceEpoch;
-  return TimeFromElapsedSecondsAD(seconds);
-}
-
-} } // namespace mozilla::pkix
deleted file mode 100644
--- a/security/pkix/lib/pkixutil.h
+++ /dev/null
@@ -1,291 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef mozilla_pkix_pkixutil_h
-#define mozilla_pkix_pkixutil_h
-
-#include "pkixder.h"
-
-namespace mozilla { namespace pkix {
-
-// During path building and verification, we build a linked list of BackCerts
-// from the current cert toward the end-entity certificate. The linked list
-// is used to verify properties that aren't local to the current certificate
-// and/or the direct link between the current certificate and its issuer,
-// such as name constraints.
-//
-// Each BackCert contains pointers to all the given certificate's extensions
-// so that we can parse the extension block once and then process the
-// extensions in an order that may be different than they appear in the cert.
-class BackCert final
-{
-public:
-  // certDER and childCert must be valid for the lifetime of BackCert.
-  BackCert(Input aCertDER,
-           EndEntityOrCA aEndEntityOrCA,
-           const BackCert* aChildCert)
-    : der(aCertDER)
-    , endEntityOrCA(aEndEntityOrCA)
-    , childCert(aChildCert)
-    , version(der::Version::Uninitialized)
-  {
-  }
-
-  Result Init();
-
-  const Input GetDER() const { return der; }
-  const der::SignedDataWithSignature& GetSignedData() const {
-    return signedData;
-  }
-
-  der::Version GetVersion() const { return version; }
-  const Input GetSerialNumber() const { return serialNumber; }
-  const Input GetSignature() const { return signature; }
-  const Input GetIssuer() const { return issuer; }
-  // XXX: "validity" is a horrible name for the structure that holds
-  // notBefore & notAfter, but that is the name used in RFC 5280 and we use the
-  // RFC 5280 names for everything.
-  const Input GetValidity() const { return validity; }
-  const Input GetSubject() const { return subject; }
-  const Input GetSubjectPublicKeyInfo() const
-  {
-    return subjectPublicKeyInfo;
-  }
-  const Input* GetAuthorityInfoAccess() const
-  {
-    return MaybeInput(authorityInfoAccess);
-  }
-  const Input* GetBasicConstraints() const
-  {
-    return MaybeInput(basicConstraints);
-  }
-  const Input* GetCertificatePolicies() const
-  {
-    return MaybeInput(certificatePolicies);
-  }
-  const Input* GetExtKeyUsage() const
-  {
-    return MaybeInput(extKeyUsage);
-  }
-  const Input* GetKeyUsage() const
-  {
-    return MaybeInput(keyUsage);
-  }
-  const Input* GetInhibitAnyPolicy() const
-  {
-    return MaybeInput(inhibitAnyPolicy);
-  }
-  const Input* GetNameConstraints() const
-  {
-    return MaybeInput(nameConstraints);
-  }
-  const Input* GetSubjectAltName() const
-  {
-    return MaybeInput(subjectAltName);
-  }
-  const Input* GetRequiredTLSFeatures() const
-  {
-    return MaybeInput(requiredTLSFeatures);
-  }
-  const Input* GetSignedCertificateTimestamps() const
-  {
-    return MaybeInput(signedCertificateTimestamps);
-  }
-
-private:
-  const Input der;
-
-public:
-  const EndEntityOrCA endEntityOrCA;
-  BackCert const* const childCert;
-
-private:
-  // When parsing certificates in BackCert::Init, we don't accept empty
-  // extensions. Consequently, we don't have to store a distinction between
-  // empty extensions and extensions that weren't included. However, when
-  // *processing* extensions, we distinguish between whether an extension was
-  // included or not based on whetehr the GetXXX function for the extension
-  // returns nullptr.
-  static inline const Input* MaybeInput(const Input& item)
-  {
-    return item.GetLength() > 0 ? &item : nullptr;
-  }
-
-  der::SignedDataWithSignature signedData;
-
-  der::Version version;
-  Input serialNumber;
-  Input signature;
-  Input issuer;
-  // XXX: "validity" is a horrible name for the structure that holds
-  // notBefore & notAfter, but that is the name used in RFC 5280 and we use the
-  // RFC 5280 names for everything.
-  Input validity;
-  Input subject;
-  Input subjectPublicKeyInfo;
-
-  Input authorityInfoAccess;
-  Input basicConstraints;
-  Input certificatePolicies;
-  Input extKeyUsage;
-  Input inhibitAnyPolicy;
-  Input keyUsage;
-  Input nameConstraints;
-  Input subjectAltName;
-  Input criticalNetscapeCertificateType;
-  Input requiredTLSFeatures;
-  Input signedCertificateTimestamps; // RFC 6962 (Certificate Transparency)
-
-  Result RememberExtension(Reader& extnID, Input extnValue, bool critical,
-                           /*out*/ bool& understood);
-
-  BackCert(const BackCert&) = delete;
-  void operator=(const BackCert&) = delete;
-};
-
-class NonOwningDERArray final : public DERArray
-{
-public:
-  NonOwningDERArray()
-    : numItems(0)
-  {
-    // we don't need to initialize the items array because we always check
-    // numItems before accessing i.
-  }
-
-  size_t GetLength() const override { return numItems; }
-
-  const Input* GetDER(size_t i) const override
-  {
-    return i < numItems ? &items[i] : nullptr;
-  }
-
-  Result Append(Input der)
-  {
-    if (numItems >= MAX_LENGTH) {
-      return Result::FATAL_ERROR_INVALID_ARGS;
-    }
-    Result rv = items[numItems].Init(der); // structure assignment
-    if (rv != Success) {
-      return rv;
-    }
-    ++numItems;
-    return Success;
-  }
-
-  // Public so we can static_assert on this. Keep in sync with MAX_SUBCA_COUNT.
-  static const size_t MAX_LENGTH = 8;
-private:
-  Input items[MAX_LENGTH]; // avoids any heap allocations
-  size_t numItems;
-
-  NonOwningDERArray(const NonOwningDERArray&) = delete;
-  void operator=(const NonOwningDERArray&) = delete;
-};
-
-// Extracts the SignedCertificateTimestampList structure which is encoded as an
-// OCTET STRING within the X.509v3 / OCSP extensions (see RFC 6962 section 3.3).
-Result
-ExtractSignedCertificateTimestampListFromExtension(Input extnValue,
-                                                   Input& sctList);
-
-inline unsigned int
-DaysBeforeYear(unsigned int year)
-{
-  assert(year <= 9999);
-  return ((year - 1u) * 365u)
-       + ((year - 1u) / 4u)    // leap years are every 4 years,
-       - ((year - 1u) / 100u)  // except years divisible by 100,
-       + ((year - 1u) / 400u); // except years divisible by 400.
-}
-
-static const size_t MAX_DIGEST_SIZE_IN_BYTES = 512 / 8; // sha-512
-
-Result DigestSignedData(TrustDomain& trustDomain,
-                        const der::SignedDataWithSignature& signedData,
-                        /*out*/ uint8_t(&digestBuf)[MAX_DIGEST_SIZE_IN_BYTES],
-                        /*out*/ der::PublicKeyAlgorithm& publicKeyAlg,
-                        /*out*/ SignedDigest& signedDigest);
-
-Result VerifySignedDigest(TrustDomain& trustDomain,
-                          der::PublicKeyAlgorithm publicKeyAlg,
-                          const SignedDigest& signedDigest,
-                          Input signerSubjectPublicKeyInfo);
-
-// Combines DigestSignedData and VerifySignedDigest
-Result VerifySignedData(TrustDomain& trustDomain,
-                        const der::SignedDataWithSignature& signedData,
-                        Input signerSubjectPublicKeyInfo);
-
-// Extracts the key parameters from |subjectPublicKeyInfo|, invoking
-// the relevant methods of |trustDomain|.
-Result
-CheckSubjectPublicKeyInfo(Input subjectPublicKeyInfo, TrustDomain& trustDomain,
-                          EndEntityOrCA endEntityOrCA);
-
-// In a switch over an enum, sometimes some compilers are not satisfied that
-// all control flow paths have been considered unless there is a default case.
-// However, in our code, such a default case is almost always unreachable dead
-// code. That can be particularly problematic when the compiler wants the code
-// to choose a value, such as a return value, for the default case, but there's
-// no appropriate "impossible case" value to choose.
-//
-// MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM accounts for this. Example:
-//
-//     // In xy.cpp
-//     #include "xt.h"
-//
-//     enum class XY { X, Y };
-//
-//     int func(XY xy) {
-//       switch (xy) {
-//         case XY::X: return 1;
-//         case XY::Y; return 2;
-//         MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-//       }
-//     }
-#if defined(__clang__)
-// Clang will warn if not all cases are covered (-Wswitch-enum) AND it will
-// warn if a switch statement that covers every enum label has a default case
-// (-W-covered-switch-default). Versions prior to 3.5 warned about unreachable
-// code in such default cases (-Wunreachable-code) even when
-// -W-covered-switch-default was disabled, but that changed in Clang 3.5.
-#define MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM // empty
-#elif defined(__GNUC__)
-// GCC will warn if not all cases are covered (-Wswitch-enum). It does not
-// assume that the default case is unreachable.
-#define MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM \
-        default: assert(false); __builtin_unreachable();
-#elif defined(_MSC_VER)
-// MSVC will warn if not all cases are covered (C4061, level 4). It does not
-// assume that the default case is unreachable.
-#define MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM \
-        default: assert(false); __assume(0);
-#else
-#error Unsupported compiler for MOZILLA_PKIX_UNREACHABLE_DEFAULT.
-#endif
-
-} } // namespace mozilla::pkix
-
-#endif // mozilla_pkix_pkixutil_h
deleted file mode 100644
--- a/security/pkix/lib/pkixverify.cpp
+++ /dev/null
@@ -1,106 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2015 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "pkixutil.h"
-
-namespace mozilla { namespace pkix {
-
-Result
-DigestSignedData(TrustDomain& trustDomain,
-                 const der::SignedDataWithSignature& signedData,
-                 /*out*/ uint8_t(&digestBuf)[MAX_DIGEST_SIZE_IN_BYTES],
-                 /*out*/ der::PublicKeyAlgorithm& publicKeyAlg,
-                 /*out*/ SignedDigest& signedDigest)
-{
-  Reader signatureAlg(signedData.algorithm);
-  Result rv = der::SignatureAlgorithmIdentifierValue(
-                signatureAlg, publicKeyAlg, signedDigest.digestAlgorithm);
-  if (rv != Success) {
-    return rv;
-  }
-  if (!signatureAlg.AtEnd()) {
-    return Result::ERROR_BAD_DER;
-  }
-
-  size_t digestLen;
-  switch (signedDigest.digestAlgorithm) {
-    case DigestAlgorithm::sha512: digestLen = 512 / 8; break;
-    case DigestAlgorithm::sha384: digestLen = 384 / 8; break;
-    case DigestAlgorithm::sha256: digestLen = 256 / 8; break;
-    case DigestAlgorithm::sha1: digestLen = 160 / 8; break;
-    MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-  }
-  assert(digestLen <= sizeof(digestBuf));
-
-  rv = trustDomain.DigestBuf(signedData.data, signedDigest.digestAlgorithm,
-                             digestBuf, digestLen);
-  if (rv != Success) {
-    return rv;
-  }
-  rv = signedDigest.digest.Init(digestBuf, digestLen);
-  if (rv != Success) {
-    return rv;
-  }
-
-  return signedDigest.signature.Init(signedData.signature);
-}
-
-Result
-VerifySignedDigest(TrustDomain& trustDomain,
-                   der::PublicKeyAlgorithm publicKeyAlg,
-                   const SignedDigest& signedDigest,
-                   Input signerSubjectPublicKeyInfo)
-{
-  switch (publicKeyAlg) {
-    case der::PublicKeyAlgorithm::ECDSA:
-      return trustDomain.VerifyECDSASignedDigest(signedDigest,
-                                                 signerSubjectPublicKeyInfo);
-    case der::PublicKeyAlgorithm::RSA_PKCS1:
-      return trustDomain.VerifyRSAPKCS1SignedDigest(signedDigest,
-                                                    signerSubjectPublicKeyInfo);
-    case der::PublicKeyAlgorithm::Uninitialized:
-      assert(false);
-      return Result::FATAL_ERROR_LIBRARY_FAILURE;
-    MOZILLA_PKIX_UNREACHABLE_DEFAULT_ENUM
-  }
-}
-
-Result
-VerifySignedData(TrustDomain& trustDomain,
-                 const der::SignedDataWithSignature& signedData,
-                 Input signerSubjectPublicKeyInfo)
-{
-  uint8_t digestBuf[MAX_DIGEST_SIZE_IN_BYTES];
-  der::PublicKeyAlgorithm publicKeyAlg;
-  SignedDigest signedDigest;
-  Result rv = DigestSignedData(trustDomain, signedData, digestBuf,
-                               publicKeyAlg, signedDigest);
-  if (rv != Success) {
-    return rv;
-  }
-  return VerifySignedDigest(trustDomain, publicKeyAlg, signedDigest,
-                            signerSubjectPublicKeyInfo);
-}
-
-} } // namespace mozilla::pkix
deleted file mode 100644
--- a/security/pkix/moz.build
+++ /dev/null
@@ -1,36 +0,0 @@
-# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
-# vim: set filetype=python:
-# This Source Code Form is subject to the terms of the Mozilla Public
-# License, v. 2.0. If a copy of the MPL was not distributed with this
-# file, You can obtain one at http://mozilla.org/MPL/2.0/.
-
-with Files("**"):
-    BUG_COMPONENT = ("Core", "Security: PSM")
-
-SOURCES += [
-    'lib/pkixbuild.cpp',
-    'lib/pkixcert.cpp',
-    'lib/pkixcheck.cpp',
-    'lib/pkixder.cpp',
-    'lib/pkixnames.cpp',
-    'lib/pkixnss.cpp',
-    'lib/pkixocsp.cpp',
-    'lib/pkixresult.cpp',
-    'lib/pkixtime.cpp',
-    'lib/pkixverify.cpp',
-]
-
-LOCAL_INCLUDES += [
-    'include',
-]
-
-TEST_DIRS += [
-    'test/gtest',
-    'test/lib',
-]
-
-include('warnings.mozbuild')
-
-Library('mozillapkix')
-
-FINAL_LIBRARY = 'xul'
deleted file mode 100644
--- a/security/pkix/test/gtest/README.txt
+++ /dev/null
@@ -1,61 +0,0 @@
--------------
-Running Tests
--------------
-
-Because of the rules below, you can run all the unit tests in this directory,
-and only these tests, with:
-
-  mach gtest "pkix*"
-
-You can run just the tests for functions defined in filename pkixfoo.cpp with:
-
-  mach gtest "pkixfoo*"
-
-If you run "mach gtest" then you'll end up running every gtest in Gecko.
-
-
-
-------------
-Naming Files
-------------
-
-Name files containing tests according to one of the following patterns:
-
-  * <filename>_tests.cpp
-  * <filename>_<Function>_tests.cpp
-  * <filename>_<category>_tests.cpp
-
-  <filename> is the name of the file containing the definitions of the
-             function(s) being tested by every test.
-  <Function> is the name of the function that is being tested by every
-             test.
-  <category> describes the group of related functions that are being
-             tested by every test.
-
-
-
-------------------------------------------------
-Always Use a Fixture Class: TEST_F(), not TEST()
-------------------------------------------------
-
-Many tests don't technically need a fixture, and so TEST() could technically
-be used to define the test. However, when you use TEST_F() instead of TEST(),
-the compiler will not allow you to make any typos in the test case name, but
-if you use TEST() then the name of the test case is not checked.
-
-See https://code.google.com/p/googletest/wiki/Primer#Test_Fixtures:_Using_the_Same_Data_Configuration_for_Multiple_Te
-to learn more about test fixtures.
-
----------------
-Naming Fixtures
----------------
-
-When all tests in a file use the same fixture, use the base name of the file
-without the "_tests" suffix as the name of the fixture class; e.g. tests in
-"pkixocsp.cpp" should use a fixture "class pkixocsp" by default.
-
-Sometimes tests in a file need separate fixtures. In this case, name the
-fixture class according to the pattern <fixture_base>_<fixture_suffix>, where
-<fixture_base> is the base name of the file without the "_tests" suffix, and
-<fixture_suffix> is a descriptive name for the fixture class, e.g.
-"class pkixocsp_DelegatedResponder".
deleted file mode 100644
--- a/security/pkix/test/gtest/moz.build
+++ /dev/null
@@ -1,81 +0,0 @@
-# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
-# vim: set filetype=python:
-# This Source Code Form is subject to the terms of the Mozilla Public
-# License, v. 2.0. If a copy of the MPL was not distributed with this
-# file, You can obtain one at http://mozilla.org/MPL/2.0/.
-
-SOURCES += [
-    'pkixbuild_tests.cpp',
-    'pkixcert_extension_tests.cpp',
-    'pkixcert_signature_algorithm_tests.cpp',
-    'pkixcheck_CheckExtendedKeyUsage_tests.cpp',
-    'pkixcheck_CheckIssuer_tests.cpp',
-    'pkixcheck_CheckKeyUsage_tests.cpp',
-    'pkixcheck_CheckSignatureAlgorithm_tests.cpp',
-    'pkixcheck_CheckValidity_tests.cpp',
-    'pkixcheck_ParseValidity_tests.cpp',
-    'pkixcheck_TLSFeaturesSatisfiedInternal_tests.cpp',
-
-    # The naming conventions are described in ./README.txt.
-
-    'pkixder_input_tests.cpp',
-    'pkixder_pki_types_tests.cpp',
-    'pkixder_universal_types_tests.cpp',
-    'pkixgtest.cpp',
-    'pkixnames_tests.cpp',
-    'pkixocsp_CreateEncodedOCSPRequest_tests.cpp',
-    'pkixocsp_VerifyEncodedOCSPResponse.cpp',
-]
-
-LOCAL_INCLUDES += [
-    '../../include',
-    '../../lib',
-    '../lib',
-]
-
-FINAL_LIBRARY = 'xul-gtest'
-
-include('../../warnings.mozbuild')
-
-# GTest uses a variadic macro in a questionable way and it doesn't seem to be
-# possible to selectively disable just that error when -pedantic-errors is set.
-if CONFIG['CC_TYPE'] == 'gcc':
-  CXXFLAGS.remove('-pedantic-errors')
-
-# These warnings are disabled in order to minimize the amount of boilerplate
-# required to implement tests, and/or because they originate in the GTest
-# framework in a way we cannot otherwise work around.
-if CONFIG['CC_TYPE'] in ('clang', 'clang-cl', 'gcc'):
-  CXXFLAGS += [
-    '-Wno-old-style-cast',
-  ]
-  if CONFIG['CC_TYPE'] in ('clang', 'clang-cl'):
-    CXXFLAGS += [
-      '-Wno-exit-time-destructors',
-      '-Wno-global-constructors',
-      '-Wno-thread-safety',
-      '-Wno-used-but-marked-unused',
-      '-Wno-zero-as-null-pointer-constant',
-    ]
-elif CONFIG['CC_TYPE'] == 'msvc':
-  CXXFLAGS += [
-    '-wd4350', # behavior change: 'std::_Wrap_alloc<std::allocator<_Ty>>::...
-    '-wd4275', # non dll-interface class used as base for dll-interface class
-    '-wd4548', # Expression before comma has no effect
-    '-wd4625', # copy constructor could not be generated.
-    '-wd4626', # assugment operator could not be generated.
-    '-wd4640', # construction of local static object is not thread safe.
-
-    # This is intended as a temporary hack to support building with VS2015.
-    # declaration of '*' hides class member
-    '-wd4458',
-  ]
-  # Disable Spectre diagnostics only if optimization is disabled.
-  if not CONFIG['MOZ_OPTIMIZE']:
-    CXXFLAGS += [
-      '-wd5045', # Compiler will insert Spectre mitigation for memory load if
-                 # /Qspectre switch specified
-    ]
-
-if CONFIG['CC_TYPE'] == 'clang-cl':
-    AllowCompilerWarnings()  # workaround for bug 1090497
deleted file mode 100644
--- a/security/pkix/test/gtest/pkixbuild_tests.cpp
+++ /dev/null
@@ -1,893 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* This code is made available to you under your choice of the following sets
- * of licensing terms:
- */
-/* This Source Code Form is subject to the terms of the Mozilla Public
- * License, v. 2.0. If a copy of the MPL was not distributed with this
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
- */
-/* Copyright 2013 Mozilla Contributors
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#if defined(_MSC_VER) && _MSC_VER < 1900
-// When building with -D_HAS_EXCEPTIONS=0, MSVC's <xtree> header triggers
-// warning C4702: unreachable code.
-// https://connect.microsoft.com/VisualStudio/feedback/details/809962
-#pragma warning(push)
-#pragma warning(disable: 4702)
-#endif
-
-#include <map>
-#include <vector>
-
-#if defined(_MSC_VER) && _MSC_VER < 1900
-#pragma warning(pop)
-#endif
-
-#include "pkixder.h"
-#include "pkixgtest.h"
-
-using namespace mozilla::pkix;
-using namespace mozilla::pkix::test;
-
-static ByteString
-CreateCert(const char* issuerCN, // null means "empty name"
-           const char* subjectCN, // null means "empty name"
-           EndEntityOrCA endEntityOrCA,
-           /*optional modified*/ std::map<ByteString, ByteString>*
-             subjectDERToCertDER = nullptr,
-           /*optional*/ const ByteString* extension = nullptr,
-           /*optional*/ const TestKeyPair* issuerKeyPair = nullptr,
-           /*optional*/ const TestKeyPair* subjectKeyPair = nullptr)
-{
-  static long serialNumberValue = 0;
-  ++serialNumberValue;
-  ByteString serialNumber(CreateEncodedSerialNumber(serialNumberValue));
-  EXPECT_FALSE(ENCODING_FAILED(serialNumber));
-
-  ByteString issuerDER(issuerCN ? CNToDERName(issuerCN) : Name(ByteString()));
-  ByteString subjectDER(subjectCN ? CNToDERName(subjectCN) : Name(ByteString()));
-
-  std::vector<ByteString> extensions;
-  if (endEntityOrCA == EndEntityOrCA::MustBeCA) {
-    ByteString basicConstraints =
-      CreateEncodedBasicConstraints(true, nullptr, Critical::Yes);
-    EXPECT_FALSE(ENCODING_FAILED(basicConstraints));
-    extensions.push_back(basicConstraints);
-  }
-  if (extension) {
-    extensions.push_back(*extension);
-  }
-  extensions.push_back(ByteString()); // marks the end of the list
-
-  ScopedTestKeyPair reusedKey(CloneReusedKeyPair());
-  ByteString certDER(CreateEncodedCertificate(
-                       v3, sha256WithRSAEncryption(), serialNumber, issuerDER,
-                       oneDayBeforeNow, oneDayAfterNow, subjectDER,
-                       subjectKeyPair ? *subjectKeyPair : *reusedKey,
-                       extensions.data(),
-                       issuerKeyPair ? *issuerKeyPair : *reusedKey,
-                       sha256WithRSAEncryption()));
-  EXPECT_FALSE(ENCODING_FAILED(certDER));
-
-  if (subjectDERToCertDER) {
-    (*subjectDERToCertDER)[subjectDER] = certDER;
-  }
-
-  return certDER;
-}
-
-class TestTrustDomain final : public DefaultCryptoTrustDomain
-{
-public:
-  // The "cert chain tail" is a longish chain of certificates that is used by
-  // all of the tests here. We share this chain across all the tests in order
-  // to speed up the tests (generating keypairs for the certs is very slow).
-  bool SetUpCertChainTail()
-  {
-    static char const* const names[] = {
-        "CA1 (Root)", "CA2", "CA3", "CA4", "CA5", "CA6", "CA7"
-    };
-
-    for (size_t i = 0; i < MOZILLA_PKIX_ARRAY_LENGTH(names); ++i) {
-      const char* issuerName = i == 0 ? names[0] : names[i-1];
-      CreateCACert(issuerName, names[i]);
-      if (i == 0) {
-        rootCACertDER = leafCACertDER;
-      }
-    }
-
-    return true;
-  }
-
-  void CreateCACert(const char* issuerName, const char* subjectName)
-  {
-    leafCACertDER = CreateCert(issuerName, subjectName,
-                               EndEntityOrCA::MustBeCA, &subjectDERToCertDER);
-    assert(!ENCODING_FAILED(leafCACertDER));
-  }
-
-  ByteString GetLeafCACertDER() const { return leafCACertDER; }
-
-private:
-  Result GetCertTrust(EndEntityOrCA, const CertPolicyId&, Input candidateCert,
-                      /*out*/ TrustLevel& trustLevel) override
-  {
-    trustLevel = InputEqualsByteString(candidateCert, rootCACertDER)
-               ? TrustLevel::TrustAnchor
-               : TrustLevel::InheritsTrust;
-    return Success;
-  }
-
-  Result FindIssuer(Input encodedIssuerName, IssuerChecker& checker, Time)
-                    override
-  {
-    ByteString subjectDER(InputToByteString(encodedIssuerName));
-    ByteString certDER(subjectDERToCertDER[subjectDER]);
-    Input derCert;
-    Result rv = derCert.Init(certDER.data(), certDER.length());
-    if (rv != Success) {
-      return rv;
-    }
-    bool keepGoing;
-    rv = checker.Check(derCert, nullptr/*additionalNameConstraints*/,
-                       keepGoing);
-    if (rv != Success) {
-      return rv;
-    }
-    return Success;
-  }
-
-  Result CheckRevocation(EndEntityOrCA, const CertID&, Time, Duration,
-                         /*optional*/ const Input*, /*optional*/ const Input*)
-                         override
-  {
-    return Success;
-  }
-
-  Result IsChainValid(const DERArray&, Time, const CertPolicyId&) override
-  {
-    return Success;
-  }
-
-  std::map<ByteString, ByteString> subjectDERToCertDER;
-  ByteString leafCACertDER;
-  ByteString rootCACertDER;
-};
-
-class pkixbuild : public ::testing::Test
-{
-public:
-  static void SetUpTestCase()
-  {
-    if (!trustDomain.SetUpCertChainTail()) {
-      abort();
-    }
-  }
-
-protected:
-
-  static TestTrustDomain trustDomain;
-};
-
-/*static*/ TestTrustDomain pkixbuild::trustDomain;
-
-TEST_F(pkixbuild, MaxAcceptableCertChainLength)
-{
-  {
-    ByteString leafCACert(trustDomain.GetLeafCACertDER());
-    Input certDER;
-    ASSERT_EQ(Success, certDER.Init(leafCACert.data(), leafCACert.length()));
-    ASSERT_EQ(Success,
-              BuildCertChain(trustDomain, certDER, Now(),
-                             EndEntityOrCA::MustBeCA,
-                             KeyUsage::noParticularKeyUsageRequired,
-                             KeyPurposeId::id_kp_serverAuth,
-                             CertPolicyId::anyPolicy,
-                             nullptr/*stapledOCSPResponse*/));
-  }
-
-  {
-    ByteString certDER(CreateCert("CA7", "Direct End-Entity",
-                                  EndEntityOrCA::MustBeEndEntity));
-    ASSERT_FALSE(ENCODING_FAILED(certDER));
-    Input certDERInput;
-    ASSERT_EQ(Success, certDERInput.Init(certDER.data(), certDER.length()));
-    ASSERT_EQ(Success,
-              BuildCertChain(trustDomain, certDERInput, Now(),
-                             EndEntityOrCA::MustBeEndEntity,
-                             KeyUsage::noParticularKeyUsageRequired,
-                             KeyPurposeId::id_kp_serverAuth,
-                             CertPolicyId::anyPolicy,
-                             nullptr/*stapledOCSPResponse*/));
-  }
-}
-
-TEST_F(pkixbuild, BeyondMaxAcceptableCertChainLength)
-{
-  static char const* const caCertName = "CA Too Far";
-
-  trustDomain.CreateCACert("CA7", caCertName);
-
-  {
-    ByteString certDER(trustDomain.GetLeafCACertDER());
-    Input certDERInput;
-    ASSERT_EQ(Success, certDERInput.Init(certDER.data(), certDER.length()));
-    ASSERT_EQ(Result::ERROR_UNKNOWN_ISSUER,
-              BuildCertChain(trustDomain, certDERInput, Now(),
-                             EndEntityOrCA::MustBeCA,
-                             KeyUsage::noParticularKeyUsageRequired,
-                             KeyPurposeId::id_kp_serverAuth,
-                             CertPolicyId::anyPolicy,
-                             nullptr/*stapledOCSPResponse*/));
-  }
-
-  {
-    ByteString certDER(CreateCert(caCertName, "End-Entity Too Far",
-                                  EndEntityOrCA::MustBeEndEntity));
-    ASSERT_FALSE(ENCODING_FAILED(certDER));
-    Input certDERInput;
-    ASSERT_EQ(Success, certDERInput.Init(certDER.data(), certDER.length()));
-    ASSERT_EQ(Result::ERROR_UNKNOWN_ISSUER,
-              BuildCertChain(trustDomain, certDERInput, Now(),
-                             EndEntityOrCA::MustBeEndEntity,
-                             KeyUsage::noParticularKeyUsageRequired,
-                             KeyPurposeId::id_kp_serverAuth,
-                             CertPolicyId::anyPolicy,
-                             nullptr/*stapledOCSPResponse*/));
-  }
-}
-
-// A TrustDomain that checks certificates against a given root certificate.
-// It is initialized with the DER encoding of a root certificate that
-// is treated as a trust anchor and is assumed to have issued all certificates
-// (i.e. FindIssuer always attempts to build the next step in the chain with
-// it).
-class SingleRootTrustDomain : public DefaultCryptoTrustDomain
-{
-public:
-  explicit SingleRootTrustDomain(ByteString aRootDER)
-    : rootDER(aRootDER)
-  {
-  }
-
-  // The CertPolicyId argument is unused because we don't care about EV.
-  Result GetCertTrust(EndEntityOrCA, const CertPolicyId&, Input candidateCert,
-                      /*out*/ TrustLevel& trustLevel) override
-  {
-    Input rootCert;
-    Result rv = rootCert.Init(rootDER.data(), rootDER.length());
-    if (rv != Success) {
-      return rv;
-    }
-    if (InputsAreEqual(candidateCert, rootCert)) {
-      trustLevel = TrustLevel::TrustAnchor;
-    } else {
-      trustLevel = TrustLevel::InheritsTrust;
-    }
-    return Success;
-  }
-
-  Result FindIssuer(Input, IssuerChecker& checker, Time) override
-  {
-    // keepGoing is an out parameter from IssuerChecker.Check. It would tell us
-    // whether or not to continue attempting other potential issuers. We only
-    // know of one potential issuer, however, so we ignore it.
-    bool keepGoing;
-    Input rootCert;
-    Result rv = rootCert.Init(rootDER.data(), rootDER.length());
-    if (rv != Success) {
-      return rv;
-    }
-    return checker.Check(rootCert, nullptr, keepGoing);
-  }
-
-  Result IsChainValid(const DERArray&, Time, const CertPolicyId&) override
-  {
-    return Success;
-  }
-
-  Result CheckRevocation(EndEntityOrCA, const CertID&, Time, Duration,
-                         /*optional*/ const Input*, /*optional*/ const Input*)
-                         override
-  {
-    return Success;
-  }
-
-private:
-  ByteString rootDER;
-};
-
-// A TrustDomain that explicitly fails if CheckRevocation is called.
-class ExpiredCertTrustDomain final : public SingleRootTrustDomain
-{
-public:
-  explicit ExpiredCertTrustDomain(ByteString aRootDER)
-    : SingleRootTrustDomain(aRootDER)
-  {
-  }
-
-  Result CheckRevocation(EndEntityOrCA, const CertID&, Time, Duration,
-                         /*optional*/ const Input*, /*optional*/ const Input*)
-                         override
-  {
-    ADD_FAILURE();
-    return NotReached("CheckRevocation should not be called",
-                      Result::FATAL_ERROR_LIBRARY_FAILURE);
-  }
-};
-
-TEST_F(pkixbuild, NoRevocationCheckingForExpiredCert)
-{
-  const char* rootCN = "Root CA";
-  ByteString rootDER(CreateCert(rootCN, rootCN, EndEntityOrCA::MustBeCA,
-                                nullptr));
-  EXPECT_FALSE(ENCODING_FAILED(rootDER));
-  ExpiredCertTrustDomain expiredCertTrustDomain(rootDER);
-
-  ByteString serialNumber(CreateEncodedSerialNumber(100));
-  EXPECT_FALSE(ENCODING_FAILED(serialNumber));
-  ByteString issuerDER(CNToDERName(rootCN));
-  ByteString subjectDER(CNToDERName("Expired End-Entity Cert"));
-  ScopedTestKeyPair reusedKey(CloneReusedKeyPair());
-  ByteString certDER(CreateEncodedCertificate(
-                       v3, sha256WithRSAEncryption(),
-                       serialNumber, issuerDER,
-                       twoDaysBeforeNow,
-                       oneDayBeforeNow,
-                       subjectDER, *reusedKey, nullptr, *reusedKey,
-                       sha256WithRSAEncryption()));
-  EXPECT_FALSE(ENCODING_FAILED(certDER));
-
-  Input cert;
-  ASSERT_EQ(Success, cert.Init(certDER.data(), certDER.length()));
-  ASSERT_EQ(Result::ERROR_EXPIRED_CERTIFICATE,
-            BuildCertChain(expiredCertTrustDomain, cert, Now(),
-                           EndEntityOrCA::MustBeEndEntity,
-                           KeyUsage::noParticularKeyUsageRequired,
-                           KeyPurposeId::id_kp_serverAuth,
-                           CertPolicyId::anyPolicy,
-                           nullptr));
-}
-
-class DSSTrustDomain final : public EverythingFailsByDefaultTrustDomain
-{
-public:
-  Result GetCertTrust(EndEntityOrCA, const CertPolicyId&,
-                      Input, /*out*/ TrustLevel& trustLevel) override
-  {
-    trustLevel = TrustLevel::TrustAnchor;
-    return Success;
-  }
-};
-
-class pkixbuild_DSS : public ::testing::Test { };
-
-TEST_F(pkixbuild_DSS, DSSEndEntityKeyNotAccepted)
-{
-  DSSTrustDomain trustDomain;
-
-  ByteString serialNumber(CreateEncodedSerialNumber(1));
-  ASSERT_FALSE(ENCODING_FAILED(serialNumber));
-
-  ByteString subjectDER(CNToDERName("DSS"));
-  ASSERT_FALSE(ENCODING_FAILED(subjectDER));
-  ScopedTestKeyPair subjectKey(GenerateDSSKeyPair());
-  ASSERT_TRUE(subjectKey.get());
-
-  ByteString issuerDER(CNToDERName("RSA"));
-  ASSERT_FALSE(ENCODING_FAILED(issuerDER));
-  ScopedTestKeyPair issuerKey(CloneReusedKeyPair());
-  ASSERT_TRUE(issuerKey.get());
-
-  ByteString cert(CreateEncodedCertificate(v3, sha256WithRSAEncryption(),
-                                           serialNumber, issuerDER,
-                                           oneDayBeforeNow, oneDayAfterNow,
-                                           subjectDER, *subjectKey, nullptr,
-                                           *issuerKey, sha256WithRSAEncryption()));
-  ASSERT_FALSE(ENCODING_FAILED(cert));
-  Input certDER;
-  ASSERT_EQ(Success, certDER.Init(cert.data(), cert.length()));
-
-  ASSERT_EQ(Result::ERROR_UNSUPPORTED_KEYALG,
-            BuildCertChain(trustDomain, certDER, Now(),
-                           EndEntityOrCA::MustBeEndEntity,
-                           KeyUsage::noParticularKeyUsageRequired,
-                           KeyPurposeId::id_kp_serverAuth,
-                           CertPolicyId::anyPolicy,
-                           nullptr/*stapledOCSPResponse*/));
-}
-
-class IssuerNameCheckTrustDomain final : public DefaultCryptoTrustDomain
-{
-public:
-  IssuerNameCheckTrustDomain(const ByteString& aIssuer, bool aExpectedKeepGoing)
-    : issuer(aIssuer)
-    , expectedKeepGoing(aExpectedKeepGoing)
-  {
-  }
-
-  Result GetCertTrust(EndEntityOrCA endEntityOrCA, const CertPolicyId&, Input,
-                      /*out*/ TrustLevel& trustLevel) override
-  {
-    trustLevel = endEntityOrCA == EndEntityOrCA::MustBeCA
-               ? TrustLevel::TrustAnchor
-               : TrustLevel::InheritsTrust;
-    return Success;
-  }
-
-  Result FindIssuer(Input, IssuerChecker& checker, Time) override
-  {
-    Input issuerInput;
-    EXPECT_EQ(Success, issuerInput.Init(issuer.data(), issuer.length()));
-    bool keepGoing;
-    EXPECT_EQ(Success,
-              checker.Check(issuerInput, nullptr /*additionalNameConstraints*/,
-                            keepGoing));
-    EXPECT_EQ(expectedKeepGoing, keepGoing);
-    return Success;
-  }
-
-  Result CheckRevocation(EndEntityOrCA, const CertID&, Time, Duration,
-                         /*optional*/ const Input*, /*optional*/ const Input*)
-                         override
-  {
-    return Success;
-  }
-
-  Result IsChainValid(const DERArray&, Time, const CertPolicyId&) override
-  {
-    return Success;
-  }
-
-private:
-  const ByteString issuer;
-  const bool expectedKeepGoing;
-};
-
-struct IssuerNameCheckParams
-{
-  const char* subjectIssuerCN; // null means "empty name"
-  const char* issuerSubjectCN; // null means "empty name"
-  bool matches;
-  Result expectedError;
-};
-
-static const IssuerNameCheckParams ISSUER_NAME_CHECK_PARAMS[] =
-{
-  { "foo", "foo", true, Success },
-  { "foo", "bar", false, Result::ERROR_UNKNOWN_ISSUER },
-  { "f", "foo", false, Result::ERROR_UNKNOWN_ISSUER }, // prefix
-  { "foo", "f", false, Result::ERROR_UNKNOWN_ISSUER }, // prefix
-  { "foo", "Foo", false, Result::ERROR_UNKNOWN_ISSUER }, // case sensitive
-  { "", "", true, Success },
-  { nullptr, nullptr, false, Result::ERROR_EMPTY_ISSUER_NAME }, // empty issuer
-
-  // check that certificate-related errors are deferred and superseded by
-  // ERROR_UNKNOWN_ISSUER when a chain can't be built due to name mismatches
-  { "foo", nullptr, false, Result::ERROR_UNKNOWN_ISSUER },
-  { nullptr, "foo", false, Result::ERROR_UNKNOWN_ISSUER }
-};
-
-class pkixbuild_IssuerNameCheck
-  : public ::testing::Test
-  , public ::testing::WithParamInterface<IssuerNameCheckParams>
-{
-};
-
-TEST_P(pkixbuild_IssuerNameCheck, MatchingName)
-{
-  const IssuerNameCheckParams& params(GetParam());
-
-  ByteString issuerCertDER(CreateCert(params.issuerSubjectCN,
-                                      params.issuerSubjectCN,
-                                      EndEntityOrCA::MustBeCA, nullptr));
-  ASSERT_FALSE(ENCODING_FAILED(issuerCertDER));
-
-  ByteString subjectCertDER(CreateCert(params.subjectIssuerCN, "end-entity",
-                                       EndEntityOrCA::MustBeEndEntity,
-                                       nullptr));
-  ASSERT_FALSE(ENCODING_FAILED(subjectCertDER));
-
-  Input subjectCertDERInput;
-  ASSERT_EQ(Success, subjectCertDERInput.Init(subjectCertDER.data(),
-                                              subjectCertDER.length()));
-
-  IssuerNameCheckTrustDomain trustDomain(issuerCertDER, !params.matches);
-  ASSERT_EQ(params.expectedError,
-            BuildCertChain(trustDomain, subjectCertDERInput, Now(),
-                           EndEntityOrCA::MustBeEndEntity,
-                           KeyUsage::noParticularKeyUsageRequired,
-                           KeyPurposeId::id_kp_serverAuth,
-                           CertPolicyId::anyPolicy,
-                           nullptr/*stapledOCSPResponse*/));
-}
-
-INSTANTIATE_TEST_CASE_P(pkixbuild_IssuerNameCheck, pkixbuild_IssuerNameCheck,
-                        testing::ValuesIn(ISSUER_NAME_CHECK_PARAMS));
-
-
-// Records the embedded SCT list extension for later examination.
-class EmbeddedSCTListTestTrustDomain final : public SingleRootTrustDomain
-{
-public:
-  explicit EmbeddedSCTListTestTrustDomain(ByteString aRootDER)
-    : SingleRootTrustDomain(aRootDER)
-  {
-  }
-
-  virtual void NoteAuxiliaryExtension(AuxiliaryExtension extension,
-                                      Input extensionData) override
-  {
-    if (extension == AuxiliaryExtension::EmbeddedSCTList) {
-      signedCertificateTimestamps = InputToByteString(extensionData);
-    } else {
-      ADD_FAILURE();
-    }
-  }
-
-  ByteString signedCertificateTimestamps;
-};
-
-TEST_F(pkixbuild, CertificateTransparencyExtension)
-{
-  // python security/pkix/tools/DottedOIDToCode.py --tlv
-  //   id-embeddedSctList 1.3.6.1.4.1.11129.2.4.2
-  static const uint8_t tlv_id_embeddedSctList[] = {
-    0x06, 0x0a, 0x2b, 0x06, 0x01, 0x04, 0x01, 0xd6, 0x79, 0x02, 0x04, 0x02
-  };
-  static const uint8_t dummySctList[] = {
-    0x01, 0x02, 0x03, 0x04, 0x05
-  };
-
-  ByteString ctExtension = TLV(der::SEQUENCE,
-    BytesToByteString(tlv_id_embeddedSctList) +
-    Boolean(false) +
-    TLV(der::OCTET_STRING,
-      // SignedCertificateTimestampList structure is encoded as an OCTET STRING
-      // within the X.509v3 extension (see RFC 6962 section 3.3).
-      // pkix decodes it internally and returns the actual structure.
-      TLV(der::OCTET_STRING, BytesToByteString(dummySctList))));
-
-  const char* rootCN = "Root CA";
-  ByteString rootDER(CreateCert(rootCN, rootCN, EndEntityOrCA::MustBeCA));
-  ASSERT_FALSE(ENCODING_FAILED(rootDER));
-
-  ByteString certDER(CreateCert(rootCN, "Cert with SCT list",
-                                EndEntityOrCA::MustBeEndEntity,
-                                nullptr, /*subjectDERToCertDER*/
-                                &ctExtension));
-  ASSERT_FALSE(ENCODING_FAILED(certDER));
-
-  Input certInput;
-  ASSERT_EQ(Success, certInput.Init(certDER.data(), certDER.length()));
-
-  EmbeddedSCTListTestTrustDomain extTrustDomain(rootDER);
-  ASSERT_EQ(Success,
-            BuildCertChain(extTrustDomain, certInput, Now(),
-                           EndEntityOrCA::MustBeEndEntity,
-                           KeyUsage::noParticularKeyUsageRequired,
-                           KeyPurposeId::anyExtendedKeyUsage,
-                           CertPolicyId::anyPolicy,
-                           nullptr /*stapledOCSPResponse*/));
-  ASSERT_EQ(BytesToByteString(dummySctList),
-            extTrustDomain.signedCertificateTimestamps);
-}
-
-// This TrustDomain implements a hierarchy like so:
-//
-// A   B
-// |   |
-// C   D
-//  \ /
-//   E
-//
-// where A is a trust anchor, B is not a trust anchor and has no known issuer, C
-// and D are intermediates with the same subject and subject public key, and E
-// is an end-entity (in practice, the end-entity will be generated by the test
-// functions using this trust domain).
-class MultiplePathTrustDomain: public DefaultCryptoTrustDomain
-{
-public:
-  void SetUpCerts()
-  {
-    ASSERT_FALSE(ENCODING_FAILED(CreateCert("UntrustedRoot", "UntrustedRoot",
-                                            EndEntityOrCA::MustBeCA,
-                                            &subjectDERToCertDER)));
-    // The subject DER -> cert DER mapping would be overwritten for subject
-    // "Intermediate" when we create the second "Intermediate" certificate, so
-    // we keep a copy of this "Intermediate".
-    intermediateSignedByUntrustedRootCertDER =
-      CreateCert("UntrustedRoot", "Intermediate", EndEntityOrCA::MustBeCA);
-    ASSERT_FALSE(ENCODING_FAILED(intermediateSignedByUntrustedRootCertDER));
-    rootCACertDER = CreateCert("TrustedRoot", "TrustedRoot",
-                               EndEntityOrCA::MustBeCA, &subjectDERToCertDER);
-    ASSERT_FALSE(ENCODING_FAILED(rootCACertDER));
-    ASSERT_FALSE(ENCODING_FAILED(CreateCert("TrustedRoot", "Intermediate",
-                                            EndEntityOrCA::MustBeCA,
-                                            &subjectDERToCertDER)));
-  }
-
-private:
-  Result GetCertTrust(EndEntityOrCA, const CertPolicyId&, Input candidateCert,
-                      /*out*/ TrustLevel& trustLevel) override
-  {
-    trustLevel = InputEqualsByteString(candidateCert, rootCACertDER)
-               ? TrustLevel::TrustAnchor
-               : TrustLevel::InheritsTrust;
-    return Success;
-  }
-
-  Result CheckCert(ByteString& certDER, IssuerChecker& checker, bool& keepGoing)
-  {
-    Input derCert;
-    Result rv = derCert.Init(certDER.data(), certDER.length());
-    if (rv != Success) {
-      return rv;
-    }
-    return checker.Check(derCert, nullptr/*additionalNameConstraints*/,
-                         keepGoing);
-  }
-
-  Result FindIssuer(Input encodedIssuerName, IssuerChecker& checker, Time)
-                    override
-  {
-    ByteString subjectDER(InputToByteString(encodedIssuerName));
-    ByteString certDER(subjectDERToCertDER[subjectDER]);
-    assert(!ENCODING_FAILED(certDER));
-    bool keepGoing;
-    Result rv = CheckCert(certDER, checker, keepGoing);