Botan 3.0.0
Crypto and TLS for C&
block_cipher.h
Go to the documentation of this file.
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 <string_view>
13#include <string>
14#include <memory>
15#include <vector>
16
17namespace Botan {
18
19/**
20* This class represents a block cipher object.
21*/
23 {
24 public:
25
26 /**
27 * Create an instance based on a name
28 * If provider is empty then best available is chosen.
29 * @param algo_spec algorithm name
30 * @param provider provider implementation to choose
31 * @return a null pointer if the algo/provider combination cannot be found
32 */
33 static std::unique_ptr<BlockCipher>
34 create(std::string_view algo_spec,
35 std::string_view provider = "");
36
37 /**
38 * Create an instance based on a name, or throw if the
39 * algo/provider combination cannot be found. If provider is
40 * empty then best available is chosen.
41 */
42 static std::unique_ptr<BlockCipher>
43 create_or_throw(std::string_view algo_spec,
44 std::string_view provider = "");
45
46 /**
47 * @return list of available providers for this algorithm, empty if not available
48 * @param algo_spec algorithm name
49 */
50 static std::vector<std::string> providers(std::string_view algo_spec);
51
52 /**
53 * @return block size of this algorithm
54 */
55 virtual size_t block_size() const = 0;
56
57 /**
58 * @return native parallelism of this cipher in blocks
59 */
60 virtual size_t parallelism() const { return 1; }
61
62 /**
63 * @return prefererred parallelism of this cipher in bytes
64 */
65 size_t parallel_bytes() const
66 {
67 return parallelism() * block_size() * BOTAN_BLOCK_CIPHER_PAR_MULT;
68 }
69
70 /**
71 * @return provider information about this implementation. Default is "base",
72 * might also return "sse2", "avx2", "openssl", or some other arbitrary string.
73 */
74 virtual std::string provider() const { return "base"; }
75
76 /**
77 * Encrypt a block.
78 * @param in The plaintext block to be encrypted as a byte array.
79 * Must be of length block_size().
80 * @param out The byte array designated to hold the encrypted block.
81 * Must be of length block_size().
82 */
83 void encrypt(const uint8_t in[], uint8_t out[]) const
84 { encrypt_n(in, out, 1); }
85
86 /**
87 * Decrypt a block.
88 * @param in The ciphertext block to be decypted as a byte array.
89 * Must be of length block_size().
90 * @param out The byte array designated to hold the decrypted block.
91 * Must be of length block_size().
92 */
93 void decrypt(const uint8_t in[], uint8_t out[]) const
94 { decrypt_n(in, out, 1); }
95
96 /**
97 * Encrypt a block.
98 * @param block the plaintext block to be encrypted
99 * Must be of length block_size(). Will hold the result when the function
100 * has finished.
101 */
102 void encrypt(uint8_t block[]) const { encrypt_n(block, block, 1); }
103
104 /**
105 * Decrypt a block.
106 * @param block the ciphertext block to be decrypted
107 * Must be of length block_size(). Will hold the result when the function
108 * has finished.
109 */
110 void decrypt(uint8_t block[]) const { decrypt_n(block, block, 1); }
111
112 /**
113 * Encrypt one or more blocks
114 * @param block the input/output buffer (multiple of block_size())
115 */
116 void encrypt(std::span<uint8_t> block) const
117 {
118 return encrypt_n(block.data(), block.data(), block.size() / block_size());
119 }
120
121 /**
122 * Decrypt one or more blocks
123 * @param block the input/output buffer (multiple of block_size())
124 */
125 void decrypt(std::span<uint8_t> block) const
126 {
127 return decrypt_n(block.data(), block.data(), block.size() / block_size());
128 }
129
130 /**
131 * Encrypt one or more blocks
132 * @param in the input buffer (multiple of block_size())
133 * @param out the output buffer (same size as in)
134 */
135 void encrypt(std::span<const uint8_t> in, std::span<uint8_t> out) const
136 {
137 return encrypt_n(in.data(), out.data(), in.size() / block_size());
138 }
139
140 /**
141 * Decrypt one or more blocks
142 * @param in the input buffer (multiple of block_size())
143 * @param out the output buffer (same size as in)
144 */
145 void decrypt(std::span<const uint8_t> in, std::span<uint8_t> out) const
146 {
147 return decrypt_n(in.data(), out.data(), in.size() / block_size());
148 }
149
150 /**
151 * Encrypt one or more blocks
152 * @param in the input buffer (multiple of block_size())
153 * @param out the output buffer (same size as in)
154 * @param blocks the number of blocks to process
155 */
156 virtual void encrypt_n(const uint8_t in[], uint8_t out[],
157 size_t blocks) const = 0;
158
159 /**
160 * Decrypt one or more blocks
161 * @param in the input buffer (multiple of block_size())
162 * @param out the output buffer (same size as in)
163 * @param blocks the number of blocks to process
164 */
165 virtual void decrypt_n(const uint8_t in[], uint8_t out[],
166 size_t blocks) const = 0;
167
168 virtual void encrypt_n_xex(uint8_t data[],
169 const uint8_t mask[],
170 size_t blocks) const
171 {
172 const size_t BS = block_size();
173 xor_buf(data, mask, blocks * BS);
174 encrypt_n(data, data, blocks);
175 xor_buf(data, mask, blocks * BS);
176 }
177
178 virtual void decrypt_n_xex(uint8_t data[],
179 const uint8_t mask[],
180 size_t blocks) const
181 {
182 const size_t BS = block_size();
183 xor_buf(data, mask, blocks * BS);
184 decrypt_n(data, data, blocks);
185 xor_buf(data, mask, blocks * BS);
186 }
187
188 /**
189 * @return new object representing the same algorithm as *this
190 */
191 virtual std::unique_ptr<BlockCipher> new_object() const = 0;
192
194 {
195 return this->new_object().release();
196 }
197
198 virtual ~BlockCipher() = default;
199 };
200
201/**
202* Tweakable block ciphers allow setting a tweak which is a non-keyed
203* value which affects the encryption/decryption operation.
204*/
206 {
207 public:
208 /**
209 * Set the tweak value. This must be called after setting a key. The value
210 * persists until either set_tweak, set_key, or clear is called.
211 * Different algorithms support different tweak length(s). If called with
212 * an unsupported length, Invalid_Argument will be thrown.
213 */
214 virtual void set_tweak(const uint8_t tweak[], size_t len) = 0;
215 };
216
217/**
218* Represents a block cipher with a single fixed block size
219*/
220template<size_t BS, size_t KMIN, size_t KMAX = 0, size_t KMOD = 1, typename BaseClass = BlockCipher>
221class Block_Cipher_Fixed_Params : public BaseClass
222 {
223 public:
224 enum { BLOCK_SIZE = BS };
225 size_t block_size() const final override { return BS; }
226
227 // override to take advantage of compile time constant block size
228 void encrypt_n_xex(uint8_t data[],
229 const uint8_t mask[],
230 size_t blocks) const final override
231 {
232 xor_buf(data, mask, blocks * BS);
233 this->encrypt_n(data, data, blocks);
234 xor_buf(data, mask, blocks * BS);
235 }
236
237 void decrypt_n_xex(uint8_t data[],
238 const uint8_t mask[],
239 size_t blocks) const final override
240 {
241 xor_buf(data, mask, blocks * BS);
242 this->decrypt_n(data, data, blocks);
243 xor_buf(data, mask, blocks * BS);
244 }
245
247 {
248 return Key_Length_Specification(KMIN, KMAX, KMOD);
249 }
250 };
251
252}
253
254#endif
void encrypt(const uint8_t in[], uint8_t out[]) const
Definition: block_cipher.h:83
void decrypt(const uint8_t in[], uint8_t out[]) const
Definition: block_cipher.h:93
void decrypt(std::span< uint8_t > block) const
Definition: block_cipher.h:125
void decrypt(std::span< const uint8_t > in, std::span< uint8_t > out) const
Definition: block_cipher.h:145
void encrypt(std::span< const uint8_t > in, std::span< uint8_t > out) const
Definition: block_cipher.h:135
virtual ~BlockCipher()=default
virtual void encrypt_n_xex(uint8_t data[], const uint8_t mask[], size_t blocks) const
Definition: block_cipher.h:168
void encrypt(std::span< uint8_t > block) const
Definition: block_cipher.h:116
virtual void decrypt_n(const uint8_t in[], uint8_t out[], size_t blocks) const =0
virtual void decrypt_n_xex(uint8_t data[], const uint8_t mask[], size_t blocks) const
Definition: block_cipher.h:178
virtual void encrypt_n(const uint8_t in[], uint8_t out[], size_t blocks) const =0
BlockCipher * clone() const
Definition: block_cipher.h:193
virtual std::unique_ptr< BlockCipher > new_object() const =0
virtual size_t block_size() const =0
virtual size_t parallelism() const
Definition: block_cipher.h:60
void decrypt(uint8_t block[]) const
Definition: block_cipher.h:110
virtual std::string provider() const
Definition: block_cipher.h:74
size_t parallel_bytes() const
Definition: block_cipher.h:65
void encrypt(uint8_t block[]) const
Definition: block_cipher.h:102
Key_Length_Specification key_spec() const final override
Definition: block_cipher.h:246
void encrypt_n_xex(uint8_t data[], const uint8_t mask[], size_t blocks) const final override
Definition: block_cipher.h:228
size_t block_size() const final override
Definition: block_cipher.h:225
void decrypt_n_xex(uint8_t data[], const uint8_t mask[], size_t blocks) const final override
Definition: block_cipher.h:237
virtual void set_tweak(const uint8_t tweak[], size_t len)=0
int(* final)(unsigned char *, CTX *)
#define BOTAN_PUBLIC_API(maj, min)
Definition: compiler.h:31
#define BOTAN_BLOCK_CIPHER_PAR_MULT
Definition: build.h:420
Definition: alg_id.cpp:12
void xor_buf(uint8_t out[], const uint8_t in[], size_t length)
Definition: mem_ops.h:255