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_done.c 14 GCM implementation, Terminate the stream, by Tom St Denis 15 */ 16 #include "tomcrypt.h" 17 18 #ifdef GCM_MODE 19 20 /** 21 Terminate a GCM stream 22 @param gcm The GCM state 23 @param tag [out] The destination for the MAC tag 24 @param taglen [in/out] The length of the MAC tag 25 @return CRYPT_OK on success 26 */ 27 int gcm_done(gcm_state *gcm, 28 unsigned char *tag, unsigned long *taglen) 29 { 30 unsigned long x; 31 int err; 32 33 LTC_ARGCHK(gcm != NULL); 34 LTC_ARGCHK(tag != NULL); 35 LTC_ARGCHK(taglen != NULL); 36 37 if (gcm->buflen > 16 || gcm->buflen < 0) { 38 return CRYPT_INVALID_ARG; 39 } 40 41 if ((err = cipher_is_valid(gcm->cipher)) != CRYPT_OK) { 42 return err; 43 } 44 45 46 if (gcm->mode != GCM_MODE_TEXT) { 47 return CRYPT_INVALID_ARG; 48 } 49 50 /* handle remaining ciphertext */ 51 if (gcm->buflen) { 52 gcm->pttotlen += gcm->buflen * CONST64(8); 53 gcm_mult_h(gcm, gcm->X); 54 } 55 56 /* length */ 57 STORE64H(gcm->totlen, gcm->buf); 58 STORE64H(gcm->pttotlen, gcm->buf+8); 59 for (x = 0; x < 16; x++) { 60 gcm->X[x] ^= gcm->buf[x]; 61 } 62 gcm_mult_h(gcm, gcm->X); 63 64 /* encrypt original counter */ 65 if ((err = cipher_descriptor[gcm->cipher].ecb_encrypt(gcm->Y_0, gcm->buf, &gcm->K)) != CRYPT_OK) { 66 return err; 67 } 68 for (x = 0; x < 16 && x < *taglen; x++) { 69 tag[x] = gcm->buf[x] ^ gcm->X[x]; 70 } 71 *taglen = x; 72 73 cipher_descriptor[gcm->cipher].done(&gcm->K); 74 75 return CRYPT_OK; 76 } 77 78 #endif 79 80 81 /* $Source: /cvs/libtom/libtomcrypt/src/encauth/gcm/gcm_done.c,v $ */ 82 /* $Revision: 1.9 $ */ 83 /* $Date: 2006/03/31 14:15:35 $ */ 84