wolfSSL SSL/TLS library, support up to TLS1.3
Dependents: CyaSSL-Twitter-OAuth4Tw Example-client-tls-cert TwitterReader TweetTest ... more
aes.c
00001 /* aes.c 00002 * 00003 * Copyright (C) 2006-2020 wolfSSL Inc. 00004 * 00005 * This file is part of wolfSSL. 00006 * 00007 * wolfSSL is free software; you can redistribute it and/or modify 00008 * it under the terms of the GNU General Public License as published by 00009 * the Free Software Foundation; either version 2 of the License, or 00010 * (at your option) any later version. 00011 * 00012 * wolfSSL is distributed in the hope that it will be useful, 00013 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00015 * GNU General Public License for more details. 00016 * 00017 * You should have received a copy of the GNU General Public License 00018 * along with this program; if not, write to the Free Software 00019 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA 00020 */ 00021 00022 00023 #ifdef HAVE_CONFIG_H 00024 #include <config.h> 00025 #endif 00026 00027 #include <wolfssl/wolfcrypt/settings.h> 00028 #include <wolfssl/wolfcrypt/error-crypt.h > 00029 00030 #if !defined(NO_AES) 00031 00032 /* Tip: Locate the software cipher modes by searching for "Software AES" */ 00033 00034 #if defined(HAVE_FIPS) && \ 00035 defined(HAVE_FIPS_VERSION) && (HAVE_FIPS_VERSION >= 2) 00036 00037 /* set NO_WRAPPERS before headers, use direct internal f()s not wrappers */ 00038 #define FIPS_NO_WRAPPERS 00039 00040 #ifdef USE_WINDOWS_API 00041 #pragma code_seg(".fipsA$g") 00042 #pragma const_seg(".fipsB$g") 00043 #endif 00044 #endif 00045 00046 #include <wolfssl/wolfcrypt/aes.h > 00047 #include <wolfssl/wolfcrypt/cpuid.h> 00048 00049 #ifdef WOLF_CRYPTO_CB 00050 #include <wolfssl/wolfcrypt/cryptocb.h> 00051 #endif 00052 00053 00054 /* fips wrapper calls, user can call direct */ 00055 #if defined(HAVE_FIPS) && \ 00056 (!defined(HAVE_FIPS_VERSION) || (HAVE_FIPS_VERSION < 2)) 00057 00058 int wc_AesSetKey(Aes* aes, const byte* key, word32 len, const byte* iv, 00059 int dir) 00060 { 00061 if (aes == NULL || !( (len == 16) || (len == 24) || (len == 32)) ) { 00062 return BAD_FUNC_ARG; 00063 } 00064 00065 return AesSetKey_fips(aes, key, len, iv, dir); 00066 } 00067 int wc_AesSetIV(Aes* aes, const byte* iv) 00068 { 00069 if (aes == NULL) { 00070 return BAD_FUNC_ARG; 00071 } 00072 00073 return AesSetIV_fips(aes, iv); 00074 } 00075 #ifdef HAVE_AES_CBC 00076 int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 00077 { 00078 if (aes == NULL || out == NULL || in == NULL) { 00079 return BAD_FUNC_ARG; 00080 } 00081 00082 return AesCbcEncrypt_fips(aes, out, in, sz); 00083 } 00084 #ifdef HAVE_AES_DECRYPT 00085 int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 00086 { 00087 if (aes == NULL || out == NULL || in == NULL 00088 || sz % AES_BLOCK_SIZE != 0) { 00089 return BAD_FUNC_ARG; 00090 } 00091 00092 return AesCbcDecrypt_fips(aes, out, in, sz); 00093 } 00094 #endif /* HAVE_AES_DECRYPT */ 00095 #endif /* HAVE_AES_CBC */ 00096 00097 /* AES-CTR */ 00098 #ifdef WOLFSSL_AES_COUNTER 00099 int wc_AesCtrEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 00100 { 00101 if (aes == NULL || out == NULL || in == NULL) { 00102 return BAD_FUNC_ARG; 00103 } 00104 00105 return AesCtrEncrypt(aes, out, in, sz); 00106 } 00107 #endif 00108 00109 /* AES-DIRECT */ 00110 #if defined(WOLFSSL_AES_DIRECT) 00111 void wc_AesEncryptDirect(Aes* aes, byte* out, const byte* in) 00112 { 00113 AesEncryptDirect(aes, out, in); 00114 } 00115 00116 #ifdef HAVE_AES_DECRYPT 00117 void wc_AesDecryptDirect(Aes* aes, byte* out, const byte* in) 00118 { 00119 AesDecryptDirect(aes, out, in); 00120 } 00121 #endif /* HAVE_AES_DECRYPT */ 00122 00123 int wc_AesSetKeyDirect(Aes* aes, const byte* key, word32 len, 00124 const byte* iv, int dir) 00125 { 00126 return AesSetKeyDirect(aes, key, len, iv, dir); 00127 } 00128 #endif /* WOLFSSL_AES_DIRECT */ 00129 00130 /* AES-GCM */ 00131 #ifdef HAVE_AESGCM 00132 int wc_AesGcmSetKey(Aes* aes, const byte* key, word32 len) 00133 { 00134 if (aes == NULL || !( (len == 16) || (len == 24) || (len == 32)) ) { 00135 return BAD_FUNC_ARG; 00136 } 00137 00138 return AesGcmSetKey_fips(aes, key, len); 00139 } 00140 int wc_AesGcmEncrypt(Aes* aes, byte* out, const byte* in, word32 sz, 00141 const byte* iv, word32 ivSz, 00142 byte* authTag, word32 authTagSz, 00143 const byte* authIn, word32 authInSz) 00144 { 00145 if (aes == NULL || authTagSz > AES_BLOCK_SIZE || 00146 authTagSz < WOLFSSL_MIN_AUTH_TAG_SZ || 00147 ivSz == 0 || ivSz > AES_BLOCK_SIZE) { 00148 return BAD_FUNC_ARG; 00149 } 00150 00151 return AesGcmEncrypt_fips(aes, out, in, sz, iv, ivSz, authTag, 00152 authTagSz, authIn, authInSz); 00153 } 00154 00155 #ifdef HAVE_AES_DECRYPT 00156 int wc_AesGcmDecrypt(Aes* aes, byte* out, const byte* in, word32 sz, 00157 const byte* iv, word32 ivSz, 00158 const byte* authTag, word32 authTagSz, 00159 const byte* authIn, word32 authInSz) 00160 { 00161 if (aes == NULL || out == NULL || in == NULL || iv == NULL 00162 || authTag == NULL || authTagSz > AES_BLOCK_SIZE || 00163 ivSz == 0 || ivSz > AES_BLOCK_SIZE) { 00164 return BAD_FUNC_ARG; 00165 } 00166 00167 return AesGcmDecrypt_fips(aes, out, in, sz, iv, ivSz, authTag, 00168 authTagSz, authIn, authInSz); 00169 } 00170 #endif /* HAVE_AES_DECRYPT */ 00171 00172 int wc_GmacSetKey(Gmac* gmac, const byte* key, word32 len) 00173 { 00174 if (gmac == NULL || key == NULL || !((len == 16) || 00175 (len == 24) || (len == 32)) ) { 00176 return BAD_FUNC_ARG; 00177 } 00178 00179 return GmacSetKey(gmac, key, len); 00180 } 00181 int wc_GmacUpdate(Gmac* gmac, const byte* iv, word32 ivSz, 00182 const byte* authIn, word32 authInSz, 00183 byte* authTag, word32 authTagSz) 00184 { 00185 if (gmac == NULL || authTagSz > AES_BLOCK_SIZE || 00186 authTagSz < WOLFSSL_MIN_AUTH_TAG_SZ) { 00187 return BAD_FUNC_ARG; 00188 } 00189 00190 return GmacUpdate(gmac, iv, ivSz, authIn, authInSz, 00191 authTag, authTagSz); 00192 } 00193 #endif /* HAVE_AESGCM */ 00194 00195 /* AES-CCM */ 00196 #if defined(HAVE_AESCCM) && \ 00197 defined(HAVE_FIPS_VERSION) && (HAVE_FIPS_VERSION >= 2) 00198 int wc_AesCcmSetKey(Aes* aes, const byte* key, word32 keySz) 00199 { 00200 return AesCcmSetKey(aes, key, keySz); 00201 } 00202 int wc_AesCcmEncrypt(Aes* aes, byte* out, const byte* in, word32 inSz, 00203 const byte* nonce, word32 nonceSz, 00204 byte* authTag, word32 authTagSz, 00205 const byte* authIn, word32 authInSz) 00206 { 00207 /* sanity check on arguments */ 00208 if (aes == NULL || out == NULL || in == NULL || nonce == NULL 00209 || authTag == NULL || nonceSz < 7 || nonceSz > 13) 00210 return BAD_FUNC_ARG; 00211 00212 AesCcmEncrypt(aes, out, in, inSz, nonce, nonceSz, authTag, 00213 authTagSz, authIn, authInSz); 00214 return 0; 00215 } 00216 00217 #ifdef HAVE_AES_DECRYPT 00218 int wc_AesCcmDecrypt(Aes* aes, byte* out, 00219 const byte* in, word32 inSz, 00220 const byte* nonce, word32 nonceSz, 00221 const byte* authTag, word32 authTagSz, 00222 const byte* authIn, word32 authInSz) 00223 { 00224 00225 if (aes == NULL || out == NULL || in == NULL || nonce == NULL 00226 || authTag == NULL || nonceSz < 7 || nonceSz > 13) { 00227 return BAD_FUNC_ARG; 00228 } 00229 00230 return AesCcmDecrypt(aes, out, in, inSz, nonce, nonceSz, 00231 authTag, authTagSz, authIn, authInSz); 00232 } 00233 #endif /* HAVE_AES_DECRYPT */ 00234 #endif /* HAVE_AESCCM && HAVE_FIPS_VERSION 2 */ 00235 00236 int wc_AesInit(Aes* aes, void* h, int i) 00237 { 00238 if (aes == NULL) 00239 return BAD_FUNC_ARG; 00240 00241 (void)h; 00242 (void)i; 00243 00244 /* FIPS doesn't support: 00245 return AesInit(aes, h, i); */ 00246 return 0; 00247 } 00248 void wc_AesFree(Aes* aes) 00249 { 00250 (void)aes; 00251 /* FIPS doesn't support: 00252 AesFree(aes); */ 00253 } 00254 00255 #else /* else build without fips, or for FIPS v2 */ 00256 00257 00258 #if defined(WOLFSSL_TI_CRYPT) 00259 #include <wolfcrypt/src/port/ti/ti-aes.c> 00260 #else 00261 00262 #include <wolfssl/wolfcrypt/logging.h > 00263 00264 #ifdef NO_INLINE 00265 #include <wolfssl/wolfcrypt/misc.h> 00266 #else 00267 #define WOLFSSL_MISC_INCLUDED 00268 #include <wolfcrypt/src/misc.c> 00269 #endif 00270 00271 #if !defined(WOLFSSL_ARMASM) 00272 00273 #ifdef WOLFSSL_IMX6_CAAM_BLOB 00274 /* case of possibly not using hardware acceleration for AES but using key 00275 blobs */ 00276 #include <wolfssl/wolfcrypt/port/caam/wolfcaam.h> 00277 #endif 00278 00279 #ifdef DEBUG_AESNI 00280 #include <stdio.h> 00281 #endif 00282 00283 #ifdef _MSC_VER 00284 /* 4127 warning constant while(1) */ 00285 #pragma warning(disable: 4127) 00286 #endif 00287 00288 00289 /* Define AES implementation includes and functions */ 00290 #if defined(STM32_CRYPTO) 00291 /* STM32F2/F4/F7/L4 hardware AES support for ECB, CBC, CTR and GCM modes */ 00292 00293 #if defined(WOLFSSL_AES_DIRECT) || defined(HAVE_AESGCM) || defined(HAVE_AESCCM) 00294 00295 static int wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00296 { 00297 int ret = 0; 00298 #ifdef WOLFSSL_STM32_CUBEMX 00299 CRYP_HandleTypeDef hcryp; 00300 #else 00301 CRYP_InitTypeDef cryptInit; 00302 CRYP_KeyInitTypeDef keyInit; 00303 #endif 00304 00305 #ifdef WOLFSSL_STM32_CUBEMX 00306 ret = wc_Stm32_Aes_Init(aes, &hcryp); 00307 if (ret != 0) 00308 return ret; 00309 00310 #ifdef STM32_CRYPTO_AES_ONLY 00311 hcryp.Init.OperatingMode = CRYP_ALGOMODE_ENCRYPT; 00312 hcryp.Init.ChainingMode = CRYP_CHAINMODE_AES_ECB; 00313 hcryp.Init.KeyWriteFlag = CRYP_KEY_WRITE_ENABLE; 00314 #elif defined(STM32_HAL_V2) 00315 hcryp.Init.Algorithm = CRYP_AES_ECB; 00316 #endif 00317 HAL_CRYP_Init(&hcryp); 00318 00319 #ifdef STM32_CRYPTO_AES_ONLY 00320 ret = HAL_CRYPEx_AES(&hcryp, (uint8_t*)inBlock, AES_BLOCK_SIZE, 00321 outBlock, STM32_HAL_TIMEOUT); 00322 #elif defined(STM32_HAL_V2) 00323 ret = HAL_CRYP_Encrypt(&hcryp, (uint32_t*)inBlock, AES_BLOCK_SIZE, 00324 (uint32_t*)outBlock, STM32_HAL_TIMEOUT); 00325 #else 00326 ret = HAL_CRYP_AESECB_Encrypt(&hcryp, (uint8_t*)inBlock, AES_BLOCK_SIZE, 00327 outBlock, STM32_HAL_TIMEOUT); 00328 #endif 00329 if (ret != HAL_OK) { 00330 ret = WC_TIMEOUT_E; 00331 } 00332 HAL_CRYP_DeInit(&hcryp); 00333 00334 #else /* STD_PERI_LIB */ 00335 ret = wc_Stm32_Aes_Init(aes, &cryptInit, &keyInit); 00336 if (ret != 0) 00337 return ret; 00338 00339 /* reset registers to their default values */ 00340 CRYP_DeInit(); 00341 00342 /* setup key */ 00343 CRYP_KeyInit(&keyInit); 00344 00345 /* set direction and mode */ 00346 cryptInit.CRYP_AlgoDir = CRYP_AlgoDir_Encrypt; 00347 cryptInit.CRYP_AlgoMode = CRYP_AlgoMode_AES_ECB; 00348 CRYP_Init(&cryptInit); 00349 00350 /* enable crypto processor */ 00351 CRYP_Cmd(ENABLE); 00352 00353 /* flush IN/OUT FIFOs */ 00354 CRYP_FIFOFlush(); 00355 00356 CRYP_DataIn(*(uint32_t*)&inBlock[0]); 00357 CRYP_DataIn(*(uint32_t*)&inBlock[4]); 00358 CRYP_DataIn(*(uint32_t*)&inBlock[8]); 00359 CRYP_DataIn(*(uint32_t*)&inBlock[12]); 00360 00361 /* wait until the complete message has been processed */ 00362 while (CRYP_GetFlagStatus(CRYP_FLAG_BUSY) != RESET) {} 00363 00364 *(uint32_t*)&outBlock[0] = CRYP_DataOut(); 00365 *(uint32_t*)&outBlock[4] = CRYP_DataOut(); 00366 *(uint32_t*)&outBlock[8] = CRYP_DataOut(); 00367 *(uint32_t*)&outBlock[12] = CRYP_DataOut(); 00368 00369 /* disable crypto processor */ 00370 CRYP_Cmd(DISABLE); 00371 #endif /* WOLFSSL_STM32_CUBEMX */ 00372 00373 return ret; 00374 } 00375 #endif /* WOLFSSL_AES_DIRECT || HAVE_AESGCM || HAVE_AESCCM */ 00376 00377 #ifdef HAVE_AES_DECRYPT 00378 #if defined(WOLFSSL_AES_DIRECT) || defined(HAVE_AESCCM) 00379 static int wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00380 { 00381 int ret = 0; 00382 #ifdef WOLFSSL_STM32_CUBEMX 00383 CRYP_HandleTypeDef hcryp; 00384 #else 00385 CRYP_InitTypeDef cryptInit; 00386 CRYP_KeyInitTypeDef keyInit; 00387 #endif 00388 00389 #ifdef WOLFSSL_STM32_CUBEMX 00390 ret = wc_Stm32_Aes_Init(aes, &hcryp); 00391 if (ret != 0) 00392 return ret; 00393 00394 #ifdef STM32_CRYPTO_AES_ONLY 00395 hcryp.Init.OperatingMode = CRYP_ALGOMODE_DECRYPT; 00396 hcryp.Init.ChainingMode = CRYP_CHAINMODE_AES_ECB; 00397 hcryp.Init.KeyWriteFlag = CRYP_KEY_WRITE_ENABLE; 00398 #elif defined(STM32_HAL_V2) 00399 hcryp.Init.Algorithm = CRYP_AES_ECB; 00400 #endif 00401 HAL_CRYP_Init(&hcryp); 00402 00403 #ifdef STM32_CRYPTO_AES_ONLY 00404 ret = HAL_CRYPEx_AES(&hcryp, (uint8_t*)inBlock, AES_BLOCK_SIZE, 00405 outBlock, STM32_HAL_TIMEOUT); 00406 #elif defined(STM32_HAL_V2) 00407 ret = HAL_CRYP_Decrypt(&hcryp, (uint32_t*)inBlock, AES_BLOCK_SIZE, 00408 (uint32_t*)outBlock, STM32_HAL_TIMEOUT); 00409 #else 00410 ret = HAL_CRYP_AESECB_Decrypt(&hcryp, (uint8_t*)inBlock, AES_BLOCK_SIZE, 00411 outBlock, STM32_HAL_TIMEOUT); 00412 #endif 00413 if (ret != HAL_OK) { 00414 ret = WC_TIMEOUT_E; 00415 } 00416 HAL_CRYP_DeInit(&hcryp); 00417 00418 #else /* STD_PERI_LIB */ 00419 ret = wc_Stm32_Aes_Init(aes, &cryptInit, &keyInit); 00420 if (ret != 0) 00421 return ret; 00422 00423 /* reset registers to their default values */ 00424 CRYP_DeInit(); 00425 00426 /* set direction and key */ 00427 CRYP_KeyInit(&keyInit); 00428 cryptInit.CRYP_AlgoDir = CRYP_AlgoDir_Decrypt; 00429 cryptInit.CRYP_AlgoMode = CRYP_AlgoMode_AES_Key; 00430 CRYP_Init(&cryptInit); 00431 00432 /* enable crypto processor */ 00433 CRYP_Cmd(ENABLE); 00434 00435 /* wait until decrypt key has been initialized */ 00436 while (CRYP_GetFlagStatus(CRYP_FLAG_BUSY) != RESET) {} 00437 00438 /* set direction and mode */ 00439 cryptInit.CRYP_AlgoDir = CRYP_AlgoDir_Decrypt; 00440 cryptInit.CRYP_AlgoMode = CRYP_AlgoMode_AES_ECB; 00441 CRYP_Init(&cryptInit); 00442 00443 /* enable crypto processor */ 00444 CRYP_Cmd(ENABLE); 00445 00446 /* flush IN/OUT FIFOs */ 00447 CRYP_FIFOFlush(); 00448 00449 CRYP_DataIn(*(uint32_t*)&inBlock[0]); 00450 CRYP_DataIn(*(uint32_t*)&inBlock[4]); 00451 CRYP_DataIn(*(uint32_t*)&inBlock[8]); 00452 CRYP_DataIn(*(uint32_t*)&inBlock[12]); 00453 00454 /* wait until the complete message has been processed */ 00455 while (CRYP_GetFlagStatus(CRYP_FLAG_BUSY) != RESET) {} 00456 00457 *(uint32_t*)&outBlock[0] = CRYP_DataOut(); 00458 *(uint32_t*)&outBlock[4] = CRYP_DataOut(); 00459 *(uint32_t*)&outBlock[8] = CRYP_DataOut(); 00460 *(uint32_t*)&outBlock[12] = CRYP_DataOut(); 00461 00462 /* disable crypto processor */ 00463 CRYP_Cmd(DISABLE); 00464 #endif /* WOLFSSL_STM32_CUBEMX */ 00465 00466 return ret; 00467 } 00468 #endif /* WOLFSSL_AES_DIRECT || HAVE_AESCCM */ 00469 #endif /* HAVE_AES_DECRYPT */ 00470 00471 #elif defined(HAVE_COLDFIRE_SEC) 00472 /* Freescale Coldfire SEC support for CBC mode. 00473 * NOTE: no support for AES-CTR/GCM/CCM/Direct */ 00474 #include <wolfssl/wolfcrypt/types.h > 00475 #include "sec.h" 00476 #include "mcf5475_sec.h" 00477 #include "mcf5475_siu.h" 00478 #elif defined(FREESCALE_LTC) 00479 #include "fsl_ltc.h" 00480 #if defined(FREESCALE_LTC_AES_GCM) 00481 #undef NEED_AES_TABLES 00482 #undef GCM_TABLE 00483 #else 00484 /* if LTC doesn't have GCM, use software with LTC AES ECB mode */ 00485 static int wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00486 { 00487 wc_AesEncryptDirect(aes, outBlock, inBlock); 00488 return 0; 00489 } 00490 static int wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00491 { 00492 wc_AesDecryptDirect(aes, outBlock, inBlock); 00493 return 0; 00494 } 00495 #endif 00496 #elif defined(FREESCALE_MMCAU) 00497 /* Freescale mmCAU hardware AES support for Direct, CBC, CCM, GCM modes 00498 * through the CAU/mmCAU library. Documentation located in 00499 * ColdFire/ColdFire+ CAU and Kinetis mmCAU Software Library User 00500 * Guide (See note in README). */ 00501 #ifdef FREESCALE_MMCAU_CLASSIC 00502 /* MMCAU 1.4 library used with non-KSDK / classic MQX builds */ 00503 #include "cau_api.h" 00504 #else 00505 #include "fsl_mmcau.h" 00506 #endif 00507 00508 static int wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00509 { 00510 int ret; 00511 00512 #ifdef FREESCALE_MMCAU_CLASSIC 00513 if ((wolfssl_word)outBlock % WOLFSSL_MMCAU_ALIGNMENT) { 00514 WOLFSSL_MSG("Bad cau_aes_encrypt alignment"); 00515 return BAD_ALIGN_E; 00516 } 00517 #endif 00518 00519 ret = wolfSSL_CryptHwMutexLock(); 00520 if(ret == 0) { 00521 #ifdef FREESCALE_MMCAU_CLASSIC 00522 cau_aes_encrypt(inBlock, (byte*)aes->key, aes->rounds, outBlock); 00523 #else 00524 MMCAU_AES_EncryptEcb(inBlock, (byte*)aes->key, aes->rounds, 00525 outBlock); 00526 #endif 00527 wolfSSL_CryptHwMutexUnLock(); 00528 } 00529 return ret; 00530 } 00531 #ifdef HAVE_AES_DECRYPT 00532 static int wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00533 { 00534 int ret; 00535 00536 #ifdef FREESCALE_MMCAU_CLASSIC 00537 if ((wolfssl_word)outBlock % WOLFSSL_MMCAU_ALIGNMENT) { 00538 WOLFSSL_MSG("Bad cau_aes_decrypt alignment"); 00539 return BAD_ALIGN_E; 00540 } 00541 #endif 00542 00543 ret = wolfSSL_CryptHwMutexLock(); 00544 if(ret == 0) { 00545 #ifdef FREESCALE_MMCAU_CLASSIC 00546 cau_aes_decrypt(inBlock, (byte*)aes->key, aes->rounds, outBlock); 00547 #else 00548 MMCAU_AES_DecryptEcb(inBlock, (byte*)aes->key, aes->rounds, 00549 outBlock); 00550 #endif 00551 wolfSSL_CryptHwMutexUnLock(); 00552 } 00553 return ret; 00554 } 00555 #endif /* HAVE_AES_DECRYPT */ 00556 00557 #elif defined(WOLFSSL_PIC32MZ_CRYPT) 00558 00559 #include <wolfssl/wolfcrypt/port/pic32/pic32mz-crypt.h> 00560 00561 #if defined(HAVE_AESGCM) || defined(WOLFSSL_AES_DIRECT) 00562 static int wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00563 { 00564 return wc_Pic32AesCrypt(aes->key, aes->keylen, NULL, 0, 00565 outBlock, inBlock, AES_BLOCK_SIZE, 00566 PIC32_ENCRYPTION, PIC32_ALGO_AES, PIC32_CRYPTOALGO_RECB); 00567 } 00568 #endif 00569 00570 #if defined(HAVE_AES_DECRYPT) && defined(WOLFSSL_AES_DIRECT) 00571 static int wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00572 { 00573 return wc_Pic32AesCrypt(aes->key, aes->keylen, NULL, 0, 00574 outBlock, inBlock, AES_BLOCK_SIZE, 00575 PIC32_DECRYPTION, PIC32_ALGO_AES, PIC32_CRYPTOALGO_RECB); 00576 } 00577 #endif 00578 00579 #elif defined(WOLFSSL_NRF51_AES) 00580 /* Use built-in AES hardware - AES 128 ECB Encrypt Only */ 00581 #include "wolfssl/wolfcrypt/port/nrf51.h" 00582 00583 static int wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00584 { 00585 return nrf51_aes_encrypt(inBlock, (byte*)aes->key, aes->rounds, outBlock); 00586 } 00587 00588 #ifdef HAVE_AES_DECRYPT 00589 #error nRF51 AES Hardware does not support decrypt 00590 #endif /* HAVE_AES_DECRYPT */ 00591 00592 #elif defined(WOLFSSL_ESP32WROOM32_CRYPT) && \ 00593 !defined(NO_WOLFSSL_ESP32WROOM32_CRYPT_AES) 00594 00595 #include "wolfssl/wolfcrypt/port/Espressif/esp32-crypt.h" 00596 00597 #if defined(HAVE_AESGCM) || defined(WOLFSSL_AES_DIRECT) 00598 static int wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00599 { 00600 return wc_esp32AesEncrypt(aes, inBlock, outBlock); 00601 } 00602 #endif 00603 00604 #if defined(HAVE_AES_DECRYPT) && defined(WOLFSSL_AES_DIRECT) 00605 static int wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00606 { 00607 return wc_esp32AesDecrypt(aes, inBlock, outBlock); 00608 } 00609 #endif 00610 00611 #elif defined(WOLFSSL_AESNI) 00612 00613 #define NEED_AES_TABLES 00614 00615 /* Each platform needs to query info type 1 from cpuid to see if aesni is 00616 * supported. Also, let's setup a macro for proper linkage w/o ABI conflicts 00617 */ 00618 00619 #ifndef AESNI_ALIGN 00620 #define AESNI_ALIGN 16 00621 #endif 00622 00623 #ifdef _MSC_VER 00624 #define XASM_LINK(f) 00625 #elif defined(__APPLE__) 00626 #define XASM_LINK(f) asm("_" f) 00627 #else 00628 #define XASM_LINK(f) asm(f) 00629 #endif /* _MSC_VER */ 00630 00631 static int checkAESNI = 0; 00632 static int haveAESNI = 0; 00633 static word32 intel_flags = 0; 00634 00635 static int Check_CPU_support_AES(void) 00636 { 00637 intel_flags = cpuid_get_flags(); 00638 00639 return IS_INTEL_AESNI(intel_flags) != 0; 00640 } 00641 00642 00643 /* tell C compiler these are asm functions in case any mix up of ABI underscore 00644 prefix between clang/gcc/llvm etc */ 00645 #ifdef HAVE_AES_CBC 00646 void AES_CBC_encrypt(const unsigned char* in, unsigned char* out, 00647 unsigned char* ivec, unsigned long length, 00648 const unsigned char* KS, int nr) 00649 XASM_LINK("AES_CBC_encrypt"); 00650 00651 #ifdef HAVE_AES_DECRYPT 00652 #if defined(WOLFSSL_AESNI_BY4) 00653 void AES_CBC_decrypt_by4(const unsigned char* in, unsigned char* out, 00654 unsigned char* ivec, unsigned long length, 00655 const unsigned char* KS, int nr) 00656 XASM_LINK("AES_CBC_decrypt_by4"); 00657 #elif defined(WOLFSSL_AESNI_BY6) 00658 void AES_CBC_decrypt_by6(const unsigned char* in, unsigned char* out, 00659 unsigned char* ivec, unsigned long length, 00660 const unsigned char* KS, int nr) 00661 XASM_LINK("AES_CBC_decrypt_by6"); 00662 #else /* WOLFSSL_AESNI_BYx */ 00663 void AES_CBC_decrypt_by8(const unsigned char* in, unsigned char* out, 00664 unsigned char* ivec, unsigned long length, 00665 const unsigned char* KS, int nr) 00666 XASM_LINK("AES_CBC_decrypt_by8"); 00667 #endif /* WOLFSSL_AESNI_BYx */ 00668 #endif /* HAVE_AES_DECRYPT */ 00669 #endif /* HAVE_AES_CBC */ 00670 00671 void AES_ECB_encrypt(const unsigned char* in, unsigned char* out, 00672 unsigned long length, const unsigned char* KS, int nr) 00673 XASM_LINK("AES_ECB_encrypt"); 00674 00675 #ifdef HAVE_AES_DECRYPT 00676 void AES_ECB_decrypt(const unsigned char* in, unsigned char* out, 00677 unsigned long length, const unsigned char* KS, int nr) 00678 XASM_LINK("AES_ECB_decrypt"); 00679 #endif 00680 00681 void AES_128_Key_Expansion(const unsigned char* userkey, 00682 unsigned char* key_schedule) 00683 XASM_LINK("AES_128_Key_Expansion"); 00684 00685 void AES_192_Key_Expansion(const unsigned char* userkey, 00686 unsigned char* key_schedule) 00687 XASM_LINK("AES_192_Key_Expansion"); 00688 00689 void AES_256_Key_Expansion(const unsigned char* userkey, 00690 unsigned char* key_schedule) 00691 XASM_LINK("AES_256_Key_Expansion"); 00692 00693 00694 static int AES_set_encrypt_key(const unsigned char *userKey, const int bits, 00695 Aes* aes) 00696 { 00697 int ret; 00698 00699 if (!userKey || !aes) 00700 return BAD_FUNC_ARG; 00701 00702 switch (bits) { 00703 case 128: 00704 AES_128_Key_Expansion (userKey,(byte*)aes->key); aes->rounds = 10; 00705 return 0; 00706 case 192: 00707 AES_192_Key_Expansion (userKey,(byte*)aes->key); aes->rounds = 12; 00708 return 0; 00709 case 256: 00710 AES_256_Key_Expansion (userKey,(byte*)aes->key); aes->rounds = 14; 00711 return 0; 00712 default: 00713 ret = BAD_FUNC_ARG; 00714 } 00715 00716 return ret; 00717 } 00718 00719 #ifdef HAVE_AES_DECRYPT 00720 static int AES_set_decrypt_key(const unsigned char* userKey, 00721 const int bits, Aes* aes) 00722 { 00723 int nr; 00724 Aes temp_key; 00725 __m128i *Key_Schedule = (__m128i*)aes->key; 00726 __m128i *Temp_Key_Schedule = (__m128i*)temp_key.key; 00727 00728 if (!userKey || !aes) 00729 return BAD_FUNC_ARG; 00730 00731 if (AES_set_encrypt_key(userKey,bits,&temp_key) == BAD_FUNC_ARG) 00732 return BAD_FUNC_ARG; 00733 00734 nr = temp_key.rounds; 00735 aes->rounds = nr; 00736 00737 Key_Schedule[nr] = Temp_Key_Schedule[0]; 00738 Key_Schedule[nr-1] = _mm_aesimc_si128(Temp_Key_Schedule[1]); 00739 Key_Schedule[nr-2] = _mm_aesimc_si128(Temp_Key_Schedule[2]); 00740 Key_Schedule[nr-3] = _mm_aesimc_si128(Temp_Key_Schedule[3]); 00741 Key_Schedule[nr-4] = _mm_aesimc_si128(Temp_Key_Schedule[4]); 00742 Key_Schedule[nr-5] = _mm_aesimc_si128(Temp_Key_Schedule[5]); 00743 Key_Schedule[nr-6] = _mm_aesimc_si128(Temp_Key_Schedule[6]); 00744 Key_Schedule[nr-7] = _mm_aesimc_si128(Temp_Key_Schedule[7]); 00745 Key_Schedule[nr-8] = _mm_aesimc_si128(Temp_Key_Schedule[8]); 00746 Key_Schedule[nr-9] = _mm_aesimc_si128(Temp_Key_Schedule[9]); 00747 00748 if (nr>10) { 00749 Key_Schedule[nr-10] = _mm_aesimc_si128(Temp_Key_Schedule[10]); 00750 Key_Schedule[nr-11] = _mm_aesimc_si128(Temp_Key_Schedule[11]); 00751 } 00752 00753 if (nr>12) { 00754 Key_Schedule[nr-12] = _mm_aesimc_si128(Temp_Key_Schedule[12]); 00755 Key_Schedule[nr-13] = _mm_aesimc_si128(Temp_Key_Schedule[13]); 00756 } 00757 00758 Key_Schedule[0] = Temp_Key_Schedule[nr]; 00759 00760 return 0; 00761 } 00762 #endif /* HAVE_AES_DECRYPT */ 00763 00764 #elif (defined(WOLFSSL_IMX6_CAAM) && !defined(NO_IMX6_CAAM_AES)) || \ 00765 ((defined(WOLFSSL_AFALG) || defined(WOLFSSL_DEVCRYPTO_AES)) && \ 00766 defined(HAVE_AESCCM)) 00767 static int wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00768 { 00769 wc_AesEncryptDirect(aes, outBlock, inBlock); 00770 return 0; 00771 } 00772 00773 #elif defined(WOLFSSL_AFALG) 00774 #elif defined(WOLFSSL_DEVCRYPTO_AES) 00775 00776 #elif defined(WOLFSSL_SCE) && !defined(WOLFSSL_SCE_NO_AES) 00777 #include "hal_data.h" 00778 00779 #ifndef WOLFSSL_SCE_AES256_HANDLE 00780 #define WOLFSSL_SCE_AES256_HANDLE g_sce_aes_256 00781 #endif 00782 00783 #ifndef WOLFSSL_SCE_AES192_HANDLE 00784 #define WOLFSSL_SCE_AES192_HANDLE g_sce_aes_192 00785 #endif 00786 00787 #ifndef WOLFSSL_SCE_AES128_HANDLE 00788 #define WOLFSSL_SCE_AES128_HANDLE g_sce_aes_128 00789 #endif 00790 00791 static int AES_ECB_encrypt(Aes* aes, const byte* inBlock, byte* outBlock, 00792 int sz) 00793 { 00794 uint32_t ret; 00795 00796 if (WOLFSSL_SCE_GSCE_HANDLE.p_cfg->endian_flag == 00797 CRYPTO_WORD_ENDIAN_BIG) { 00798 ByteReverseWords((word32*)inBlock, (word32*)inBlock, sz); 00799 } 00800 00801 switch (aes->keylen) { 00802 #ifdef WOLFSSL_AES_128 00803 case AES_128_KEY_SIZE: 00804 ret = WOLFSSL_SCE_AES128_HANDLE.p_api->encrypt( 00805 WOLFSSL_SCE_AES128_HANDLE.p_ctrl, aes->key, 00806 NULL, (sz / sizeof(word32)), (word32*)inBlock, 00807 (word32*)outBlock); 00808 break; 00809 #endif 00810 #ifdef WOLFSSL_AES_192 00811 case AES_192_KEY_SIZE: 00812 ret = WOLFSSL_SCE_AES192_HANDLE.p_api->encrypt( 00813 WOLFSSL_SCE_AES192_HANDLE.p_ctrl, aes->key, 00814 NULL, (sz / sizeof(word32)), (word32*)inBlock, 00815 (word32*)outBlock); 00816 break; 00817 #endif 00818 #ifdef WOLFSSL_AES_256 00819 case AES_256_KEY_SIZE: 00820 ret = WOLFSSL_SCE_AES256_HANDLE.p_api->encrypt( 00821 WOLFSSL_SCE_AES256_HANDLE.p_ctrl, aes->key, 00822 NULL, (sz / sizeof(word32)), (word32*)inBlock, 00823 (word32*)outBlock); 00824 break; 00825 #endif 00826 default: 00827 WOLFSSL_MSG("Unknown key size"); 00828 return BAD_FUNC_ARG; 00829 } 00830 00831 if (ret != SSP_SUCCESS) { 00832 /* revert input */ 00833 ByteReverseWords((word32*)inBlock, (word32*)inBlock, sz); 00834 return WC_HW_E; 00835 } 00836 00837 if (WOLFSSL_SCE_GSCE_HANDLE.p_cfg->endian_flag == 00838 CRYPTO_WORD_ENDIAN_BIG) { 00839 ByteReverseWords((word32*)outBlock, (word32*)outBlock, sz); 00840 if (inBlock != outBlock) { 00841 /* revert input */ 00842 ByteReverseWords((word32*)inBlock, (word32*)inBlock, sz); 00843 } 00844 } 00845 return 0; 00846 } 00847 00848 #if defined(HAVE_AES_DECRYPT) 00849 static int AES_ECB_decrypt(Aes* aes, const byte* inBlock, byte* outBlock, 00850 int sz) 00851 { 00852 uint32_t ret; 00853 00854 if (WOLFSSL_SCE_GSCE_HANDLE.p_cfg->endian_flag == 00855 CRYPTO_WORD_ENDIAN_BIG) { 00856 ByteReverseWords((word32*)inBlock, (word32*)inBlock, sz); 00857 } 00858 00859 switch (aes->keylen) { 00860 #ifdef WOLFSSL_AES_128 00861 case AES_128_KEY_SIZE: 00862 ret = WOLFSSL_SCE_AES128_HANDLE.p_api->decrypt( 00863 WOLFSSL_SCE_AES128_HANDLE.p_ctrl, aes->key, aes->reg, 00864 (sz / sizeof(word32)), (word32*)inBlock, 00865 (word32*)outBlock); 00866 break; 00867 #endif 00868 #ifdef WOLFSSL_AES_192 00869 case AES_192_KEY_SIZE: 00870 ret = WOLFSSL_SCE_AES192_HANDLE.p_api->decrypt( 00871 WOLFSSL_SCE_AES192_HANDLE.p_ctrl, aes->key, aes->reg, 00872 (sz / sizeof(word32)), (word32*)inBlock, 00873 (word32*)outBlock); 00874 break; 00875 #endif 00876 #ifdef WOLFSSL_AES_256 00877 case AES_256_KEY_SIZE: 00878 ret = WOLFSSL_SCE_AES256_HANDLE.p_api->decrypt( 00879 WOLFSSL_SCE_AES256_HANDLE.p_ctrl, aes->key, aes->reg, 00880 (sz / sizeof(word32)), (word32*)inBlock, 00881 (word32*)outBlock); 00882 break; 00883 #endif 00884 default: 00885 WOLFSSL_MSG("Unknown key size"); 00886 return BAD_FUNC_ARG; 00887 } 00888 if (ret != SSP_SUCCESS) { 00889 return WC_HW_E; 00890 } 00891 00892 if (WOLFSSL_SCE_GSCE_HANDLE.p_cfg->endian_flag == 00893 CRYPTO_WORD_ENDIAN_BIG) { 00894 ByteReverseWords((word32*)outBlock, (word32*)outBlock, sz); 00895 if (inBlock != outBlock) { 00896 /* revert input */ 00897 ByteReverseWords((word32*)inBlock, (word32*)inBlock, sz); 00898 } 00899 } 00900 00901 return 0; 00902 } 00903 00904 #endif 00905 00906 #if defined(HAVE_AESGCM) || defined(WOLFSSL_AES_DIRECT) 00907 static int wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00908 { 00909 return AES_ECB_encrypt(aes, inBlock, outBlock, AES_BLOCK_SIZE); 00910 } 00911 #endif 00912 00913 #if defined(HAVE_AES_DECRYPT) && defined(WOLFSSL_AES_DIRECT) 00914 static int wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock) 00915 { 00916 return AES_ECB_decrypt(aes, inBlock, outBlock, AES_BLOCK_SIZE); 00917 } 00918 #endif 00919 #else 00920 00921 /* using wolfCrypt software implementation */ 00922 #define NEED_AES_TABLES 00923 #endif 00924 00925 00926 00927 #ifdef NEED_AES_TABLES 00928 00929 static const word32 rcon[] = { 00930 0x01000000, 0x02000000, 0x04000000, 0x08000000, 00931 0x10000000, 0x20000000, 0x40000000, 0x80000000, 00932 0x1B000000, 0x36000000, 00933 /* for 128-bit blocks, Rijndael never uses more than 10 rcon values */ 00934 }; 00935 00936 #ifndef WOLFSSL_AES_SMALL_TABLES 00937 static const word32 Te[4][256] = { 00938 { 00939 0xc66363a5U, 0xf87c7c84U, 0xee777799U, 0xf67b7b8dU, 00940 0xfff2f20dU, 0xd66b6bbdU, 0xde6f6fb1U, 0x91c5c554U, 00941 0x60303050U, 0x02010103U, 0xce6767a9U, 0x562b2b7dU, 00942 0xe7fefe19U, 0xb5d7d762U, 0x4dababe6U, 0xec76769aU, 00943 0x8fcaca45U, 0x1f82829dU, 0x89c9c940U, 0xfa7d7d87U, 00944 0xeffafa15U, 0xb25959ebU, 0x8e4747c9U, 0xfbf0f00bU, 00945 0x41adadecU, 0xb3d4d467U, 0x5fa2a2fdU, 0x45afafeaU, 00946 0x239c9cbfU, 0x53a4a4f7U, 0xe4727296U, 0x9bc0c05bU, 00947 0x75b7b7c2U, 0xe1fdfd1cU, 0x3d9393aeU, 0x4c26266aU, 00948 0x6c36365aU, 0x7e3f3f41U, 0xf5f7f702U, 0x83cccc4fU, 00949 0x6834345cU, 0x51a5a5f4U, 0xd1e5e534U, 0xf9f1f108U, 00950 0xe2717193U, 0xabd8d873U, 0x62313153U, 0x2a15153fU, 00951 0x0804040cU, 0x95c7c752U, 0x46232365U, 0x9dc3c35eU, 00952 0x30181828U, 0x379696a1U, 0x0a05050fU, 0x2f9a9ab5U, 00953 0x0e070709U, 0x24121236U, 0x1b80809bU, 0xdfe2e23dU, 00954 0xcdebeb26U, 0x4e272769U, 0x7fb2b2cdU, 0xea75759fU, 00955 0x1209091bU, 0x1d83839eU, 0x582c2c74U, 0x341a1a2eU, 00956 0x361b1b2dU, 0xdc6e6eb2U, 0xb45a5aeeU, 0x5ba0a0fbU, 00957 0xa45252f6U, 0x763b3b4dU, 0xb7d6d661U, 0x7db3b3ceU, 00958 0x5229297bU, 0xdde3e33eU, 0x5e2f2f71U, 0x13848497U, 00959 0xa65353f5U, 0xb9d1d168U, 0x00000000U, 0xc1eded2cU, 00960 0x40202060U, 0xe3fcfc1fU, 0x79b1b1c8U, 0xb65b5bedU, 00961 0xd46a6abeU, 0x8dcbcb46U, 0x67bebed9U, 0x7239394bU, 00962 0x944a4adeU, 0x984c4cd4U, 0xb05858e8U, 0x85cfcf4aU, 00963 0xbbd0d06bU, 0xc5efef2aU, 0x4faaaae5U, 0xedfbfb16U, 00964 0x864343c5U, 0x9a4d4dd7U, 0x66333355U, 0x11858594U, 00965 0x8a4545cfU, 0xe9f9f910U, 0x04020206U, 0xfe7f7f81U, 00966 0xa05050f0U, 0x783c3c44U, 0x259f9fbaU, 0x4ba8a8e3U, 00967 0xa25151f3U, 0x5da3a3feU, 0x804040c0U, 0x058f8f8aU, 00968 0x3f9292adU, 0x219d9dbcU, 0x70383848U, 0xf1f5f504U, 00969 0x63bcbcdfU, 0x77b6b6c1U, 0xafdada75U, 0x42212163U, 00970 0x20101030U, 0xe5ffff1aU, 0xfdf3f30eU, 0xbfd2d26dU, 00971 0x81cdcd4cU, 0x180c0c14U, 0x26131335U, 0xc3ecec2fU, 00972 0xbe5f5fe1U, 0x359797a2U, 0x884444ccU, 0x2e171739U, 00973 0x93c4c457U, 0x55a7a7f2U, 0xfc7e7e82U, 0x7a3d3d47U, 00974 0xc86464acU, 0xba5d5de7U, 0x3219192bU, 0xe6737395U, 00975 0xc06060a0U, 0x19818198U, 0x9e4f4fd1U, 0xa3dcdc7fU, 00976 0x44222266U, 0x542a2a7eU, 0x3b9090abU, 0x0b888883U, 00977 0x8c4646caU, 0xc7eeee29U, 0x6bb8b8d3U, 0x2814143cU, 00978 0xa7dede79U, 0xbc5e5ee2U, 0x160b0b1dU, 0xaddbdb76U, 00979 0xdbe0e03bU, 0x64323256U, 0x743a3a4eU, 0x140a0a1eU, 00980 0x924949dbU, 0x0c06060aU, 0x4824246cU, 0xb85c5ce4U, 00981 0x9fc2c25dU, 0xbdd3d36eU, 0x43acacefU, 0xc46262a6U, 00982 0x399191a8U, 0x319595a4U, 0xd3e4e437U, 0xf279798bU, 00983 0xd5e7e732U, 0x8bc8c843U, 0x6e373759U, 0xda6d6db7U, 00984 0x018d8d8cU, 0xb1d5d564U, 0x9c4e4ed2U, 0x49a9a9e0U, 00985 0xd86c6cb4U, 0xac5656faU, 0xf3f4f407U, 0xcfeaea25U, 00986 0xca6565afU, 0xf47a7a8eU, 0x47aeaee9U, 0x10080818U, 00987 0x6fbabad5U, 0xf0787888U, 0x4a25256fU, 0x5c2e2e72U, 00988 0x381c1c24U, 0x57a6a6f1U, 0x73b4b4c7U, 0x97c6c651U, 00989 0xcbe8e823U, 0xa1dddd7cU, 0xe874749cU, 0x3e1f1f21U, 00990 0x964b4bddU, 0x61bdbddcU, 0x0d8b8b86U, 0x0f8a8a85U, 00991 0xe0707090U, 0x7c3e3e42U, 0x71b5b5c4U, 0xcc6666aaU, 00992 0x904848d8U, 0x06030305U, 0xf7f6f601U, 0x1c0e0e12U, 00993 0xc26161a3U, 0x6a35355fU, 0xae5757f9U, 0x69b9b9d0U, 00994 0x17868691U, 0x99c1c158U, 0x3a1d1d27U, 0x279e9eb9U, 00995 0xd9e1e138U, 0xebf8f813U, 0x2b9898b3U, 0x22111133U, 00996 0xd26969bbU, 0xa9d9d970U, 0x078e8e89U, 0x339494a7U, 00997 0x2d9b9bb6U, 0x3c1e1e22U, 0x15878792U, 0xc9e9e920U, 00998 0x87cece49U, 0xaa5555ffU, 0x50282878U, 0xa5dfdf7aU, 00999 0x038c8c8fU, 0x59a1a1f8U, 0x09898980U, 0x1a0d0d17U, 01000 0x65bfbfdaU, 0xd7e6e631U, 0x844242c6U, 0xd06868b8U, 01001 0x824141c3U, 0x299999b0U, 0x5a2d2d77U, 0x1e0f0f11U, 01002 0x7bb0b0cbU, 0xa85454fcU, 0x6dbbbbd6U, 0x2c16163aU, 01003 }, 01004 { 01005 0xa5c66363U, 0x84f87c7cU, 0x99ee7777U, 0x8df67b7bU, 01006 0x0dfff2f2U, 0xbdd66b6bU, 0xb1de6f6fU, 0x5491c5c5U, 01007 0x50603030U, 0x03020101U, 0xa9ce6767U, 0x7d562b2bU, 01008 0x19e7fefeU, 0x62b5d7d7U, 0xe64dababU, 0x9aec7676U, 01009 0x458fcacaU, 0x9d1f8282U, 0x4089c9c9U, 0x87fa7d7dU, 01010 0x15effafaU, 0xebb25959U, 0xc98e4747U, 0x0bfbf0f0U, 01011 0xec41adadU, 0x67b3d4d4U, 0xfd5fa2a2U, 0xea45afafU, 01012 0xbf239c9cU, 0xf753a4a4U, 0x96e47272U, 0x5b9bc0c0U, 01013 0xc275b7b7U, 0x1ce1fdfdU, 0xae3d9393U, 0x6a4c2626U, 01014 0x5a6c3636U, 0x417e3f3fU, 0x02f5f7f7U, 0x4f83ccccU, 01015 0x5c683434U, 0xf451a5a5U, 0x34d1e5e5U, 0x08f9f1f1U, 01016 0x93e27171U, 0x73abd8d8U, 0x53623131U, 0x3f2a1515U, 01017 0x0c080404U, 0x5295c7c7U, 0x65462323U, 0x5e9dc3c3U, 01018 0x28301818U, 0xa1379696U, 0x0f0a0505U, 0xb52f9a9aU, 01019 0x090e0707U, 0x36241212U, 0x9b1b8080U, 0x3ddfe2e2U, 01020 0x26cdebebU, 0x694e2727U, 0xcd7fb2b2U, 0x9fea7575U, 01021 0x1b120909U, 0x9e1d8383U, 0x74582c2cU, 0x2e341a1aU, 01022 0x2d361b1bU, 0xb2dc6e6eU, 0xeeb45a5aU, 0xfb5ba0a0U, 01023 0xf6a45252U, 0x4d763b3bU, 0x61b7d6d6U, 0xce7db3b3U, 01024 0x7b522929U, 0x3edde3e3U, 0x715e2f2fU, 0x97138484U, 01025 0xf5a65353U, 0x68b9d1d1U, 0x00000000U, 0x2cc1ededU, 01026 0x60402020U, 0x1fe3fcfcU, 0xc879b1b1U, 0xedb65b5bU, 01027 0xbed46a6aU, 0x468dcbcbU, 0xd967bebeU, 0x4b723939U, 01028 0xde944a4aU, 0xd4984c4cU, 0xe8b05858U, 0x4a85cfcfU, 01029 0x6bbbd0d0U, 0x2ac5efefU, 0xe54faaaaU, 0x16edfbfbU, 01030 0xc5864343U, 0xd79a4d4dU, 0x55663333U, 0x94118585U, 01031 0xcf8a4545U, 0x10e9f9f9U, 0x06040202U, 0x81fe7f7fU, 01032 0xf0a05050U, 0x44783c3cU, 0xba259f9fU, 0xe34ba8a8U, 01033 0xf3a25151U, 0xfe5da3a3U, 0xc0804040U, 0x8a058f8fU, 01034 0xad3f9292U, 0xbc219d9dU, 0x48703838U, 0x04f1f5f5U, 01035 0xdf63bcbcU, 0xc177b6b6U, 0x75afdadaU, 0x63422121U, 01036 0x30201010U, 0x1ae5ffffU, 0x0efdf3f3U, 0x6dbfd2d2U, 01037 0x4c81cdcdU, 0x14180c0cU, 0x35261313U, 0x2fc3ececU, 01038 0xe1be5f5fU, 0xa2359797U, 0xcc884444U, 0x392e1717U, 01039 0x5793c4c4U, 0xf255a7a7U, 0x82fc7e7eU, 0x477a3d3dU, 01040 0xacc86464U, 0xe7ba5d5dU, 0x2b321919U, 0x95e67373U, 01041 0xa0c06060U, 0x98198181U, 0xd19e4f4fU, 0x7fa3dcdcU, 01042 0x66442222U, 0x7e542a2aU, 0xab3b9090U, 0x830b8888U, 01043 0xca8c4646U, 0x29c7eeeeU, 0xd36bb8b8U, 0x3c281414U, 01044 0x79a7dedeU, 0xe2bc5e5eU, 0x1d160b0bU, 0x76addbdbU, 01045 0x3bdbe0e0U, 0x56643232U, 0x4e743a3aU, 0x1e140a0aU, 01046 0xdb924949U, 0x0a0c0606U, 0x6c482424U, 0xe4b85c5cU, 01047 0x5d9fc2c2U, 0x6ebdd3d3U, 0xef43acacU, 0xa6c46262U, 01048 0xa8399191U, 0xa4319595U, 0x37d3e4e4U, 0x8bf27979U, 01049 0x32d5e7e7U, 0x438bc8c8U, 0x596e3737U, 0xb7da6d6dU, 01050 0x8c018d8dU, 0x64b1d5d5U, 0xd29c4e4eU, 0xe049a9a9U, 01051 0xb4d86c6cU, 0xfaac5656U, 0x07f3f4f4U, 0x25cfeaeaU, 01052 0xafca6565U, 0x8ef47a7aU, 0xe947aeaeU, 0x18100808U, 01053 0xd56fbabaU, 0x88f07878U, 0x6f4a2525U, 0x725c2e2eU, 01054 0x24381c1cU, 0xf157a6a6U, 0xc773b4b4U, 0x5197c6c6U, 01055 0x23cbe8e8U, 0x7ca1ddddU, 0x9ce87474U, 0x213e1f1fU, 01056 0xdd964b4bU, 0xdc61bdbdU, 0x860d8b8bU, 0x850f8a8aU, 01057 0x90e07070U, 0x427c3e3eU, 0xc471b5b5U, 0xaacc6666U, 01058 0xd8904848U, 0x05060303U, 0x01f7f6f6U, 0x121c0e0eU, 01059 0xa3c26161U, 0x5f6a3535U, 0xf9ae5757U, 0xd069b9b9U, 01060 0x91178686U, 0x5899c1c1U, 0x273a1d1dU, 0xb9279e9eU, 01061 0x38d9e1e1U, 0x13ebf8f8U, 0xb32b9898U, 0x33221111U, 01062 0xbbd26969U, 0x70a9d9d9U, 0x89078e8eU, 0xa7339494U, 01063 0xb62d9b9bU, 0x223c1e1eU, 0x92158787U, 0x20c9e9e9U, 01064 0x4987ceceU, 0xffaa5555U, 0x78502828U, 0x7aa5dfdfU, 01065 0x8f038c8cU, 0xf859a1a1U, 0x80098989U, 0x171a0d0dU, 01066 0xda65bfbfU, 0x31d7e6e6U, 0xc6844242U, 0xb8d06868U, 01067 0xc3824141U, 0xb0299999U, 0x775a2d2dU, 0x111e0f0fU, 01068 0xcb7bb0b0U, 0xfca85454U, 0xd66dbbbbU, 0x3a2c1616U, 01069 }, 01070 { 01071 0x63a5c663U, 0x7c84f87cU, 0x7799ee77U, 0x7b8df67bU, 01072 0xf20dfff2U, 0x6bbdd66bU, 0x6fb1de6fU, 0xc55491c5U, 01073 0x30506030U, 0x01030201U, 0x67a9ce67U, 0x2b7d562bU, 01074 0xfe19e7feU, 0xd762b5d7U, 0xabe64dabU, 0x769aec76U, 01075 0xca458fcaU, 0x829d1f82U, 0xc94089c9U, 0x7d87fa7dU, 01076 0xfa15effaU, 0x59ebb259U, 0x47c98e47U, 0xf00bfbf0U, 01077 0xadec41adU, 0xd467b3d4U, 0xa2fd5fa2U, 0xafea45afU, 01078 0x9cbf239cU, 0xa4f753a4U, 0x7296e472U, 0xc05b9bc0U, 01079 0xb7c275b7U, 0xfd1ce1fdU, 0x93ae3d93U, 0x266a4c26U, 01080 0x365a6c36U, 0x3f417e3fU, 0xf702f5f7U, 0xcc4f83ccU, 01081 0x345c6834U, 0xa5f451a5U, 0xe534d1e5U, 0xf108f9f1U, 01082 0x7193e271U, 0xd873abd8U, 0x31536231U, 0x153f2a15U, 01083 0x040c0804U, 0xc75295c7U, 0x23654623U, 0xc35e9dc3U, 01084 0x18283018U, 0x96a13796U, 0x050f0a05U, 0x9ab52f9aU, 01085 0x07090e07U, 0x12362412U, 0x809b1b80U, 0xe23ddfe2U, 01086 0xeb26cdebU, 0x27694e27U, 0xb2cd7fb2U, 0x759fea75U, 01087 0x091b1209U, 0x839e1d83U, 0x2c74582cU, 0x1a2e341aU, 01088 0x1b2d361bU, 0x6eb2dc6eU, 0x5aeeb45aU, 0xa0fb5ba0U, 01089 0x52f6a452U, 0x3b4d763bU, 0xd661b7d6U, 0xb3ce7db3U, 01090 0x297b5229U, 0xe33edde3U, 0x2f715e2fU, 0x84971384U, 01091 0x53f5a653U, 0xd168b9d1U, 0x00000000U, 0xed2cc1edU, 01092 0x20604020U, 0xfc1fe3fcU, 0xb1c879b1U, 0x5bedb65bU, 01093 0x6abed46aU, 0xcb468dcbU, 0xbed967beU, 0x394b7239U, 01094 0x4ade944aU, 0x4cd4984cU, 0x58e8b058U, 0xcf4a85cfU, 01095 0xd06bbbd0U, 0xef2ac5efU, 0xaae54faaU, 0xfb16edfbU, 01096 0x43c58643U, 0x4dd79a4dU, 0x33556633U, 0x85941185U, 01097 0x45cf8a45U, 0xf910e9f9U, 0x02060402U, 0x7f81fe7fU, 01098 0x50f0a050U, 0x3c44783cU, 0x9fba259fU, 0xa8e34ba8U, 01099 0x51f3a251U, 0xa3fe5da3U, 0x40c08040U, 0x8f8a058fU, 01100 0x92ad3f92U, 0x9dbc219dU, 0x38487038U, 0xf504f1f5U, 01101 0xbcdf63bcU, 0xb6c177b6U, 0xda75afdaU, 0x21634221U, 01102 0x10302010U, 0xff1ae5ffU, 0xf30efdf3U, 0xd26dbfd2U, 01103 0xcd4c81cdU, 0x0c14180cU, 0x13352613U, 0xec2fc3ecU, 01104 0x5fe1be5fU, 0x97a23597U, 0x44cc8844U, 0x17392e17U, 01105 0xc45793c4U, 0xa7f255a7U, 0x7e82fc7eU, 0x3d477a3dU, 01106 0x64acc864U, 0x5de7ba5dU, 0x192b3219U, 0x7395e673U, 01107 0x60a0c060U, 0x81981981U, 0x4fd19e4fU, 0xdc7fa3dcU, 01108 0x22664422U, 0x2a7e542aU, 0x90ab3b90U, 0x88830b88U, 01109 0x46ca8c46U, 0xee29c7eeU, 0xb8d36bb8U, 0x143c2814U, 01110 0xde79a7deU, 0x5ee2bc5eU, 0x0b1d160bU, 0xdb76addbU, 01111 0xe03bdbe0U, 0x32566432U, 0x3a4e743aU, 0x0a1e140aU, 01112 0x49db9249U, 0x060a0c06U, 0x246c4824U, 0x5ce4b85cU, 01113 0xc25d9fc2U, 0xd36ebdd3U, 0xacef43acU, 0x62a6c462U, 01114 0x91a83991U, 0x95a43195U, 0xe437d3e4U, 0x798bf279U, 01115 0xe732d5e7U, 0xc8438bc8U, 0x37596e37U, 0x6db7da6dU, 01116 0x8d8c018dU, 0xd564b1d5U, 0x4ed29c4eU, 0xa9e049a9U, 01117 0x6cb4d86cU, 0x56faac56U, 0xf407f3f4U, 0xea25cfeaU, 01118 0x65afca65U, 0x7a8ef47aU, 0xaee947aeU, 0x08181008U, 01119 0xbad56fbaU, 0x7888f078U, 0x256f4a25U, 0x2e725c2eU, 01120 0x1c24381cU, 0xa6f157a6U, 0xb4c773b4U, 0xc65197c6U, 01121 0xe823cbe8U, 0xdd7ca1ddU, 0x749ce874U, 0x1f213e1fU, 01122 0x4bdd964bU, 0xbddc61bdU, 0x8b860d8bU, 0x8a850f8aU, 01123 0x7090e070U, 0x3e427c3eU, 0xb5c471b5U, 0x66aacc66U, 01124 0x48d89048U, 0x03050603U, 0xf601f7f6U, 0x0e121c0eU, 01125 0x61a3c261U, 0x355f6a35U, 0x57f9ae57U, 0xb9d069b9U, 01126 0x86911786U, 0xc15899c1U, 0x1d273a1dU, 0x9eb9279eU, 01127 0xe138d9e1U, 0xf813ebf8U, 0x98b32b98U, 0x11332211U, 01128 0x69bbd269U, 0xd970a9d9U, 0x8e89078eU, 0x94a73394U, 01129 0x9bb62d9bU, 0x1e223c1eU, 0x87921587U, 0xe920c9e9U, 01130 0xce4987ceU, 0x55ffaa55U, 0x28785028U, 0xdf7aa5dfU, 01131 0x8c8f038cU, 0xa1f859a1U, 0x89800989U, 0x0d171a0dU, 01132 0xbfda65bfU, 0xe631d7e6U, 0x42c68442U, 0x68b8d068U, 01133 0x41c38241U, 0x99b02999U, 0x2d775a2dU, 0x0f111e0fU, 01134 0xb0cb7bb0U, 0x54fca854U, 0xbbd66dbbU, 0x163a2c16U, 01135 }, 01136 { 01137 0x6363a5c6U, 0x7c7c84f8U, 0x777799eeU, 0x7b7b8df6U, 01138 0xf2f20dffU, 0x6b6bbdd6U, 0x6f6fb1deU, 0xc5c55491U, 01139 0x30305060U, 0x01010302U, 0x6767a9ceU, 0x2b2b7d56U, 01140 0xfefe19e7U, 0xd7d762b5U, 0xababe64dU, 0x76769aecU, 01141 0xcaca458fU, 0x82829d1fU, 0xc9c94089U, 0x7d7d87faU, 01142 0xfafa15efU, 0x5959ebb2U, 0x4747c98eU, 0xf0f00bfbU, 01143 0xadadec41U, 0xd4d467b3U, 0xa2a2fd5fU, 0xafafea45U, 01144 0x9c9cbf23U, 0xa4a4f753U, 0x727296e4U, 0xc0c05b9bU, 01145 0xb7b7c275U, 0xfdfd1ce1U, 0x9393ae3dU, 0x26266a4cU, 01146 0x36365a6cU, 0x3f3f417eU, 0xf7f702f5U, 0xcccc4f83U, 01147 0x34345c68U, 0xa5a5f451U, 0xe5e534d1U, 0xf1f108f9U, 01148 0x717193e2U, 0xd8d873abU, 0x31315362U, 0x15153f2aU, 01149 0x04040c08U, 0xc7c75295U, 0x23236546U, 0xc3c35e9dU, 01150 0x18182830U, 0x9696a137U, 0x05050f0aU, 0x9a9ab52fU, 01151 0x0707090eU, 0x12123624U, 0x80809b1bU, 0xe2e23ddfU, 01152 0xebeb26cdU, 0x2727694eU, 0xb2b2cd7fU, 0x75759feaU, 01153 0x09091b12U, 0x83839e1dU, 0x2c2c7458U, 0x1a1a2e34U, 01154 0x1b1b2d36U, 0x6e6eb2dcU, 0x5a5aeeb4U, 0xa0a0fb5bU, 01155 0x5252f6a4U, 0x3b3b4d76U, 0xd6d661b7U, 0xb3b3ce7dU, 01156 0x29297b52U, 0xe3e33eddU, 0x2f2f715eU, 0x84849713U, 01157 0x5353f5a6U, 0xd1d168b9U, 0x00000000U, 0xeded2cc1U, 01158 0x20206040U, 0xfcfc1fe3U, 0xb1b1c879U, 0x5b5bedb6U, 01159 0x6a6abed4U, 0xcbcb468dU, 0xbebed967U, 0x39394b72U, 01160 0x4a4ade94U, 0x4c4cd498U, 0x5858e8b0U, 0xcfcf4a85U, 01161 0xd0d06bbbU, 0xefef2ac5U, 0xaaaae54fU, 0xfbfb16edU, 01162 0x4343c586U, 0x4d4dd79aU, 0x33335566U, 0x85859411U, 01163 0x4545cf8aU, 0xf9f910e9U, 0x02020604U, 0x7f7f81feU, 01164 0x5050f0a0U, 0x3c3c4478U, 0x9f9fba25U, 0xa8a8e34bU, 01165 0x5151f3a2U, 0xa3a3fe5dU, 0x4040c080U, 0x8f8f8a05U, 01166 0x9292ad3fU, 0x9d9dbc21U, 0x38384870U, 0xf5f504f1U, 01167 0xbcbcdf63U, 0xb6b6c177U, 0xdada75afU, 0x21216342U, 01168 0x10103020U, 0xffff1ae5U, 0xf3f30efdU, 0xd2d26dbfU, 01169 0xcdcd4c81U, 0x0c0c1418U, 0x13133526U, 0xecec2fc3U, 01170 0x5f5fe1beU, 0x9797a235U, 0x4444cc88U, 0x1717392eU, 01171 0xc4c45793U, 0xa7a7f255U, 0x7e7e82fcU, 0x3d3d477aU, 01172 0x6464acc8U, 0x5d5de7baU, 0x19192b32U, 0x737395e6U, 01173 0x6060a0c0U, 0x81819819U, 0x4f4fd19eU, 0xdcdc7fa3U, 01174 0x22226644U, 0x2a2a7e54U, 0x9090ab3bU, 0x8888830bU, 01175 0x4646ca8cU, 0xeeee29c7U, 0xb8b8d36bU, 0x14143c28U, 01176 0xdede79a7U, 0x5e5ee2bcU, 0x0b0b1d16U, 0xdbdb76adU, 01177 0xe0e03bdbU, 0x32325664U, 0x3a3a4e74U, 0x0a0a1e14U, 01178 0x4949db92U, 0x06060a0cU, 0x24246c48U, 0x5c5ce4b8U, 01179 0xc2c25d9fU, 0xd3d36ebdU, 0xacacef43U, 0x6262a6c4U, 01180 0x9191a839U, 0x9595a431U, 0xe4e437d3U, 0x79798bf2U, 01181 0xe7e732d5U, 0xc8c8438bU, 0x3737596eU, 0x6d6db7daU, 01182 0x8d8d8c01U, 0xd5d564b1U, 0x4e4ed29cU, 0xa9a9e049U, 01183 0x6c6cb4d8U, 0x5656faacU, 0xf4f407f3U, 0xeaea25cfU, 01184 0x6565afcaU, 0x7a7a8ef4U, 0xaeaee947U, 0x08081810U, 01185 0xbabad56fU, 0x787888f0U, 0x25256f4aU, 0x2e2e725cU, 01186 0x1c1c2438U, 0xa6a6f157U, 0xb4b4c773U, 0xc6c65197U, 01187 0xe8e823cbU, 0xdddd7ca1U, 0x74749ce8U, 0x1f1f213eU, 01188 0x4b4bdd96U, 0xbdbddc61U, 0x8b8b860dU, 0x8a8a850fU, 01189 0x707090e0U, 0x3e3e427cU, 0xb5b5c471U, 0x6666aaccU, 01190 0x4848d890U, 0x03030506U, 0xf6f601f7U, 0x0e0e121cU, 01191 0x6161a3c2U, 0x35355f6aU, 0x5757f9aeU, 0xb9b9d069U, 01192 0x86869117U, 0xc1c15899U, 0x1d1d273aU, 0x9e9eb927U, 01193 0xe1e138d9U, 0xf8f813ebU, 0x9898b32bU, 0x11113322U, 01194 0x6969bbd2U, 0xd9d970a9U, 0x8e8e8907U, 0x9494a733U, 01195 0x9b9bb62dU, 0x1e1e223cU, 0x87879215U, 0xe9e920c9U, 01196 0xcece4987U, 0x5555ffaaU, 0x28287850U, 0xdfdf7aa5U, 01197 0x8c8c8f03U, 0xa1a1f859U, 0x89898009U, 0x0d0d171aU, 01198 0xbfbfda65U, 0xe6e631d7U, 0x4242c684U, 0x6868b8d0U, 01199 0x4141c382U, 0x9999b029U, 0x2d2d775aU, 0x0f0f111eU, 01200 0xb0b0cb7bU, 0x5454fca8U, 0xbbbbd66dU, 0x16163a2cU, 01201 } 01202 }; 01203 01204 #ifdef HAVE_AES_DECRYPT 01205 static const word32 Td[4][256] = { 01206 { 01207 0x51f4a750U, 0x7e416553U, 0x1a17a4c3U, 0x3a275e96U, 01208 0x3bab6bcbU, 0x1f9d45f1U, 0xacfa58abU, 0x4be30393U, 01209 0x2030fa55U, 0xad766df6U, 0x88cc7691U, 0xf5024c25U, 01210 0x4fe5d7fcU, 0xc52acbd7U, 0x26354480U, 0xb562a38fU, 01211 0xdeb15a49U, 0x25ba1b67U, 0x45ea0e98U, 0x5dfec0e1U, 01212 0xc32f7502U, 0x814cf012U, 0x8d4697a3U, 0x6bd3f9c6U, 01213 0x038f5fe7U, 0x15929c95U, 0xbf6d7aebU, 0x955259daU, 01214 0xd4be832dU, 0x587421d3U, 0x49e06929U, 0x8ec9c844U, 01215 0x75c2896aU, 0xf48e7978U, 0x99583e6bU, 0x27b971ddU, 01216 0xbee14fb6U, 0xf088ad17U, 0xc920ac66U, 0x7dce3ab4U, 01217 0x63df4a18U, 0xe51a3182U, 0x97513360U, 0x62537f45U, 01218 0xb16477e0U, 0xbb6bae84U, 0xfe81a01cU, 0xf9082b94U, 01219 0x70486858U, 0x8f45fd19U, 0x94de6c87U, 0x527bf8b7U, 01220 0xab73d323U, 0x724b02e2U, 0xe31f8f57U, 0x6655ab2aU, 01221 0xb2eb2807U, 0x2fb5c203U, 0x86c57b9aU, 0xd33708a5U, 01222 0x302887f2U, 0x23bfa5b2U, 0x02036abaU, 0xed16825cU, 01223 0x8acf1c2bU, 0xa779b492U, 0xf307f2f0U, 0x4e69e2a1U, 01224 0x65daf4cdU, 0x0605bed5U, 0xd134621fU, 0xc4a6fe8aU, 01225 0x342e539dU, 0xa2f355a0U, 0x058ae132U, 0xa4f6eb75U, 01226 0x0b83ec39U, 0x4060efaaU, 0x5e719f06U, 0xbd6e1051U, 01227 0x3e218af9U, 0x96dd063dU, 0xdd3e05aeU, 0x4de6bd46U, 01228 0x91548db5U, 0x71c45d05U, 0x0406d46fU, 0x605015ffU, 01229 0x1998fb24U, 0xd6bde997U, 0x894043ccU, 0x67d99e77U, 01230 0xb0e842bdU, 0x07898b88U, 0xe7195b38U, 0x79c8eedbU, 01231 0xa17c0a47U, 0x7c420fe9U, 0xf8841ec9U, 0x00000000U, 01232 0x09808683U, 0x322bed48U, 0x1e1170acU, 0x6c5a724eU, 01233 0xfd0efffbU, 0x0f853856U, 0x3daed51eU, 0x362d3927U, 01234 0x0a0fd964U, 0x685ca621U, 0x9b5b54d1U, 0x24362e3aU, 01235 0x0c0a67b1U, 0x9357e70fU, 0xb4ee96d2U, 0x1b9b919eU, 01236 0x80c0c54fU, 0x61dc20a2U, 0x5a774b69U, 0x1c121a16U, 01237 0xe293ba0aU, 0xc0a02ae5U, 0x3c22e043U, 0x121b171dU, 01238 0x0e090d0bU, 0xf28bc7adU, 0x2db6a8b9U, 0x141ea9c8U, 01239 0x57f11985U, 0xaf75074cU, 0xee99ddbbU, 0xa37f60fdU, 01240 0xf701269fU, 0x5c72f5bcU, 0x44663bc5U, 0x5bfb7e34U, 01241 0x8b432976U, 0xcb23c6dcU, 0xb6edfc68U, 0xb8e4f163U, 01242 0xd731dccaU, 0x42638510U, 0x13972240U, 0x84c61120U, 01243 0x854a247dU, 0xd2bb3df8U, 0xaef93211U, 0xc729a16dU, 01244 0x1d9e2f4bU, 0xdcb230f3U, 0x0d8652ecU, 0x77c1e3d0U, 01245 0x2bb3166cU, 0xa970b999U, 0x119448faU, 0x47e96422U, 01246 0xa8fc8cc4U, 0xa0f03f1aU, 0x567d2cd8U, 0x223390efU, 01247 0x87494ec7U, 0xd938d1c1U, 0x8ccaa2feU, 0x98d40b36U, 01248 0xa6f581cfU, 0xa57ade28U, 0xdab78e26U, 0x3fadbfa4U, 01249 0x2c3a9de4U, 0x5078920dU, 0x6a5fcc9bU, 0x547e4662U, 01250 0xf68d13c2U, 0x90d8b8e8U, 0x2e39f75eU, 0x82c3aff5U, 01251 0x9f5d80beU, 0x69d0937cU, 0x6fd52da9U, 0xcf2512b3U, 01252 0xc8ac993bU, 0x10187da7U, 0xe89c636eU, 0xdb3bbb7bU, 01253 0xcd267809U, 0x6e5918f4U, 0xec9ab701U, 0x834f9aa8U, 01254 0xe6956e65U, 0xaaffe67eU, 0x21bccf08U, 0xef15e8e6U, 01255 0xbae79bd9U, 0x4a6f36ceU, 0xea9f09d4U, 0x29b07cd6U, 01256 0x31a4b2afU, 0x2a3f2331U, 0xc6a59430U, 0x35a266c0U, 01257 0x744ebc37U, 0xfc82caa6U, 0xe090d0b0U, 0x33a7d815U, 01258 0xf104984aU, 0x41ecdaf7U, 0x7fcd500eU, 0x1791f62fU, 01259 0x764dd68dU, 0x43efb04dU, 0xccaa4d54U, 0xe49604dfU, 01260 0x9ed1b5e3U, 0x4c6a881bU, 0xc12c1fb8U, 0x4665517fU, 01261 0x9d5eea04U, 0x018c355dU, 0xfa877473U, 0xfb0b412eU, 01262 0xb3671d5aU, 0x92dbd252U, 0xe9105633U, 0x6dd64713U, 01263 0x9ad7618cU, 0x37a10c7aU, 0x59f8148eU, 0xeb133c89U, 01264 0xcea927eeU, 0xb761c935U, 0xe11ce5edU, 0x7a47b13cU, 01265 0x9cd2df59U, 0x55f2733fU, 0x1814ce79U, 0x73c737bfU, 01266 0x53f7cdeaU, 0x5ffdaa5bU, 0xdf3d6f14U, 0x7844db86U, 01267 0xcaaff381U, 0xb968c43eU, 0x3824342cU, 0xc2a3405fU, 01268 0x161dc372U, 0xbce2250cU, 0x283c498bU, 0xff0d9541U, 01269 0x39a80171U, 0x080cb3deU, 0xd8b4e49cU, 0x6456c190U, 01270 0x7bcb8461U, 0xd532b670U, 0x486c5c74U, 0xd0b85742U, 01271 }, 01272 { 01273 0x5051f4a7U, 0x537e4165U, 0xc31a17a4U, 0x963a275eU, 01274 0xcb3bab6bU, 0xf11f9d45U, 0xabacfa58U, 0x934be303U, 01275 0x552030faU, 0xf6ad766dU, 0x9188cc76U, 0x25f5024cU, 01276 0xfc4fe5d7U, 0xd7c52acbU, 0x80263544U, 0x8fb562a3U, 01277 0x49deb15aU, 0x6725ba1bU, 0x9845ea0eU, 0xe15dfec0U, 01278 0x02c32f75U, 0x12814cf0U, 0xa38d4697U, 0xc66bd3f9U, 01279 0xe7038f5fU, 0x9515929cU, 0xebbf6d7aU, 0xda955259U, 01280 0x2dd4be83U, 0xd3587421U, 0x2949e069U, 0x448ec9c8U, 01281 0x6a75c289U, 0x78f48e79U, 0x6b99583eU, 0xdd27b971U, 01282 0xb6bee14fU, 0x17f088adU, 0x66c920acU, 0xb47dce3aU, 01283 0x1863df4aU, 0x82e51a31U, 0x60975133U, 0x4562537fU, 01284 0xe0b16477U, 0x84bb6baeU, 0x1cfe81a0U, 0x94f9082bU, 01285 0x58704868U, 0x198f45fdU, 0x8794de6cU, 0xb7527bf8U, 01286 0x23ab73d3U, 0xe2724b02U, 0x57e31f8fU, 0x2a6655abU, 01287 0x07b2eb28U, 0x032fb5c2U, 0x9a86c57bU, 0xa5d33708U, 01288 0xf2302887U, 0xb223bfa5U, 0xba02036aU, 0x5ced1682U, 01289 0x2b8acf1cU, 0x92a779b4U, 0xf0f307f2U, 0xa14e69e2U, 01290 0xcd65daf4U, 0xd50605beU, 0x1fd13462U, 0x8ac4a6feU, 01291 0x9d342e53U, 0xa0a2f355U, 0x32058ae1U, 0x75a4f6ebU, 01292 0x390b83ecU, 0xaa4060efU, 0x065e719fU, 0x51bd6e10U, 01293 0xf93e218aU, 0x3d96dd06U, 0xaedd3e05U, 0x464de6bdU, 01294 0xb591548dU, 0x0571c45dU, 0x6f0406d4U, 0xff605015U, 01295 0x241998fbU, 0x97d6bde9U, 0xcc894043U, 0x7767d99eU, 01296 0xbdb0e842U, 0x8807898bU, 0x38e7195bU, 0xdb79c8eeU, 01297 0x47a17c0aU, 0xe97c420fU, 0xc9f8841eU, 0x00000000U, 01298 0x83098086U, 0x48322bedU, 0xac1e1170U, 0x4e6c5a72U, 01299 0xfbfd0effU, 0x560f8538U, 0x1e3daed5U, 0x27362d39U, 01300 0x640a0fd9U, 0x21685ca6U, 0xd19b5b54U, 0x3a24362eU, 01301 0xb10c0a67U, 0x0f9357e7U, 0xd2b4ee96U, 0x9e1b9b91U, 01302 0x4f80c0c5U, 0xa261dc20U, 0x695a774bU, 0x161c121aU, 01303 0x0ae293baU, 0xe5c0a02aU, 0x433c22e0U, 0x1d121b17U, 01304 0x0b0e090dU, 0xadf28bc7U, 0xb92db6a8U, 0xc8141ea9U, 01305 0x8557f119U, 0x4caf7507U, 0xbbee99ddU, 0xfda37f60U, 01306 0x9ff70126U, 0xbc5c72f5U, 0xc544663bU, 0x345bfb7eU, 01307 0x768b4329U, 0xdccb23c6U, 0x68b6edfcU, 0x63b8e4f1U, 01308 0xcad731dcU, 0x10426385U, 0x40139722U, 0x2084c611U, 01309 0x7d854a24U, 0xf8d2bb3dU, 0x11aef932U, 0x6dc729a1U, 01310 0x4b1d9e2fU, 0xf3dcb230U, 0xec0d8652U, 0xd077c1e3U, 01311 0x6c2bb316U, 0x99a970b9U, 0xfa119448U, 0x2247e964U, 01312 0xc4a8fc8cU, 0x1aa0f03fU, 0xd8567d2cU, 0xef223390U, 01313 0xc787494eU, 0xc1d938d1U, 0xfe8ccaa2U, 0x3698d40bU, 01314 0xcfa6f581U, 0x28a57adeU, 0x26dab78eU, 0xa43fadbfU, 01315 0xe42c3a9dU, 0x0d507892U, 0x9b6a5fccU, 0x62547e46U, 01316 0xc2f68d13U, 0xe890d8b8U, 0x5e2e39f7U, 0xf582c3afU, 01317 0xbe9f5d80U, 0x7c69d093U, 0xa96fd52dU, 0xb3cf2512U, 01318 0x3bc8ac99U, 0xa710187dU, 0x6ee89c63U, 0x7bdb3bbbU, 01319 0x09cd2678U, 0xf46e5918U, 0x01ec9ab7U, 0xa8834f9aU, 01320 0x65e6956eU, 0x7eaaffe6U, 0x0821bccfU, 0xe6ef15e8U, 01321 0xd9bae79bU, 0xce4a6f36U, 0xd4ea9f09U, 0xd629b07cU, 01322 0xaf31a4b2U, 0x312a3f23U, 0x30c6a594U, 0xc035a266U, 01323 0x37744ebcU, 0xa6fc82caU, 0xb0e090d0U, 0x1533a7d8U, 01324 0x4af10498U, 0xf741ecdaU, 0x0e7fcd50U, 0x2f1791f6U, 01325 0x8d764dd6U, 0x4d43efb0U, 0x54ccaa4dU, 0xdfe49604U, 01326 0xe39ed1b5U, 0x1b4c6a88U, 0xb8c12c1fU, 0x7f466551U, 01327 0x049d5eeaU, 0x5d018c35U, 0x73fa8774U, 0x2efb0b41U, 01328 0x5ab3671dU, 0x5292dbd2U, 0x33e91056U, 0x136dd647U, 01329 0x8c9ad761U, 0x7a37a10cU, 0x8e59f814U, 0x89eb133cU, 01330 0xeecea927U, 0x35b761c9U, 0xede11ce5U, 0x3c7a47b1U, 01331 0x599cd2dfU, 0x3f55f273U, 0x791814ceU, 0xbf73c737U, 01332 0xea53f7cdU, 0x5b5ffdaaU, 0x14df3d6fU, 0x867844dbU, 01333 0x81caaff3U, 0x3eb968c4U, 0x2c382434U, 0x5fc2a340U, 01334 0x72161dc3U, 0x0cbce225U, 0x8b283c49U, 0x41ff0d95U, 01335 0x7139a801U, 0xde080cb3U, 0x9cd8b4e4U, 0x906456c1U, 01336 0x617bcb84U, 0x70d532b6U, 0x74486c5cU, 0x42d0b857U, 01337 }, 01338 { 01339 0xa75051f4U, 0x65537e41U, 0xa4c31a17U, 0x5e963a27U, 01340 0x6bcb3babU, 0x45f11f9dU, 0x58abacfaU, 0x03934be3U, 01341 0xfa552030U, 0x6df6ad76U, 0x769188ccU, 0x4c25f502U, 01342 0xd7fc4fe5U, 0xcbd7c52aU, 0x44802635U, 0xa38fb562U, 01343 0x5a49deb1U, 0x1b6725baU, 0x0e9845eaU, 0xc0e15dfeU, 01344 0x7502c32fU, 0xf012814cU, 0x97a38d46U, 0xf9c66bd3U, 01345 0x5fe7038fU, 0x9c951592U, 0x7aebbf6dU, 0x59da9552U, 01346 0x832dd4beU, 0x21d35874U, 0x692949e0U, 0xc8448ec9U, 01347 0x896a75c2U, 0x7978f48eU, 0x3e6b9958U, 0x71dd27b9U, 01348 0x4fb6bee1U, 0xad17f088U, 0xac66c920U, 0x3ab47dceU, 01349 0x4a1863dfU, 0x3182e51aU, 0x33609751U, 0x7f456253U, 01350 0x77e0b164U, 0xae84bb6bU, 0xa01cfe81U, 0x2b94f908U, 01351 0x68587048U, 0xfd198f45U, 0x6c8794deU, 0xf8b7527bU, 01352 0xd323ab73U, 0x02e2724bU, 0x8f57e31fU, 0xab2a6655U, 01353 0x2807b2ebU, 0xc2032fb5U, 0x7b9a86c5U, 0x08a5d337U, 01354 0x87f23028U, 0xa5b223bfU, 0x6aba0203U, 0x825ced16U, 01355 0x1c2b8acfU, 0xb492a779U, 0xf2f0f307U, 0xe2a14e69U, 01356 0xf4cd65daU, 0xbed50605U, 0x621fd134U, 0xfe8ac4a6U, 01357 0x539d342eU, 0x55a0a2f3U, 0xe132058aU, 0xeb75a4f6U, 01358 0xec390b83U, 0xefaa4060U, 0x9f065e71U, 0x1051bd6eU, 01359 01360 0x8af93e21U, 0x063d96ddU, 0x05aedd3eU, 0xbd464de6U, 01361 0x8db59154U, 0x5d0571c4U, 0xd46f0406U, 0x15ff6050U, 01362 0xfb241998U, 0xe997d6bdU, 0x43cc8940U, 0x9e7767d9U, 01363 0x42bdb0e8U, 0x8b880789U, 0x5b38e719U, 0xeedb79c8U, 01364 0x0a47a17cU, 0x0fe97c42U, 0x1ec9f884U, 0x00000000U, 01365 0x86830980U, 0xed48322bU, 0x70ac1e11U, 0x724e6c5aU, 01366 0xfffbfd0eU, 0x38560f85U, 0xd51e3daeU, 0x3927362dU, 01367 0xd9640a0fU, 0xa621685cU, 0x54d19b5bU, 0x2e3a2436U, 01368 0x67b10c0aU, 0xe70f9357U, 0x96d2b4eeU, 0x919e1b9bU, 01369 0xc54f80c0U, 0x20a261dcU, 0x4b695a77U, 0x1a161c12U, 01370 0xba0ae293U, 0x2ae5c0a0U, 0xe0433c22U, 0x171d121bU, 01371 0x0d0b0e09U, 0xc7adf28bU, 0xa8b92db6U, 0xa9c8141eU, 01372 0x198557f1U, 0x074caf75U, 0xddbbee99U, 0x60fda37fU, 01373 0x269ff701U, 0xf5bc5c72U, 0x3bc54466U, 0x7e345bfbU, 01374 0x29768b43U, 0xc6dccb23U, 0xfc68b6edU, 0xf163b8e4U, 01375 0xdccad731U, 0x85104263U, 0x22401397U, 0x112084c6U, 01376 0x247d854aU, 0x3df8d2bbU, 0x3211aef9U, 0xa16dc729U, 01377 0x2f4b1d9eU, 0x30f3dcb2U, 0x52ec0d86U, 0xe3d077c1U, 01378 0x166c2bb3U, 0xb999a970U, 0x48fa1194U, 0x642247e9U, 01379 0x8cc4a8fcU, 0x3f1aa0f0U, 0x2cd8567dU, 0x90ef2233U, 01380 0x4ec78749U, 0xd1c1d938U, 0xa2fe8ccaU, 0x0b3698d4U, 01381 0x81cfa6f5U, 0xde28a57aU, 0x8e26dab7U, 0xbfa43fadU, 01382 0x9de42c3aU, 0x920d5078U, 0xcc9b6a5fU, 0x4662547eU, 01383 0x13c2f68dU, 0xb8e890d8U, 0xf75e2e39U, 0xaff582c3U, 01384 0x80be9f5dU, 0x937c69d0U, 0x2da96fd5U, 0x12b3cf25U, 01385 0x993bc8acU, 0x7da71018U, 0x636ee89cU, 0xbb7bdb3bU, 01386 0x7809cd26U, 0x18f46e59U, 0xb701ec9aU, 0x9aa8834fU, 01387 0x6e65e695U, 0xe67eaaffU, 0xcf0821bcU, 0xe8e6ef15U, 01388 0x9bd9bae7U, 0x36ce4a6fU, 0x09d4ea9fU, 0x7cd629b0U, 01389 0xb2af31a4U, 0x23312a3fU, 0x9430c6a5U, 0x66c035a2U, 01390 0xbc37744eU, 0xcaa6fc82U, 0xd0b0e090U, 0xd81533a7U, 01391 0x984af104U, 0xdaf741ecU, 0x500e7fcdU, 0xf62f1791U, 01392 0xd68d764dU, 0xb04d43efU, 0x4d54ccaaU, 0x04dfe496U, 01393 0xb5e39ed1U, 0x881b4c6aU, 0x1fb8c12cU, 0x517f4665U, 01394 0xea049d5eU, 0x355d018cU, 0x7473fa87U, 0x412efb0bU, 01395 0x1d5ab367U, 0xd25292dbU, 0x5633e910U, 0x47136dd6U, 01396 0x618c9ad7U, 0x0c7a37a1U, 0x148e59f8U, 0x3c89eb13U, 01397 0x27eecea9U, 0xc935b761U, 0xe5ede11cU, 0xb13c7a47U, 01398 0xdf599cd2U, 0x733f55f2U, 0xce791814U, 0x37bf73c7U, 01399 0xcdea53f7U, 0xaa5b5ffdU, 0x6f14df3dU, 0xdb867844U, 01400 0xf381caafU, 0xc43eb968U, 0x342c3824U, 0x405fc2a3U, 01401 0xc372161dU, 0x250cbce2U, 0x498b283cU, 0x9541ff0dU, 01402 0x017139a8U, 0xb3de080cU, 0xe49cd8b4U, 0xc1906456U, 01403 0x84617bcbU, 0xb670d532U, 0x5c74486cU, 0x5742d0b8U, 01404 }, 01405 { 01406 0xf4a75051U, 0x4165537eU, 0x17a4c31aU, 0x275e963aU, 01407 0xab6bcb3bU, 0x9d45f11fU, 0xfa58abacU, 0xe303934bU, 01408 0x30fa5520U, 0x766df6adU, 0xcc769188U, 0x024c25f5U, 01409 0xe5d7fc4fU, 0x2acbd7c5U, 0x35448026U, 0x62a38fb5U, 01410 0xb15a49deU, 0xba1b6725U, 0xea0e9845U, 0xfec0e15dU, 01411 0x2f7502c3U, 0x4cf01281U, 0x4697a38dU, 0xd3f9c66bU, 01412 0x8f5fe703U, 0x929c9515U, 0x6d7aebbfU, 0x5259da95U, 01413 0xbe832dd4U, 0x7421d358U, 0xe0692949U, 0xc9c8448eU, 01414 0xc2896a75U, 0x8e7978f4U, 0x583e6b99U, 0xb971dd27U, 01415 0xe14fb6beU, 0x88ad17f0U, 0x20ac66c9U, 0xce3ab47dU, 01416 0xdf4a1863U, 0x1a3182e5U, 0x51336097U, 0x537f4562U, 01417 0x6477e0b1U, 0x6bae84bbU, 0x81a01cfeU, 0x082b94f9U, 01418 0x48685870U, 0x45fd198fU, 0xde6c8794U, 0x7bf8b752U, 01419 0x73d323abU, 0x4b02e272U, 0x1f8f57e3U, 0x55ab2a66U, 01420 0xeb2807b2U, 0xb5c2032fU, 0xc57b9a86U, 0x3708a5d3U, 01421 0x2887f230U, 0xbfa5b223U, 0x036aba02U, 0x16825cedU, 01422 0xcf1c2b8aU, 0x79b492a7U, 0x07f2f0f3U, 0x69e2a14eU, 01423 0xdaf4cd65U, 0x05bed506U, 0x34621fd1U, 0xa6fe8ac4U, 01424 0x2e539d34U, 0xf355a0a2U, 0x8ae13205U, 0xf6eb75a4U, 01425 0x83ec390bU, 0x60efaa40U, 0x719f065eU, 0x6e1051bdU, 01426 0x218af93eU, 0xdd063d96U, 0x3e05aeddU, 0xe6bd464dU, 01427 0x548db591U, 0xc45d0571U, 0x06d46f04U, 0x5015ff60U, 01428 0x98fb2419U, 0xbde997d6U, 0x4043cc89U, 0xd99e7767U, 01429 0xe842bdb0U, 0x898b8807U, 0x195b38e7U, 0xc8eedb79U, 01430 0x7c0a47a1U, 0x420fe97cU, 0x841ec9f8U, 0x00000000U, 01431 0x80868309U, 0x2bed4832U, 0x1170ac1eU, 0x5a724e6cU, 01432 0x0efffbfdU, 0x8538560fU, 0xaed51e3dU, 0x2d392736U, 01433 0x0fd9640aU, 0x5ca62168U, 0x5b54d19bU, 0x362e3a24U, 01434 0x0a67b10cU, 0x57e70f93U, 0xee96d2b4U, 0x9b919e1bU, 01435 0xc0c54f80U, 0xdc20a261U, 0x774b695aU, 0x121a161cU, 01436 0x93ba0ae2U, 0xa02ae5c0U, 0x22e0433cU, 0x1b171d12U, 01437 0x090d0b0eU, 0x8bc7adf2U, 0xb6a8b92dU, 0x1ea9c814U, 01438 0xf1198557U, 0x75074cafU, 0x99ddbbeeU, 0x7f60fda3U, 01439 0x01269ff7U, 0x72f5bc5cU, 0x663bc544U, 0xfb7e345bU, 01440 0x4329768bU, 0x23c6dccbU, 0xedfc68b6U, 0xe4f163b8U, 01441 0x31dccad7U, 0x63851042U, 0x97224013U, 0xc6112084U, 01442 0x4a247d85U, 0xbb3df8d2U, 0xf93211aeU, 0x29a16dc7U, 01443 0x9e2f4b1dU, 0xb230f3dcU, 0x8652ec0dU, 0xc1e3d077U, 01444 0xb3166c2bU, 0x70b999a9U, 0x9448fa11U, 0xe9642247U, 01445 0xfc8cc4a8U, 0xf03f1aa0U, 0x7d2cd856U, 0x3390ef22U, 01446 0x494ec787U, 0x38d1c1d9U, 0xcaa2fe8cU, 0xd40b3698U, 01447 0xf581cfa6U, 0x7ade28a5U, 0xb78e26daU, 0xadbfa43fU, 01448 0x3a9de42cU, 0x78920d50U, 0x5fcc9b6aU, 0x7e466254U, 01449 0x8d13c2f6U, 0xd8b8e890U, 0x39f75e2eU, 0xc3aff582U, 01450 0x5d80be9fU, 0xd0937c69U, 0xd52da96fU, 0x2512b3cfU, 01451 0xac993bc8U, 0x187da710U, 0x9c636ee8U, 0x3bbb7bdbU, 01452 0x267809cdU, 0x5918f46eU, 0x9ab701ecU, 0x4f9aa883U, 01453 0x956e65e6U, 0xffe67eaaU, 0xbccf0821U, 0x15e8e6efU, 01454 0xe79bd9baU, 0x6f36ce4aU, 0x9f09d4eaU, 0xb07cd629U, 01455 0xa4b2af31U, 0x3f23312aU, 0xa59430c6U, 0xa266c035U, 01456 0x4ebc3774U, 0x82caa6fcU, 0x90d0b0e0U, 0xa7d81533U, 01457 0x04984af1U, 0xecdaf741U, 0xcd500e7fU, 0x91f62f17U, 01458 0x4dd68d76U, 0xefb04d43U, 0xaa4d54ccU, 0x9604dfe4U, 01459 0xd1b5e39eU, 0x6a881b4cU, 0x2c1fb8c1U, 0x65517f46U, 01460 0x5eea049dU, 0x8c355d01U, 0x877473faU, 0x0b412efbU, 01461 0x671d5ab3U, 0xdbd25292U, 0x105633e9U, 0xd647136dU, 01462 0xd7618c9aU, 0xa10c7a37U, 0xf8148e59U, 0x133c89ebU, 01463 0xa927eeceU, 0x61c935b7U, 0x1ce5ede1U, 0x47b13c7aU, 01464 0xd2df599cU, 0xf2733f55U, 0x14ce7918U, 0xc737bf73U, 01465 0xf7cdea53U, 0xfdaa5b5fU, 0x3d6f14dfU, 0x44db8678U, 01466 0xaff381caU, 0x68c43eb9U, 0x24342c38U, 0xa3405fc2U, 01467 0x1dc37216U, 0xe2250cbcU, 0x3c498b28U, 0x0d9541ffU, 01468 0xa8017139U, 0x0cb3de08U, 0xb4e49cd8U, 0x56c19064U, 01469 0xcb84617bU, 0x32b670d5U, 0x6c5c7448U, 0xb85742d0U, 01470 } 01471 }; 01472 #endif /* HAVE_AES_DECRYPT */ 01473 #endif 01474 01475 #ifdef HAVE_AES_DECRYPT 01476 #if (defined(HAVE_AES_CBC) && !defined(WOLFSSL_DEVCRYPTO_CBC)) \ 01477 || defined(WOLFSSL_AES_DIRECT) 01478 static const byte Td4[256] = 01479 { 01480 0x52U, 0x09U, 0x6aU, 0xd5U, 0x30U, 0x36U, 0xa5U, 0x38U, 01481 0xbfU, 0x40U, 0xa3U, 0x9eU, 0x81U, 0xf3U, 0xd7U, 0xfbU, 01482 0x7cU, 0xe3U, 0x39U, 0x82U, 0x9bU, 0x2fU, 0xffU, 0x87U, 01483 0x34U, 0x8eU, 0x43U, 0x44U, 0xc4U, 0xdeU, 0xe9U, 0xcbU, 01484 0x54U, 0x7bU, 0x94U, 0x32U, 0xa6U, 0xc2U, 0x23U, 0x3dU, 01485 0xeeU, 0x4cU, 0x95U, 0x0bU, 0x42U, 0xfaU, 0xc3U, 0x4eU, 01486 0x08U, 0x2eU, 0xa1U, 0x66U, 0x28U, 0xd9U, 0x24U, 0xb2U, 01487 0x76U, 0x5bU, 0xa2U, 0x49U, 0x6dU, 0x8bU, 0xd1U, 0x25U, 01488 0x72U, 0xf8U, 0xf6U, 0x64U, 0x86U, 0x68U, 0x98U, 0x16U, 01489 0xd4U, 0xa4U, 0x5cU, 0xccU, 0x5dU, 0x65U, 0xb6U, 0x92U, 01490 0x6cU, 0x70U, 0x48U, 0x50U, 0xfdU, 0xedU, 0xb9U, 0xdaU, 01491 0x5eU, 0x15U, 0x46U, 0x57U, 0xa7U, 0x8dU, 0x9dU, 0x84U, 01492 0x90U, 0xd8U, 0xabU, 0x00U, 0x8cU, 0xbcU, 0xd3U, 0x0aU, 01493 0xf7U, 0xe4U, 0x58U, 0x05U, 0xb8U, 0xb3U, 0x45U, 0x06U, 01494 0xd0U, 0x2cU, 0x1eU, 0x8fU, 0xcaU, 0x3fU, 0x0fU, 0x02U, 01495 0xc1U, 0xafU, 0xbdU, 0x03U, 0x01U, 0x13U, 0x8aU, 0x6bU, 01496 0x3aU, 0x91U, 0x11U, 0x41U, 0x4fU, 0x67U, 0xdcU, 0xeaU, 01497 0x97U, 0xf2U, 0xcfU, 0xceU, 0xf0U, 0xb4U, 0xe6U, 0x73U, 01498 0x96U, 0xacU, 0x74U, 0x22U, 0xe7U, 0xadU, 0x35U, 0x85U, 01499 0xe2U, 0xf9U, 0x37U, 0xe8U, 0x1cU, 0x75U, 0xdfU, 0x6eU, 01500 0x47U, 0xf1U, 0x1aU, 0x71U, 0x1dU, 0x29U, 0xc5U, 0x89U, 01501 0x6fU, 0xb7U, 0x62U, 0x0eU, 0xaaU, 0x18U, 0xbeU, 0x1bU, 01502 0xfcU, 0x56U, 0x3eU, 0x4bU, 0xc6U, 0xd2U, 0x79U, 0x20U, 01503 0x9aU, 0xdbU, 0xc0U, 0xfeU, 0x78U, 0xcdU, 0x5aU, 0xf4U, 01504 0x1fU, 0xddU, 0xa8U, 0x33U, 0x88U, 0x07U, 0xc7U, 0x31U, 01505 0xb1U, 0x12U, 0x10U, 0x59U, 0x27U, 0x80U, 0xecU, 0x5fU, 01506 0x60U, 0x51U, 0x7fU, 0xa9U, 0x19U, 0xb5U, 0x4aU, 0x0dU, 01507 0x2dU, 0xe5U, 0x7aU, 0x9fU, 0x93U, 0xc9U, 0x9cU, 0xefU, 01508 0xa0U, 0xe0U, 0x3bU, 0x4dU, 0xaeU, 0x2aU, 0xf5U, 0xb0U, 01509 0xc8U, 0xebU, 0xbbU, 0x3cU, 0x83U, 0x53U, 0x99U, 0x61U, 01510 0x17U, 0x2bU, 0x04U, 0x7eU, 0xbaU, 0x77U, 0xd6U, 0x26U, 01511 0xe1U, 0x69U, 0x14U, 0x63U, 0x55U, 0x21U, 0x0cU, 0x7dU, 01512 }; 01513 #endif /* HAVE_AES_CBC || WOLFSSL_AES_DIRECT */ 01514 #endif /* HAVE_AES_DECRYPT */ 01515 01516 #define GETBYTE(x, y) (word32)((byte)((x) >> (8 * (y)))) 01517 01518 #ifdef WOLFSSL_AES_SMALL_TABLES 01519 static const byte Tsbox[256] = { 01520 0x63U, 0x7cU, 0x77U, 0x7bU, 0xf2U, 0x6bU, 0x6fU, 0xc5U, 01521 0x30U, 0x01U, 0x67U, 0x2bU, 0xfeU, 0xd7U, 0xabU, 0x76U, 01522 0xcaU, 0x82U, 0xc9U, 0x7dU, 0xfaU, 0x59U, 0x47U, 0xf0U, 01523 0xadU, 0xd4U, 0xa2U, 0xafU, 0x9cU, 0xa4U, 0x72U, 0xc0U, 01524 0xb7U, 0xfdU, 0x93U, 0x26U, 0x36U, 0x3fU, 0xf7U, 0xccU, 01525 0x34U, 0xa5U, 0xe5U, 0xf1U, 0x71U, 0xd8U, 0x31U, 0x15U, 01526 0x04U, 0xc7U, 0x23U, 0xc3U, 0x18U, 0x96U, 0x05U, 0x9aU, 01527 0x07U, 0x12U, 0x80U, 0xe2U, 0xebU, 0x27U, 0xb2U, 0x75U, 01528 0x09U, 0x83U, 0x2cU, 0x1aU, 0x1bU, 0x6eU, 0x5aU, 0xa0U, 01529 0x52U, 0x3bU, 0xd6U, 0xb3U, 0x29U, 0xe3U, 0x2fU, 0x84U, 01530 0x53U, 0xd1U, 0x00U, 0xedU, 0x20U, 0xfcU, 0xb1U, 0x5bU, 01531 0x6aU, 0xcbU, 0xbeU, 0x39U, 0x4aU, 0x4cU, 0x58U, 0xcfU, 01532 0xd0U, 0xefU, 0xaaU, 0xfbU, 0x43U, 0x4dU, 0x33U, 0x85U, 01533 0x45U, 0xf9U, 0x02U, 0x7fU, 0x50U, 0x3cU, 0x9fU, 0xa8U, 01534 0x51U, 0xa3U, 0x40U, 0x8fU, 0x92U, 0x9dU, 0x38U, 0xf5U, 01535 0xbcU, 0xb6U, 0xdaU, 0x21U, 0x10U, 0xffU, 0xf3U, 0xd2U, 01536 0xcdU, 0x0cU, 0x13U, 0xecU, 0x5fU, 0x97U, 0x44U, 0x17U, 01537 0xc4U, 0xa7U, 0x7eU, 0x3dU, 0x64U, 0x5dU, 0x19U, 0x73U, 01538 0x60U, 0x81U, 0x4fU, 0xdcU, 0x22U, 0x2aU, 0x90U, 0x88U, 01539 0x46U, 0xeeU, 0xb8U, 0x14U, 0xdeU, 0x5eU, 0x0bU, 0xdbU, 01540 0xe0U, 0x32U, 0x3aU, 0x0aU, 0x49U, 0x06U, 0x24U, 0x5cU, 01541 0xc2U, 0xd3U, 0xacU, 0x62U, 0x91U, 0x95U, 0xe4U, 0x79U, 01542 0xe7U, 0xc8U, 0x37U, 0x6dU, 0x8dU, 0xd5U, 0x4eU, 0xa9U, 01543 0x6cU, 0x56U, 0xf4U, 0xeaU, 0x65U, 0x7aU, 0xaeU, 0x08U, 01544 0xbaU, 0x78U, 0x25U, 0x2eU, 0x1cU, 0xa6U, 0xb4U, 0xc6U, 01545 0xe8U, 0xddU, 0x74U, 0x1fU, 0x4bU, 0xbdU, 0x8bU, 0x8aU, 01546 0x70U, 0x3eU, 0xb5U, 0x66U, 0x48U, 0x03U, 0xf6U, 0x0eU, 01547 0x61U, 0x35U, 0x57U, 0xb9U, 0x86U, 0xc1U, 0x1dU, 0x9eU, 01548 0xe1U, 0xf8U, 0x98U, 0x11U, 0x69U, 0xd9U, 0x8eU, 0x94U, 01549 0x9bU, 0x1eU, 0x87U, 0xe9U, 0xceU, 0x55U, 0x28U, 0xdfU, 01550 0x8cU, 0xa1U, 0x89U, 0x0dU, 0xbfU, 0xe6U, 0x42U, 0x68U, 01551 0x41U, 0x99U, 0x2dU, 0x0fU, 0xb0U, 0x54U, 0xbbU, 0x16U 01552 }; 01553 01554 #define AES_XTIME(x) ((byte)((byte)((x) << 1) ^ ((0 - ((x) >> 7)) & 0x1b))) 01555 01556 static word32 col_mul(word32 t, int i2, int i3, int ia, int ib) 01557 { 01558 byte t3 = GETBYTE(t, i3); 01559 byte tm = AES_XTIME(GETBYTE(t, i2) ^ t3); 01560 01561 return GETBYTE(t, ia) ^ GETBYTE(t, ib) ^ t3 ^ tm; 01562 } 01563 01564 static word32 inv_col_mul(word32 t, int i9, int ib, int id, int ie) 01565 { 01566 byte t9 = GETBYTE(t, i9); 01567 byte tb = GETBYTE(t, ib); 01568 byte td = GETBYTE(t, id); 01569 byte te = GETBYTE(t, ie); 01570 byte t0 = t9 ^ tb ^ td; 01571 return t0 ^ AES_XTIME(AES_XTIME(AES_XTIME(t0 ^ te) ^ td ^ te) ^ tb ^ te); 01572 } 01573 #endif 01574 01575 #if defined(HAVE_AES_CBC) || defined(WOLFSSL_AES_DIRECT) || defined(HAVE_AESGCM) 01576 01577 #ifndef WC_CACHE_LINE_SZ 01578 #if defined(__x86_64__) || defined(_M_X64) || \ 01579 (defined(__ILP32__) && (__ILP32__ >= 1)) 01580 #define WC_CACHE_LINE_SZ 64 01581 #else 01582 /* default cache line size */ 01583 #define WC_CACHE_LINE_SZ 32 01584 #endif 01585 #endif 01586 01587 01588 #ifndef WOLFSSL_AES_SMALL_TABLES 01589 /* load 4 Te Tables into cache by cache line stride */ 01590 static WC_INLINE word32 PreFetchTe(void) 01591 { 01592 word32 x = 0; 01593 int i,j; 01594 01595 for (i = 0; i < 4; i++) { 01596 /* 256 elements, each one is 4 bytes */ 01597 for (j = 0; j < 256; j += WC_CACHE_LINE_SZ/4) { 01598 x &= Te[i][j]; 01599 } 01600 } 01601 return x; 01602 } 01603 #else 01604 /* load sbox into cache by cache line stride */ 01605 static WC_INLINE word32 PreFetchSBox(void) 01606 { 01607 word32 x = 0; 01608 int i; 01609 01610 for (i = 0; i < 256; i += WC_CACHE_LINE_SZ/4) { 01611 x &= Tsbox[i]; 01612 } 01613 return x; 01614 } 01615 #endif 01616 01617 /* Software AES - ECB Encrypt */ 01618 static void wc_AesEncrypt(Aes* aes, const byte* inBlock, byte* outBlock) 01619 { 01620 word32 s0, s1, s2, s3; 01621 word32 t0, t1, t2, t3; 01622 word32 r = aes->rounds >> 1; 01623 const word32* rk = aes->key; 01624 01625 if (r > 7 || r == 0) { 01626 WOLFSSL_MSG("AesEncrypt encountered improper key, set it up"); 01627 return; /* stop instead of seg-faulting, set up your keys! */ 01628 } 01629 01630 #ifdef WOLFSSL_AESNI 01631 if (haveAESNI && aes->use_aesni) { 01632 #ifdef DEBUG_AESNI 01633 printf("about to aes encrypt\n"); 01634 printf("in = %p\n", inBlock); 01635 printf("out = %p\n", outBlock); 01636 printf("aes->key = %p\n", aes->key); 01637 printf("aes->rounds = %d\n", aes->rounds); 01638 printf("sz = %d\n", AES_BLOCK_SIZE); 01639 #endif 01640 01641 /* check alignment, decrypt doesn't need alignment */ 01642 if ((wolfssl_word)inBlock % AESNI_ALIGN) { 01643 #ifndef NO_WOLFSSL_ALLOC_ALIGN 01644 byte* tmp = (byte*)XMALLOC(AES_BLOCK_SIZE + AESNI_ALIGN, aes->heap, 01645 DYNAMIC_TYPE_TMP_BUFFER); 01646 byte* tmp_align; 01647 if (tmp == NULL) return; 01648 01649 tmp_align = tmp + (AESNI_ALIGN - ((size_t)tmp % AESNI_ALIGN)); 01650 01651 XMEMCPY(tmp_align, inBlock, AES_BLOCK_SIZE); 01652 AES_ECB_encrypt(tmp_align, tmp_align, AES_BLOCK_SIZE, 01653 (byte*)aes->key, aes->rounds); 01654 XMEMCPY(outBlock, tmp_align, AES_BLOCK_SIZE); 01655 XFREE(tmp, aes->heap, DYNAMIC_TYPE_TMP_BUFFER); 01656 return; 01657 #else 01658 WOLFSSL_MSG("AES-ECB encrypt with bad alignment"); 01659 return; 01660 #endif 01661 } 01662 01663 AES_ECB_encrypt(inBlock, outBlock, AES_BLOCK_SIZE, (byte*)aes->key, 01664 aes->rounds); 01665 01666 return; 01667 } 01668 else { 01669 #ifdef DEBUG_AESNI 01670 printf("Skipping AES-NI\n"); 01671 #endif 01672 } 01673 #endif 01674 #if defined(WOLFSSL_SCE) && !defined(WOLFSSL_SCE_NO_AES) 01675 AES_ECB_encrypt(aes, inBlock, outBlock, AES_BLOCK_SIZE); 01676 return; 01677 #endif 01678 01679 /* 01680 * map byte array block to cipher state 01681 * and add initial round key: 01682 */ 01683 XMEMCPY(&s0, inBlock, sizeof(s0)); 01684 XMEMCPY(&s1, inBlock + sizeof(s0), sizeof(s1)); 01685 XMEMCPY(&s2, inBlock + 2 * sizeof(s0), sizeof(s2)); 01686 XMEMCPY(&s3, inBlock + 3 * sizeof(s0), sizeof(s3)); 01687 01688 #ifdef LITTLE_ENDIAN_ORDER 01689 s0 = ByteReverseWord32(s0); 01690 s1 = ByteReverseWord32(s1); 01691 s2 = ByteReverseWord32(s2); 01692 s3 = ByteReverseWord32(s3); 01693 #endif 01694 01695 /* AddRoundKey */ 01696 s0 ^= rk[0]; 01697 s1 ^= rk[1]; 01698 s2 ^= rk[2]; 01699 s3 ^= rk[3]; 01700 01701 #ifndef WOLFSSL_AES_SMALL_TABLES 01702 s0 |= PreFetchTe(); 01703 01704 /* 01705 * Nr - 1 full rounds: 01706 */ 01707 01708 for (;;) { 01709 t0 = 01710 Te[0][GETBYTE(s0, 3)] ^ 01711 Te[1][GETBYTE(s1, 2)] ^ 01712 Te[2][GETBYTE(s2, 1)] ^ 01713 Te[3][GETBYTE(s3, 0)] ^ 01714 rk[4]; 01715 t1 = 01716 Te[0][GETBYTE(s1, 3)] ^ 01717 Te[1][GETBYTE(s2, 2)] ^ 01718 Te[2][GETBYTE(s3, 1)] ^ 01719 Te[3][GETBYTE(s0, 0)] ^ 01720 rk[5]; 01721 t2 = 01722 Te[0][GETBYTE(s2, 3)] ^ 01723 Te[1][GETBYTE(s3, 2)] ^ 01724 Te[2][GETBYTE(s0, 1)] ^ 01725 Te[3][GETBYTE(s1, 0)] ^ 01726 rk[6]; 01727 t3 = 01728 Te[0][GETBYTE(s3, 3)] ^ 01729 Te[1][GETBYTE(s0, 2)] ^ 01730 Te[2][GETBYTE(s1, 1)] ^ 01731 Te[3][GETBYTE(s2, 0)] ^ 01732 rk[7]; 01733 01734 rk += 8; 01735 if (--r == 0) { 01736 break; 01737 } 01738 01739 s0 = 01740 Te[0][GETBYTE(t0, 3)] ^ 01741 Te[1][GETBYTE(t1, 2)] ^ 01742 Te[2][GETBYTE(t2, 1)] ^ 01743 Te[3][GETBYTE(t3, 0)] ^ 01744 rk[0]; 01745 s1 = 01746 Te[0][GETBYTE(t1, 3)] ^ 01747 Te[1][GETBYTE(t2, 2)] ^ 01748 Te[2][GETBYTE(t3, 1)] ^ 01749 Te[3][GETBYTE(t0, 0)] ^ 01750 rk[1]; 01751 s2 = 01752 Te[0][GETBYTE(t2, 3)] ^ 01753 Te[1][GETBYTE(t3, 2)] ^ 01754 Te[2][GETBYTE(t0, 1)] ^ 01755 Te[3][GETBYTE(t1, 0)] ^ 01756 rk[2]; 01757 s3 = 01758 Te[0][GETBYTE(t3, 3)] ^ 01759 Te[1][GETBYTE(t0, 2)] ^ 01760 Te[2][GETBYTE(t1, 1)] ^ 01761 Te[3][GETBYTE(t2, 0)] ^ 01762 rk[3]; 01763 } 01764 01765 /* 01766 * apply last round and 01767 * map cipher state to byte array block: 01768 */ 01769 01770 s0 = 01771 (Te[2][GETBYTE(t0, 3)] & 0xff000000) ^ 01772 (Te[3][GETBYTE(t1, 2)] & 0x00ff0000) ^ 01773 (Te[0][GETBYTE(t2, 1)] & 0x0000ff00) ^ 01774 (Te[1][GETBYTE(t3, 0)] & 0x000000ff) ^ 01775 rk[0]; 01776 s1 = 01777 (Te[2][GETBYTE(t1, 3)] & 0xff000000) ^ 01778 (Te[3][GETBYTE(t2, 2)] & 0x00ff0000) ^ 01779 (Te[0][GETBYTE(t3, 1)] & 0x0000ff00) ^ 01780 (Te[1][GETBYTE(t0, 0)] & 0x000000ff) ^ 01781 rk[1]; 01782 s2 = 01783 (Te[2][GETBYTE(t2, 3)] & 0xff000000) ^ 01784 (Te[3][GETBYTE(t3, 2)] & 0x00ff0000) ^ 01785 (Te[0][GETBYTE(t0, 1)] & 0x0000ff00) ^ 01786 (Te[1][GETBYTE(t1, 0)] & 0x000000ff) ^ 01787 rk[2]; 01788 s3 = 01789 (Te[2][GETBYTE(t3, 3)] & 0xff000000) ^ 01790 (Te[3][GETBYTE(t0, 2)] & 0x00ff0000) ^ 01791 (Te[0][GETBYTE(t1, 1)] & 0x0000ff00) ^ 01792 (Te[1][GETBYTE(t2, 0)] & 0x000000ff) ^ 01793 rk[3]; 01794 #else 01795 s0 |= PreFetchSBox(); 01796 01797 r *= 2; 01798 /* Two rounds at a time */ 01799 for (rk += 4; r > 1; r--, rk += 4) { 01800 t0 = 01801 ((word32)Tsbox[GETBYTE(s0, 3)] << 24) ^ 01802 ((word32)Tsbox[GETBYTE(s1, 2)] << 16) ^ 01803 ((word32)Tsbox[GETBYTE(s2, 1)] << 8) ^ 01804 ((word32)Tsbox[GETBYTE(s3, 0)]); 01805 t1 = 01806 ((word32)Tsbox[GETBYTE(s1, 3)] << 24) ^ 01807 ((word32)Tsbox[GETBYTE(s2, 2)] << 16) ^ 01808 ((word32)Tsbox[GETBYTE(s3, 1)] << 8) ^ 01809 ((word32)Tsbox[GETBYTE(s0, 0)]); 01810 t2 = 01811 ((word32)Tsbox[GETBYTE(s2, 3)] << 24) ^ 01812 ((word32)Tsbox[GETBYTE(s3, 2)] << 16) ^ 01813 ((word32)Tsbox[GETBYTE(s0, 1)] << 8) ^ 01814 ((word32)Tsbox[GETBYTE(s1, 0)]); 01815 t3 = 01816 ((word32)Tsbox[GETBYTE(s3, 3)] << 24) ^ 01817 ((word32)Tsbox[GETBYTE(s0, 2)] << 16) ^ 01818 ((word32)Tsbox[GETBYTE(s1, 1)] << 8) ^ 01819 ((word32)Tsbox[GETBYTE(s2, 0)]); 01820 01821 s0 = 01822 (col_mul(t0, 3, 2, 0, 1) << 24) ^ 01823 (col_mul(t0, 2, 1, 0, 3) << 16) ^ 01824 (col_mul(t0, 1, 0, 2, 3) << 8) ^ 01825 (col_mul(t0, 0, 3, 2, 1) ) ^ 01826 rk[0]; 01827 s1 = 01828 (col_mul(t1, 3, 2, 0, 1) << 24) ^ 01829 (col_mul(t1, 2, 1, 0, 3) << 16) ^ 01830 (col_mul(t1, 1, 0, 2, 3) << 8) ^ 01831 (col_mul(t1, 0, 3, 2, 1) ) ^ 01832 rk[1]; 01833 s2 = 01834 (col_mul(t2, 3, 2, 0, 1) << 24) ^ 01835 (col_mul(t2, 2, 1, 0, 3) << 16) ^ 01836 (col_mul(t2, 1, 0, 2, 3) << 8) ^ 01837 (col_mul(t2, 0, 3, 2, 1) ) ^ 01838 rk[2]; 01839 s3 = 01840 (col_mul(t3, 3, 2, 0, 1) << 24) ^ 01841 (col_mul(t3, 2, 1, 0, 3) << 16) ^ 01842 (col_mul(t3, 1, 0, 2, 3) << 8) ^ 01843 (col_mul(t3, 0, 3, 2, 1) ) ^ 01844 rk[3]; 01845 } 01846 01847 t0 = 01848 ((word32)Tsbox[GETBYTE(s0, 3)] << 24) ^ 01849 ((word32)Tsbox[GETBYTE(s1, 2)] << 16) ^ 01850 ((word32)Tsbox[GETBYTE(s2, 1)] << 8) ^ 01851 ((word32)Tsbox[GETBYTE(s3, 0)]); 01852 t1 = 01853 ((word32)Tsbox[GETBYTE(s1, 3)] << 24) ^ 01854 ((word32)Tsbox[GETBYTE(s2, 2)] << 16) ^ 01855 ((word32)Tsbox[GETBYTE(s3, 1)] << 8) ^ 01856 ((word32)Tsbox[GETBYTE(s0, 0)]); 01857 t2 = 01858 ((word32)Tsbox[GETBYTE(s2, 3)] << 24) ^ 01859 ((word32)Tsbox[GETBYTE(s3, 2)] << 16) ^ 01860 ((word32)Tsbox[GETBYTE(s0, 1)] << 8) ^ 01861 ((word32)Tsbox[GETBYTE(s1, 0)]); 01862 t3 = 01863 ((word32)Tsbox[GETBYTE(s3, 3)] << 24) ^ 01864 ((word32)Tsbox[GETBYTE(s0, 2)] << 16) ^ 01865 ((word32)Tsbox[GETBYTE(s1, 1)] << 8) ^ 01866 ((word32)Tsbox[GETBYTE(s2, 0)]); 01867 s0 = t0 ^ rk[0]; 01868 s1 = t1 ^ rk[1]; 01869 s2 = t2 ^ rk[2]; 01870 s3 = t3 ^ rk[3]; 01871 #endif 01872 01873 /* write out */ 01874 #ifdef LITTLE_ENDIAN_ORDER 01875 s0 = ByteReverseWord32(s0); 01876 s1 = ByteReverseWord32(s1); 01877 s2 = ByteReverseWord32(s2); 01878 s3 = ByteReverseWord32(s3); 01879 #endif 01880 01881 XMEMCPY(outBlock, &s0, sizeof(s0)); 01882 XMEMCPY(outBlock + sizeof(s0), &s1, sizeof(s1)); 01883 XMEMCPY(outBlock + 2 * sizeof(s0), &s2, sizeof(s2)); 01884 XMEMCPY(outBlock + 3 * sizeof(s0), &s3, sizeof(s3)); 01885 01886 } 01887 #endif /* HAVE_AES_CBC || WOLFSSL_AES_DIRECT || HAVE_AESGCM */ 01888 01889 #if defined(HAVE_AES_DECRYPT) 01890 #if (defined(HAVE_AES_CBC) && !defined(WOLFSSL_DEVCRYPTO_CBC)) || \ 01891 defined(WOLFSSL_AES_DIRECT) 01892 01893 #ifndef WOLFSSL_AES_SMALL_TABLES 01894 /* load 4 Td Tables into cache by cache line stride */ 01895 static WC_INLINE word32 PreFetchTd(void) 01896 { 01897 word32 x = 0; 01898 int i,j; 01899 01900 for (i = 0; i < 4; i++) { 01901 /* 256 elements, each one is 4 bytes */ 01902 for (j = 0; j < 256; j += WC_CACHE_LINE_SZ/4) { 01903 x &= Td[i][j]; 01904 } 01905 } 01906 return x; 01907 } 01908 #endif 01909 01910 /* load Td Table4 into cache by cache line stride */ 01911 static WC_INLINE word32 PreFetchTd4(void) 01912 { 01913 word32 x = 0; 01914 int i; 01915 01916 for (i = 0; i < 256; i += WC_CACHE_LINE_SZ) { 01917 x &= (word32)Td4[i]; 01918 } 01919 return x; 01920 } 01921 01922 /* Software AES - ECB Decrypt */ 01923 static void wc_AesDecrypt(Aes* aes, const byte* inBlock, byte* outBlock) 01924 { 01925 word32 s0, s1, s2, s3; 01926 word32 t0, t1, t2, t3; 01927 word32 r = aes->rounds >> 1; 01928 01929 const word32* rk = aes->key; 01930 if (r > 7 || r == 0) { 01931 WOLFSSL_MSG("AesDecrypt encountered improper key, set it up"); 01932 return; /* stop instead of seg-faulting, set up your keys! */ 01933 } 01934 #ifdef WOLFSSL_AESNI 01935 if (haveAESNI && aes->use_aesni) { 01936 #ifdef DEBUG_AESNI 01937 printf("about to aes decrypt\n"); 01938 printf("in = %p\n", inBlock); 01939 printf("out = %p\n", outBlock); 01940 printf("aes->key = %p\n", aes->key); 01941 printf("aes->rounds = %d\n", aes->rounds); 01942 printf("sz = %d\n", AES_BLOCK_SIZE); 01943 #endif 01944 01945 /* if input and output same will overwrite input iv */ 01946 if ((const byte*)aes->tmp != inBlock) 01947 XMEMCPY(aes->tmp, inBlock, AES_BLOCK_SIZE); 01948 AES_ECB_decrypt(inBlock, outBlock, AES_BLOCK_SIZE, (byte*)aes->key, 01949 aes->rounds); 01950 return; 01951 } 01952 else { 01953 #ifdef DEBUG_AESNI 01954 printf("Skipping AES-NI\n"); 01955 #endif 01956 } 01957 #endif /* WOLFSSL_AESNI */ 01958 #if defined(WOLFSSL_SCE) && !defined(WOLFSSL_SCE_NO_AES) 01959 return AES_ECB_decrypt(aes, inBlock, outBlock, AES_BLOCK_SIZE); 01960 #endif 01961 01962 /* 01963 * map byte array block to cipher state 01964 * and add initial round key: 01965 */ 01966 XMEMCPY(&s0, inBlock, sizeof(s0)); 01967 XMEMCPY(&s1, inBlock + sizeof(s0), sizeof(s1)); 01968 XMEMCPY(&s2, inBlock + 2 * sizeof(s0), sizeof(s2)); 01969 XMEMCPY(&s3, inBlock + 3 * sizeof(s0), sizeof(s3)); 01970 01971 #ifdef LITTLE_ENDIAN_ORDER 01972 s0 = ByteReverseWord32(s0); 01973 s1 = ByteReverseWord32(s1); 01974 s2 = ByteReverseWord32(s2); 01975 s3 = ByteReverseWord32(s3); 01976 #endif 01977 01978 s0 ^= rk[0]; 01979 s1 ^= rk[1]; 01980 s2 ^= rk[2]; 01981 s3 ^= rk[3]; 01982 01983 #ifndef WOLFSSL_AES_SMALL_TABLES 01984 s0 |= PreFetchTd(); 01985 01986 /* 01987 * Nr - 1 full rounds: 01988 */ 01989 01990 for (;;) { 01991 t0 = 01992 Td[0][GETBYTE(s0, 3)] ^ 01993 Td[1][GETBYTE(s3, 2)] ^ 01994 Td[2][GETBYTE(s2, 1)] ^ 01995 Td[3][GETBYTE(s1, 0)] ^ 01996 rk[4]; 01997 t1 = 01998 Td[0][GETBYTE(s1, 3)] ^ 01999 Td[1][GETBYTE(s0, 2)] ^ 02000 Td[2][GETBYTE(s3, 1)] ^ 02001 Td[3][GETBYTE(s2, 0)] ^ 02002 rk[5]; 02003 t2 = 02004 Td[0][GETBYTE(s2, 3)] ^ 02005 Td[1][GETBYTE(s1, 2)] ^ 02006 Td[2][GETBYTE(s0, 1)] ^ 02007 Td[3][GETBYTE(s3, 0)] ^ 02008 rk[6]; 02009 t3 = 02010 Td[0][GETBYTE(s3, 3)] ^ 02011 Td[1][GETBYTE(s2, 2)] ^ 02012 Td[2][GETBYTE(s1, 1)] ^ 02013 Td[3][GETBYTE(s0, 0)] ^ 02014 rk[7]; 02015 02016 rk += 8; 02017 if (--r == 0) { 02018 break; 02019 } 02020 02021 s0 = 02022 Td[0][GETBYTE(t0, 3)] ^ 02023 Td[1][GETBYTE(t3, 2)] ^ 02024 Td[2][GETBYTE(t2, 1)] ^ 02025 Td[3][GETBYTE(t1, 0)] ^ 02026 rk[0]; 02027 s1 = 02028 Td[0][GETBYTE(t1, 3)] ^ 02029 Td[1][GETBYTE(t0, 2)] ^ 02030 Td[2][GETBYTE(t3, 1)] ^ 02031 Td[3][GETBYTE(t2, 0)] ^ 02032 rk[1]; 02033 s2 = 02034 Td[0][GETBYTE(t2, 3)] ^ 02035 Td[1][GETBYTE(t1, 2)] ^ 02036 Td[2][GETBYTE(t0, 1)] ^ 02037 Td[3][GETBYTE(t3, 0)] ^ 02038 rk[2]; 02039 s3 = 02040 Td[0][GETBYTE(t3, 3)] ^ 02041 Td[1][GETBYTE(t2, 2)] ^ 02042 Td[2][GETBYTE(t1, 1)] ^ 02043 Td[3][GETBYTE(t0, 0)] ^ 02044 rk[3]; 02045 } 02046 /* 02047 * apply last round and 02048 * map cipher state to byte array block: 02049 */ 02050 02051 t0 |= PreFetchTd4(); 02052 02053 s0 = 02054 ((word32)Td4[GETBYTE(t0, 3)] << 24) ^ 02055 ((word32)Td4[GETBYTE(t3, 2)] << 16) ^ 02056 ((word32)Td4[GETBYTE(t2, 1)] << 8) ^ 02057 ((word32)Td4[GETBYTE(t1, 0)]) ^ 02058 rk[0]; 02059 s1 = 02060 ((word32)Td4[GETBYTE(t1, 3)] << 24) ^ 02061 ((word32)Td4[GETBYTE(t0, 2)] << 16) ^ 02062 ((word32)Td4[GETBYTE(t3, 1)] << 8) ^ 02063 ((word32)Td4[GETBYTE(t2, 0)]) ^ 02064 rk[1]; 02065 s2 = 02066 ((word32)Td4[GETBYTE(t2, 3)] << 24) ^ 02067 ((word32)Td4[GETBYTE(t1, 2)] << 16) ^ 02068 ((word32)Td4[GETBYTE(t0, 1)] << 8) ^ 02069 ((word32)Td4[GETBYTE(t3, 0)]) ^ 02070 rk[2]; 02071 s3 = 02072 ((word32)Td4[GETBYTE(t3, 3)] << 24) ^ 02073 ((word32)Td4[GETBYTE(t2, 2)] << 16) ^ 02074 ((word32)Td4[GETBYTE(t1, 1)] << 8) ^ 02075 ((word32)Td4[GETBYTE(t0, 0)]) ^ 02076 rk[3]; 02077 #else 02078 s0 |= PreFetchTd4(); 02079 02080 r *= 2; 02081 for (rk += 4; r > 1; r--, rk += 4) { 02082 t0 = 02083 ((word32)Td4[GETBYTE(s0, 3)] << 24) ^ 02084 ((word32)Td4[GETBYTE(s3, 2)] << 16) ^ 02085 ((word32)Td4[GETBYTE(s2, 1)] << 8) ^ 02086 ((word32)Td4[GETBYTE(s1, 0)]) ^ 02087 rk[0]; 02088 t1 = 02089 ((word32)Td4[GETBYTE(s1, 3)] << 24) ^ 02090 ((word32)Td4[GETBYTE(s0, 2)] << 16) ^ 02091 ((word32)Td4[GETBYTE(s3, 1)] << 8) ^ 02092 ((word32)Td4[GETBYTE(s2, 0)]) ^ 02093 rk[1]; 02094 t2 = 02095 ((word32)Td4[GETBYTE(s2, 3)] << 24) ^ 02096 ((word32)Td4[GETBYTE(s1, 2)] << 16) ^ 02097 ((word32)Td4[GETBYTE(s0, 1)] << 8) ^ 02098 ((word32)Td4[GETBYTE(s3, 0)]) ^ 02099 rk[2]; 02100 t3 = 02101 ((word32)Td4[GETBYTE(s3, 3)] << 24) ^ 02102 ((word32)Td4[GETBYTE(s2, 2)] << 16) ^ 02103 ((word32)Td4[GETBYTE(s1, 1)] << 8) ^ 02104 ((word32)Td4[GETBYTE(s0, 0)]) ^ 02105 rk[3]; 02106 02107 s0 = 02108 (inv_col_mul(t0, 0, 2, 1, 3) << 24) ^ 02109 (inv_col_mul(t0, 3, 1, 0, 2) << 16) ^ 02110 (inv_col_mul(t0, 2, 0, 3, 1) << 8) ^ 02111 (inv_col_mul(t0, 1, 3, 2, 0) ); 02112 s1 = 02113 (inv_col_mul(t1, 0, 2, 1, 3) << 24) ^ 02114 (inv_col_mul(t1, 3, 1, 0, 2) << 16) ^ 02115 (inv_col_mul(t1, 2, 0, 3, 1) << 8) ^ 02116 (inv_col_mul(t1, 1, 3, 2, 0) ); 02117 s2 = 02118 (inv_col_mul(t2, 0, 2, 1, 3) << 24) ^ 02119 (inv_col_mul(t2, 3, 1, 0, 2) << 16) ^ 02120 (inv_col_mul(t2, 2, 0, 3, 1) << 8) ^ 02121 (inv_col_mul(t2, 1, 3, 2, 0) ); 02122 s3 = 02123 (inv_col_mul(t3, 0, 2, 1, 3) << 24) ^ 02124 (inv_col_mul(t3, 3, 1, 0, 2) << 16) ^ 02125 (inv_col_mul(t3, 2, 0, 3, 1) << 8) ^ 02126 (inv_col_mul(t3, 1, 3, 2, 0) ); 02127 } 02128 02129 t0 = 02130 ((word32)Td4[GETBYTE(s0, 3)] << 24) ^ 02131 ((word32)Td4[GETBYTE(s3, 2)] << 16) ^ 02132 ((word32)Td4[GETBYTE(s2, 1)] << 8) ^ 02133 ((word32)Td4[GETBYTE(s1, 0)]); 02134 t1 = 02135 ((word32)Td4[GETBYTE(s1, 3)] << 24) ^ 02136 ((word32)Td4[GETBYTE(s0, 2)] << 16) ^ 02137 ((word32)Td4[GETBYTE(s3, 1)] << 8) ^ 02138 ((word32)Td4[GETBYTE(s2, 0)]); 02139 t2 = 02140 ((word32)Td4[GETBYTE(s2, 3)] << 24) ^ 02141 ((word32)Td4[GETBYTE(s1, 2)] << 16) ^ 02142 ((word32)Td4[GETBYTE(s0, 1)] << 8) ^ 02143 ((word32)Td4[GETBYTE(s3, 0)]); 02144 t3 = 02145 ((word32)Td4[GETBYTE(s3, 3)] << 24) ^ 02146 ((word32)Td4[GETBYTE(s2, 2)] << 16) ^ 02147 ((word32)Td4[GETBYTE(s1, 1)] << 8) ^ 02148 ((word32)Td4[GETBYTE(s0, 0)]); 02149 s0 = t0 ^ rk[0]; 02150 s1 = t1 ^ rk[1]; 02151 s2 = t2 ^ rk[2]; 02152 s3 = t3 ^ rk[3]; 02153 #endif 02154 02155 /* write out */ 02156 #ifdef LITTLE_ENDIAN_ORDER 02157 s0 = ByteReverseWord32(s0); 02158 s1 = ByteReverseWord32(s1); 02159 s2 = ByteReverseWord32(s2); 02160 s3 = ByteReverseWord32(s3); 02161 #endif 02162 02163 XMEMCPY(outBlock, &s0, sizeof(s0)); 02164 XMEMCPY(outBlock + sizeof(s0), &s1, sizeof(s1)); 02165 XMEMCPY(outBlock + 2 * sizeof(s0), &s2, sizeof(s2)); 02166 XMEMCPY(outBlock + 3 * sizeof(s0), &s3, sizeof(s3)); 02167 } 02168 #endif /* HAVE_AES_CBC || WOLFSSL_AES_DIRECT */ 02169 #endif /* HAVE_AES_DECRYPT */ 02170 02171 #endif /* NEED_AES_TABLES */ 02172 02173 02174 02175 /* wc_AesSetKey */ 02176 #if defined(STM32_CRYPTO) 02177 02178 int wc_AesSetKey(Aes* aes, const byte* userKey, word32 keylen, 02179 const byte* iv, int dir) 02180 { 02181 word32 *rk; 02182 02183 (void)dir; 02184 02185 if (aes == NULL || (keylen != 16 && 02186 #ifdef WOLFSSL_AES_192 02187 keylen != 24 && 02188 #endif 02189 keylen != 32)) { 02190 return BAD_FUNC_ARG; 02191 } 02192 02193 rk = aes->key; 02194 aes->keylen = keylen; 02195 aes->rounds = keylen/4 + 6; 02196 XMEMCPY(rk, userKey, keylen); 02197 #if !defined(WOLFSSL_STM32_CUBEMX) || defined(STM32_HAL_V2) 02198 ByteReverseWords(rk, rk, keylen); 02199 #endif 02200 #if defined(WOLFSSL_AES_CFB) || defined(WOLFSSL_AES_COUNTER) || \ 02201 defined(WOLFSSL_AES_OFB) 02202 aes->left = 0; 02203 #endif 02204 02205 return wc_AesSetIV(aes, iv); 02206 } 02207 #if defined(WOLFSSL_AES_DIRECT) 02208 int wc_AesSetKeyDirect(Aes* aes, const byte* userKey, word32 keylen, 02209 const byte* iv, int dir) 02210 { 02211 return wc_AesSetKey(aes, userKey, keylen, iv, dir); 02212 } 02213 #endif 02214 02215 #elif defined(HAVE_COLDFIRE_SEC) 02216 #if defined (HAVE_THREADX) 02217 #include "memory_pools.h" 02218 extern TX_BYTE_POOL mp_ncached; /* Non Cached memory pool */ 02219 #endif 02220 02221 #define AES_BUFFER_SIZE (AES_BLOCK_SIZE * 64) 02222 static unsigned char *AESBuffIn = NULL; 02223 static unsigned char *AESBuffOut = NULL; 02224 static byte *secReg; 02225 static byte *secKey; 02226 static volatile SECdescriptorType *secDesc; 02227 02228 static wolfSSL_Mutex Mutex_AesSEC; 02229 02230 #define SEC_DESC_AES_CBC_ENCRYPT 0x60300010 02231 #define SEC_DESC_AES_CBC_DECRYPT 0x60200010 02232 02233 extern volatile unsigned char __MBAR[]; 02234 02235 int wc_AesSetKey(Aes* aes, const byte* userKey, word32 keylen, 02236 const byte* iv, int dir) 02237 { 02238 if (AESBuffIn == NULL) { 02239 #if defined (HAVE_THREADX) 02240 int s1, s2, s3, s4, s5; 02241 s5 = tx_byte_allocate(&mp_ncached,(void *)&secDesc, 02242 sizeof(SECdescriptorType), TX_NO_WAIT); 02243 s1 = tx_byte_allocate(&mp_ncached, (void *)&AESBuffIn, 02244 AES_BUFFER_SIZE, TX_NO_WAIT); 02245 s2 = tx_byte_allocate(&mp_ncached, (void *)&AESBuffOut, 02246 AES_BUFFER_SIZE, TX_NO_WAIT); 02247 s3 = tx_byte_allocate(&mp_ncached, (void *)&secKey, 02248 AES_BLOCK_SIZE*2, TX_NO_WAIT); 02249 s4 = tx_byte_allocate(&mp_ncached, (void *)&secReg, 02250 AES_BLOCK_SIZE, TX_NO_WAIT); 02251 02252 if (s1 || s2 || s3 || s4 || s5) 02253 return BAD_FUNC_ARG; 02254 #else 02255 #warning "Allocate non-Cache buffers" 02256 #endif 02257 02258 wc_InitMutex(&Mutex_AesSEC); 02259 } 02260 02261 if (!((keylen == 16) || (keylen == 24) || (keylen == 32))) 02262 return BAD_FUNC_ARG; 02263 02264 if (aes == NULL) 02265 return BAD_FUNC_ARG; 02266 02267 aes->keylen = keylen; 02268 aes->rounds = keylen/4 + 6; 02269 XMEMCPY(aes->key, userKey, keylen); 02270 02271 if (iv) 02272 XMEMCPY(aes->reg, iv, AES_BLOCK_SIZE); 02273 02274 #if defined(WOLFSSL_AES_CFB) || defined(WOLFSSL_AES_COUNTER) || \ 02275 defined(WOLFSSL_AES_OFB) 02276 aes->left = 0; 02277 #endif 02278 02279 return 0; 02280 } 02281 #elif defined(FREESCALE_LTC) 02282 int wc_AesSetKey(Aes* aes, const byte* userKey, word32 keylen, const byte* iv, 02283 int dir) 02284 { 02285 if (aes == NULL || !((keylen == 16) || (keylen == 24) || (keylen == 32))) 02286 return BAD_FUNC_ARG; 02287 02288 aes->rounds = keylen/4 + 6; 02289 XMEMCPY(aes->key, userKey, keylen); 02290 02291 #if defined(WOLFSSL_AES_CFB) || defined(WOLFSSL_AES_COUNTER) || \ 02292 defined(WOLFSSL_AES_OFB) 02293 aes->left = 0; 02294 #endif 02295 02296 return wc_AesSetIV(aes, iv); 02297 } 02298 02299 int wc_AesSetKeyDirect(Aes* aes, const byte* userKey, word32 keylen, 02300 const byte* iv, int dir) 02301 { 02302 return wc_AesSetKey(aes, userKey, keylen, iv, dir); 02303 } 02304 #elif defined(FREESCALE_MMCAU) 02305 int wc_AesSetKey(Aes* aes, const byte* userKey, word32 keylen, 02306 const byte* iv, int dir) 02307 { 02308 int ret; 02309 byte* rk; 02310 byte* tmpKey = (byte*)userKey; 02311 int tmpKeyDynamic = 0; 02312 word32 alignOffset = 0; 02313 02314 (void)dir; 02315 02316 if (!((keylen == 16) || (keylen == 24) || (keylen == 32))) 02317 return BAD_FUNC_ARG; 02318 if (aes == NULL) 02319 return BAD_FUNC_ARG; 02320 02321 rk = (byte*)aes->key; 02322 if (rk == NULL) 02323 return BAD_FUNC_ARG; 02324 02325 #if defined(WOLFSSL_AES_CFB) || defined(WOLFSSL_AES_COUNTER) || \ 02326 defined(WOLFSSL_AES_OFB) 02327 aes->left = 0; 02328 #endif 02329 02330 aes->rounds = keylen/4 + 6; 02331 02332 #ifdef FREESCALE_MMCAU_CLASSIC 02333 if ((wolfssl_word)userKey % WOLFSSL_MMCAU_ALIGNMENT) { 02334 #ifndef NO_WOLFSSL_ALLOC_ALIGN 02335 byte* tmp = (byte*)XMALLOC(keylen + WOLFSSL_MMCAU_ALIGNMENT, 02336 aes->heap, DYNAMIC_TYPE_TMP_BUFFER); 02337 if (tmp == NULL) { 02338 return MEMORY_E; 02339 } 02340 alignOffset = WOLFSSL_MMCAU_ALIGNMENT - 02341 ((wolfssl_word)tmp % WOLFSSL_MMCAU_ALIGNMENT); 02342 tmpKey = tmp + alignOffset; 02343 XMEMCPY(tmpKey, userKey, keylen); 02344 tmpKeyDynamic = 1; 02345 #else 02346 WOLFSSL_MSG("Bad cau_aes_set_key alignment"); 02347 return BAD_ALIGN_E; 02348 #endif 02349 } 02350 #endif 02351 02352 ret = wolfSSL_CryptHwMutexLock(); 02353 if(ret == 0) { 02354 #ifdef FREESCALE_MMCAU_CLASSIC 02355 cau_aes_set_key(tmpKey, keylen*8, rk); 02356 #else 02357 MMCAU_AES_SetKey(tmpKey, keylen, rk); 02358 #endif 02359 wolfSSL_CryptHwMutexUnLock(); 02360 02361 ret = wc_AesSetIV(aes, iv); 02362 } 02363 02364 if (tmpKeyDynamic == 1) { 02365 XFREE(tmpKey - alignOffset, aes->heap, DYNAMIC_TYPE_TMP_BUFFER); 02366 } 02367 02368 return ret; 02369 } 02370 02371 int wc_AesSetKeyDirect(Aes* aes, const byte* userKey, word32 keylen, 02372 const byte* iv, int dir) 02373 { 02374 return wc_AesSetKey(aes, userKey, keylen, iv, dir); 02375 } 02376 02377 #elif defined(WOLFSSL_NRF51_AES) 02378 int wc_AesSetKey(Aes* aes, const byte* userKey, word32 keylen, 02379 const byte* iv, int dir) 02380 { 02381 int ret; 02382 02383 (void)dir; 02384 (void)iv; 02385 02386 if (aes == NULL || keylen != 16) 02387 return BAD_FUNC_ARG; 02388 02389 aes->keylen = keylen; 02390 aes->rounds = keylen/4 + 6; 02391 ret = nrf51_aes_set_key(userKey); 02392 02393 #if defined(WOLFSSL_AES_CFB) || defined(WOLFSSL_AES_COUNTER) || \ 02394 defined(WOLFSSL_AES_OFB) 02395 aes->left = 0; 02396 #endif 02397 02398 return ret; 02399 } 02400 02401 int wc_AesSetKeyDirect(Aes* aes, const byte* userKey, word32 keylen, 02402 const byte* iv, int dir) 02403 { 02404 return wc_AesSetKey(aes, userKey, keylen, iv, dir); 02405 } 02406 #elif defined(WOLFSSL_ESP32WROOM32_CRYPT) && \ 02407 !defined(NO_WOLFSSL_ESP32WROOM32_CRYPT_AES) 02408 02409 int wc_AesSetKey(Aes* aes, const byte* userKey, word32 keylen, 02410 const byte* iv, int dir) 02411 { 02412 (void)dir; 02413 (void)iv; 02414 02415 if (aes == NULL || (keylen != 16 && keylen != 24 && keylen != 32)) { 02416 return BAD_FUNC_ARG; 02417 } 02418 02419 aes->keylen = keylen; 02420 aes->rounds = keylen/4 + 6; 02421 02422 XMEMCPY(aes->key, userKey, keylen); 02423 #if defined(WOLFSSL_AES_COUNTER) 02424 aes->left = 0; 02425 #endif 02426 return wc_AesSetIV(aes, iv); 02427 } 02428 02429 int wc_AesSetKeyDirect(Aes* aes, const byte* userKey, word32 keylen, 02430 const byte* iv, int dir) 02431 { 02432 return wc_AesSetKey(aes, userKey, keylen, iv, dir); 02433 } 02434 #elif defined(WOLFSSL_CRYPTOCELL) && defined(WOLFSSL_CRYPTOCELL_AES) 02435 02436 int wc_AesSetKey(Aes* aes, const byte* userKey, word32 keylen, const byte* iv, 02437 int dir) 02438 { 02439 SaSiError_t ret = SASI_OK; 02440 SaSiAesIv_t iv_aes; 02441 02442 if (aes == NULL || 02443 (keylen != AES_128_KEY_SIZE && 02444 keylen != AES_192_KEY_SIZE && 02445 keylen != AES_256_KEY_SIZE)) { 02446 return BAD_FUNC_ARG; 02447 } 02448 #if defined(AES_MAX_KEY_SIZE) 02449 if (keylen > (AES_MAX_KEY_SIZE/8)) { 02450 return BAD_FUNC_ARG; 02451 } 02452 #endif 02453 if (dir != AES_ENCRYPTION && 02454 dir != AES_DECRYPTION) { 02455 return BAD_FUNC_ARG; 02456 } 02457 02458 if (dir == AES_ENCRYPTION) { 02459 aes->ctx.mode = SASI_AES_ENCRYPT; 02460 SaSi_AesInit(&aes->ctx.user_ctx, 02461 SASI_AES_ENCRYPT, 02462 SASI_AES_MODE_CBC, 02463 SASI_AES_PADDING_NONE); 02464 } 02465 else { 02466 aes->ctx.mode = SASI_AES_DECRYPT; 02467 SaSi_AesInit(&aes->ctx.user_ctx, 02468 SASI_AES_DECRYPT, 02469 SASI_AES_MODE_CBC, 02470 SASI_AES_PADDING_NONE); 02471 } 02472 02473 aes->keylen = keylen; 02474 aes->rounds = keylen/4 + 6; 02475 XMEMCPY(aes->key, userKey, keylen); 02476 02477 aes->ctx.key.pKey = (uint8_t*)aes->key; 02478 aes->ctx.key.keySize= keylen; 02479 02480 ret = SaSi_AesSetKey(&aes->ctx.user_ctx, 02481 SASI_AES_USER_KEY, 02482 &aes->ctx.key, 02483 sizeof(aes->ctx.key)); 02484 if (ret != SASI_OK) { 02485 return BAD_FUNC_ARG; 02486 } 02487 02488 ret = wc_AesSetIV(aes, iv); 02489 02490 if (iv) 02491 XMEMCPY(iv_aes, iv, AES_BLOCK_SIZE); 02492 else 02493 XMEMSET(iv_aes, 0, AES_BLOCK_SIZE); 02494 02495 02496 ret = SaSi_AesSetIv(&aes->ctx.user_ctx, iv_aes); 02497 if (ret != SASI_OK) { 02498 return ret; 02499 } 02500 return ret; 02501 } 02502 #if defined(WOLFSSL_AES_DIRECT) 02503 int wc_AesSetKeyDirect(Aes* aes, const byte* userKey, word32 keylen, 02504 const byte* iv, int dir) 02505 { 02506 return wc_AesSetKey(aes, userKey, keylen, iv, dir); 02507 } 02508 #endif 02509 02510 #elif defined(WOLFSSL_IMX6_CAAM) && !defined(NO_IMX6_CAAM_AES) 02511 /* implemented in wolfcrypt/src/port/caam/caam_aes.c */ 02512 02513 #elif defined(WOLFSSL_AFALG) 02514 /* implemented in wolfcrypt/src/port/af_alg/afalg_aes.c */ 02515 02516 #elif defined(WOLFSSL_DEVCRYPTO_AES) 02517 /* implemented in wolfcrypt/src/port/devcrypto/devcrypto_aes.c */ 02518 02519 #else 02520 02521 /* Software AES - SetKey */ 02522 static int wc_AesSetKeyLocal(Aes* aes, const byte* userKey, word32 keylen, 02523 const byte* iv, int dir) 02524 { 02525 word32 *rk = aes->key; 02526 #ifdef NEED_AES_TABLES 02527 word32 temp; 02528 unsigned int i = 0; 02529 #endif 02530 02531 #ifdef WOLFSSL_AESNI 02532 aes->use_aesni = 0; 02533 #endif /* WOLFSSL_AESNI */ 02534 #if defined(WOLFSSL_AES_CFB) || defined(WOLFSSL_AES_COUNTER) || \ 02535 defined(WOLFSSL_AES_OFB) 02536 aes->left = 0; 02537 #endif 02538 02539 aes->keylen = keylen; 02540 aes->rounds = (keylen/4) + 6; 02541 02542 XMEMCPY(rk, userKey, keylen); 02543 #if defined(LITTLE_ENDIAN_ORDER) && !defined(WOLFSSL_PIC32MZ_CRYPT) && \ 02544 (!defined(WOLFSSL_ESP32WROOM32_CRYPT) || \ 02545 defined(NO_WOLFSSL_ESP32WROOM32_CRYPT_AES)) 02546 ByteReverseWords(rk, rk, keylen); 02547 #endif 02548 02549 #ifdef NEED_AES_TABLES 02550 switch (keylen) { 02551 #if defined(AES_MAX_KEY_SIZE) && AES_MAX_KEY_SIZE >= 128 && \ 02552 defined(WOLFSSL_AES_128) 02553 case 16: 02554 while (1) 02555 { 02556 temp = rk[3]; 02557 rk[4] = rk[0] ^ 02558 #ifndef WOLFSSL_AES_SMALL_TABLES 02559 (Te[2][GETBYTE(temp, 2)] & 0xff000000) ^ 02560 (Te[3][GETBYTE(temp, 1)] & 0x00ff0000) ^ 02561 (Te[0][GETBYTE(temp, 0)] & 0x0000ff00) ^ 02562 (Te[1][GETBYTE(temp, 3)] & 0x000000ff) ^ 02563 #else 02564 ((word32)Tsbox[GETBYTE(temp, 2)] << 24) ^ 02565 ((word32)Tsbox[GETBYTE(temp, 1)] << 16) ^ 02566 ((word32)Tsbox[GETBYTE(temp, 0)] << 8) ^ 02567 ((word32)Tsbox[GETBYTE(temp, 3)]) ^ 02568 #endif 02569 rcon[i]; 02570 rk[5] = rk[1] ^ rk[4]; 02571 rk[6] = rk[2] ^ rk[5]; 02572 rk[7] = rk[3] ^ rk[6]; 02573 if (++i == 10) 02574 break; 02575 rk += 4; 02576 } 02577 break; 02578 #endif /* 128 */ 02579 02580 #if defined(AES_MAX_KEY_SIZE) && AES_MAX_KEY_SIZE >= 192 && \ 02581 defined(WOLFSSL_AES_192) 02582 case 24: 02583 /* for (;;) here triggers a bug in VC60 SP4 w/ Pro Pack */ 02584 while (1) 02585 { 02586 temp = rk[ 5]; 02587 rk[ 6] = rk[ 0] ^ 02588 #ifndef WOLFSSL_AES_SMALL_TABLES 02589 (Te[2][GETBYTE(temp, 2)] & 0xff000000) ^ 02590 (Te[3][GETBYTE(temp, 1)] & 0x00ff0000) ^ 02591 (Te[0][GETBYTE(temp, 0)] & 0x0000ff00) ^ 02592 (Te[1][GETBYTE(temp, 3)] & 0x000000ff) ^ 02593 #else 02594 ((word32)Tsbox[GETBYTE(temp, 2)] << 24) ^ 02595 ((word32)Tsbox[GETBYTE(temp, 1)] << 16) ^ 02596 ((word32)Tsbox[GETBYTE(temp, 0)] << 8) ^ 02597 ((word32)Tsbox[GETBYTE(temp, 3)]) ^ 02598 #endif 02599 rcon[i]; 02600 rk[ 7] = rk[ 1] ^ rk[ 6]; 02601 rk[ 8] = rk[ 2] ^ rk[ 7]; 02602 rk[ 9] = rk[ 3] ^ rk[ 8]; 02603 if (++i == 8) 02604 break; 02605 rk[10] = rk[ 4] ^ rk[ 9]; 02606 rk[11] = rk[ 5] ^ rk[10]; 02607 rk += 6; 02608 } 02609 break; 02610 #endif /* 192 */ 02611 02612 #if defined(AES_MAX_KEY_SIZE) && AES_MAX_KEY_SIZE >= 256 && \ 02613 defined(WOLFSSL_AES_256) 02614 case 32: 02615 while (1) 02616 { 02617 temp = rk[ 7]; 02618 rk[ 8] = rk[ 0] ^ 02619 #ifndef WOLFSSL_AES_SMALL_TABLES 02620 (Te[2][GETBYTE(temp, 2)] & 0xff000000) ^ 02621 (Te[3][GETBYTE(temp, 1)] & 0x00ff0000) ^ 02622 (Te[0][GETBYTE(temp, 0)] & 0x0000ff00) ^ 02623 (Te[1][GETBYTE(temp, 3)] & 0x000000ff) ^ 02624 #else 02625 ((word32)Tsbox[GETBYTE(temp, 2)] << 24) ^ 02626 ((word32)Tsbox[GETBYTE(temp, 1)] << 16) ^ 02627 ((word32)Tsbox[GETBYTE(temp, 0)] << 8) ^ 02628 ((word32)Tsbox[GETBYTE(temp, 3)]) ^ 02629 #endif 02630 rcon[i]; 02631 rk[ 9] = rk[ 1] ^ rk[ 8]; 02632 rk[10] = rk[ 2] ^ rk[ 9]; 02633 rk[11] = rk[ 3] ^ rk[10]; 02634 if (++i == 7) 02635 break; 02636 temp = rk[11]; 02637 rk[12] = rk[ 4] ^ 02638 #ifndef WOLFSSL_AES_SMALL_TABLES 02639 (Te[2][GETBYTE(temp, 3)] & 0xff000000) ^ 02640 (Te[3][GETBYTE(temp, 2)] & 0x00ff0000) ^ 02641 (Te[0][GETBYTE(temp, 1)] & 0x0000ff00) ^ 02642 (Te[1][GETBYTE(temp, 0)] & 0x000000ff); 02643 #else 02644 ((word32)Tsbox[GETBYTE(temp, 3)] << 24) ^ 02645 ((word32)Tsbox[GETBYTE(temp, 2)] << 16) ^ 02646 ((word32)Tsbox[GETBYTE(temp, 1)] << 8) ^ 02647 ((word32)Tsbox[GETBYTE(temp, 0)]); 02648 #endif 02649 rk[13] = rk[ 5] ^ rk[12]; 02650 rk[14] = rk[ 6] ^ rk[13]; 02651 rk[15] = rk[ 7] ^ rk[14]; 02652 02653 rk += 8; 02654 } 02655 break; 02656 #endif /* 256 */ 02657 02658 default: 02659 return BAD_FUNC_ARG; 02660 } /* switch */ 02661 02662 #if defined(HAVE_AES_DECRYPT) 02663 if (dir == AES_DECRYPTION) { 02664 unsigned int j; 02665 rk = aes->key; 02666 02667 /* invert the order of the round keys: */ 02668 for (i = 0, j = 4* aes->rounds; i < j; i += 4, j -= 4) { 02669 temp = rk[i ]; rk[i ] = rk[j ]; rk[j ] = temp; 02670 temp = rk[i + 1]; rk[i + 1] = rk[j + 1]; rk[j + 1] = temp; 02671 temp = rk[i + 2]; rk[i + 2] = rk[j + 2]; rk[j + 2] = temp; 02672 temp = rk[i + 3]; rk[i + 3] = rk[j + 3]; rk[j + 3] = temp; 02673 } 02674 #if !defined(WOLFSSL_AES_SMALL_TABLES) 02675 /* apply the inverse MixColumn transform to all round keys but the 02676 first and the last: */ 02677 for (i = 1; i < aes->rounds; i++) { 02678 rk += 4; 02679 rk[0] = 02680 Td[0][Te[1][GETBYTE(rk[0], 3)] & 0xff] ^ 02681 Td[1][Te[1][GETBYTE(rk[0], 2)] & 0xff] ^ 02682 Td[2][Te[1][GETBYTE(rk[0], 1)] & 0xff] ^ 02683 Td[3][Te[1][GETBYTE(rk[0], 0)] & 0xff]; 02684 rk[1] = 02685 Td[0][Te[1][GETBYTE(rk[1], 3)] & 0xff] ^ 02686 Td[1][Te[1][GETBYTE(rk[1], 2)] & 0xff] ^ 02687 Td[2][Te[1][GETBYTE(rk[1], 1)] & 0xff] ^ 02688 Td[3][Te[1][GETBYTE(rk[1], 0)] & 0xff]; 02689 rk[2] = 02690 Td[0][Te[1][GETBYTE(rk[2], 3)] & 0xff] ^ 02691 Td[1][Te[1][GETBYTE(rk[2], 2)] & 0xff] ^ 02692 Td[2][Te[1][GETBYTE(rk[2], 1)] & 0xff] ^ 02693 Td[3][Te[1][GETBYTE(rk[2], 0)] & 0xff]; 02694 rk[3] = 02695 Td[0][Te[1][GETBYTE(rk[3], 3)] & 0xff] ^ 02696 Td[1][Te[1][GETBYTE(rk[3], 2)] & 0xff] ^ 02697 Td[2][Te[1][GETBYTE(rk[3], 1)] & 0xff] ^ 02698 Td[3][Te[1][GETBYTE(rk[3], 0)] & 0xff]; 02699 } 02700 #endif 02701 } 02702 #else 02703 (void)dir; 02704 #endif /* HAVE_AES_DECRYPT */ 02705 (void)temp; 02706 #endif /* NEED_AES_TABLES */ 02707 02708 #if defined(WOLFSSL_SCE) && !defined(WOLFSSL_SCE_NO_AES) 02709 XMEMCPY((byte*)aes->key, userKey, keylen); 02710 if (WOLFSSL_SCE_GSCE_HANDLE.p_cfg->endian_flag == CRYPTO_WORD_ENDIAN_BIG) { 02711 ByteReverseWords(aes->key, aes->key, 32); 02712 } 02713 #endif 02714 02715 return wc_AesSetIV(aes, iv); 02716 } 02717 02718 int wc_AesSetKey(Aes* aes, const byte* userKey, word32 keylen, 02719 const byte* iv, int dir) 02720 { 02721 int ret; 02722 #if defined(AES_MAX_KEY_SIZE) 02723 const word32 max_key_len = (AES_MAX_KEY_SIZE / 8); 02724 #endif 02725 02726 #ifdef WOLFSSL_IMX6_CAAM_BLOB 02727 byte local[32]; 02728 word32 localSz = 32; 02729 02730 if (keylen == (16 + WC_CAAM_BLOB_SZ) || 02731 keylen == (24 + WC_CAAM_BLOB_SZ) || 02732 keylen == (32 + WC_CAAM_BLOB_SZ)) { 02733 if (wc_caamOpenBlob((byte*)userKey, keylen, local, &localSz) != 0) { 02734 return BAD_FUNC_ARG; 02735 } 02736 02737 /* set local values */ 02738 userKey = local; 02739 keylen = localSz; 02740 } 02741 #endif 02742 if (aes == NULL || 02743 !((keylen == 16) || (keylen == 24) || (keylen == 32))) { 02744 return BAD_FUNC_ARG; 02745 } 02746 02747 #if defined(AES_MAX_KEY_SIZE) 02748 /* Check key length */ 02749 if (keylen > max_key_len) { 02750 return BAD_FUNC_ARG; 02751 } 02752 #endif 02753 aes->keylen = keylen; 02754 aes->rounds = keylen/4 + 6; 02755 02756 #if defined(WOLF_CRYPTO_CB) || (defined(WOLFSSL_DEVCRYPTO) && \ 02757 (defined(WOLFSSL_DEVCRYPTO_AES) || defined(WOLFSSL_DEVCRYPTO_CBC))) || \ 02758 (defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_AES)) 02759 #ifdef WOLF_CRYPTO_CB 02760 if (aes->devId != INVALID_DEVID) 02761 #endif 02762 { 02763 XMEMCPY(aes->devKey, userKey, keylen); 02764 } 02765 #endif 02766 02767 #ifdef WOLFSSL_AESNI 02768 if (checkAESNI == 0) { 02769 haveAESNI = Check_CPU_support_AES(); 02770 checkAESNI = 1; 02771 } 02772 if (haveAESNI) { 02773 #if defined(WOLFSSL_AES_COUNTER) || defined(WOLFSSL_AES_CFB) || \ 02774 defined(WOLFSSL_AES_OFB) 02775 aes->left = 0; 02776 #endif /* WOLFSSL_AES_COUNTER */ 02777 aes->use_aesni = 1; 02778 if (iv) 02779 XMEMCPY(aes->reg, iv, AES_BLOCK_SIZE); 02780 else 02781 XMEMSET(aes->reg, 0, AES_BLOCK_SIZE); 02782 if (dir == AES_ENCRYPTION) 02783 return AES_set_encrypt_key(userKey, keylen * 8, aes); 02784 #ifdef HAVE_AES_DECRYPT 02785 else 02786 return AES_set_decrypt_key(userKey, keylen * 8, aes); 02787 #endif 02788 } 02789 #endif /* WOLFSSL_AESNI */ 02790 02791 ret = wc_AesSetKeyLocal(aes, userKey, keylen, iv, dir); 02792 02793 #if defined(WOLFSSL_DEVCRYPTO) && \ 02794 (defined(WOLFSSL_DEVCRYPTO_AES) || defined(WOLFSSL_DEVCRYPTO_CBC)) 02795 aes->ctx.cfd = -1; 02796 #endif 02797 #ifdef WOLFSSL_IMX6_CAAM_BLOB 02798 ForceZero(local, sizeof(local)); 02799 #endif 02800 return ret; 02801 } 02802 02803 #if defined(WOLFSSL_AES_DIRECT) || defined(WOLFSSL_AES_COUNTER) 02804 /* AES-CTR and AES-DIRECT need to use this for key setup, no aesni yet */ 02805 int wc_AesSetKeyDirect(Aes* aes, const byte* userKey, word32 keylen, 02806 const byte* iv, int dir) 02807 { 02808 int ret; 02809 02810 #ifdef WOLFSSL_IMX6_CAAM_BLOB 02811 byte local[32]; 02812 word32 localSz = 32; 02813 02814 if (keylen == (16 + WC_CAAM_BLOB_SZ) || 02815 keylen == (24 + WC_CAAM_BLOB_SZ) || 02816 keylen == (32 + WC_CAAM_BLOB_SZ)) { 02817 if (wc_caamOpenBlob((byte*)userKey, keylen, local, &localSz) 02818 != 0) { 02819 return BAD_FUNC_ARG; 02820 } 02821 02822 /* set local values */ 02823 userKey = local; 02824 keylen = localSz; 02825 } 02826 #endif 02827 ret = wc_AesSetKeyLocal(aes, userKey, keylen, iv, dir); 02828 02829 #ifdef WOLFSSL_IMX6_CAAM_BLOB 02830 ForceZero(local, sizeof(local)); 02831 #endif 02832 02833 return ret; 02834 } 02835 #endif /* WOLFSSL_AES_DIRECT || WOLFSSL_AES_COUNTER */ 02836 #endif /* wc_AesSetKey block */ 02837 02838 02839 /* wc_AesSetIV is shared between software and hardware */ 02840 int wc_AesSetIV(Aes* aes, const byte* iv) 02841 { 02842 if (aes == NULL) 02843 return BAD_FUNC_ARG; 02844 02845 if (iv) 02846 XMEMCPY(aes->reg, iv, AES_BLOCK_SIZE); 02847 else 02848 XMEMSET(aes->reg, 0, AES_BLOCK_SIZE); 02849 02850 return 0; 02851 } 02852 02853 /* AES-DIRECT */ 02854 #if defined(WOLFSSL_AES_DIRECT) 02855 #if defined(HAVE_COLDFIRE_SEC) 02856 #error "Coldfire SEC doesn't yet support AES direct" 02857 02858 #elif defined(FREESCALE_LTC) 02859 /* Allow direct access to one block encrypt */ 02860 void wc_AesEncryptDirect(Aes* aes, byte* out, const byte* in) 02861 { 02862 byte *key; 02863 uint32_t keySize; 02864 02865 key = (byte*)aes->key; 02866 wc_AesGetKeySize(aes, &keySize); 02867 02868 LTC_AES_EncryptEcb(LTC_BASE, in, out, AES_BLOCK_SIZE, 02869 key, keySize); 02870 } 02871 02872 /* Allow direct access to one block decrypt */ 02873 void wc_AesDecryptDirect(Aes* aes, byte* out, const byte* in) 02874 { 02875 byte *key; 02876 uint32_t keySize; 02877 02878 key = (byte*)aes->key; 02879 wc_AesGetKeySize(aes, &keySize); 02880 02881 LTC_AES_DecryptEcb(LTC_BASE, in, out, AES_BLOCK_SIZE, 02882 key, keySize, kLTC_EncryptKey); 02883 } 02884 02885 #elif defined(WOLFSSL_IMX6_CAAM) && !defined(NO_IMX6_CAAM_AES) 02886 /* implemented in wolfcrypt/src/port/caam/caam_aes.c */ 02887 02888 #elif defined(WOLFSSL_AFALG) 02889 /* implemented in wolfcrypt/src/port/af_alg/afalg_aes.c */ 02890 02891 #elif defined(WOLFSSL_DEVCRYPTO_AES) 02892 /* implemented in wolfcrypt/src/port/devcrypt/devcrypto_aes.c */ 02893 02894 #elif defined(STM32_CRYPTO) 02895 /* Allow direct access to one block encrypt */ 02896 void wc_AesEncryptDirect(Aes* aes, byte* out, const byte* in) 02897 { 02898 if (wolfSSL_CryptHwMutexLock() == 0) { 02899 wc_AesEncrypt(aes, in, out); 02900 wolfSSL_CryptHwMutexUnLock(); 02901 } 02902 } 02903 #ifdef HAVE_AES_DECRYPT 02904 /* Allow direct access to one block decrypt */ 02905 void wc_AesDecryptDirect(Aes* aes, byte* out, const byte* in) 02906 { 02907 if (wolfSSL_CryptHwMutexLock() == 0) { 02908 wc_AesDecrypt(aes, in, out); 02909 wolfSSL_CryptHwMutexUnLock(); 02910 } 02911 } 02912 #endif /* HAVE_AES_DECRYPT */ 02913 02914 #elif defined(WOLFSSL_ESP32WROOM32_CRYPT) && \ 02915 !defined(NO_WOLFSSL_ESP32WROOM32_CRYPT_AES) 02916 02917 /* Allow direct access to one block encrypt */ 02918 void wc_AesEncryptDirect(Aes* aes, byte* out, const byte* in) 02919 { 02920 wc_AesEncrypt(aes, in, out); 02921 } 02922 #ifdef HAVE_AES_DECRYPT 02923 /* Allow direct access to one block decrypt */ 02924 void wc_AesDecryptDirect(Aes* aes, byte* out, const byte* in) 02925 { 02926 wc_AesDecrypt(aes, in, out); 02927 } 02928 #endif /* HAVE_AES_DECRYPT */ 02929 #else 02930 /* Allow direct access to one block encrypt */ 02931 void wc_AesEncryptDirect(Aes* aes, byte* out, const byte* in) 02932 { 02933 wc_AesEncrypt(aes, in, out); 02934 } 02935 #ifdef HAVE_AES_DECRYPT 02936 /* Allow direct access to one block decrypt */ 02937 void wc_AesDecryptDirect(Aes* aes, byte* out, const byte* in) 02938 { 02939 wc_AesDecrypt(aes, in, out); 02940 } 02941 #endif /* HAVE_AES_DECRYPT */ 02942 #endif /* AES direct block */ 02943 #endif /* WOLFSSL_AES_DIRECT */ 02944 02945 02946 /* AES-CBC */ 02947 #ifdef HAVE_AES_CBC 02948 #if defined(STM32_CRYPTO) 02949 02950 #ifdef WOLFSSL_STM32_CUBEMX 02951 int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 02952 { 02953 int ret = 0; 02954 word32 blocks = (sz / AES_BLOCK_SIZE); 02955 CRYP_HandleTypeDef hcryp; 02956 02957 ret = wc_Stm32_Aes_Init(aes, &hcryp); 02958 if (ret != 0) 02959 return ret; 02960 02961 ret = wolfSSL_CryptHwMutexLock(); 02962 if (ret != 0) { 02963 return ret; 02964 } 02965 02966 #ifdef STM32_CRYPTO_AES_ONLY 02967 hcryp.Init.OperatingMode = CRYP_ALGOMODE_ENCRYPT; 02968 hcryp.Init.ChainingMode = CRYP_CHAINMODE_AES_CBC; 02969 hcryp.Init.KeyWriteFlag = CRYP_KEY_WRITE_ENABLE; 02970 #elif defined(STM32_HAL_V2) 02971 hcryp.Init.Algorithm = CRYP_AES_CBC; 02972 ByteReverseWords(aes->reg, aes->reg, AES_BLOCK_SIZE); 02973 #endif 02974 hcryp.Init.pInitVect = (STM_CRYPT_TYPE*)aes->reg; 02975 HAL_CRYP_Init(&hcryp); 02976 02977 while (blocks--) { 02978 #ifdef STM32_CRYPTO_AES_ONLY 02979 ret = HAL_CRYPEx_AES(&hcryp, (uint8_t*)in, AES_BLOCK_SIZE, 02980 out, STM32_HAL_TIMEOUT); 02981 #elif defined(STM32_HAL_V2) 02982 ret = HAL_CRYP_Encrypt(&hcryp, (uint32_t*)in, AES_BLOCK_SIZE, 02983 (uint32_t*)out, STM32_HAL_TIMEOUT); 02984 #else 02985 ret = HAL_CRYP_AESCBC_Encrypt(&hcryp, (uint8_t*)in, AES_BLOCK_SIZE, 02986 out, STM32_HAL_TIMEOUT); 02987 #endif 02988 if (ret != HAL_OK) { 02989 ret = WC_TIMEOUT_E; 02990 break; 02991 } 02992 02993 /* store iv for next call */ 02994 XMEMCPY(aes->reg, out + sz - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 02995 02996 sz -= AES_BLOCK_SIZE; 02997 in += AES_BLOCK_SIZE; 02998 out += AES_BLOCK_SIZE; 02999 } 03000 03001 HAL_CRYP_DeInit(&hcryp); 03002 03003 wolfSSL_CryptHwMutexUnLock(); 03004 03005 return ret; 03006 } 03007 #ifdef HAVE_AES_DECRYPT 03008 int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03009 { 03010 int ret = 0; 03011 word32 blocks = (sz / AES_BLOCK_SIZE); 03012 CRYP_HandleTypeDef hcryp; 03013 03014 ret = wc_Stm32_Aes_Init(aes, &hcryp); 03015 if (ret != 0) 03016 return ret; 03017 03018 ret = wolfSSL_CryptHwMutexLock(); 03019 if (ret != 0) { 03020 return ret; 03021 } 03022 03023 /* if input and output same will overwrite input iv */ 03024 XMEMCPY(aes->tmp, in + sz - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 03025 03026 #ifdef STM32_CRYPTO_AES_ONLY 03027 hcryp.Init.OperatingMode = CRYP_ALGOMODE_KEYDERIVATION_DECRYPT; 03028 hcryp.Init.ChainingMode = CRYP_CHAINMODE_AES_CBC; 03029 hcryp.Init.KeyWriteFlag = CRYP_KEY_WRITE_ENABLE; 03030 #elif defined(STM32_HAL_V2) 03031 hcryp.Init.Algorithm = CRYP_AES_CBC; 03032 ByteReverseWords(aes->reg, aes->reg, AES_BLOCK_SIZE); 03033 #endif 03034 03035 hcryp.Init.pInitVect = (STM_CRYPT_TYPE*)aes->reg; 03036 HAL_CRYP_Init(&hcryp); 03037 03038 while (blocks--) { 03039 #ifdef STM32_CRYPTO_AES_ONLY 03040 ret = HAL_CRYPEx_AES(&hcryp, (uint8_t*)in, AES_BLOCK_SIZE, 03041 out, STM32_HAL_TIMEOUT); 03042 #elif defined(STM32_HAL_V2) 03043 ret = HAL_CRYP_Decrypt(&hcryp, (uint32_t*)in, AES_BLOCK_SIZE, 03044 (uint32_t*)out, STM32_HAL_TIMEOUT); 03045 #else 03046 ret = HAL_CRYP_AESCBC_Decrypt(&hcryp, (uint8_t*)in, AES_BLOCK_SIZE, 03047 out, STM32_HAL_TIMEOUT); 03048 #endif 03049 if (ret != HAL_OK) { 03050 ret = WC_TIMEOUT_E; 03051 break; 03052 } 03053 03054 /* store iv for next call */ 03055 XMEMCPY(aes->reg, aes->tmp, AES_BLOCK_SIZE); 03056 03057 in += AES_BLOCK_SIZE; 03058 out += AES_BLOCK_SIZE; 03059 } 03060 03061 HAL_CRYP_DeInit(&hcryp); 03062 wolfSSL_CryptHwMutexUnLock(); 03063 03064 return ret; 03065 } 03066 #endif /* HAVE_AES_DECRYPT */ 03067 03068 #else /* STD_PERI_LIB */ 03069 int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03070 { 03071 int ret; 03072 word32 *iv; 03073 word32 blocks = (sz / AES_BLOCK_SIZE); 03074 CRYP_InitTypeDef cryptInit; 03075 CRYP_KeyInitTypeDef keyInit; 03076 CRYP_IVInitTypeDef ivInit; 03077 03078 ret = wc_Stm32_Aes_Init(aes, &cryptInit, &keyInit); 03079 if (ret != 0) 03080 return ret; 03081 03082 ret = wolfSSL_CryptHwMutexLock(); 03083 if (ret != 0) { 03084 return ret; 03085 } 03086 03087 /* reset registers to their default values */ 03088 CRYP_DeInit(); 03089 03090 /* set key */ 03091 CRYP_KeyInit(&keyInit); 03092 03093 /* set iv */ 03094 iv = aes->reg; 03095 CRYP_IVStructInit(&ivInit); 03096 ByteReverseWords(iv, iv, AES_BLOCK_SIZE); 03097 ivInit.CRYP_IV0Left = iv[0]; 03098 ivInit.CRYP_IV0Right = iv[1]; 03099 ivInit.CRYP_IV1Left = iv[2]; 03100 ivInit.CRYP_IV1Right = iv[3]; 03101 CRYP_IVInit(&ivInit); 03102 03103 /* set direction and mode */ 03104 cryptInit.CRYP_AlgoDir = CRYP_AlgoDir_Encrypt; 03105 cryptInit.CRYP_AlgoMode = CRYP_AlgoMode_AES_CBC; 03106 CRYP_Init(&cryptInit); 03107 03108 /* enable crypto processor */ 03109 CRYP_Cmd(ENABLE); 03110 03111 while (blocks--) { 03112 /* flush IN/OUT FIFOs */ 03113 CRYP_FIFOFlush(); 03114 03115 CRYP_DataIn(*(uint32_t*)&in[0]); 03116 CRYP_DataIn(*(uint32_t*)&in[4]); 03117 CRYP_DataIn(*(uint32_t*)&in[8]); 03118 CRYP_DataIn(*(uint32_t*)&in[12]); 03119 03120 /* wait until the complete message has been processed */ 03121 while (CRYP_GetFlagStatus(CRYP_FLAG_BUSY) != RESET) {} 03122 03123 *(uint32_t*)&out[0] = CRYP_DataOut(); 03124 *(uint32_t*)&out[4] = CRYP_DataOut(); 03125 *(uint32_t*)&out[8] = CRYP_DataOut(); 03126 *(uint32_t*)&out[12] = CRYP_DataOut(); 03127 03128 /* store iv for next call */ 03129 XMEMCPY(aes->reg, out + sz - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 03130 03131 sz -= AES_BLOCK_SIZE; 03132 in += AES_BLOCK_SIZE; 03133 out += AES_BLOCK_SIZE; 03134 } 03135 03136 /* disable crypto processor */ 03137 CRYP_Cmd(DISABLE); 03138 wolfSSL_CryptHwMutexUnLock(); 03139 03140 return ret; 03141 } 03142 03143 #ifdef HAVE_AES_DECRYPT 03144 int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03145 { 03146 int ret; 03147 word32 *iv; 03148 word32 blocks = (sz / AES_BLOCK_SIZE); 03149 CRYP_InitTypeDef cryptInit; 03150 CRYP_KeyInitTypeDef keyInit; 03151 CRYP_IVInitTypeDef ivInit; 03152 03153 ret = wc_Stm32_Aes_Init(aes, &cryptInit, &keyInit); 03154 if (ret != 0) 03155 return ret; 03156 03157 ret = wolfSSL_CryptHwMutexLock(); 03158 if (ret != 0) { 03159 return ret; 03160 } 03161 03162 /* if input and output same will overwrite input iv */ 03163 XMEMCPY(aes->tmp, in + sz - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 03164 03165 /* reset registers to their default values */ 03166 CRYP_DeInit(); 03167 03168 /* set direction and key */ 03169 CRYP_KeyInit(&keyInit); 03170 cryptInit.CRYP_AlgoDir = CRYP_AlgoDir_Decrypt; 03171 cryptInit.CRYP_AlgoMode = CRYP_AlgoMode_AES_Key; 03172 CRYP_Init(&cryptInit); 03173 03174 /* enable crypto processor */ 03175 CRYP_Cmd(ENABLE); 03176 03177 /* wait until key has been prepared */ 03178 while (CRYP_GetFlagStatus(CRYP_FLAG_BUSY) != RESET) {} 03179 03180 /* set direction and mode */ 03181 cryptInit.CRYP_AlgoDir = CRYP_AlgoDir_Decrypt; 03182 cryptInit.CRYP_AlgoMode = CRYP_AlgoMode_AES_CBC; 03183 CRYP_Init(&cryptInit); 03184 03185 /* set iv */ 03186 iv = aes->reg; 03187 CRYP_IVStructInit(&ivInit); 03188 ByteReverseWords(iv, iv, AES_BLOCK_SIZE); 03189 ivInit.CRYP_IV0Left = iv[0]; 03190 ivInit.CRYP_IV0Right = iv[1]; 03191 ivInit.CRYP_IV1Left = iv[2]; 03192 ivInit.CRYP_IV1Right = iv[3]; 03193 CRYP_IVInit(&ivInit); 03194 03195 /* enable crypto processor */ 03196 CRYP_Cmd(ENABLE); 03197 03198 while (blocks--) { 03199 /* flush IN/OUT FIFOs */ 03200 CRYP_FIFOFlush(); 03201 03202 CRYP_DataIn(*(uint32_t*)&in[0]); 03203 CRYP_DataIn(*(uint32_t*)&in[4]); 03204 CRYP_DataIn(*(uint32_t*)&in[8]); 03205 CRYP_DataIn(*(uint32_t*)&in[12]); 03206 03207 /* wait until the complete message has been processed */ 03208 while (CRYP_GetFlagStatus(CRYP_FLAG_BUSY) != RESET) {} 03209 03210 *(uint32_t*)&out[0] = CRYP_DataOut(); 03211 *(uint32_t*)&out[4] = CRYP_DataOut(); 03212 *(uint32_t*)&out[8] = CRYP_DataOut(); 03213 *(uint32_t*)&out[12] = CRYP_DataOut(); 03214 03215 /* store iv for next call */ 03216 XMEMCPY(aes->reg, aes->tmp, AES_BLOCK_SIZE); 03217 03218 in += AES_BLOCK_SIZE; 03219 out += AES_BLOCK_SIZE; 03220 } 03221 03222 /* disable crypto processor */ 03223 CRYP_Cmd(DISABLE); 03224 wolfSSL_CryptHwMutexUnLock(); 03225 03226 return ret; 03227 } 03228 #endif /* HAVE_AES_DECRYPT */ 03229 #endif /* WOLFSSL_STM32_CUBEMX */ 03230 03231 #elif defined(HAVE_COLDFIRE_SEC) 03232 static int wc_AesCbcCrypt(Aes* aes, byte* po, const byte* pi, word32 sz, 03233 word32 descHeader) 03234 { 03235 #ifdef DEBUG_WOLFSSL 03236 int i; int stat1, stat2; int ret; 03237 #endif 03238 03239 int size; 03240 volatile int v; 03241 03242 if ((pi == NULL) || (po == NULL)) 03243 return BAD_FUNC_ARG; /*wrong pointer*/ 03244 03245 wc_LockMutex(&Mutex_AesSEC); 03246 03247 /* Set descriptor for SEC */ 03248 secDesc->length1 = 0x0; 03249 secDesc->pointer1 = NULL; 03250 03251 secDesc->length2 = AES_BLOCK_SIZE; 03252 secDesc->pointer2 = (byte *)secReg; /* Initial Vector */ 03253 03254 switch(aes->rounds) { 03255 case 10: secDesc->length3 = 16; break; 03256 case 12: secDesc->length3 = 24; break; 03257 case 14: secDesc->length3 = 32; break; 03258 } 03259 XMEMCPY(secKey, aes->key, secDesc->length3); 03260 03261 secDesc->pointer3 = (byte *)secKey; 03262 secDesc->pointer4 = AESBuffIn; 03263 secDesc->pointer5 = AESBuffOut; 03264 secDesc->length6 = 0x0; 03265 secDesc->pointer6 = NULL; 03266 secDesc->length7 = 0x0; 03267 secDesc->pointer7 = NULL; 03268 secDesc->nextDescriptorPtr = NULL; 03269 03270 while (sz) { 03271 secDesc->header = descHeader; 03272 XMEMCPY(secReg, aes->reg, AES_BLOCK_SIZE); 03273 if ((sz % AES_BUFFER_SIZE) == sz) { 03274 size = sz; 03275 sz = 0; 03276 } else { 03277 size = AES_BUFFER_SIZE; 03278 sz -= AES_BUFFER_SIZE; 03279 } 03280 secDesc->length4 = size; 03281 secDesc->length5 = size; 03282 03283 XMEMCPY(AESBuffIn, pi, size); 03284 if(descHeader == SEC_DESC_AES_CBC_DECRYPT) { 03285 XMEMCPY((void*)aes->tmp, (void*)&(pi[size-AES_BLOCK_SIZE]), 03286 AES_BLOCK_SIZE); 03287 } 03288 03289 /* Point SEC to the location of the descriptor */ 03290 MCF_SEC_FR0 = (uint32)secDesc; 03291 /* Initialize SEC and wait for encryption to complete */ 03292 MCF_SEC_CCCR0 = 0x0000001a; 03293 /* poll SISR to determine when channel is complete */ 03294 v=0; 03295 03296 while ((secDesc->header>> 24) != 0xff) v++; 03297 03298 #ifdef DEBUG_WOLFSSL 03299 ret = MCF_SEC_SISRH; 03300 stat1 = MCF_SEC_AESSR; 03301 stat2 = MCF_SEC_AESISR; 03302 if (ret & 0xe0000000) { 03303 db_printf("Aes_Cbc(i=%d):ISRH=%08x, AESSR=%08x, " 03304 "AESISR=%08x\n", i, ret, stat1, stat2); 03305 } 03306 #endif 03307 03308 XMEMCPY(po, AESBuffOut, size); 03309 03310 if (descHeader == SEC_DESC_AES_CBC_ENCRYPT) { 03311 XMEMCPY((void*)aes->reg, (void*)&(po[size-AES_BLOCK_SIZE]), 03312 AES_BLOCK_SIZE); 03313 } else { 03314 XMEMCPY((void*)aes->reg, (void*)aes->tmp, AES_BLOCK_SIZE); 03315 } 03316 03317 pi += size; 03318 po += size; 03319 } 03320 03321 wc_UnLockMutex(&Mutex_AesSEC); 03322 return 0; 03323 } 03324 03325 int wc_AesCbcEncrypt(Aes* aes, byte* po, const byte* pi, word32 sz) 03326 { 03327 return (wc_AesCbcCrypt(aes, po, pi, sz, SEC_DESC_AES_CBC_ENCRYPT)); 03328 } 03329 03330 #ifdef HAVE_AES_DECRYPT 03331 int wc_AesCbcDecrypt(Aes* aes, byte* po, const byte* pi, word32 sz) 03332 { 03333 return (wc_AesCbcCrypt(aes, po, pi, sz, SEC_DESC_AES_CBC_DECRYPT)); 03334 } 03335 #endif /* HAVE_AES_DECRYPT */ 03336 03337 #elif defined(FREESCALE_LTC) 03338 int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03339 { 03340 uint32_t keySize; 03341 status_t status; 03342 byte *iv, *enc_key; 03343 word32 blocks = (sz / AES_BLOCK_SIZE); 03344 03345 iv = (byte*)aes->reg; 03346 enc_key = (byte*)aes->key; 03347 03348 status = wc_AesGetKeySize(aes, &keySize); 03349 if (status != 0) { 03350 return status; 03351 } 03352 03353 status = LTC_AES_EncryptCbc(LTC_BASE, in, out, blocks * AES_BLOCK_SIZE, 03354 iv, enc_key, keySize); 03355 03356 /* store iv for next call */ 03357 if (status == kStatus_Success) { 03358 XMEMCPY(iv, out + sz - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 03359 } 03360 03361 return (status == kStatus_Success) ? 0 : -1; 03362 } 03363 03364 #ifdef HAVE_AES_DECRYPT 03365 int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03366 { 03367 uint32_t keySize; 03368 status_t status; 03369 byte* iv, *dec_key; 03370 word32 blocks = (sz / AES_BLOCK_SIZE); 03371 byte temp_block[AES_BLOCK_SIZE]; 03372 03373 iv = (byte*)aes->reg; 03374 dec_key = (byte*)aes->key; 03375 03376 status = wc_AesGetKeySize(aes, &keySize); 03377 if (status != 0) { 03378 return status; 03379 } 03380 03381 /* get IV for next call */ 03382 XMEMCPY(temp_block, in + sz - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 03383 03384 status = LTC_AES_DecryptCbc(LTC_BASE, in, out, blocks * AES_BLOCK_SIZE, 03385 iv, dec_key, keySize, kLTC_EncryptKey); 03386 03387 /* store IV for next call */ 03388 if (status == kStatus_Success) { 03389 XMEMCPY(iv, temp_block, AES_BLOCK_SIZE); 03390 } 03391 03392 return (status == kStatus_Success) ? 0 : -1; 03393 } 03394 #endif /* HAVE_AES_DECRYPT */ 03395 03396 #elif defined(FREESCALE_MMCAU) 03397 int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03398 { 03399 int i; 03400 int offset = 0; 03401 word32 blocks = (sz / AES_BLOCK_SIZE); 03402 byte *iv; 03403 byte temp_block[AES_BLOCK_SIZE]; 03404 03405 iv = (byte*)aes->reg; 03406 03407 while (blocks--) { 03408 XMEMCPY(temp_block, in + offset, AES_BLOCK_SIZE); 03409 03410 /* XOR block with IV for CBC */ 03411 for (i = 0; i < AES_BLOCK_SIZE; i++) 03412 temp_block[i] ^= iv[i]; 03413 03414 wc_AesEncrypt(aes, temp_block, out + offset); 03415 03416 offset += AES_BLOCK_SIZE; 03417 03418 /* store IV for next block */ 03419 XMEMCPY(iv, out + offset - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 03420 } 03421 03422 return 0; 03423 } 03424 #ifdef HAVE_AES_DECRYPT 03425 int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03426 { 03427 int i; 03428 int offset = 0; 03429 word32 blocks = (sz / AES_BLOCK_SIZE); 03430 byte* iv; 03431 byte temp_block[AES_BLOCK_SIZE]; 03432 03433 iv = (byte*)aes->reg; 03434 03435 while (blocks--) { 03436 XMEMCPY(temp_block, in + offset, AES_BLOCK_SIZE); 03437 03438 wc_AesDecrypt(aes, in + offset, out + offset); 03439 03440 /* XOR block with IV for CBC */ 03441 for (i = 0; i < AES_BLOCK_SIZE; i++) 03442 (out + offset)[i] ^= iv[i]; 03443 03444 /* store IV for next block */ 03445 XMEMCPY(iv, temp_block, AES_BLOCK_SIZE); 03446 03447 offset += AES_BLOCK_SIZE; 03448 } 03449 03450 return 0; 03451 } 03452 #endif /* HAVE_AES_DECRYPT */ 03453 03454 #elif defined(WOLFSSL_PIC32MZ_CRYPT) 03455 03456 int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03457 { 03458 int ret; 03459 03460 /* hardware fails on input that is not a multiple of AES block size */ 03461 if (sz % AES_BLOCK_SIZE != 0) { 03462 return BAD_FUNC_ARG; 03463 } 03464 03465 ret = wc_Pic32AesCrypt( 03466 aes->key, aes->keylen, aes->reg, AES_BLOCK_SIZE, 03467 out, in, sz, PIC32_ENCRYPTION, 03468 PIC32_ALGO_AES, PIC32_CRYPTOALGO_RCBC); 03469 03470 /* store iv for next call */ 03471 if (ret == 0) { 03472 XMEMCPY(aes->reg, out + sz - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 03473 } 03474 03475 return ret; 03476 } 03477 #ifdef HAVE_AES_DECRYPT 03478 int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03479 { 03480 int ret; 03481 byte scratch[AES_BLOCK_SIZE]; 03482 03483 /* hardware fails on input that is not a multiple of AES block size */ 03484 if (sz % AES_BLOCK_SIZE != 0) { 03485 return BAD_FUNC_ARG; 03486 } 03487 XMEMCPY(scratch, in + sz - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 03488 03489 ret = wc_Pic32AesCrypt( 03490 aes->key, aes->keylen, aes->reg, AES_BLOCK_SIZE, 03491 out, in, sz, PIC32_DECRYPTION, 03492 PIC32_ALGO_AES, PIC32_CRYPTOALGO_RCBC); 03493 03494 /* store iv for next call */ 03495 if (ret == 0) { 03496 XMEMCPY((byte*)aes->reg, scratch, AES_BLOCK_SIZE); 03497 } 03498 03499 return ret; 03500 } 03501 #endif /* HAVE_AES_DECRYPT */ 03502 #elif defined(WOLFSSL_ESP32WROOM32_CRYPT) && \ 03503 !defined(NO_WOLFSSL_ESP32WROOM32_CRYPT_AES) 03504 03505 int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03506 { 03507 return wc_esp32AesCbcEncrypt(aes, out, in, sz); 03508 } 03509 int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03510 { 03511 return wc_esp32AesCbcDecrypt(aes, out, in, sz); 03512 } 03513 #elif defined(WOLFSSL_CRYPTOCELL) && defined(WOLFSSL_CRYPTOCELL_AES) 03514 int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03515 { 03516 return SaSi_AesBlock(&aes->ctx.user_ctx, (uint8_t* )in, sz, out); 03517 } 03518 int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03519 { 03520 return SaSi_AesBlock(&aes->ctx.user_ctx, (uint8_t* )in, sz, out); 03521 } 03522 #elif defined(WOLFSSL_IMX6_CAAM) && !defined(NO_IMX6_CAAM_AES) 03523 /* implemented in wolfcrypt/src/port/caam/caam_aes.c */ 03524 03525 #elif defined(WOLFSSL_AFALG) 03526 /* implemented in wolfcrypt/src/port/af_alg/afalg_aes.c */ 03527 03528 #elif defined(WOLFSSL_DEVCRYPTO_CBC) 03529 /* implemented in wolfcrypt/src/port/devcrypt/devcrypto_aes.c */ 03530 03531 #else 03532 03533 /* Software AES - CBC Encrypt */ 03534 int wc_AesCbcEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03535 { 03536 word32 blocks = (sz / AES_BLOCK_SIZE); 03537 03538 if (aes == NULL || out == NULL || in == NULL) { 03539 return BAD_FUNC_ARG; 03540 } 03541 03542 #ifdef WOLF_CRYPTO_CB 03543 if (aes->devId != INVALID_DEVID) { 03544 int ret = wc_CryptoCb_AesCbcEncrypt(aes, out, in, sz); 03545 if (ret != CRYPTOCB_UNAVAILABLE) 03546 return ret; 03547 /* fall-through when unavailable */ 03548 } 03549 #endif 03550 #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_AES) 03551 /* if async and byte count above threshold */ 03552 if (aes->asyncDev.marker == WOLFSSL_ASYNC_MARKER_AES && 03553 sz >= WC_ASYNC_THRESH_AES_CBC) { 03554 #if defined(HAVE_CAVIUM) 03555 return NitroxAesCbcEncrypt(aes, out, in, sz); 03556 #elif defined(HAVE_INTEL_QA) 03557 return IntelQaSymAesCbcEncrypt(&aes->asyncDev, out, in, sz, 03558 (const byte*)aes->devKey, aes->keylen, 03559 (byte*)aes->reg, AES_BLOCK_SIZE); 03560 #else /* WOLFSSL_ASYNC_CRYPT_TEST */ 03561 if (wc_AsyncTestInit(&aes->asyncDev, ASYNC_TEST_AES_CBC_ENCRYPT)) { 03562 WC_ASYNC_TEST* testDev = &aes->asyncDev.test; 03563 testDev->aes.aes = aes; 03564 testDev->aes.out = out; 03565 testDev->aes.in = in; 03566 testDev->aes.sz = sz; 03567 return WC_PENDING_E; 03568 } 03569 #endif 03570 } 03571 #endif /* WOLFSSL_ASYNC_CRYPT */ 03572 03573 #ifdef WOLFSSL_AESNI 03574 if (haveAESNI) { 03575 #ifdef DEBUG_AESNI 03576 printf("about to aes cbc encrypt\n"); 03577 printf("in = %p\n", in); 03578 printf("out = %p\n", out); 03579 printf("aes->key = %p\n", aes->key); 03580 printf("aes->reg = %p\n", aes->reg); 03581 printf("aes->rounds = %d\n", aes->rounds); 03582 printf("sz = %d\n", sz); 03583 #endif 03584 03585 /* check alignment, decrypt doesn't need alignment */ 03586 if ((wolfssl_word)in % AESNI_ALIGN) { 03587 #ifndef NO_WOLFSSL_ALLOC_ALIGN 03588 byte* tmp = (byte*)XMALLOC(sz + AES_BLOCK_SIZE + AESNI_ALIGN, 03589 aes->heap, DYNAMIC_TYPE_TMP_BUFFER); 03590 byte* tmp_align; 03591 if (tmp == NULL) return MEMORY_E; 03592 03593 tmp_align = tmp + (AESNI_ALIGN - ((size_t)tmp % AESNI_ALIGN)); 03594 XMEMCPY(tmp_align, in, sz); 03595 AES_CBC_encrypt(tmp_align, tmp_align, (byte*)aes->reg, sz, 03596 (byte*)aes->key, aes->rounds); 03597 /* store iv for next call */ 03598 XMEMCPY(aes->reg, tmp_align + sz - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 03599 03600 XMEMCPY(out, tmp_align, sz); 03601 XFREE(tmp, aes->heap, DYNAMIC_TYPE_TMP_BUFFER); 03602 return 0; 03603 #else 03604 WOLFSSL_MSG("AES-CBC encrypt with bad alignment"); 03605 return BAD_ALIGN_E; 03606 #endif 03607 } 03608 03609 AES_CBC_encrypt(in, out, (byte*)aes->reg, sz, (byte*)aes->key, 03610 aes->rounds); 03611 /* store iv for next call */ 03612 XMEMCPY(aes->reg, out + sz - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 03613 03614 return 0; 03615 } 03616 #endif 03617 03618 while (blocks--) { 03619 xorbuf((byte*)aes->reg, in, AES_BLOCK_SIZE); 03620 wc_AesEncrypt(aes, (byte*)aes->reg, (byte*)aes->reg); 03621 XMEMCPY(out, aes->reg, AES_BLOCK_SIZE); 03622 03623 out += AES_BLOCK_SIZE; 03624 in += AES_BLOCK_SIZE; 03625 } 03626 03627 return 0; 03628 } 03629 03630 #ifdef HAVE_AES_DECRYPT 03631 /* Software AES - CBC Decrypt */ 03632 int wc_AesCbcDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03633 { 03634 word32 blocks; 03635 03636 if (aes == NULL || out == NULL || in == NULL 03637 || sz % AES_BLOCK_SIZE != 0) { 03638 return BAD_FUNC_ARG; 03639 } 03640 03641 #ifdef WOLF_CRYPTO_CB 03642 if (aes->devId != INVALID_DEVID) { 03643 int ret = wc_CryptoCb_AesCbcDecrypt(aes, out, in, sz); 03644 if (ret != CRYPTOCB_UNAVAILABLE) 03645 return ret; 03646 /* fall-through when unavailable */ 03647 } 03648 #endif 03649 #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_AES) 03650 /* if async and byte count above threshold */ 03651 if (aes->asyncDev.marker == WOLFSSL_ASYNC_MARKER_AES && 03652 sz >= WC_ASYNC_THRESH_AES_CBC) { 03653 #if defined(HAVE_CAVIUM) 03654 return NitroxAesCbcDecrypt(aes, out, in, sz); 03655 #elif defined(HAVE_INTEL_QA) 03656 return IntelQaSymAesCbcDecrypt(&aes->asyncDev, out, in, sz, 03657 (const byte*)aes->devKey, aes->keylen, 03658 (byte*)aes->reg, AES_BLOCK_SIZE); 03659 #else /* WOLFSSL_ASYNC_CRYPT_TEST */ 03660 if (wc_AsyncTestInit(&aes->asyncDev, ASYNC_TEST_AES_CBC_DECRYPT)) { 03661 WC_ASYNC_TEST* testDev = &aes->asyncDev.test; 03662 testDev->aes.aes = aes; 03663 testDev->aes.out = out; 03664 testDev->aes.in = in; 03665 testDev->aes.sz = sz; 03666 return WC_PENDING_E; 03667 } 03668 #endif 03669 } 03670 #endif 03671 03672 #ifdef WOLFSSL_AESNI 03673 if (haveAESNI) { 03674 #ifdef DEBUG_AESNI 03675 printf("about to aes cbc decrypt\n"); 03676 printf("in = %p\n", in); 03677 printf("out = %p\n", out); 03678 printf("aes->key = %p\n", aes->key); 03679 printf("aes->reg = %p\n", aes->reg); 03680 printf("aes->rounds = %d\n", aes->rounds); 03681 printf("sz = %d\n", sz); 03682 #endif 03683 03684 /* if input and output same will overwrite input iv */ 03685 XMEMCPY(aes->tmp, in + sz - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 03686 #if defined(WOLFSSL_AESNI_BY4) 03687 AES_CBC_decrypt_by4(in, out, (byte*)aes->reg, sz, (byte*)aes->key, 03688 aes->rounds); 03689 #elif defined(WOLFSSL_AESNI_BY6) 03690 AES_CBC_decrypt_by6(in, out, (byte*)aes->reg, sz, (byte*)aes->key, 03691 aes->rounds); 03692 #else /* WOLFSSL_AESNI_BYx */ 03693 AES_CBC_decrypt_by8(in, out, (byte*)aes->reg, sz, (byte*)aes->key, 03694 aes->rounds); 03695 #endif /* WOLFSSL_AESNI_BYx */ 03696 /* store iv for next call */ 03697 XMEMCPY(aes->reg, aes->tmp, AES_BLOCK_SIZE); 03698 return 0; 03699 } 03700 #endif 03701 03702 blocks = sz / AES_BLOCK_SIZE; 03703 while (blocks--) { 03704 XMEMCPY(aes->tmp, in, AES_BLOCK_SIZE); 03705 wc_AesDecrypt(aes, (byte*)aes->tmp, out); 03706 xorbuf(out, (byte*)aes->reg, AES_BLOCK_SIZE); 03707 /* store iv for next call */ 03708 XMEMCPY(aes->reg, aes->tmp, AES_BLOCK_SIZE); 03709 03710 out += AES_BLOCK_SIZE; 03711 in += AES_BLOCK_SIZE; 03712 } 03713 03714 return 0; 03715 } 03716 #endif 03717 03718 #endif /* AES-CBC block */ 03719 #endif /* HAVE_AES_CBC */ 03720 03721 /* AES-CTR */ 03722 #if defined(WOLFSSL_AES_COUNTER) 03723 03724 #ifdef STM32_CRYPTO 03725 #define NEED_AES_CTR_SOFT 03726 #define XTRANSFORM_AESCTRBLOCK wc_AesCtrEncryptBlock 03727 03728 int wc_AesCtrEncryptBlock(Aes* aes, byte* out, const byte* in) 03729 { 03730 int ret = 0; 03731 #ifdef WOLFSSL_STM32_CUBEMX 03732 CRYP_HandleTypeDef hcryp; 03733 #ifdef STM32_HAL_V2 03734 word32 iv[AES_BLOCK_SIZE/sizeof(word32)]; 03735 #endif 03736 #else 03737 word32 *iv; 03738 CRYP_InitTypeDef cryptInit; 03739 CRYP_KeyInitTypeDef keyInit; 03740 CRYP_IVInitTypeDef ivInit; 03741 #endif 03742 03743 ret = wolfSSL_CryptHwMutexLock(); 03744 if (ret != 0) { 03745 return ret; 03746 } 03747 03748 #ifdef WOLFSSL_STM32_CUBEMX 03749 ret = wc_Stm32_Aes_Init(aes, &hcryp); 03750 if (ret != 0) { 03751 wolfSSL_CryptHwMutexUnLock(); 03752 return ret; 03753 } 03754 03755 #ifdef STM32_CRYPTO_AES_ONLY 03756 hcryp.Init.OperatingMode = CRYP_ALGOMODE_ENCRYPT; 03757 hcryp.Init.ChainingMode = CRYP_CHAINMODE_AES_CTR; 03758 hcryp.Init.KeyWriteFlag = CRYP_KEY_WRITE_ENABLE; 03759 hcryp.Init.pInitVect = (STM_CRYPT_TYPE*)aes->reg; 03760 #elif defined(STM32_HAL_V2) 03761 hcryp.Init.Algorithm = CRYP_AES_CTR; 03762 ByteReverseWords(iv, aes->reg, AES_BLOCK_SIZE); 03763 hcryp.Init.pInitVect = (STM_CRYPT_TYPE*)iv; 03764 #else 03765 hcryp.Init.pInitVect = (STM_CRYPT_TYPE*)aes->reg; 03766 #endif 03767 HAL_CRYP_Init(&hcryp); 03768 03769 #ifdef STM32_CRYPTO_AES_ONLY 03770 ret = HAL_CRYPEx_AES(&hcryp, (byte*)in, AES_BLOCK_SIZE, 03771 out, STM32_HAL_TIMEOUT); 03772 #elif defined(STM32_HAL_V2) 03773 ret = HAL_CRYP_Encrypt(&hcryp, (uint32_t*)in, AES_BLOCK_SIZE, 03774 (uint32_t*)out, STM32_HAL_TIMEOUT); 03775 #else 03776 ret = HAL_CRYP_AESCTR_Encrypt(&hcryp, (byte*)in, AES_BLOCK_SIZE, 03777 out, STM32_HAL_TIMEOUT); 03778 #endif 03779 if (ret != HAL_OK) { 03780 ret = WC_TIMEOUT_E; 03781 } 03782 HAL_CRYP_DeInit(&hcryp); 03783 03784 #else /* STD_PERI_LIB */ 03785 ret = wc_Stm32_Aes_Init(aes, &cryptInit, &keyInit); 03786 if (ret != 0) { 03787 wolfSSL_CryptHwMutexUnLock(); 03788 return ret; 03789 } 03790 03791 /* reset registers to their default values */ 03792 CRYP_DeInit(); 03793 03794 /* set key */ 03795 CRYP_KeyInit(&keyInit); 03796 03797 /* set iv */ 03798 iv = aes->reg; 03799 CRYP_IVStructInit(&ivInit); 03800 ivInit.CRYP_IV0Left = ByteReverseWord32(iv[0]); 03801 ivInit.CRYP_IV0Right = ByteReverseWord32(iv[1]); 03802 ivInit.CRYP_IV1Left = ByteReverseWord32(iv[2]); 03803 ivInit.CRYP_IV1Right = ByteReverseWord32(iv[3]); 03804 CRYP_IVInit(&ivInit); 03805 03806 /* set direction and mode */ 03807 cryptInit.CRYP_AlgoDir = CRYP_AlgoDir_Encrypt; 03808 cryptInit.CRYP_AlgoMode = CRYP_AlgoMode_AES_CTR; 03809 CRYP_Init(&cryptInit); 03810 03811 /* enable crypto processor */ 03812 CRYP_Cmd(ENABLE); 03813 03814 /* flush IN/OUT FIFOs */ 03815 CRYP_FIFOFlush(); 03816 03817 CRYP_DataIn(*(uint32_t*)&in[0]); 03818 CRYP_DataIn(*(uint32_t*)&in[4]); 03819 CRYP_DataIn(*(uint32_t*)&in[8]); 03820 CRYP_DataIn(*(uint32_t*)&in[12]); 03821 03822 /* wait until the complete message has been processed */ 03823 while (CRYP_GetFlagStatus(CRYP_FLAG_BUSY) != RESET) {} 03824 03825 *(uint32_t*)&out[0] = CRYP_DataOut(); 03826 *(uint32_t*)&out[4] = CRYP_DataOut(); 03827 *(uint32_t*)&out[8] = CRYP_DataOut(); 03828 *(uint32_t*)&out[12] = CRYP_DataOut(); 03829 03830 /* disable crypto processor */ 03831 CRYP_Cmd(DISABLE); 03832 03833 #endif /* WOLFSSL_STM32_CUBEMX */ 03834 03835 wolfSSL_CryptHwMutexUnLock(); 03836 return ret; 03837 } 03838 03839 03840 #elif defined(WOLFSSL_PIC32MZ_CRYPT) 03841 03842 #define NEED_AES_CTR_SOFT 03843 #define XTRANSFORM_AESCTRBLOCK wc_AesCtrEncryptBlock 03844 03845 int wc_AesCtrEncryptBlock(Aes* aes, byte* out, const byte* in) 03846 { 03847 word32 tmpIv[AES_BLOCK_SIZE / sizeof(word32)]; 03848 XMEMCPY(tmpIv, aes->reg, AES_BLOCK_SIZE); 03849 return wc_Pic32AesCrypt( 03850 aes->key, aes->keylen, tmpIv, AES_BLOCK_SIZE, 03851 out, in, AES_BLOCK_SIZE, 03852 PIC32_ENCRYPTION, PIC32_ALGO_AES, PIC32_CRYPTOALGO_RCTR); 03853 } 03854 03855 #elif defined(HAVE_COLDFIRE_SEC) 03856 #error "Coldfire SEC doesn't currently support AES-CTR mode" 03857 03858 #elif defined(FREESCALE_LTC) 03859 int wc_AesCtrEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03860 { 03861 uint32_t keySize; 03862 byte *iv, *enc_key; 03863 byte* tmp; 03864 03865 if (aes == NULL || out == NULL || in == NULL) { 03866 return BAD_FUNC_ARG; 03867 } 03868 03869 /* consume any unused bytes left in aes->tmp */ 03870 tmp = (byte*)aes->tmp + AES_BLOCK_SIZE - aes->left; 03871 while (aes->left && sz) { 03872 *(out++) = *(in++) ^ *(tmp++); 03873 aes->left--; 03874 sz--; 03875 } 03876 03877 if (sz) { 03878 iv = (byte*)aes->reg; 03879 enc_key = (byte*)aes->key; 03880 03881 wc_AesGetKeySize(aes, &keySize); 03882 03883 LTC_AES_CryptCtr(LTC_BASE, in, out, sz, 03884 iv, enc_key, keySize, (byte*)aes->tmp, 03885 (uint32_t*)&aes->left); 03886 } 03887 03888 return 0; 03889 } 03890 03891 #elif defined(WOLFSSL_IMX6_CAAM) && !defined(NO_IMX6_CAAM_AES) 03892 /* implemented in wolfcrypt/src/port/caam/caam_aes.c */ 03893 03894 #elif defined(WOLFSSL_AFALG) 03895 /* implemented in wolfcrypt/src/port/af_alg/afalg_aes.c */ 03896 03897 #elif defined(WOLFSSL_DEVCRYPTO_AES) 03898 /* implemented in wolfcrypt/src/port/devcrypt/devcrypto_aes.c */ 03899 03900 #elif defined(WOLFSSL_ESP32WROOM32_CRYPT) && \ 03901 !defined(NO_WOLFSSL_ESP32WROOM32_CRYPT_AES) 03902 /* esp32 doesn't support CRT mode by hw. */ 03903 /* use aes ecnryption plus sw implementation */ 03904 #define NEED_AES_CTR_SOFT 03905 03906 #else 03907 03908 /* Use software based AES counter */ 03909 #define NEED_AES_CTR_SOFT 03910 #endif 03911 03912 #ifdef NEED_AES_CTR_SOFT 03913 /* Increment AES counter */ 03914 static WC_INLINE void IncrementAesCounter(byte* inOutCtr) 03915 { 03916 /* in network byte order so start at end and work back */ 03917 int i; 03918 for (i = AES_BLOCK_SIZE - 1; i >= 0; i--) { 03919 if (++inOutCtr[i]) /* we're done unless we overflow */ 03920 return; 03921 } 03922 } 03923 03924 /* Software AES - CTR Encrypt */ 03925 int wc_AesCtrEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 03926 { 03927 byte* tmp; 03928 byte scratch[AES_BLOCK_SIZE]; 03929 03930 if (aes == NULL || out == NULL || in == NULL) { 03931 return BAD_FUNC_ARG; 03932 } 03933 03934 /* consume any unused bytes left in aes->tmp */ 03935 tmp = (byte*)aes->tmp + AES_BLOCK_SIZE - aes->left; 03936 while (aes->left && sz) { 03937 *(out++) = *(in++) ^ *(tmp++); 03938 aes->left--; 03939 sz--; 03940 } 03941 03942 /* do as many block size ops as possible */ 03943 while (sz >= AES_BLOCK_SIZE) { 03944 #ifdef XTRANSFORM_AESCTRBLOCK 03945 XTRANSFORM_AESCTRBLOCK(aes, out, in); 03946 #else 03947 wc_AesEncrypt(aes, (byte*)aes->reg, scratch); 03948 xorbuf(scratch, in, AES_BLOCK_SIZE); 03949 XMEMCPY(out, scratch, AES_BLOCK_SIZE); 03950 #endif 03951 IncrementAesCounter((byte*)aes->reg); 03952 03953 out += AES_BLOCK_SIZE; 03954 in += AES_BLOCK_SIZE; 03955 sz -= AES_BLOCK_SIZE; 03956 aes->left = 0; 03957 } 03958 ForceZero(scratch, AES_BLOCK_SIZE); 03959 03960 /* handle non block size remaining and store unused byte count in left */ 03961 if (sz) { 03962 wc_AesEncrypt(aes, (byte*)aes->reg, (byte*)aes->tmp); 03963 IncrementAesCounter((byte*)aes->reg); 03964 03965 aes->left = AES_BLOCK_SIZE; 03966 tmp = (byte*)aes->tmp; 03967 03968 while (sz--) { 03969 *(out++) = *(in++) ^ *(tmp++); 03970 aes->left--; 03971 } 03972 } 03973 03974 return 0; 03975 } 03976 03977 #endif /* NEED_AES_CTR_SOFT */ 03978 03979 #endif /* WOLFSSL_AES_COUNTER */ 03980 #endif /* !WOLFSSL_ARMASM */ 03981 03982 03983 /* 03984 * The IV for AES GCM and CCM, stored in struct Aes's member reg, is comprised 03985 * of two parts in order: 03986 * 1. The fixed field which may be 0 or 4 bytes long. In TLS, this is set 03987 * to the implicit IV. 03988 * 2. The explicit IV is generated by wolfCrypt. It needs to be managed 03989 * by wolfCrypt to ensure the IV is unique for each call to encrypt. 03990 * The IV may be a 96-bit random value, or the 32-bit fixed value and a 03991 * 64-bit set of 0 or random data. The final 32-bits of reg is used as a 03992 * block counter during the encryption. 03993 */ 03994 03995 #if (defined(HAVE_AESGCM) && !defined(WC_NO_RNG)) || defined(HAVE_AESCCM) 03996 static WC_INLINE void IncCtr(byte* ctr, word32 ctrSz) 03997 { 03998 int i; 03999 for (i = ctrSz-1; i >= 0; i--) { 04000 if (++ctr[i]) 04001 break; 04002 } 04003 } 04004 #endif /* HAVE_AESGCM || HAVE_AESCCM */ 04005 04006 04007 #ifdef HAVE_AESGCM 04008 04009 #if defined(HAVE_COLDFIRE_SEC) 04010 #error "Coldfire SEC doesn't currently support AES-GCM mode" 04011 04012 #elif defined(WOLFSSL_NRF51_AES) 04013 #error "nRF51 doesn't currently support AES-GCM mode" 04014 04015 #endif 04016 04017 #ifdef WOLFSSL_ARMASM 04018 /* implementation is located in wolfcrypt/src/port/arm/armv8-aes.c */ 04019 04020 #elif defined(WOLFSSL_AFALG) 04021 /* implemented in wolfcrypt/src/port/afalg/afalg_aes.c */ 04022 04023 #elif defined(WOLFSSL_DEVCRYPTO_AES) 04024 /* implemented in wolfcrypt/src/port/devcrypt/devcrypto_aes.c */ 04025 04026 #else /* software + AESNI implementation */ 04027 04028 #if !defined(FREESCALE_LTC_AES_GCM) 04029 static WC_INLINE void IncrementGcmCounter(byte* inOutCtr) 04030 { 04031 int i; 04032 04033 /* in network byte order so start at end and work back */ 04034 for (i = AES_BLOCK_SIZE - 1; i >= AES_BLOCK_SIZE - CTR_SZ; i--) { 04035 if (++inOutCtr[i]) /* we're done unless we overflow */ 04036 return; 04037 } 04038 } 04039 #ifdef STM32_CRYPTO_AES_GCM 04040 static WC_INLINE void DecrementGcmCounter(byte* inOutCtr) 04041 { 04042 int i; 04043 04044 /* in network byte order so start at end and work back */ 04045 for (i = AES_BLOCK_SIZE - 1; i >= AES_BLOCK_SIZE - CTR_SZ; i--) { 04046 if (--inOutCtr[i] != 0xFF) /* we're done unless we underflow */ 04047 return; 04048 } 04049 } 04050 #endif /* STM32_CRYPTO_AES_GCM */ 04051 #endif /* !FREESCALE_LTC_AES_GCM */ 04052 04053 #if defined(GCM_SMALL) || defined(GCM_TABLE) 04054 04055 static WC_INLINE void FlattenSzInBits(byte* buf, word32 sz) 04056 { 04057 /* Multiply the sz by 8 */ 04058 word32 szHi = (sz >> (8*sizeof(sz) - 3)); 04059 sz <<= 3; 04060 04061 /* copy over the words of the sz into the destination buffer */ 04062 buf[0] = (szHi >> 24) & 0xff; 04063 buf[1] = (szHi >> 16) & 0xff; 04064 buf[2] = (szHi >> 8) & 0xff; 04065 buf[3] = szHi & 0xff; 04066 buf[4] = (sz >> 24) & 0xff; 04067 buf[5] = (sz >> 16) & 0xff; 04068 buf[6] = (sz >> 8) & 0xff; 04069 buf[7] = sz & 0xff; 04070 } 04071 04072 04073 static WC_INLINE void RIGHTSHIFTX(byte* x) 04074 { 04075 int i; 04076 int carryOut = 0; 04077 int carryIn = 0; 04078 int borrow = x[15] & 0x01; 04079 04080 for (i = 0; i < AES_BLOCK_SIZE; i++) { 04081 carryOut = x[i] & 0x01; 04082 x[i] = (x[i] >> 1) | (carryIn ? 0x80 : 0); 04083 carryIn = carryOut; 04084 } 04085 if (borrow) x[0] ^= 0xE1; 04086 } 04087 04088 #endif /* defined(GCM_SMALL) || defined(GCM_TABLE) */ 04089 04090 04091 #ifdef GCM_TABLE 04092 04093 static void GenerateM0(Aes* aes) 04094 { 04095 int i, j; 04096 byte (*m)[AES_BLOCK_SIZE] = aes->M0; 04097 04098 XMEMCPY(m[128], aes->H, AES_BLOCK_SIZE); 04099 04100 for (i = 64; i > 0; i /= 2) { 04101 XMEMCPY(m[i], m[i*2], AES_BLOCK_SIZE); 04102 RIGHTSHIFTX(m[i]); 04103 } 04104 04105 for (i = 2; i < 256; i *= 2) { 04106 for (j = 1; j < i; j++) { 04107 XMEMCPY(m[i+j], m[i], AES_BLOCK_SIZE); 04108 xorbuf(m[i+j], m[j], AES_BLOCK_SIZE); 04109 } 04110 } 04111 04112 XMEMSET(m[0], 0, AES_BLOCK_SIZE); 04113 } 04114 04115 #endif /* GCM_TABLE */ 04116 04117 /* Software AES - GCM SetKey */ 04118 int wc_AesGcmSetKey(Aes* aes, const byte* key, word32 len) 04119 { 04120 int ret; 04121 byte iv[AES_BLOCK_SIZE]; 04122 04123 #ifdef WOLFSSL_IMX6_CAAM_BLOB 04124 byte local[32]; 04125 word32 localSz = 32; 04126 04127 if (len == (16 + WC_CAAM_BLOB_SZ) || 04128 len == (24 + WC_CAAM_BLOB_SZ) || 04129 len == (32 + WC_CAAM_BLOB_SZ)) { 04130 if (wc_caamOpenBlob((byte*)key, len, local, &localSz) != 0) { 04131 return BAD_FUNC_ARG; 04132 } 04133 04134 /* set local values */ 04135 key = local; 04136 len = localSz; 04137 } 04138 #endif 04139 04140 if (!((len == 16) || (len == 24) || (len == 32))) 04141 return BAD_FUNC_ARG; 04142 04143 #ifdef OPENSSL_EXTRA 04144 if (aes != NULL) { 04145 XMEMSET(aes->aadH, 0, sizeof(aes->aadH)); 04146 aes->aadLen = 0; 04147 } 04148 #endif 04149 XMEMSET(iv, 0, AES_BLOCK_SIZE); 04150 ret = wc_AesSetKey(aes, key, len, iv, AES_ENCRYPTION); 04151 04152 #ifdef WOLFSSL_AESNI 04153 /* AES-NI code generates its own H value. */ 04154 if (haveAESNI) 04155 return ret; 04156 #endif /* WOLFSSL_AESNI */ 04157 04158 #if !defined(FREESCALE_LTC_AES_GCM) 04159 if (ret == 0) { 04160 wc_AesEncrypt(aes, iv, aes->H); 04161 #ifdef GCM_TABLE 04162 GenerateM0(aes); 04163 #endif /* GCM_TABLE */ 04164 } 04165 #endif /* FREESCALE_LTC_AES_GCM */ 04166 04167 #if defined(WOLFSSL_XILINX_CRYPT) 04168 wc_AesGcmSetKey_ex(aes, key, len, XSECURE_CSU_AES_KEY_SRC_KUP); 04169 #elif defined(WOLFSSL_AFALG_XILINX_AES) 04170 wc_AesGcmSetKey_ex(aes, key, len, 0); 04171 #endif 04172 04173 #ifdef WOLF_CRYPTO_CB 04174 if (aes->devId != INVALID_DEVID) { 04175 XMEMCPY(aes->devKey, key, len); 04176 } 04177 #endif 04178 04179 #ifdef WOLFSSL_IMX6_CAAM_BLOB 04180 ForceZero(local, sizeof(local)); 04181 #endif 04182 04183 return ret; 04184 } 04185 04186 04187 #ifdef WOLFSSL_AESNI 04188 04189 #if defined(USE_INTEL_SPEEDUP) 04190 #define HAVE_INTEL_AVX1 04191 #define HAVE_INTEL_AVX2 04192 #endif /* USE_INTEL_SPEEDUP */ 04193 04194 #ifndef _MSC_VER 04195 04196 void AES_GCM_encrypt(const unsigned char *in, unsigned char *out, 04197 const unsigned char* addt, const unsigned char* ivec, 04198 unsigned char *tag, unsigned int nbytes, 04199 unsigned int abytes, unsigned int ibytes, 04200 unsigned int tbytes, const unsigned char* key, int nr) 04201 XASM_LINK("AES_GCM_encrypt"); 04202 #ifdef HAVE_INTEL_AVX1 04203 void AES_GCM_encrypt_avx1(const unsigned char *in, unsigned char *out, 04204 const unsigned char* addt, const unsigned char* ivec, 04205 unsigned char *tag, unsigned int nbytes, 04206 unsigned int abytes, unsigned int ibytes, 04207 unsigned int tbytes, const unsigned char* key, 04208 int nr) 04209 XASM_LINK("AES_GCM_encrypt_avx1"); 04210 #ifdef HAVE_INTEL_AVX2 04211 void AES_GCM_encrypt_avx2(const unsigned char *in, unsigned char *out, 04212 const unsigned char* addt, const unsigned char* ivec, 04213 unsigned char *tag, unsigned int nbytes, 04214 unsigned int abytes, unsigned int ibytes, 04215 unsigned int tbytes, const unsigned char* key, 04216 int nr) 04217 XASM_LINK("AES_GCM_encrypt_avx2"); 04218 #endif /* HAVE_INTEL_AVX2 */ 04219 #endif /* HAVE_INTEL_AVX1 */ 04220 04221 #ifdef HAVE_AES_DECRYPT 04222 void AES_GCM_decrypt(const unsigned char *in, unsigned char *out, 04223 const unsigned char* addt, const unsigned char* ivec, 04224 const unsigned char *tag, int nbytes, int abytes, 04225 int ibytes, int tbytes, const unsigned char* key, int nr, 04226 int* res) 04227 XASM_LINK("AES_GCM_decrypt"); 04228 #ifdef HAVE_INTEL_AVX1 04229 void AES_GCM_decrypt_avx1(const unsigned char *in, unsigned char *out, 04230 const unsigned char* addt, const unsigned char* ivec, 04231 const unsigned char *tag, int nbytes, int abytes, 04232 int ibytes, int tbytes, const unsigned char* key, 04233 int nr, int* res) 04234 XASM_LINK("AES_GCM_decrypt_avx1"); 04235 #ifdef HAVE_INTEL_AVX2 04236 void AES_GCM_decrypt_avx2(const unsigned char *in, unsigned char *out, 04237 const unsigned char* addt, const unsigned char* ivec, 04238 const unsigned char *tag, int nbytes, int abytes, 04239 int ibytes, int tbytes, const unsigned char* key, 04240 int nr, int* res) 04241 XASM_LINK("AES_GCM_decrypt_avx2"); 04242 #endif /* HAVE_INTEL_AVX2 */ 04243 #endif /* HAVE_INTEL_AVX1 */ 04244 #endif /* HAVE_AES_DECRYPT */ 04245 04246 #else /* _MSC_VER */ 04247 04248 #define S(w,z) ((char)((unsigned long long)(w) >> (8*(7-(z))) & 0xFF)) 04249 #define M128_INIT(x,y) { S((x),7), S((x),6), S((x),5), S((x),4), \ 04250 S((x),3), S((x),2), S((x),1), S((x),0), \ 04251 S((y),7), S((y),6), S((y),5), S((y),4), \ 04252 S((y),3), S((y),2), S((y),1), S((y),0) } 04253 04254 static const __m128i MOD2_128 = 04255 M128_INIT(0x1, (long long int)0xc200000000000000UL); 04256 04257 04258 /* See Intel® Carry-Less Multiplication Instruction 04259 * and its Usage for Computing the GCM Mode White Paper 04260 * by Shay Gueron, Intel Mobility Group, Israel Development Center; 04261 * and Michael E. Kounavis, Intel Labs, Circuits and Systems Research */ 04262 04263 04264 /* Figure 9. AES-GCM – Encrypt With Single Block Ghash at a Time */ 04265 04266 static const __m128i ONE = M128_INIT(0x0, 0x1); 04267 #ifndef AES_GCM_AESNI_NO_UNROLL 04268 static const __m128i TWO = M128_INIT(0x0, 0x2); 04269 static const __m128i THREE = M128_INIT(0x0, 0x3); 04270 static const __m128i FOUR = M128_INIT(0x0, 0x4); 04271 static const __m128i FIVE = M128_INIT(0x0, 0x5); 04272 static const __m128i SIX = M128_INIT(0x0, 0x6); 04273 static const __m128i SEVEN = M128_INIT(0x0, 0x7); 04274 static const __m128i EIGHT = M128_INIT(0x0, 0x8); 04275 #endif 04276 static const __m128i BSWAP_EPI64 = 04277 M128_INIT(0x0001020304050607, 0x08090a0b0c0d0e0f); 04278 static const __m128i BSWAP_MASK = 04279 M128_INIT(0x08090a0b0c0d0e0f, 0x0001020304050607); 04280 04281 04282 /* The following are for MSC based builds which do not allow 04283 * inline assembly. Intrinsic functions are used instead. */ 04284 04285 #define aes_gcm_calc_iv_12(KEY, ivec, nr, H, Y, T) \ 04286 do \ 04287 { \ 04288 word32 iv12[4]; \ 04289 iv12[0] = *(word32*)&ivec[0]; \ 04290 iv12[1] = *(word32*)&ivec[4]; \ 04291 iv12[2] = *(word32*)&ivec[8]; \ 04292 iv12[3] = 0x01000000; \ 04293 Y = _mm_loadu_si128((__m128i*)iv12); \ 04294 \ 04295 /* (Compute E[ZERO, KS] and E[Y0, KS] together */ \ 04296 tmp1 = _mm_load_si128(&KEY[0]); \ 04297 tmp2 = _mm_xor_si128(Y, KEY[0]); \ 04298 tmp1 = _mm_aesenc_si128(tmp1, KEY[1]); \ 04299 tmp2 = _mm_aesenc_si128(tmp2, KEY[1]); \ 04300 tmp1 = _mm_aesenc_si128(tmp1, KEY[2]); \ 04301 tmp2 = _mm_aesenc_si128(tmp2, KEY[2]); \ 04302 tmp1 = _mm_aesenc_si128(tmp1, KEY[3]); \ 04303 tmp2 = _mm_aesenc_si128(tmp2, KEY[3]); \ 04304 tmp1 = _mm_aesenc_si128(tmp1, KEY[4]); \ 04305 tmp2 = _mm_aesenc_si128(tmp2, KEY[4]); \ 04306 tmp1 = _mm_aesenc_si128(tmp1, KEY[5]); \ 04307 tmp2 = _mm_aesenc_si128(tmp2, KEY[5]); \ 04308 tmp1 = _mm_aesenc_si128(tmp1, KEY[6]); \ 04309 tmp2 = _mm_aesenc_si128(tmp2, KEY[6]); \ 04310 tmp1 = _mm_aesenc_si128(tmp1, KEY[7]); \ 04311 tmp2 = _mm_aesenc_si128(tmp2, KEY[7]); \ 04312 tmp1 = _mm_aesenc_si128(tmp1, KEY[8]); \ 04313 tmp2 = _mm_aesenc_si128(tmp2, KEY[8]); \ 04314 tmp1 = _mm_aesenc_si128(tmp1, KEY[9]); \ 04315 tmp2 = _mm_aesenc_si128(tmp2, KEY[9]); \ 04316 lastKey = KEY[10]; \ 04317 if (nr > 10) { \ 04318 tmp1 = _mm_aesenc_si128(tmp1, lastKey); \ 04319 tmp2 = _mm_aesenc_si128(tmp2, lastKey); \ 04320 tmp1 = _mm_aesenc_si128(tmp1, KEY[11]); \ 04321 tmp2 = _mm_aesenc_si128(tmp2, KEY[11]); \ 04322 lastKey = KEY[12]; \ 04323 if (nr > 12) { \ 04324 tmp1 = _mm_aesenc_si128(tmp1, lastKey); \ 04325 tmp2 = _mm_aesenc_si128(tmp2, lastKey); \ 04326 tmp1 = _mm_aesenc_si128(tmp1, KEY[13]); \ 04327 tmp2 = _mm_aesenc_si128(tmp2, KEY[13]); \ 04328 lastKey = KEY[14]; \ 04329 } \ 04330 } \ 04331 H = _mm_aesenclast_si128(tmp1, lastKey); \ 04332 T = _mm_aesenclast_si128(tmp2, lastKey); \ 04333 H = _mm_shuffle_epi8(H, BSWAP_MASK); \ 04334 } \ 04335 while (0) 04336 04337 #define aes_gcm_calc_iv(KEY, ivec, ibytes, nr, H, Y, T) \ 04338 do \ 04339 { \ 04340 if (ibytes % 16) { \ 04341 i = ibytes / 16; \ 04342 for (j=0; j < (int)(ibytes%16); j++) \ 04343 ((unsigned char*)&last_block)[j] = ivec[i*16+j]; \ 04344 } \ 04345 tmp1 = _mm_load_si128(&KEY[0]); \ 04346 tmp1 = _mm_aesenc_si128(tmp1, KEY[1]); \ 04347 tmp1 = _mm_aesenc_si128(tmp1, KEY[2]); \ 04348 tmp1 = _mm_aesenc_si128(tmp1, KEY[3]); \ 04349 tmp1 = _mm_aesenc_si128(tmp1, KEY[4]); \ 04350 tmp1 = _mm_aesenc_si128(tmp1, KEY[5]); \ 04351 tmp1 = _mm_aesenc_si128(tmp1, KEY[6]); \ 04352 tmp1 = _mm_aesenc_si128(tmp1, KEY[7]); \ 04353 tmp1 = _mm_aesenc_si128(tmp1, KEY[8]); \ 04354 tmp1 = _mm_aesenc_si128(tmp1, KEY[9]); \ 04355 lastKey = KEY[10]; \ 04356 if (nr > 10) { \ 04357 tmp1 = _mm_aesenc_si128(tmp1, lastKey); \ 04358 tmp1 = _mm_aesenc_si128(tmp1, KEY[11]); \ 04359 lastKey = KEY[12]; \ 04360 if (nr > 12) { \ 04361 tmp1 = _mm_aesenc_si128(tmp1, lastKey); \ 04362 tmp1 = _mm_aesenc_si128(tmp1, KEY[13]); \ 04363 lastKey = KEY[14]; \ 04364 } \ 04365 } \ 04366 H = _mm_aesenclast_si128(tmp1, lastKey); \ 04367 H = _mm_shuffle_epi8(H, BSWAP_MASK); \ 04368 Y = _mm_setzero_si128(); \ 04369 for (i=0; i < (int)(ibytes/16); i++) { \ 04370 tmp1 = _mm_loadu_si128(&((__m128i*)ivec)[i]); \ 04371 tmp1 = _mm_shuffle_epi8(tmp1, BSWAP_MASK); \ 04372 Y = _mm_xor_si128(Y, tmp1); \ 04373 Y = gfmul_sw(Y, H); \ 04374 } \ 04375 if (ibytes % 16) { \ 04376 tmp1 = last_block; \ 04377 tmp1 = _mm_shuffle_epi8(tmp1, BSWAP_MASK); \ 04378 Y = _mm_xor_si128(Y, tmp1); \ 04379 Y = gfmul_sw(Y, H); \ 04380 } \ 04381 tmp1 = _mm_insert_epi64(tmp1, ibytes*8, 0); \ 04382 tmp1 = _mm_insert_epi64(tmp1, 0, 1); \ 04383 Y = _mm_xor_si128(Y, tmp1); \ 04384 Y = gfmul_sw(Y, H); \ 04385 Y = _mm_shuffle_epi8(Y, BSWAP_MASK); /* Compute E(K, Y0) */ \ 04386 tmp1 = _mm_xor_si128(Y, KEY[0]); \ 04387 tmp1 = _mm_aesenc_si128(tmp1, KEY[1]); \ 04388 tmp1 = _mm_aesenc_si128(tmp1, KEY[2]); \ 04389 tmp1 = _mm_aesenc_si128(tmp1, KEY[3]); \ 04390 tmp1 = _mm_aesenc_si128(tmp1, KEY[4]); \ 04391 tmp1 = _mm_aesenc_si128(tmp1, KEY[5]); \ 04392 tmp1 = _mm_aesenc_si128(tmp1, KEY[6]); \ 04393 tmp1 = _mm_aesenc_si128(tmp1, KEY[7]); \ 04394 tmp1 = _mm_aesenc_si128(tmp1, KEY[8]); \ 04395 tmp1 = _mm_aesenc_si128(tmp1, KEY[9]); \ 04396 lastKey = KEY[10]; \ 04397 if (nr > 10) { \ 04398 tmp1 = _mm_aesenc_si128(tmp1, lastKey); \ 04399 tmp1 = _mm_aesenc_si128(tmp1, KEY[11]); \ 04400 lastKey = KEY[12]; \ 04401 if (nr > 12) { \ 04402 tmp1 = _mm_aesenc_si128(tmp1, lastKey); \ 04403 tmp1 = _mm_aesenc_si128(tmp1, KEY[13]); \ 04404 lastKey = KEY[14]; \ 04405 } \ 04406 } \ 04407 T = _mm_aesenclast_si128(tmp1, lastKey); \ 04408 } \ 04409 while (0) 04410 04411 #define AES_ENC_8(j) \ 04412 tmp1 = _mm_aesenc_si128(tmp1, KEY[j]); \ 04413 tmp2 = _mm_aesenc_si128(tmp2, KEY[j]); \ 04414 tmp3 = _mm_aesenc_si128(tmp3, KEY[j]); \ 04415 tmp4 = _mm_aesenc_si128(tmp4, KEY[j]); \ 04416 tmp5 = _mm_aesenc_si128(tmp5, KEY[j]); \ 04417 tmp6 = _mm_aesenc_si128(tmp6, KEY[j]); \ 04418 tmp7 = _mm_aesenc_si128(tmp7, KEY[j]); \ 04419 tmp8 = _mm_aesenc_si128(tmp8, KEY[j]); 04420 04421 #define AES_ENC_LAST_8() \ 04422 tmp1 =_mm_aesenclast_si128(tmp1, lastKey); \ 04423 tmp2 =_mm_aesenclast_si128(tmp2, lastKey); \ 04424 tmp1 = _mm_xor_si128(tmp1, _mm_loadu_si128(&((__m128i*)in)[i*8+0])); \ 04425 tmp2 = _mm_xor_si128(tmp2, _mm_loadu_si128(&((__m128i*)in)[i*8+1])); \ 04426 _mm_storeu_si128(&((__m128i*)out)[i*8+0], tmp1); \ 04427 _mm_storeu_si128(&((__m128i*)out)[i*8+1], tmp2); \ 04428 tmp3 =_mm_aesenclast_si128(tmp3, lastKey); \ 04429 tmp4 =_mm_aesenclast_si128(tmp4, lastKey); \ 04430 tmp3 = _mm_xor_si128(tmp3, _mm_loadu_si128(&((__m128i*)in)[i*8+2])); \ 04431 tmp4 = _mm_xor_si128(tmp4, _mm_loadu_si128(&((__m128i*)in)[i*8+3])); \ 04432 _mm_storeu_si128(&((__m128i*)out)[i*8+2], tmp3); \ 04433 _mm_storeu_si128(&((__m128i*)out)[i*8+3], tmp4); \ 04434 tmp5 =_mm_aesenclast_si128(tmp5, lastKey); \ 04435 tmp6 =_mm_aesenclast_si128(tmp6, lastKey); \ 04436 tmp5 = _mm_xor_si128(tmp5, _mm_loadu_si128(&((__m128i*)in)[i*8+4])); \ 04437 tmp6 = _mm_xor_si128(tmp6, _mm_loadu_si128(&((__m128i*)in)[i*8+5])); \ 04438 _mm_storeu_si128(&((__m128i*)out)[i*8+4], tmp5); \ 04439 _mm_storeu_si128(&((__m128i*)out)[i*8+5], tmp6); \ 04440 tmp7 =_mm_aesenclast_si128(tmp7, lastKey); \ 04441 tmp8 =_mm_aesenclast_si128(tmp8, lastKey); \ 04442 tmp7 = _mm_xor_si128(tmp7, _mm_loadu_si128(&((__m128i*)in)[i*8+6])); \ 04443 tmp8 = _mm_xor_si128(tmp8, _mm_loadu_si128(&((__m128i*)in)[i*8+7])); \ 04444 _mm_storeu_si128(&((__m128i*)out)[i*8+6], tmp7); \ 04445 _mm_storeu_si128(&((__m128i*)out)[i*8+7], tmp8); 04446 04447 04448 static __m128i gfmul_sw(__m128i a, __m128i b) 04449 { 04450 __m128i r, t1, t2, t3, t4, t5, t6, t7; 04451 t2 = _mm_shuffle_epi32(b, 78); 04452 t3 = _mm_shuffle_epi32(a, 78); 04453 t2 = _mm_xor_si128(t2, b); 04454 t3 = _mm_xor_si128(t3, a); 04455 t4 = _mm_clmulepi64_si128(b, a, 0x11); 04456 t1 = _mm_clmulepi64_si128(b, a, 0x00); 04457 t2 = _mm_clmulepi64_si128(t2, t3, 0x00); 04458 t2 = _mm_xor_si128(t2, t1); 04459 t2 = _mm_xor_si128(t2, t4); 04460 t3 = _mm_slli_si128(t2, 8); 04461 t2 = _mm_srli_si128(t2, 8); 04462 t1 = _mm_xor_si128(t1, t3); 04463 t4 = _mm_xor_si128(t4, t2); 04464 04465 t5 = _mm_srli_epi32(t1, 31); 04466 t6 = _mm_srli_epi32(t4, 31); 04467 t1 = _mm_slli_epi32(t1, 1); 04468 t4 = _mm_slli_epi32(t4, 1); 04469 t7 = _mm_srli_si128(t5, 12); 04470 t5 = _mm_slli_si128(t5, 4); 04471 t6 = _mm_slli_si128(t6, 4); 04472 t4 = _mm_or_si128(t4, t7); 04473 t1 = _mm_or_si128(t1, t5); 04474 t4 = _mm_or_si128(t4, t6); 04475 04476 t5 = _mm_slli_epi32(t1, 31); 04477 t6 = _mm_slli_epi32(t1, 30); 04478 t7 = _mm_slli_epi32(t1, 25); 04479 t5 = _mm_xor_si128(t5, t6); 04480 t5 = _mm_xor_si128(t5, t7); 04481 04482 t6 = _mm_srli_si128(t5, 4); 04483 t5 = _mm_slli_si128(t5, 12); 04484 t1 = _mm_xor_si128(t1, t5); 04485 t7 = _mm_srli_epi32(t1, 1); 04486 t3 = _mm_srli_epi32(t1, 2); 04487 t2 = _mm_srli_epi32(t1, 7); 04488 04489 t7 = _mm_xor_si128(t7, t3); 04490 t7 = _mm_xor_si128(t7, t2); 04491 t7 = _mm_xor_si128(t7, t6); 04492 t7 = _mm_xor_si128(t7, t1); 04493 r = _mm_xor_si128(t4, t7); 04494 04495 return r; 04496 } 04497 04498 static void gfmul_only(__m128i a, __m128i b, __m128i* r0, __m128i* r1) 04499 { 04500 __m128i t1, t2, t3, t4; 04501 04502 /* 128 x 128 Carryless Multiply */ 04503 t2 = _mm_shuffle_epi32(b, 78); 04504 t3 = _mm_shuffle_epi32(a, 78); 04505 t2 = _mm_xor_si128(t2, b); 04506 t3 = _mm_xor_si128(t3, a); 04507 t4 = _mm_clmulepi64_si128(b, a, 0x11); 04508 t1 = _mm_clmulepi64_si128(b, a, 0x00); 04509 t2 = _mm_clmulepi64_si128(t2, t3, 0x00); 04510 t2 = _mm_xor_si128(t2, t1); 04511 t2 = _mm_xor_si128(t2, t4); 04512 t3 = _mm_slli_si128(t2, 8); 04513 t2 = _mm_srli_si128(t2, 8); 04514 t1 = _mm_xor_si128(t1, t3); 04515 t4 = _mm_xor_si128(t4, t2); 04516 *r0 = _mm_xor_si128(t1, *r0); 04517 *r1 = _mm_xor_si128(t4, *r1); 04518 } 04519 04520 static __m128i gfmul_shl1(__m128i a) 04521 { 04522 __m128i t1 = a, t2; 04523 t2 = _mm_srli_epi64(t1, 63); 04524 t1 = _mm_slli_epi64(t1, 1); 04525 t2 = _mm_slli_si128(t2, 8); 04526 t1 = _mm_or_si128(t1, t2); 04527 /* if (a[1] >> 63) t1 = _mm_xor_si128(t1, MOD2_128); */ 04528 a = _mm_shuffle_epi32(a, 0xff); 04529 a = _mm_srai_epi32(a, 31); 04530 a = _mm_and_si128(a, MOD2_128); 04531 t1 = _mm_xor_si128(t1, a); 04532 return t1; 04533 } 04534 04535 static __m128i ghash_red(__m128i r0, __m128i r1) 04536 { 04537 __m128i t2, t3; 04538 __m128i t5, t6, t7; 04539 04540 t5 = _mm_slli_epi32(r0, 31); 04541 t6 = _mm_slli_epi32(r0, 30); 04542 t7 = _mm_slli_epi32(r0, 25); 04543 t5 = _mm_xor_si128(t5, t6); 04544 t5 = _mm_xor_si128(t5, t7); 04545 04546 t6 = _mm_srli_si128(t5, 4); 04547 t5 = _mm_slli_si128(t5, 12); 04548 r0 = _mm_xor_si128(r0, t5); 04549 t7 = _mm_srli_epi32(r0, 1); 04550 t3 = _mm_srli_epi32(r0, 2); 04551 t2 = _mm_srli_epi32(r0, 7); 04552 04553 t7 = _mm_xor_si128(t7, t3); 04554 t7 = _mm_xor_si128(t7, t2); 04555 t7 = _mm_xor_si128(t7, t6); 04556 t7 = _mm_xor_si128(t7, r0); 04557 return _mm_xor_si128(r1, t7); 04558 } 04559 04560 static __m128i gfmul_shifted(__m128i a, __m128i b) 04561 { 04562 __m128i t0 = _mm_setzero_si128(), t1 = _mm_setzero_si128(); 04563 gfmul_only(a, b, &t0, &t1); 04564 return ghash_red(t0, t1); 04565 } 04566 04567 #ifndef AES_GCM_AESNI_NO_UNROLL 04568 static __m128i gfmul8(__m128i a1, __m128i a2, __m128i a3, __m128i a4, 04569 __m128i a5, __m128i a6, __m128i a7, __m128i a8, 04570 __m128i b1, __m128i b2, __m128i b3, __m128i b4, 04571 __m128i b5, __m128i b6, __m128i b7, __m128i b8) 04572 { 04573 __m128i t0 = _mm_setzero_si128(), t1 = _mm_setzero_si128(); 04574 gfmul_only(a1, b8, &t0, &t1); 04575 gfmul_only(a2, b7, &t0, &t1); 04576 gfmul_only(a3, b6, &t0, &t1); 04577 gfmul_only(a4, b5, &t0, &t1); 04578 gfmul_only(a5, b4, &t0, &t1); 04579 gfmul_only(a6, b3, &t0, &t1); 04580 gfmul_only(a7, b2, &t0, &t1); 04581 gfmul_only(a8, b1, &t0, &t1); 04582 return ghash_red(t0, t1); 04583 } 04584 #endif 04585 04586 04587 static void AES_GCM_encrypt(const unsigned char *in, 04588 unsigned char *out, 04589 const unsigned char* addt, 04590 const unsigned char* ivec, 04591 unsigned char *tag, unsigned int nbytes, 04592 unsigned int abytes, unsigned int ibytes, 04593 unsigned int tbytes, 04594 const unsigned char* key, int nr) 04595 { 04596 int i, j ,k; 04597 __m128i ctr1; 04598 __m128i H, Y, T; 04599 __m128i X = _mm_setzero_si128(); 04600 __m128i *KEY = (__m128i*)key, lastKey; 04601 __m128i last_block = _mm_setzero_si128(); 04602 __m128i tmp1, tmp2; 04603 #ifndef AES_GCM_AESNI_NO_UNROLL 04604 __m128i HT[8]; 04605 __m128i r0, r1; 04606 __m128i XV; 04607 __m128i tmp3, tmp4, tmp5, tmp6, tmp7, tmp8; 04608 #endif 04609 04610 if (ibytes == GCM_NONCE_MID_SZ) 04611 aes_gcm_calc_iv_12(KEY, ivec, nr, H, Y, T); 04612 else 04613 aes_gcm_calc_iv(KEY, ivec, ibytes, nr, H, Y, T); 04614 04615 for (i=0; i < (int)(abytes/16); i++) { 04616 tmp1 = _mm_loadu_si128(&((__m128i*)addt)[i]); 04617 tmp1 = _mm_shuffle_epi8(tmp1, BSWAP_MASK); 04618 X = _mm_xor_si128(X, tmp1); 04619 X = gfmul_sw(X, H); 04620 } 04621 if (abytes%16) { 04622 last_block = _mm_setzero_si128(); 04623 for (j=0; j < (int)(abytes%16); j++) 04624 ((unsigned char*)&last_block)[j] = addt[i*16+j]; 04625 tmp1 = last_block; 04626 tmp1 = _mm_shuffle_epi8(tmp1, BSWAP_MASK); 04627 X = _mm_xor_si128(X, tmp1); 04628 X = gfmul_sw(X, H); 04629 } 04630 tmp1 = _mm_shuffle_epi8(Y, BSWAP_EPI64); 04631 ctr1 = _mm_add_epi32(tmp1, ONE); 04632 H = gfmul_shl1(H); 04633 04634 #ifndef AES_GCM_AESNI_NO_UNROLL 04635 i = 0; 04636 if (nbytes >= 16*8) { 04637 HT[0] = H; 04638 HT[1] = gfmul_shifted(H, H); 04639 HT[2] = gfmul_shifted(H, HT[1]); 04640 HT[3] = gfmul_shifted(HT[1], HT[1]); 04641 HT[4] = gfmul_shifted(HT[1], HT[2]); 04642 HT[5] = gfmul_shifted(HT[2], HT[2]); 04643 HT[6] = gfmul_shifted(HT[2], HT[3]); 04644 HT[7] = gfmul_shifted(HT[3], HT[3]); 04645 04646 tmp1 = _mm_shuffle_epi8(ctr1, BSWAP_EPI64); 04647 tmp2 = _mm_add_epi32(ctr1, ONE); 04648 tmp2 = _mm_shuffle_epi8(tmp2, BSWAP_EPI64); 04649 tmp3 = _mm_add_epi32(ctr1, TWO); 04650 tmp3 = _mm_shuffle_epi8(tmp3, BSWAP_EPI64); 04651 tmp4 = _mm_add_epi32(ctr1, THREE); 04652 tmp4 = _mm_shuffle_epi8(tmp4, BSWAP_EPI64); 04653 tmp5 = _mm_add_epi32(ctr1, FOUR); 04654 tmp5 = _mm_shuffle_epi8(tmp5, BSWAP_EPI64); 04655 tmp6 = _mm_add_epi32(ctr1, FIVE); 04656 tmp6 = _mm_shuffle_epi8(tmp6, BSWAP_EPI64); 04657 tmp7 = _mm_add_epi32(ctr1, SIX); 04658 tmp7 = _mm_shuffle_epi8(tmp7, BSWAP_EPI64); 04659 tmp8 = _mm_add_epi32(ctr1, SEVEN); 04660 tmp8 = _mm_shuffle_epi8(tmp8, BSWAP_EPI64); 04661 ctr1 = _mm_add_epi32(ctr1, EIGHT); 04662 tmp1 =_mm_xor_si128(tmp1, KEY[0]); 04663 tmp2 =_mm_xor_si128(tmp2, KEY[0]); 04664 tmp3 =_mm_xor_si128(tmp3, KEY[0]); 04665 tmp4 =_mm_xor_si128(tmp4, KEY[0]); 04666 tmp5 =_mm_xor_si128(tmp5, KEY[0]); 04667 tmp6 =_mm_xor_si128(tmp6, KEY[0]); 04668 tmp7 =_mm_xor_si128(tmp7, KEY[0]); 04669 tmp8 =_mm_xor_si128(tmp8, KEY[0]); 04670 AES_ENC_8(1); 04671 AES_ENC_8(2); 04672 AES_ENC_8(3); 04673 AES_ENC_8(4); 04674 AES_ENC_8(5); 04675 AES_ENC_8(6); 04676 AES_ENC_8(7); 04677 AES_ENC_8(8); 04678 AES_ENC_8(9); 04679 lastKey = KEY[10]; 04680 if (nr > 10) { 04681 AES_ENC_8(10); 04682 AES_ENC_8(11); 04683 lastKey = KEY[12]; 04684 if (nr > 12) { 04685 AES_ENC_8(12); 04686 AES_ENC_8(13); 04687 lastKey = KEY[14]; 04688 } 04689 } 04690 AES_ENC_LAST_8(); 04691 04692 for (i=1; i < (int)(nbytes/16/8); i++) { 04693 r0 = _mm_setzero_si128(); 04694 r1 = _mm_setzero_si128(); 04695 tmp1 = _mm_shuffle_epi8(ctr1, BSWAP_EPI64); 04696 tmp2 = _mm_add_epi32(ctr1, ONE); 04697 tmp2 = _mm_shuffle_epi8(tmp2, BSWAP_EPI64); 04698 tmp3 = _mm_add_epi32(ctr1, TWO); 04699 tmp3 = _mm_shuffle_epi8(tmp3, BSWAP_EPI64); 04700 tmp4 = _mm_add_epi32(ctr1, THREE); 04701 tmp4 = _mm_shuffle_epi8(tmp4, BSWAP_EPI64); 04702 tmp5 = _mm_add_epi32(ctr1, FOUR); 04703 tmp5 = _mm_shuffle_epi8(tmp5, BSWAP_EPI64); 04704 tmp6 = _mm_add_epi32(ctr1, FIVE); 04705 tmp6 = _mm_shuffle_epi8(tmp6, BSWAP_EPI64); 04706 tmp7 = _mm_add_epi32(ctr1, SIX); 04707 tmp7 = _mm_shuffle_epi8(tmp7, BSWAP_EPI64); 04708 tmp8 = _mm_add_epi32(ctr1, SEVEN); 04709 tmp8 = _mm_shuffle_epi8(tmp8, BSWAP_EPI64); 04710 ctr1 = _mm_add_epi32(ctr1, EIGHT); 04711 tmp1 =_mm_xor_si128(tmp1, KEY[0]); 04712 tmp2 =_mm_xor_si128(tmp2, KEY[0]); 04713 tmp3 =_mm_xor_si128(tmp3, KEY[0]); 04714 tmp4 =_mm_xor_si128(tmp4, KEY[0]); 04715 tmp5 =_mm_xor_si128(tmp5, KEY[0]); 04716 tmp6 =_mm_xor_si128(tmp6, KEY[0]); 04717 tmp7 =_mm_xor_si128(tmp7, KEY[0]); 04718 tmp8 =_mm_xor_si128(tmp8, KEY[0]); 04719 /* 128 x 128 Carryless Multiply */ 04720 XV = _mm_loadu_si128(&((__m128i*)out)[(i-1)*8+0]); 04721 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 04722 XV = _mm_xor_si128(XV, X); 04723 gfmul_only(XV, HT[7], &r0, &r1); 04724 tmp1 = _mm_aesenc_si128(tmp1, KEY[1]); 04725 tmp2 = _mm_aesenc_si128(tmp2, KEY[1]); 04726 tmp3 = _mm_aesenc_si128(tmp3, KEY[1]); 04727 tmp4 = _mm_aesenc_si128(tmp4, KEY[1]); 04728 tmp5 = _mm_aesenc_si128(tmp5, KEY[1]); 04729 tmp6 = _mm_aesenc_si128(tmp6, KEY[1]); 04730 tmp7 = _mm_aesenc_si128(tmp7, KEY[1]); 04731 tmp8 = _mm_aesenc_si128(tmp8, KEY[1]); 04732 /* 128 x 128 Carryless Multiply */ 04733 XV = _mm_loadu_si128(&((__m128i*)out)[(i-1)*8+1]); 04734 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 04735 gfmul_only(XV, HT[6], &r0, &r1); 04736 tmp1 = _mm_aesenc_si128(tmp1, KEY[2]); 04737 tmp2 = _mm_aesenc_si128(tmp2, KEY[2]); 04738 tmp3 = _mm_aesenc_si128(tmp3, KEY[2]); 04739 tmp4 = _mm_aesenc_si128(tmp4, KEY[2]); 04740 tmp5 = _mm_aesenc_si128(tmp5, KEY[2]); 04741 tmp6 = _mm_aesenc_si128(tmp6, KEY[2]); 04742 tmp7 = _mm_aesenc_si128(tmp7, KEY[2]); 04743 tmp8 = _mm_aesenc_si128(tmp8, KEY[2]); 04744 /* 128 x 128 Carryless Multiply */ 04745 XV = _mm_loadu_si128(&((__m128i*)out)[(i-1)*8+2]); 04746 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 04747 gfmul_only(XV, HT[5], &r0, &r1); 04748 tmp1 = _mm_aesenc_si128(tmp1, KEY[3]); 04749 tmp2 = _mm_aesenc_si128(tmp2, KEY[3]); 04750 tmp3 = _mm_aesenc_si128(tmp3, KEY[3]); 04751 tmp4 = _mm_aesenc_si128(tmp4, KEY[3]); 04752 tmp5 = _mm_aesenc_si128(tmp5, KEY[3]); 04753 tmp6 = _mm_aesenc_si128(tmp6, KEY[3]); 04754 tmp7 = _mm_aesenc_si128(tmp7, KEY[3]); 04755 tmp8 = _mm_aesenc_si128(tmp8, KEY[3]); 04756 /* 128 x 128 Carryless Multiply */ 04757 XV = _mm_loadu_si128(&((__m128i*)out)[(i-1)*8+3]); 04758 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 04759 gfmul_only(XV, HT[4], &r0, &r1); 04760 tmp1 = _mm_aesenc_si128(tmp1, KEY[4]); 04761 tmp2 = _mm_aesenc_si128(tmp2, KEY[4]); 04762 tmp3 = _mm_aesenc_si128(tmp3, KEY[4]); 04763 tmp4 = _mm_aesenc_si128(tmp4, KEY[4]); 04764 tmp5 = _mm_aesenc_si128(tmp5, KEY[4]); 04765 tmp6 = _mm_aesenc_si128(tmp6, KEY[4]); 04766 tmp7 = _mm_aesenc_si128(tmp7, KEY[4]); 04767 tmp8 = _mm_aesenc_si128(tmp8, KEY[4]); 04768 /* 128 x 128 Carryless Multiply */ 04769 XV = _mm_loadu_si128(&((__m128i*)out)[(i-1)*8+4]); 04770 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 04771 gfmul_only(XV, HT[3], &r0, &r1); 04772 tmp1 = _mm_aesenc_si128(tmp1, KEY[5]); 04773 tmp2 = _mm_aesenc_si128(tmp2, KEY[5]); 04774 tmp3 = _mm_aesenc_si128(tmp3, KEY[5]); 04775 tmp4 = _mm_aesenc_si128(tmp4, KEY[5]); 04776 tmp5 = _mm_aesenc_si128(tmp5, KEY[5]); 04777 tmp6 = _mm_aesenc_si128(tmp6, KEY[5]); 04778 tmp7 = _mm_aesenc_si128(tmp7, KEY[5]); 04779 tmp8 = _mm_aesenc_si128(tmp8, KEY[5]); 04780 /* 128 x 128 Carryless Multiply */ 04781 XV = _mm_loadu_si128(&((__m128i*)out)[(i-1)*8+5]); 04782 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 04783 gfmul_only(XV, HT[2], &r0, &r1); 04784 tmp1 = _mm_aesenc_si128(tmp1, KEY[6]); 04785 tmp2 = _mm_aesenc_si128(tmp2, KEY[6]); 04786 tmp3 = _mm_aesenc_si128(tmp3, KEY[6]); 04787 tmp4 = _mm_aesenc_si128(tmp4, KEY[6]); 04788 tmp5 = _mm_aesenc_si128(tmp5, KEY[6]); 04789 tmp6 = _mm_aesenc_si128(tmp6, KEY[6]); 04790 tmp7 = _mm_aesenc_si128(tmp7, KEY[6]); 04791 tmp8 = _mm_aesenc_si128(tmp8, KEY[6]); 04792 /* 128 x 128 Carryless Multiply */ 04793 XV = _mm_loadu_si128(&((__m128i*)out)[(i-1)*8+6]); 04794 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 04795 gfmul_only(XV, HT[1], &r0, &r1); 04796 tmp1 = _mm_aesenc_si128(tmp1, KEY[7]); 04797 tmp2 = _mm_aesenc_si128(tmp2, KEY[7]); 04798 tmp3 = _mm_aesenc_si128(tmp3, KEY[7]); 04799 tmp4 = _mm_aesenc_si128(tmp4, KEY[7]); 04800 tmp5 = _mm_aesenc_si128(tmp5, KEY[7]); 04801 tmp6 = _mm_aesenc_si128(tmp6, KEY[7]); 04802 tmp7 = _mm_aesenc_si128(tmp7, KEY[7]); 04803 tmp8 = _mm_aesenc_si128(tmp8, KEY[7]); 04804 /* 128 x 128 Carryless Multiply */ 04805 XV = _mm_loadu_si128(&((__m128i*)out)[(i-1)*8+7]); 04806 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 04807 gfmul_only(XV, HT[0], &r0, &r1); 04808 tmp1 = _mm_aesenc_si128(tmp1, KEY[8]); 04809 tmp2 = _mm_aesenc_si128(tmp2, KEY[8]); 04810 tmp3 = _mm_aesenc_si128(tmp3, KEY[8]); 04811 tmp4 = _mm_aesenc_si128(tmp4, KEY[8]); 04812 tmp5 = _mm_aesenc_si128(tmp5, KEY[8]); 04813 tmp6 = _mm_aesenc_si128(tmp6, KEY[8]); 04814 tmp7 = _mm_aesenc_si128(tmp7, KEY[8]); 04815 tmp8 = _mm_aesenc_si128(tmp8, KEY[8]); 04816 /* Reduction */ 04817 X = ghash_red(r0, r1); 04818 tmp1 = _mm_aesenc_si128(tmp1, KEY[9]); 04819 tmp2 = _mm_aesenc_si128(tmp2, KEY[9]); 04820 tmp3 = _mm_aesenc_si128(tmp3, KEY[9]); 04821 tmp4 = _mm_aesenc_si128(tmp4, KEY[9]); 04822 tmp5 = _mm_aesenc_si128(tmp5, KEY[9]); 04823 tmp6 = _mm_aesenc_si128(tmp6, KEY[9]); 04824 tmp7 = _mm_aesenc_si128(tmp7, KEY[9]); 04825 tmp8 = _mm_aesenc_si128(tmp8, KEY[9]); 04826 lastKey = KEY[10]; 04827 if (nr > 10) { 04828 tmp1 = _mm_aesenc_si128(tmp1, KEY[10]); 04829 tmp2 = _mm_aesenc_si128(tmp2, KEY[10]); 04830 tmp3 = _mm_aesenc_si128(tmp3, KEY[10]); 04831 tmp4 = _mm_aesenc_si128(tmp4, KEY[10]); 04832 tmp5 = _mm_aesenc_si128(tmp5, KEY[10]); 04833 tmp6 = _mm_aesenc_si128(tmp6, KEY[10]); 04834 tmp7 = _mm_aesenc_si128(tmp7, KEY[10]); 04835 tmp8 = _mm_aesenc_si128(tmp8, KEY[10]); 04836 tmp1 = _mm_aesenc_si128(tmp1, KEY[11]); 04837 tmp2 = _mm_aesenc_si128(tmp2, KEY[11]); 04838 tmp3 = _mm_aesenc_si128(tmp3, KEY[11]); 04839 tmp4 = _mm_aesenc_si128(tmp4, KEY[11]); 04840 tmp5 = _mm_aesenc_si128(tmp5, KEY[11]); 04841 tmp6 = _mm_aesenc_si128(tmp6, KEY[11]); 04842 tmp7 = _mm_aesenc_si128(tmp7, KEY[11]); 04843 tmp8 = _mm_aesenc_si128(tmp8, KEY[11]); 04844 lastKey = KEY[12]; 04845 if (nr > 12) { 04846 tmp1 = _mm_aesenc_si128(tmp1, KEY[12]); 04847 tmp2 = _mm_aesenc_si128(tmp2, KEY[12]); 04848 tmp3 = _mm_aesenc_si128(tmp3, KEY[12]); 04849 tmp4 = _mm_aesenc_si128(tmp4, KEY[12]); 04850 tmp5 = _mm_aesenc_si128(tmp5, KEY[12]); 04851 tmp6 = _mm_aesenc_si128(tmp6, KEY[12]); 04852 tmp7 = _mm_aesenc_si128(tmp7, KEY[12]); 04853 tmp8 = _mm_aesenc_si128(tmp8, KEY[12]); 04854 tmp1 = _mm_aesenc_si128(tmp1, KEY[13]); 04855 tmp2 = _mm_aesenc_si128(tmp2, KEY[13]); 04856 tmp3 = _mm_aesenc_si128(tmp3, KEY[13]); 04857 tmp4 = _mm_aesenc_si128(tmp4, KEY[13]); 04858 tmp5 = _mm_aesenc_si128(tmp5, KEY[13]); 04859 tmp6 = _mm_aesenc_si128(tmp6, KEY[13]); 04860 tmp7 = _mm_aesenc_si128(tmp7, KEY[13]); 04861 tmp8 = _mm_aesenc_si128(tmp8, KEY[13]); 04862 lastKey = KEY[14]; 04863 } 04864 } 04865 AES_ENC_LAST_8(); 04866 } 04867 04868 tmp1 = _mm_shuffle_epi8(tmp1, BSWAP_MASK); 04869 tmp2 = _mm_shuffle_epi8(tmp2, BSWAP_MASK); 04870 tmp3 = _mm_shuffle_epi8(tmp3, BSWAP_MASK); 04871 tmp4 = _mm_shuffle_epi8(tmp4, BSWAP_MASK); 04872 tmp5 = _mm_shuffle_epi8(tmp5, BSWAP_MASK); 04873 tmp6 = _mm_shuffle_epi8(tmp6, BSWAP_MASK); 04874 tmp7 = _mm_shuffle_epi8(tmp7, BSWAP_MASK); 04875 tmp8 = _mm_shuffle_epi8(tmp8, BSWAP_MASK); 04876 tmp1 = _mm_xor_si128(X, tmp1); 04877 X = gfmul8(tmp1, tmp2, tmp3, tmp4, tmp5, tmp6, tmp7, tmp8, 04878 HT[0], HT[1], HT[2], HT[3], HT[4], HT[5], HT[6], HT[7]); 04879 } 04880 for (k = i*8; k < (int)(nbytes/16); k++) { 04881 tmp1 = _mm_shuffle_epi8(ctr1, BSWAP_EPI64); 04882 ctr1 = _mm_add_epi32(ctr1, ONE); 04883 tmp1 = _mm_xor_si128(tmp1, KEY[0]); 04884 tmp1 = _mm_aesenc_si128(tmp1, KEY[1]); 04885 tmp1 = _mm_aesenc_si128(tmp1, KEY[2]); 04886 tmp1 = _mm_aesenc_si128(tmp1, KEY[3]); 04887 tmp1 = _mm_aesenc_si128(tmp1, KEY[4]); 04888 tmp1 = _mm_aesenc_si128(tmp1, KEY[5]); 04889 tmp1 = _mm_aesenc_si128(tmp1, KEY[6]); 04890 tmp1 = _mm_aesenc_si128(tmp1, KEY[7]); 04891 tmp1 = _mm_aesenc_si128(tmp1, KEY[8]); 04892 tmp1 = _mm_aesenc_si128(tmp1, KEY[9]); 04893 lastKey = KEY[10]; 04894 if (nr > 10) { 04895 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 04896 tmp1 = _mm_aesenc_si128(tmp1, KEY[11]); 04897 lastKey = KEY[12]; 04898 if (nr > 12) { 04899 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 04900 tmp1 = _mm_aesenc_si128(tmp1, KEY[13]); 04901 lastKey = KEY[14]; 04902 } 04903 } 04904 tmp1 = _mm_aesenclast_si128(tmp1, lastKey); 04905 tmp1 = _mm_xor_si128(tmp1, _mm_loadu_si128(&((__m128i*)in)[k])); 04906 _mm_storeu_si128(&((__m128i*)out)[k], tmp1); 04907 tmp1 = _mm_shuffle_epi8(tmp1, BSWAP_MASK); 04908 X =_mm_xor_si128(X, tmp1); 04909 X = gfmul_shifted(X, H); 04910 } 04911 #else /* AES_GCM_AESNI_NO_UNROLL */ 04912 for (k = 0; k < (int)(nbytes/16) && k < 1; k++) { 04913 tmp1 = _mm_shuffle_epi8(ctr1, BSWAP_EPI64); 04914 ctr1 = _mm_add_epi32(ctr1, ONE); 04915 tmp1 = _mm_xor_si128(tmp1, KEY[0]); 04916 tmp1 = _mm_aesenc_si128(tmp1, KEY[1]); 04917 tmp1 = _mm_aesenc_si128(tmp1, KEY[2]); 04918 tmp1 = _mm_aesenc_si128(tmp1, KEY[3]); 04919 tmp1 = _mm_aesenc_si128(tmp1, KEY[4]); 04920 tmp1 = _mm_aesenc_si128(tmp1, KEY[5]); 04921 tmp1 = _mm_aesenc_si128(tmp1, KEY[6]); 04922 tmp1 = _mm_aesenc_si128(tmp1, KEY[7]); 04923 tmp1 = _mm_aesenc_si128(tmp1, KEY[8]); 04924 tmp1 = _mm_aesenc_si128(tmp1, KEY[9]); 04925 lastKey = KEY[10]; 04926 if (nr > 10) { 04927 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 04928 tmp1 = _mm_aesenc_si128(tmp1, KEY[11]); 04929 lastKey = KEY[12]; 04930 if (nr > 12) { 04931 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 04932 tmp1 = _mm_aesenc_si128(tmp1, KEY[13]); 04933 lastKey = KEY[14]; 04934 } 04935 } 04936 tmp1 = _mm_aesenclast_si128(tmp1, lastKey); 04937 tmp1 = _mm_xor_si128(tmp1, _mm_loadu_si128(&((__m128i*)in)[k])); 04938 _mm_storeu_si128(&((__m128i*)out)[k], tmp1); 04939 tmp1 = _mm_shuffle_epi8(tmp1, BSWAP_MASK); 04940 X =_mm_xor_si128(X, tmp1); 04941 } 04942 for (; k < (int)(nbytes/16); k++) { 04943 tmp1 = _mm_shuffle_epi8(ctr1, BSWAP_EPI64); 04944 ctr1 = _mm_add_epi32(ctr1, ONE); 04945 tmp1 = _mm_xor_si128(tmp1, KEY[0]); 04946 tmp1 = _mm_aesenc_si128(tmp1, KEY[1]); 04947 tmp1 = _mm_aesenc_si128(tmp1, KEY[2]); 04948 tmp1 = _mm_aesenc_si128(tmp1, KEY[3]); 04949 tmp1 = _mm_aesenc_si128(tmp1, KEY[4]); 04950 tmp1 = _mm_aesenc_si128(tmp1, KEY[5]); 04951 tmp1 = _mm_aesenc_si128(tmp1, KEY[6]); 04952 tmp1 = _mm_aesenc_si128(tmp1, KEY[7]); 04953 tmp1 = _mm_aesenc_si128(tmp1, KEY[8]); 04954 tmp1 = _mm_aesenc_si128(tmp1, KEY[9]); 04955 X = gfmul_shifted(X, H); 04956 lastKey = KEY[10]; 04957 if (nr > 10) { 04958 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 04959 tmp1 = _mm_aesenc_si128(tmp1, KEY[11]); 04960 lastKey = KEY[12]; 04961 if (nr > 12) { 04962 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 04963 tmp1 = _mm_aesenc_si128(tmp1, KEY[13]); 04964 lastKey = KEY[14]; 04965 } 04966 } 04967 tmp1 = _mm_aesenclast_si128(tmp1, lastKey); 04968 tmp1 = _mm_xor_si128(tmp1, _mm_loadu_si128(&((__m128i*)in)[k])); 04969 _mm_storeu_si128(&((__m128i*)out)[k], tmp1); 04970 tmp1 = _mm_shuffle_epi8(tmp1, BSWAP_MASK); 04971 X =_mm_xor_si128(X, tmp1); 04972 } 04973 if (k > 0) { 04974 X = gfmul_shifted(X, H); 04975 } 04976 #endif /* AES_GCM_AESNI_NO_UNROLL */ 04977 04978 /* If one partial block remains */ 04979 if (nbytes % 16) { 04980 tmp1 = _mm_shuffle_epi8(ctr1, BSWAP_EPI64); 04981 tmp1 = _mm_xor_si128(tmp1, KEY[0]); 04982 tmp1 = _mm_aesenc_si128(tmp1, KEY[1]); 04983 tmp1 = _mm_aesenc_si128(tmp1, KEY[2]); 04984 tmp1 = _mm_aesenc_si128(tmp1, KEY[3]); 04985 tmp1 = _mm_aesenc_si128(tmp1, KEY[4]); 04986 tmp1 = _mm_aesenc_si128(tmp1, KEY[5]); 04987 tmp1 = _mm_aesenc_si128(tmp1, KEY[6]); 04988 tmp1 = _mm_aesenc_si128(tmp1, KEY[7]); 04989 tmp1 = _mm_aesenc_si128(tmp1, KEY[8]); 04990 tmp1 = _mm_aesenc_si128(tmp1, KEY[9]); 04991 lastKey = KEY[10]; 04992 if (nr > 10) { 04993 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 04994 tmp1 = _mm_aesenc_si128(tmp1, KEY[11]); 04995 lastKey = KEY[12]; 04996 if (nr > 12) { 04997 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 04998 tmp1 = _mm_aesenc_si128(tmp1, KEY[13]); 04999 lastKey = KEY[14]; 05000 } 05001 } 05002 tmp1 = _mm_aesenclast_si128(tmp1, lastKey); 05003 last_block = tmp1; 05004 for (j=0; j < (int)(nbytes%16); j++) 05005 ((unsigned char*)&last_block)[j] = in[k*16+j]; 05006 tmp1 = _mm_xor_si128(tmp1, last_block); 05007 last_block = tmp1; 05008 for (j=0; j < (int)(nbytes%16); j++) 05009 out[k*16+j] = ((unsigned char*)&last_block)[j]; 05010 tmp1 = last_block; 05011 tmp1 = _mm_shuffle_epi8(tmp1, BSWAP_MASK); 05012 X =_mm_xor_si128(X, tmp1); 05013 X = gfmul_shifted(X, H); 05014 } 05015 tmp1 = _mm_insert_epi64(tmp1, nbytes*8, 0); 05016 tmp1 = _mm_insert_epi64(tmp1, abytes*8, 1); 05017 X = _mm_xor_si128(X, tmp1); 05018 X = gfmul_shifted(X, H); 05019 X = _mm_shuffle_epi8(X, BSWAP_MASK); 05020 T = _mm_xor_si128(X, T); 05021 /*_mm_storeu_si128((__m128i*)tag, T);*/ 05022 XMEMCPY(tag, &T, tbytes); 05023 } 05024 05025 #ifdef HAVE_AES_DECRYPT 05026 05027 static void AES_GCM_decrypt(const unsigned char *in, 05028 unsigned char *out, 05029 const unsigned char* addt, 05030 const unsigned char* ivec, 05031 const unsigned char *tag, int nbytes, int abytes, 05032 int ibytes, word32 tbytes, const unsigned char* key, 05033 int nr, int* res) 05034 { 05035 int i, j ,k; 05036 __m128i H, Y, T; 05037 __m128i *KEY = (__m128i*)key, lastKey; 05038 __m128i ctr1; 05039 __m128i last_block = _mm_setzero_si128(); 05040 __m128i X = _mm_setzero_si128(); 05041 __m128i tmp1, tmp2, XV; 05042 #ifndef AES_GCM_AESNI_NO_UNROLL 05043 __m128i HT[8]; 05044 __m128i r0, r1; 05045 __m128i tmp3, tmp4, tmp5, tmp6, tmp7, tmp8; 05046 #endif /* AES_GCM_AESNI_NO_UNROLL */ 05047 05048 if (ibytes == GCM_NONCE_MID_SZ) 05049 aes_gcm_calc_iv_12(KEY, ivec, nr, H, Y, T); 05050 else 05051 aes_gcm_calc_iv(KEY, ivec, ibytes, nr, H, Y, T); 05052 05053 for (i=0; i<abytes/16; i++) { 05054 tmp1 = _mm_loadu_si128(&((__m128i*)addt)[i]); 05055 tmp1 = _mm_shuffle_epi8(tmp1, BSWAP_MASK); 05056 X = _mm_xor_si128(X, tmp1); 05057 X = gfmul_sw(X, H); 05058 } 05059 if (abytes%16) { 05060 last_block = _mm_setzero_si128(); 05061 for (j=0; j<abytes%16; j++) 05062 ((unsigned char*)&last_block)[j] = addt[i*16+j]; 05063 tmp1 = last_block; 05064 tmp1 = _mm_shuffle_epi8(tmp1, BSWAP_MASK); 05065 X = _mm_xor_si128(X, tmp1); 05066 X = gfmul_sw(X, H); 05067 } 05068 05069 tmp1 = _mm_shuffle_epi8(Y, BSWAP_EPI64); 05070 ctr1 = _mm_add_epi32(tmp1, ONE); 05071 H = gfmul_shl1(H); 05072 i = 0; 05073 05074 #ifndef AES_GCM_AESNI_NO_UNROLL 05075 05076 if (0 < nbytes/16/8) { 05077 HT[0] = H; 05078 HT[1] = gfmul_shifted(H, H); 05079 HT[2] = gfmul_shifted(H, HT[1]); 05080 HT[3] = gfmul_shifted(HT[1], HT[1]); 05081 HT[4] = gfmul_shifted(HT[1], HT[2]); 05082 HT[5] = gfmul_shifted(HT[2], HT[2]); 05083 HT[6] = gfmul_shifted(HT[2], HT[3]); 05084 HT[7] = gfmul_shifted(HT[3], HT[3]); 05085 05086 for (; i < nbytes/16/8; i++) { 05087 r0 = _mm_setzero_si128(); 05088 r1 = _mm_setzero_si128(); 05089 05090 tmp1 = _mm_shuffle_epi8(ctr1, BSWAP_EPI64); 05091 tmp2 = _mm_add_epi32(ctr1, ONE); 05092 tmp2 = _mm_shuffle_epi8(tmp2, BSWAP_EPI64); 05093 tmp3 = _mm_add_epi32(ctr1, TWO); 05094 tmp3 = _mm_shuffle_epi8(tmp3, BSWAP_EPI64); 05095 tmp4 = _mm_add_epi32(ctr1, THREE); 05096 tmp4 = _mm_shuffle_epi8(tmp4, BSWAP_EPI64); 05097 tmp5 = _mm_add_epi32(ctr1, FOUR); 05098 tmp5 = _mm_shuffle_epi8(tmp5, BSWAP_EPI64); 05099 tmp6 = _mm_add_epi32(ctr1, FIVE); 05100 tmp6 = _mm_shuffle_epi8(tmp6, BSWAP_EPI64); 05101 tmp7 = _mm_add_epi32(ctr1, SIX); 05102 tmp7 = _mm_shuffle_epi8(tmp7, BSWAP_EPI64); 05103 tmp8 = _mm_add_epi32(ctr1, SEVEN); 05104 tmp8 = _mm_shuffle_epi8(tmp8, BSWAP_EPI64); 05105 ctr1 = _mm_add_epi32(ctr1, EIGHT); 05106 tmp1 =_mm_xor_si128(tmp1, KEY[0]); 05107 tmp2 =_mm_xor_si128(tmp2, KEY[0]); 05108 tmp3 =_mm_xor_si128(tmp3, KEY[0]); 05109 tmp4 =_mm_xor_si128(tmp4, KEY[0]); 05110 tmp5 =_mm_xor_si128(tmp5, KEY[0]); 05111 tmp6 =_mm_xor_si128(tmp6, KEY[0]); 05112 tmp7 =_mm_xor_si128(tmp7, KEY[0]); 05113 tmp8 =_mm_xor_si128(tmp8, KEY[0]); 05114 /* 128 x 128 Carryless Multiply */ 05115 XV = _mm_loadu_si128(&((__m128i*)in)[i*8+0]); 05116 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 05117 XV = _mm_xor_si128(XV, X); 05118 gfmul_only(XV, HT[7], &r0, &r1); 05119 tmp1 = _mm_aesenc_si128(tmp1, KEY[1]); 05120 tmp2 = _mm_aesenc_si128(tmp2, KEY[1]); 05121 tmp3 = _mm_aesenc_si128(tmp3, KEY[1]); 05122 tmp4 = _mm_aesenc_si128(tmp4, KEY[1]); 05123 tmp5 = _mm_aesenc_si128(tmp5, KEY[1]); 05124 tmp6 = _mm_aesenc_si128(tmp6, KEY[1]); 05125 tmp7 = _mm_aesenc_si128(tmp7, KEY[1]); 05126 tmp8 = _mm_aesenc_si128(tmp8, KEY[1]); 05127 /* 128 x 128 Carryless Multiply */ 05128 XV = _mm_loadu_si128(&((__m128i*)in)[i*8+1]); 05129 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 05130 gfmul_only(XV, HT[6], &r0, &r1); 05131 tmp1 = _mm_aesenc_si128(tmp1, KEY[2]); 05132 tmp2 = _mm_aesenc_si128(tmp2, KEY[2]); 05133 tmp3 = _mm_aesenc_si128(tmp3, KEY[2]); 05134 tmp4 = _mm_aesenc_si128(tmp4, KEY[2]); 05135 tmp5 = _mm_aesenc_si128(tmp5, KEY[2]); 05136 tmp6 = _mm_aesenc_si128(tmp6, KEY[2]); 05137 tmp7 = _mm_aesenc_si128(tmp7, KEY[2]); 05138 tmp8 = _mm_aesenc_si128(tmp8, KEY[2]); 05139 /* 128 x 128 Carryless Multiply */ 05140 XV = _mm_loadu_si128(&((__m128i*)in)[i*8+2]); 05141 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 05142 gfmul_only(XV, HT[5], &r0, &r1); 05143 tmp1 = _mm_aesenc_si128(tmp1, KEY[3]); 05144 tmp2 = _mm_aesenc_si128(tmp2, KEY[3]); 05145 tmp3 = _mm_aesenc_si128(tmp3, KEY[3]); 05146 tmp4 = _mm_aesenc_si128(tmp4, KEY[3]); 05147 tmp5 = _mm_aesenc_si128(tmp5, KEY[3]); 05148 tmp6 = _mm_aesenc_si128(tmp6, KEY[3]); 05149 tmp7 = _mm_aesenc_si128(tmp7, KEY[3]); 05150 tmp8 = _mm_aesenc_si128(tmp8, KEY[3]); 05151 /* 128 x 128 Carryless Multiply */ 05152 XV = _mm_loadu_si128(&((__m128i*)in)[i*8+3]); 05153 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 05154 gfmul_only(XV, HT[4], &r0, &r1); 05155 tmp1 = _mm_aesenc_si128(tmp1, KEY[4]); 05156 tmp2 = _mm_aesenc_si128(tmp2, KEY[4]); 05157 tmp3 = _mm_aesenc_si128(tmp3, KEY[4]); 05158 tmp4 = _mm_aesenc_si128(tmp4, KEY[4]); 05159 tmp5 = _mm_aesenc_si128(tmp5, KEY[4]); 05160 tmp6 = _mm_aesenc_si128(tmp6, KEY[4]); 05161 tmp7 = _mm_aesenc_si128(tmp7, KEY[4]); 05162 tmp8 = _mm_aesenc_si128(tmp8, KEY[4]); 05163 /* 128 x 128 Carryless Multiply */ 05164 XV = _mm_loadu_si128(&((__m128i*)in)[i*8+4]); 05165 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 05166 gfmul_only(XV, HT[3], &r0, &r1); 05167 tmp1 = _mm_aesenc_si128(tmp1, KEY[5]); 05168 tmp2 = _mm_aesenc_si128(tmp2, KEY[5]); 05169 tmp3 = _mm_aesenc_si128(tmp3, KEY[5]); 05170 tmp4 = _mm_aesenc_si128(tmp4, KEY[5]); 05171 tmp5 = _mm_aesenc_si128(tmp5, KEY[5]); 05172 tmp6 = _mm_aesenc_si128(tmp6, KEY[5]); 05173 tmp7 = _mm_aesenc_si128(tmp7, KEY[5]); 05174 tmp8 = _mm_aesenc_si128(tmp8, KEY[5]); 05175 /* 128 x 128 Carryless Multiply */ 05176 XV = _mm_loadu_si128(&((__m128i*)in)[i*8+5]); 05177 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 05178 gfmul_only(XV, HT[2], &r0, &r1); 05179 tmp1 = _mm_aesenc_si128(tmp1, KEY[6]); 05180 tmp2 = _mm_aesenc_si128(tmp2, KEY[6]); 05181 tmp3 = _mm_aesenc_si128(tmp3, KEY[6]); 05182 tmp4 = _mm_aesenc_si128(tmp4, KEY[6]); 05183 tmp5 = _mm_aesenc_si128(tmp5, KEY[6]); 05184 tmp6 = _mm_aesenc_si128(tmp6, KEY[6]); 05185 tmp7 = _mm_aesenc_si128(tmp7, KEY[6]); 05186 tmp8 = _mm_aesenc_si128(tmp8, KEY[6]); 05187 /* 128 x 128 Carryless Multiply */ 05188 XV = _mm_loadu_si128(&((__m128i*)in)[i*8+6]); 05189 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 05190 gfmul_only(XV, HT[1], &r0, &r1); 05191 tmp1 = _mm_aesenc_si128(tmp1, KEY[7]); 05192 tmp2 = _mm_aesenc_si128(tmp2, KEY[7]); 05193 tmp3 = _mm_aesenc_si128(tmp3, KEY[7]); 05194 tmp4 = _mm_aesenc_si128(tmp4, KEY[7]); 05195 tmp5 = _mm_aesenc_si128(tmp5, KEY[7]); 05196 tmp6 = _mm_aesenc_si128(tmp6, KEY[7]); 05197 tmp7 = _mm_aesenc_si128(tmp7, KEY[7]); 05198 tmp8 = _mm_aesenc_si128(tmp8, KEY[7]); 05199 /* 128 x 128 Carryless Multiply */ 05200 XV = _mm_loadu_si128(&((__m128i*)in)[i*8+7]); 05201 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 05202 gfmul_only(XV, HT[0], &r0, &r1); 05203 tmp1 = _mm_aesenc_si128(tmp1, KEY[8]); 05204 tmp2 = _mm_aesenc_si128(tmp2, KEY[8]); 05205 tmp3 = _mm_aesenc_si128(tmp3, KEY[8]); 05206 tmp4 = _mm_aesenc_si128(tmp4, KEY[8]); 05207 tmp5 = _mm_aesenc_si128(tmp5, KEY[8]); 05208 tmp6 = _mm_aesenc_si128(tmp6, KEY[8]); 05209 tmp7 = _mm_aesenc_si128(tmp7, KEY[8]); 05210 tmp8 = _mm_aesenc_si128(tmp8, KEY[8]); 05211 /* Reduction */ 05212 X = ghash_red(r0, r1); 05213 tmp1 = _mm_aesenc_si128(tmp1, KEY[9]); 05214 tmp2 = _mm_aesenc_si128(tmp2, KEY[9]); 05215 tmp3 = _mm_aesenc_si128(tmp3, KEY[9]); 05216 tmp4 = _mm_aesenc_si128(tmp4, KEY[9]); 05217 tmp5 = _mm_aesenc_si128(tmp5, KEY[9]); 05218 tmp6 = _mm_aesenc_si128(tmp6, KEY[9]); 05219 tmp7 = _mm_aesenc_si128(tmp7, KEY[9]); 05220 tmp8 = _mm_aesenc_si128(tmp8, KEY[9]); 05221 lastKey = KEY[10]; 05222 if (nr > 10) { 05223 tmp1 = _mm_aesenc_si128(tmp1, KEY[10]); 05224 tmp2 = _mm_aesenc_si128(tmp2, KEY[10]); 05225 tmp3 = _mm_aesenc_si128(tmp3, KEY[10]); 05226 tmp4 = _mm_aesenc_si128(tmp4, KEY[10]); 05227 tmp5 = _mm_aesenc_si128(tmp5, KEY[10]); 05228 tmp6 = _mm_aesenc_si128(tmp6, KEY[10]); 05229 tmp7 = _mm_aesenc_si128(tmp7, KEY[10]); 05230 tmp8 = _mm_aesenc_si128(tmp8, KEY[10]); 05231 tmp1 = _mm_aesenc_si128(tmp1, KEY[11]); 05232 tmp2 = _mm_aesenc_si128(tmp2, KEY[11]); 05233 tmp3 = _mm_aesenc_si128(tmp3, KEY[11]); 05234 tmp4 = _mm_aesenc_si128(tmp4, KEY[11]); 05235 tmp5 = _mm_aesenc_si128(tmp5, KEY[11]); 05236 tmp6 = _mm_aesenc_si128(tmp6, KEY[11]); 05237 tmp7 = _mm_aesenc_si128(tmp7, KEY[11]); 05238 tmp8 = _mm_aesenc_si128(tmp8, KEY[11]); 05239 lastKey = KEY[12]; 05240 if (nr > 12) { 05241 tmp1 = _mm_aesenc_si128(tmp1, KEY[12]); 05242 tmp2 = _mm_aesenc_si128(tmp2, KEY[12]); 05243 tmp3 = _mm_aesenc_si128(tmp3, KEY[12]); 05244 tmp4 = _mm_aesenc_si128(tmp4, KEY[12]); 05245 tmp5 = _mm_aesenc_si128(tmp5, KEY[12]); 05246 tmp6 = _mm_aesenc_si128(tmp6, KEY[12]); 05247 tmp7 = _mm_aesenc_si128(tmp7, KEY[12]); 05248 tmp8 = _mm_aesenc_si128(tmp8, KEY[12]); 05249 tmp1 = _mm_aesenc_si128(tmp1, KEY[13]); 05250 tmp2 = _mm_aesenc_si128(tmp2, KEY[13]); 05251 tmp3 = _mm_aesenc_si128(tmp3, KEY[13]); 05252 tmp4 = _mm_aesenc_si128(tmp4, KEY[13]); 05253 tmp5 = _mm_aesenc_si128(tmp5, KEY[13]); 05254 tmp6 = _mm_aesenc_si128(tmp6, KEY[13]); 05255 tmp7 = _mm_aesenc_si128(tmp7, KEY[13]); 05256 tmp8 = _mm_aesenc_si128(tmp8, KEY[13]); 05257 lastKey = KEY[14]; 05258 } 05259 } 05260 AES_ENC_LAST_8(); 05261 } 05262 } 05263 05264 #endif /* AES_GCM_AESNI_NO_UNROLL */ 05265 05266 for (k = i*8; k < nbytes/16; k++) { 05267 tmp1 = _mm_shuffle_epi8(ctr1, BSWAP_EPI64); 05268 ctr1 = _mm_add_epi32(ctr1, ONE); 05269 tmp1 = _mm_xor_si128(tmp1, KEY[0]); 05270 tmp1 = _mm_aesenc_si128(tmp1, KEY[1]); 05271 tmp1 = _mm_aesenc_si128(tmp1, KEY[2]); 05272 tmp1 = _mm_aesenc_si128(tmp1, KEY[3]); 05273 tmp1 = _mm_aesenc_si128(tmp1, KEY[4]); 05274 tmp1 = _mm_aesenc_si128(tmp1, KEY[5]); 05275 tmp1 = _mm_aesenc_si128(tmp1, KEY[6]); 05276 tmp1 = _mm_aesenc_si128(tmp1, KEY[7]); 05277 tmp1 = _mm_aesenc_si128(tmp1, KEY[8]); 05278 tmp1 = _mm_aesenc_si128(tmp1, KEY[9]); 05279 /* 128 x 128 Carryless Multiply */ 05280 XV = _mm_loadu_si128(&((__m128i*)in)[k]); 05281 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 05282 XV = _mm_xor_si128(XV, X); 05283 X = gfmul_shifted(XV, H); 05284 lastKey = KEY[10]; 05285 if (nr > 10) { 05286 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 05287 tmp1 = _mm_aesenc_si128(tmp1, KEY[11]); 05288 lastKey = KEY[12]; 05289 if (nr > 12) { 05290 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 05291 tmp1 = _mm_aesenc_si128(tmp1, KEY[13]); 05292 lastKey = KEY[14]; 05293 } 05294 } 05295 tmp1 = _mm_aesenclast_si128(tmp1, lastKey); 05296 tmp2 = _mm_loadu_si128(&((__m128i*)in)[k]); 05297 tmp1 = _mm_xor_si128(tmp1, tmp2); 05298 _mm_storeu_si128(&((__m128i*)out)[k], tmp1); 05299 } 05300 05301 /* If one partial block remains */ 05302 if (nbytes % 16) { 05303 tmp1 = _mm_shuffle_epi8(ctr1, BSWAP_EPI64); 05304 tmp1 = _mm_xor_si128(tmp1, KEY[0]); 05305 tmp1 = _mm_aesenc_si128(tmp1, KEY[1]); 05306 tmp1 = _mm_aesenc_si128(tmp1, KEY[2]); 05307 tmp1 = _mm_aesenc_si128(tmp1, KEY[3]); 05308 tmp1 = _mm_aesenc_si128(tmp1, KEY[4]); 05309 tmp1 = _mm_aesenc_si128(tmp1, KEY[5]); 05310 tmp1 = _mm_aesenc_si128(tmp1, KEY[6]); 05311 tmp1 = _mm_aesenc_si128(tmp1, KEY[7]); 05312 tmp1 = _mm_aesenc_si128(tmp1, KEY[8]); 05313 tmp1 = _mm_aesenc_si128(tmp1, KEY[9]); 05314 lastKey = KEY[10]; 05315 if (nr > 10) { 05316 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 05317 tmp1 = _mm_aesenc_si128(tmp1, KEY[11]); 05318 lastKey = KEY[12]; 05319 if (nr > 12) { 05320 tmp1 = _mm_aesenc_si128(tmp1, lastKey); 05321 tmp1 = _mm_aesenc_si128(tmp1, KEY[13]); 05322 lastKey = KEY[14]; 05323 } 05324 } 05325 tmp1 = _mm_aesenclast_si128(tmp1, lastKey); 05326 last_block = _mm_setzero_si128(); 05327 for (j=0; j < nbytes%16; j++) 05328 ((unsigned char*)&last_block)[j] = in[k*16+j]; 05329 XV = last_block; 05330 tmp1 = _mm_xor_si128(tmp1, last_block); 05331 last_block = tmp1; 05332 for (j=0; j < nbytes%16; j++) 05333 out[k*16+j] = ((unsigned char*)&last_block)[j]; 05334 XV = _mm_shuffle_epi8(XV, BSWAP_MASK); 05335 XV = _mm_xor_si128(XV, X); 05336 X = gfmul_shifted(XV, H); 05337 } 05338 05339 tmp1 = _mm_insert_epi64(tmp1, nbytes*8, 0); 05340 tmp1 = _mm_insert_epi64(tmp1, abytes*8, 1); 05341 /* 128 x 128 Carryless Multiply */ 05342 X = _mm_xor_si128(X, tmp1); 05343 X = gfmul_shifted(X, H); 05344 X = _mm_shuffle_epi8(X, BSWAP_MASK); 05345 T = _mm_xor_si128(X, T); 05346 05347 /* if (0xffff != 05348 _mm_movemask_epi8(_mm_cmpeq_epi8(T, _mm_loadu_si128((__m128i*)tag)))) */ 05349 if (XMEMCMP(tag, &T, tbytes) != 0) 05350 *res = 0; /* in case the authentication failed */ 05351 else 05352 *res = 1; /* when successful returns 1 */ 05353 } 05354 05355 #endif /* HAVE_AES_DECRYPT */ 05356 #endif /* _MSC_VER */ 05357 #endif /* WOLFSSL_AESNI */ 05358 05359 05360 #if defined(GCM_SMALL) 05361 static void GMULT(byte* X, byte* Y) 05362 { 05363 byte Z[AES_BLOCK_SIZE]; 05364 byte V[AES_BLOCK_SIZE]; 05365 int i, j; 05366 05367 XMEMSET(Z, 0, AES_BLOCK_SIZE); 05368 XMEMCPY(V, X, AES_BLOCK_SIZE); 05369 for (i = 0; i < AES_BLOCK_SIZE; i++) 05370 { 05371 byte y = Y[i]; 05372 for (j = 0; j < 8; j++) 05373 { 05374 if (y & 0x80) { 05375 xorbuf(Z, V, AES_BLOCK_SIZE); 05376 } 05377 05378 RIGHTSHIFTX(V); 05379 y = y << 1; 05380 } 05381 } 05382 XMEMCPY(X, Z, AES_BLOCK_SIZE); 05383 } 05384 05385 05386 void GHASH(Aes* aes, const byte* a, word32 aSz, const byte* c, 05387 word32 cSz, byte* s, word32 sSz) 05388 { 05389 byte x[AES_BLOCK_SIZE]; 05390 byte scratch[AES_BLOCK_SIZE]; 05391 word32 blocks, partial; 05392 byte* h = aes->H; 05393 05394 XMEMSET(x, 0, AES_BLOCK_SIZE); 05395 05396 /* Hash in A, the Additional Authentication Data */ 05397 if (aSz != 0 && a != NULL) { 05398 blocks = aSz / AES_BLOCK_SIZE; 05399 partial = aSz % AES_BLOCK_SIZE; 05400 while (blocks--) { 05401 xorbuf(x, a, AES_BLOCK_SIZE); 05402 GMULT(x, h); 05403 a += AES_BLOCK_SIZE; 05404 } 05405 if (partial != 0) { 05406 XMEMSET(scratch, 0, AES_BLOCK_SIZE); 05407 XMEMCPY(scratch, a, partial); 05408 xorbuf(x, scratch, AES_BLOCK_SIZE); 05409 GMULT(x, h); 05410 } 05411 } 05412 05413 /* Hash in C, the Ciphertext */ 05414 if (cSz != 0 && c != NULL) { 05415 blocks = cSz / AES_BLOCK_SIZE; 05416 partial = cSz % AES_BLOCK_SIZE; 05417 while (blocks--) { 05418 xorbuf(x, c, AES_BLOCK_SIZE); 05419 GMULT(x, h); 05420 c += AES_BLOCK_SIZE; 05421 } 05422 if (partial != 0) { 05423 XMEMSET(scratch, 0, AES_BLOCK_SIZE); 05424 XMEMCPY(scratch, c, partial); 05425 xorbuf(x, scratch, AES_BLOCK_SIZE); 05426 GMULT(x, h); 05427 } 05428 } 05429 05430 /* Hash in the lengths of A and C in bits */ 05431 FlattenSzInBits(&scratch[0], aSz); 05432 FlattenSzInBits(&scratch[8], cSz); 05433 xorbuf(x, scratch, AES_BLOCK_SIZE); 05434 GMULT(x, h); 05435 05436 /* Copy the result into s. */ 05437 XMEMCPY(s, x, sSz); 05438 } 05439 05440 /* end GCM_SMALL */ 05441 #elif defined(GCM_TABLE) 05442 05443 static const byte R[256][2] = { 05444 {0x00, 0x00}, {0x01, 0xc2}, {0x03, 0x84}, {0x02, 0x46}, 05445 {0x07, 0x08}, {0x06, 0xca}, {0x04, 0x8c}, {0x05, 0x4e}, 05446 {0x0e, 0x10}, {0x0f, 0xd2}, {0x0d, 0x94}, {0x0c, 0x56}, 05447 {0x09, 0x18}, {0x08, 0xda}, {0x0a, 0x9c}, {0x0b, 0x5e}, 05448 {0x1c, 0x20}, {0x1d, 0xe2}, {0x1f, 0xa4}, {0x1e, 0x66}, 05449 {0x1b, 0x28}, {0x1a, 0xea}, {0x18, 0xac}, {0x19, 0x6e}, 05450 {0x12, 0x30}, {0x13, 0xf2}, {0x11, 0xb4}, {0x10, 0x76}, 05451 {0x15, 0x38}, {0x14, 0xfa}, {0x16, 0xbc}, {0x17, 0x7e}, 05452 {0x38, 0x40}, {0x39, 0x82}, {0x3b, 0xc4}, {0x3a, 0x06}, 05453 {0x3f, 0x48}, {0x3e, 0x8a}, {0x3c, 0xcc}, {0x3d, 0x0e}, 05454 {0x36, 0x50}, {0x37, 0x92}, {0x35, 0xd4}, {0x34, 0x16}, 05455 {0x31, 0x58}, {0x30, 0x9a}, {0x32, 0xdc}, {0x33, 0x1e}, 05456 {0x24, 0x60}, {0x25, 0xa2}, {0x27, 0xe4}, {0x26, 0x26}, 05457 {0x23, 0x68}, {0x22, 0xaa}, {0x20, 0xec}, {0x21, 0x2e}, 05458 {0x2a, 0x70}, {0x2b, 0xb2}, {0x29, 0xf4}, {0x28, 0x36}, 05459 {0x2d, 0x78}, {0x2c, 0xba}, {0x2e, 0xfc}, {0x2f, 0x3e}, 05460 {0x70, 0x80}, {0x71, 0x42}, {0x73, 0x04}, {0x72, 0xc6}, 05461 {0x77, 0x88}, {0x76, 0x4a}, {0x74, 0x0c}, {0x75, 0xce}, 05462 {0x7e, 0x90}, {0x7f, 0x52}, {0x7d, 0x14}, {0x7c, 0xd6}, 05463 {0x79, 0x98}, {0x78, 0x5a}, {0x7a, 0x1c}, {0x7b, 0xde}, 05464 {0x6c, 0xa0}, {0x6d, 0x62}, {0x6f, 0x24}, {0x6e, 0xe6}, 05465 {0x6b, 0xa8}, {0x6a, 0x6a}, {0x68, 0x2c}, {0x69, 0xee}, 05466 {0x62, 0xb0}, {0x63, 0x72}, {0x61, 0x34}, {0x60, 0xf6}, 05467 {0x65, 0xb8}, {0x64, 0x7a}, {0x66, 0x3c}, {0x67, 0xfe}, 05468 {0x48, 0xc0}, {0x49, 0x02}, {0x4b, 0x44}, {0x4a, 0x86}, 05469 {0x4f, 0xc8}, {0x4e, 0x0a}, {0x4c, 0x4c}, {0x4d, 0x8e}, 05470 {0x46, 0xd0}, {0x47, 0x12}, {0x45, 0x54}, {0x44, 0x96}, 05471 {0x41, 0xd8}, {0x40, 0x1a}, {0x42, 0x5c}, {0x43, 0x9e}, 05472 {0x54, 0xe0}, {0x55, 0x22}, {0x57, 0x64}, {0x56, 0xa6}, 05473 {0x53, 0xe8}, {0x52, 0x2a}, {0x50, 0x6c}, {0x51, 0xae}, 05474 {0x5a, 0xf0}, {0x5b, 0x32}, {0x59, 0x74}, {0x58, 0xb6}, 05475 {0x5d, 0xf8}, {0x5c, 0x3a}, {0x5e, 0x7c}, {0x5f, 0xbe}, 05476 {0xe1, 0x00}, {0xe0, 0xc2}, {0xe2, 0x84}, {0xe3, 0x46}, 05477 {0xe6, 0x08}, {0xe7, 0xca}, {0xe5, 0x8c}, {0xe4, 0x4e}, 05478 {0xef, 0x10}, {0xee, 0xd2}, {0xec, 0x94}, {0xed, 0x56}, 05479 {0xe8, 0x18}, {0xe9, 0xda}, {0xeb, 0x9c}, {0xea, 0x5e}, 05480 {0xfd, 0x20}, {0xfc, 0xe2}, {0xfe, 0xa4}, {0xff, 0x66}, 05481 {0xfa, 0x28}, {0xfb, 0xea}, {0xf9, 0xac}, {0xf8, 0x6e}, 05482 {0xf3, 0x30}, {0xf2, 0xf2}, {0xf0, 0xb4}, {0xf1, 0x76}, 05483 {0xf4, 0x38}, {0xf5, 0xfa}, {0xf7, 0xbc}, {0xf6, 0x7e}, 05484 {0xd9, 0x40}, {0xd8, 0x82}, {0xda, 0xc4}, {0xdb, 0x06}, 05485 {0xde, 0x48}, {0xdf, 0x8a}, {0xdd, 0xcc}, {0xdc, 0x0e}, 05486 {0xd7, 0x50}, {0xd6, 0x92}, {0xd4, 0xd4}, {0xd5, 0x16}, 05487 {0xd0, 0x58}, {0xd1, 0x9a}, {0xd3, 0xdc}, {0xd2, 0x1e}, 05488 {0xc5, 0x60}, {0xc4, 0xa2}, {0xc6, 0xe4}, {0xc7, 0x26}, 05489 {0xc2, 0x68}, {0xc3, 0xaa}, {0xc1, 0xec}, {0xc0, 0x2e}, 05490 {0xcb, 0x70}, {0xca, 0xb2}, {0xc8, 0xf4}, {0xc9, 0x36}, 05491 {0xcc, 0x78}, {0xcd, 0xba}, {0xcf, 0xfc}, {0xce, 0x3e}, 05492 {0x91, 0x80}, {0x90, 0x42}, {0x92, 0x04}, {0x93, 0xc6}, 05493 {0x96, 0x88}, {0x97, 0x4a}, {0x95, 0x0c}, {0x94, 0xce}, 05494 {0x9f, 0x90}, {0x9e, 0x52}, {0x9c, 0x14}, {0x9d, 0xd6}, 05495 {0x98, 0x98}, {0x99, 0x5a}, {0x9b, 0x1c}, {0x9a, 0xde}, 05496 {0x8d, 0xa0}, {0x8c, 0x62}, {0x8e, 0x24}, {0x8f, 0xe6}, 05497 {0x8a, 0xa8}, {0x8b, 0x6a}, {0x89, 0x2c}, {0x88, 0xee}, 05498 {0x83, 0xb0}, {0x82, 0x72}, {0x80, 0x34}, {0x81, 0xf6}, 05499 {0x84, 0xb8}, {0x85, 0x7a}, {0x87, 0x3c}, {0x86, 0xfe}, 05500 {0xa9, 0xc0}, {0xa8, 0x02}, {0xaa, 0x44}, {0xab, 0x86}, 05501 {0xae, 0xc8}, {0xaf, 0x0a}, {0xad, 0x4c}, {0xac, 0x8e}, 05502 {0xa7, 0xd0}, {0xa6, 0x12}, {0xa4, 0x54}, {0xa5, 0x96}, 05503 {0xa0, 0xd8}, {0xa1, 0x1a}, {0xa3, 0x5c}, {0xa2, 0x9e}, 05504 {0xb5, 0xe0}, {0xb4, 0x22}, {0xb6, 0x64}, {0xb7, 0xa6}, 05505 {0xb2, 0xe8}, {0xb3, 0x2a}, {0xb1, 0x6c}, {0xb0, 0xae}, 05506 {0xbb, 0xf0}, {0xba, 0x32}, {0xb8, 0x74}, {0xb9, 0xb6}, 05507 {0xbc, 0xf8}, {0xbd, 0x3a}, {0xbf, 0x7c}, {0xbe, 0xbe} }; 05508 05509 05510 static void GMULT(byte *x, byte m[256][AES_BLOCK_SIZE]) 05511 { 05512 int i, j; 05513 byte Z[AES_BLOCK_SIZE]; 05514 byte a; 05515 05516 XMEMSET(Z, 0, sizeof(Z)); 05517 05518 for (i = 15; i > 0; i--) { 05519 xorbuf(Z, m[x[i]], AES_BLOCK_SIZE); 05520 a = Z[15]; 05521 05522 for (j = 15; j > 0; j--) { 05523 Z[j] = Z[j-1]; 05524 } 05525 05526 Z[0] = R[a][0]; 05527 Z[1] ^= R[a][1]; 05528 } 05529 xorbuf(Z, m[x[0]], AES_BLOCK_SIZE); 05530 05531 XMEMCPY(x, Z, AES_BLOCK_SIZE); 05532 } 05533 05534 05535 void GHASH(Aes* aes, const byte* a, word32 aSz, const byte* c, 05536 word32 cSz, byte* s, word32 sSz) 05537 { 05538 byte x[AES_BLOCK_SIZE]; 05539 byte scratch[AES_BLOCK_SIZE]; 05540 word32 blocks, partial; 05541 05542 XMEMSET(x, 0, AES_BLOCK_SIZE); 05543 05544 /* Hash in A, the Additional Authentication Data */ 05545 if (aSz != 0 && a != NULL) { 05546 blocks = aSz / AES_BLOCK_SIZE; 05547 partial = aSz % AES_BLOCK_SIZE; 05548 while (blocks--) { 05549 xorbuf(x, a, AES_BLOCK_SIZE); 05550 GMULT(x, aes->M0); 05551 a += AES_BLOCK_SIZE; 05552 } 05553 if (partial != 0) { 05554 XMEMSET(scratch, 0, AES_BLOCK_SIZE); 05555 XMEMCPY(scratch, a, partial); 05556 xorbuf(x, scratch, AES_BLOCK_SIZE); 05557 GMULT(x, aes->M0); 05558 } 05559 } 05560 05561 /* Hash in C, the Ciphertext */ 05562 if (cSz != 0 && c != NULL) { 05563 blocks = cSz / AES_BLOCK_SIZE; 05564 partial = cSz % AES_BLOCK_SIZE; 05565 while (blocks--) { 05566 xorbuf(x, c, AES_BLOCK_SIZE); 05567 GMULT(x, aes->M0); 05568 c += AES_BLOCK_SIZE; 05569 } 05570 if (partial != 0) { 05571 XMEMSET(scratch, 0, AES_BLOCK_SIZE); 05572 XMEMCPY(scratch, c, partial); 05573 xorbuf(x, scratch, AES_BLOCK_SIZE); 05574 GMULT(x, aes->M0); 05575 } 05576 } 05577 05578 /* Hash in the lengths of A and C in bits */ 05579 FlattenSzInBits(&scratch[0], aSz); 05580 FlattenSzInBits(&scratch[8], cSz); 05581 xorbuf(x, scratch, AES_BLOCK_SIZE); 05582 GMULT(x, aes->M0); 05583 05584 /* Copy the result into s. */ 05585 XMEMCPY(s, x, sSz); 05586 } 05587 05588 /* end GCM_TABLE */ 05589 #elif defined(WORD64_AVAILABLE) && !defined(GCM_WORD32) 05590 05591 #if !defined(FREESCALE_LTC_AES_GCM) 05592 static void GMULT(word64* X, word64* Y) 05593 { 05594 word64 Z[2] = {0,0}; 05595 word64 V[2]; 05596 int i, j; 05597 V[0] = X[0]; V[1] = X[1]; 05598 05599 for (i = 0; i < 2; i++) 05600 { 05601 word64 y = Y[i]; 05602 for (j = 0; j < 64; j++) 05603 { 05604 if (y & 0x8000000000000000ULL) { 05605 Z[0] ^= V[0]; 05606 Z[1] ^= V[1]; 05607 } 05608 05609 if (V[1] & 0x0000000000000001) { 05610 V[1] >>= 1; 05611 V[1] |= ((V[0] & 0x0000000000000001) ? 05612 0x8000000000000000ULL : 0); 05613 V[0] >>= 1; 05614 V[0] ^= 0xE100000000000000ULL; 05615 } 05616 else { 05617 V[1] >>= 1; 05618 V[1] |= ((V[0] & 0x0000000000000001) ? 05619 0x8000000000000000ULL : 0); 05620 V[0] >>= 1; 05621 } 05622 y <<= 1; 05623 } 05624 } 05625 X[0] = Z[0]; 05626 X[1] = Z[1]; 05627 } 05628 05629 05630 void GHASH(Aes* aes, const byte* a, word32 aSz, const byte* c, 05631 word32 cSz, byte* s, word32 sSz) 05632 { 05633 word64 x[2] = {0,0}; 05634 word32 blocks, partial; 05635 word64 bigH[2]; 05636 05637 XMEMCPY(bigH, aes->H, AES_BLOCK_SIZE); 05638 #ifdef LITTLE_ENDIAN_ORDER 05639 ByteReverseWords64(bigH, bigH, AES_BLOCK_SIZE); 05640 #endif 05641 05642 /* Hash in A, the Additional Authentication Data */ 05643 if (aSz != 0 && a != NULL) { 05644 word64 bigA[2]; 05645 blocks = aSz / AES_BLOCK_SIZE; 05646 partial = aSz % AES_BLOCK_SIZE; 05647 while (blocks--) { 05648 XMEMCPY(bigA, a, AES_BLOCK_SIZE); 05649 #ifdef LITTLE_ENDIAN_ORDER 05650 ByteReverseWords64(bigA, bigA, AES_BLOCK_SIZE); 05651 #endif 05652 x[0] ^= bigA[0]; 05653 x[1] ^= bigA[1]; 05654 GMULT(x, bigH); 05655 a += AES_BLOCK_SIZE; 05656 } 05657 if (partial != 0) { 05658 XMEMSET(bigA, 0, AES_BLOCK_SIZE); 05659 XMEMCPY(bigA, a, partial); 05660 #ifdef LITTLE_ENDIAN_ORDER 05661 ByteReverseWords64(bigA, bigA, AES_BLOCK_SIZE); 05662 #endif 05663 x[0] ^= bigA[0]; 05664 x[1] ^= bigA[1]; 05665 GMULT(x, bigH); 05666 } 05667 #ifdef OPENSSL_EXTRA 05668 /* store AAD partial tag for next call */ 05669 aes->aadH[0] = (word32)((x[0] & 0xFFFFFFFF00000000) >> 32); 05670 aes->aadH[1] = (word32)(x[0] & 0xFFFFFFFF); 05671 aes->aadH[2] = (word32)((x[1] & 0xFFFFFFFF00000000) >> 32); 05672 aes->aadH[3] = (word32)(x[1] & 0xFFFFFFFF); 05673 #endif 05674 } 05675 05676 /* Hash in C, the Ciphertext */ 05677 if (cSz != 0 && c != NULL) { 05678 word64 bigC[2]; 05679 blocks = cSz / AES_BLOCK_SIZE; 05680 partial = cSz % AES_BLOCK_SIZE; 05681 #ifdef OPENSSL_EXTRA 05682 /* Start from last AAD partial tag */ 05683 if(aes->aadLen) { 05684 x[0] = ((word64)aes->aadH[0]) << 32 | aes->aadH[1]; 05685 x[1] = ((word64)aes->aadH[2]) << 32 | aes->aadH[3]; 05686 } 05687 #endif 05688 while (blocks--) { 05689 XMEMCPY(bigC, c, AES_BLOCK_SIZE); 05690 #ifdef LITTLE_ENDIAN_ORDER 05691 ByteReverseWords64(bigC, bigC, AES_BLOCK_SIZE); 05692 #endif 05693 x[0] ^= bigC[0]; 05694 x[1] ^= bigC[1]; 05695 GMULT(x, bigH); 05696 c += AES_BLOCK_SIZE; 05697 } 05698 if (partial != 0) { 05699 XMEMSET(bigC, 0, AES_BLOCK_SIZE); 05700 XMEMCPY(bigC, c, partial); 05701 #ifdef LITTLE_ENDIAN_ORDER 05702 ByteReverseWords64(bigC, bigC, AES_BLOCK_SIZE); 05703 #endif 05704 x[0] ^= bigC[0]; 05705 x[1] ^= bigC[1]; 05706 GMULT(x, bigH); 05707 } 05708 } 05709 05710 /* Hash in the lengths in bits of A and C */ 05711 { 05712 word64 len[2]; 05713 len[0] = aSz; len[1] = cSz; 05714 #ifdef OPENSSL_EXTRA 05715 if (aes->aadLen) 05716 len[0] = (word64)aes->aadLen; 05717 #endif 05718 /* Lengths are in bytes. Convert to bits. */ 05719 len[0] *= 8; 05720 len[1] *= 8; 05721 05722 x[0] ^= len[0]; 05723 x[1] ^= len[1]; 05724 GMULT(x, bigH); 05725 } 05726 #ifdef LITTLE_ENDIAN_ORDER 05727 ByteReverseWords64(x, x, AES_BLOCK_SIZE); 05728 #endif 05729 XMEMCPY(s, x, sSz); 05730 } 05731 #endif /* !FREESCALE_LTC_AES_GCM */ 05732 05733 /* end defined(WORD64_AVAILABLE) && !defined(GCM_WORD32) */ 05734 #else /* GCM_WORD32 */ 05735 05736 static void GMULT(word32* X, word32* Y) 05737 { 05738 word32 Z[4] = {0,0,0,0}; 05739 word32 V[4]; 05740 int i, j; 05741 05742 V[0] = X[0]; V[1] = X[1]; V[2] = X[2]; V[3] = X[3]; 05743 05744 for (i = 0; i < 4; i++) 05745 { 05746 word32 y = Y[i]; 05747 for (j = 0; j < 32; j++) 05748 { 05749 if (y & 0x80000000) { 05750 Z[0] ^= V[0]; 05751 Z[1] ^= V[1]; 05752 Z[2] ^= V[2]; 05753 Z[3] ^= V[3]; 05754 } 05755 05756 if (V[3] & 0x00000001) { 05757 V[3] >>= 1; 05758 V[3] |= ((V[2] & 0x00000001) ? 0x80000000 : 0); 05759 V[2] >>= 1; 05760 V[2] |= ((V[1] & 0x00000001) ? 0x80000000 : 0); 05761 V[1] >>= 1; 05762 V[1] |= ((V[0] & 0x00000001) ? 0x80000000 : 0); 05763 V[0] >>= 1; 05764 V[0] ^= 0xE1000000; 05765 } else { 05766 V[3] >>= 1; 05767 V[3] |= ((V[2] & 0x00000001) ? 0x80000000 : 0); 05768 V[2] >>= 1; 05769 V[2] |= ((V[1] & 0x00000001) ? 0x80000000 : 0); 05770 V[1] >>= 1; 05771 V[1] |= ((V[0] & 0x00000001) ? 0x80000000 : 0); 05772 V[0] >>= 1; 05773 } 05774 y <<= 1; 05775 } 05776 } 05777 X[0] = Z[0]; 05778 X[1] = Z[1]; 05779 X[2] = Z[2]; 05780 X[3] = Z[3]; 05781 } 05782 05783 05784 void GHASH(Aes* aes, const byte* a, word32 aSz, const byte* c, 05785 word32 cSz, byte* s, word32 sSz) 05786 { 05787 word32 x[4] = {0,0,0,0}; 05788 word32 blocks, partial; 05789 word32 bigH[4]; 05790 05791 XMEMCPY(bigH, aes->H, AES_BLOCK_SIZE); 05792 #ifdef LITTLE_ENDIAN_ORDER 05793 ByteReverseWords(bigH, bigH, AES_BLOCK_SIZE); 05794 #endif 05795 05796 /* Hash in A, the Additional Authentication Data */ 05797 if (aSz != 0 && a != NULL) { 05798 word32 bigA[4]; 05799 blocks = aSz / AES_BLOCK_SIZE; 05800 partial = aSz % AES_BLOCK_SIZE; 05801 while (blocks--) { 05802 XMEMCPY(bigA, a, AES_BLOCK_SIZE); 05803 #ifdef LITTLE_ENDIAN_ORDER 05804 ByteReverseWords(bigA, bigA, AES_BLOCK_SIZE); 05805 #endif 05806 x[0] ^= bigA[0]; 05807 x[1] ^= bigA[1]; 05808 x[2] ^= bigA[2]; 05809 x[3] ^= bigA[3]; 05810 GMULT(x, bigH); 05811 a += AES_BLOCK_SIZE; 05812 } 05813 if (partial != 0) { 05814 XMEMSET(bigA, 0, AES_BLOCK_SIZE); 05815 XMEMCPY(bigA, a, partial); 05816 #ifdef LITTLE_ENDIAN_ORDER 05817 ByteReverseWords(bigA, bigA, AES_BLOCK_SIZE); 05818 #endif 05819 x[0] ^= bigA[0]; 05820 x[1] ^= bigA[1]; 05821 x[2] ^= bigA[2]; 05822 x[3] ^= bigA[3]; 05823 GMULT(x, bigH); 05824 } 05825 } 05826 05827 /* Hash in C, the Ciphertext */ 05828 if (cSz != 0 && c != NULL) { 05829 word32 bigC[4]; 05830 blocks = cSz / AES_BLOCK_SIZE; 05831 partial = cSz % AES_BLOCK_SIZE; 05832 while (blocks--) { 05833 XMEMCPY(bigC, c, AES_BLOCK_SIZE); 05834 #ifdef LITTLE_ENDIAN_ORDER 05835 ByteReverseWords(bigC, bigC, AES_BLOCK_SIZE); 05836 #endif 05837 x[0] ^= bigC[0]; 05838 x[1] ^= bigC[1]; 05839 x[2] ^= bigC[2]; 05840 x[3] ^= bigC[3]; 05841 GMULT(x, bigH); 05842 c += AES_BLOCK_SIZE; 05843 } 05844 if (partial != 0) { 05845 XMEMSET(bigC, 0, AES_BLOCK_SIZE); 05846 XMEMCPY(bigC, c, partial); 05847 #ifdef LITTLE_ENDIAN_ORDER 05848 ByteReverseWords(bigC, bigC, AES_BLOCK_SIZE); 05849 #endif 05850 x[0] ^= bigC[0]; 05851 x[1] ^= bigC[1]; 05852 x[2] ^= bigC[2]; 05853 x[3] ^= bigC[3]; 05854 GMULT(x, bigH); 05855 } 05856 } 05857 05858 /* Hash in the lengths in bits of A and C */ 05859 { 05860 word32 len[4]; 05861 05862 /* Lengths are in bytes. Convert to bits. */ 05863 len[0] = (aSz >> (8*sizeof(aSz) - 3)); 05864 len[1] = aSz << 3; 05865 len[2] = (cSz >> (8*sizeof(cSz) - 3)); 05866 len[3] = cSz << 3; 05867 05868 x[0] ^= len[0]; 05869 x[1] ^= len[1]; 05870 x[2] ^= len[2]; 05871 x[3] ^= len[3]; 05872 GMULT(x, bigH); 05873 } 05874 #ifdef LITTLE_ENDIAN_ORDER 05875 ByteReverseWords(x, x, AES_BLOCK_SIZE); 05876 #endif 05877 XMEMCPY(s, x, sSz); 05878 } 05879 05880 #endif /* end GCM_WORD32 */ 05881 05882 05883 #if !defined(WOLFSSL_XILINX_CRYPT) && !defined(WOLFSSL_AFALG_XILINX_AES) 05884 #ifdef FREESCALE_LTC_AES_GCM 05885 int wc_AesGcmEncrypt(Aes* aes, byte* out, const byte* in, word32 sz, 05886 const byte* iv, word32 ivSz, 05887 byte* authTag, word32 authTagSz, 05888 const byte* authIn, word32 authInSz) 05889 { 05890 status_t status; 05891 word32 keySize; 05892 05893 /* argument checks */ 05894 if (aes == NULL || authTagSz > AES_BLOCK_SIZE || ivSz == 0) { 05895 return BAD_FUNC_ARG; 05896 } 05897 05898 if (authTagSz < WOLFSSL_MIN_AUTH_TAG_SZ) { 05899 WOLFSSL_MSG("GcmEncrypt authTagSz too small error"); 05900 return BAD_FUNC_ARG; 05901 } 05902 05903 status = wc_AesGetKeySize(aes, &keySize); 05904 if (status) 05905 return status; 05906 05907 status = LTC_AES_EncryptTagGcm(LTC_BASE, in, out, sz, iv, ivSz, 05908 authIn, authInSz, (byte*)aes->key, keySize, authTag, authTagSz); 05909 05910 return (status == kStatus_Success) ? 0 : AES_GCM_AUTH_E; 05911 } 05912 05913 #else 05914 05915 #ifdef STM32_CRYPTO_AES_GCM 05916 05917 /* this function supports inline encrypt */ 05918 static int wc_AesGcmEncrypt_STM32(Aes* aes, byte* out, const byte* in, word32 sz, 05919 const byte* iv, word32 ivSz, 05920 byte* authTag, word32 authTagSz, 05921 const byte* authIn, word32 authInSz) 05922 { 05923 int ret; 05924 #ifdef WOLFSSL_STM32_CUBEMX 05925 CRYP_HandleTypeDef hcryp; 05926 #else 05927 word32 keyCopy[AES_256_KEY_SIZE/sizeof(word32)]; 05928 #endif 05929 word32 keySize; 05930 int status = HAL_OK; 05931 word32 blocks = sz / AES_BLOCK_SIZE; 05932 word32 partial = sz % AES_BLOCK_SIZE; 05933 byte tag[AES_BLOCK_SIZE]; 05934 byte partialBlock[AES_BLOCK_SIZE]; 05935 byte ctr[AES_BLOCK_SIZE]; 05936 byte* authInPadded = NULL; 05937 int authPadSz; 05938 05939 ret = wc_AesGetKeySize(aes, &keySize); 05940 if (ret != 0) 05941 return ret; 05942 05943 #ifdef WOLFSSL_STM32_CUBEMX 05944 ret = wc_Stm32_Aes_Init(aes, &hcryp); 05945 if (ret != 0) 05946 return ret; 05947 #endif 05948 05949 ret = wolfSSL_CryptHwMutexLock(); 05950 if (ret != 0) { 05951 return ret; 05952 } 05953 05954 XMEMSET(ctr, 0, AES_BLOCK_SIZE); 05955 if (ivSz == GCM_NONCE_MID_SZ) { 05956 XMEMCPY(ctr, iv, ivSz); 05957 ctr[AES_BLOCK_SIZE - 1] = 1; 05958 } 05959 else { 05960 GHASH(aes, NULL, 0, iv, ivSz, ctr, AES_BLOCK_SIZE); 05961 } 05962 /* Hardware requires counter + 1 */ 05963 IncrementGcmCounter(ctr); 05964 05965 if (authInSz == 0 || (authInSz % AES_BLOCK_SIZE) != 0) { 05966 /* Need to pad the AAD to a full block with zeros. */ 05967 authPadSz = ((authInSz / AES_BLOCK_SIZE) + 1) * AES_BLOCK_SIZE; 05968 authInPadded = (byte*)XMALLOC(authPadSz, aes->heap, 05969 DYNAMIC_TYPE_TMP_BUFFER); 05970 if (authInPadded == NULL) { 05971 wolfSSL_CryptHwMutexUnLock(); 05972 return MEMORY_E; 05973 } 05974 XMEMSET(authInPadded, 0, authPadSz); 05975 XMEMCPY(authInPadded, authIn, authInSz); 05976 } else { 05977 authPadSz = authInSz; 05978 authInPadded = (byte*)authIn; 05979 } 05980 05981 #ifdef WOLFSSL_STM32_CUBEMX 05982 hcryp.Init.pInitVect = (STM_CRYPT_TYPE*)ctr; 05983 hcryp.Init.Header = (STM_CRYPT_TYPE*)authInPadded; 05984 hcryp.Init.HeaderSize = authInSz; 05985 05986 #ifdef STM32_CRYPTO_AES_ONLY 05987 /* Set the CRYP parameters */ 05988 hcryp.Init.ChainingMode = CRYP_CHAINMODE_AES_GCM_GMAC; 05989 hcryp.Init.OperatingMode = CRYP_ALGOMODE_ENCRYPT; 05990 hcryp.Init.GCMCMACPhase = CRYP_INIT_PHASE; 05991 HAL_CRYP_Init(&hcryp); 05992 05993 /* GCM init phase */ 05994 status = HAL_CRYPEx_AES_Auth(&hcryp, NULL, 0, NULL, STM32_HAL_TIMEOUT); 05995 if (status == HAL_OK) { 05996 /* GCM header phase */ 05997 hcryp.Init.GCMCMACPhase = CRYP_HEADER_PHASE; 05998 status = HAL_CRYPEx_AES_Auth(&hcryp, NULL, 0, NULL, STM32_HAL_TIMEOUT); 05999 } 06000 if (status == HAL_OK) { 06001 /* GCM payload phase - blocks */ 06002 hcryp.Init.GCMCMACPhase = CRYP_PAYLOAD_PHASE; 06003 if (blocks) { 06004 status = HAL_CRYPEx_AES_Auth(&hcryp, (byte*)in, 06005 (blocks * AES_BLOCK_SIZE), out, STM32_HAL_TIMEOUT); 06006 } 06007 } 06008 if (status == HAL_OK && (partial != 0 || blocks == 0)) { 06009 /* GCM payload phase - partial remainder */ 06010 XMEMSET(partialBlock, 0, sizeof(partialBlock)); 06011 XMEMCPY(partialBlock, in + (blocks * AES_BLOCK_SIZE), partial); 06012 status = HAL_CRYPEx_AES_Auth(&hcryp, partialBlock, partial, 06013 partialBlock, STM32_HAL_TIMEOUT); 06014 XMEMCPY(out + (blocks * AES_BLOCK_SIZE), partialBlock, partial); 06015 } 06016 if (status == HAL_OK) { 06017 /* GCM final phase */ 06018 hcryp.Init.GCMCMACPhase = CRYP_FINAL_PHASE; 06019 status = HAL_CRYPEx_AES_Auth(&hcryp, NULL, sz, tag, STM32_HAL_TIMEOUT); 06020 } 06021 #elif defined(STM32_HAL_V2) 06022 hcryp.Init.Algorithm = CRYP_AES_GCM; 06023 ByteReverseWords((word32*)partialBlock, (word32*)ctr, AES_BLOCK_SIZE); 06024 hcryp.Init.pInitVect = (STM_CRYPT_TYPE*)partialBlock; 06025 HAL_CRYP_Init(&hcryp); 06026 06027 /* GCM payload phase - can handle partial blocks */ 06028 status = HAL_CRYP_Encrypt(&hcryp, (uint32_t*)in, 06029 (blocks * AES_BLOCK_SIZE) + partial, (uint32_t*)out, STM32_HAL_TIMEOUT); 06030 if (status == HAL_OK) { 06031 /* Compute the authTag */ 06032 status = HAL_CRYPEx_AESGCM_GenerateAuthTAG(&hcryp, (uint32_t*)tag, 06033 STM32_HAL_TIMEOUT); 06034 } 06035 #else 06036 HAL_CRYP_Init(&hcryp); 06037 if (blocks) { 06038 /* GCM payload phase - blocks */ 06039 status = HAL_CRYPEx_AESGCM_Encrypt(&hcryp, (byte*)in, 06040 (blocks * AES_BLOCK_SIZE), out, STM32_HAL_TIMEOUT); 06041 } 06042 if (status == HAL_OK && (partial != 0 || blocks == 0)) { 06043 /* GCM payload phase - partial remainder */ 06044 XMEMSET(partialBlock, 0, sizeof(partialBlock)); 06045 XMEMCPY(partialBlock, in + (blocks * AES_BLOCK_SIZE), partial); 06046 status = HAL_CRYPEx_AESGCM_Encrypt(&hcryp, partialBlock, partial, 06047 partialBlock, STM32_HAL_TIMEOUT); 06048 XMEMCPY(out + (blocks * AES_BLOCK_SIZE), partialBlock, partial); 06049 } 06050 if (status == HAL_OK) { 06051 /* Compute the authTag */ 06052 status = HAL_CRYPEx_AESGCM_Finish(&hcryp, sz, tag, STM32_HAL_TIMEOUT); 06053 } 06054 #endif 06055 06056 if (status != HAL_OK) 06057 ret = AES_GCM_AUTH_E; 06058 HAL_CRYP_DeInit(&hcryp); 06059 06060 #else /* STD_PERI_LIB */ 06061 ByteReverseWords(keyCopy, (word32*)aes->key, keySize); 06062 status = CRYP_AES_GCM(MODE_ENCRYPT, (uint8_t*)ctr, 06063 (uint8_t*)keyCopy, keySize * 8, 06064 (uint8_t*)in, sz, 06065 (uint8_t*)authInPadded, authInSz, 06066 (uint8_t*)out, tag); 06067 if (status != SUCCESS) 06068 ret = AES_GCM_AUTH_E; 06069 #endif /* WOLFSSL_STM32_CUBEMX */ 06070 06071 if (ret == 0) { 06072 /* return authTag */ 06073 if (authTag) { 06074 /* STM32 GCM won't compute Auth correctly for partial or 06075 when IV != 12, so use software here */ 06076 if (sz == 0 || partial != 0 || ivSz != GCM_NONCE_MID_SZ) { 06077 DecrementGcmCounter(ctr); /* hardware requires +1, so subtract it */ 06078 GHASH(aes, authIn, authInSz, out, sz, authTag, authTagSz); 06079 wc_AesEncrypt(aes, ctr, tag); 06080 xorbuf(authTag, tag, authTagSz); 06081 } 06082 else { 06083 XMEMCPY(authTag, tag, authTagSz); 06084 } 06085 } 06086 } 06087 06088 /* Free memory if not a multiple of AES_BLOCK_SZ */ 06089 if (authInPadded != authIn) { 06090 XFREE(authInPadded, aes->heap, DYNAMIC_TYPE_TMP_BUFFER); 06091 } 06092 06093 wolfSSL_CryptHwMutexUnLock(); 06094 06095 return ret; 06096 } 06097 06098 #endif /* STM32_CRYPTO_AES_GCM */ 06099 06100 #ifdef WOLFSSL_AESNI 06101 int AES_GCM_encrypt_C(Aes* aes, byte* out, const byte* in, word32 sz, 06102 const byte* iv, word32 ivSz, 06103 byte* authTag, word32 authTagSz, 06104 const byte* authIn, word32 authInSz); 06105 #else 06106 static 06107 #endif 06108 int AES_GCM_encrypt_C(Aes* aes, byte* out, const byte* in, word32 sz, 06109 const byte* iv, word32 ivSz, 06110 byte* authTag, word32 authTagSz, 06111 const byte* authIn, word32 authInSz) 06112 { 06113 int ret = 0; 06114 word32 blocks = sz / AES_BLOCK_SIZE; 06115 word32 partial = sz % AES_BLOCK_SIZE; 06116 const byte* p = in; 06117 byte* c = out; 06118 byte counter[AES_BLOCK_SIZE]; 06119 byte initialCounter[AES_BLOCK_SIZE]; 06120 byte *ctr; 06121 byte scratch[AES_BLOCK_SIZE]; 06122 #ifdef OPENSSL_EXTRA 06123 word32 aadTemp; 06124 #endif 06125 ctr = counter; 06126 XMEMSET(initialCounter, 0, AES_BLOCK_SIZE); 06127 XMEMSET(scratch, 0, AES_BLOCK_SIZE); 06128 if (ivSz == GCM_NONCE_MID_SZ) { 06129 XMEMCPY(initialCounter, iv, ivSz); 06130 initialCounter[AES_BLOCK_SIZE - 1] = 1; 06131 } 06132 else { 06133 #ifdef OPENSSL_EXTRA 06134 aadTemp = aes->aadLen; 06135 aes->aadLen = 0; 06136 #endif 06137 GHASH(aes, NULL, 0, iv, ivSz, initialCounter, AES_BLOCK_SIZE); 06138 #ifdef OPENSSL_EXTRA 06139 aes->aadLen = aadTemp; 06140 #endif 06141 } 06142 XMEMCPY(ctr, initialCounter, AES_BLOCK_SIZE); 06143 06144 #ifdef WOLFSSL_PIC32MZ_CRYPT 06145 if (blocks) { 06146 /* use initial IV for HW, but don't use it below */ 06147 XMEMCPY(aes->reg, ctr, AES_BLOCK_SIZE); 06148 06149 ret = wc_Pic32AesCrypt( 06150 aes->key, aes->keylen, aes->reg, AES_BLOCK_SIZE, 06151 out, in, (blocks * AES_BLOCK_SIZE), 06152 PIC32_ENCRYPTION, PIC32_ALGO_AES, PIC32_CRYPTOALGO_AES_GCM); 06153 if (ret != 0) 06154 return ret; 06155 } 06156 /* process remainder using partial handling */ 06157 #endif 06158 06159 #if defined(HAVE_AES_ECB) && !defined(WOLFSSL_PIC32MZ_CRYPT) 06160 /* some hardware acceleration can gain performance from doing AES encryption 06161 * of the whole buffer at once */ 06162 if (c != p && blocks > 0) { /* can not handle inline encryption */ 06163 while (blocks--) { 06164 IncrementGcmCounter(ctr); 06165 XMEMCPY(c, ctr, AES_BLOCK_SIZE); 06166 c += AES_BLOCK_SIZE; 06167 } 06168 06169 /* reset number of blocks and then do encryption */ 06170 blocks = sz / AES_BLOCK_SIZE; 06171 wc_AesEcbEncrypt(aes, out, out, AES_BLOCK_SIZE * blocks); 06172 xorbuf(out, p, AES_BLOCK_SIZE * blocks); 06173 p += AES_BLOCK_SIZE * blocks; 06174 } 06175 else 06176 #endif /* HAVE_AES_ECB && !WOLFSSL_PIC32MZ_CRYPT */ 06177 06178 while (blocks--) { 06179 IncrementGcmCounter(ctr); 06180 #if !defined(WOLFSSL_PIC32MZ_CRYPT) 06181 wc_AesEncrypt(aes, ctr, scratch); 06182 xorbuf(scratch, p, AES_BLOCK_SIZE); 06183 XMEMCPY(c, scratch, AES_BLOCK_SIZE); 06184 #endif 06185 p += AES_BLOCK_SIZE; 06186 c += AES_BLOCK_SIZE; 06187 } 06188 06189 if (partial != 0) { 06190 IncrementGcmCounter(ctr); 06191 wc_AesEncrypt(aes, ctr, scratch); 06192 xorbuf(scratch, p, partial); 06193 XMEMCPY(c, scratch, partial); 06194 } 06195 if (authTag) { 06196 GHASH(aes, authIn, authInSz, out, sz, authTag, authTagSz); 06197 wc_AesEncrypt(aes, initialCounter, scratch); 06198 xorbuf(authTag, scratch, authTagSz); 06199 #ifdef OPENSSL_EXTRA 06200 if (!in && !sz) 06201 /* store AAD size for next call */ 06202 aes->aadLen = authInSz; 06203 #endif 06204 } 06205 06206 return ret; 06207 } 06208 06209 /* Software AES - GCM Encrypt */ 06210 int wc_AesGcmEncrypt(Aes* aes, byte* out, const byte* in, word32 sz, 06211 const byte* iv, word32 ivSz, 06212 byte* authTag, word32 authTagSz, 06213 const byte* authIn, word32 authInSz) 06214 { 06215 /* argument checks */ 06216 if (aes == NULL || authTagSz > AES_BLOCK_SIZE || ivSz == 0) { 06217 return BAD_FUNC_ARG; 06218 } 06219 06220 if (authTagSz < WOLFSSL_MIN_AUTH_TAG_SZ) { 06221 WOLFSSL_MSG("GcmEncrypt authTagSz too small error"); 06222 return BAD_FUNC_ARG; 06223 } 06224 06225 #ifdef WOLF_CRYPTO_CB 06226 if (aes->devId != INVALID_DEVID) { 06227 int ret = wc_CryptoCb_AesGcmEncrypt(aes, out, in, sz, iv, ivSz, 06228 authTag, authTagSz, authIn, authInSz); 06229 if (ret != CRYPTOCB_UNAVAILABLE) 06230 return ret; 06231 /* fall-through when unavailable */ 06232 } 06233 #endif 06234 06235 #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_AES) 06236 /* if async and byte count above threshold */ 06237 /* only 12-byte IV is supported in HW */ 06238 if (aes->asyncDev.marker == WOLFSSL_ASYNC_MARKER_AES && 06239 sz >= WC_ASYNC_THRESH_AES_GCM && ivSz == GCM_NONCE_MID_SZ) { 06240 #if defined(HAVE_CAVIUM) 06241 #ifdef HAVE_CAVIUM_V 06242 if (authInSz == 20) { /* Nitrox V GCM is only working with 20 byte AAD */ 06243 return NitroxAesGcmEncrypt(aes, out, in, sz, 06244 (const byte*)aes->devKey, aes->keylen, iv, ivSz, 06245 authTag, authTagSz, authIn, authInSz); 06246 } 06247 #endif 06248 #elif defined(HAVE_INTEL_QA) 06249 return IntelQaSymAesGcmEncrypt(&aes->asyncDev, out, in, sz, 06250 (const byte*)aes->devKey, aes->keylen, iv, ivSz, 06251 authTag, authTagSz, authIn, authInSz); 06252 #else /* WOLFSSL_ASYNC_CRYPT_TEST */ 06253 if (wc_AsyncTestInit(&aes->asyncDev, ASYNC_TEST_AES_GCM_ENCRYPT)) { 06254 WC_ASYNC_TEST* testDev = &aes->asyncDev.test; 06255 testDev->aes.aes = aes; 06256 testDev->aes.out = out; 06257 testDev->aes.in = in; 06258 testDev->aes.sz = sz; 06259 testDev->aes.iv = iv; 06260 testDev->aes.ivSz = ivSz; 06261 testDev->aes.authTag = authTag; 06262 testDev->aes.authTagSz = authTagSz; 06263 testDev->aes.authIn = authIn; 06264 testDev->aes.authInSz = authInSz; 06265 return WC_PENDING_E; 06266 } 06267 #endif 06268 } 06269 #endif /* WOLFSSL_ASYNC_CRYPT */ 06270 06271 #ifdef STM32_CRYPTO_AES_GCM 06272 /* The STM standard peripheral library API's doesn't support partial blocks */ 06273 #ifdef STD_PERI_LIB 06274 if (partial == 0) 06275 #endif 06276 { 06277 return wc_AesGcmEncrypt_STM32( 06278 aes, out, in, sz, iv, ivSz, 06279 authTag, authTagSz, authIn, authInSz); 06280 } 06281 #endif /* STM32_CRYPTO_AES_GCM */ 06282 06283 #ifdef WOLFSSL_AESNI 06284 #ifdef HAVE_INTEL_AVX2 06285 if (IS_INTEL_AVX2(intel_flags)) { 06286 AES_GCM_encrypt_avx2(in, out, authIn, iv, authTag, sz, authInSz, ivSz, 06287 authTagSz, (const byte*)aes->key, aes->rounds); 06288 return 0; 06289 } 06290 else 06291 #endif 06292 #ifdef HAVE_INTEL_AVX1 06293 if (IS_INTEL_AVX1(intel_flags)) { 06294 AES_GCM_encrypt_avx1(in, out, authIn, iv, authTag, sz, authInSz, ivSz, 06295 authTagSz, (const byte*)aes->key, aes->rounds); 06296 return 0; 06297 } 06298 else 06299 #endif 06300 if (haveAESNI) { 06301 AES_GCM_encrypt(in, out, authIn, iv, authTag, sz, authInSz, ivSz, 06302 authTagSz, (const byte*)aes->key, aes->rounds); 06303 return 0; 06304 } 06305 else 06306 #endif 06307 { 06308 return AES_GCM_encrypt_C(aes, out, in, sz, iv, ivSz, authTag, authTagSz, 06309 authIn, authInSz); 06310 } 06311 } 06312 #endif 06313 06314 06315 06316 /* AES GCM Decrypt */ 06317 #if defined(HAVE_AES_DECRYPT) || defined(HAVE_AESGCM_DECRYPT) 06318 #ifdef FREESCALE_LTC_AES_GCM 06319 int wc_AesGcmDecrypt(Aes* aes, byte* out, const byte* in, word32 sz, 06320 const byte* iv, word32 ivSz, 06321 const byte* authTag, word32 authTagSz, 06322 const byte* authIn, word32 authInSz) 06323 { 06324 int ret; 06325 word32 keySize; 06326 status_t status; 06327 06328 /* argument checks */ 06329 /* If the sz is non-zero, both in and out must be set. If sz is 0, 06330 * in and out are don't cares, as this is is the GMAC case. */ 06331 if (aes == NULL || iv == NULL || (sz != 0 && (in == NULL || out == NULL)) || 06332 authTag == NULL || authTagSz > AES_BLOCK_SIZE || authTagSz == 0 || 06333 ivSz == 0) { 06334 06335 return BAD_FUNC_ARG; 06336 } 06337 06338 ret = wc_AesGetKeySize(aes, &keySize); 06339 if (ret != 0) { 06340 return ret; 06341 } 06342 06343 status = LTC_AES_DecryptTagGcm(LTC_BASE, in, out, sz, iv, ivSz, 06344 authIn, authInSz, (byte*)aes->key, keySize, authTag, authTagSz); 06345 06346 return (status == kStatus_Success) ? 0 : AES_GCM_AUTH_E; 06347 } 06348 06349 #else 06350 06351 #ifdef STM32_CRYPTO_AES_GCM 06352 /* this function supports inline decrypt */ 06353 static int wc_AesGcmDecrypt_STM32(Aes* aes, byte* out, 06354 const byte* in, word32 sz, 06355 const byte* iv, word32 ivSz, 06356 const byte* authTag, word32 authTagSz, 06357 const byte* authIn, word32 authInSz) 06358 { 06359 int ret; 06360 #ifdef WOLFSSL_STM32_CUBEMX 06361 CRYP_HandleTypeDef hcryp; 06362 #else 06363 word32 keyCopy[AES_256_KEY_SIZE/sizeof(word32)]; 06364 #endif 06365 word32 keySize; 06366 int status = HAL_OK; 06367 word32 blocks = sz / AES_BLOCK_SIZE; 06368 word32 partial = sz % AES_BLOCK_SIZE; 06369 byte tag[AES_BLOCK_SIZE]; 06370 byte partialBlock[AES_BLOCK_SIZE]; 06371 byte ctr[AES_BLOCK_SIZE]; 06372 byte* authInPadded = NULL; 06373 int authPadSz; 06374 06375 ret = wc_AesGetKeySize(aes, &keySize); 06376 if (ret != 0) 06377 return ret; 06378 06379 #ifdef WOLFSSL_STM32_CUBEMX 06380 ret = wc_Stm32_Aes_Init(aes, &hcryp); 06381 if (ret != 0) 06382 return ret; 06383 #endif 06384 06385 ret = wolfSSL_CryptHwMutexLock(); 06386 if (ret != 0) { 06387 return ret; 06388 } 06389 06390 XMEMSET(ctr, 0, AES_BLOCK_SIZE); 06391 if (ivSz == GCM_NONCE_MID_SZ) { 06392 XMEMCPY(ctr, iv, ivSz); 06393 ctr[AES_BLOCK_SIZE - 1] = 1; 06394 } 06395 else { 06396 GHASH(aes, NULL, 0, iv, ivSz, ctr, AES_BLOCK_SIZE); 06397 } 06398 /* Hardware requires counter + 1 */ 06399 IncrementGcmCounter(ctr); 06400 06401 if (authInSz == 0 || (authInSz % AES_BLOCK_SIZE) != 0) { 06402 /* Need to pad the AAD to a full block with zeros. */ 06403 authPadSz = ((authInSz / AES_BLOCK_SIZE) + 1) * AES_BLOCK_SIZE; 06404 authInPadded = (byte*)XMALLOC(authPadSz, aes->heap, 06405 DYNAMIC_TYPE_TMP_BUFFER); 06406 if (authInPadded == NULL) { 06407 wolfSSL_CryptHwMutexUnLock(); 06408 return MEMORY_E; 06409 } 06410 XMEMSET(authInPadded, 0, authPadSz); 06411 XMEMCPY(authInPadded, authIn, authInSz); 06412 } else { 06413 authPadSz = authInSz; 06414 authInPadded = (byte*)authIn; 06415 } 06416 06417 #ifdef WOLFSSL_STM32_CUBEMX 06418 hcryp.Init.pInitVect = (STM_CRYPT_TYPE*)ctr; 06419 hcryp.Init.Header = (STM_CRYPT_TYPE*)authInPadded; 06420 hcryp.Init.HeaderSize = authInSz; 06421 06422 #ifdef STM32_CRYPTO_AES_ONLY 06423 /* Set the CRYP parameters */ 06424 hcryp.Init.ChainingMode = CRYP_CHAINMODE_AES_GCM_GMAC; 06425 hcryp.Init.OperatingMode = CRYP_ALGOMODE_DECRYPT; 06426 hcryp.Init.GCMCMACPhase = CRYP_INIT_PHASE; 06427 HAL_CRYP_Init(&hcryp); 06428 06429 /* GCM init phase */ 06430 status = HAL_CRYPEx_AES_Auth(&hcryp, NULL, 0, NULL, STM32_HAL_TIMEOUT); 06431 if (status == HAL_OK) { 06432 /* GCM header phase */ 06433 hcryp.Init.GCMCMACPhase = CRYP_HEADER_PHASE; 06434 status = HAL_CRYPEx_AES_Auth(&hcryp, NULL, 0, NULL, STM32_HAL_TIMEOUT); 06435 } 06436 if (status == HAL_OK) { 06437 /* GCM payload phase - blocks */ 06438 hcryp.Init.GCMCMACPhase = CRYP_PAYLOAD_PHASE; 06439 if (blocks) { 06440 status = HAL_CRYPEx_AES_Auth(&hcryp, (byte*)in, 06441 (blocks * AES_BLOCK_SIZE), out, STM32_HAL_TIMEOUT); 06442 } 06443 } 06444 if (status == HAL_OK && (partial != 0 || blocks == 0)) { 06445 /* GCM payload phase - partial remainder */ 06446 XMEMSET(partialBlock, 0, sizeof(partialBlock)); 06447 XMEMCPY(partialBlock, in + (blocks * AES_BLOCK_SIZE), partial); 06448 status = HAL_CRYPEx_AES_Auth(&hcryp, partialBlock, partial, 06449 partialBlock, STM32_HAL_TIMEOUT); 06450 XMEMCPY(out + (blocks * AES_BLOCK_SIZE), partialBlock, partial); 06451 } 06452 if (status == HAL_OK) { 06453 /* GCM final phase */ 06454 hcryp.Init.GCMCMACPhase = CRYP_FINAL_PHASE; 06455 status = HAL_CRYPEx_AES_Auth(&hcryp, NULL, sz, tag, STM32_HAL_TIMEOUT); 06456 } 06457 #elif defined(STM32_HAL_V2) 06458 hcryp.Init.Algorithm = CRYP_AES_GCM; 06459 ByteReverseWords((word32*)partialBlock, (word32*)ctr, AES_BLOCK_SIZE); 06460 hcryp.Init.pInitVect = (STM_CRYPT_TYPE*)partialBlock; 06461 HAL_CRYP_Init(&hcryp); 06462 06463 /* GCM payload phase - can handle partial blocks */ 06464 status = HAL_CRYP_Decrypt(&hcryp, (uint32_t*)in, 06465 (blocks * AES_BLOCK_SIZE) + partial, (uint32_t*)out, STM32_HAL_TIMEOUT); 06466 if (status == HAL_OK) { 06467 /* Compute the authTag */ 06468 status = HAL_CRYPEx_AESGCM_GenerateAuthTAG(&hcryp, (uint32_t*)tag, 06469 STM32_HAL_TIMEOUT); 06470 } 06471 #else 06472 HAL_CRYP_Init(&hcryp); 06473 if (blocks) { 06474 /* GCM payload phase - blocks */ 06475 status = HAL_CRYPEx_AESGCM_Decrypt(&hcryp, (byte*)in, 06476 (blocks * AES_BLOCK_SIZE), out, STM32_HAL_TIMEOUT); 06477 } 06478 if (status == HAL_OK && (partial != 0 || blocks == 0)) { 06479 /* GCM payload phase - partial remainder */ 06480 XMEMSET(partialBlock, 0, sizeof(partialBlock)); 06481 XMEMCPY(partialBlock, in + (blocks * AES_BLOCK_SIZE), partial); 06482 status = HAL_CRYPEx_AESGCM_Decrypt(&hcryp, partialBlock, partial, 06483 partialBlock, STM32_HAL_TIMEOUT); 06484 XMEMCPY(out + (blocks * AES_BLOCK_SIZE), partialBlock, partial); 06485 } 06486 if (status == HAL_OK) { 06487 /* Compute the authTag */ 06488 status = HAL_CRYPEx_AESGCM_Finish(&hcryp, sz, tag, STM32_HAL_TIMEOUT); 06489 } 06490 #endif 06491 06492 if (status != HAL_OK) 06493 ret = AES_GCM_AUTH_E; 06494 06495 HAL_CRYP_DeInit(&hcryp); 06496 06497 #else /* STD_PERI_LIB */ 06498 ByteReverseWords(keyCopy, (word32*)aes->key, aes->keylen); 06499 06500 /* Input size and auth size need to be the actual sizes, even though 06501 * they are not block aligned, because this length (in bits) is used 06502 * in the final GHASH. */ 06503 status = CRYP_AES_GCM(MODE_DECRYPT, (uint8_t*)ctr, 06504 (uint8_t*)keyCopy, keySize * 8, 06505 (uint8_t*)in, sz, 06506 (uint8_t*)authInPadded, authInSz, 06507 (uint8_t*)out, tag); 06508 if (status != SUCCESS) 06509 ret = AES_GCM_AUTH_E; 06510 #endif /* WOLFSSL_STM32_CUBEMX */ 06511 06512 /* STM32 GCM hardware only supports IV of 12 bytes, so use software for auth */ 06513 if (sz == 0 || ivSz != GCM_NONCE_MID_SZ) { 06514 DecrementGcmCounter(ctr); /* hardware requires +1, so subtract it */ 06515 GHASH(aes, authIn, authInSz, in, sz, tag, sizeof(tag)); 06516 wc_AesEncrypt(aes, ctr, partialBlock); 06517 xorbuf(tag, partialBlock, sizeof(tag)); 06518 } 06519 06520 if (ConstantCompare(authTag, tag, authTagSz) != 0) { 06521 ret = AES_GCM_AUTH_E; 06522 } 06523 06524 /* Free memory if not a multiple of AES_BLOCK_SZ */ 06525 if (authInPadded != authIn) { 06526 XFREE(authInPadded, aes->heap, DYNAMIC_TYPE_TMP_BUFFER); 06527 } 06528 06529 wolfSSL_CryptHwMutexUnLock(); 06530 06531 return ret; 06532 } 06533 06534 #endif /* STM32_CRYPTO_AES_GCM */ 06535 06536 #ifdef WOLFSSL_AESNI 06537 int AES_GCM_decrypt_C(Aes* aes, byte* out, const byte* in, word32 sz, 06538 const byte* iv, word32 ivSz, 06539 const byte* authTag, word32 authTagSz, 06540 const byte* authIn, word32 authInSz); 06541 #else 06542 static 06543 #endif 06544 int AES_GCM_decrypt_C(Aes* aes, byte* out, const byte* in, word32 sz, 06545 const byte* iv, word32 ivSz, 06546 const byte* authTag, word32 authTagSz, 06547 const byte* authIn, word32 authInSz) 06548 { 06549 int ret = 0; 06550 word32 blocks = sz / AES_BLOCK_SIZE; 06551 word32 partial = sz % AES_BLOCK_SIZE; 06552 const byte* c = in; 06553 byte* p = out; 06554 byte counter[AES_BLOCK_SIZE]; 06555 byte initialCounter[AES_BLOCK_SIZE]; 06556 byte *ctr; 06557 byte scratch[AES_BLOCK_SIZE]; 06558 byte Tprime[AES_BLOCK_SIZE]; 06559 byte EKY0[AES_BLOCK_SIZE]; 06560 #ifdef OPENSSL_EXTRA 06561 word32 aadTemp; 06562 #endif 06563 ctr = counter; 06564 XMEMSET(initialCounter, 0, AES_BLOCK_SIZE); 06565 if (ivSz == GCM_NONCE_MID_SZ) { 06566 XMEMCPY(initialCounter, iv, ivSz); 06567 initialCounter[AES_BLOCK_SIZE - 1] = 1; 06568 } 06569 else { 06570 #ifdef OPENSSL_EXTRA 06571 aadTemp = aes->aadLen; 06572 aes->aadLen = 0; 06573 #endif 06574 GHASH(aes, NULL, 0, iv, ivSz, initialCounter, AES_BLOCK_SIZE); 06575 #ifdef OPENSSL_EXTRA 06576 aes->aadLen = aadTemp; 06577 #endif 06578 } 06579 XMEMCPY(ctr, initialCounter, AES_BLOCK_SIZE); 06580 06581 /* Calc the authTag again using the received auth data and the cipher text */ 06582 GHASH(aes, authIn, authInSz, in, sz, Tprime, sizeof(Tprime)); 06583 wc_AesEncrypt(aes, ctr, EKY0); 06584 xorbuf(Tprime, EKY0, sizeof(Tprime)); 06585 06586 #ifdef OPENSSL_EXTRA 06587 if (!out) { 06588 /* authenticated, non-confidential data */ 06589 /* store AAD size for next call */ 06590 aes->aadLen = authInSz; 06591 } 06592 #endif 06593 if (ConstantCompare(authTag, Tprime, authTagSz) != 0) { 06594 return AES_GCM_AUTH_E; 06595 } 06596 06597 #if defined(WOLFSSL_PIC32MZ_CRYPT) 06598 if (blocks) { 06599 /* use initial IV for HW, but don't use it below */ 06600 XMEMCPY(aes->reg, ctr, AES_BLOCK_SIZE); 06601 06602 ret = wc_Pic32AesCrypt( 06603 aes->key, aes->keylen, aes->reg, AES_BLOCK_SIZE, 06604 out, in, (blocks * AES_BLOCK_SIZE), 06605 PIC32_DECRYPTION, PIC32_ALGO_AES, PIC32_CRYPTOALGO_AES_GCM); 06606 if (ret != 0) 06607 return ret; 06608 } 06609 /* process remainder using partial handling */ 06610 #endif 06611 06612 #if defined(HAVE_AES_ECB) && !defined(WOLFSSL_PIC32MZ_CRYPT) 06613 /* some hardware acceleration can gain performance from doing AES encryption 06614 * of the whole buffer at once */ 06615 if (c != p && blocks > 0) { /* can not handle inline decryption */ 06616 while (blocks--) { 06617 IncrementGcmCounter(ctr); 06618 XMEMCPY(p, ctr, AES_BLOCK_SIZE); 06619 p += AES_BLOCK_SIZE; 06620 } 06621 06622 /* reset number of blocks and then do encryption */ 06623 blocks = sz / AES_BLOCK_SIZE; 06624 06625 wc_AesEcbEncrypt(aes, out, out, AES_BLOCK_SIZE * blocks); 06626 xorbuf(out, c, AES_BLOCK_SIZE * blocks); 06627 c += AES_BLOCK_SIZE * blocks; 06628 } 06629 else 06630 #endif /* HAVE_AES_ECB && !PIC32MZ */ 06631 while (blocks--) { 06632 IncrementGcmCounter(ctr); 06633 #if !defined(WOLFSSL_PIC32MZ_CRYPT) 06634 wc_AesEncrypt(aes, ctr, scratch); 06635 xorbuf(scratch, c, AES_BLOCK_SIZE); 06636 XMEMCPY(p, scratch, AES_BLOCK_SIZE); 06637 #endif 06638 p += AES_BLOCK_SIZE; 06639 c += AES_BLOCK_SIZE; 06640 } 06641 06642 if (partial != 0) { 06643 IncrementGcmCounter(ctr); 06644 wc_AesEncrypt(aes, ctr, scratch); 06645 xorbuf(scratch, c, partial); 06646 XMEMCPY(p, scratch, partial); 06647 } 06648 06649 return ret; 06650 } 06651 06652 /* Software AES - GCM Decrypt */ 06653 int wc_AesGcmDecrypt(Aes* aes, byte* out, const byte* in, word32 sz, 06654 const byte* iv, word32 ivSz, 06655 const byte* authTag, word32 authTagSz, 06656 const byte* authIn, word32 authInSz) 06657 { 06658 #ifdef WOLFSSL_AESNI 06659 int res = AES_GCM_AUTH_E; 06660 #endif 06661 06662 /* argument checks */ 06663 /* If the sz is non-zero, both in and out must be set. If sz is 0, 06664 * in and out are don't cares, as this is is the GMAC case. */ 06665 if (aes == NULL || iv == NULL || (sz != 0 && (in == NULL || out == NULL)) || 06666 authTag == NULL || authTagSz > AES_BLOCK_SIZE || authTagSz == 0 || 06667 ivSz == 0) { 06668 06669 return BAD_FUNC_ARG; 06670 } 06671 06672 #ifdef WOLF_CRYPTO_CB 06673 if (aes->devId != INVALID_DEVID) { 06674 int ret = wc_CryptoCb_AesGcmDecrypt(aes, out, in, sz, iv, ivSz, 06675 authTag, authTagSz, authIn, authInSz); 06676 if (ret != CRYPTOCB_UNAVAILABLE) 06677 return ret; 06678 /* fall-through when unavailable */ 06679 } 06680 #endif 06681 06682 #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_AES) 06683 /* if async and byte count above threshold */ 06684 /* only 12-byte IV is supported in HW */ 06685 if (aes->asyncDev.marker == WOLFSSL_ASYNC_MARKER_AES && 06686 sz >= WC_ASYNC_THRESH_AES_GCM && ivSz == GCM_NONCE_MID_SZ) { 06687 #if defined(HAVE_CAVIUM) 06688 #ifdef HAVE_CAVIUM_V 06689 if (authInSz == 20) { /* Nitrox V GCM is only working with 20 byte AAD */ 06690 return NitroxAesGcmDecrypt(aes, out, in, sz, 06691 (const byte*)aes->devKey, aes->keylen, iv, ivSz, 06692 authTag, authTagSz, authIn, authInSz); 06693 } 06694 #endif 06695 #elif defined(HAVE_INTEL_QA) 06696 return IntelQaSymAesGcmDecrypt(&aes->asyncDev, out, in, sz, 06697 (const byte*)aes->devKey, aes->keylen, iv, ivSz, 06698 authTag, authTagSz, authIn, authInSz); 06699 #else /* WOLFSSL_ASYNC_CRYPT_TEST */ 06700 if (wc_AsyncTestInit(&aes->asyncDev, ASYNC_TEST_AES_GCM_DECRYPT)) { 06701 WC_ASYNC_TEST* testDev = &aes->asyncDev.test; 06702 testDev->aes.aes = aes; 06703 testDev->aes.out = out; 06704 testDev->aes.in = in; 06705 testDev->aes.sz = sz; 06706 testDev->aes.iv = iv; 06707 testDev->aes.ivSz = ivSz; 06708 testDev->aes.authTag = (byte*)authTag; 06709 testDev->aes.authTagSz = authTagSz; 06710 testDev->aes.authIn = authIn; 06711 testDev->aes.authInSz = authInSz; 06712 return WC_PENDING_E; 06713 } 06714 #endif 06715 } 06716 #endif /* WOLFSSL_ASYNC_CRYPT */ 06717 06718 #ifdef STM32_CRYPTO_AES_GCM 06719 /* The STM standard peripheral library API's doesn't support partial blocks */ 06720 #ifdef STD_PERI_LIB 06721 if (partial == 0) 06722 #endif 06723 { 06724 return wc_AesGcmDecrypt_STM32( 06725 aes, out, in, sz, iv, ivSz, 06726 authTag, authTagSz, authIn, authInSz); 06727 } 06728 #endif /* STM32_CRYPTO_AES_GCM */ 06729 06730 #ifdef WOLFSSL_AESNI 06731 #ifdef HAVE_INTEL_AVX2 06732 if (IS_INTEL_AVX2(intel_flags)) { 06733 AES_GCM_decrypt_avx2(in, out, authIn, iv, authTag, sz, authInSz, ivSz, 06734 authTagSz, (byte*)aes->key, aes->rounds, &res); 06735 if (res == 0) 06736 return AES_GCM_AUTH_E; 06737 return 0; 06738 } 06739 else 06740 #endif 06741 #ifdef HAVE_INTEL_AVX1 06742 if (IS_INTEL_AVX1(intel_flags)) { 06743 AES_GCM_decrypt_avx1(in, out, authIn, iv, authTag, sz, authInSz, ivSz, 06744 authTagSz, (byte*)aes->key, aes->rounds, &res); 06745 if (res == 0) 06746 return AES_GCM_AUTH_E; 06747 return 0; 06748 } 06749 else 06750 #endif 06751 if (haveAESNI) { 06752 AES_GCM_decrypt(in, out, authIn, iv, authTag, sz, authInSz, ivSz, 06753 authTagSz, (byte*)aes->key, aes->rounds, &res); 06754 if (res == 0) 06755 return AES_GCM_AUTH_E; 06756 return 0; 06757 } 06758 else 06759 #endif 06760 { 06761 return AES_GCM_decrypt_C(aes, out, in, sz, iv, ivSz, authTag, authTagSz, 06762 authIn, authInSz); 06763 } 06764 } 06765 #endif 06766 #endif /* HAVE_AES_DECRYPT || HAVE_AESGCM_DECRYPT */ 06767 #endif /* WOLFSSL_XILINX_CRYPT */ 06768 #endif /* end of block for AESGCM implementation selection */ 06769 06770 06771 /* Common to all, abstract functions that build off of lower level AESGCM 06772 * functions */ 06773 #ifndef WC_NO_RNG 06774 06775 int wc_AesGcmSetExtIV(Aes* aes, const byte* iv, word32 ivSz) 06776 { 06777 int ret = 0; 06778 06779 if (aes == NULL || iv == NULL || 06780 (ivSz != GCM_NONCE_MIN_SZ && ivSz != GCM_NONCE_MID_SZ && 06781 ivSz != GCM_NONCE_MAX_SZ)) { 06782 06783 ret = BAD_FUNC_ARG; 06784 } 06785 06786 if (ret == 0) { 06787 XMEMCPY((byte*)aes->reg, iv, ivSz); 06788 06789 /* If the IV is 96, allow for a 2^64 invocation counter. 06790 * For any other size for the nonce, limit the invocation 06791 * counter to 32-bits. (SP 800-38D 8.3) */ 06792 aes->invokeCtr[0] = 0; 06793 aes->invokeCtr[1] = (ivSz == GCM_NONCE_MID_SZ) ? 0 : 0xFFFFFFFF; 06794 aes->nonceSz = ivSz; 06795 } 06796 06797 return ret; 06798 } 06799 06800 06801 int wc_AesGcmSetIV(Aes* aes, word32 ivSz, 06802 const byte* ivFixed, word32 ivFixedSz, 06803 WC_RNG* rng) 06804 { 06805 int ret = 0; 06806 06807 if (aes == NULL || rng == NULL || 06808 (ivSz != GCM_NONCE_MIN_SZ && ivSz != GCM_NONCE_MID_SZ && 06809 ivSz != GCM_NONCE_MAX_SZ) || 06810 (ivFixed == NULL && ivFixedSz != 0) || 06811 (ivFixed != NULL && ivFixedSz != AES_IV_FIXED_SZ)) { 06812 06813 ret = BAD_FUNC_ARG; 06814 } 06815 06816 if (ret == 0) { 06817 byte* iv = (byte*)aes->reg; 06818 06819 if (ivFixedSz) 06820 XMEMCPY(iv, ivFixed, ivFixedSz); 06821 06822 ret = wc_RNG_GenerateBlock(rng, iv + ivFixedSz, ivSz - ivFixedSz); 06823 } 06824 06825 if (ret == 0) { 06826 /* If the IV is 96, allow for a 2^64 invocation counter. 06827 * For any other size for the nonce, limit the invocation 06828 * counter to 32-bits. (SP 800-38D 8.3) */ 06829 aes->invokeCtr[0] = 0; 06830 aes->invokeCtr[1] = (ivSz == GCM_NONCE_MID_SZ) ? 0 : 0xFFFFFFFF; 06831 aes->nonceSz = ivSz; 06832 } 06833 06834 return ret; 06835 } 06836 06837 06838 int wc_AesGcmEncrypt_ex(Aes* aes, byte* out, const byte* in, word32 sz, 06839 byte* ivOut, word32 ivOutSz, 06840 byte* authTag, word32 authTagSz, 06841 const byte* authIn, word32 authInSz) 06842 { 06843 int ret = 0; 06844 06845 if (aes == NULL || (sz != 0 && (in == NULL || out == NULL)) || 06846 ivOut == NULL || ivOutSz != aes->nonceSz || 06847 (authIn == NULL && authInSz != 0)) { 06848 06849 ret = BAD_FUNC_ARG; 06850 } 06851 06852 if (ret == 0) { 06853 aes->invokeCtr[0]++; 06854 if (aes->invokeCtr[0] == 0) { 06855 aes->invokeCtr[1]++; 06856 if (aes->invokeCtr[1] == 0) 06857 ret = AES_GCM_OVERFLOW_E; 06858 } 06859 } 06860 06861 if (ret == 0) { 06862 XMEMCPY(ivOut, aes->reg, ivOutSz); 06863 ret = wc_AesGcmEncrypt(aes, out, in, sz, 06864 (byte*)aes->reg, ivOutSz, 06865 authTag, authTagSz, 06866 authIn, authInSz); 06867 if (ret == 0) 06868 IncCtr((byte*)aes->reg, ivOutSz); 06869 } 06870 06871 return ret; 06872 } 06873 06874 int wc_Gmac(const byte* key, word32 keySz, byte* iv, word32 ivSz, 06875 const byte* authIn, word32 authInSz, 06876 byte* authTag, word32 authTagSz, WC_RNG* rng) 06877 { 06878 Aes aes; 06879 int ret; 06880 06881 if (key == NULL || iv == NULL || (authIn == NULL && authInSz != 0) || 06882 authTag == NULL || authTagSz == 0 || rng == NULL) { 06883 06884 return BAD_FUNC_ARG; 06885 } 06886 06887 ret = wc_AesInit(&aes, NULL, INVALID_DEVID); 06888 if (ret == 0) { 06889 ret = wc_AesGcmSetKey(&aes, key, keySz); 06890 if (ret == 0) 06891 ret = wc_AesGcmSetIV(&aes, ivSz, NULL, 0, rng); 06892 if (ret == 0) 06893 ret = wc_AesGcmEncrypt_ex(&aes, NULL, NULL, 0, iv, ivSz, 06894 authTag, authTagSz, authIn, authInSz); 06895 wc_AesFree(&aes); 06896 } 06897 ForceZero(&aes, sizeof(aes)); 06898 06899 return ret; 06900 } 06901 06902 int wc_GmacVerify(const byte* key, word32 keySz, 06903 const byte* iv, word32 ivSz, 06904 const byte* authIn, word32 authInSz, 06905 const byte* authTag, word32 authTagSz) 06906 { 06907 int ret; 06908 #ifndef NO_AES_DECRYPT 06909 Aes aes; 06910 06911 if (key == NULL || iv == NULL || (authIn == NULL && authInSz != 0) || 06912 authTag == NULL || authTagSz == 0 || authTagSz > AES_BLOCK_SIZE) { 06913 06914 return BAD_FUNC_ARG; 06915 } 06916 06917 ret = wc_AesInit(&aes, NULL, INVALID_DEVID); 06918 if (ret == 0) { 06919 ret = wc_AesGcmSetKey(&aes, key, keySz); 06920 if (ret == 0) 06921 ret = wc_AesGcmDecrypt(&aes, NULL, NULL, 0, iv, ivSz, 06922 authTag, authTagSz, authIn, authInSz); 06923 wc_AesFree(&aes); 06924 } 06925 ForceZero(&aes, sizeof(aes)); 06926 #else 06927 (void)key; 06928 (void)keySz; 06929 (void)iv; 06930 (void)ivSz; 06931 (void)authIn; 06932 (void)authInSz; 06933 (void)authTag; 06934 (void)authTagSz; 06935 ret = NOT_COMPILED_IN; 06936 #endif 06937 return ret; 06938 } 06939 06940 #endif /* WC_NO_RNG */ 06941 06942 06943 WOLFSSL_API int wc_GmacSetKey(Gmac* gmac, const byte* key, word32 len) 06944 { 06945 if (gmac == NULL || key == NULL) { 06946 return BAD_FUNC_ARG; 06947 } 06948 return wc_AesGcmSetKey(&gmac->aes, key, len); 06949 } 06950 06951 06952 WOLFSSL_API int wc_GmacUpdate(Gmac* gmac, const byte* iv, word32 ivSz, 06953 const byte* authIn, word32 authInSz, 06954 byte* authTag, word32 authTagSz) 06955 { 06956 return wc_AesGcmEncrypt(&gmac->aes, NULL, NULL, 0, iv, ivSz, 06957 authTag, authTagSz, authIn, authInSz); 06958 } 06959 06960 #endif /* HAVE_AESGCM */ 06961 06962 06963 #ifdef HAVE_AESCCM 06964 06965 int wc_AesCcmSetKey(Aes* aes, const byte* key, word32 keySz) 06966 { 06967 if (!((keySz == 16) || (keySz == 24) || (keySz == 32))) 06968 return BAD_FUNC_ARG; 06969 06970 return wc_AesSetKey(aes, key, keySz, NULL, AES_ENCRYPTION); 06971 } 06972 06973 #ifdef WOLFSSL_ARMASM 06974 /* implementation located in wolfcrypt/src/port/arm/armv8-aes.c */ 06975 06976 #elif defined(HAVE_COLDFIRE_SEC) 06977 #error "Coldfire SEC doesn't currently support AES-CCM mode" 06978 06979 #elif defined(WOLFSSL_IMX6_CAAM) && !defined(NO_IMX6_CAAM_AES) 06980 /* implemented in wolfcrypt/src/port/caam_aes.c */ 06981 06982 #elif defined(FREESCALE_LTC) 06983 06984 /* return 0 on success */ 06985 int wc_AesCcmEncrypt(Aes* aes, byte* out, const byte* in, word32 inSz, 06986 const byte* nonce, word32 nonceSz, 06987 byte* authTag, word32 authTagSz, 06988 const byte* authIn, word32 authInSz) 06989 { 06990 byte *key; 06991 uint32_t keySize; 06992 status_t status; 06993 06994 /* sanity check on arguments */ 06995 if (aes == NULL || out == NULL || in == NULL || nonce == NULL 06996 || authTag == NULL || nonceSz < 7 || nonceSz > 13) 06997 return BAD_FUNC_ARG; 06998 06999 key = (byte*)aes->key; 07000 07001 status = wc_AesGetKeySize(aes, &keySize); 07002 if (status != 0) { 07003 return status; 07004 } 07005 07006 status = LTC_AES_EncryptTagCcm(LTC_BASE, in, out, inSz, 07007 nonce, nonceSz, authIn, authInSz, key, keySize, authTag, authTagSz); 07008 07009 return (kStatus_Success == status) ? 0 : BAD_FUNC_ARG; 07010 } 07011 07012 #ifdef HAVE_AES_DECRYPT 07013 int wc_AesCcmDecrypt(Aes* aes, byte* out, const byte* in, word32 inSz, 07014 const byte* nonce, word32 nonceSz, 07015 const byte* authTag, word32 authTagSz, 07016 const byte* authIn, word32 authInSz) 07017 { 07018 byte *key; 07019 uint32_t keySize; 07020 status_t status; 07021 07022 /* sanity check on arguments */ 07023 if (aes == NULL || out == NULL || in == NULL || nonce == NULL 07024 || authTag == NULL || nonceSz < 7 || nonceSz > 13) 07025 return BAD_FUNC_ARG; 07026 07027 key = (byte*)aes->key; 07028 07029 status = wc_AesGetKeySize(aes, &keySize); 07030 if (status != 0) { 07031 return status; 07032 } 07033 07034 status = LTC_AES_DecryptTagCcm(LTC_BASE, in, out, inSz, 07035 nonce, nonceSz, authIn, authInSz, key, keySize, authTag, authTagSz); 07036 07037 if (status == kStatus_Success) { 07038 return 0; 07039 } 07040 else { 07041 XMEMSET(out, 0, inSz); 07042 return AES_CCM_AUTH_E; 07043 } 07044 } 07045 #endif /* HAVE_AES_DECRYPT */ 07046 07047 #else 07048 07049 /* Software CCM */ 07050 static void roll_x(Aes* aes, const byte* in, word32 inSz, byte* out) 07051 { 07052 /* process the bulk of the data */ 07053 while (inSz >= AES_BLOCK_SIZE) { 07054 xorbuf(out, in, AES_BLOCK_SIZE); 07055 in += AES_BLOCK_SIZE; 07056 inSz -= AES_BLOCK_SIZE; 07057 07058 wc_AesEncrypt(aes, out, out); 07059 } 07060 07061 /* process remainder of the data */ 07062 if (inSz > 0) { 07063 xorbuf(out, in, inSz); 07064 wc_AesEncrypt(aes, out, out); 07065 } 07066 } 07067 07068 static void roll_auth(Aes* aes, const byte* in, word32 inSz, byte* out) 07069 { 07070 word32 authLenSz; 07071 word32 remainder; 07072 07073 /* encode the length in */ 07074 if (inSz <= 0xFEFF) { 07075 authLenSz = 2; 07076 out[0] ^= ((inSz & 0xFF00) >> 8); 07077 out[1] ^= (inSz & 0x00FF); 07078 } 07079 else if (inSz <= 0xFFFFFFFF) { 07080 authLenSz = 6; 07081 out[0] ^= 0xFF; out[1] ^= 0xFE; 07082 out[2] ^= ((inSz & 0xFF000000) >> 24); 07083 out[3] ^= ((inSz & 0x00FF0000) >> 16); 07084 out[4] ^= ((inSz & 0x0000FF00) >> 8); 07085 out[5] ^= (inSz & 0x000000FF); 07086 } 07087 /* Note, the protocol handles auth data up to 2^64, but we are 07088 * using 32-bit sizes right now, so the bigger data isn't handled 07089 * else if (inSz <= 0xFFFFFFFFFFFFFFFF) {} */ 07090 else 07091 return; 07092 07093 /* start fill out the rest of the first block */ 07094 remainder = AES_BLOCK_SIZE - authLenSz; 07095 if (inSz >= remainder) { 07096 /* plenty of bulk data to fill the remainder of this block */ 07097 xorbuf(out + authLenSz, in, remainder); 07098 inSz -= remainder; 07099 in += remainder; 07100 } 07101 else { 07102 /* not enough bulk data, copy what is available, and pad zero */ 07103 xorbuf(out + authLenSz, in, inSz); 07104 inSz = 0; 07105 } 07106 wc_AesEncrypt(aes, out, out); 07107 07108 if (inSz > 0) 07109 roll_x(aes, in, inSz, out); 07110 } 07111 07112 07113 static WC_INLINE void AesCcmCtrInc(byte* B, word32 lenSz) 07114 { 07115 word32 i; 07116 07117 for (i = 0; i < lenSz; i++) { 07118 if (++B[AES_BLOCK_SIZE - 1 - i] != 0) return; 07119 } 07120 } 07121 07122 #ifdef WOLFSSL_AESNI 07123 static WC_INLINE void AesCcmCtrIncSet4(byte* B, word32 lenSz) 07124 { 07125 word32 i; 07126 07127 /* B+1 = B */ 07128 XMEMCPY(B + AES_BLOCK_SIZE * 1, B, AES_BLOCK_SIZE); 07129 /* B+2,B+3 = B,B+1 */ 07130 XMEMCPY(B + AES_BLOCK_SIZE * 2, B, AES_BLOCK_SIZE * 2); 07131 07132 for (i = 0; i < lenSz; i++) { 07133 if (++B[AES_BLOCK_SIZE * 1 - 1 - i] != 0) break; 07134 } 07135 B[AES_BLOCK_SIZE * 2 - 1] += 2; 07136 if (B[AES_BLOCK_SIZE * 2 - 1] < 2) { 07137 for (i = 1; i < lenSz; i++) { 07138 if (++B[AES_BLOCK_SIZE * 2 - 1 - i] != 0) break; 07139 } 07140 } 07141 B[AES_BLOCK_SIZE * 3 - 1] += 3; 07142 if (B[AES_BLOCK_SIZE * 3 - 1] < 3) { 07143 for (i = 1; i < lenSz; i++) { 07144 if (++B[AES_BLOCK_SIZE * 3 - 1 - i] != 0) break; 07145 } 07146 } 07147 } 07148 07149 static WC_INLINE void AesCcmCtrInc4(byte* B, word32 lenSz) 07150 { 07151 word32 i; 07152 07153 B[AES_BLOCK_SIZE - 1] += 4; 07154 if (B[AES_BLOCK_SIZE - 1] < 4) { 07155 for (i = 1; i < lenSz; i++) { 07156 if (++B[AES_BLOCK_SIZE - 1 - i] != 0) break; 07157 } 07158 } 07159 } 07160 #endif 07161 07162 /* Software AES - CCM Encrypt */ 07163 /* return 0 on success */ 07164 int wc_AesCcmEncrypt(Aes* aes, byte* out, const byte* in, word32 inSz, 07165 const byte* nonce, word32 nonceSz, 07166 byte* authTag, word32 authTagSz, 07167 const byte* authIn, word32 authInSz) 07168 { 07169 #ifndef WOLFSSL_AESNI 07170 byte A[AES_BLOCK_SIZE]; 07171 byte B[AES_BLOCK_SIZE]; 07172 #else 07173 ALIGN128 byte A[AES_BLOCK_SIZE * 4]; 07174 ALIGN128 byte B[AES_BLOCK_SIZE * 4]; 07175 #endif 07176 byte lenSz; 07177 word32 i; 07178 byte mask = 0xFF; 07179 const word32 wordSz = (word32)sizeof(word32); 07180 07181 /* sanity check on arguments */ 07182 if (aes == NULL || out == NULL || in == NULL || nonce == NULL 07183 || authTag == NULL || nonceSz < 7 || nonceSz > 13 || 07184 authTagSz > AES_BLOCK_SIZE) 07185 return BAD_FUNC_ARG; 07186 07187 XMEMSET(A, 0, sizeof(A)); 07188 XMEMCPY(B+1, nonce, nonceSz); 07189 lenSz = AES_BLOCK_SIZE - 1 - (byte)nonceSz; 07190 B[0] = (authInSz > 0 ? 64 : 0) 07191 + (8 * (((byte)authTagSz - 2) / 2)) 07192 + (lenSz - 1); 07193 for (i = 0; i < lenSz; i++) { 07194 if (mask && i >= wordSz) 07195 mask = 0x00; 07196 B[AES_BLOCK_SIZE - 1 - i] = (inSz >> ((8 * i) & mask)) & mask; 07197 } 07198 07199 wc_AesEncrypt(aes, B, A); 07200 07201 if (authInSz > 0) 07202 roll_auth(aes, authIn, authInSz, A); 07203 if (inSz > 0) 07204 roll_x(aes, in, inSz, A); 07205 XMEMCPY(authTag, A, authTagSz); 07206 07207 B[0] = lenSz - 1; 07208 for (i = 0; i < lenSz; i++) 07209 B[AES_BLOCK_SIZE - 1 - i] = 0; 07210 wc_AesEncrypt(aes, B, A); 07211 xorbuf(authTag, A, authTagSz); 07212 07213 B[15] = 1; 07214 #ifdef WOLFSSL_AESNI 07215 if (haveAESNI && aes->use_aesni) { 07216 while (inSz >= AES_BLOCK_SIZE * 4) { 07217 AesCcmCtrIncSet4(B, lenSz); 07218 07219 AES_ECB_encrypt(B, A, AES_BLOCK_SIZE * 4, (byte*)aes->key, 07220 aes->rounds); 07221 xorbuf(A, in, AES_BLOCK_SIZE * 4); 07222 XMEMCPY(out, A, AES_BLOCK_SIZE * 4); 07223 07224 inSz -= AES_BLOCK_SIZE * 4; 07225 in += AES_BLOCK_SIZE * 4; 07226 out += AES_BLOCK_SIZE * 4; 07227 07228 if (inSz < AES_BLOCK_SIZE * 4) { 07229 AesCcmCtrInc4(B, lenSz); 07230 } 07231 } 07232 } 07233 #endif 07234 while (inSz >= AES_BLOCK_SIZE) { 07235 wc_AesEncrypt(aes, B, A); 07236 xorbuf(A, in, AES_BLOCK_SIZE); 07237 XMEMCPY(out, A, AES_BLOCK_SIZE); 07238 07239 AesCcmCtrInc(B, lenSz); 07240 inSz -= AES_BLOCK_SIZE; 07241 in += AES_BLOCK_SIZE; 07242 out += AES_BLOCK_SIZE; 07243 } 07244 if (inSz > 0) { 07245 wc_AesEncrypt(aes, B, A); 07246 xorbuf(A, in, inSz); 07247 XMEMCPY(out, A, inSz); 07248 } 07249 07250 ForceZero(A, AES_BLOCK_SIZE); 07251 ForceZero(B, AES_BLOCK_SIZE); 07252 07253 return 0; 07254 } 07255 07256 #ifdef HAVE_AES_DECRYPT 07257 /* Software AES - CCM Decrypt */ 07258 int wc_AesCcmDecrypt(Aes* aes, byte* out, const byte* in, word32 inSz, 07259 const byte* nonce, word32 nonceSz, 07260 const byte* authTag, word32 authTagSz, 07261 const byte* authIn, word32 authInSz) 07262 { 07263 #ifndef WOLFSSL_AESNI 07264 byte A[AES_BLOCK_SIZE]; 07265 byte B[AES_BLOCK_SIZE]; 07266 #else 07267 ALIGN128 byte B[AES_BLOCK_SIZE * 4]; 07268 ALIGN128 byte A[AES_BLOCK_SIZE * 4]; 07269 #endif 07270 byte* o; 07271 byte lenSz; 07272 word32 i, oSz; 07273 int result = 0; 07274 byte mask = 0xFF; 07275 const word32 wordSz = (word32)sizeof(word32); 07276 07277 /* sanity check on arguments */ 07278 if (aes == NULL || out == NULL || in == NULL || nonce == NULL 07279 || authTag == NULL || nonceSz < 7 || nonceSz > 13 || 07280 authTagSz > AES_BLOCK_SIZE) 07281 return BAD_FUNC_ARG; 07282 07283 o = out; 07284 oSz = inSz; 07285 XMEMCPY(B+1, nonce, nonceSz); 07286 lenSz = AES_BLOCK_SIZE - 1 - (byte)nonceSz; 07287 07288 B[0] = lenSz - 1; 07289 for (i = 0; i < lenSz; i++) 07290 B[AES_BLOCK_SIZE - 1 - i] = 0; 07291 B[15] = 1; 07292 07293 #ifdef WOLFSSL_AESNI 07294 if (haveAESNI && aes->use_aesni) { 07295 while (oSz >= AES_BLOCK_SIZE * 4) { 07296 AesCcmCtrIncSet4(B, lenSz); 07297 07298 AES_ECB_encrypt(B, A, AES_BLOCK_SIZE * 4, (byte*)aes->key, 07299 aes->rounds); 07300 xorbuf(A, in, AES_BLOCK_SIZE * 4); 07301 XMEMCPY(o, A, AES_BLOCK_SIZE * 4); 07302 07303 oSz -= AES_BLOCK_SIZE * 4; 07304 in += AES_BLOCK_SIZE * 4; 07305 o += AES_BLOCK_SIZE * 4; 07306 07307 if (oSz < AES_BLOCK_SIZE * 4) { 07308 AesCcmCtrInc4(B, lenSz); 07309 } 07310 } 07311 } 07312 #endif 07313 while (oSz >= AES_BLOCK_SIZE) { 07314 wc_AesEncrypt(aes, B, A); 07315 xorbuf(A, in, AES_BLOCK_SIZE); 07316 XMEMCPY(o, A, AES_BLOCK_SIZE); 07317 07318 AesCcmCtrInc(B, lenSz); 07319 oSz -= AES_BLOCK_SIZE; 07320 in += AES_BLOCK_SIZE; 07321 o += AES_BLOCK_SIZE; 07322 } 07323 if (inSz > 0) { 07324 wc_AesEncrypt(aes, B, A); 07325 xorbuf(A, in, oSz); 07326 XMEMCPY(o, A, oSz); 07327 } 07328 07329 for (i = 0; i < lenSz; i++) 07330 B[AES_BLOCK_SIZE - 1 - i] = 0; 07331 wc_AesEncrypt(aes, B, A); 07332 07333 o = out; 07334 oSz = inSz; 07335 07336 B[0] = (authInSz > 0 ? 64 : 0) 07337 + (8 * (((byte)authTagSz - 2) / 2)) 07338 + (lenSz - 1); 07339 for (i = 0; i < lenSz; i++) { 07340 if (mask && i >= wordSz) 07341 mask = 0x00; 07342 B[AES_BLOCK_SIZE - 1 - i] = (inSz >> ((8 * i) & mask)) & mask; 07343 } 07344 07345 wc_AesEncrypt(aes, B, A); 07346 07347 if (authInSz > 0) 07348 roll_auth(aes, authIn, authInSz, A); 07349 if (inSz > 0) 07350 roll_x(aes, o, oSz, A); 07351 07352 B[0] = lenSz - 1; 07353 for (i = 0; i < lenSz; i++) 07354 B[AES_BLOCK_SIZE - 1 - i] = 0; 07355 wc_AesEncrypt(aes, B, B); 07356 xorbuf(A, B, authTagSz); 07357 07358 if (ConstantCompare(A, authTag, authTagSz) != 0) { 07359 /* If the authTag check fails, don't keep the decrypted data. 07360 * Unfortunately, you need the decrypted data to calculate the 07361 * check value. */ 07362 XMEMSET(out, 0, inSz); 07363 result = AES_CCM_AUTH_E; 07364 } 07365 07366 ForceZero(A, AES_BLOCK_SIZE); 07367 ForceZero(B, AES_BLOCK_SIZE); 07368 o = NULL; 07369 07370 return result; 07371 } 07372 07373 #endif /* HAVE_AES_DECRYPT */ 07374 #endif /* software CCM */ 07375 07376 /* abstract functions that call lower level AESCCM functions */ 07377 #ifndef WC_NO_RNG 07378 07379 int wc_AesCcmSetNonce(Aes* aes, const byte* nonce, word32 nonceSz) 07380 { 07381 int ret = 0; 07382 07383 if (aes == NULL || nonce == NULL || 07384 nonceSz < CCM_NONCE_MIN_SZ || nonceSz > CCM_NONCE_MAX_SZ) { 07385 07386 ret = BAD_FUNC_ARG; 07387 } 07388 07389 if (ret == 0) { 07390 XMEMCPY(aes->reg, nonce, nonceSz); 07391 aes->nonceSz = nonceSz; 07392 07393 /* Invocation counter should be 2^61 */ 07394 aes->invokeCtr[0] = 0; 07395 aes->invokeCtr[1] = 0xE0000000; 07396 } 07397 07398 return ret; 07399 } 07400 07401 07402 int wc_AesCcmEncrypt_ex(Aes* aes, byte* out, const byte* in, word32 sz, 07403 byte* ivOut, word32 ivOutSz, 07404 byte* authTag, word32 authTagSz, 07405 const byte* authIn, word32 authInSz) 07406 { 07407 int ret = 0; 07408 07409 if (aes == NULL || out == NULL || 07410 (in == NULL && sz != 0) || 07411 ivOut == NULL || 07412 (authIn == NULL && authInSz != 0) || 07413 (ivOutSz != aes->nonceSz)) { 07414 07415 ret = BAD_FUNC_ARG; 07416 } 07417 07418 if (ret == 0) { 07419 aes->invokeCtr[0]++; 07420 if (aes->invokeCtr[0] == 0) { 07421 aes->invokeCtr[1]++; 07422 if (aes->invokeCtr[1] == 0) 07423 ret = AES_CCM_OVERFLOW_E; 07424 } 07425 } 07426 07427 if (ret == 0) { 07428 ret = wc_AesCcmEncrypt(aes, out, in, sz, 07429 (byte*)aes->reg, aes->nonceSz, 07430 authTag, authTagSz, 07431 authIn, authInSz); 07432 if (ret == 0) { 07433 XMEMCPY(ivOut, aes->reg, aes->nonceSz); 07434 IncCtr((byte*)aes->reg, aes->nonceSz); 07435 } 07436 } 07437 07438 return ret; 07439 } 07440 07441 #endif /* WC_NO_RNG */ 07442 07443 #endif /* HAVE_AESCCM */ 07444 07445 07446 /* Initialize Aes for use with async hardware */ 07447 int wc_AesInit(Aes* aes, void* heap, int devId) 07448 { 07449 int ret = 0; 07450 07451 if (aes == NULL) 07452 return BAD_FUNC_ARG; 07453 07454 aes->heap = heap; 07455 07456 #ifdef WOLF_CRYPTO_CB 07457 aes->devId = devId; 07458 aes->devCtx = NULL; 07459 #else 07460 (void)devId; 07461 #endif 07462 #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_AES) 07463 ret = wolfAsync_DevCtxInit(&aes->asyncDev, WOLFSSL_ASYNC_MARKER_AES, 07464 aes->heap, devId); 07465 #endif /* WOLFSSL_ASYNC_CRYPT */ 07466 07467 #ifdef WOLFSSL_AFALG 07468 aes->alFd = -1; 07469 aes->rdFd = -1; 07470 #endif 07471 #if defined(WOLFSSL_DEVCRYPTO) && \ 07472 (defined(WOLFSSL_DEVCRYPTO_AES) || defined(WOLFSSL_DEVCRYPTO_CBC)) 07473 aes->ctx.cfd = -1; 07474 #endif 07475 #if defined(WOLFSSL_CRYPTOCELL) && defined(WOLFSSL_CRYPTOCELL_AES) 07476 XMEMSET(&aes->ctx, 0, sizeof(aes->ctx)); 07477 #endif 07478 #ifdef HAVE_AESGCM 07479 #ifdef OPENSSL_EXTRA 07480 XMEMSET(aes->aadH, 0, sizeof(aes->aadH)); 07481 aes->aadLen = 0; 07482 #endif 07483 #endif 07484 return ret; 07485 } 07486 07487 #ifdef HAVE_PKCS11 07488 int wc_AesInit_Id(Aes* aes, unsigned char* id, int len, void* heap, int devId) 07489 { 07490 int ret = 0; 07491 07492 if (aes == NULL) 07493 ret = BAD_FUNC_ARG; 07494 if (ret == 0 && (len < 0 || len > AES_MAX_ID_LEN)) 07495 ret = BUFFER_E; 07496 07497 if (ret == 0) 07498 ret = wc_AesInit(aes, heap, devId); 07499 if (ret == 0) { 07500 XMEMCPY(aes->id, id, len); 07501 aes->idLen = len; 07502 } 07503 07504 return ret; 07505 } 07506 #endif 07507 07508 /* Free Aes from use with async hardware */ 07509 void wc_AesFree(Aes* aes) 07510 { 07511 if (aes == NULL) 07512 return; 07513 07514 #if defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_AES) 07515 wolfAsync_DevCtxFree(&aes->asyncDev, WOLFSSL_ASYNC_MARKER_AES); 07516 #endif /* WOLFSSL_ASYNC_CRYPT */ 07517 #if defined(WOLFSSL_AFALG) || defined(WOLFSSL_AFALG_XILINX_AES) 07518 if (aes->rdFd > 0) { /* negative is error case */ 07519 close(aes->rdFd); 07520 } 07521 if (aes->alFd > 0) { 07522 close(aes->alFd); 07523 } 07524 #endif /* WOLFSSL_AFALG */ 07525 #if defined(WOLFSSL_DEVCRYPTO) && \ 07526 (defined(WOLFSSL_DEVCRYPTO_AES) || defined(WOLFSSL_DEVCRYPTO_CBC)) 07527 wc_DevCryptoFree(&aes->ctx); 07528 #endif 07529 #if defined(WOLF_CRYPTO_CB) || (defined(WOLFSSL_DEVCRYPTO) && \ 07530 (defined(WOLFSSL_DEVCRYPTO_AES) || defined(WOLFSSL_DEVCRYPTO_CBC))) || \ 07531 (defined(WOLFSSL_ASYNC_CRYPT) && defined(WC_ASYNC_ENABLE_AES)) 07532 ForceZero((byte*)aes->devKey, AES_MAX_KEY_SIZE/WOLFSSL_BIT_SIZE); 07533 #endif 07534 } 07535 07536 07537 int wc_AesGetKeySize(Aes* aes, word32* keySize) 07538 { 07539 int ret = 0; 07540 07541 if (aes == NULL || keySize == NULL) { 07542 return BAD_FUNC_ARG; 07543 } 07544 #if defined(WOLFSSL_CRYPTOCELL) && defined(WOLFSSL_CRYPTOCELL_AES) 07545 *keySize = aes->ctx.key.keySize; 07546 return ret; 07547 #endif 07548 switch (aes->rounds) { 07549 #ifdef WOLFSSL_AES_128 07550 case 10: 07551 *keySize = 16; 07552 break; 07553 #endif 07554 #ifdef WOLFSSL_AES_192 07555 case 12: 07556 *keySize = 24; 07557 break; 07558 #endif 07559 #ifdef WOLFSSL_AES_256 07560 case 14: 07561 *keySize = 32; 07562 break; 07563 #endif 07564 default: 07565 *keySize = 0; 07566 ret = BAD_FUNC_ARG; 07567 } 07568 07569 return ret; 07570 } 07571 07572 #endif /* !WOLFSSL_TI_CRYPT */ 07573 07574 #ifdef HAVE_AES_ECB 07575 #if defined(WOLFSSL_IMX6_CAAM) && !defined(NO_IMX6_CAAM_AES) 07576 /* implemented in wolfcrypt/src/port/caam/caam_aes.c */ 07577 07578 #elif defined(WOLFSSL_AFALG) 07579 /* implemented in wolfcrypt/src/port/af_alg/afalg_aes.c */ 07580 07581 #elif defined(WOLFSSL_DEVCRYPTO_AES) 07582 /* implemented in wolfcrypt/src/port/devcrypt/devcrypto_aes.c */ 07583 07584 #elif defined(WOLFSSL_SCE) && !defined(WOLFSSL_SCE_NO_AES) 07585 07586 /* Software AES - ECB */ 07587 int wc_AesEcbEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 07588 { 07589 if ((in == NULL) || (out == NULL) || (aes == NULL)) 07590 return BAD_FUNC_ARG; 07591 07592 return AES_ECB_encrypt(aes, in, out, sz); 07593 } 07594 07595 07596 int wc_AesEcbDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 07597 { 07598 if ((in == NULL) || (out == NULL) || (aes == NULL)) 07599 return BAD_FUNC_ARG; 07600 07601 return AES_ECB_decrypt(aes, in, out, sz); 07602 } 07603 07604 #else 07605 07606 /* Software AES - ECB */ 07607 int wc_AesEcbEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 07608 { 07609 word32 blocks = sz / AES_BLOCK_SIZE; 07610 07611 if ((in == NULL) || (out == NULL) || (aes == NULL)) 07612 return BAD_FUNC_ARG; 07613 while (blocks>0) { 07614 wc_AesEncryptDirect(aes, out, in); 07615 out += AES_BLOCK_SIZE; 07616 in += AES_BLOCK_SIZE; 07617 sz -= AES_BLOCK_SIZE; 07618 blocks--; 07619 } 07620 return 0; 07621 } 07622 07623 07624 int wc_AesEcbDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 07625 { 07626 word32 blocks = sz / AES_BLOCK_SIZE; 07627 07628 if ((in == NULL) || (out == NULL) || (aes == NULL)) 07629 return BAD_FUNC_ARG; 07630 while (blocks>0) { 07631 wc_AesDecryptDirect(aes, out, in); 07632 out += AES_BLOCK_SIZE; 07633 in += AES_BLOCK_SIZE; 07634 sz -= AES_BLOCK_SIZE; 07635 blocks--; 07636 } 07637 return 0; 07638 } 07639 #endif 07640 #endif /* HAVE_AES_ECB */ 07641 07642 #if defined(WOLFSSL_AES_CFB) || defined(WOLFSSL_AES_OFB) 07643 /* Feedback AES mode 07644 * 07645 * aes structure holding key to use for encryption 07646 * out buffer to hold result of encryption (must be at least as large as input 07647 * buffer) 07648 * in buffer to encrypt 07649 * sz size of input buffer 07650 * mode flag to specify AES mode 07651 * 07652 * returns 0 on success and negative error values on failure 07653 */ 07654 /* Software AES - CFB Encrypt */ 07655 static int wc_AesFeedbackEncrypt(Aes* aes, byte* out, const byte* in, 07656 word32 sz, byte mode) 07657 { 07658 byte* tmp = NULL; 07659 #ifdef WOLFSSL_AES_CFB 07660 byte* reg = NULL; 07661 #endif 07662 07663 if (aes == NULL || out == NULL || in == NULL) { 07664 return BAD_FUNC_ARG; 07665 } 07666 07667 #ifdef WOLFSSL_AES_CFB 07668 if (aes->left && sz) { 07669 reg = (byte*)aes->reg + AES_BLOCK_SIZE - aes->left; 07670 } 07671 #endif 07672 07673 /* consume any unused bytes left in aes->tmp */ 07674 tmp = (byte*)aes->tmp + AES_BLOCK_SIZE - aes->left; 07675 while (aes->left && sz) { 07676 *(out) = *(in++) ^ *(tmp++); 07677 #ifdef WOLFSSL_AES_CFB 07678 if (mode == AES_CFB_MODE) { 07679 *(reg++) = *out; 07680 } 07681 #endif 07682 out++; 07683 aes->left--; 07684 sz--; 07685 } 07686 07687 while (sz >= AES_BLOCK_SIZE) { 07688 /* Using aes->tmp here for inline case i.e. in=out */ 07689 wc_AesEncryptDirect(aes, (byte*)aes->tmp, (byte*)aes->reg); 07690 #ifdef WOLFSSL_AES_OFB 07691 if (mode == AES_OFB_MODE) { 07692 XMEMCPY(aes->reg, aes->tmp, AES_BLOCK_SIZE); 07693 } 07694 #endif 07695 xorbuf((byte*)aes->tmp, in, AES_BLOCK_SIZE); 07696 #ifdef WOLFSSL_AES_CFB 07697 if (mode == AES_CFB_MODE) { 07698 XMEMCPY(aes->reg, aes->tmp, AES_BLOCK_SIZE); 07699 } 07700 #endif 07701 XMEMCPY(out, aes->tmp, AES_BLOCK_SIZE); 07702 out += AES_BLOCK_SIZE; 07703 in += AES_BLOCK_SIZE; 07704 sz -= AES_BLOCK_SIZE; 07705 aes->left = 0; 07706 } 07707 07708 /* encrypt left over data */ 07709 if (sz) { 07710 wc_AesEncryptDirect(aes, (byte*)aes->tmp, (byte*)aes->reg); 07711 aes->left = AES_BLOCK_SIZE; 07712 tmp = (byte*)aes->tmp; 07713 #ifdef WOLFSSL_AES_OFB 07714 if (mode == AES_OFB_MODE) { 07715 XMEMCPY(aes->reg, aes->tmp, AES_BLOCK_SIZE); 07716 } 07717 #endif 07718 #ifdef WOLFSSL_AES_CFB 07719 reg = (byte*)aes->reg; 07720 #endif 07721 07722 while (sz--) { 07723 *(out) = *(in++) ^ *(tmp++); 07724 #ifdef WOLFSSL_AES_CFB 07725 if (mode == AES_CFB_MODE) { 07726 *(reg++) = *out; 07727 } 07728 #endif 07729 out++; 07730 aes->left--; 07731 } 07732 } 07733 07734 return 0; 07735 } 07736 07737 07738 #ifdef HAVE_AES_DECRYPT 07739 /* CFB 128 07740 * 07741 * aes structure holding key to use for decryption 07742 * out buffer to hold result of decryption (must be at least as large as input 07743 * buffer) 07744 * in buffer to decrypt 07745 * sz size of input buffer 07746 * 07747 * returns 0 on success and negative error values on failure 07748 */ 07749 /* Software AES - CFB Decrypt */ 07750 static int wc_AesFeedbackDecrypt(Aes* aes, byte* out, const byte* in, word32 sz, 07751 byte mode) 07752 { 07753 byte* tmp; 07754 07755 if (aes == NULL || out == NULL || in == NULL) { 07756 return BAD_FUNC_ARG; 07757 } 07758 07759 #ifdef WOLFSSL_AES_CFB 07760 /* check if more input needs copied over to aes->reg */ 07761 if (aes->left && sz && mode == AES_CFB_MODE) { 07762 int size = min(aes->left, sz); 07763 XMEMCPY((byte*)aes->reg + AES_BLOCK_SIZE - aes->left, in, size); 07764 } 07765 #endif 07766 07767 /* consume any unused bytes left in aes->tmp */ 07768 tmp = (byte*)aes->tmp + AES_BLOCK_SIZE - aes->left; 07769 while (aes->left && sz) { 07770 *(out++) = *(in++) ^ *(tmp++); 07771 aes->left--; 07772 sz--; 07773 } 07774 07775 while (sz > AES_BLOCK_SIZE) { 07776 /* Using aes->tmp here for inline case i.e. in=out */ 07777 wc_AesEncryptDirect(aes, (byte*)aes->tmp, (byte*)aes->reg); 07778 #ifdef WOLFSSL_AES_OFB 07779 if (mode == AES_OFB_MODE) { 07780 XMEMCPY((byte*)aes->reg, (byte*)aes->tmp, AES_BLOCK_SIZE); 07781 } 07782 #endif 07783 xorbuf((byte*)aes->tmp, in, AES_BLOCK_SIZE); 07784 #ifdef WOLFSSL_AES_CFB 07785 if (mode == AES_CFB_MODE) { 07786 XMEMCPY(aes->reg, in, AES_BLOCK_SIZE); 07787 } 07788 #endif 07789 XMEMCPY(out, (byte*)aes->tmp, AES_BLOCK_SIZE); 07790 out += AES_BLOCK_SIZE; 07791 in += AES_BLOCK_SIZE; 07792 sz -= AES_BLOCK_SIZE; 07793 aes->left = 0; 07794 } 07795 07796 /* decrypt left over data */ 07797 if (sz) { 07798 wc_AesEncryptDirect(aes, (byte*)aes->tmp, (byte*)aes->reg); 07799 #ifdef WOLFSSL_AES_CFB 07800 if (mode == AES_CFB_MODE) { 07801 XMEMCPY(aes->reg, in, sz); 07802 } 07803 #endif 07804 #ifdef WOLFSSL_AES_OFB 07805 if (mode == AES_OFB_MODE) { 07806 XMEMCPY(aes->reg, aes->tmp, AES_BLOCK_SIZE); 07807 } 07808 #endif 07809 07810 aes->left = AES_BLOCK_SIZE; 07811 tmp = (byte*)aes->tmp; 07812 07813 while (sz--) { 07814 *(out++) = *(in++) ^ *(tmp++); 07815 aes->left--; 07816 } 07817 } 07818 07819 return 0; 07820 } 07821 #endif /* HAVE_AES_DECRYPT */ 07822 #endif /* WOLFSSL_AES_CFB */ 07823 07824 #ifdef WOLFSSL_AES_CFB 07825 /* CFB 128 07826 * 07827 * aes structure holding key to use for encryption 07828 * out buffer to hold result of encryption (must be at least as large as input 07829 * buffer) 07830 * in buffer to encrypt 07831 * sz size of input buffer 07832 * 07833 * returns 0 on success and negative error values on failure 07834 */ 07835 /* Software AES - CFB Encrypt */ 07836 int wc_AesCfbEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 07837 { 07838 return wc_AesFeedbackEncrypt(aes, out, in, sz, AES_CFB_MODE); 07839 } 07840 07841 07842 #ifdef HAVE_AES_DECRYPT 07843 /* CFB 128 07844 * 07845 * aes structure holding key to use for decryption 07846 * out buffer to hold result of decryption (must be at least as large as input 07847 * buffer) 07848 * in buffer to decrypt 07849 * sz size of input buffer 07850 * 07851 * returns 0 on success and negative error values on failure 07852 */ 07853 /* Software AES - CFB Decrypt */ 07854 int wc_AesCfbDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 07855 { 07856 return wc_AesFeedbackDecrypt(aes, out, in, sz, AES_CFB_MODE); 07857 } 07858 #endif /* HAVE_AES_DECRYPT */ 07859 07860 07861 /* shift the whole AES_BLOCK_SIZE array left by 8 or 1 bits */ 07862 static void shiftLeftArray(byte* ary, byte shift) 07863 { 07864 int i; 07865 07866 if (shift == WOLFSSL_BIT_SIZE) { 07867 /* shifting over by 8 bits */ 07868 for (i = 0; i < AES_BLOCK_SIZE - 1; i++) { 07869 ary[i] = ary[i+1]; 07870 } 07871 ary[i] = 0; 07872 } 07873 else { 07874 byte carry = 0; 07875 07876 /* shifting over by 7 or less bits */ 07877 for (i = 0; i < AES_BLOCK_SIZE - 1; i++) { 07878 carry = ary[i+1] & (0XFF << (WOLFSSL_BIT_SIZE - shift)); 07879 carry >>= (WOLFSSL_BIT_SIZE - shift); 07880 ary[i] = (ary[i] << shift) + carry; 07881 } 07882 ary[i] = ary[i] << shift; 07883 } 07884 } 07885 07886 07887 /* returns 0 on success and negative values on failure */ 07888 static int wc_AesFeedbackCFB8(Aes* aes, byte* out, const byte* in, 07889 word32 sz, byte dir) 07890 { 07891 byte *pt; 07892 07893 if (aes == NULL || out == NULL || in == NULL) { 07894 return BAD_FUNC_ARG; 07895 } 07896 07897 if (sz == 0) { 07898 return 0; 07899 } 07900 07901 while (sz > 0) { 07902 wc_AesEncryptDirect(aes, (byte*)aes->tmp, (byte*)aes->reg); 07903 if (dir == AES_DECRYPTION) { 07904 pt = (byte*)aes->reg; 07905 07906 /* LSB + CAT */ 07907 shiftLeftArray(pt, WOLFSSL_BIT_SIZE); 07908 pt[AES_BLOCK_SIZE - 1] = in[0]; 07909 } 07910 07911 /* MSB + XOR */ 07912 out[0] = aes->tmp[0] ^ in[0]; 07913 if (dir == AES_ENCRYPTION) { 07914 pt = (byte*)aes->reg; 07915 07916 /* LSB + CAT */ 07917 shiftLeftArray(pt, WOLFSSL_BIT_SIZE); 07918 pt[AES_BLOCK_SIZE - 1] = out[0]; 07919 } 07920 07921 out += 1; 07922 in += 1; 07923 sz -= 1; 07924 } 07925 07926 return 0; 07927 } 07928 07929 07930 /* returns 0 on success and negative values on failure */ 07931 static int wc_AesFeedbackCFB1(Aes* aes, byte* out, const byte* in, 07932 word32 sz, byte dir) 07933 { 07934 byte tmp; 07935 byte cur = 0; /* hold current work in order to handle inline in=out */ 07936 byte* pt; 07937 int bit = 7; 07938 07939 if (aes == NULL || out == NULL || in == NULL) { 07940 return BAD_FUNC_ARG; 07941 } 07942 07943 if (sz == 0) { 07944 return 0; 07945 } 07946 07947 while (sz > 0) { 07948 wc_AesEncryptDirect(aes, (byte*)aes->tmp, (byte*)aes->reg); 07949 if (dir == AES_DECRYPTION) { 07950 pt = (byte*)aes->reg; 07951 07952 /* LSB + CAT */ 07953 tmp = (0X01 << bit) & in[0]; 07954 tmp = tmp >> bit; 07955 tmp &= 0x01; 07956 shiftLeftArray((byte*)aes->reg, 1); 07957 pt[AES_BLOCK_SIZE - 1] |= tmp; 07958 } 07959 07960 /* MSB + XOR */ 07961 tmp = (0X01 << bit) & in[0]; 07962 pt = (byte*)aes->tmp; 07963 tmp = (pt[0] >> 7) ^ (tmp >> bit); 07964 tmp &= 0x01; 07965 cur |= (tmp << bit); 07966 07967 07968 if (dir == AES_ENCRYPTION) { 07969 pt = (byte*)aes->reg; 07970 07971 /* LSB + CAT */ 07972 shiftLeftArray((byte*)aes->reg, 1); 07973 pt[AES_BLOCK_SIZE - 1] |= tmp; 07974 } 07975 07976 bit--; 07977 if (bit < 0) { 07978 out[0] = cur; 07979 out += 1; 07980 in += 1; 07981 sz -= 1; 07982 bit = 7; 07983 cur = 0; 07984 } 07985 else { 07986 sz -= 1; 07987 } 07988 } 07989 07990 if (bit > 0 && bit < 7) { 07991 out[0] = cur; 07992 } 07993 07994 return 0; 07995 } 07996 07997 07998 /* CFB 1 07999 * 08000 * aes structure holding key to use for encryption 08001 * out buffer to hold result of encryption (must be at least as large as input 08002 * buffer) 08003 * in buffer to encrypt (packed to left, i.e. 101 is 0x90) 08004 * sz size of input buffer in bits (0x1 would be size of 1 and 0xFF size of 8) 08005 * 08006 * returns 0 on success and negative values on failure 08007 */ 08008 int wc_AesCfb1Encrypt(Aes* aes, byte* out, const byte* in, word32 sz) 08009 { 08010 return wc_AesFeedbackCFB1(aes, out, in, sz, AES_ENCRYPTION); 08011 } 08012 08013 08014 /* CFB 8 08015 * 08016 * aes structure holding key to use for encryption 08017 * out buffer to hold result of encryption (must be at least as large as input 08018 * buffer) 08019 * in buffer to encrypt 08020 * sz size of input buffer 08021 * 08022 * returns 0 on success and negative values on failure 08023 */ 08024 int wc_AesCfb8Encrypt(Aes* aes, byte* out, const byte* in, word32 sz) 08025 { 08026 return wc_AesFeedbackCFB8(aes, out, in, sz, AES_ENCRYPTION); 08027 } 08028 #ifdef HAVE_AES_DECRYPT 08029 08030 /* CFB 1 08031 * 08032 * aes structure holding key to use for encryption 08033 * out buffer to hold result of encryption (must be at least as large as input 08034 * buffer) 08035 * in buffer to encrypt 08036 * sz size of input buffer in bits (0x1 would be size of 1 and 0xFF size of 8) 08037 * 08038 * returns 0 on success and negative values on failure 08039 */ 08040 int wc_AesCfb1Decrypt(Aes* aes, byte* out, const byte* in, word32 sz) 08041 { 08042 return wc_AesFeedbackCFB1(aes, out, in, sz, AES_DECRYPTION); 08043 } 08044 08045 08046 /* CFB 8 08047 * 08048 * aes structure holding key to use for encryption 08049 * out buffer to hold result of encryption (must be at least as large as input 08050 * buffer) 08051 * in buffer to encrypt 08052 * sz size of input buffer 08053 * 08054 * returns 0 on success and negative values on failure 08055 */ 08056 int wc_AesCfb8Decrypt(Aes* aes, byte* out, const byte* in, word32 sz) 08057 { 08058 return wc_AesFeedbackCFB8(aes, out, in, sz, AES_DECRYPTION); 08059 } 08060 #endif /* HAVE_AES_DECRYPT */ 08061 #endif /* WOLFSSL_AES_CFB */ 08062 08063 #ifdef WOLFSSL_AES_OFB 08064 /* OFB 08065 * 08066 * aes structure holding key to use for encryption 08067 * out buffer to hold result of encryption (must be at least as large as input 08068 * buffer) 08069 * in buffer to encrypt 08070 * sz size of input buffer 08071 * 08072 * returns 0 on success and negative error values on failure 08073 */ 08074 /* Software AES - CFB Encrypt */ 08075 int wc_AesOfbEncrypt(Aes* aes, byte* out, const byte* in, word32 sz) 08076 { 08077 return wc_AesFeedbackEncrypt(aes, out, in, sz, AES_OFB_MODE); 08078 } 08079 08080 08081 #ifdef HAVE_AES_DECRYPT 08082 /* OFB 08083 * 08084 * aes structure holding key to use for decryption 08085 * out buffer to hold result of decryption (must be at least as large as input 08086 * buffer) 08087 * in buffer to decrypt 08088 * sz size of input buffer 08089 * 08090 * returns 0 on success and negative error values on failure 08091 */ 08092 /* Software AES - OFB Decrypt */ 08093 int wc_AesOfbDecrypt(Aes* aes, byte* out, const byte* in, word32 sz) 08094 { 08095 return wc_AesFeedbackDecrypt(aes, out, in, sz, AES_OFB_MODE); 08096 } 08097 #endif /* HAVE_AES_DECRYPT */ 08098 #endif /* WOLFSSL_AES_OFB */ 08099 08100 08101 #ifdef HAVE_AES_KEYWRAP 08102 08103 /* Initialize key wrap counter with value */ 08104 static WC_INLINE void InitKeyWrapCounter(byte* inOutCtr, word32 value) 08105 { 08106 int i; 08107 word32 bytes; 08108 08109 bytes = sizeof(word32); 08110 for (i = 0; i < (int)sizeof(word32); i++) { 08111 inOutCtr[i+sizeof(word32)] = (value >> ((bytes - 1) * 8)) & 0xFF; 08112 bytes--; 08113 } 08114 } 08115 08116 /* Increment key wrap counter */ 08117 static WC_INLINE void IncrementKeyWrapCounter(byte* inOutCtr) 08118 { 08119 int i; 08120 08121 /* in network byte order so start at end and work back */ 08122 for (i = KEYWRAP_BLOCK_SIZE - 1; i >= 0; i--) { 08123 if (++inOutCtr[i]) /* we're done unless we overflow */ 08124 return; 08125 } 08126 } 08127 08128 /* Decrement key wrap counter */ 08129 static WC_INLINE void DecrementKeyWrapCounter(byte* inOutCtr) 08130 { 08131 int i; 08132 08133 for (i = KEYWRAP_BLOCK_SIZE - 1; i >= 0; i--) { 08134 if (--inOutCtr[i] != 0xFF) /* we're done unless we underflow */ 08135 return; 08136 } 08137 } 08138 08139 /* perform AES key wrap (RFC3394), return out sz on success, negative on err */ 08140 int wc_AesKeyWrap(const byte* key, word32 keySz, const byte* in, word32 inSz, 08141 byte* out, word32 outSz, const byte* iv) 08142 { 08143 Aes aes; 08144 byte* r; 08145 word32 i; 08146 int ret, j; 08147 08148 byte t[KEYWRAP_BLOCK_SIZE]; 08149 byte tmp[AES_BLOCK_SIZE]; 08150 08151 /* n must be at least 2, output size is n + 8 bytes */ 08152 if (key == NULL || in == NULL || inSz < 2 || 08153 out == NULL || outSz < (inSz + KEYWRAP_BLOCK_SIZE)) 08154 return BAD_FUNC_ARG; 08155 08156 /* input must be multiple of 64-bits */ 08157 if (inSz % KEYWRAP_BLOCK_SIZE != 0) 08158 return BAD_FUNC_ARG; 08159 08160 /* user IV is optional */ 08161 if (iv == NULL) { 08162 XMEMSET(tmp, 0xA6, KEYWRAP_BLOCK_SIZE); 08163 } else { 08164 XMEMCPY(tmp, iv, KEYWRAP_BLOCK_SIZE); 08165 } 08166 08167 r = out + 8; 08168 XMEMCPY(r, in, inSz); 08169 XMEMSET(t, 0, sizeof(t)); 08170 08171 ret = wc_AesInit(&aes, NULL, INVALID_DEVID); 08172 if (ret != 0) 08173 return ret; 08174 08175 ret = wc_AesSetKey(&aes, key, keySz, NULL, AES_ENCRYPTION); 08176 if (ret != 0) 08177 return ret; 08178 08179 for (j = 0; j <= 5; j++) { 08180 for (i = 1; i <= inSz / KEYWRAP_BLOCK_SIZE; i++) { 08181 08182 /* load R[i] */ 08183 XMEMCPY(tmp + KEYWRAP_BLOCK_SIZE, r, KEYWRAP_BLOCK_SIZE); 08184 08185 wc_AesEncryptDirect(&aes, tmp, tmp); 08186 08187 /* calculate new A */ 08188 IncrementKeyWrapCounter(t); 08189 xorbuf(tmp, t, KEYWRAP_BLOCK_SIZE); 08190 08191 /* save R[i] */ 08192 XMEMCPY(r, tmp + KEYWRAP_BLOCK_SIZE, KEYWRAP_BLOCK_SIZE); 08193 r += KEYWRAP_BLOCK_SIZE; 08194 } 08195 r = out + KEYWRAP_BLOCK_SIZE; 08196 } 08197 08198 /* C[0] = A */ 08199 XMEMCPY(out, tmp, KEYWRAP_BLOCK_SIZE); 08200 08201 wc_AesFree(&aes); 08202 08203 return inSz + KEYWRAP_BLOCK_SIZE; 08204 } 08205 08206 int wc_AesKeyUnWrap(const byte* key, word32 keySz, const byte* in, word32 inSz, 08207 byte* out, word32 outSz, const byte* iv) 08208 { 08209 Aes aes; 08210 byte* r; 08211 word32 i, n; 08212 int ret, j; 08213 08214 byte t[KEYWRAP_BLOCK_SIZE]; 08215 byte tmp[AES_BLOCK_SIZE]; 08216 08217 const byte* expIv; 08218 const byte defaultIV[] = { 08219 0xA6, 0xA6, 0xA6, 0xA6, 0xA6, 0xA6, 0xA6, 0xA6 08220 }; 08221 08222 (void)iv; 08223 08224 if (key == NULL || in == NULL || inSz < 3 || 08225 out == NULL || outSz < (inSz - KEYWRAP_BLOCK_SIZE)) 08226 return BAD_FUNC_ARG; 08227 08228 /* input must be multiple of 64-bits */ 08229 if (inSz % KEYWRAP_BLOCK_SIZE != 0) 08230 return BAD_FUNC_ARG; 08231 08232 /* user IV optional */ 08233 if (iv != NULL) { 08234 expIv = iv; 08235 } else { 08236 expIv = defaultIV; 08237 } 08238 08239 /* A = C[0], R[i] = C[i] */ 08240 XMEMCPY(tmp, in, KEYWRAP_BLOCK_SIZE); 08241 XMEMCPY(out, in + KEYWRAP_BLOCK_SIZE, inSz - KEYWRAP_BLOCK_SIZE); 08242 XMEMSET(t, 0, sizeof(t)); 08243 08244 ret = wc_AesInit(&aes, NULL, INVALID_DEVID); 08245 if (ret != 0) 08246 return ret; 08247 08248 ret = wc_AesSetKey(&aes, key, keySz, NULL, AES_DECRYPTION); 08249 if (ret != 0) 08250 return ret; 08251 08252 /* initialize counter to 6n */ 08253 n = (inSz - 1) / KEYWRAP_BLOCK_SIZE; 08254 InitKeyWrapCounter(t, 6 * n); 08255 08256 for (j = 5; j >= 0; j--) { 08257 for (i = n; i >= 1; i--) { 08258 08259 /* calculate A */ 08260 xorbuf(tmp, t, KEYWRAP_BLOCK_SIZE); 08261 DecrementKeyWrapCounter(t); 08262 08263 /* load R[i], starting at end of R */ 08264 r = out + ((i - 1) * KEYWRAP_BLOCK_SIZE); 08265 XMEMCPY(tmp + KEYWRAP_BLOCK_SIZE, r, KEYWRAP_BLOCK_SIZE); 08266 wc_AesDecryptDirect(&aes, tmp, tmp); 08267 08268 /* save R[i] */ 08269 XMEMCPY(r, tmp + KEYWRAP_BLOCK_SIZE, KEYWRAP_BLOCK_SIZE); 08270 } 08271 } 08272 08273 wc_AesFree(&aes); 08274 08275 /* verify IV */ 08276 if (XMEMCMP(tmp, expIv, KEYWRAP_BLOCK_SIZE) != 0) 08277 return BAD_KEYWRAP_IV_E; 08278 08279 return inSz - KEYWRAP_BLOCK_SIZE; 08280 } 08281 08282 #endif /* HAVE_AES_KEYWRAP */ 08283 08284 #ifdef WOLFSSL_AES_XTS 08285 08286 /* Galios Field to use */ 08287 #define GF_XTS 0x87 08288 08289 /* This is to help with setting keys to correct encrypt or decrypt type. 08290 * 08291 * tweak AES key for tweak in XTS 08292 * aes AES key for encrypt/decrypt process 08293 * key buffer holding aes key | tweak key 08294 * len length of key buffer in bytes. Should be twice that of key size. i.e. 08295 * 32 for a 16 byte key. 08296 * dir direction, either AES_ENCRYPTION or AES_DECRYPTION 08297 * heap heap hint to use for memory. Can be NULL 08298 * devId id to use with async crypto. Can be 0 08299 * 08300 * Note: is up to user to call wc_AesFree on tweak and aes key when done. 08301 * 08302 * return 0 on success 08303 */ 08304 int wc_AesXtsSetKey(XtsAes* aes, const byte* key, word32 len, int dir, 08305 void* heap, int devId) 08306 { 08307 word32 keySz; 08308 int ret = 0; 08309 08310 if (aes == NULL || key == NULL) { 08311 return BAD_FUNC_ARG; 08312 } 08313 08314 if ((ret = wc_AesInit(&aes->tweak, heap, devId)) != 0) { 08315 return ret; 08316 } 08317 if ((ret = wc_AesInit(&aes->aes, heap, devId)) != 0) { 08318 return ret; 08319 } 08320 08321 keySz = len/2; 08322 if (keySz != 16 && keySz != 32) { 08323 WOLFSSL_MSG("Unsupported key size"); 08324 return WC_KEY_SIZE_E; 08325 } 08326 08327 if ((ret = wc_AesSetKey(&aes->aes, key, keySz, NULL, dir)) == 0) { 08328 ret = wc_AesSetKey(&aes->tweak, key + keySz, keySz, NULL, 08329 AES_ENCRYPTION); 08330 if (ret != 0) { 08331 wc_AesFree(&aes->aes); 08332 } 08333 } 08334 08335 return ret; 08336 } 08337 08338 08339 /* This is used to free up resources used by Aes structs 08340 * 08341 * aes AES keys to free 08342 * 08343 * return 0 on success 08344 */ 08345 int wc_AesXtsFree(XtsAes* aes) 08346 { 08347 if (aes != NULL) { 08348 wc_AesFree(&aes->aes); 08349 wc_AesFree(&aes->tweak); 08350 } 08351 08352 return 0; 08353 } 08354 08355 08356 /* Same process as wc_AesXtsEncrypt but uses a word64 type as the tweak value 08357 * instead of a byte array. This just converts the word64 to a byte array and 08358 * calls wc_AesXtsEncrypt. 08359 * 08360 * aes AES keys to use for block encrypt/decrypt 08361 * out output buffer to hold cipher text 08362 * in input plain text buffer to encrypt 08363 * sz size of both out and in buffers 08364 * sector value to use for tweak 08365 * 08366 * returns 0 on success 08367 */ 08368 int wc_AesXtsEncryptSector(XtsAes* aes, byte* out, const byte* in, 08369 word32 sz, word64 sector) 08370 { 08371 byte* pt; 08372 byte i[AES_BLOCK_SIZE]; 08373 08374 XMEMSET(i, 0, AES_BLOCK_SIZE); 08375 #ifdef BIG_ENDIAN_ORDER 08376 sector = ByteReverseWord64(sector); 08377 #endif 08378 pt = (byte*)§or; 08379 XMEMCPY(i, pt, sizeof(word64)); 08380 08381 return wc_AesXtsEncrypt(aes, out, in, sz, (const byte*)i, AES_BLOCK_SIZE); 08382 } 08383 08384 08385 /* Same process as wc_AesXtsDecrypt but uses a word64 type as the tweak value 08386 * instead of a byte array. This just converts the word64 to a byte array. 08387 * 08388 * aes AES keys to use for block encrypt/decrypt 08389 * out output buffer to hold plain text 08390 * in input cipher text buffer to encrypt 08391 * sz size of both out and in buffers 08392 * sector value to use for tweak 08393 * 08394 * returns 0 on success 08395 */ 08396 int wc_AesXtsDecryptSector(XtsAes* aes, byte* out, const byte* in, word32 sz, 08397 word64 sector) 08398 { 08399 byte* pt; 08400 byte i[AES_BLOCK_SIZE]; 08401 08402 XMEMSET(i, 0, AES_BLOCK_SIZE); 08403 #ifdef BIG_ENDIAN_ORDER 08404 sector = ByteReverseWord64(sector); 08405 #endif 08406 pt = (byte*)§or; 08407 XMEMCPY(i, pt, sizeof(word64)); 08408 08409 return wc_AesXtsDecrypt(aes, out, in, sz, (const byte*)i, AES_BLOCK_SIZE); 08410 } 08411 08412 #ifdef HAVE_AES_ECB 08413 /* helper function for encrypting / decrypting full buffer at once */ 08414 static int _AesXtsHelper(Aes* aes, byte* out, const byte* in, word32 sz, int dir) 08415 { 08416 word32 outSz = sz; 08417 word32 totalSz = (sz / AES_BLOCK_SIZE) * AES_BLOCK_SIZE; /* total bytes */ 08418 byte* pt = out; 08419 08420 outSz -= AES_BLOCK_SIZE; 08421 08422 while (outSz > 0) { 08423 word32 j; 08424 byte carry = 0; 08425 08426 /* multiply by shift left and propagate carry */ 08427 for (j = 0; j < AES_BLOCK_SIZE && outSz > 0; j++, outSz--) { 08428 byte tmpC; 08429 08430 tmpC = (pt[j] >> 7) & 0x01; 08431 pt[j+AES_BLOCK_SIZE] = ((pt[j] << 1) + carry) & 0xFF; 08432 carry = tmpC; 08433 } 08434 if (carry) { 08435 pt[AES_BLOCK_SIZE] ^= GF_XTS; 08436 } 08437 08438 pt += AES_BLOCK_SIZE; 08439 } 08440 08441 xorbuf(out, in, totalSz); 08442 if (dir == AES_ENCRYPTION) { 08443 return wc_AesEcbEncrypt(aes, out, out, totalSz); 08444 } 08445 else { 08446 return wc_AesEcbDecrypt(aes, out, out, totalSz); 08447 } 08448 } 08449 #endif /* HAVE_AES_ECB */ 08450 08451 08452 /* AES with XTS mode. (XTS) XEX encryption with Tweak and cipher text Stealing. 08453 * 08454 * xaes AES keys to use for block encrypt/decrypt 08455 * out output buffer to hold cipher text 08456 * in input plain text buffer to encrypt 08457 * sz size of both out and in buffers 08458 * i value to use for tweak 08459 * iSz size of i buffer, should always be AES_BLOCK_SIZE but having this input 08460 * adds a sanity check on how the user calls the function. 08461 * 08462 * returns 0 on success 08463 */ 08464 /* Software AES - XTS Encrypt */ 08465 int wc_AesXtsEncrypt(XtsAes* xaes, byte* out, const byte* in, word32 sz, 08466 const byte* i, word32 iSz) 08467 { 08468 int ret = 0; 08469 word32 blocks = (sz / AES_BLOCK_SIZE); 08470 Aes *aes, *tweak; 08471 08472 if (xaes == NULL || out == NULL || in == NULL) { 08473 return BAD_FUNC_ARG; 08474 } 08475 08476 aes = &xaes->aes; 08477 tweak = &xaes->tweak; 08478 08479 if (iSz < AES_BLOCK_SIZE) { 08480 return BAD_FUNC_ARG; 08481 } 08482 08483 if (blocks > 0) { 08484 byte tmp[AES_BLOCK_SIZE]; 08485 08486 XMEMSET(tmp, 0, AES_BLOCK_SIZE); /* set to 0's in case of improper AES 08487 * key setup passed to encrypt direct*/ 08488 08489 wc_AesEncryptDirect(tweak, tmp, i); 08490 08491 #ifdef HAVE_AES_ECB 08492 /* encrypt all of buffer at once when possible */ 08493 if (in != out) { /* can not handle inline */ 08494 XMEMCPY(out, tmp, AES_BLOCK_SIZE); 08495 if ((ret = _AesXtsHelper(aes, out, in, sz, AES_ENCRYPTION)) != 0) { 08496 return ret; 08497 } 08498 } 08499 #endif 08500 08501 while (blocks > 0) { 08502 word32 j; 08503 byte carry = 0; 08504 byte buf[AES_BLOCK_SIZE]; 08505 08506 #ifdef HAVE_AES_ECB 08507 if (in == out) { /* check for if inline */ 08508 #endif 08509 XMEMCPY(buf, in, AES_BLOCK_SIZE); 08510 xorbuf(buf, tmp, AES_BLOCK_SIZE); 08511 wc_AesEncryptDirect(aes, out, buf); 08512 #ifdef HAVE_AES_ECB 08513 } 08514 #endif 08515 xorbuf(out, tmp, AES_BLOCK_SIZE); 08516 08517 /* multiply by shift left and propagate carry */ 08518 for (j = 0; j < AES_BLOCK_SIZE; j++) { 08519 byte tmpC; 08520 08521 tmpC = (tmp[j] >> 7) & 0x01; 08522 tmp[j] = ((tmp[j] << 1) + carry) & 0xFF; 08523 carry = tmpC; 08524 } 08525 if (carry) { 08526 tmp[0] ^= GF_XTS; 08527 } 08528 08529 in += AES_BLOCK_SIZE; 08530 out += AES_BLOCK_SIZE; 08531 sz -= AES_BLOCK_SIZE; 08532 blocks--; 08533 } 08534 08535 /* stealing operation of XTS to handle left overs */ 08536 if (sz > 0) { 08537 byte buf[AES_BLOCK_SIZE]; 08538 08539 XMEMCPY(buf, out - AES_BLOCK_SIZE, AES_BLOCK_SIZE); 08540 if (sz >= AES_BLOCK_SIZE) { /* extra sanity check before copy */ 08541 return BUFFER_E; 08542 } 08543 XMEMCPY(out, buf, sz); 08544 XMEMCPY(buf, in, sz); 08545 08546 xorbuf(buf, tmp, AES_BLOCK_SIZE); 08547 wc_AesEncryptDirect(aes, out - AES_BLOCK_SIZE, buf); 08548 xorbuf(out - AES_BLOCK_SIZE, tmp, AES_BLOCK_SIZE); 08549 } 08550 } 08551 else { 08552 WOLFSSL_MSG("Plain text input too small for encryption"); 08553 return BAD_FUNC_ARG; 08554 } 08555 08556 return ret; 08557 } 08558 08559 08560 /* Same process as encryption but Aes key is AES_DECRYPTION type. 08561 * 08562 * xaes AES keys to use for block encrypt/decrypt 08563 * out output buffer to hold plain text 08564 * in input cipher text buffer to decrypt 08565 * sz size of both out and in buffers 08566 * i value to use for tweak 08567 * iSz size of i buffer, should always be AES_BLOCK_SIZE but having this input 08568 * adds a sanity check on how the user calls the function. 08569 * 08570 * returns 0 on success 08571 */ 08572 /* Software AES - XTS Decrypt */ 08573 int wc_AesXtsDecrypt(XtsAes* xaes, byte* out, const byte* in, word32 sz, 08574 const byte* i, word32 iSz) 08575 { 08576 int ret = 0; 08577 word32 blocks = (sz / AES_BLOCK_SIZE); 08578 Aes *aes, *tweak; 08579 08580 if (xaes == NULL || out == NULL || in == NULL) { 08581 return BAD_FUNC_ARG; 08582 } 08583 08584 aes = &xaes->aes; 08585 tweak = &xaes->tweak; 08586 08587 if (iSz < AES_BLOCK_SIZE) { 08588 return BAD_FUNC_ARG; 08589 } 08590 08591 if (blocks > 0) { 08592 word32 j; 08593 byte carry = 0; 08594 byte tmp[AES_BLOCK_SIZE]; 08595 byte stl = (sz % AES_BLOCK_SIZE); 08596 08597 XMEMSET(tmp, 0, AES_BLOCK_SIZE); /* set to 0's in case of improper AES 08598 * key setup passed to decrypt direct*/ 08599 08600 wc_AesEncryptDirect(tweak, tmp, i); 08601 08602 /* if Stealing then break out of loop one block early to handle special 08603 * case */ 08604 if (stl > 0) { 08605 blocks--; 08606 } 08607 08608 #ifdef HAVE_AES_ECB 08609 /* decrypt all of buffer at once when possible */ 08610 if (in != out) { /* can not handle inline */ 08611 XMEMCPY(out, tmp, AES_BLOCK_SIZE); 08612 if ((ret = _AesXtsHelper(aes, out, in, sz, AES_DECRYPTION)) != 0) { 08613 return ret; 08614 } 08615 } 08616 #endif 08617 08618 while (blocks > 0) { 08619 byte buf[AES_BLOCK_SIZE]; 08620 08621 #ifdef HAVE_AES_ECB 08622 if (in == out) { /* check for if inline */ 08623 #endif 08624 XMEMCPY(buf, in, AES_BLOCK_SIZE); 08625 xorbuf(buf, tmp, AES_BLOCK_SIZE); 08626 wc_AesDecryptDirect(aes, out, buf); 08627 #ifdef HAVE_AES_ECB 08628 } 08629 #endif 08630 xorbuf(out, tmp, AES_BLOCK_SIZE); 08631 08632 /* multiply by shift left and propagate carry */ 08633 for (j = 0; j < AES_BLOCK_SIZE; j++) { 08634 byte tmpC; 08635 08636 tmpC = (tmp[j] >> 7) & 0x01; 08637 tmp[j] = ((tmp[j] << 1) + carry) & 0xFF; 08638 carry = tmpC; 08639 } 08640 if (carry) { 08641 tmp[0] ^= GF_XTS; 08642 } 08643 carry = 0; 08644 08645 in += AES_BLOCK_SIZE; 08646 out += AES_BLOCK_SIZE; 08647 sz -= AES_BLOCK_SIZE; 08648 blocks--; 08649 } 08650 08651 /* stealing operation of XTS to handle left overs */ 08652 if (sz > 0) { 08653 byte buf[AES_BLOCK_SIZE]; 08654 byte tmp2[AES_BLOCK_SIZE]; 08655 08656 /* multiply by shift left and propagate carry */ 08657 for (j = 0; j < AES_BLOCK_SIZE; j++) { 08658 byte tmpC; 08659 08660 tmpC = (tmp[j] >> 7) & 0x01; 08661 tmp2[j] = ((tmp[j] << 1) + carry) & 0xFF; 08662 carry = tmpC; 08663 } 08664 if (carry) { 08665 tmp2[0] ^= GF_XTS; 08666 } 08667 08668 XMEMCPY(buf, in, AES_BLOCK_SIZE); 08669 xorbuf(buf, tmp2, AES_BLOCK_SIZE); 08670 wc_AesDecryptDirect(aes, out, buf); 08671 xorbuf(out, tmp2, AES_BLOCK_SIZE); 08672 08673 /* tmp2 holds partial | last */ 08674 XMEMCPY(tmp2, out, AES_BLOCK_SIZE); 08675 in += AES_BLOCK_SIZE; 08676 out += AES_BLOCK_SIZE; 08677 sz -= AES_BLOCK_SIZE; 08678 08679 /* Make buffer with end of cipher text | last */ 08680 XMEMCPY(buf, tmp2, AES_BLOCK_SIZE); 08681 if (sz >= AES_BLOCK_SIZE) { /* extra sanity check before copy */ 08682 return BUFFER_E; 08683 } 08684 XMEMCPY(buf, in, sz); 08685 XMEMCPY(out, tmp2, sz); 08686 08687 xorbuf(buf, tmp, AES_BLOCK_SIZE); 08688 wc_AesDecryptDirect(aes, tmp2, buf); 08689 xorbuf(tmp2, tmp, AES_BLOCK_SIZE); 08690 XMEMCPY(out - AES_BLOCK_SIZE, tmp2, AES_BLOCK_SIZE); 08691 } 08692 } 08693 else { 08694 WOLFSSL_MSG("Plain text input too small for encryption"); 08695 return BAD_FUNC_ARG; 08696 } 08697 08698 return ret; 08699 } 08700 08701 #endif /* WOLFSSL_AES_XTS */ 08702 08703 #endif /* HAVE_FIPS */ 08704 #endif /* !NO_AES */ 08705
Generated on Tue Jul 12 2022 20:58:32 by 1.7.2