wolfSSL SSL/TLS library, support up to TLS1.3

Dependents:   CyaSSL-Twitter-OAuth4Tw Example-client-tls-cert TwitterReader TweetTest ... more

Committer:
wolfSSL
Date:
Tue Aug 22 10:48:22 2017 +0000
Revision:
13:f67a6c6013ca
Parent:
11:cee25a834751
wolfSSL3.12.0 with TLS1.3

Who changed what in which revision?

UserRevisionLine numberNew contents of line
wolfSSL 11:cee25a834751 1 /* cmac.c
wolfSSL 11:cee25a834751 2 *
wolfSSL 11:cee25a834751 3 * Copyright (C) 2006-2016 wolfSSL Inc.
wolfSSL 11:cee25a834751 4 *
wolfSSL 11:cee25a834751 5 * This file is part of wolfSSL.
wolfSSL 11:cee25a834751 6 *
wolfSSL 11:cee25a834751 7 * wolfSSL is free software; you can redistribute it and/or modify
wolfSSL 11:cee25a834751 8 * it under the terms of the GNU General Public License as published by
wolfSSL 11:cee25a834751 9 * the Free Software Foundation; either version 2 of the License, or
wolfSSL 11:cee25a834751 10 * (at your option) any later version.
wolfSSL 11:cee25a834751 11 *
wolfSSL 11:cee25a834751 12 * wolfSSL is distributed in the hope that it will be useful,
wolfSSL 11:cee25a834751 13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
wolfSSL 11:cee25a834751 14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
wolfSSL 11:cee25a834751 15 * GNU General Public License for more details.
wolfSSL 11:cee25a834751 16 *
wolfSSL 11:cee25a834751 17 * You should have received a copy of the GNU General Public License
wolfSSL 11:cee25a834751 18 * along with this program; if not, write to the Free Software
wolfSSL 11:cee25a834751 19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
wolfSSL 11:cee25a834751 20 */
wolfSSL 11:cee25a834751 21
wolfSSL 11:cee25a834751 22
wolfSSL 11:cee25a834751 23 #ifdef HAVE_CONFIG_H
wolfSSL 11:cee25a834751 24 #include <config.h>
wolfSSL 11:cee25a834751 25 #endif
wolfSSL 11:cee25a834751 26
wolfSSL 11:cee25a834751 27 #include <wolfssl/wolfcrypt/settings.h>
wolfSSL 11:cee25a834751 28
wolfSSL 11:cee25a834751 29 #if defined(WOLFSSL_CMAC) && !defined(NO_AES) && defined(WOLFSSL_AES_DIRECT)
wolfSSL 11:cee25a834751 30
wolfSSL 11:cee25a834751 31 #ifdef NO_INLINE
wolfSSL 11:cee25a834751 32 #include <wolfssl/wolfcrypt/misc.h>
wolfSSL 11:cee25a834751 33 #else
wolfSSL 11:cee25a834751 34 #define WOLFSSL_MISC_INCLUDED
wolfSSL 11:cee25a834751 35 #include <wolfcrypt/src/misc.c>
wolfSSL 11:cee25a834751 36 #endif
wolfSSL 11:cee25a834751 37
wolfSSL 11:cee25a834751 38 #include <wolfssl/wolfcrypt/error-crypt.h>
wolfSSL 11:cee25a834751 39 #include <wolfssl/wolfcrypt/aes.h>
wolfSSL 11:cee25a834751 40 #include <wolfssl/wolfcrypt/cmac.h>
wolfSSL 11:cee25a834751 41
wolfSSL 11:cee25a834751 42
wolfSSL 11:cee25a834751 43 static void ShiftAndXorRb(byte* out, byte* in)
wolfSSL 11:cee25a834751 44 {
wolfSSL 11:cee25a834751 45 int i, j, xorRb;
wolfSSL 11:cee25a834751 46 int mask = 0, last = 0;
wolfSSL 11:cee25a834751 47 byte Rb = 0x87;
wolfSSL 11:cee25a834751 48
wolfSSL 11:cee25a834751 49 xorRb = (in[0] & 0x80) != 0;
wolfSSL 11:cee25a834751 50
wolfSSL 11:cee25a834751 51 for (i = 1, j = AES_BLOCK_SIZE - 1; i <= AES_BLOCK_SIZE; i++, j--) {
wolfSSL 11:cee25a834751 52 last = (in[j] & 0x80) ? 1 : 0;
wolfSSL 11:cee25a834751 53 out[j] = (in[j] << 1) | mask;
wolfSSL 11:cee25a834751 54 mask = last;
wolfSSL 11:cee25a834751 55 if (xorRb) {
wolfSSL 11:cee25a834751 56 out[j] ^= Rb;
wolfSSL 11:cee25a834751 57 Rb = 0;
wolfSSL 11:cee25a834751 58 }
wolfSSL 11:cee25a834751 59 }
wolfSSL 11:cee25a834751 60 }
wolfSSL 11:cee25a834751 61
wolfSSL 11:cee25a834751 62
wolfSSL 11:cee25a834751 63 int wc_InitCmac(Cmac* cmac, const byte* key, word32 keySz,
wolfSSL 11:cee25a834751 64 int type, void* unused)
wolfSSL 11:cee25a834751 65 {
wolfSSL 11:cee25a834751 66 int ret;
wolfSSL 11:cee25a834751 67
wolfSSL 11:cee25a834751 68 (void)unused;
wolfSSL 11:cee25a834751 69
wolfSSL 11:cee25a834751 70 if (cmac == NULL || key == NULL || keySz == 0 || type != WC_CMAC_AES)
wolfSSL 11:cee25a834751 71 return BAD_FUNC_ARG;
wolfSSL 11:cee25a834751 72
wolfSSL 11:cee25a834751 73 XMEMSET(cmac, 0, sizeof(Cmac));
wolfSSL 11:cee25a834751 74 ret = wc_AesSetKey(&cmac->aes, key, keySz, NULL, AES_ENCRYPTION);
wolfSSL 11:cee25a834751 75 if (ret == 0) {
wolfSSL 11:cee25a834751 76 byte l[AES_BLOCK_SIZE];
wolfSSL 11:cee25a834751 77
wolfSSL 11:cee25a834751 78 XMEMSET(l, 0, AES_BLOCK_SIZE);
wolfSSL 11:cee25a834751 79 wc_AesEncryptDirect(&cmac->aes, l, l);
wolfSSL 11:cee25a834751 80 ShiftAndXorRb(cmac->k1, l);
wolfSSL 11:cee25a834751 81 ShiftAndXorRb(cmac->k2, cmac->k1);
wolfSSL 11:cee25a834751 82 ForceZero(l, AES_BLOCK_SIZE);
wolfSSL 11:cee25a834751 83 }
wolfSSL 11:cee25a834751 84 return ret;
wolfSSL 11:cee25a834751 85 }
wolfSSL 11:cee25a834751 86
wolfSSL 11:cee25a834751 87
wolfSSL 11:cee25a834751 88 int wc_CmacUpdate(Cmac* cmac, const byte* in, word32 inSz)
wolfSSL 11:cee25a834751 89 {
wolfSSL 11:cee25a834751 90 if ((cmac == NULL) || (in == NULL && inSz != 0))
wolfSSL 11:cee25a834751 91 return BAD_FUNC_ARG;
wolfSSL 11:cee25a834751 92
wolfSSL 11:cee25a834751 93 while (inSz != 0) {
wolfSSL 11:cee25a834751 94 word32 add = min(inSz, AES_BLOCK_SIZE - cmac->bufferSz);
wolfSSL 11:cee25a834751 95 XMEMCPY(&cmac->buffer[cmac->bufferSz], in, add);
wolfSSL 11:cee25a834751 96
wolfSSL 11:cee25a834751 97 cmac->bufferSz += add;
wolfSSL 11:cee25a834751 98 in += add;
wolfSSL 11:cee25a834751 99 inSz -= add;
wolfSSL 11:cee25a834751 100
wolfSSL 11:cee25a834751 101 if (cmac->bufferSz == AES_BLOCK_SIZE && inSz != 0) {
wolfSSL 11:cee25a834751 102 if (cmac->totalSz != 0)
wolfSSL 11:cee25a834751 103 xorbuf(cmac->buffer, cmac->digest, AES_BLOCK_SIZE);
wolfSSL 11:cee25a834751 104 wc_AesEncryptDirect(&cmac->aes,
wolfSSL 11:cee25a834751 105 cmac->digest,
wolfSSL 11:cee25a834751 106 cmac->buffer);
wolfSSL 11:cee25a834751 107 cmac->totalSz += AES_BLOCK_SIZE;
wolfSSL 11:cee25a834751 108 cmac->bufferSz = 0;
wolfSSL 11:cee25a834751 109 }
wolfSSL 11:cee25a834751 110 }
wolfSSL 11:cee25a834751 111
wolfSSL 11:cee25a834751 112 return 0;
wolfSSL 11:cee25a834751 113 }
wolfSSL 11:cee25a834751 114
wolfSSL 11:cee25a834751 115
wolfSSL 11:cee25a834751 116 int wc_CmacFinal(Cmac* cmac, byte* out, word32* outSz)
wolfSSL 11:cee25a834751 117 {
wolfSSL 11:cee25a834751 118 const byte* subKey;
wolfSSL 11:cee25a834751 119
wolfSSL 11:cee25a834751 120 if (cmac == NULL || out == NULL)
wolfSSL 11:cee25a834751 121 return BAD_FUNC_ARG;
wolfSSL 11:cee25a834751 122
wolfSSL 11:cee25a834751 123 if (outSz != NULL && *outSz < AES_BLOCK_SIZE)
wolfSSL 11:cee25a834751 124 return BUFFER_E;
wolfSSL 11:cee25a834751 125
wolfSSL 11:cee25a834751 126 if (cmac->bufferSz == AES_BLOCK_SIZE) {
wolfSSL 11:cee25a834751 127 subKey = cmac->k1;
wolfSSL 11:cee25a834751 128 }
wolfSSL 11:cee25a834751 129 else {
wolfSSL 11:cee25a834751 130 word32 remainder = AES_BLOCK_SIZE - cmac->bufferSz;
wolfSSL 11:cee25a834751 131
wolfSSL 11:cee25a834751 132 if (remainder == 0)
wolfSSL 11:cee25a834751 133 remainder = AES_BLOCK_SIZE;
wolfSSL 11:cee25a834751 134
wolfSSL 11:cee25a834751 135 if (remainder > 1)
wolfSSL 11:cee25a834751 136 XMEMSET(cmac->buffer + AES_BLOCK_SIZE - remainder, 0, remainder);
wolfSSL 11:cee25a834751 137 cmac->buffer[AES_BLOCK_SIZE - remainder] = 0x80;
wolfSSL 11:cee25a834751 138 subKey = cmac->k2;
wolfSSL 11:cee25a834751 139 }
wolfSSL 11:cee25a834751 140 xorbuf(cmac->buffer, cmac->digest, AES_BLOCK_SIZE);
wolfSSL 11:cee25a834751 141 xorbuf(cmac->buffer, subKey, AES_BLOCK_SIZE);
wolfSSL 11:cee25a834751 142 wc_AesEncryptDirect(&cmac->aes, out, cmac->buffer);
wolfSSL 11:cee25a834751 143
wolfSSL 11:cee25a834751 144 if (outSz != NULL)
wolfSSL 11:cee25a834751 145 *outSz = AES_BLOCK_SIZE;
wolfSSL 11:cee25a834751 146 ForceZero(cmac, sizeof(Cmac));
wolfSSL 11:cee25a834751 147
wolfSSL 11:cee25a834751 148 return 0;
wolfSSL 11:cee25a834751 149 }
wolfSSL 11:cee25a834751 150
wolfSSL 11:cee25a834751 151
wolfSSL 11:cee25a834751 152 int wc_AesCmacGenerate(byte* out, word32* outSz,
wolfSSL 11:cee25a834751 153 const byte* in, word32 inSz,
wolfSSL 11:cee25a834751 154 const byte* key, word32 keySz)
wolfSSL 11:cee25a834751 155 {
wolfSSL 11:cee25a834751 156 Cmac cmac;
wolfSSL 11:cee25a834751 157 int ret;
wolfSSL 11:cee25a834751 158
wolfSSL 11:cee25a834751 159 if (out == NULL || (in == NULL && inSz > 0) || key == NULL || keySz == 0)
wolfSSL 11:cee25a834751 160 return BAD_FUNC_ARG;
wolfSSL 11:cee25a834751 161
wolfSSL 11:cee25a834751 162 ret = wc_InitCmac(&cmac, key, keySz, WC_CMAC_AES, NULL);
wolfSSL 11:cee25a834751 163 if (ret != 0)
wolfSSL 11:cee25a834751 164 return ret;
wolfSSL 11:cee25a834751 165
wolfSSL 11:cee25a834751 166 ret = wc_CmacUpdate(&cmac, in, inSz);
wolfSSL 11:cee25a834751 167 if (ret != 0)
wolfSSL 11:cee25a834751 168 return ret;
wolfSSL 11:cee25a834751 169
wolfSSL 11:cee25a834751 170 ret = wc_CmacFinal(&cmac, out, outSz);
wolfSSL 11:cee25a834751 171 if (ret != 0)
wolfSSL 11:cee25a834751 172 return ret;
wolfSSL 11:cee25a834751 173
wolfSSL 11:cee25a834751 174 return 0;
wolfSSL 11:cee25a834751 175 }
wolfSSL 11:cee25a834751 176
wolfSSL 11:cee25a834751 177
wolfSSL 11:cee25a834751 178 int wc_AesCmacVerify(const byte* check, word32 checkSz,
wolfSSL 11:cee25a834751 179 const byte* in, word32 inSz,
wolfSSL 11:cee25a834751 180 const byte* key, word32 keySz)
wolfSSL 11:cee25a834751 181 {
wolfSSL 11:cee25a834751 182 byte a[AES_BLOCK_SIZE];
wolfSSL 11:cee25a834751 183 word32 aSz = sizeof(a);
wolfSSL 11:cee25a834751 184 int result;
wolfSSL 11:cee25a834751 185 int compareRet;
wolfSSL 11:cee25a834751 186
wolfSSL 11:cee25a834751 187 if (check == NULL || checkSz == 0 || (in == NULL && inSz != 0) ||
wolfSSL 11:cee25a834751 188 key == NULL || keySz == 0)
wolfSSL 11:cee25a834751 189
wolfSSL 11:cee25a834751 190 return BAD_FUNC_ARG;
wolfSSL 11:cee25a834751 191
wolfSSL 11:cee25a834751 192 XMEMSET(a, 0, aSz);
wolfSSL 11:cee25a834751 193 result = wc_AesCmacGenerate(a, &aSz, in, inSz, key, keySz);
wolfSSL 11:cee25a834751 194 compareRet = ConstantCompare(check, a, min(checkSz, aSz));
wolfSSL 11:cee25a834751 195
wolfSSL 11:cee25a834751 196 if (result == 0)
wolfSSL 11:cee25a834751 197 result = compareRet ? 1 : 0;
wolfSSL 11:cee25a834751 198
wolfSSL 11:cee25a834751 199 return result;
wolfSSL 11:cee25a834751 200 }
wolfSSL 11:cee25a834751 201
wolfSSL 11:cee25a834751 202
wolfSSL 11:cee25a834751 203 #endif /* WOLFSSL_CMAC && NO_AES && WOLFSSL_AES_DIRECT */
wolfSSL 11:cee25a834751 204