diff options
author | Jack Lloyd <[email protected]> | 2018-01-19 07:03:10 -0500 |
---|---|---|
committer | Jack Lloyd <[email protected]> | 2018-01-19 07:03:10 -0500 |
commit | ba41d6079f99a96dc3380a8ba47693be14aad5c2 (patch) | |
tree | 016a8d3d98b8a7f047dadaaddd69f73af8ab6e5c | |
parent | 2b7000735fcb33abba0134b1eb5388d82a3ba1c4 (diff) |
Reorganize code to avoid cli/test build failures if filesystem disabled
Fixes #1422
-rw-r--r-- | src/cli/pubkey.cpp | 216 | ||||
-rw-r--r-- | src/cli/tls_client.cpp | 3 | ||||
-rw-r--r-- | src/cli/tls_http_server.cpp | 2 | ||||
-rw-r--r-- | src/cli/tls_proxy.cpp | 2 | ||||
-rw-r--r-- | src/cli/tls_server.cpp | 3 | ||||
-rw-r--r-- | src/cli/x509.cpp | 2 | ||||
-rw-r--r-- | src/tests/test_certstor.cpp | 2 | ||||
-rw-r--r-- | src/tests/test_name_constraint.cpp | 2 | ||||
-rw-r--r-- | src/tests/test_ocsp.cpp | 2 | ||||
-rw-r--r-- | src/tests/test_pkcs11_high_level.cpp | 2 | ||||
-rw-r--r-- | src/tests/unit_ecdsa.cpp | 103 | ||||
-rw-r--r-- | src/tests/unit_x509.cpp | 239 |
12 files changed, 301 insertions, 277 deletions
diff --git a/src/cli/pubkey.cpp b/src/cli/pubkey.cpp index 2c431c403..ffe1470dc 100644 --- a/src/cli/pubkey.cpp +++ b/src/cli/pubkey.cpp @@ -27,36 +27,6 @@ namespace Botan_CLI { -class PK_Fingerprint final : public Command - { - public: - PK_Fingerprint() : Command("fingerprint --algo=SHA-256 *keys") {} - - std::string group() const override - { - return "pubkey"; - } - - std::string description() const override - { - return "Calculate a public key fingerprint"; - } - - void go() override - { - const std::string hash_algo = get_arg("algo"); - - for(std::string key_file : get_arg_list("keys")) - { - std::unique_ptr<Botan::Public_Key> key(Botan::X509::load_key(key_file)); - - output() << key_file << ": " << key->fingerprint_public(hash_algo) << "\n"; - } - } - }; - -BOTAN_REGISTER_COMMAND("fingerprint", PK_Fingerprint); - class PK_Keygen final : public Command { public: @@ -118,6 +88,8 @@ class PK_Keygen final : public Command BOTAN_REGISTER_COMMAND("keygen", PK_Keygen); +#if defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) + namespace { std::string algo_default_emsa(const std::string& key) @@ -138,6 +110,36 @@ std::string algo_default_emsa(const std::string& key) } +class PK_Fingerprint final : public Command + { + public: + PK_Fingerprint() : Command("fingerprint --algo=SHA-256 *keys") {} + + std::string group() const override + { + return "pubkey"; + } + + std::string description() const override + { + return "Calculate a public key fingerprint"; + } + + void go() override + { + const std::string hash_algo = get_arg("algo"); + + for(std::string key_file : get_arg_list("keys")) + { + std::unique_ptr<Botan::Public_Key> key(Botan::X509::load_key(key_file)); + + output() << key_file << ": " << key->fingerprint_public(hash_algo) << "\n"; + } + } + }; + +BOTAN_REGISTER_COMMAND("fingerprint", PK_Fingerprint); + class PK_Sign final : public Command { public: @@ -233,6 +235,84 @@ class PK_Verify final : public Command BOTAN_REGISTER_COMMAND("verify", PK_Verify); +class PKCS8_Tool final : public Command + { + public: + PKCS8_Tool() : Command("pkcs8 --pass-in= --pub-out --der-out --pass-out= --pbe= --pbe-millis=300 key") {} + + std::string group() const override + { + return "pubkey"; + } + + std::string description() const override + { + return "Open a PKCS #8 formatted key"; + } + + void go() override + { + std::unique_ptr<Botan::Private_Key> key; + std::string pass_in = get_arg("pass-in"); + + if (pass_in.empty()) + { + key.reset(Botan::PKCS8::load_key(get_arg("key"), rng())); + } + else + { + key.reset(Botan::PKCS8::load_key(get_arg("key"), rng(), pass_in)); + } + + const std::chrono::milliseconds pbe_millis(get_arg_sz("pbe-millis")); + const std::string pbe = get_arg("pbe"); + const bool der_out = flag_set("der-out"); + + if(flag_set("pub-out")) + { + if(der_out) + { + write_output(Botan::X509::BER_encode(*key)); + } + else + { + output() << Botan::X509::PEM_encode(*key); + } + } + else + { + const std::string pass_out = get_arg("pass-out"); + + if(der_out) + { + if(pass_out.empty()) + { + write_output(Botan::PKCS8::BER_encode(*key)); + } + else + { + write_output(Botan::PKCS8::BER_encode(*key, rng(), pass_out, pbe_millis, pbe)); + } + } + else + { + if(pass_out.empty()) + { + output() << Botan::PKCS8::PEM_encode(*key); + } + else + { + output() << Botan::PKCS8::PEM_encode(*key, rng(), pass_out, pbe_millis, pbe); + } + } + } + } + }; + +BOTAN_REGISTER_COMMAND("pkcs8", PKCS8_Tool); + +#endif + #if defined(BOTAN_HAS_ECC_GROUP) class EC_Group_Info final : public Command @@ -352,82 +432,6 @@ BOTAN_REGISTER_COMMAND("gen_dl_group", Gen_DL_Group); #endif -class PKCS8_Tool final : public Command - { - public: - PKCS8_Tool() : Command("pkcs8 --pass-in= --pub-out --der-out --pass-out= --pbe= --pbe-millis=300 key") {} - - std::string group() const override - { - return "pubkey"; - } - - std::string description() const override - { - return "Open a PKCS #8 formatted key"; - } - - void go() override - { - std::unique_ptr<Botan::Private_Key> key; - std::string pass_in = get_arg("pass-in"); - - if (pass_in.empty()) - { - key.reset(Botan::PKCS8::load_key(get_arg("key"), rng())); - } - else - { - key.reset(Botan::PKCS8::load_key(get_arg("key"), rng(), pass_in)); - } - - const std::chrono::milliseconds pbe_millis(get_arg_sz("pbe-millis")); - const std::string pbe = get_arg("pbe"); - const bool der_out = flag_set("der-out"); - - if(flag_set("pub-out")) - { - if(der_out) - { - write_output(Botan::X509::BER_encode(*key)); - } - else - { - output() << Botan::X509::PEM_encode(*key); - } - } - else - { - const std::string pass_out = get_arg("pass-out"); - - if(der_out) - { - if(pass_out.empty()) - { - write_output(Botan::PKCS8::BER_encode(*key)); - } - else - { - write_output(Botan::PKCS8::BER_encode(*key, rng(), pass_out, pbe_millis, pbe)); - } - } - else - { - if(pass_out.empty()) - { - output() << Botan::PKCS8::PEM_encode(*key); - } - else - { - output() << Botan::PKCS8::PEM_encode(*key, rng(), pass_out, pbe_millis, pbe); - } - } - } - } - }; - -BOTAN_REGISTER_COMMAND("pkcs8", PKCS8_Tool); - } #endif diff --git a/src/cli/tls_client.cpp b/src/cli/tls_client.cpp index 53e3926e0..f3fe0c266 100644 --- a/src/cli/tls_client.cpp +++ b/src/cli/tls_client.cpp @@ -8,7 +8,8 @@ #include "cli.h" -#if defined(BOTAN_HAS_TLS) && (defined(BOTAN_TARGET_OS_HAS_SOCKETS) || defined(BOTAN_TARGET_OS_HAS_WINSOCK2)) +#if defined(BOTAN_HAS_TLS) && defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) && \ + (defined(BOTAN_TARGET_OS_HAS_SOCKETS) || defined(BOTAN_TARGET_OS_HAS_WINSOCK2)) #include <botan/tls_client.h> #include <botan/tls_policy.h> diff --git a/src/cli/tls_http_server.cpp b/src/cli/tls_http_server.cpp index 339cd2a67..255cd31b3 100644 --- a/src/cli/tls_http_server.cpp +++ b/src/cli/tls_http_server.cpp @@ -7,7 +7,7 @@ #include "cli.h" -#if defined(BOTAN_HAS_TLS) && defined(BOTAN_HAS_BOOST_ASIO) +#if defined(BOTAN_HAS_TLS) && defined(BOTAN_HAS_BOOST_ASIO) && defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) #include <iostream> #include <fstream> diff --git a/src/cli/tls_proxy.cpp b/src/cli/tls_proxy.cpp index d9540d9d3..ed7ee5645 100644 --- a/src/cli/tls_proxy.cpp +++ b/src/cli/tls_proxy.cpp @@ -8,7 +8,7 @@ #include "cli.h" -#if defined(BOTAN_HAS_TLS) && defined(BOTAN_HAS_BOOST_ASIO) +#if defined(BOTAN_HAS_TLS) && defined(BOTAN_HAS_BOOST_ASIO) && defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) #include <iostream> #include <string> diff --git a/src/cli/tls_server.cpp b/src/cli/tls_server.cpp index b9cd0d029..9da65b0f4 100644 --- a/src/cli/tls_server.cpp +++ b/src/cli/tls_server.cpp @@ -8,7 +8,8 @@ #include "cli.h" -#if defined(BOTAN_HAS_TLS) && (defined(BOTAN_TARGET_OS_HAS_SOCKETS) || defined(BOTAN_TARGET_OS_HAS_WINSOCK2)) +#if defined(BOTAN_HAS_TLS) && defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) && \ + (defined(BOTAN_TARGET_OS_HAS_SOCKETS) || defined(BOTAN_TARGET_OS_HAS_WINSOCK2)) #include <botan/tls_server.h> #include <botan/tls_policy.h> diff --git a/src/cli/x509.cpp b/src/cli/x509.cpp index ed9eb3d4f..9a059d799 100644 --- a/src/cli/x509.cpp +++ b/src/cli/x509.cpp @@ -7,7 +7,7 @@ #include "cli.h" -#if defined(BOTAN_HAS_X509_CERTIFICATES) +#if defined(BOTAN_HAS_X509_CERTIFICATES) && defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) #include <botan/certstor.h> #include <botan/pk_keys.h> diff --git a/src/tests/test_certstor.cpp b/src/tests/test_certstor.cpp index ea69e05c2..d48973ac4 100644 --- a/src/tests/test_certstor.cpp +++ b/src/tests/test_certstor.cpp @@ -22,7 +22,7 @@ namespace Botan_Tests { namespace { -#if defined(BOTAN_HAS_CERTSTOR_SQL) && defined(BOTAN_HAS_RSA) +#if defined(BOTAN_HAS_CERTSTOR_SQL) && defined(BOTAN_HAS_RSA) && defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) struct CertificateAndKey { diff --git a/src/tests/test_name_constraint.cpp b/src/tests/test_name_constraint.cpp index 3d01d84c7..f0abda710 100644 --- a/src/tests/test_name_constraint.cpp +++ b/src/tests/test_name_constraint.cpp @@ -17,7 +17,7 @@ namespace Botan_Tests { namespace { -#if defined(BOTAN_HAS_X509_CERTIFICATES) && defined(BOTAN_HAS_RSA) && defined(BOTAN_HAS_EMSA_PKCS1) +#if defined(BOTAN_HAS_X509_CERTIFICATES) && defined(BOTAN_HAS_RSA) && defined(BOTAN_HAS_EMSA_PKCS1) && defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) class Name_Constraint_Tests final : public Test { diff --git a/src/tests/test_ocsp.cpp b/src/tests/test_ocsp.cpp index 6a872ae62..dc3c6f47e 100644 --- a/src/tests/test_ocsp.cpp +++ b/src/tests/test_ocsp.cpp @@ -16,7 +16,7 @@ namespace Botan_Tests { -#if defined(BOTAN_HAS_OCSP) && defined(BOTAN_HAS_RSA) && defined(BOTAN_HAS_EMSA_PKCS1) +#if defined(BOTAN_HAS_OCSP) && defined(BOTAN_HAS_RSA) && defined(BOTAN_HAS_EMSA_PKCS1) && defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) class OCSP_Tests final : public Test { diff --git a/src/tests/test_pkcs11_high_level.cpp b/src/tests/test_pkcs11_high_level.cpp index 950171d9c..e89715189 100644 --- a/src/tests/test_pkcs11_high_level.cpp +++ b/src/tests/test_pkcs11_high_level.cpp @@ -1550,6 +1550,7 @@ Test::Result test_x509_import() { Test::Result result("PKCS11 X509 cert import"); +#if defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) TestSession test_session(true); X509_Certificate root(Test::data_file("x509/nist/test01/end.crt")); @@ -1565,6 +1566,7 @@ Test::Result test_x509_import() result.test_eq("X509 certificate by handle", pkcs11_cert == pkcs11_cert2, true); pkcs11_cert.destroy(); +#endif return result; } diff --git a/src/tests/unit_ecdsa.cpp b/src/tests/unit_ecdsa.cpp index 99acc3f21..5d137bacf 100644 --- a/src/tests/unit_ecdsa.cpp +++ b/src/tests/unit_ecdsa.cpp @@ -76,7 +76,7 @@ Test::Result test_hash_larger_than_n() return result; } -#if defined(BOTAN_HAS_X509_CERTIFICATES) +#if defined(BOTAN_HAS_X509_CERTIFICATES) && defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) Test::Result test_decode_ecdsa_X509() { Test::Result result("ECDSA Unit"); @@ -262,6 +262,8 @@ Test::Result test_unusual_curve() return result; } +#if defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) + Test::Result test_read_pkcs8() { Test::Result result("ECDSA Unit"); @@ -306,7 +308,49 @@ Test::Result test_read_pkcs8() return result; } +Test::Result test_ecc_key_with_rfc5915_extensions() + { + Test::Result result("ECDSA Unit"); + + try + { + std::unique_ptr<Botan::Private_Key> pkcs8( + Botan::PKCS8::load_key(Test::data_file("x509/ecc/ecc_private_with_rfc5915_ext.pem"), Test::rng())); + + result.confirm("loaded RFC 5915 key", pkcs8.get()); + result.test_eq("key is ECDSA", pkcs8->algo_name(), "ECDSA"); + result.confirm("key type is ECDSA", dynamic_cast<Botan::ECDSA_PrivateKey*>(pkcs8.get())); + } + catch(std::exception& e) + { + result.test_failure("load_rfc5915_ext", e.what()); + } + + return result; + } + +Test::Result test_ecc_key_with_rfc5915_parameters() + { + Test::Result result("ECDSA Unit"); + + try + { + std::unique_ptr<Botan::Private_Key> pkcs8( + Botan::PKCS8::load_key(Test::data_file("x509/ecc/ecc_private_with_rfc5915_parameters.pem"), Test::rng())); + result.confirm("loaded RFC 5915 key", pkcs8.get()); + result.test_eq("key is ECDSA", pkcs8->algo_name(), "ECDSA"); + result.confirm("key type is ECDSA", dynamic_cast<Botan::ECDSA_PrivateKey*>(pkcs8.get())); + } + catch(std::exception& e) + { + result.test_failure("load_rfc5915_params", e.what()); + } + + return result; + } + +#endif Test::Result test_curve_registry() { @@ -364,49 +408,6 @@ Test::Result test_curve_registry() return result; } -Test::Result test_ecc_key_with_rfc5915_extensions() - { - Test::Result result("ECDSA Unit"); - - try - { - std::unique_ptr<Botan::Private_Key> pkcs8( - Botan::PKCS8::load_key(Test::data_file("x509/ecc/ecc_private_with_rfc5915_ext.pem"), Test::rng())); - - result.confirm("loaded RFC 5915 key", pkcs8.get()); - result.test_eq("key is ECDSA", pkcs8->algo_name(), "ECDSA"); - result.confirm("key type is ECDSA", dynamic_cast<Botan::ECDSA_PrivateKey*>(pkcs8.get())); - } - catch(std::exception& e) - { - result.test_failure("load_rfc5915_ext", e.what()); - } - - return result; - } - -Test::Result test_ecc_key_with_rfc5915_parameters() - { - Test::Result result("ECDSA Unit"); - - try - { - std::unique_ptr<Botan::Private_Key> pkcs8( - Botan::PKCS8::load_key(Test::data_file("x509/ecc/ecc_private_with_rfc5915_parameters.pem"), Test::rng())); - - result.confirm("loaded RFC 5915 key", pkcs8.get()); - result.test_eq("key is ECDSA", pkcs8->algo_name(), "ECDSA"); - result.confirm("key type is ECDSA", dynamic_cast<Botan::ECDSA_PrivateKey*>(pkcs8.get())); - } - catch(std::exception& e) - { - result.test_failure("load_rfc5915_params", e.what()); - } - - return result; - } - - class ECDSA_Unit_Tests final : public Test { @@ -414,20 +415,26 @@ class ECDSA_Unit_Tests final : public Test std::vector<Test::Result> run() override { std::vector<Test::Result> results; - results.push_back(test_hash_larger_than_n()); + +#if defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) + results.push_back(test_read_pkcs8()); + results.push_back(test_ecc_key_with_rfc5915_extensions()); + results.push_back(test_ecc_key_with_rfc5915_parameters()); + #if defined(BOTAN_HAS_X509_CERTIFICATES) results.push_back(test_decode_ecdsa_X509()); results.push_back(test_decode_ver_link_SHA256()); results.push_back(test_decode_ver_link_SHA1()); #endif + +#endif + + results.push_back(test_hash_larger_than_n()); results.push_back(test_sign_then_ver()); results.push_back(test_ec_sign()); - results.push_back(test_read_pkcs8()); results.push_back(test_ecdsa_create_save_load()); results.push_back(test_unusual_curve()); results.push_back(test_curve_registry()); - results.push_back(test_ecc_key_with_rfc5915_extensions()); - results.push_back(test_ecc_key_with_rfc5915_parameters()); return results; } }; diff --git a/src/tests/unit_x509.cpp b/src/tests/unit_x509.cpp index 0aa9d0209..5e787d72d 100644 --- a/src/tests/unit_x509.cpp +++ b/src/tests/unit_x509.cpp @@ -372,6 +372,8 @@ Test::Result test_x509_dates() return result; } +#if defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) + Test::Result test_crl_dn_name() { Test::Result result("CRL DN name"); @@ -398,6 +400,24 @@ Test::Result test_crl_dn_name() return result; } +Test::Result test_x509_decode_list() + { + Test::Result result("X509_Certificate list decode"); + + Botan::DataSource_Stream input(Test::data_file("x509/misc/cert_seq.der"), true); + + Botan::BER_Decoder dec(input); + std::vector<Botan::X509_Certificate> certs; + dec.decode_list(certs); + + result.test_eq("Expected number of certs in list", certs.size(), 2); + + result.test_eq("Expected cert 1 CN", certs[0].subject_dn().get_first_attribute("CN"), "CA1-PP.01.02"); + result.test_eq("Expected cert 2 CN", certs[1].subject_dn().get_first_attribute("CN"), "User1-PP.01.02"); + + return result; + } + Test::Result test_x509_utf8() { Test::Result result("X509 with UTF-8 encoded fields"); @@ -503,6 +523,100 @@ Test::Result test_x509_authority_info_access_extension() return result; } +/* + * @brief checks the configurability of the EMSA4(RSA-PSS) signature scheme + * + * For the other algorithms than RSA, only one padding is supported right now. + */ +Test::Result test_padding_config() { + // Throughout the test, some synonyms for EMSA4 are used, e.g. PSSR, EMSA-PSS + Test::Result test_result("X509 Padding Config"); + + std::unique_ptr<Botan::Private_Key> sk(Botan::PKCS8::load_key( + Test::data_file("x509/misc/rsa_key.pem"), Test::rng())); + + // Create X509 CA certificate; EMSA3 is used for signing by default + Botan::X509_Cert_Options opt("TESTCA"); + opt.CA_key(); + Botan::X509_Certificate ca_cert_def = Botan::X509::create_self_signed_cert(opt, (*sk), "SHA-512", Test::rng()); + test_result.test_eq("CA certificate signature algorithm (default)", + Botan::OIDS::lookup(ca_cert_def.signature_algorithm().oid),"RSA/EMSA3(SHA-512)"); + + // Create X509 CA certificate; RSA-PSS is explicitly set + opt.set_padding_scheme("PSSR"); + Botan::X509_Certificate ca_cert_exp = Botan::X509::create_self_signed_cert(opt, (*sk), "SHA-512", Test::rng()); + test_result.test_eq("CA certificate signature algorithm (explicit)", + Botan::OIDS::lookup(ca_cert_exp.signature_algorithm().oid),"RSA/EMSA4"); + + // Try to set a padding scheme that is not supported for signing with the given key type + opt.set_padding_scheme("EMSA1"); + try + { + Botan::X509_Certificate ca_cert_wrong = Botan::X509::create_self_signed_cert(opt, (*sk), "SHA-512", Test::rng()); + test_result.test_failure("Could build CA certitiface with invalid encoding scheme EMSA1 for key type " + sk->algo_name()); + } + catch (const Botan::Invalid_Argument& e) + { + test_result.test_eq("Build CA certitiface with invalid encoding scheme EMSA1 for key type " + + sk->algo_name(), e.what(), + "Invalid argument Encoding scheme with canonical name EMSA1 not supported for signature algorithm RSA"); + } + test_result.test_eq("CA certificate signature algorithm (explicit)", + Botan::OIDS::lookup(ca_cert_exp.signature_algorithm().oid),"RSA/EMSA4"); + + const auto not_before = Botan::calendar_point(2017, 1, 1, 1, 1, 1).to_std_timepoint(); + const auto not_after = Botan::calendar_point(2037, 12, 25, 1, 1, 1).to_std_timepoint(); + + // Prepare a signing request for the end certificate + Botan::X509_Cert_Options req_opt("endpoint"); + req_opt.set_padding_scheme("EMSA4(SHA-512,MGF1,64)"); + Botan::PKCS10_Request end_req = Botan::X509::create_cert_req(req_opt, (*sk), "SHA-512", Test::rng()); + test_result.test_eq("Certificate request signature algorithm", Botan::OIDS::lookup(end_req.signature_algorithm().oid),"RSA/EMSA4"); + + // Create X509 CA object: will fail as the chosen hash functions differ + try + { + Botan::X509_CA ca_fail(ca_cert_exp, (*sk), {{"padding","EMSA4(SHA-256)"}},"SHA-512", Test::rng()); + test_result.test_failure("Configured conflicting hash functions for CA"); + } + catch(const Botan::Invalid_Argument& e) + { + test_result.test_eq("Configured conflicting hash functions for CA", + e.what(), + "Invalid argument Hash function from opts and hash_fn argument need to be identical"); + } + + // Create X509 CA object: its signer will use the padding scheme from the CA certificate, i.e. EMSA3 + Botan::X509_CA ca_def(ca_cert_def, (*sk), "SHA-512", Test::rng()); + Botan::X509_Certificate end_cert_emsa3 = ca_def.sign_request(end_req, Test::rng(), Botan::X509_Time(not_before), Botan::X509_Time(not_after)); + test_result.test_eq("End certificate signature algorithm", Botan::OIDS::lookup(end_cert_emsa3.signature_algorithm().oid), "RSA/EMSA3(SHA-512)"); + + // Create X509 CA object: its signer will use the explicitly configured padding scheme, which is different from the CA certificate's scheme + Botan::X509_CA ca_diff(ca_cert_def, (*sk), {{"padding","EMSA-PSS"}}, "SHA-512", Test::rng()); + Botan::X509_Certificate end_cert_diff_emsa4 = ca_diff.sign_request(end_req, Test::rng(), Botan::X509_Time(not_before), Botan::X509_Time(not_after)); + test_result.test_eq("End certificate signature algorithm", Botan::OIDS::lookup(end_cert_diff_emsa4.signature_algorithm().oid), "RSA/EMSA4"); + + // Create X509 CA object: its signer will use the explicitly configured padding scheme, which is identical to the CA certificate's scheme + Botan::X509_CA ca_exp(ca_cert_exp, (*sk), {{"padding","EMSA4(SHA-512,MGF1,64)"}},"SHA-512", Test::rng()); + Botan::X509_Certificate end_cert_emsa4= ca_exp.sign_request(end_req, Test::rng(), Botan::X509_Time(not_before), Botan::X509_Time(not_after)); + test_result.test_eq("End certificate signature algorithm", Botan::OIDS::lookup(end_cert_emsa4.signature_algorithm().oid), "RSA/EMSA4"); + + // Check CRL signature algorithm + Botan::X509_CRL crl = ca_exp.new_crl(Test::rng()); + test_result.test_eq("CRL signature algorithm", Botan::OIDS::lookup(crl.signature_algorithm().oid), "RSA/EMSA4"); + + // sanity check for verification, the heavy lifting is done in the other unit tests + const Botan::Certificate_Store_In_Memory trusted(ca_exp.ca_certificate()); + const Botan::Path_Validation_Restrictions restrictions(false, 80); + const Botan::Path_Validation_Result validation_result = Botan::x509_path_validate( + end_cert_emsa4, restrictions, trusted); + test_result.confirm("EMSA4-signed certificate validates", validation_result.successful_validation()); + + return test_result; +} + +#endif + Test::Result test_x509_cert(const std::string& sig_algo, const std::string& sig_padding = "", const std::string& hash_fn = "SHA-256") { Test::Result result("X509 Unit"); @@ -827,24 +941,6 @@ Test::Result test_x509_uninit() return result; } -Test::Result test_x509_decode_list() - { - Test::Result result("X509_Certificate list decode"); - - Botan::DataSource_Stream input(Test::data_file("x509/misc/cert_seq.der"), true); - - Botan::BER_Decoder dec(input); - std::vector<Botan::X509_Certificate> certs; - dec.decode_list(certs); - - result.test_eq("Expected number of certs in list", certs.size(), 2); - - result.test_eq("Expected cert 1 CN", certs[0].subject_dn().get_first_attribute("CN"), "CA1-PP.01.02"); - result.test_eq("Expected cert 2 CN", certs[1].subject_dn().get_first_attribute("CN"), "User1-PP.01.02"); - - return result; - } - using Botan::Key_Constraints; @@ -1266,98 +1362,6 @@ Test::Result test_hashes(const std::string& algo, const std::string& hash_fn = " return result; } -/* - * @brief checks the configurability of the EMSA4(RSA-PSS) signature scheme - * - * For the other algorithms than RSA, only one padding is supported right now. - */ -Test::Result test_padding_config() { - // Throughout the test, some synonyms for EMSA4 are used, e.g. PSSR, EMSA-PSS - Test::Result test_result("X509 Padding Config"); - - std::unique_ptr<Botan::Private_Key> sk(Botan::PKCS8::load_key( - Test::data_file("x509/misc/rsa_key.pem"), Test::rng())); - - // Create X509 CA certificate; EMSA3 is used for signing by default - Botan::X509_Cert_Options opt("TESTCA"); - opt.CA_key(); - Botan::X509_Certificate ca_cert_def = Botan::X509::create_self_signed_cert(opt, (*sk), "SHA-512", Test::rng()); - test_result.test_eq("CA certificate signature algorithm (default)", - Botan::OIDS::lookup(ca_cert_def.signature_algorithm().oid),"RSA/EMSA3(SHA-512)"); - - // Create X509 CA certificate; RSA-PSS is explicitly set - opt.set_padding_scheme("PSSR"); - Botan::X509_Certificate ca_cert_exp = Botan::X509::create_self_signed_cert(opt, (*sk), "SHA-512", Test::rng()); - test_result.test_eq("CA certificate signature algorithm (explicit)", - Botan::OIDS::lookup(ca_cert_exp.signature_algorithm().oid),"RSA/EMSA4"); - - // Try to set a padding scheme that is not supported for signing with the given key type - opt.set_padding_scheme("EMSA1"); - try - { - Botan::X509_Certificate ca_cert_wrong = Botan::X509::create_self_signed_cert(opt, (*sk), "SHA-512", Test::rng()); - test_result.test_failure("Could build CA certitiface with invalid encoding scheme EMSA1 for key type " + sk->algo_name()); - } - catch (const Botan::Invalid_Argument& e) - { - test_result.test_eq("Build CA certitiface with invalid encoding scheme EMSA1 for key type " + - sk->algo_name(), e.what(), - "Invalid argument Encoding scheme with canonical name EMSA1 not supported for signature algorithm RSA"); - } - test_result.test_eq("CA certificate signature algorithm (explicit)", - Botan::OIDS::lookup(ca_cert_exp.signature_algorithm().oid),"RSA/EMSA4"); - - const auto not_before = Botan::calendar_point(2017, 1, 1, 1, 1, 1).to_std_timepoint(); - const auto not_after = Botan::calendar_point(2037, 12, 25, 1, 1, 1).to_std_timepoint(); - - // Prepare a signing request for the end certificate - Botan::X509_Cert_Options req_opt("endpoint"); - req_opt.set_padding_scheme("EMSA4(SHA-512,MGF1,64)"); - Botan::PKCS10_Request end_req = Botan::X509::create_cert_req(req_opt, (*sk), "SHA-512", Test::rng()); - test_result.test_eq("Certificate request signature algorithm", Botan::OIDS::lookup(end_req.signature_algorithm().oid),"RSA/EMSA4"); - - // Create X509 CA object: will fail as the chosen hash functions differ - try - { - Botan::X509_CA ca_fail(ca_cert_exp, (*sk), {{"padding","EMSA4(SHA-256)"}},"SHA-512", Test::rng()); - test_result.test_failure("Configured conflicting hash functions for CA"); - } - catch(const Botan::Invalid_Argument& e) - { - test_result.test_eq("Configured conflicting hash functions for CA", - e.what(), - "Invalid argument Hash function from opts and hash_fn argument need to be identical"); - } - - // Create X509 CA object: its signer will use the padding scheme from the CA certificate, i.e. EMSA3 - Botan::X509_CA ca_def(ca_cert_def, (*sk), "SHA-512", Test::rng()); - Botan::X509_Certificate end_cert_emsa3 = ca_def.sign_request(end_req, Test::rng(), Botan::X509_Time(not_before), Botan::X509_Time(not_after)); - test_result.test_eq("End certificate signature algorithm", Botan::OIDS::lookup(end_cert_emsa3.signature_algorithm().oid), "RSA/EMSA3(SHA-512)"); - - // Create X509 CA object: its signer will use the explicitly configured padding scheme, which is different from the CA certificate's scheme - Botan::X509_CA ca_diff(ca_cert_def, (*sk), {{"padding","EMSA-PSS"}}, "SHA-512", Test::rng()); - Botan::X509_Certificate end_cert_diff_emsa4 = ca_diff.sign_request(end_req, Test::rng(), Botan::X509_Time(not_before), Botan::X509_Time(not_after)); - test_result.test_eq("End certificate signature algorithm", Botan::OIDS::lookup(end_cert_diff_emsa4.signature_algorithm().oid), "RSA/EMSA4"); - - // Create X509 CA object: its signer will use the explicitly configured padding scheme, which is identical to the CA certificate's scheme - Botan::X509_CA ca_exp(ca_cert_exp, (*sk), {{"padding","EMSA4(SHA-512,MGF1,64)"}},"SHA-512", Test::rng()); - Botan::X509_Certificate end_cert_emsa4= ca_exp.sign_request(end_req, Test::rng(), Botan::X509_Time(not_before), Botan::X509_Time(not_after)); - test_result.test_eq("End certificate signature algorithm", Botan::OIDS::lookup(end_cert_emsa4.signature_algorithm().oid), "RSA/EMSA4"); - - // Check CRL signature algorithm - Botan::X509_CRL crl = ca_exp.new_crl(Test::rng()); - test_result.test_eq("CRL signature algorithm", Botan::OIDS::lookup(crl.signature_algorithm().oid), "RSA/EMSA4"); - - // sanity check for verification, the heavy lifting is done in the other unit tests - const Botan::Certificate_Store_In_Memory trusted(ca_exp.ca_certificate()); - const Botan::Path_Validation_Restrictions restrictions(false, 80); - const Botan::Path_Validation_Result validation_result = Botan::x509_path_validate( - end_cert_emsa4, restrictions, trusted); - test_result.confirm("EMSA4-signed certificate validates", validation_result.successful_validation()); - - return test_result; -} - class X509_Cert_Unit_Tests final : public Test { public: @@ -1425,6 +1429,7 @@ class X509_Cert_Unit_Tests final : public Test results.push_back(self_issued_result); results.push_back(extensions_result); +#if defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) Test::Result pad_config_result("X509 Padding Config"); try { @@ -1435,6 +1440,7 @@ class X509_Cert_Unit_Tests final : public Test pad_config_result.test_failure("test_padding_config", e.what()); } results.push_back(pad_config_result); +#endif const std::vector<std::string> pk_algos { @@ -1453,16 +1459,19 @@ class X509_Cert_Unit_Tests final : public Test valid_constraints_result.merge(test_valid_constraints(algo)); } - results.push_back(valid_constraints_result); - results.push_back(test_x509_dates()); - results.push_back(test_cert_status_strings()); - results.push_back(test_hashes("ECDSA")); +#if defined(BOTAN_TARGET_OS_HAS_FILESYSTEM) results.push_back(test_x509_utf8()); results.push_back(test_x509_bmpstring()); results.push_back(test_crl_dn_name()); - results.push_back(test_x509_uninit()); results.push_back(test_x509_decode_list()); results.push_back(test_x509_authority_info_access_extension()); +#endif + + results.push_back(valid_constraints_result); + results.push_back(test_x509_dates()); + results.push_back(test_cert_status_strings()); + results.push_back(test_hashes("ECDSA")); + results.push_back(test_x509_uninit()); return results; } |