diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-07 17:32:43 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-04-07 17:32:43 +0000 |
commit | 6bf0a5cb5034a7e684dcc3500e841785237ce2dd (patch) | |
tree | a68f146d7fa01f0134297619fbe7e33db084e0aa /comm/third_party/botan/src/cli/encryption.cpp | |
parent | Initial commit. (diff) | |
download | thunderbird-upstream.tar.xz thunderbird-upstream.zip |
Adding upstream version 1:115.7.0.upstream/1%115.7.0upstream
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'comm/third_party/botan/src/cli/encryption.cpp')
-rw-r--r-- | comm/third_party/botan/src/cli/encryption.cpp | 127 |
1 files changed, 127 insertions, 0 deletions
diff --git a/comm/third_party/botan/src/cli/encryption.cpp b/comm/third_party/botan/src/cli/encryption.cpp new file mode 100644 index 0000000000..fa8de7cfdb --- /dev/null +++ b/comm/third_party/botan/src/cli/encryption.cpp @@ -0,0 +1,127 @@ +/* +* (C) 2015,2017 Simon Warta (Kullo GmbH) +* +* Botan is released under the Simplified BSD License (see license.txt) +*/ + +#include "cli.h" + +#if (defined(BOTAN_HAS_AES) || defined(BOTAN_HAS_AEAD_CHACHA20_POLY1305)) && defined(BOTAN_HAS_AEAD_MODES) + +#include <botan/aead.h> +#include <botan/hex.h> +#include <sstream> + +namespace Botan_CLI { + +namespace { + +auto VALID_MODES = std::map<std::string, std::string>{ + // Don't add algorithms here without extending tests + // in `src/scripts/test_cli_crypt.py` + { "aes-128-cfb", "AES-128/CFB" }, + { "aes-192-cfb", "AES-192/CFB" }, + { "aes-256-cfb", "AES-256/CFB" }, + { "aes-128-gcm", "AES-128/GCM" }, + { "aes-192-gcm", "AES-192/GCM" }, + { "aes-256-gcm", "AES-256/GCM" }, + { "aes-128-ocb", "AES-128/OCB" }, + { "aes-128-xts", "AES-128/XTS" }, + { "aes-256-xts", "AES-256/XTS" }, + { "chacha20poly1305", "ChaCha20Poly1305" }, +}; + +Botan::secure_vector<uint8_t> +do_crypt(const std::string &cipher, + const std::vector<uint8_t> &input, + const Botan::SymmetricKey &key, + const Botan::InitializationVector &iv, + const std::vector<uint8_t>& ad, + Botan::Cipher_Dir direction) + { + if(iv.size() == 0) + throw CLI_Usage_Error("IV must not be empty"); + + // TODO: implement streaming + + std::unique_ptr<Botan::Cipher_Mode> processor(Botan::Cipher_Mode::create(cipher, direction)); + if(!processor) + throw CLI_Error("Cipher algorithm not found"); + + // Set key + processor->set_key(key); + + if(Botan::AEAD_Mode* aead = dynamic_cast<Botan::AEAD_Mode*>(processor.get())) + { + aead->set_ad(ad); + } + else if(ad.size() != 0) + { + throw CLI_Usage_Error("Cannot specify associated data with non-AEAD mode"); + } + + // Set IV + processor->start(iv.bits_of()); + + Botan::secure_vector<uint8_t> buf(input.begin(), input.end()); + processor->finish(buf); + + return buf; + } + +} + +class Encryption final : public Command + { + public: + Encryption() : Command("encryption --buf-size=4096 --decrypt --mode= --key= --iv= --ad=") {} + + std::string group() const override + { + return "encryption"; + } + + std::string description() const override + { + return "Encrypt or decrypt a given file"; + } + + void go() override + { + std::string mode = get_arg_or("mode", ""); + if (!VALID_MODES.count(mode)) + { + std::ostringstream error; + error << "Invalid mode: '" << mode << "'\n" + << "valid modes are:"; + for (auto valid_mode : VALID_MODES) error << " " << valid_mode.first; + + throw CLI_Usage_Error(error.str()); + } + + const std::string key_hex = get_arg("key"); + const std::string iv_hex = get_arg("iv"); + const std::string ad_hex = get_arg_or("ad", ""); + const size_t buf_size = get_arg_sz("buf-size"); + + const std::vector<uint8_t> input = this->slurp_file("-", buf_size); + + if (verbose()) + { + error_output() << "Got " << input.size() << " bytes of input data.\n"; + } + + const Botan::SymmetricKey key(key_hex); + const Botan::InitializationVector iv(iv_hex); + const std::vector<uint8_t> ad = Botan::hex_decode(ad_hex); + + auto direction = flag_set("decrypt") ? Botan::Cipher_Dir::DECRYPTION : Botan::Cipher_Dir::ENCRYPTION; + write_output(do_crypt(VALID_MODES[mode], input, key, iv, ad, direction)); + } + }; + +BOTAN_REGISTER_COMMAND("encryption", Encryption); + +} + +#endif |