1 /* LibTomCrypt, modular cryptographic library -- Tom St Denis */
2 /* SPDX-License-Identifier: Unlicense */
3 
4 /**
5   @file ocb3_decrypt_verify_memory.c
6   OCB implementation, helper to decrypt block of memory, by Tom St Denis
7 */
8 #include "tomcrypt_private.h"
9 
10 #ifdef LTC_OCB3_MODE
11 
12 /**
13    Decrypt and compare the tag with OCB
14    @param cipher     The index of the cipher desired
15    @param key        The secret key
16    @param keylen     The length of the secret key (octets)
17    @param nonce      The session nonce (length of the block size of the block cipher)
18    @param noncelen   The length of the nonce (octets)
19    @param adata      The AAD - additional associated data
20    @param adatalen   The length of AAD (octets)
21    @param ct         The ciphertext
22    @param ctlen      The length of the ciphertext (octets)
23    @param pt         [out] The plaintext
24    @param tag        The tag to compare against
25    @param taglen     The length of the tag (octets)
26    @param stat       [out] The result of the tag comparison (1==valid, 0==invalid)
27    @return CRYPT_OK if successful regardless of the tag comparison
28 */
ocb3_decrypt_verify_memory(int cipher,const unsigned char * key,unsigned long keylen,const unsigned char * nonce,unsigned long noncelen,const unsigned char * adata,unsigned long adatalen,const unsigned char * ct,unsigned long ctlen,unsigned char * pt,const unsigned char * tag,unsigned long taglen,int * stat)29 int ocb3_decrypt_verify_memory(int cipher,
30     const unsigned char *key,    unsigned long keylen,
31     const unsigned char *nonce,  unsigned long noncelen,
32     const unsigned char *adata,  unsigned long adatalen,
33     const unsigned char *ct,     unsigned long ctlen,
34           unsigned char *pt,
35     const unsigned char *tag,    unsigned long taglen,
36           int           *stat)
37 {
38    int            err;
39    ocb3_state     *ocb;
40    unsigned char *buf;
41    unsigned long  buflen;
42 
43    LTC_ARGCHK(stat    != NULL);
44 
45    /* default to zero */
46    *stat = 0;
47 
48    /* limit taglen */
49    taglen = MIN(taglen, MAXBLOCKSIZE);
50 
51    /* allocate memory */
52    buf = XMALLOC(taglen);
53    ocb = XMALLOC(sizeof(ocb3_state));
54    if (ocb == NULL || buf == NULL) {
55       if (ocb != NULL) {
56          XFREE(ocb);
57       }
58       if (buf != NULL) {
59          XFREE(buf);
60       }
61       return CRYPT_MEM;
62    }
63 
64    if ((err = ocb3_init(ocb, cipher, key, keylen, nonce, noncelen, taglen)) != CRYPT_OK) {
65       goto LBL_ERR;
66    }
67 
68    if (adata != NULL || adatalen != 0) {
69       if ((err = ocb3_add_aad(ocb, adata, adatalen)) != CRYPT_OK) {
70          goto LBL_ERR;
71       }
72    }
73 
74    if ((err = ocb3_decrypt_last(ocb, ct, ctlen, pt)) != CRYPT_OK) {
75       goto LBL_ERR;
76    }
77 
78    buflen = taglen;
79    if ((err = ocb3_done(ocb, buf, &buflen)) != CRYPT_OK) {
80       goto LBL_ERR;
81    }
82 
83    /* compare tags */
84    if (buflen >= taglen && XMEM_NEQ(buf, tag, taglen) == 0) {
85       *stat = 1;
86    }
87 
88    err = CRYPT_OK;
89 
90 LBL_ERR:
91 #ifdef LTC_CLEAN_STACK
92    zeromem(ocb, sizeof(ocb3_state));
93 #endif
94 
95    XFREE(ocb);
96    XFREE(buf);
97    return err;
98 }
99 
100 #endif
101