1 /* LibTomCrypt, modular cryptographic library -- Tom St Denis */
2 /* SPDX-License-Identifier: Unlicense */
3 
4 /**
5    @file eax_done.c
6    EAX implementation, terminate session, by Tom St Denis
7 */
8 #include "tomcrypt_private.h"
9 
10 #ifdef LTC_EAX_MODE
11 
12 /**
13    Terminate an EAX session and get the tag.
14    @param eax       The EAX state
15    @param tag       [out] The destination of the authentication tag
16    @param taglen    [in/out] The max length and resulting length of the authentication tag
17    @return CRYPT_OK if successful
18 */
eax_done(eax_state * eax,unsigned char * tag,unsigned long * taglen)19 int eax_done(eax_state *eax, unsigned char *tag, unsigned long *taglen)
20 {
21    int           err;
22    unsigned char *headermac, *ctmac;
23    unsigned long x, len;
24 
25    LTC_ARGCHK(eax    != NULL);
26    LTC_ARGCHK(tag    != NULL);
27    LTC_ARGCHK(taglen != NULL);
28 
29    /* allocate ram */
30    headermac = XMALLOC(MAXBLOCKSIZE);
31    ctmac     = XMALLOC(MAXBLOCKSIZE);
32 
33    if (headermac == NULL || ctmac == NULL) {
34       if (headermac != NULL) {
35          XFREE(headermac);
36       }
37       if (ctmac != NULL) {
38          XFREE(ctmac);
39       }
40       return CRYPT_MEM;
41    }
42 
43    /* finish ctomac */
44    len = MAXBLOCKSIZE;
45    if ((err = omac_done(&eax->ctomac, ctmac, &len)) != CRYPT_OK) {
46       goto LBL_ERR;
47    }
48 
49    /* finish headeromac */
50 
51    /* note we specifically don't reset len so the two lens are minimal */
52 
53    if ((err = omac_done(&eax->headeromac, headermac, &len)) != CRYPT_OK) {
54       goto LBL_ERR;
55    }
56 
57    /* terminate the CTR chain */
58    if ((err = ctr_done(&eax->ctr)) != CRYPT_OK) {
59       goto LBL_ERR;
60    }
61 
62    /* compute N xor H xor C */
63    for (x = 0; x < len && x < *taglen; x++) {
64        tag[x] = eax->N[x] ^ headermac[x] ^ ctmac[x];
65    }
66    *taglen = x;
67 
68    err = CRYPT_OK;
69 LBL_ERR:
70 #ifdef LTC_CLEAN_STACK
71    zeromem(ctmac,     MAXBLOCKSIZE);
72    zeromem(headermac, MAXBLOCKSIZE);
73    zeromem(eax,       sizeof(*eax));
74 #endif
75 
76    XFREE(ctmac);
77    XFREE(headermac);
78 
79    return err;
80 }
81 
82 #endif
83