Home | History | Annotate | Download | only in gcm
      1 /* LibTomCrypt, modular cryptographic library -- Tom St Denis
      2  *
      3  * LibTomCrypt is a library that provides various cryptographic
      4  * algorithms in a highly modular and flexible manner.
      5  *
      6  * The library is free for all purposes without any express
      7  * guarantee it works.
      8  *
      9  * Tom St Denis, tomstdenis (at) gmail.com, http://libtomcrypt.com
     10  */
     11 
     12 /**
     13    @file gcm_add_aad.c
     14    GCM implementation, Add AAD data to the stream, by Tom St Denis
     15 */
     16 #include "tomcrypt.h"
     17 
     18 #ifdef GCM_MODE
     19 
     20 /**
     21   Add AAD to the GCM state
     22   @param gcm       The GCM state
     23   @param adata     The additional authentication data to add to the GCM state
     24   @param adatalen  The length of the AAD data.
     25   @return CRYPT_OK on success
     26  */
     27 int gcm_add_aad(gcm_state *gcm,
     28                const unsigned char *adata,  unsigned long adatalen)
     29 {
     30    unsigned long x;
     31    int           err;
     32 #ifdef LTC_FAST
     33    unsigned long y;
     34 #endif
     35 
     36    LTC_ARGCHK(gcm    != NULL);
     37    if (adatalen > 0) {
     38       LTC_ARGCHK(adata  != NULL);
     39    }
     40 
     41    if (gcm->buflen > 16 || gcm->buflen < 0) {
     42       return CRYPT_INVALID_ARG;
     43    }
     44 
     45    if ((err = cipher_is_valid(gcm->cipher)) != CRYPT_OK) {
     46       return err;
     47    }
     48 
     49    /* in IV mode? */
     50    if (gcm->mode == GCM_MODE_IV) {
     51       /* let's process the IV */
     52       if (gcm->ivmode || gcm->buflen != 12) {
     53          for (x = 0; x < (unsigned long)gcm->buflen; x++) {
     54              gcm->X[x] ^= gcm->buf[x];
     55          }
     56          if (gcm->buflen) {
     57             gcm->totlen += gcm->buflen * CONST64(8);
     58             gcm_mult_h(gcm, gcm->X);
     59          }
     60 
     61          /* mix in the length */
     62          zeromem(gcm->buf, 8);
     63          STORE64H(gcm->totlen, gcm->buf+8);
     64          for (x = 0; x < 16; x++) {
     65              gcm->X[x] ^= gcm->buf[x];
     66          }
     67          gcm_mult_h(gcm, gcm->X);
     68 
     69          /* copy counter out */
     70          XMEMCPY(gcm->Y, gcm->X, 16);
     71          zeromem(gcm->X, 16);
     72       } else {
     73          XMEMCPY(gcm->Y, gcm->buf, 12);
     74          gcm->Y[12] = 0;
     75          gcm->Y[13] = 0;
     76          gcm->Y[14] = 0;
     77          gcm->Y[15] = 1;
     78       }
     79       XMEMCPY(gcm->Y_0, gcm->Y, 16);
     80       zeromem(gcm->buf, 16);
     81       gcm->buflen = 0;
     82       gcm->totlen = 0;
     83       gcm->mode   = GCM_MODE_AAD;
     84    }
     85 
     86    if (gcm->mode != GCM_MODE_AAD || gcm->buflen >= 16) {
     87       return CRYPT_INVALID_ARG;
     88    }
     89 
     90    x = 0;
     91 #ifdef LTC_FAST
     92    if (gcm->buflen == 0) {
     93       for (x = 0; x < (adatalen & ~15); x += 16) {
     94           for (y = 0; y < 16; y += sizeof(LTC_FAST_TYPE)) {
     95               *((LTC_FAST_TYPE*)(&gcm->X[y])) ^= *((LTC_FAST_TYPE*)(&adata[x + y]));
     96           }
     97           gcm_mult_h(gcm, gcm->X);
     98           gcm->totlen += 128;
     99       }
    100       adata += x;
    101    }
    102 #endif
    103 
    104 
    105    /* start adding AAD data to the state */
    106    for (; x < adatalen; x++) {
    107        gcm->X[gcm->buflen++] ^= *adata++;
    108 
    109        if (gcm->buflen == 16) {
    110          /* GF mult it */
    111          gcm_mult_h(gcm, gcm->X);
    112          gcm->buflen = 0;
    113          gcm->totlen += 128;
    114       }
    115    }
    116 
    117    return CRYPT_OK;
    118 }
    119 #endif
    120 
    121 
    122 /* $Source: /cvs/libtom/libtomcrypt/src/encauth/gcm/gcm_add_aad.c,v $ */
    123 /* $Revision: 1.16 $ */
    124 /* $Date: 2006/09/23 19:24:21 $ */
    125