From 34aa73d0f9c3bf817a0a46889206003f0becd3f1 Mon Sep 17 00:00:00 2001 From: Marcus Brinkmann Date: Sat, 25 Nov 2017 20:22:57 +0100 Subject: Add create and create_or_throw factories for Compression_Algorithm and Decompression_Algorithm. --- src/lib/compression/compression.cpp | 39 +++++++++++++++++++++++++ src/lib/compression/compression.h | 32 ++++++++++++++++++++ src/tests/test_compression.cpp | 58 +++++++++++++++++++++++++++++++++++++ 3 files changed, 129 insertions(+) (limited to 'src') diff --git a/src/lib/compression/compression.cpp b/src/lib/compression/compression.cpp index ded6b3b08..361bf7dd3 100644 --- a/src/lib/compression/compression.cpp +++ b/src/lib/compression/compression.cpp @@ -7,6 +7,7 @@ #include #include +#include #include #if defined(BOTAN_HAS_ZLIB) @@ -48,6 +49,25 @@ Compression_Algorithm* make_compressor(const std::string& name) return nullptr; } +//static +std::unique_ptr +Compression_Algorithm::create(const std::string& algo) + { + std::unique_ptr compressor(make_compressor(algo)); + return compressor; + } + +//static +std::unique_ptr +Compression_Algorithm::create_or_throw(const std::string& algo) + { + if(auto compressor = Compression_Algorithm::create(algo)) + { + return compressor; + } + throw Lookup_Error("Compression", algo, ""); + } + Decompression_Algorithm* make_decompressor(const std::string& name) { #if defined(BOTAN_HAS_ZLIB) @@ -73,5 +93,24 @@ Decompression_Algorithm* make_decompressor(const std::string& name) return nullptr; } +//static +std::unique_ptr +Decompression_Algorithm::create(const std::string& algo) + { + std::unique_ptr decompressor(make_decompressor(algo)); + return decompressor; + } + +//static +std::unique_ptr +Decompression_Algorithm::create_or_throw(const std::string& algo) + { + if(auto decompressor = Decompression_Algorithm::create(algo)) + { + return decompressor; + } + throw Lookup_Error("Decompression", algo, ""); + } } + diff --git a/src/lib/compression/compression.h b/src/lib/compression/compression.h index 2ebde3f2f..403b335e1 100644 --- a/src/lib/compression/compression.h +++ b/src/lib/compression/compression.h @@ -19,6 +19,22 @@ namespace Botan { class BOTAN_PUBLIC_API(2,0) Compression_Algorithm { public: + /** + * Create an instance based on a name, or return null if the + * algo/provider combination cannot be found. If provider is + * empty then best available is chosen. + */ + static std::unique_ptr + create(const std::string& algo_spec); + + /** + * Create an instance based on a name + * @param algo_spec algorithm name + * Throws Lookup_Error if not not found. + */ + static std::unique_ptr + create_or_throw(const std::string& algo_spec); + /** * Begin compressing. Most compression algorithms offer a tunable * time/compression tradeoff parameter generally represented by @@ -65,6 +81,22 @@ class BOTAN_PUBLIC_API(2,0) Compression_Algorithm class BOTAN_PUBLIC_API(2,0) Decompression_Algorithm { public: + /** + * Create an instance based on a name, or return null if the + * algo/provider combination cannot be found. If provider is + * empty then best available is chosen. + */ + static std::unique_ptr + create(const std::string& algo_spec); + + /** + * Create an instance based on a name + * @param algo_spec algorithm name + * Throws Lookup_Error if not not found. + */ + static std::unique_ptr + create_or_throw(const std::string& algo_spec); + /** * Begin decompressing. * Decompression does not support levels, as compression does. diff --git a/src/tests/test_compression.cpp b/src/tests/test_compression.cpp index 04eb26200..d9045b23e 100644 --- a/src/tests/test_compression.cpp +++ b/src/tests/test_compression.cpp @@ -154,6 +154,64 @@ class Compression_Tests final : public Test BOTAN_REGISTER_TEST("compression", Compression_Tests); +class CompressionCreate_Tests final : public Test + { + public: + std::vector run() override + { + std::vector results; + + for(std::string algo : { "zlib", "deflate", "gzip", "bz2", "lzma" }) + { + try + { + Test::Result result(algo + " create compression"); + + std::unique_ptr c1(Botan::Compression_Algorithm::create(algo)); + std::unique_ptr d1(Botan::Decompression_Algorithm::create(algo)); + + if(!c1 || !d1) + { + result.note_missing(algo); + continue; + } + result.test_ne("Not the same name after create", c1->name(), d1->name()); + + std::unique_ptr c2(Botan::Compression_Algorithm::create_or_throw(algo)); + std::unique_ptr d2(Botan::Decompression_Algorithm::create_or_throw(algo)); + + if(!c2 || !d2) + { + result.note_missing(algo); + continue; + } + result.test_ne("Not the same name after create_or_throw", c2->name(), d2->name()); + + results.push_back(result); + } + catch(std::exception& e) + { + results.push_back(Test::Result::Failure("testing " + algo, e.what())); + } + } + + { + Test::Result result("create invalid compression"); + result.test_throws("lookup error", + "Unavailable Compression bogocompress", + [&]() { Botan::Compression_Algorithm::create_or_throw("bogocompress"); }); + result.test_throws("lookup error", + "Unavailable Decompression bogocompress", + [&]() { Botan::Decompression_Algorithm::create_or_throw("bogocompress"); }); + results.push_back(result); + } + + return results; + } + }; + +BOTAN_REGISTER_TEST("create_compression", CompressionCreate_Tests); + } #endif -- cgit v1.2.3