/* * Block Ciphers * (C) 2015 Jack Lloyd * * Botan is released under the Simplified BSD License (see license.txt) */ #include #include #include #if defined(BOTAN_HAS_AES) #include #endif #if defined(BOTAN_HAS_ARIA) #include #endif #if defined(BOTAN_HAS_BLOWFISH) #include #endif #if defined(BOTAN_HAS_CAMELLIA) #include #endif #if defined(BOTAN_HAS_CAST_128) #include #endif #if defined(BOTAN_HAS_CASCADE) #include #endif #if defined(BOTAN_HAS_DES) #include #endif #if defined(BOTAN_HAS_GOST_28147_89) #include #endif #if defined(BOTAN_HAS_IDEA) #include #endif #if defined(BOTAN_HAS_LION) #include #endif #if defined(BOTAN_HAS_NOEKEON) #include #endif #if defined(BOTAN_HAS_SEED) #include #endif #if defined(BOTAN_HAS_SERPENT) #include #endif #if defined(BOTAN_HAS_SHACAL2) #include #endif #if defined(BOTAN_HAS_SM4) #include #endif #if defined(BOTAN_HAS_TWOFISH) #include #endif #if defined(BOTAN_HAS_THREEFISH_512) #include #endif #if defined(BOTAN_HAS_OPENSSL) #include #endif #if defined(BOTAN_HAS_COMMONCRYPTO) #include #endif namespace Botan { std::unique_ptr BlockCipher::create(const std::string& algo, const std::string& provider) { #if defined(BOTAN_HAS_COMMONCRYPTO) if(provider.empty() || provider == "commoncrypto") { if(auto bc = make_commoncrypto_block_cipher(algo)) return bc; if(!provider.empty()) return nullptr; } #endif #if defined(BOTAN_HAS_OPENSSL) if(provider.empty() || provider == "openssl") { if(auto bc = make_openssl_block_cipher(algo)) return bc; if(!provider.empty()) return nullptr; } #endif // TODO: CryptoAPI // TODO: /dev/crypto // Only base providers from here on out if(provider.empty() == false && provider != "base") return nullptr; #if defined(BOTAN_HAS_AES) if(algo == "AES-128") { return std::unique_ptr(new AES_128); } if(algo == "AES-192") { return std::unique_ptr(new AES_192); } if(algo == "AES-256") { return std::unique_ptr(new AES_256); } #endif #if defined(BOTAN_HAS_ARIA) if(algo == "ARIA-128") { return std::unique_ptr(new ARIA_128); } if(algo == "ARIA-192") { return std::unique_ptr(new ARIA_192); } if(algo == "ARIA-256") { return std::unique_ptr(new ARIA_256); } #endif #if defined(BOTAN_HAS_SERPENT) if(algo == "Serpent") { return std::unique_ptr(new Serpent); } #endif #if defined(BOTAN_HAS_SHACAL2) if(algo == "SHACAL2") { return std::unique_ptr(new SHACAL2); } #endif #if defined(BOTAN_HAS_TWOFISH) if(algo == "Twofish") { return std::unique_ptr(new Twofish); } #endif #if defined(BOTAN_HAS_THREEFISH_512) if(algo == "Threefish-512") { return std::unique_ptr(new Threefish_512); } #endif #if defined(BOTAN_HAS_BLOWFISH) if(algo == "Blowfish") { return std::unique_ptr(new Blowfish); } #endif #if defined(BOTAN_HAS_CAMELLIA) if(algo == "Camellia-128") { return std::unique_ptr(new Camellia_128); } if(algo == "Camellia-192") { return std::unique_ptr(new Camellia_192); } if(algo == "Camellia-256") { return std::unique_ptr(new Camellia_256); } #endif #if defined(BOTAN_HAS_DES) if(algo == "DES") { return std::unique_ptr(new DES); } if(algo == "TripleDES" || algo == "3DES" || algo == "DES-EDE") { return std::unique_ptr(new TripleDES); } #endif #if defined(BOTAN_HAS_NOEKEON) if(algo == "Noekeon") { return std::unique_ptr(new Noekeon); } #endif #if defined(BOTAN_HAS_CAST_128) if(algo == "CAST-128" || algo == "CAST5") { return std::unique_ptr(new CAST_128); } #endif #if defined(BOTAN_HAS_IDEA) if(algo == "IDEA") { return std::unique_ptr(new IDEA); } #endif #if defined(BOTAN_HAS_SEED) if(algo == "SEED") { return std::unique_ptr(new SEED); } #endif #if defined(BOTAN_HAS_SM4) if(algo == "SM4") { return std::unique_ptr(new SM4); } #endif const SCAN_Name req(algo); #if defined(BOTAN_HAS_GOST_28147_89) if(req.algo_name() == "GOST-28147-89") { return std::unique_ptr(new GOST_28147_89(req.arg(0, "R3411_94_TestParam"))); } #endif #if defined(BOTAN_HAS_CASCADE) if(req.algo_name() == "Cascade" && req.arg_count() == 2) { std::unique_ptr c1(BlockCipher::create(req.arg(0))); std::unique_ptr c2(BlockCipher::create(req.arg(1))); if(c1 && c2) return std::unique_ptr(new Cascade_Cipher(c1.release(), c2.release())); } #endif #if defined(BOTAN_HAS_LION) if(req.algo_name() == "Lion" && req.arg_count_between(2, 3)) { std::unique_ptr hash(HashFunction::create(req.arg(0))); std::unique_ptr stream(StreamCipher::create(req.arg(1))); if(hash && stream) { const size_t block_size = req.arg_as_integer(2, 1024); return std::unique_ptr(new Lion(hash.release(), stream.release(), block_size)); } } #endif BOTAN_UNUSED(req); BOTAN_UNUSED(provider); return nullptr; } //static std::unique_ptr BlockCipher::create_or_throw(const std::string& algo, const std::string& provider) { if(auto bc = BlockCipher::create(algo, provider)) { return bc; } throw Lookup_Error("Block cipher", algo, provider); } std::vector BlockCipher::providers(const std::string& algo) { return probe_providers_of(algo, { "base", "openssl", "commoncrypto" }); } }