LCOV - code coverage report
Current view: top level - ballet/aes - fd_aes_gcm.h (source / functions) Hit Total Coverage
Test: cov.lcov Lines: 10 10 100.0 %
Date: 2024-11-13 11:58:15 Functions: 0 0 -

          Line data    Source code
       1             : #ifndef HEADER_fd_src_ballet_aes_fd_aes_gcm_h
       2             : #define HEADER_fd_src_ballet_aes_fd_aes_gcm_h
       3             : 
       4             : #include "../fd_ballet_base.h"
       5             : 
       6             : /* AES-GCM ************************************************************/
       7             : 
       8             : /* fd_aes_gcm are APIs for authenticated AES-GCM encryption of messages.
       9             :    Compatible with TLS 1.3 and QUIC.
      10             : 
      11             :    AES-GCM is an extension of the AES-CTR stream cipher, adding the
      12             :    ability to detect malicious tampering of the ciphertext.  (Henceforth
      13             :    referred to as 'authentication'.)   Additionally, can protect a
      14             :    variable-sz unencrypted 'additional data' blob.
      15             : 
      16             :    ### Optimization Notes
      17             : 
      18             :    Currently supports 'all-in-one' API only, wherein the entire plain-
      19             :    text is encrypted/decrypted in a single blocking call.  API may
      20             :    change in the future to support a batched 'multi block' API or
      21             :    streaming mode of operation.
      22             : 
      23             :    AES-GCM offers opportunity for processing of multiple AES blocks in
      24             :    parallel.  However, the computation of the auth tag is a sequential
      25             :    chain with depth of block count of message.  In QUIC, the max
      26             :    AES-GCM msg sz is limited by the packet MTU.  Thus, auth tag
      27             :    processing can still be vectorized by processing independent packets
      28             :    in parallel. */
      29             : 
      30             : /* Reference backend internals ****************************************/
      31             : 
      32             : #include "fd_aes_gcm_ref.h"
      33             : 
      34             : /* AES-NI backend internals *******************************************/
      35             : 
      36             : struct fd_aes_gcm_aesni_key {
      37             :   uchar key_enc[ 240 ];
      38             :   uchar key_dec[ 240 ];
      39             :   uint  key_sz; /* 16 */
      40             : };
      41             : typedef struct fd_aes_gcm_aesni_key fd_aes_gcm_aesni_key_t;
      42             : 
      43             : /* Do not change. These offsets are hardcoded in fd_aes_gcm_aesni.S. */
      44             : struct fd_aes_gcm_aesni_state {
      45             :   fd_aes_gcm_aesni_key_t key;
      46             :   uchar pad1[  12 ];
      47             :   uchar gcm [ 208 ];
      48             :   uchar iv  [  12 ];
      49             :   uchar pad2[  52 ];
      50             : };
      51             : typedef struct fd_aes_gcm_aesni_state fd_aes_gcm_aesni_t;
      52             : 
      53             : /* AVX10 backend internals ********************************************/
      54             : 
      55             : /* Do not change. These offsets are hardcoded in fd_aes_gcm_avx10.S. */
      56             : struct fd_aes_gcm_avx10_state {
      57             :   fd_aes_gcm_aesni_key_t key;
      58             :   uchar pad1[  28 ];
      59             :   uchar gcm [ 320 ];
      60             :   uchar iv  [  12 ];
      61             :   uchar pad2[  52 ];
      62             : };
      63             : typedef struct fd_aes_gcm_avx10_state fd_aes_gcm_avx10_t;
      64             : 
      65             : /* Backend selection **************************************************/
      66             : 
      67             : #if FD_HAS_AVX512 && FD_HAS_GFNI && FD_HAS_AESNI
      68             : #define FD_AES_GCM_IMPL 3 /* AVX10.1/512, VAES, VPCLMUL */
      69             : #elif FD_HAS_AVX && FD_HAS_AESNI
      70             : #define FD_AES_GCM_IMPL 2 /* AVX2, VAES */
      71             : #elif FD_HAS_AESNI
      72             : #define FD_AES_GCM_IMPL 1 /* AESNI */
      73             : #else
      74             : #define FD_AES_GCM_IMPL 0 /* Portable */
      75             : #endif
      76             : 
      77             : #if FD_AES_GCM_IMPL == 0
      78             : 
      79             :   typedef fd_aes_gcm_ref_t    fd_aes_gcm_t;
      80     8571387 :   #define fd_aes_128_gcm_init fd_aes_128_gcm_init_ref
      81     4416902 :   #define fd_aes_gcm_encrypt  fd_aes_gcm_encrypt_ref
      82     4154485 :   #define fd_aes_gcm_decrypt  fd_aes_gcm_decrypt_ref
      83             : 
      84             : #elif FD_AES_GCM_IMPL == 1
      85             : 
      86             :   typedef fd_aes_gcm_aesni_t  fd_aes_gcm_t;
      87             :   #define fd_aes_128_gcm_init fd_aes_128_gcm_init_aesni
      88             :   #define fd_aes_gcm_encrypt  fd_aes_gcm_encrypt_aesni
      89             :   #define fd_aes_gcm_decrypt  fd_aes_gcm_decrypt_aesni
      90             : 
      91             : #elif FD_AES_GCM_IMPL == 2
      92             : 
      93             :   typedef fd_aes_gcm_aesni_t  fd_aes_gcm_t;
      94    25719072 :   #define fd_aes_128_gcm_init fd_aes_128_gcm_init_avx2
      95    13094777 :   #define fd_aes_gcm_encrypt  fd_aes_gcm_encrypt_avx2
      96    12624295 :   #define fd_aes_gcm_decrypt  fd_aes_gcm_decrypt_avx2
      97             : 
      98             : #elif FD_AES_GCM_IMPL == 3
      99             : 
     100             :   typedef fd_aes_gcm_avx10_t  fd_aes_gcm_t;
     101    27328905 :   #define fd_aes_128_gcm_init fd_aes_128_gcm_init_avx10_512
     102    13901092 :   #define fd_aes_gcm_encrypt  fd_aes_gcm_encrypt_avx10_512
     103    13427813 :   #define fd_aes_gcm_decrypt  fd_aes_gcm_decrypt_avx10_512
     104             : 
     105             : #endif
     106             : 
     107             : /* Public API *********************************************************/
     108             : 
     109             : /* FD_AES_GCM_ALIGN: minimum alignment of fd_aes_gcm_t.
     110             :    Large enough to satisfy alignment requirements on all architectures. */
     111             : #define FD_AES_GCM_ALIGN (64UL)
     112             : 
     113             : #define FD_AES_GCM_TAG_SZ (16UL)
     114       72984 : #define FD_AES_GCM_IV_SZ  (12UL)
     115             : 
     116             : FD_PROTOTYPES_BEGIN
     117             : 
     118             : /* fd_aes_128_gcm_init initializes an fd_aes_gcm_t object for
     119             :    encrypt or decrypt use.  aes_gcm points to unused and uninitialized
     120             :    memory aligned to FD_AES_GCM_STATE_ALIGN with sizeof(fd_aes_gcm_t)
     121             :    bytes available. */
     122             : 
     123             : void
     124             : fd_aes_128_gcm_init( fd_aes_gcm_t * aes_gcm,
     125             :                      uchar const    key[ 16 ],
     126             :                      uchar const    iv [ 12 ] );
     127             : 
     128             : /* fd_aes_gcm_aead_{encrypt,decrypt} implements the AES-GCM AEAD cipher
     129             :    c points to the ciphertext buffer.  p points to the plaintext buffer.
     130             :    sz is the length of the p and c buffers.  p,c,sz do not have align-
     131             :    ment requirements.  iv points to the 12 byte initialization vector.
     132             :    aad points to the 'associated data' buffer (with size aad_sz).  tag
     133             :    points to the 16 byte authentication tag (written by both decrypt and
     134             :    encrypt).
     135             : 
     136             :    (AAD serves to mix in arbitrary additional data into the auth tag,
     137             :    such that tampering with the AAD results in a decryption failure)
     138             : 
     139             :    fd_aes_gcm_encrypt reads plaintext from p, writes ciphertext to
     140             :    c, and writes the auth tag to 'tag'.  encrypt cannot fail.
     141             : 
     142             :    fd_aes_gcm_decrypt reads the expected auth tag and ciphertext,
     143             :    and writes the decrypted plaintext to p.  Ciphertext and auth tag are
     144             :    usually transmitted as-is over a network packet.  Returns 1 on
     145             :    success, or 0 on failure.  Reasons for failure include:  Corrupt
     146             :    ciphertext, corrupt sz, corrupt AAD, or corrupt tag (could be due to
     147             :    network corruption or malicious tampering). */
     148             : 
     149             : void
     150             : fd_aes_gcm_encrypt( fd_aes_gcm_t * aes_gcm,
     151             :                     uchar *        c,
     152             :                     uchar const *  p,
     153             :                     ulong          sz,
     154             :                     uchar const *  aad,
     155             :                     ulong          aad_sz,
     156             :                     uchar          tag[ 16 ] );
     157             : 
     158             : int
     159             : fd_aes_gcm_decrypt( fd_aes_gcm_t * aes_gcm,
     160             :                     uchar const *  c,
     161             :                     uchar *        p,
     162             :                     ulong          sz,
     163             :                     uchar const *  aad,
     164             :                     ulong          aad_sz,
     165             :                     uchar const    tag[ 16 ] );
     166             : 
     167             : #define FD_AES_GCM_DECRYPT_FAIL (0)
     168             : #define FD_AES_GCM_DECRYPT_OK   (1)
     169             : 
     170             : FD_PROTOTYPES_END
     171             : 
     172             : #endif /* HEADER_fd_src_ballet_aes_fd_aes_gcm_h */

Generated by: LCOV version 1.14