328 lines
16 KiB
C
328 lines
16 KiB
C
/*
|
|
==============================================================================
|
|
Name : main.c
|
|
Author : polfosol
|
|
Version : 9.1.1.0
|
|
Copyright : copyright © 2022 - polfosol
|
|
Description : test vectors for µAES ™ library, mostly generated by Crypto++ ®
|
|
==============================================================================
|
|
*/
|
|
|
|
#include "micro_aes.h"
|
|
#define TestStringSize 114 /* hex characters in plain-text */
|
|
#define BuffL ((TestStringSize / 2 + 31) & ~15)
|
|
|
|
static const char
|
|
*masterKey = "0001020304050607 08090A0B0C0D0E0F 1011121314151617 18191A1B1C1D1E1F",
|
|
*secretKey = "0011223344556677 8899AABBCCDDEEFF 0001020304050607 08090A0B0C0D0E0F",
|
|
*cipherKey = "279fb74a7572135e 8f9b8ef6d1eee003 69c4e0d86a7b0430 d8cdb78070b4c55a",
|
|
*iVec = "8ea2b7ca516745bf eafc49904b496089",
|
|
*plainText = "c9f775baafa36c25 cd610d3c75a482ea dda97ca4864cdfe0 6eaf70a0ec0d7191\
|
|
d55027cf8f900214 e634412583ff0b47 8ea2b7ca516745bf ea",
|
|
#if AES_KEY_LENGTH == 16
|
|
*ecbcipher = "5d00c273f8b2607d a834632dcbb521f4 697dd4ab20bb0645 32a6545e24e33ae9\
|
|
f545176111f93773 dbecd262841cf83b 10d145e71b772cf7 a12889cda84be795",
|
|
#if !CTS /* ↑↑ and ↓↓ both zero-padded plain text. */
|
|
*cbccipher = "65c48fdf9fbd6261 28f2d8bac3f71251 75e7f4821fda0263 70011632779d7403\
|
|
7e9e2d298e154bc4 2dc7a9bc419b915d c119ef461ac4e1bc 8a7e36bf92b3b3d1",
|
|
#else
|
|
*cbccipher = "65c48fdf9fbd6261 28f2d8bac3f71251 75e7f4821fda0263 70011632779d7403\
|
|
c119ef461ac4e1bc 8a7e36bf92b3b3d1 7e9e2d298e154bc4 2d",
|
|
#endif
|
|
*cfbcipher = "edab3105e673bc9e b9102539a9f457bc 245c14e1bff81b5b 4a4a147c988cb0a6\
|
|
3f9c56525efbe64a 876ad1d761d3fc93 59fb4f5b2354acd4 90",
|
|
*ofbcipher = "edab3105e673bc9e b9102539a9f457bc d28c8e4c92995f5c d9426926be1e775d\
|
|
e22b8ce4d0278b18 181b8bec93b9726f 959aa5d701d46102 f0",
|
|
#if CTR_IV_LENGTH == 16
|
|
*ctrcipher = "edab3105e673bc9e b9102539a9f457bc f2e2606dfa3f93c5 c51b910a89cddb67\
|
|
191a118531ea0427 97626c9bfd370426 fdf3f59158bf7d4d 43",
|
|
#elif CTR_STARTVALUE == 1
|
|
*ctrcipher = "6c6bae886c235d8c 7997d45c1bf0bca2 48b4bca9eb396d1b f6945e5b7a4fc10f\
|
|
488cfe76fd5eaeff 2b8fb469f78fa61e 285e4cf9b9aee3d0 a8",
|
|
#endif
|
|
*xtscipher = "10f9301a157bfceb 3eb9e7bd38500b7e 959e21ba3cc1179a d7f7d7d99460e695\
|
|
5e8bcb177571c719 6de58ff28c381913 e7c82d0adfd90c45 ca",
|
|
*ccmcipher = "d2575123438338d7 0b2955537fdfcf41 729870884e85af15 f0a74975a72b337d\
|
|
04d426de87594b9a be3e6dcf07f21c99 db3999f81299d302 ad1e5ba683e9039a\
|
|
5483685f1bd2c3fa 3b", /* <---- with 16 bytes tag */
|
|
*gcmcipher = "5ceab5b7c2d6dede 555a23c7e3e63274 4075a51df482730b a31485ec987ddcc8\
|
|
73acdcfc6759a47b a424d838e7c0cb71 b9a4d8f4572e2141 18c8ab284ca845c1\
|
|
4394618703cddf3a fb", /* <---- with 16 bytes tag */
|
|
*ocbcipher = "fc254896eb785b05 dd87f240722dd935 61f5a0ef6aff2eb6 5953da0b26257ed0\
|
|
d69cb496e9a0cb1b f646151aa07e629a 28d99f0ffd7ea753 5c39f440df33c988\
|
|
c55cbcc8ac086ffa 23", /* <---- with 16 bytes tag */
|
|
#if EAXP
|
|
*eaxcipher = "f516e9c20069292c c51ba8b6403ddedf 5a34798f62187f58 d723fa33573fd80b\
|
|
f08ffbb09dadbd0b 6fa4812ca4bb5e6d db9a384943b36690 e81738a7a1",
|
|
#else /* ↑↑↑↑ with 4 bytes tag */
|
|
*eaxcipher = "4e2fa1bef9ffc23f 6965ee7135981c91 af9bfe97a6b13c01 b8b99e114dda2391\
|
|
50661c618335a005 47cca55a8f22fbd5 ed5ab4b4a17d0aa3 29febd14ef271bae\
|
|
986810a504f01ec6 02", /* <---- with 16 bytes tag */
|
|
#endif
|
|
*gsvcipher = "2f1488496ada3f70 9760420ac72e5acf a977f6add4c55ac6 85f1b9dff8f381e0\
|
|
2a64bbdd64cdd778 525462949bb0b141 db908c5cfa365750 3666f879ac879fcb\
|
|
f25c15d496a1e6f7 f8", /* <---- with 16 bytes tag */
|
|
*sivcipher = "f6d8137b17d58d13 af040e8abadd965b 9bae3a3de90ca6f7 049c2528767da2cf\
|
|
ef17de85b1d07b59 d26b0595071ae428 3015840928e2c7f5 9abf06003b14b9ee\
|
|
25111d34bb2bfcc2 25", /* 16 bytes i.v. PREPENDED */
|
|
*cmac_hash = "b887df1fd8c239c3 e8a64d9822e21128",
|
|
*wrapped = "1FA68B0A8112B447 AEF34BD8FB5A7B82 9D3E862371D2CFE5";
|
|
#elif AES_KEY_LENGTH == 24 /* ↓↓↓↓ PKCS#7 is enabled */
|
|
*ecbcipher = "af1893f0fbb09a43 7f6b0fd4f4977890 7bb85cccf1e9d2e3 ebe5bae935107868\
|
|
c6d72cb2ca375c12 ce6b6b1141141fd0 d268d14db351d680 5aabb99427341da9",
|
|
*wrapped = "031D33264E15D332 68F24EC260743EDC E1C6C7DDEE725A93 6BA814915C6762D2";
|
|
#else
|
|
*xtscipher = "40bfcc14845b1bb4 15dd13abf1e6f89d 3bfd794cf6655ffd 14c0d7e4177eeaf4\
|
|
5dd95f05663fcfb4 47671154a91b9d00 d1bd7a35c14c7410 9a",
|
|
*wrapped = "28C9F404C4B810F4 CBCCB35CFB87F826 3F5786E2D80ED326 CBC7F0E71A99F43B\
|
|
FB988B9B7A02DD21"; /* <---- it is in RFC-3394 */
|
|
#endif
|
|
|
|
#include <stdio.h>
|
|
|
|
static void check(const char* method, uint8_t* result, uint8_t* expected, size_t size)
|
|
{
|
|
int c = memcmp(expected, result, size);
|
|
printf("AES-%d %s: %s\n", AES_KEY_LENGTH*8, method, c ? "FAILED :(" : "PASSED!");
|
|
memset(result, 0xcc , BuffL);
|
|
}
|
|
|
|
static void str2bytes(const char* str, uint8_t* bytes)
|
|
#define char2num(c) (c > '9' ? (c & 7) + 9 : c & 0xF)
|
|
{
|
|
size_t i, j;
|
|
for (i = 0, j = ~0; str[i]; ++i)
|
|
{
|
|
if (str[i] < '0' || str[i] > 'f') continue;
|
|
if (j++ & 1) bytes[j / 2] = char2num(str[i]) << 4;
|
|
else bytes[j / 2] |= char2num(str[i]);
|
|
}
|
|
}
|
|
|
|
int main()
|
|
{
|
|
uint8_t mainKey[32], key[64], iv[16], input[BuffL - 16], test[BuffL], output[BuffL],
|
|
*a = mainKey + 1, sa = sizeof mainKey - 1, st = TestStringSize / 2;
|
|
str2bytes(cipherKey, key);
|
|
str2bytes(secretKey, key + 32);
|
|
str2bytes(masterKey, mainKey);
|
|
str2bytes(iVec, iv);
|
|
str2bytes(plainText, input);
|
|
printf("Test results...\n");
|
|
|
|
#if MICRO_RJNDL
|
|
memcpy(input + 48, iv, 16);
|
|
a = AES_KEY_LENGTH == 16 ? key : input + (AES_KEY_LENGTH - 24) * 4;
|
|
|
|
memcpy(test, a, 32);
|
|
memcpy(test + 32, mainKey, 16);
|
|
memcpy(test + 48, key + 32, 16);
|
|
AES_Cipher(key + 32, 'E', mainKey, output);
|
|
AES_Cipher(mainKey, 'E', key + 32, output + 16);
|
|
AES_Cipher(key + 32, 'D', a, output + 32);
|
|
AES_Cipher(mainKey, 'D', a + 16, output + 48);
|
|
check("encryption & decryption", output, test, 64);
|
|
#endif
|
|
#if ECB && AES_KEY_LENGTH != 32
|
|
str2bytes(ecbcipher, test);
|
|
AES_ECB_encrypt(key, input, st, output);
|
|
check("ECB encryption", output, test, sizeof input);
|
|
*output ^= AES_ECB_decrypt(key, test, sizeof input, output);
|
|
check("ECB decryption", output, input, st);
|
|
#endif
|
|
#if CBC && AES_KEY_LENGTH == 16
|
|
str2bytes(cbccipher, test);
|
|
*output ^= AES_CBC_encrypt(key, iv, input, st, output);
|
|
check("CBC encryption", output, test, CTS ? st : sizeof input);
|
|
*output ^= AES_CBC_decrypt(key, iv, test, CTS ? st : sizeof input, output);
|
|
check("CBC decryption", output, input, st);
|
|
#endif
|
|
#if CFB && AES_KEY_LENGTH == 16
|
|
str2bytes(cfbcipher, test);
|
|
AES_CFB_encrypt(key, iv, input, st, output);
|
|
check("CFB encryption", output, test, st);
|
|
AES_CFB_decrypt(key, iv, test, st, output);
|
|
check("CFB decryption", output, input, st);
|
|
#endif
|
|
#if OFB && AES_KEY_LENGTH == 16
|
|
str2bytes(ofbcipher, test);
|
|
AES_OFB_encrypt(key, iv, input, st, output);
|
|
check("OFB encryption", output, test, st);
|
|
AES_OFB_decrypt(key, iv, test, st, output);
|
|
check("OFB decryption", output, input, st);
|
|
#endif
|
|
#if CTR_NA && AES_KEY_LENGTH == 16
|
|
str2bytes(ctrcipher, test);
|
|
AES_CTR_encrypt(key, iv, input, st, output);
|
|
check("CTR encryption", output, test, st);
|
|
AES_CTR_decrypt(key, iv, test, st, output);
|
|
check("CTR decryption", output, input, st);
|
|
#endif
|
|
#if XTS && AES_KEY_LENGTH != 24
|
|
str2bytes(xtscipher, test);
|
|
*output ^= AES_XTS_encrypt(key, iv, input, st, output);
|
|
check("XTS encryption", output, test, st);
|
|
*output ^= AES_XTS_decrypt(key, iv, test, st, output);
|
|
check("XTS decryption", output, input, st);
|
|
#endif
|
|
#if CMAC && AES_KEY_LENGTH == 16
|
|
str2bytes(cmac_hash, test);
|
|
AES_CMAC(key, input, st, output);
|
|
check("validate CMAC ", output, test, 16);
|
|
#endif
|
|
#if GCM && AES_KEY_LENGTH == 16
|
|
str2bytes(gcmcipher, test);
|
|
AES_GCM_encrypt(key, iv, input, st, a, sa, output, output + st);
|
|
check("GCM encryption", output, test, st + 16);
|
|
*output ^= AES_GCM_decrypt(key, iv, test, st, a, sa, 16, output);
|
|
check("GCM decryption", output, input, st);
|
|
#endif
|
|
#if CCM && AES_KEY_LENGTH == 16
|
|
str2bytes(ccmcipher, test);
|
|
AES_CCM_encrypt(key, iv, input, st, a, sa, output, output + st);
|
|
check("CCM encryption", output, test, st + CCM_TAG_LEN);
|
|
*output ^= AES_CCM_decrypt(key, iv, test, st, a, sa, CCM_TAG_LEN, output);
|
|
check("CCM decryption", output, input, st);
|
|
#endif
|
|
#if OCB && AES_KEY_LENGTH == 16
|
|
str2bytes(ocbcipher, test);
|
|
AES_OCB_encrypt(key, iv, input, st, a, sa, output, output + st);
|
|
check("OCB encryption", output, test, st + OCB_TAG_LEN);
|
|
*output ^= AES_OCB_decrypt(key, iv, test, st, a, sa, OCB_TAG_LEN, output);
|
|
check("OCB decryption", output, input, st);
|
|
#endif
|
|
#if SIV && AES_KEY_LENGTH == 16
|
|
str2bytes(sivcipher, test);
|
|
AES_SIV_encrypt(key, input, st, a, sa, output, output + 16);
|
|
check("SIV encryption", output, test, st + 16);
|
|
*output ^= AES_SIV_decrypt(key, test, test + 16, st, a, sa, output);
|
|
check("SIV decryption", output, input, st);
|
|
#endif
|
|
#if GCM_SIV && AES_KEY_LENGTH == 16
|
|
str2bytes(gsvcipher, test);
|
|
GCM_SIV_encrypt(key, iv, input, st, a, sa, output, output + st);
|
|
check("GCMSIV encrypt", output, test, st + 16);
|
|
*output ^= GCM_SIV_decrypt(key, iv, test, st, a, sa, 16, output);
|
|
check("GCMSIV decrypt", output, input, st);
|
|
#endif
|
|
#if EAX && AES_KEY_LENGTH == 16
|
|
str2bytes(eaxcipher, test);
|
|
#if EAXP
|
|
AES_EAX_encrypt(key, a, input, st, sa, output);
|
|
check("EAX encryption", output, test, st + 4);
|
|
*output ^= AES_EAX_decrypt(key, a, test, st, sa, output);
|
|
#else
|
|
AES_EAX_encrypt(key, iv, input, st, a, sa, output, output + st);
|
|
check("EAX encryption", output, test, st + 16);
|
|
*output ^= AES_EAX_decrypt(key, iv, test, st, a, sa, 16, output);
|
|
#endif
|
|
check("EAX decryption", output, input, st);
|
|
#endif
|
|
#if KWA
|
|
str2bytes(wrapped, test);
|
|
AES_KEY_wrap(mainKey, key + 32, AES_KEY_LENGTH, output);
|
|
check("key wrapping ", output, test, AES_KEY_LENGTH + 8);
|
|
*output ^= AES_KEY_unwrap(mainKey, test, AES_KEY_LENGTH + 8, output);
|
|
check("key unwrapping", output, key + 32, AES_KEY_LENGTH);
|
|
#endif
|
|
|
|
/** a template for "OFFICIAL TEST VECTORS": */
|
|
#if OCB && EAX && SIV && GCM_SIV && AES_KEY_LENGTH == 16
|
|
printf("+-> Let's do some extra tests\n");
|
|
|
|
st = sa = 24; /* taken from RFC 7253: */
|
|
str2bytes("000102030405060708090A0B0C0D0E0F", key);
|
|
str2bytes("BBAA99887766554433221107", iv);
|
|
str2bytes("000102030405060708090A0B0C0D0E0F1011121314151617", a);
|
|
str2bytes("000102030405060708090A0B0C0D0E0F1011121314151617", input);
|
|
str2bytes("1CA2207308C87C010756104D8840CE1952F09673A448A122\
|
|
C92C62241051F57356D7F3C90BB0E07F", test);
|
|
AES_OCB_encrypt(key, iv, input, st, a, sa, output, output + st);
|
|
check("OCB encryption", output, test, st + OCB_TAG_LEN);
|
|
*output ^= AES_OCB_decrypt(key, iv, test, st, a, sa, OCB_TAG_LEN, output);
|
|
check("OCB decryption", output, input, st);
|
|
|
|
st = 11; sa = 7; /* taken from RFC 8452: */
|
|
str2bytes("ee8e1ed9ff2540ae8f2ba9f50bc2f27c", key);
|
|
str2bytes("752abad3e0afb5f434dc4310", iv);
|
|
str2bytes("6578616d706c65", a);
|
|
str2bytes("48656c6c6f20776f726c64", input);
|
|
str2bytes("5d349ead175ef6b1def6fd4fbcdeb7e4793f4a1d7e4faa70100af1", test);
|
|
GCM_SIV_encrypt(key, iv, input, st, a, sa, output, output + st);
|
|
check("GCMSIV encrypt", output, test, st + 16);
|
|
*output ^= GCM_SIV_decrypt(key, iv, test, st, a, sa, 16, output);
|
|
check("GCMSIV decrypt", output, input, st);
|
|
st = 12; sa = 1; /* taken from RFC 8452: */
|
|
str2bytes("01000000000000000000000000000000", key);
|
|
str2bytes("030000000000000000000000", iv);
|
|
str2bytes("01", a);
|
|
str2bytes("020000000000000000000000", input);
|
|
str2bytes("296c7889fd99f41917f4462008299c51\
|
|
02745aaa3a0c469fad9e075a", test);
|
|
GCM_SIV_encrypt(key, iv, input, st, a, sa, output, output + st);
|
|
check("GCMSIV encrypt", output, test, st + 16);
|
|
*output ^= GCM_SIV_decrypt(key, iv, test, st, a, sa, 16, output);
|
|
check("GCMSIV decrypt", output, input, st);
|
|
|
|
st = 14; sa = 24; /* taken from RFC 5297: */
|
|
str2bytes("fffefdfc fbfaf9f8 f7f6f5f4 f3f2f1f0\
|
|
f0f1f2f3 f4f5f6f7 f8f9fafb fcfdfeff", key);
|
|
str2bytes("10111213 14151617 18191a1b 1c1d1e1f\
|
|
20212223 24252627", a);
|
|
str2bytes("11223344 55667788 99aabbcc ddee", input);
|
|
str2bytes("85632d07 c6e8f37f 950acd32 0a2ecc93\
|
|
40c02b96 90c4dc04 daef7f6a fe5c", test);
|
|
AES_SIV_encrypt(key, input, st, a, sa, output, output + 16);
|
|
check("SIV encryption", output, test, st + 16);
|
|
*output ^= AES_SIV_decrypt(key, test, test + 16, st, a, sa, output);
|
|
check("SIV decryption", output, input, st);
|
|
st = 16; sa = 0; /* from miscreant: https://bit.ly/3yc2GBs */
|
|
str2bytes("fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff", key);
|
|
str2bytes("00112233445566778899aabbccddeeff", input);
|
|
str2bytes("f304f912863e303d5b540e5057c7010c942ffaf45b0e5ca5fb9a56a5263bb065", test);
|
|
AES_SIV_encrypt(key, input, st, a, sa, output, output + 16);
|
|
check("SIV encryption", output, test, st + 16);
|
|
*output ^= AES_SIV_decrypt(key, test, test + 16, st, a, sa, output);
|
|
check("SIV decryption", output, input, st);
|
|
#if EAXP
|
|
st = 0; sa = 50; /* from Annex G of the IEEE Std 1703-2012 */
|
|
str2bytes("01020304050607080102030405060708", mainKey);
|
|
str2bytes("A20D060B607C86F7540116007BC175A8\
|
|
03020100BE0D280B810984A60C060A60\
|
|
7C86F7540116007B040248F3C2040330\
|
|
0005", test);
|
|
str2bytes("515AE775", key);
|
|
AES_EAX_encrypt(mainKey, test, input, st, sa, output);
|
|
check("EAX encryption", output, key, st + 4);
|
|
*output ^= AES_EAX_decrypt(mainKey, test, key, st, sa, output);
|
|
check("EAX decryption", output, input, st);
|
|
st = 28; sa = 65; /* from Moise-Beroset-Phinney-Burns paper: */
|
|
str2bytes("10 20 30 40 50 60 70 80 90 a0 b0 c0 d0 e0 f0 00", mainKey);
|
|
str2bytes("a2 0e 06 0c 60 86 48 01 86 fc 2f 81 1c aa 4e 01\
|
|
a8 06 02 04 39 a0 0e bb ac 0f a2 0d a0 0b a1 09\
|
|
80 01 00 81 04 4b ce e2 c3 be 25 28 23 81 21 88\
|
|
a6 0a 06 08 2b 06 01 04 01 82 85 63 00 4b ce e2\
|
|
c3", test);
|
|
str2bytes("17 51 30 30 30 30 30 30 30 30 30 30 30 30 30 30\
|
|
30 30 30 30 30 30 00 00 03 30 00 01", input);
|
|
str2bytes("9c f3 2c 7e c2 4c 25 0b e7 b0 74 9f ee e7 1a 22\
|
|
0d 0e ee 97 6e c2 3d bf 0c aa 08 ea 00 54 3e 66", key);
|
|
AES_EAX_encrypt(mainKey, test, input, st, sa, output);
|
|
check("EAX encryption", output, key, st + 4);
|
|
*output ^= AES_EAX_decrypt(mainKey, test, key, st, sa, output);
|
|
#else
|
|
st = 12; sa = 8; /* from Bellare-Rogaway-Wagner 2004 paper: */
|
|
str2bytes("BD8E6E11475E60B268784C38C62FEB22", key);
|
|
str2bytes("6EAC5C93072D8E8513F750935E46DA1B", iv);
|
|
str2bytes("D4482D1CA78DCE0F", a);
|
|
str2bytes("4DE3B35C3FC039245BD1FB7D", input);
|
|
str2bytes("835BB4F15D743E350E728414ABB8644FD6CCB86947C5E10590210A4F", test);
|
|
AES_EAX_encrypt(key, iv, input, st, a, sa, output, output + st);
|
|
check("EAX encryption", output, test, st + 16);
|
|
*output ^= AES_EAX_decrypt(key, iv, test, st, a, sa, 16, output);
|
|
#endif
|
|
check("EAX decryption", output, input, st);
|
|
#endif
|
|
return 0;
|
|
}
|