Coverage Report

Created: 2026-01-09 06:21

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/botan/build/include/public/botan/block_cipher.h
Line
Count
Source
1
/*
2
* Block Cipher Base Class
3
* (C) 1999-2009 Jack Lloyd
4
*
5
* Botan is released under the Simplified BSD License (see license.txt)
6
*/
7
8
#ifndef BOTAN_BLOCK_CIPHER_H_
9
#define BOTAN_BLOCK_CIPHER_H_
10
11
#include <botan/sym_algo.h>
12
#include <memory>
13
#include <string>
14
#include <string_view>
15
#include <vector>
16
17
namespace Botan {
18
19
/**
20
* This class represents a block cipher object.
21
*/
22
class BOTAN_PUBLIC_API(2, 0) BlockCipher : public SymmetricAlgorithm {
23
   public:
24
      /**
25
      * Create an instance based on a name
26
      * If provider is empty then best available is chosen.
27
      * @param algo_spec algorithm name
28
      * @param provider provider implementation to choose
29
      * @return a null pointer if the algo/provider combination cannot be found
30
      */
31
      static std::unique_ptr<BlockCipher> create(std::string_view algo_spec, std::string_view provider = "");
32
33
      /**
34
      * Create an instance based on a name, or throw if the
35
      * algo/provider combination cannot be found. If provider is
36
      * empty then best available is chosen.
37
      */
38
      static std::unique_ptr<BlockCipher> create_or_throw(std::string_view algo_spec, std::string_view provider = "");
39
40
      /**
41
      * @return list of available providers for this algorithm, empty if not available
42
      * @param algo_spec algorithm name
43
      */
44
      static std::vector<std::string> providers(std::string_view algo_spec);
45
46
      /**
47
      * Multiplier on a block cipher's native parallelism
48
      *
49
      * Usually notable performance gains come from further loop blocking,
50
      * at least for 2 or 4x
51
      */
52
      static constexpr size_t ParallelismMult = 4;
53
54
      /**
55
      * @return block size of this algorithm
56
      */
57
      virtual size_t block_size() const = 0;
58
59
      /**
60
      * @return native parallelism of this cipher in blocks
61
      */
62
1.06k
      virtual size_t parallelism() const { return 1; }
63
64
      /**
65
      * @return preferred parallelism of this cipher in bytes
66
      */
67
2.63k
      size_t parallel_bytes() const { return parallelism() * block_size() * BlockCipher::ParallelismMult; }
68
69
      /**
70
      * @return provider information about this implementation. Default is "base",
71
      * might also return "sse2", "avx2", "openssl", or some other arbitrary string.
72
      */
73
0
      virtual std::string provider() const { return "base"; }
74
75
      /**
76
      * Encrypt a block.
77
      * @param in The plaintext block to be encrypted as a byte array.
78
      * Must be of length block_size().
79
      * @param out The byte array designated to hold the encrypted block.
80
      * Must be of length block_size().
81
      */
82
33.6k
      void encrypt(const uint8_t in[], uint8_t out[]) const { encrypt_n(in, out, 1); }
83
84
      /**
85
      * Decrypt a block.
86
      * @param in The ciphertext block to be decrypted as a byte array.
87
      * Must be of length block_size().
88
      * @param out The byte array designated to hold the decrypted block.
89
      * Must be of length block_size().
90
      */
91
0
      void decrypt(const uint8_t in[], uint8_t out[]) const { decrypt_n(in, out, 1); }
92
93
      /**
94
      * Encrypt a block.
95
      * @param block the plaintext block to be encrypted
96
      * Must be of length block_size(). Will hold the result when the function
97
      * has finished.
98
      */
99
4.01k
      void encrypt(uint8_t block[]) const { encrypt_n(block, block, 1); }
100
101
      /**
102
      * Decrypt a block.
103
      * @param block the ciphertext block to be decrypted
104
      * Must be of length block_size(). Will hold the result when the function
105
      * has finished.
106
      */
107
0
      void decrypt(uint8_t block[]) const { decrypt_n(block, block, 1); }
108
109
      /**
110
      * Encrypt one or more blocks
111
      * @param block the input/output buffer (multiple of block_size())
112
      */
113
5.31k
      void encrypt(std::span<uint8_t> block) const {
114
5.31k
         return encrypt_n(block.data(), block.data(), block.size() / block_size());
115
5.31k
      }
116
117
      /**
118
      * Decrypt one or more blocks
119
      * @param block the input/output buffer (multiple of block_size())
120
      */
121
0
      void decrypt(std::span<uint8_t> block) const {
122
0
         return decrypt_n(block.data(), block.data(), block.size() / block_size());
123
0
      }
124
125
      /**
126
      * Encrypt one or more blocks
127
      * @param in the input buffer (multiple of block_size())
128
      * @param out the output buffer (same size as in)
129
      */
130
4.69k
      void encrypt(std::span<const uint8_t> in, std::span<uint8_t> out) const {
131
4.69k
         return encrypt_n(in.data(), out.data(), in.size() / block_size());
132
4.69k
      }
133
134
      /**
135
      * Decrypt one or more blocks
136
      * @param in the input buffer (multiple of block_size())
137
      * @param out the output buffer (same size as in)
138
      */
139
0
      void decrypt(std::span<const uint8_t> in, std::span<uint8_t> out) const {
140
0
         return decrypt_n(in.data(), out.data(), in.size() / block_size());
141
0
      }
142
143
      /**
144
      * Encrypt one or more blocks
145
      * @param in the input buffer (multiple of block_size())
146
      * @param out the output buffer (same size as in)
147
      * @param blocks the number of blocks to process
148
      */
149
      virtual void encrypt_n(const uint8_t in[], uint8_t out[], size_t blocks) const = 0;
150
151
      /**
152
      * Decrypt one or more blocks
153
      * @param in the input buffer (multiple of block_size())
154
      * @param out the output buffer (same size as in)
155
      * @param blocks the number of blocks to process
156
      */
157
      virtual void decrypt_n(const uint8_t in[], uint8_t out[], size_t blocks) const = 0;
158
159
      BOTAN_DEPRECATED("Deprecated no replacement")
160
0
      void encrypt_n_xex(uint8_t data[], const uint8_t mask[], size_t blocks) const {
161
0
         const size_t BS = block_size();
162
0
         for(size_t i = 0; i != blocks * BS; ++i) {
163
0
            data[i] ^= mask[i];
164
0
         }
165
0
         encrypt_n(data, data, blocks);
166
0
         for(size_t i = 0; i != blocks * BS; ++i) {
167
0
            data[i] ^= mask[i];
168
0
         }
169
0
      }
170
171
      BOTAN_DEPRECATED("Deprecated no replacement")
172
0
      void decrypt_n_xex(uint8_t data[], const uint8_t mask[], size_t blocks) const {
173
0
         const size_t BS = block_size();
174
0
         for(size_t i = 0; i != blocks * BS; ++i) {
175
0
            data[i] ^= mask[i];
176
0
         }
177
0
         decrypt_n(data, data, blocks);
178
0
         for(size_t i = 0; i != blocks * BS; ++i) {
179
0
            data[i] ^= mask[i];
180
0
         }
181
0
      }
182
183
      /**
184
      * @return new object representing the same algorithm as *this
185
      */
186
      virtual std::unique_ptr<BlockCipher> new_object() const = 0;
187
188
0
      BlockCipher* clone() const { return this->new_object().release(); }
189
};
190
191
/**
192
* Tweakable block ciphers allow setting a tweak which is a non-keyed
193
* value which affects the encryption/decryption operation.
194
*/
195
class BOTAN_PUBLIC_API(2, 8) Tweakable_Block_Cipher : public BlockCipher {
196
   public:
197
      /**
198
      * Set the tweak value. This must be called after setting a key. The value
199
      * persists until either set_tweak, set_key, or clear is called.
200
      * Different algorithms support different tweak length(s). If called with
201
      * an unsupported length, Invalid_Argument will be thrown.
202
      */
203
      virtual void set_tweak(const uint8_t tweak[], size_t len) = 0;
204
};
205
206
/**
207
* Represents a block cipher with a single fixed block size
208
*/
209
template <size_t BS, size_t KMIN, size_t KMAX = 0, size_t KMOD = 1, typename BaseClass = BlockCipher>
210
class Block_Cipher_Fixed_Params : public BaseClass {
211
   public:
212
      enum { BLOCK_SIZE = BS }; /* NOLINT(*-enum-size,*-use-enum-class) */
213
214
17.8k
      size_t block_size() const final { return BS; }
Botan::Block_Cipher_Fixed_Params<16ul, 16ul, 0ul, 1ul, Botan::BlockCipher>::block_size() const
Line
Count
Source
214
5.35k
      size_t block_size() const final { return BS; }
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<16ul, 24ul, 0ul, 1ul, Botan::BlockCipher>::block_size() const
Botan::Block_Cipher_Fixed_Params<16ul, 32ul, 0ul, 1ul, Botan::BlockCipher>::block_size() const
Line
Count
Source
214
11.3k
      size_t block_size() const final { return BS; }
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<8ul, 1ul, 56ul, 1ul, Botan::BlockCipher>::block_size() const
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<8ul, 11ul, 16ul, 1ul, Botan::BlockCipher>::block_size() const
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<8ul, 8ul, 0ul, 1ul, Botan::BlockCipher>::block_size() const
Botan::Block_Cipher_Fixed_Params<8ul, 16ul, 24ul, 8ul, Botan::BlockCipher>::block_size() const
Line
Count
Source
214
1.07k
      size_t block_size() const final { return BS; }
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<8ul, 16ul, 0ul, 1ul, Botan::BlockCipher>::block_size() const
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<16ul, 16ul, 32ul, 8ul, Botan::BlockCipher>::block_size() const
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<32ul, 16ul, 64ul, 4ul, Botan::BlockCipher>::block_size() const
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<64ul, 64ul, 0ul, 1ul, Botan::Tweakable_Block_Cipher>::block_size() const
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<8ul, 32ul, 0ul, 1ul, Botan::BlockCipher>::block_size() const
215
216
40.4k
      Key_Length_Specification key_spec() const final { return Key_Length_Specification(KMIN, KMAX, KMOD); }
Botan::Block_Cipher_Fixed_Params<16ul, 16ul, 0ul, 1ul, Botan::BlockCipher>::key_spec() const
Line
Count
Source
216
2.06k
      Key_Length_Specification key_spec() const final { return Key_Length_Specification(KMIN, KMAX, KMOD); }
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<16ul, 24ul, 0ul, 1ul, Botan::BlockCipher>::key_spec() const
Botan::Block_Cipher_Fixed_Params<16ul, 32ul, 0ul, 1ul, Botan::BlockCipher>::key_spec() const
Line
Count
Source
216
3.38k
      Key_Length_Specification key_spec() const final { return Key_Length_Specification(KMIN, KMAX, KMOD); }
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<8ul, 1ul, 56ul, 1ul, Botan::BlockCipher>::key_spec() const
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<8ul, 11ul, 16ul, 1ul, Botan::BlockCipher>::key_spec() const
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<8ul, 8ul, 0ul, 1ul, Botan::BlockCipher>::key_spec() const
Botan::Block_Cipher_Fixed_Params<8ul, 16ul, 24ul, 8ul, Botan::BlockCipher>::key_spec() const
Line
Count
Source
216
1.35k
      Key_Length_Specification key_spec() const final { return Key_Length_Specification(KMIN, KMAX, KMOD); }
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<8ul, 16ul, 0ul, 1ul, Botan::BlockCipher>::key_spec() const
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<16ul, 16ul, 32ul, 8ul, Botan::BlockCipher>::key_spec() const
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<32ul, 16ul, 64ul, 4ul, Botan::BlockCipher>::key_spec() const
Unexecuted instantiation: Botan::Block_Cipher_Fixed_Params<64ul, 64ul, 0ul, 1ul, Botan::Tweakable_Block_Cipher>::key_spec() const
Botan::Block_Cipher_Fixed_Params<8ul, 32ul, 0ul, 1ul, Botan::BlockCipher>::key_spec() const
Line
Count
Source
216
33.6k
      Key_Length_Specification key_spec() const final { return Key_Length_Specification(KMIN, KMAX, KMOD); }
217
};
218
219
}  // namespace Botan
220
221
#endif