1 /**
2  * \file chachapoly.h
3  *
4  * \brief   This file contains the AEAD-ChaCha20-Poly1305 definitions and
5  *          functions.
6  *
7  *          ChaCha20-Poly1305 is an algorithm for Authenticated Encryption
8  *          with Associated Data (AEAD) that can be used to encrypt and
9  *          authenticate data. It is based on ChaCha20 and Poly1305 by Daniel
10  *          Bernstein and was standardized in RFC 7539.
11  *
12  * \author Daniel King <damaki.gh@gmail.com>
13  */
14 
15 /*
16  *  Copyright The Mbed TLS Contributors
17  *  SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
18  *
19  *  This file is provided under the Apache License 2.0, or the
20  *  GNU General Public License v2.0 or later.
21  *
22  *  **********
23  *  Apache License 2.0:
24  *
25  *  Licensed under the Apache License, Version 2.0 (the "License"); you may
26  *  not use this file except in compliance with the License.
27  *  You may obtain a copy of the License at
28  *
29  *  http://www.apache.org/licenses/LICENSE-2.0
30  *
31  *  Unless required by applicable law or agreed to in writing, software
32  *  distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
33  *  WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
34  *  See the License for the specific language governing permissions and
35  *  limitations under the License.
36  *
37  *  **********
38  *
39  *  **********
40  *  GNU General Public License v2.0 or later:
41  *
42  *  This program is free software; you can redistribute it and/or modify
43  *  it under the terms of the GNU General Public License as published by
44  *  the Free Software Foundation; either version 2 of the License, or
45  *  (at your option) any later version.
46  *
47  *  This program is distributed in the hope that it will be useful,
48  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
49  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
50  *  GNU General Public License for more details.
51  *
52  *  You should have received a copy of the GNU General Public License along
53  *  with this program; if not, write to the Free Software Foundation, Inc.,
54  *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
55  *
56  *  **********
57  */
58 
59 #ifndef MBEDTLS_CHACHAPOLY_H
60 #define MBEDTLS_CHACHAPOLY_H
61 
62 #if !defined(MBEDTLS_CONFIG_FILE)
63 #include "config.h"
64 #else
65 #include MBEDTLS_CONFIG_FILE
66 #endif
67 
68 /* for shared error codes */
69 #include "poly1305.h"
70 
71 #define MBEDTLS_ERR_CHACHAPOLY_BAD_STATE            -0x0054 /**< The requested operation is not permitted in the current state. */
72 #define MBEDTLS_ERR_CHACHAPOLY_AUTH_FAILED          -0x0056 /**< Authenticated decryption failed: data was not authentic. */
73 
74 #ifdef __cplusplus
75 extern "C" {
76 #endif
77 
78 typedef enum
79 {
80     MBEDTLS_CHACHAPOLY_ENCRYPT,     /**< The mode value for performing encryption. */
81     MBEDTLS_CHACHAPOLY_DECRYPT      /**< The mode value for performing decryption. */
82 }
83 mbedtls_chachapoly_mode_t;
84 
85 #if !defined(MBEDTLS_CHACHAPOLY_ALT)
86 
87 #include "chacha20.h"
88 
89 typedef struct mbedtls_chachapoly_context
90 {
91     mbedtls_chacha20_context chacha20_ctx;  /**< The ChaCha20 context. */
92     mbedtls_poly1305_context poly1305_ctx;  /**< The Poly1305 context. */
93     uint64_t aad_len;                       /**< The length (bytes) of the Additional Authenticated Data. */
94     uint64_t ciphertext_len;                /**< The length (bytes) of the ciphertext. */
95     int state;                              /**< The current state of the context. */
96     mbedtls_chachapoly_mode_t mode;         /**< Cipher mode (encrypt or decrypt). */
97 }
98 mbedtls_chachapoly_context;
99 
100 #else /* !MBEDTLS_CHACHAPOLY_ALT */
101 #include "chachapoly_alt.h"
102 #endif /* !MBEDTLS_CHACHAPOLY_ALT */
103 
104 /**
105  * \brief           This function initializes the specified ChaCha20-Poly1305 context.
106  *
107  *                  It must be the first API called before using
108  *                  the context. It must be followed by a call to
109  *                  \c mbedtls_chachapoly_setkey() before any operation can be
110  *                  done, and to \c mbedtls_chachapoly_free() once all
111  *                  operations with that context have been finished.
112  *
113  *                  In order to encrypt or decrypt full messages at once, for
114  *                  each message you should make a single call to
115  *                  \c mbedtls_chachapoly_crypt_and_tag() or
116  *                  \c mbedtls_chachapoly_auth_decrypt().
117  *
118  *                  In order to encrypt messages piecewise, for each
119  *                  message you should make a call to
120  *                  \c mbedtls_chachapoly_starts(), then 0 or more calls to
121  *                  \c mbedtls_chachapoly_update_aad(), then 0 or more calls to
122  *                  \c mbedtls_chachapoly_update(), then one call to
123  *                  \c mbedtls_chachapoly_finish().
124  *
125  * \warning         Decryption with the piecewise API is discouraged! Always
126  *                  use \c mbedtls_chachapoly_auth_decrypt() when possible!
127  *
128  *                  If however this is not possible because the data is too
129  *                  large to fit in memory, you need to:
130  *
131  *                  - call \c mbedtls_chachapoly_starts() and (if needed)
132  *                  \c mbedtls_chachapoly_update_aad() as above,
133  *                  - call \c mbedtls_chachapoly_update() multiple times and
134  *                  ensure its output (the plaintext) is NOT used in any other
135  *                  way than placing it in temporary storage at this point,
136  *                  - call \c mbedtls_chachapoly_finish() to compute the
137  *                  authentication tag and compared it in constant time to the
138  *                  tag received with the ciphertext.
139  *
140  *                  If the tags are not equal, you must immediately discard
141  *                  all previous outputs of \c mbedtls_chachapoly_update(),
142  *                  otherwise you can now safely use the plaintext.
143  *
144  * \param ctx       The ChachaPoly context to initialize. Must not be \c NULL.
145  */
146 void mbedtls_chachapoly_init( mbedtls_chachapoly_context *ctx );
147 
148 /**
149  * \brief           This function releases and clears the specified
150  *                  ChaCha20-Poly1305 context.
151  *
152  * \param ctx       The ChachaPoly context to clear. This may be \c NULL, in which
153  *                  case this function is a no-op.
154  */
155 void mbedtls_chachapoly_free( mbedtls_chachapoly_context *ctx );
156 
157 /**
158  * \brief           This function sets the ChaCha20-Poly1305
159  *                  symmetric encryption key.
160  *
161  * \param ctx       The ChaCha20-Poly1305 context to which the key should be
162  *                  bound. This must be initialized.
163  * \param key       The \c 256 Bit (\c 32 Bytes) key.
164  *
165  * \return          \c 0 on success.
166  * \return          A negative error code on failure.
167  */
168 int mbedtls_chachapoly_setkey( mbedtls_chachapoly_context *ctx,
169                                const unsigned char key[32] );
170 
171 /**
172  * \brief           This function starts a ChaCha20-Poly1305 encryption or
173  *                  decryption operation.
174  *
175  * \warning         You must never use the same nonce twice with the same key.
176  *                  This would void any confidentiality and authenticity
177  *                  guarantees for the messages encrypted with the same nonce
178  *                  and key.
179  *
180  * \note            If the context is being used for AAD only (no data to
181  *                  encrypt or decrypt) then \p mode can be set to any value.
182  *
183  * \warning         Decryption with the piecewise API is discouraged, see the
184  *                  warning on \c mbedtls_chachapoly_init().
185  *
186  * \param ctx       The ChaCha20-Poly1305 context. This must be initialized
187  *                  and bound to a key.
188  * \param nonce     The nonce/IV to use for the message.
189  *                  This must be a redable buffer of length \c 12 Bytes.
190  * \param mode      The operation to perform: #MBEDTLS_CHACHAPOLY_ENCRYPT or
191  *                  #MBEDTLS_CHACHAPOLY_DECRYPT (discouraged, see warning).
192  *
193  * \return          \c 0 on success.
194  * \return          A negative error code on failure.
195  */
196 int mbedtls_chachapoly_starts( mbedtls_chachapoly_context *ctx,
197                                const unsigned char nonce[12],
198                                mbedtls_chachapoly_mode_t mode );
199 
200 /**
201  * \brief           This function feeds additional data to be authenticated
202  *                  into an ongoing ChaCha20-Poly1305 operation.
203  *
204  *                  The Additional Authenticated Data (AAD), also called
205  *                  Associated Data (AD) is only authenticated but not
206  *                  encrypted nor included in the encrypted output. It is
207  *                  usually transmitted separately from the ciphertext or
208  *                  computed locally by each party.
209  *
210  * \note            This function is called before data is encrypted/decrypted.
211  *                  I.e. call this function to process the AAD before calling
212  *                  \c mbedtls_chachapoly_update().
213  *
214  *                  You may call this function multiple times to process
215  *                  an arbitrary amount of AAD. It is permitted to call
216  *                  this function 0 times, if no AAD is used.
217  *
218  *                  This function cannot be called any more if data has
219  *                  been processed by \c mbedtls_chachapoly_update(),
220  *                  or if the context has been finished.
221  *
222  * \warning         Decryption with the piecewise API is discouraged, see the
223  *                  warning on \c mbedtls_chachapoly_init().
224  *
225  * \param ctx       The ChaCha20-Poly1305 context. This must be initialized
226  *                  and bound to a key.
227  * \param aad_len   The length in Bytes of the AAD. The length has no
228  *                  restrictions.
229  * \param aad       Buffer containing the AAD.
230  *                  This pointer can be \c NULL if `aad_len == 0`.
231  *
232  * \return          \c 0 on success.
233  * \return          #MBEDTLS_ERR_POLY1305_BAD_INPUT_DATA
234  *                  if \p ctx or \p aad are NULL.
235  * \return          #MBEDTLS_ERR_CHACHAPOLY_BAD_STATE
236  *                  if the operations has not been started or has been
237  *                  finished, or if the AAD has been finished.
238  */
239 int mbedtls_chachapoly_update_aad( mbedtls_chachapoly_context *ctx,
240                                    const unsigned char *aad,
241                                    size_t aad_len );
242 
243 /**
244  * \brief           Thus function feeds data to be encrypted or decrypted
245  *                  into an on-going ChaCha20-Poly1305
246  *                  operation.
247  *
248  *                  The direction (encryption or decryption) depends on the
249  *                  mode that was given when calling
250  *                  \c mbedtls_chachapoly_starts().
251  *
252  *                  You may call this function multiple times to process
253  *                  an arbitrary amount of data. It is permitted to call
254  *                  this function 0 times, if no data is to be encrypted
255  *                  or decrypted.
256  *
257  * \warning         Decryption with the piecewise API is discouraged, see the
258  *                  warning on \c mbedtls_chachapoly_init().
259  *
260  * \param ctx       The ChaCha20-Poly1305 context to use. This must be initialized.
261  * \param len       The length (in bytes) of the data to encrypt or decrypt.
262  * \param input     The buffer containing the data to encrypt or decrypt.
263  *                  This pointer can be \c NULL if `len == 0`.
264  * \param output    The buffer to where the encrypted or decrypted data is
265  *                  written. This must be able to hold \p len bytes.
266  *                  This pointer can be \c NULL if `len == 0`.
267  *
268  * \return          \c 0 on success.
269  * \return          #MBEDTLS_ERR_CHACHAPOLY_BAD_STATE
270  *                  if the operation has not been started or has been
271  *                  finished.
272  * \return          Another negative error code on other kinds of failure.
273  */
274 int mbedtls_chachapoly_update( mbedtls_chachapoly_context *ctx,
275                                size_t len,
276                                const unsigned char *input,
277                                unsigned char *output );
278 
279 /**
280  * \brief           This function finished the ChaCha20-Poly1305 operation and
281  *                  generates the MAC (authentication tag).
282  *
283  * \param ctx       The ChaCha20-Poly1305 context to use. This must be initialized.
284  * \param mac       The buffer to where the 128-bit (16 bytes) MAC is written.
285  *
286  * \warning         Decryption with the piecewise API is discouraged, see the
287  *                  warning on \c mbedtls_chachapoly_init().
288  *
289  * \return          \c 0 on success.
290  * \return          #MBEDTLS_ERR_CHACHAPOLY_BAD_STATE
291  *                  if the operation has not been started or has been
292  *                  finished.
293  * \return          Another negative error code on other kinds of failure.
294  */
295 int mbedtls_chachapoly_finish( mbedtls_chachapoly_context *ctx,
296                                unsigned char mac[16] );
297 
298 /**
299  * \brief           This function performs a complete ChaCha20-Poly1305
300  *                  authenticated encryption with the previously-set key.
301  *
302  * \note            Before using this function, you must set the key with
303  *                  \c mbedtls_chachapoly_setkey().
304  *
305  * \warning         You must never use the same nonce twice with the same key.
306  *                  This would void any confidentiality and authenticity
307  *                  guarantees for the messages encrypted with the same nonce
308  *                  and key.
309  *
310  * \param ctx       The ChaCha20-Poly1305 context to use (holds the key).
311  *                  This must be initialized.
312  * \param length    The length (in bytes) of the data to encrypt or decrypt.
313  * \param nonce     The 96-bit (12 bytes) nonce/IV to use.
314  * \param aad       The buffer containing the additional authenticated
315  *                  data (AAD). This pointer can be \c NULL if `aad_len == 0`.
316  * \param aad_len   The length (in bytes) of the AAD data to process.
317  * \param input     The buffer containing the data to encrypt or decrypt.
318  *                  This pointer can be \c NULL if `ilen == 0`.
319  * \param output    The buffer to where the encrypted or decrypted data
320  *                  is written. This pointer can be \c NULL if `ilen == 0`.
321  * \param tag       The buffer to where the computed 128-bit (16 bytes) MAC
322  *                  is written. This must not be \c NULL.
323  *
324  * \return          \c 0 on success.
325  * \return          A negative error code on failure.
326  */
327 int mbedtls_chachapoly_encrypt_and_tag( mbedtls_chachapoly_context *ctx,
328                                         size_t length,
329                                         const unsigned char nonce[12],
330                                         const unsigned char *aad,
331                                         size_t aad_len,
332                                         const unsigned char *input,
333                                         unsigned char *output,
334                                         unsigned char tag[16] );
335 
336 /**
337  * \brief           This function performs a complete ChaCha20-Poly1305
338  *                  authenticated decryption with the previously-set key.
339  *
340  * \note            Before using this function, you must set the key with
341  *                  \c mbedtls_chachapoly_setkey().
342  *
343  * \param ctx       The ChaCha20-Poly1305 context to use (holds the key).
344  * \param length    The length (in Bytes) of the data to decrypt.
345  * \param nonce     The \c 96 Bit (\c 12 bytes) nonce/IV to use.
346  * \param aad       The buffer containing the additional authenticated data (AAD).
347  *                  This pointer can be \c NULL if `aad_len == 0`.
348  * \param aad_len   The length (in bytes) of the AAD data to process.
349  * \param tag       The buffer holding the authentication tag.
350  *                  This must be a readable buffer of length \c 16 Bytes.
351  * \param input     The buffer containing the data to decrypt.
352  *                  This pointer can be \c NULL if `ilen == 0`.
353  * \param output    The buffer to where the decrypted data is written.
354  *                  This pointer can be \c NULL if `ilen == 0`.
355  *
356  * \return          \c 0 on success.
357  * \return          #MBEDTLS_ERR_CHACHAPOLY_AUTH_FAILED
358  *                  if the data was not authentic.
359  * \return          Another negative error code on other kinds of failure.
360  */
361 int mbedtls_chachapoly_auth_decrypt( mbedtls_chachapoly_context *ctx,
362                                      size_t length,
363                                      const unsigned char nonce[12],
364                                      const unsigned char *aad,
365                                      size_t aad_len,
366                                      const unsigned char tag[16],
367                                      const unsigned char *input,
368                                      unsigned char *output );
369 
370 #if defined(MBEDTLS_SELF_TEST)
371 /**
372  * \brief           The ChaCha20-Poly1305 checkup routine.
373  *
374  * \return          \c 0 on success.
375  * \return          \c 1 on failure.
376  */
377 int mbedtls_chachapoly_self_test( int verbose );
378 #endif /* MBEDTLS_SELF_TEST */
379 
380 #ifdef __cplusplus
381 }
382 #endif
383 
384 #endif /* MBEDTLS_CHACHAPOLY_H */
385