/* Copyright (c) 2016, Google Inc. * * Permission to use, copy, modify, and/or distribute this software for any * purpose with or without fee is hereby granted, provided that the above * copyright notice and this permission notice appear in all copies. * * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include <limits.h> #include <algorithm> #include <functional> #include <string> #include <vector> #include <gtest/gtest.h> #include <openssl/asn1.h> #include <openssl/bio.h> #include <openssl/bytestring.h> #include <openssl/conf.h> #include <openssl/crypto.h> #include <openssl/curve25519.h> #include <openssl/digest.h> #include <openssl/err.h> #include <openssl/nid.h> #include <openssl/pem.h> #include <openssl/pool.h> #include <openssl/x509.h> #include "internal.h" #include "../internal.h" #include "../test/file_util.h" #include "../test/test_data.h" #include "../test/test_util.h" #if defined(OPENSSL_THREADS) #include <thread> #endif static const char kCrossSigningRootPEM[] = …; static const char kRootCAPEM[] = …; static const char kRootCrossSignedPEM[] = …; static const char kIntermediatePEM[] = …; static const char kIntermediateSelfSignedPEM[] = …; static const char kLeafPEM[] = …; static const char kLeafNoKeyUsagePEM[] = …; static const char kForgeryPEM[] = …; // kBadPSSCertPEM is a self-signed RSA-PSS certificate with bad parameters. static const char kBadPSSCertPEM[] = …; static const char kRSAKey[] = …; static const char kP256Key[] = …; // kCRLTestRoot is a test root certificate. It has private key: // // -----BEGIN RSA PRIVATE KEY----- // MIIEpAIBAAKCAQEAo16WiLWZuaymsD8n5SKPmxV1y6jjgr3BS/dUBpbrzd1aeFzN // lI8l2jfAnzUyp+I21RQ+nh/MhqjGElkTtK9xMn1Y+S9GMRh+5R/Du0iCb1tCZIPY // 07Tgrb0KMNWe0v2QKVVruuYSgxIWodBfxlKO64Z8AJ5IbnWpuRqO6rctN9qUoMlT // IAB6dL4G0tDJ/PGFWOJYwOMEIX54bly2wgyYJVBKiRRt4f7n8H922qmvPNA9idmX // 9G1VAtgV6x97XXi7ULORIQvn9lVQF6nTYDBJhyuPB+mLThbLP2o9orxGx7aCtnnB // ZUIxUvHNOI0FaSaZH7Fi0xsZ/GkG2HZe7ImPJwIDAQABAoIBAQCJF9MTHfHGkk+/ // DwCXlA0Wg0e6hBuHl10iNobYkMWIl/xXjOknhYiqOqb181py76472SVC5ERprC+r // Lf0PXzqKuA117mnkwT2bYLCL9Skf8WEhoFLQNbVlloF6wYjqXcYgKYKh8HgQbZl4 // aLg2YQl2NADTNABsUWj/4H2WEelsODVviqfFs725lFg9KHDI8zxAZXLzDt/M9uVL // GxJiX12tr0AwaeAFZ1oPM/y+LznM3N3+Ht3jHHw3jZ/u8Z1RdAmdpu3bZ6tbwGBr // 9edsH5rKkm9aBvMrY7eX5VHqaqyRNFyG152ZOJh4XiiFG7EmgTPCpaHo50Y018Re // grVtk+FBAoGBANY3lY+V8ZOwMxSHes+kTnoimHO5Ob7nxrOC71i27x+4HHsYUeAr // /zOOghiDIn+oNkuiX5CIOWZKx159Bp65CPpCbTb/fh+HYnSgXFgCw7XptycO7LXM // 5GwR5jSfpfzBFdYxjxoUzDMFBwTEYRTm0HkUHkH+s+ajjw5wqqbcGLcfAoGBAMM8 // DKW6Tb66xsf708f0jonAjKYTLZ+WOcwsBEWSFHoY8dUjvW5gqx5acHTEsc5ZTeh4 // BCFLa+Mn9cuJWVJNs09k7Xb2PNl92HQ4GN2vbdkJhExbkT6oLDHg1hVD0w8KLfz1 // lTAW6pS+6CdOHMEJpvqx89EgU/1GgIQ1fXYczE75AoGAKeJoXdDFkUjsU+FBhAPu // TDcjc80Nm2QaF9NMFR5/lsYa236f06MGnQAKM9zADBHJu/Qdl1brUjLg1HrBppsr // RDNkw1IlSOjhuUf5hkPUHGd8Jijm440SRIcjabqla8wdBupdvo2+d2NOQgJbsQiI // ToQ+fkzcxAXK3Nnuo/1436UCgYBjLH7UNOZHS8OsVM0I1r8NVKVdu4JCfeJQR8/H // s2P5ffBir+wLRMnH+nMDreMQiibcPxMCArkERAlE4jlgaJ38Z62E76KLbLTmnJRt // EC9Bv+bXjvAiHvWMRMUbOj/ddPNVez7Uld+FvdBaHwDWQlvzHzBWfBCOKSEhh7Z6 // qDhUqQKBgQDPMDx2i5rfmQp3imV9xUcCkIRsyYQVf8Eo7NV07IdUy/otmksgn4Zt // Lbf3v2dvxOpTNTONWjp2c+iUQo8QxJCZr5Sfb21oQ9Ktcrmc/CY7LeBVDibXwxdM // vRG8kBzvslFWh7REzC3u06GSVhyKDfW93kN2cKVwGoahRlhj7oHuZQ== // -----END RSA PRIVATE KEY----- static const char kCRLTestRoot[] = …; static const char kCRLTestLeaf[] = …; static const char kBasicCRL[] = …; static const char kRevokedCRL[] = …; static const char kBadIssuerCRL[] = …; // kKnownCriticalCRL is kBasicCRL but with a critical issuing distribution point // extension. static const char kKnownCriticalCRL[] = …; // kUnknownCriticalCRL is kBasicCRL but with an unknown critical extension. static const char kUnknownCriticalCRL[] = …; // kUnknownCriticalCRL2 is kBasicCRL but with a critical issuing distribution // point extension followed by an unknown critical extension static const char kUnknownCriticalCRL2[] = …; // kBadExtensionCRL is kBasicCRL but with an incorrectly-encoded issuing // distribution point extension. static const char kBadExtensionCRL[] = …; // kAlgorithmMismatchCRL is kBasicCRL but with mismatched AlgorithmIdentifiers // in the outer structure and signed portion. The signature reflects the signed // portion. static const char kAlgorithmMismatchCRL[] = …; // kAlgorithmMismatchCRL2 is kBasicCRL but with mismatched AlgorithmIdentifiers // in the outer structure and signed portion. The signature reflects the outer // structure. static const char kAlgorithmMismatchCRL2[] = …; // kEd25519Cert is a self-signed Ed25519 certificate. static const char kEd25519Cert[] = …; // kEd25519CertNull is an invalid self-signed Ed25519 with an explicit NULL in // the signature algorithm. static const char kEd25519CertNull[] = …; // kX25519 is the example X25519 certificate from // https://tools.ietf.org/html/rfc8410#section-10.2 static const char kX25519Cert[] = …; // kSANTypesLeaf is a leaf certificate (signed by |kSANTypesRoot|) which // contains SANS for example.com, [email protected], 127.0.0.1, and // https://example.com/. (The latter is useless for now since crypto/x509 // doesn't deal with URI SANs directly.) static const char kSANTypesLeaf[] = …; // -----BEGIN RSA PRIVATE KEY----- // MIICWwIBAAKBgQDbRn2TLhInBki8Bighq37EtqJd/h5SRYh6NkelCA2SQlvCgcC+ // l3mYQPtPbRT9KxOLwqUuZ9jUCZ7WIji3Sgt0cyvCNPHRk+WW2XR781ifbGE8wLBB // 1NkrKyQjd1scO711Xc4gVM+hY4cdHiTE8x0aUIuqthRD7ZendWL0FMhS1wIDAQAB // AoGACwf7z0i1DxOI2zSwFimLghfyCSp8mgT3fbZ3Wj0SebYu6ZUffjceneM/AVrq // gGYHYLOVHcWJqfkl7X3hPo9SDhzLx0mM545/q21ZWCwjhswH7WiCEqV2/zeDO9WU // NIO1VU0VoLm0AQ7ZvwnyB+fpgF9kkkDtbBJW7XWrfNVtlnECQQD97YENpEJ3X1kj // 3rrkrHWDkKAyoWWY1i8Fm7LnganC9Bv6AVwgn5ZlE/479aWHF8vbOFEA3pFPiNZJ // t9FTCfpJAkEA3RCXjGI0Y6GALFLwEs+nL/XZAfJaIpJEZVLCVosYQOSaMS4SchfC // GGYVquT7ZgKk9uvz89Fg87OtBMWS9lrkHwJADGkGLKeBhBoJ3kHtem2fVK3F1pOi // xoR5SdnhNYVVyaxqjZ5xZTrHe+stOrr3uxGDqhQniVZXXb6/Ul0Egv1y2QJAVg/h // kAujba4wIhFf2VLyOZ+yjil1ocPj0LZ5Zgvcs1bMGJ1hHP3W2HzVrqRaowoggui1 // HpTC891dXGA2qKYV7QJAFDmT2A7OVvh3y4AEgzVwHrDmCMwMHKjCIntS7fjxrJnF // YvJUG1zoHwUVrxxbR3DbpTODlktLcl/0b97D0IkH3w== // -----END RSA PRIVATE KEY----- static const char kSANTypesRoot[] = …; // -----BEGIN RSA PRIVATE KEY----- // MIICXAIBAAKBgQDpDn8RDOZa5oaDcPZRBy4CeBH1siSSOO4mYgLHlPE+oXdqwI/V // Imi2XeJM2uCFETXCknJJjYG0iJdrt/yyRFvZTQZw+QzGj+mz36NqhGxDWb6dstB2 // m8PX+plZw7jl81MDvUnWs8yiQ/6twgu5AbhWKZQDJKcNKCEpqa6UW0r5nwIDAQAB // AoGALEF5daZqc+aEsp8X1yky3nsoheyPL0kqSBWii33IFemZgKcSaRnAoqjPWWLS // 8dHj0I/4rej2MW8iuezVSpDak9tK5boHORC3w4p/wifkizQkLt1DANxTVbzcKvrt // aZ7LjVaKkhjRJbLddniowFHkkWVbUccjvzcUd7Y2VuLbAhECQQDq4FE88aHio8zg // bxSd0PwjEFwLYQTR19u812SoR8PmR6ofIL+pDwOV+fVs+OGcAAOgkhIukOrksQ4A // 1cKtnyhXAkEA/gRI+u3tZ7UE1twIkBfZ6IvCdRodkPqHAYIxMRLzL+MhyZt4MEGc // Ngb/F6U9/WOBFnoR/PI7IwE3ejutzKcL+QJBAKh+6eilk7QKPETZi1m3/dmNt+p1 // 3EZJ65pqjwxmB3Rg/vs7vCMk4TarTdSyKu+F1xRPFfoP/mK3Xctdjj6NyhsCQAYF // 7/0TOzfkUPMPUJyqFB6xgbDpJ55ScnUUsznoqx+NkTWInDb4t02IqO/UmT2y6FKy // Hk8TJ1fTJY+ebqaVp3ECQApx9gQ+n0zIhx97FMUuiRse73xkcW4+pZ8nF+8DmeQL // /JKuuFGmzkG+rUbXFmo/Zg2ozVplw71NnQJ4znPsf7A= // -----END RSA PRIVATE KEY----- // The following four certificates were generated with this Go program, varying // |includeNetscapeExtension| and defining rootKeyPEM and rootCertPEM to be // strings containing the kSANTypesRoot, above. // package main // import ( // "crypto/ecdsa" // "crypto/elliptic" // "crypto/rand" // "crypto/x509" // "crypto/x509/pkix" // "encoding/asn1" // "encoding/pem" // "math/big" // "os" // "time" // ) // const includeNetscapeExtension = true // func main() { // block, _ := pem.Decode([]byte(rootKeyPEM)) // rootPriv, _ := x509.ParsePKCS1PrivateKey(block.Bytes) // block, _ = pem.Decode([]byte(rootCertPEM)) // root, _ := x509.ParseCertificate(block.Bytes) // interTemplate := &x509.Certificate{ // SerialNumber: big.NewInt(2), // Subject: pkix.Name{ // CommonName: "No Basic Constraints (Netscape)", // }, // NotBefore: time.Date(2000, time.January, 1, 0, 0, 0, 0, time.UTC), // NotAfter: time.Date(2099, time.January, 1, 0, 0, 0, 0, time.UTC), // } // if includeNetscapeExtension { // interTemplate.ExtraExtensions = []pkix.Extension{ // pkix.Extension{ // Id: asn1.ObjectIdentifier([]int{2, 16, 840, 1, 113730, 1, 1}), // Value: []byte{0x03, 0x02, 2, 0x04}, // }, // } // } else { // interTemplate.KeyUsage = x509.KeyUsageCertSign // } // interKey, _ := ecdsa.GenerateKey(elliptic.P256(), rand.Reader) // interDER, err := x509.CreateCertificate(rand.Reader, interTemplate, root, &interKey.PublicKey, rootPriv) // if err != nil { // panic(err) // } // pem.Encode(os.Stdout, &pem.Block{Type: "CERTIFICATE", Bytes: interDER}) // inter, _ := x509.ParseCertificate(interDER) // leafTemplate := &x509.Certificate{ // SerialNumber: big.NewInt(3), // Subject: pkix.Name{ // CommonName: "Leaf from CA with no Basic Constraints", // }, // NotBefore: time.Date(2000, time.January, 1, 0, 0, 0, 0, time.UTC), // NotAfter: time.Date(2099, time.January, 1, 0, 0, 0, 0, time.UTC), // BasicConstraintsValid: true, // } // leafKey, _ := ecdsa.GenerateKey(elliptic.P256(), rand.Reader) // leafDER, err := x509.CreateCertificate(rand.Reader, leafTemplate, inter, &leafKey.PublicKey, interKey) // if err != nil { // panic(err) // } // pem.Encode(os.Stdout, &pem.Block{Type: "CERTIFICATE", Bytes: leafDER}) // } // kNoBasicConstraintsCertSignIntermediate doesn't have isCA set, but contains // certSign in the keyUsage. static const char kNoBasicConstraintsCertSignIntermediate[] = …; static const char kNoBasicConstraintsCertSignLeaf[] = …; // kNoBasicConstraintsNetscapeCAIntermediate doesn't have isCA set, but contains // a Netscape certificate-type extension that asserts a type of "SSL CA". static const char kNoBasicConstraintsNetscapeCAIntermediate[] = …; static const char kNoBasicConstraintsNetscapeCALeaf[] = …; static const char kSelfSignedMismatchAlgorithms[] = …; // kCommonNameWithSANs is a leaf certificate signed by kSANTypesRoot, with // *.host1.test as the common name and a SAN list of *.host2.test and // foo.host3.test. static const char kCommonNameWithSANs[] = …; // kCommonNameWithSANs is a leaf certificate signed by kSANTypesRoot, with // *.host1.test as the common name and no SAN list. static const char kCommonNameWithoutSANs[] = …; // kCommonNameWithEmailSAN is a leaf certificate signed by kSANTypesRoot, with // *.host1.test as the common name and the email address [email protected] in the // SAN list. static const char kCommonNameWithEmailSAN[] = …; // kCommonNameWithIPSAN is a leaf certificate signed by kSANTypesRoot, with // *.host1.test as the common name and the IP address 127.0.0.1 in the // SAN list. static const char kCommonNameWithIPSAN[] = …; // kConstrainedIntermediate is an intermediate signed by kSANTypesRoot, with // permitted DNS names of permitted1.test and foo.permitted2.test and an // excluded DNS name of excluded.permitted1.test. Its private key is: // // -----BEGIN PRIVATE KEY----- // MIGHAgEAMBMGByqGSM49AgEGCCqGSM49AwEHBG0wawIBAQQgTXUM4tJWM7OzATty // JhNOfIv/d8heWFBeKOfMR+RfaROhRANCAASbbbWYiN6mn+BCpg4XNpibOH0D/DN4 // kZ5C/Ml2YVomC9T83OKk2CzB8fPAabPb4P4Vv+fIabpEfjWS5nzKLY1y // -----END PRIVATE KEY----- static const char kConstrainedIntermediate[] = …; // kCommonNamePermittedLeaf is a leaf certificate signed by // kConstrainedIntermediate. Its common name is permitted by the name // constraints. static const char kCommonNamePermittedLeaf[] = …; static const char kCommonNamePermitted[] = …; // kCommonNameNotPermittedLeaf is a leaf certificate signed by // kConstrainedIntermediate. Its common name is not permitted by the name // constraints. static const char kCommonNameNotPermittedLeaf[] = …; static const char kCommonNameNotPermitted[] = …; // kCommonNameNotPermittedWithSANsLeaf is a leaf certificate signed by // kConstrainedIntermediate. Its common name is not permitted by the name // constraints but it has a SAN list. static const char kCommonNameNotPermittedWithSANsLeaf[] = …; static const char kCommonNameNotPermittedWithSANs[] = …; // kCommonNameNotDNSLeaf is a leaf certificate signed by // kConstrainedIntermediate. Its common name is not a DNS name. static const char kCommonNameNotDNSLeaf[] = …; static const char kCommonNameNotDNS[] = …; // The following six certificates are issued by |kSANTypesRoot| and have // different extended key usage values. They were created with the following // Go program: // // func main() { // block, _ := pem.Decode([]byte(rootKeyPEM)) // rootPriv, _ := x509.ParsePKCS1PrivateKey(block.Bytes) // block, _ = pem.Decode([]byte(rootCertPEM)) // root, _ := x509.ParseCertificate(block.Bytes) // // leafTemplate := &x509.Certificate{ // SerialNumber: big.NewInt(3), // Subject: pkix.Name{ // CommonName: "EKU msSGC", // }, // NotBefore: time.Date(2000, time.January, 1, 0, 0, 0, 0, time.UTC), // NotAfter: time.Date(2099, time.January, 1, 0, 0, 0, 0, time.UTC), // BasicConstraintsValid: true, // ExtKeyUsage: []x509.ExtKeyUsage{FILL IN HERE}, // } // leafKey, _ := ecdsa.GenerateKey(elliptic.P256(), rand.Reader) // leafDER, err := x509.CreateCertificate(rand.Reader, leafTemplate, root, &leafKey.PublicKey, rootPriv) // if err != nil { // panic(err) // } // pem.Encode(os.Stdout, &pem.Block{Type: "CERTIFICATE", Bytes: leafDER}) // } static const char kMicrosoftSGCCert[] = …; static const char kNetscapeSGCCert[] = …; static const char kServerEKUCert[] = …; static const char kServerEKUPlusMicrosoftSGCCert[] = …; static const char kAnyEKU[] = …; static const char kNoEKU[] = …; // CertFromPEM parses the given, NUL-terminated PEM block and returns an // |X509*|. static bssl::UniquePtr<X509> CertFromPEM(const char *pem) { … } // CRLFromPEM parses the given, NUL-terminated PEM block and returns an // |X509_CRL*|. static bssl::UniquePtr<X509_CRL> CRLFromPEM(const char *pem) { … } // CSRFromPEM parses the given, NUL-terminated PEM block and returns an // |X509_REQ*|. static bssl::UniquePtr<X509_REQ> CSRFromPEM(const char *pem) { … } // PrivateKeyFromPEM parses the given, NUL-terminated PEM block and returns an // |EVP_PKEY*|. static bssl::UniquePtr<EVP_PKEY> PrivateKeyFromPEM(const char *pem) { … } // CertsToStack converts a vector of |X509*| to an OpenSSL STACK_OF(X509), // bumping the reference counts for each certificate in question. static bssl::UniquePtr<STACK_OF(X509)> CertsToStack( const std::vector<X509 *> &certs) { … } // CRLsToStack converts a vector of |X509_CRL*| to an OpenSSL // STACK_OF(X509_CRL), bumping the reference counts for each CRL in question. static bssl::UniquePtr<STACK_OF(X509_CRL)> CRLsToStack( const std::vector<X509_CRL *> &crls) { … } static const int64_t kReferenceTime = … /* Sep 27th, 2016 */; static int Verify( X509 *leaf, const std::vector<X509 *> &roots, const std::vector<X509 *> &intermediates, const std::vector<X509_CRL *> &crls, unsigned long flags = 0, std::function<void(X509_STORE_CTX *)> configure_callback = nullptr) { … } TEST(X509Test, TestVerify) { … } #if defined(OPENSSL_THREADS) // Verifying the same |X509| objects on two threads should be safe. TEST(X509Test, VerifyThreads) { … } // Using the same CRL on two threads should be safe. TEST(X509Test, CRLThreads) { … } TEST(X509Test, StoreThreads) { … } #endif // OPENSSL_THREADS static const char kHostname[] = …; static const char kWrongHostname[] = …; static const char kEmail[] = …; static const char kWrongEmail[] = …; static const uint8_t kIP[4] = …; static const uint8_t kWrongIP[4] = …; static const char kIPString[] = …; static const char kWrongIPString[] = …; TEST(X509Test, ZeroLengthsWithX509PARAM) { … } TEST(X509Test, ZeroLengthsWithCheckFunctions) { … } TEST(X509Test, TestCRL) { … } TEST(X509Test, ManyNamesAndConstraints) { … } static bssl::UniquePtr<GENERAL_NAME> MakeGeneralName(int type, const std::string &value) { … } static bssl::UniquePtr<X509_NAME> MakeTestName(const char *common_name) { … } static bssl::UniquePtr<X509> MakeTestCert(const char *issuer, const char *subject, EVP_PKEY *key, bool is_ca) { … } static bool AddExtendedKeyUsage(X509 *x509, const std::vector<int> &eku_nids) { … } enum class KeyUsage : int { … }; static bool AddKeyUsage(X509 *x509, const std::vector<KeyUsage> usages) { … } static bool AddSubjectKeyIdentifier(X509 *x509, bssl::Span<const uint8_t> key_id) { … } static bool AddAuthorityKeyIdentifier(X509 *x509, bssl::Span<const uint8_t> key_id) { … } static bssl::UniquePtr<X509_CRL> MakeTestCRL(const char *issuer, int this_update_offset_day, int next_update_offset_day) { … } static bool AddRevokedSerialU64(X509_CRL *crl, uint64_t serial, int offset_day) { … } static bool AddAuthorityKeyIdentifier(X509_CRL *crl, bssl::Span<const uint8_t> key_id) { … } TEST(X509Test, NameConstraints) { … } TEST(X509Test, PrintGeneralName) { … } TEST(X509Test, TestPSS) { … } TEST(X509Test, TestPSSBadParameters) { … } TEST(X509Test, TestEd25519) { … } TEST(X509Test, TestEd25519BadParameters) { … } TEST(X509Test, TestX25519) { … } static bssl::UniquePtr<X509> ReencodeCertificate(X509 *cert) { … } static bssl::UniquePtr<X509_CRL> ReencodeCRL(X509_CRL *crl) { … } static bssl::UniquePtr<X509_REQ> ReencodeCSR(X509_REQ *req) { … } static bool SignatureRoundTrips(EVP_MD_CTX *md_ctx, EVP_PKEY *pkey) { … } TEST(X509Test, RSASign) { … } // Test the APIs for signing a certificate, particularly whether they correctly // handle the TBSCertificate cache. TEST(X509Test, SignCertificate) { … } // Test the APIs for signing a CRL, particularly whether they correctly handle // the TBSCertList cache. TEST(X509Test, SignCRL) { … } static const char kTestCSR[] = …; // Test the APIs for signing a CSR, particularly whether they correctly handle // the CertificationRequestInfo cache. TEST(X509Test, SignCSR) { … } TEST(X509Test, Ed25519Sign) { … } static bool PEMToDER(bssl::UniquePtr<uint8_t> *out, size_t *out_len, const char *pem) { … } TEST(X509Test, TestFromBuffer) { … } TEST(X509Test, TestFromBufferWithTrailingData) { … } TEST(X509Test, TestFromBufferModified) { … } TEST(X509Test, TestFromBufferReused) { … } TEST(X509Test, TestFailedParseFromBuffer) { … } TEST(X509Test, TestPrintUTCTIME) { … } TEST(X509Test, PrettyPrintIntegers) { … } TEST(X509Test, X509AlgorSetMd) { … } TEST(X509Test, X509NameSet) { … } // Tests that |X509_NAME_hash| and |X509_NAME_hash_old|'s values never change. // These functions figure into |X509_LOOKUP_hash_dir|'s on-disk format, so they // must remain stable. In particular, if we ever remove name canonicalization, // we'll need to preserve it for |X509_NAME_hash|. TEST(X509Test, NameHash) { … } TEST(X509Test, NoBasicConstraintsCertSign) { … } TEST(X509Test, NoBasicConstraintsNetscapeCA) { … } TEST(X509Test, MismatchAlgorithms) { … } TEST(X509Test, PEMX509Info) { … } TEST(X509Test, ReadBIOEmpty) { … } TEST(X509Test, ReadBIOOneByte) { … } TEST(X509Test, PartialBIOReturn) { … } TEST(X509Test, CommonNameFallback) { … } TEST(X509Test, LooksLikeDNSName) { … } TEST(X509Test, CommonNameAndNameConstraints) { … } TEST(X509Test, ServerGatedCryptoEKUs) { … } // Test that invalid extensions are rejected by, if not the parser, at least the // verifier. TEST(X509Test, InvalidExtensions) { … } // kExplicitDefaultVersionPEM is an X.509v1 certificate with the version number // encoded explicitly, rather than omitted as required by DER. static const char kExplicitDefaultVersionPEM[] = …; // kNegativeVersionPEM is an X.509 certificate with a negative version number. static const char kNegativeVersionPEM[] = …; // kFutureVersionPEM is an X.509 certificate with a version number value of // three, which is not defined. (v3 has value two). static const char kFutureVersionPEM[] = …; // kOverflowVersionPEM is an X.509 certificate with a version field which // overflows |uint64_t|. static const char kOverflowVersionPEM[] = …; // kV1WithExtensionsPEM is an X.509v1 certificate with extensions. static const char kV1WithExtensionsPEM[] = …; // kV2WithExtensionsPEM is an X.509v2 certificate with extensions. static const char kV2WithExtensionsPEM[] = …; // kV1WithIssuerUniqueIDPEM is an X.509v1 certificate with an issuerUniqueID. static const char kV1WithIssuerUniqueIDPEM[] = …; // kV1WithSubjectUniqueIDPEM is an X.509v1 certificate with an issuerUniqueID. static const char kV1WithSubjectUniqueIDPEM[] = …; // kV1CRLWithExtensionsPEM is a v1 CRL with extensions. static const char kV1CRLWithExtensionsPEM[] = …; // kExplicitDefaultVersionCRLPEM is a v1 CRL with an explicitly-encoded version // field. static const char kExplicitDefaultVersionCRLPEM[] = …; // kV3CRLPEM is a v3 CRL. CRL versions only go up to v2. static const char kV3CRLPEM[] = …; // kV2CSRPEM is a v2 CSR. CSR versions only go up to v1. static const char kV2CSRPEM[] = …; // kV3CSRPEM is a v3 CSR. CSR versions only go up to v1. static const char kV3CSRPEM[] = …; // Test that the library enforces versions are valid and match the fields // present. TEST(X509Test, InvalidVersion) { … } // Unlike upstream OpenSSL, we require a non-null store in // |X509_STORE_CTX_init|. TEST(X509Test, NullStore) { … } TEST(X509Test, StoreCtxReuse) { … } TEST(X509Test, BasicConstraints) { … } // The following strings are test certificates signed by kP256Key and kRSAKey, // with missing, NULL, or invalid algorithm parameters. static const char kP256NoParam[] = …; static const char kP256NullParam[] = …; static const char kP256InvalidParam[] = …; static const char kRSANoParam[] = …; static const char kRSANullParam[] = …; static const char kRSAInvalidParam[] = …; TEST(X509Test, AlgorithmParameters) { … } TEST(X509Test, GeneralName) { … } // Test that extracting fields of an |X509_ALGOR| works correctly. TEST(X509Test, X509AlgorExtract) { … } // Test the various |X509_ATTRIBUTE| creation functions. TEST(X509Test, Attribute) { … } // Test that, by default, |X509_V_FLAG_TRUSTED_FIRST| is set, which means we'll // skip over server-sent expired intermediates when there is a local trust // anchor that works better. TEST(X509Test, TrustedFirst) { … } // Test that notBefore and notAfter checks work correctly. TEST(X509Test, Expiry) { … } TEST(X509Test, SignatureVerification) { … } // kConstructedBitString is an X.509 certificate where the signature is encoded // as a BER constructed BIT STRING. Note that, while OpenSSL's parser accepts // this input, it interprets the value incorrectly. static const char kConstructedBitString[] = …; // kConstructedOctetString is an X.509 certificate where an extension is encoded // as a BER constructed OCTET STRING. static const char kConstructedOctetString[] = …; // kIndefiniteLength is an X.509 certificate where the outermost SEQUENCE uses // BER indefinite-length encoding. static const char kIndefiniteLength[] = …; // kNonZeroPadding is an X.09 certificate where the BIT STRING signature field // has non-zero padding values. static const char kNonZeroPadding[] = …; // kHighTagNumber is an X.509 certificate where the outermost SEQUENCE tag uses // high tag number form. static const char kHighTagNumber[] = …; // kNonMinimalLengthOuter is an X.509 certificate where the outermost SEQUENCE // has a non-minimal length. static const char kNonMinimalLengthOuter[] = …; // kNonMinimalLengthSignature is an X.509 certificate where the signature has a // non-minimal length. static const char kNonMinimalLengthSignature[] = …; // kNonMinimalLengthSerial is an X.509 certificate where the serial number has a // non-minimal length. static const char kNonMinimalLengthSerial[] = …; TEST(X509Test, BER) { … } TEST(X509Test, Names) { … } TEST(X509Test, AddDuplicates) { … } TEST(X509Test, BytesToHex) { … } TEST(X509Test, NamePrint) { … } // kLargeSerialPEM is a certificate with a large serial number. static const char kLargeSerialPEM[] = …; TEST(X509Test, Print) { … } TEST(X509Test, AddExt) { … } TEST(X509Test, NameEntry) { … } // Tests that non-integer types are rejected when passed as an argument to // X509_set_serialNumber(). TEST(X509Test, SetSerialNumberChecksASN1StringType) { … } TEST(X509Test, Policy) { … } #if defined(OPENSSL_THREADS) // A similar test to the above, but ensures the various bits of intermediate // state are computed safely. TEST(X509Test, PolicyThreads) { … } #endif // OPENSSL_THREADS TEST(X509Test, ExtensionFromConf) { … } TEST(X509Test, AddUnserializableExtension) { … } // Test that, when constructing an |X509_NAME|, names are sorted by DER order. TEST(X509Test, SortRDN) { … } TEST(X509Test, NameAttributeValues) { … } TEST(X509Test, GetTextByOBJ) { … } TEST(X509Test, ParamInheritance) { … } TEST(X509Test, PublicKeyCache) { … } // Tests some unusual behavior in |X509_STORE_CTX_set_purpose| and // |X509_STORE_CTX_set_trust|. TEST(X509Test, ContextTrustAndPurpose) { … } TEST(X509Test, Purpose) { … } TEST(X509Test, Trust) { … } // Test some APIs that rust-openssl uses to look up purposes by name. TEST(X509Test, PurposeByShortName) { … } TEST(X509Test, CriticalExtension) { … } enum NameHash { … }; // TemporaryHashDir constructs a temporary directory in the format of // |X509_LOOKUP_hash_dir|. class TemporaryHashDir { … }; // TODO(davidben): Also test CRL handling. There are some interesting behaviors // in here. TEST(X509Test, DirHash) { … } // Test that two directory hash paths are treated as a sequence of paths, // separated by a separator. TEST(X509Test, DirHashSeparator) { … } #if defined(OPENSSL_THREADS) // Test that directory hash lookup is thread-safe. TEST(X509Test, DirHashThreads) { … } #endif // OPENSSL_THREADS // Test that, when there are two CAs with the same name, but different key // identifiers, certificate and CRL lookup can disambiguate correctly. TEST(X509Test, DuplicateName) { … } TEST(X509Test, ParseIPAddress) { … }