blob: 40a1c244ba6e08627a7417721cea09539bb40373 [file] [log] [blame]
Paul Bakker5121ce52009-01-03 21:22:43 +00001/*
2 * FIPS-197 compliant AES implementation
3 *
Bence Szépkúti1e148272020-08-07 13:07:28 +02004 * Copyright The Mbed TLS Contributors
Dave Rodgman16799db2023-11-02 19:47:20 +00005 * SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
Paul Bakker5121ce52009-01-03 21:22:43 +00006 */
7/*
8 * The AES block cipher was designed by Vincent Rijmen and Joan Daemen.
9 *
Tom Cosgrovece37c5e2023-08-04 13:53:36 +010010 * https://csrc.nist.gov/csrc/media/projects/cryptographic-standards-and-guidelines/documents/aes-development/rijndael-ammended.pdf
Paul Bakker5121ce52009-01-03 21:22:43 +000011 * http://csrc.nist.gov/publications/fips/fips197/fips-197.pdf
12 */
13
Gilles Peskinedb09ef62020-06-03 01:43:33 +020014#include "common.h"
Paul Bakker5121ce52009-01-03 21:22:43 +000015
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020016#if defined(MBEDTLS_AES_C)
Paul Bakker5121ce52009-01-03 21:22:43 +000017
Rich Evans00ab4702015-02-06 13:43:58 +000018#include <string.h>
19
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000020#include "mbedtls/aes.h"
Ron Eldor9924bdc2018-10-04 10:59:13 +030021#include "mbedtls/platform.h"
Andres Amaya Garcia1f6301b2018-04-17 09:51:09 -050022#include "mbedtls/platform_util.h"
Janos Follath24eed8d2019-11-22 13:21:35 +000023#include "mbedtls/error.h"
Jerry Yu02b15192023-04-23 14:43:19 +080024
Dave Rodgman782df0352023-09-29 12:57:52 +010025#if defined(MBEDTLS_AES_USE_HARDWARE_ONLY)
Dave Rodgman9fd1b522023-10-10 15:23:44 +010026#if !((defined(MBEDTLS_ARCH_IS_ARMV8_A) && defined(MBEDTLS_AESCE_C)) || \
27 (defined(MBEDTLS_ARCH_IS_X64) && defined(MBEDTLS_AESNI_C)) || \
28 (defined(MBEDTLS_ARCH_IS_X86) && defined(MBEDTLS_AESNI_C)))
Jerry Yu69436812023-04-25 11:08:30 +080029#error "MBEDTLS_AES_USE_HARDWARE_ONLY defined, but not all prerequisites"
Jerry Yu02b15192023-04-23 14:43:19 +080030#endif
31#endif
32
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020033#if defined(MBEDTLS_AESNI_C)
Chris Jones187782f2021-03-09 17:28:35 +000034#include "aesni.h"
Manuel Pégourié-Gonnard5b685652013-12-18 11:45:21 +010035#endif
Jerry Yu3f2fb712023-01-10 17:05:42 +080036#if defined(MBEDTLS_AESCE_C)
37#include "aesce.h"
38#endif
Paul Bakker5121ce52009-01-03 21:22:43 +000039
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000040#include "mbedtls/platform.h"
Dave Rodgman591ff052024-01-13 16:42:38 +000041#include "ctr.h"
Paul Bakker7dc4c442014-02-01 22:50:26 +010042
Yanray Wangf03b4912023-11-09 11:23:17 +080043/*
44 * This is a convenience shorthand macro to check if we need reverse S-box and
45 * reverse tables. It's private and only defined in this file.
46 */
47#if (!defined(MBEDTLS_AES_DECRYPT_ALT) || \
48 (!defined(MBEDTLS_AES_SETKEY_DEC_ALT) && !defined(MBEDTLS_AES_USE_HARDWARE_ONLY))) && \
Yanray Wangb67b4742023-10-31 17:10:32 +080049 !defined(MBEDTLS_BLOCK_CIPHER_NO_DECRYPT)
Yanray Wangdbcc0c62023-08-30 15:04:01 +080050#define MBEDTLS_AES_NEED_REVERSE_TABLES
51#endif
52
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020053#if defined(MBEDTLS_AES_ROM_TABLES)
Paul Bakker5121ce52009-01-03 21:22:43 +000054/*
55 * Forward S-box
56 */
Dave Rodgman18ddf612023-10-04 14:03:12 +010057MBEDTLS_MAYBE_UNUSED static const unsigned char FSb[256] =
Paul Bakker5121ce52009-01-03 21:22:43 +000058{
59 0x63, 0x7C, 0x77, 0x7B, 0xF2, 0x6B, 0x6F, 0xC5,
60 0x30, 0x01, 0x67, 0x2B, 0xFE, 0xD7, 0xAB, 0x76,
61 0xCA, 0x82, 0xC9, 0x7D, 0xFA, 0x59, 0x47, 0xF0,
62 0xAD, 0xD4, 0xA2, 0xAF, 0x9C, 0xA4, 0x72, 0xC0,
63 0xB7, 0xFD, 0x93, 0x26, 0x36, 0x3F, 0xF7, 0xCC,
64 0x34, 0xA5, 0xE5, 0xF1, 0x71, 0xD8, 0x31, 0x15,
65 0x04, 0xC7, 0x23, 0xC3, 0x18, 0x96, 0x05, 0x9A,
66 0x07, 0x12, 0x80, 0xE2, 0xEB, 0x27, 0xB2, 0x75,
67 0x09, 0x83, 0x2C, 0x1A, 0x1B, 0x6E, 0x5A, 0xA0,
68 0x52, 0x3B, 0xD6, 0xB3, 0x29, 0xE3, 0x2F, 0x84,
69 0x53, 0xD1, 0x00, 0xED, 0x20, 0xFC, 0xB1, 0x5B,
70 0x6A, 0xCB, 0xBE, 0x39, 0x4A, 0x4C, 0x58, 0xCF,
71 0xD0, 0xEF, 0xAA, 0xFB, 0x43, 0x4D, 0x33, 0x85,
72 0x45, 0xF9, 0x02, 0x7F, 0x50, 0x3C, 0x9F, 0xA8,
73 0x51, 0xA3, 0x40, 0x8F, 0x92, 0x9D, 0x38, 0xF5,
74 0xBC, 0xB6, 0xDA, 0x21, 0x10, 0xFF, 0xF3, 0xD2,
75 0xCD, 0x0C, 0x13, 0xEC, 0x5F, 0x97, 0x44, 0x17,
76 0xC4, 0xA7, 0x7E, 0x3D, 0x64, 0x5D, 0x19, 0x73,
77 0x60, 0x81, 0x4F, 0xDC, 0x22, 0x2A, 0x90, 0x88,
78 0x46, 0xEE, 0xB8, 0x14, 0xDE, 0x5E, 0x0B, 0xDB,
79 0xE0, 0x32, 0x3A, 0x0A, 0x49, 0x06, 0x24, 0x5C,
80 0xC2, 0xD3, 0xAC, 0x62, 0x91, 0x95, 0xE4, 0x79,
81 0xE7, 0xC8, 0x37, 0x6D, 0x8D, 0xD5, 0x4E, 0xA9,
82 0x6C, 0x56, 0xF4, 0xEA, 0x65, 0x7A, 0xAE, 0x08,
83 0xBA, 0x78, 0x25, 0x2E, 0x1C, 0xA6, 0xB4, 0xC6,
84 0xE8, 0xDD, 0x74, 0x1F, 0x4B, 0xBD, 0x8B, 0x8A,
85 0x70, 0x3E, 0xB5, 0x66, 0x48, 0x03, 0xF6, 0x0E,
86 0x61, 0x35, 0x57, 0xB9, 0x86, 0xC1, 0x1D, 0x9E,
87 0xE1, 0xF8, 0x98, 0x11, 0x69, 0xD9, 0x8E, 0x94,
88 0x9B, 0x1E, 0x87, 0xE9, 0xCE, 0x55, 0x28, 0xDF,
89 0x8C, 0xA1, 0x89, 0x0D, 0xBF, 0xE6, 0x42, 0x68,
90 0x41, 0x99, 0x2D, 0x0F, 0xB0, 0x54, 0xBB, 0x16
91};
92
93/*
94 * Forward tables
95 */
96#define FT \
97\
Gilles Peskine449bd832023-01-11 14:50:10 +010098 V(A5, 63, 63, C6), V(84, 7C, 7C, F8), V(99, 77, 77, EE), V(8D, 7B, 7B, F6), \
99 V(0D, F2, F2, FF), V(BD, 6B, 6B, D6), V(B1, 6F, 6F, DE), V(54, C5, C5, 91), \
100 V(50, 30, 30, 60), V(03, 01, 01, 02), V(A9, 67, 67, CE), V(7D, 2B, 2B, 56), \
101 V(19, FE, FE, E7), V(62, D7, D7, B5), V(E6, AB, AB, 4D), V(9A, 76, 76, EC), \
102 V(45, CA, CA, 8F), V(9D, 82, 82, 1F), V(40, C9, C9, 89), V(87, 7D, 7D, FA), \
103 V(15, FA, FA, EF), V(EB, 59, 59, B2), V(C9, 47, 47, 8E), V(0B, F0, F0, FB), \
104 V(EC, AD, AD, 41), V(67, D4, D4, B3), V(FD, A2, A2, 5F), V(EA, AF, AF, 45), \
105 V(BF, 9C, 9C, 23), V(F7, A4, A4, 53), V(96, 72, 72, E4), V(5B, C0, C0, 9B), \
106 V(C2, B7, B7, 75), V(1C, FD, FD, E1), V(AE, 93, 93, 3D), V(6A, 26, 26, 4C), \
107 V(5A, 36, 36, 6C), V(41, 3F, 3F, 7E), V(02, F7, F7, F5), V(4F, CC, CC, 83), \
108 V(5C, 34, 34, 68), V(F4, A5, A5, 51), V(34, E5, E5, D1), V(08, F1, F1, F9), \
109 V(93, 71, 71, E2), V(73, D8, D8, AB), V(53, 31, 31, 62), V(3F, 15, 15, 2A), \
110 V(0C, 04, 04, 08), V(52, C7, C7, 95), V(65, 23, 23, 46), V(5E, C3, C3, 9D), \
111 V(28, 18, 18, 30), V(A1, 96, 96, 37), V(0F, 05, 05, 0A), V(B5, 9A, 9A, 2F), \
112 V(09, 07, 07, 0E), V(36, 12, 12, 24), V(9B, 80, 80, 1B), V(3D, E2, E2, DF), \
113 V(26, EB, EB, CD), V(69, 27, 27, 4E), V(CD, B2, B2, 7F), V(9F, 75, 75, EA), \
114 V(1B, 09, 09, 12), V(9E, 83, 83, 1D), V(74, 2C, 2C, 58), V(2E, 1A, 1A, 34), \
115 V(2D, 1B, 1B, 36), V(B2, 6E, 6E, DC), V(EE, 5A, 5A, B4), V(FB, A0, A0, 5B), \
116 V(F6, 52, 52, A4), V(4D, 3B, 3B, 76), V(61, D6, D6, B7), V(CE, B3, B3, 7D), \
117 V(7B, 29, 29, 52), V(3E, E3, E3, DD), V(71, 2F, 2F, 5E), V(97, 84, 84, 13), \
118 V(F5, 53, 53, A6), V(68, D1, D1, B9), V(00, 00, 00, 00), V(2C, ED, ED, C1), \
119 V(60, 20, 20, 40), V(1F, FC, FC, E3), V(C8, B1, B1, 79), V(ED, 5B, 5B, B6), \
120 V(BE, 6A, 6A, D4), V(46, CB, CB, 8D), V(D9, BE, BE, 67), V(4B, 39, 39, 72), \
121 V(DE, 4A, 4A, 94), V(D4, 4C, 4C, 98), V(E8, 58, 58, B0), V(4A, CF, CF, 85), \
122 V(6B, D0, D0, BB), V(2A, EF, EF, C5), V(E5, AA, AA, 4F), V(16, FB, FB, ED), \
123 V(C5, 43, 43, 86), V(D7, 4D, 4D, 9A), V(55, 33, 33, 66), V(94, 85, 85, 11), \
124 V(CF, 45, 45, 8A), V(10, F9, F9, E9), V(06, 02, 02, 04), V(81, 7F, 7F, FE), \
125 V(F0, 50, 50, A0), V(44, 3C, 3C, 78), V(BA, 9F, 9F, 25), V(E3, A8, A8, 4B), \
126 V(F3, 51, 51, A2), V(FE, A3, A3, 5D), V(C0, 40, 40, 80), V(8A, 8F, 8F, 05), \
127 V(AD, 92, 92, 3F), V(BC, 9D, 9D, 21), V(48, 38, 38, 70), V(04, F5, F5, F1), \
128 V(DF, BC, BC, 63), V(C1, B6, B6, 77), V(75, DA, DA, AF), V(63, 21, 21, 42), \
129 V(30, 10, 10, 20), V(1A, FF, FF, E5), V(0E, F3, F3, FD), V(6D, D2, D2, BF), \
130 V(4C, CD, CD, 81), V(14, 0C, 0C, 18), V(35, 13, 13, 26), V(2F, EC, EC, C3), \
131 V(E1, 5F, 5F, BE), V(A2, 97, 97, 35), V(CC, 44, 44, 88), V(39, 17, 17, 2E), \
132 V(57, C4, C4, 93), V(F2, A7, A7, 55), V(82, 7E, 7E, FC), V(47, 3D, 3D, 7A), \
133 V(AC, 64, 64, C8), V(E7, 5D, 5D, BA), V(2B, 19, 19, 32), V(95, 73, 73, E6), \
134 V(A0, 60, 60, C0), V(98, 81, 81, 19), V(D1, 4F, 4F, 9E), V(7F, DC, DC, A3), \
135 V(66, 22, 22, 44), V(7E, 2A, 2A, 54), V(AB, 90, 90, 3B), V(83, 88, 88, 0B), \
136 V(CA, 46, 46, 8C), V(29, EE, EE, C7), V(D3, B8, B8, 6B), V(3C, 14, 14, 28), \
137 V(79, DE, DE, A7), V(E2, 5E, 5E, BC), V(1D, 0B, 0B, 16), V(76, DB, DB, AD), \
138 V(3B, E0, E0, DB), V(56, 32, 32, 64), V(4E, 3A, 3A, 74), V(1E, 0A, 0A, 14), \
139 V(DB, 49, 49, 92), V(0A, 06, 06, 0C), V(6C, 24, 24, 48), V(E4, 5C, 5C, B8), \
140 V(5D, C2, C2, 9F), V(6E, D3, D3, BD), V(EF, AC, AC, 43), V(A6, 62, 62, C4), \
141 V(A8, 91, 91, 39), V(A4, 95, 95, 31), V(37, E4, E4, D3), V(8B, 79, 79, F2), \
142 V(32, E7, E7, D5), V(43, C8, C8, 8B), V(59, 37, 37, 6E), V(B7, 6D, 6D, DA), \
143 V(8C, 8D, 8D, 01), V(64, D5, D5, B1), V(D2, 4E, 4E, 9C), V(E0, A9, A9, 49), \
144 V(B4, 6C, 6C, D8), V(FA, 56, 56, AC), V(07, F4, F4, F3), V(25, EA, EA, CF), \
145 V(AF, 65, 65, CA), V(8E, 7A, 7A, F4), V(E9, AE, AE, 47), V(18, 08, 08, 10), \
146 V(D5, BA, BA, 6F), V(88, 78, 78, F0), V(6F, 25, 25, 4A), V(72, 2E, 2E, 5C), \
147 V(24, 1C, 1C, 38), V(F1, A6, A6, 57), V(C7, B4, B4, 73), V(51, C6, C6, 97), \
148 V(23, E8, E8, CB), V(7C, DD, DD, A1), V(9C, 74, 74, E8), V(21, 1F, 1F, 3E), \
149 V(DD, 4B, 4B, 96), V(DC, BD, BD, 61), V(86, 8B, 8B, 0D), V(85, 8A, 8A, 0F), \
150 V(90, 70, 70, E0), V(42, 3E, 3E, 7C), V(C4, B5, B5, 71), V(AA, 66, 66, CC), \
151 V(D8, 48, 48, 90), V(05, 03, 03, 06), V(01, F6, F6, F7), V(12, 0E, 0E, 1C), \
152 V(A3, 61, 61, C2), V(5F, 35, 35, 6A), V(F9, 57, 57, AE), V(D0, B9, B9, 69), \
153 V(91, 86, 86, 17), V(58, C1, C1, 99), V(27, 1D, 1D, 3A), V(B9, 9E, 9E, 27), \
154 V(38, E1, E1, D9), V(13, F8, F8, EB), V(B3, 98, 98, 2B), V(33, 11, 11, 22), \
155 V(BB, 69, 69, D2), V(70, D9, D9, A9), V(89, 8E, 8E, 07), V(A7, 94, 94, 33), \
156 V(B6, 9B, 9B, 2D), V(22, 1E, 1E, 3C), V(92, 87, 87, 15), V(20, E9, E9, C9), \
157 V(49, CE, CE, 87), V(FF, 55, 55, AA), V(78, 28, 28, 50), V(7A, DF, DF, A5), \
158 V(8F, 8C, 8C, 03), V(F8, A1, A1, 59), V(80, 89, 89, 09), V(17, 0D, 0D, 1A), \
159 V(DA, BF, BF, 65), V(31, E6, E6, D7), V(C6, 42, 42, 84), V(B8, 68, 68, D0), \
160 V(C3, 41, 41, 82), V(B0, 99, 99, 29), V(77, 2D, 2D, 5A), V(11, 0F, 0F, 1E), \
161 V(CB, B0, B0, 7B), V(FC, 54, 54, A8), V(D6, BB, BB, 6D), V(3A, 16, 16, 2C)
Paul Bakker5121ce52009-01-03 21:22:43 +0000162
Gilles Peskine449bd832023-01-11 14:50:10 +0100163#define V(a, b, c, d) 0x##a##b##c##d
Dave Rodgman18ddf612023-10-04 14:03:12 +0100164MBEDTLS_MAYBE_UNUSED static const uint32_t FT0[256] = { FT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000165#undef V
166
Gilles Peskine449bd832023-01-11 14:50:10 +0100167#define V(a, b, c, d) 0x##b##c##d##a
Dave Rodgman18ddf612023-10-04 14:03:12 +0100168MBEDTLS_MAYBE_UNUSED static const uint32_t FT1[256] = { FT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000169#undef V
170
Gilles Peskine449bd832023-01-11 14:50:10 +0100171#define V(a, b, c, d) 0x##c##d##a##b
Dave Rodgman18ddf612023-10-04 14:03:12 +0100172MBEDTLS_MAYBE_UNUSED static const uint32_t FT2[256] = { FT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000173#undef V
174
Gilles Peskine449bd832023-01-11 14:50:10 +0100175#define V(a, b, c, d) 0x##d##a##b##c
Dave Rodgman18ddf612023-10-04 14:03:12 +0100176MBEDTLS_MAYBE_UNUSED static const uint32_t FT3[256] = { FT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000177#undef V
178
179#undef FT
180
181/*
182 * Reverse S-box
183 */
Dave Rodgman18ddf612023-10-04 14:03:12 +0100184MBEDTLS_MAYBE_UNUSED static const unsigned char RSb[256] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000185{
186 0x52, 0x09, 0x6A, 0xD5, 0x30, 0x36, 0xA5, 0x38,
187 0xBF, 0x40, 0xA3, 0x9E, 0x81, 0xF3, 0xD7, 0xFB,
188 0x7C, 0xE3, 0x39, 0x82, 0x9B, 0x2F, 0xFF, 0x87,
189 0x34, 0x8E, 0x43, 0x44, 0xC4, 0xDE, 0xE9, 0xCB,
190 0x54, 0x7B, 0x94, 0x32, 0xA6, 0xC2, 0x23, 0x3D,
191 0xEE, 0x4C, 0x95, 0x0B, 0x42, 0xFA, 0xC3, 0x4E,
192 0x08, 0x2E, 0xA1, 0x66, 0x28, 0xD9, 0x24, 0xB2,
193 0x76, 0x5B, 0xA2, 0x49, 0x6D, 0x8B, 0xD1, 0x25,
194 0x72, 0xF8, 0xF6, 0x64, 0x86, 0x68, 0x98, 0x16,
195 0xD4, 0xA4, 0x5C, 0xCC, 0x5D, 0x65, 0xB6, 0x92,
196 0x6C, 0x70, 0x48, 0x50, 0xFD, 0xED, 0xB9, 0xDA,
197 0x5E, 0x15, 0x46, 0x57, 0xA7, 0x8D, 0x9D, 0x84,
198 0x90, 0xD8, 0xAB, 0x00, 0x8C, 0xBC, 0xD3, 0x0A,
199 0xF7, 0xE4, 0x58, 0x05, 0xB8, 0xB3, 0x45, 0x06,
200 0xD0, 0x2C, 0x1E, 0x8F, 0xCA, 0x3F, 0x0F, 0x02,
201 0xC1, 0xAF, 0xBD, 0x03, 0x01, 0x13, 0x8A, 0x6B,
202 0x3A, 0x91, 0x11, 0x41, 0x4F, 0x67, 0xDC, 0xEA,
203 0x97, 0xF2, 0xCF, 0xCE, 0xF0, 0xB4, 0xE6, 0x73,
204 0x96, 0xAC, 0x74, 0x22, 0xE7, 0xAD, 0x35, 0x85,
205 0xE2, 0xF9, 0x37, 0xE8, 0x1C, 0x75, 0xDF, 0x6E,
206 0x47, 0xF1, 0x1A, 0x71, 0x1D, 0x29, 0xC5, 0x89,
207 0x6F, 0xB7, 0x62, 0x0E, 0xAA, 0x18, 0xBE, 0x1B,
208 0xFC, 0x56, 0x3E, 0x4B, 0xC6, 0xD2, 0x79, 0x20,
209 0x9A, 0xDB, 0xC0, 0xFE, 0x78, 0xCD, 0x5A, 0xF4,
210 0x1F, 0xDD, 0xA8, 0x33, 0x88, 0x07, 0xC7, 0x31,
211 0xB1, 0x12, 0x10, 0x59, 0x27, 0x80, 0xEC, 0x5F,
212 0x60, 0x51, 0x7F, 0xA9, 0x19, 0xB5, 0x4A, 0x0D,
213 0x2D, 0xE5, 0x7A, 0x9F, 0x93, 0xC9, 0x9C, 0xEF,
214 0xA0, 0xE0, 0x3B, 0x4D, 0xAE, 0x2A, 0xF5, 0xB0,
215 0xC8, 0xEB, 0xBB, 0x3C, 0x83, 0x53, 0x99, 0x61,
216 0x17, 0x2B, 0x04, 0x7E, 0xBA, 0x77, 0xD6, 0x26,
217 0xE1, 0x69, 0x14, 0x63, 0x55, 0x21, 0x0C, 0x7D
218};
219
220/*
221 * Reverse tables
222 */
223#define RT \
224\
Gilles Peskine449bd832023-01-11 14:50:10 +0100225 V(50, A7, F4, 51), V(53, 65, 41, 7E), V(C3, A4, 17, 1A), V(96, 5E, 27, 3A), \
226 V(CB, 6B, AB, 3B), V(F1, 45, 9D, 1F), V(AB, 58, FA, AC), V(93, 03, E3, 4B), \
227 V(55, FA, 30, 20), V(F6, 6D, 76, AD), V(91, 76, CC, 88), V(25, 4C, 02, F5), \
228 V(FC, D7, E5, 4F), V(D7, CB, 2A, C5), V(80, 44, 35, 26), V(8F, A3, 62, B5), \
229 V(49, 5A, B1, DE), V(67, 1B, BA, 25), V(98, 0E, EA, 45), V(E1, C0, FE, 5D), \
230 V(02, 75, 2F, C3), V(12, F0, 4C, 81), V(A3, 97, 46, 8D), V(C6, F9, D3, 6B), \
231 V(E7, 5F, 8F, 03), V(95, 9C, 92, 15), V(EB, 7A, 6D, BF), V(DA, 59, 52, 95), \
232 V(2D, 83, BE, D4), V(D3, 21, 74, 58), V(29, 69, E0, 49), V(44, C8, C9, 8E), \
233 V(6A, 89, C2, 75), V(78, 79, 8E, F4), V(6B, 3E, 58, 99), V(DD, 71, B9, 27), \
234 V(B6, 4F, E1, BE), V(17, AD, 88, F0), V(66, AC, 20, C9), V(B4, 3A, CE, 7D), \
235 V(18, 4A, DF, 63), V(82, 31, 1A, E5), V(60, 33, 51, 97), V(45, 7F, 53, 62), \
236 V(E0, 77, 64, B1), V(84, AE, 6B, BB), V(1C, A0, 81, FE), V(94, 2B, 08, F9), \
237 V(58, 68, 48, 70), V(19, FD, 45, 8F), V(87, 6C, DE, 94), V(B7, F8, 7B, 52), \
238 V(23, D3, 73, AB), V(E2, 02, 4B, 72), V(57, 8F, 1F, E3), V(2A, AB, 55, 66), \
239 V(07, 28, EB, B2), V(03, C2, B5, 2F), V(9A, 7B, C5, 86), V(A5, 08, 37, D3), \
240 V(F2, 87, 28, 30), V(B2, A5, BF, 23), V(BA, 6A, 03, 02), V(5C, 82, 16, ED), \
241 V(2B, 1C, CF, 8A), V(92, B4, 79, A7), V(F0, F2, 07, F3), V(A1, E2, 69, 4E), \
242 V(CD, F4, DA, 65), V(D5, BE, 05, 06), V(1F, 62, 34, D1), V(8A, FE, A6, C4), \
243 V(9D, 53, 2E, 34), V(A0, 55, F3, A2), V(32, E1, 8A, 05), V(75, EB, F6, A4), \
244 V(39, EC, 83, 0B), V(AA, EF, 60, 40), V(06, 9F, 71, 5E), V(51, 10, 6E, BD), \
245 V(F9, 8A, 21, 3E), V(3D, 06, DD, 96), V(AE, 05, 3E, DD), V(46, BD, E6, 4D), \
246 V(B5, 8D, 54, 91), V(05, 5D, C4, 71), V(6F, D4, 06, 04), V(FF, 15, 50, 60), \
247 V(24, FB, 98, 19), V(97, E9, BD, D6), V(CC, 43, 40, 89), V(77, 9E, D9, 67), \
248 V(BD, 42, E8, B0), V(88, 8B, 89, 07), V(38, 5B, 19, E7), V(DB, EE, C8, 79), \
249 V(47, 0A, 7C, A1), V(E9, 0F, 42, 7C), V(C9, 1E, 84, F8), V(00, 00, 00, 00), \
250 V(83, 86, 80, 09), V(48, ED, 2B, 32), V(AC, 70, 11, 1E), V(4E, 72, 5A, 6C), \
251 V(FB, FF, 0E, FD), V(56, 38, 85, 0F), V(1E, D5, AE, 3D), V(27, 39, 2D, 36), \
252 V(64, D9, 0F, 0A), V(21, A6, 5C, 68), V(D1, 54, 5B, 9B), V(3A, 2E, 36, 24), \
253 V(B1, 67, 0A, 0C), V(0F, E7, 57, 93), V(D2, 96, EE, B4), V(9E, 91, 9B, 1B), \
254 V(4F, C5, C0, 80), V(A2, 20, DC, 61), V(69, 4B, 77, 5A), V(16, 1A, 12, 1C), \
255 V(0A, BA, 93, E2), V(E5, 2A, A0, C0), V(43, E0, 22, 3C), V(1D, 17, 1B, 12), \
256 V(0B, 0D, 09, 0E), V(AD, C7, 8B, F2), V(B9, A8, B6, 2D), V(C8, A9, 1E, 14), \
257 V(85, 19, F1, 57), V(4C, 07, 75, AF), V(BB, DD, 99, EE), V(FD, 60, 7F, A3), \
258 V(9F, 26, 01, F7), V(BC, F5, 72, 5C), V(C5, 3B, 66, 44), V(34, 7E, FB, 5B), \
259 V(76, 29, 43, 8B), V(DC, C6, 23, CB), V(68, FC, ED, B6), V(63, F1, E4, B8), \
260 V(CA, DC, 31, D7), V(10, 85, 63, 42), V(40, 22, 97, 13), V(20, 11, C6, 84), \
261 V(7D, 24, 4A, 85), V(F8, 3D, BB, D2), V(11, 32, F9, AE), V(6D, A1, 29, C7), \
262 V(4B, 2F, 9E, 1D), V(F3, 30, B2, DC), V(EC, 52, 86, 0D), V(D0, E3, C1, 77), \
263 V(6C, 16, B3, 2B), V(99, B9, 70, A9), V(FA, 48, 94, 11), V(22, 64, E9, 47), \
264 V(C4, 8C, FC, A8), V(1A, 3F, F0, A0), V(D8, 2C, 7D, 56), V(EF, 90, 33, 22), \
265 V(C7, 4E, 49, 87), V(C1, D1, 38, D9), V(FE, A2, CA, 8C), V(36, 0B, D4, 98), \
266 V(CF, 81, F5, A6), V(28, DE, 7A, A5), V(26, 8E, B7, DA), V(A4, BF, AD, 3F), \
267 V(E4, 9D, 3A, 2C), V(0D, 92, 78, 50), V(9B, CC, 5F, 6A), V(62, 46, 7E, 54), \
268 V(C2, 13, 8D, F6), V(E8, B8, D8, 90), V(5E, F7, 39, 2E), V(F5, AF, C3, 82), \
269 V(BE, 80, 5D, 9F), V(7C, 93, D0, 69), V(A9, 2D, D5, 6F), V(B3, 12, 25, CF), \
270 V(3B, 99, AC, C8), V(A7, 7D, 18, 10), V(6E, 63, 9C, E8), V(7B, BB, 3B, DB), \
271 V(09, 78, 26, CD), V(F4, 18, 59, 6E), V(01, B7, 9A, EC), V(A8, 9A, 4F, 83), \
272 V(65, 6E, 95, E6), V(7E, E6, FF, AA), V(08, CF, BC, 21), V(E6, E8, 15, EF), \
273 V(D9, 9B, E7, BA), V(CE, 36, 6F, 4A), V(D4, 09, 9F, EA), V(D6, 7C, B0, 29), \
274 V(AF, B2, A4, 31), V(31, 23, 3F, 2A), V(30, 94, A5, C6), V(C0, 66, A2, 35), \
275 V(37, BC, 4E, 74), V(A6, CA, 82, FC), V(B0, D0, 90, E0), V(15, D8, A7, 33), \
276 V(4A, 98, 04, F1), V(F7, DA, EC, 41), V(0E, 50, CD, 7F), V(2F, F6, 91, 17), \
277 V(8D, D6, 4D, 76), V(4D, B0, EF, 43), V(54, 4D, AA, CC), V(DF, 04, 96, E4), \
278 V(E3, B5, D1, 9E), V(1B, 88, 6A, 4C), V(B8, 1F, 2C, C1), V(7F, 51, 65, 46), \
279 V(04, EA, 5E, 9D), V(5D, 35, 8C, 01), V(73, 74, 87, FA), V(2E, 41, 0B, FB), \
280 V(5A, 1D, 67, B3), V(52, D2, DB, 92), V(33, 56, 10, E9), V(13, 47, D6, 6D), \
281 V(8C, 61, D7, 9A), V(7A, 0C, A1, 37), V(8E, 14, F8, 59), V(89, 3C, 13, EB), \
282 V(EE, 27, A9, CE), V(35, C9, 61, B7), V(ED, E5, 1C, E1), V(3C, B1, 47, 7A), \
283 V(59, DF, D2, 9C), V(3F, 73, F2, 55), V(79, CE, 14, 18), V(BF, 37, C7, 73), \
284 V(EA, CD, F7, 53), V(5B, AA, FD, 5F), V(14, 6F, 3D, DF), V(86, DB, 44, 78), \
285 V(81, F3, AF, CA), V(3E, C4, 68, B9), V(2C, 34, 24, 38), V(5F, 40, A3, C2), \
286 V(72, C3, 1D, 16), V(0C, 25, E2, BC), V(8B, 49, 3C, 28), V(41, 95, 0D, FF), \
287 V(71, 01, A8, 39), V(DE, B3, 0C, 08), V(9C, E4, B4, D8), V(90, C1, 56, 64), \
288 V(61, 84, CB, 7B), V(70, B6, 32, D5), V(74, 5C, 6C, 48), V(42, 57, B8, D0)
Paul Bakker5121ce52009-01-03 21:22:43 +0000289
Dave Rodgmanad4e76b2023-06-27 19:20:27 +0100290
Gilles Peskine449bd832023-01-11 14:50:10 +0100291#define V(a, b, c, d) 0x##a##b##c##d
Dave Rodgman18ddf612023-10-04 14:03:12 +0100292MBEDTLS_MAYBE_UNUSED static const uint32_t RT0[256] = { RT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000293#undef V
294
Gilles Peskine449bd832023-01-11 14:50:10 +0100295#define V(a, b, c, d) 0x##b##c##d##a
Dave Rodgman18ddf612023-10-04 14:03:12 +0100296MBEDTLS_MAYBE_UNUSED static const uint32_t RT1[256] = { RT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000297#undef V
298
Gilles Peskine449bd832023-01-11 14:50:10 +0100299#define V(a, b, c, d) 0x##c##d##a##b
Dave Rodgman18ddf612023-10-04 14:03:12 +0100300MBEDTLS_MAYBE_UNUSED static const uint32_t RT2[256] = { RT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000301#undef V
302
Gilles Peskine449bd832023-01-11 14:50:10 +0100303#define V(a, b, c, d) 0x##d##a##b##c
Dave Rodgman18ddf612023-10-04 14:03:12 +0100304MBEDTLS_MAYBE_UNUSED static const uint32_t RT3[256] = { RT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000305#undef V
306
307#undef RT
308
309/*
310 * Round constants
311 */
Dave Rodgman4b779be2023-10-12 16:17:10 +0100312MBEDTLS_MAYBE_UNUSED static const uint32_t round_constants[10] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000313{
314 0x00000001, 0x00000002, 0x00000004, 0x00000008,
315 0x00000010, 0x00000020, 0x00000040, 0x00000080,
316 0x0000001B, 0x00000036
317};
318
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200319#else /* MBEDTLS_AES_ROM_TABLES */
Paul Bakker5121ce52009-01-03 21:22:43 +0000320
321/*
322 * Forward S-box & tables
323 */
Dave Rodgman18ddf612023-10-04 14:03:12 +0100324MBEDTLS_MAYBE_UNUSED static unsigned char FSb[256];
325MBEDTLS_MAYBE_UNUSED static uint32_t FT0[256];
326MBEDTLS_MAYBE_UNUSED static uint32_t FT1[256];
327MBEDTLS_MAYBE_UNUSED static uint32_t FT2[256];
328MBEDTLS_MAYBE_UNUSED static uint32_t FT3[256];
Paul Bakker5121ce52009-01-03 21:22:43 +0000329
330/*
331 * Reverse S-box & tables
332 */
Dave Rodgman18ddf612023-10-04 14:03:12 +0100333MBEDTLS_MAYBE_UNUSED static unsigned char RSb[256];
Dave Rodgmanad4e76b2023-06-27 19:20:27 +0100334
Dave Rodgman18ddf612023-10-04 14:03:12 +0100335MBEDTLS_MAYBE_UNUSED static uint32_t RT0[256];
336MBEDTLS_MAYBE_UNUSED static uint32_t RT1[256];
337MBEDTLS_MAYBE_UNUSED static uint32_t RT2[256];
338MBEDTLS_MAYBE_UNUSED static uint32_t RT3[256];
Paul Bakker5121ce52009-01-03 21:22:43 +0000339
340/*
341 * Round constants
342 */
Dave Rodgman4b779be2023-10-12 16:17:10 +0100343MBEDTLS_MAYBE_UNUSED static uint32_t round_constants[10];
Paul Bakker5121ce52009-01-03 21:22:43 +0000344
345/*
346 * Tables generation code
347 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100348#define ROTL8(x) (((x) << 8) & 0xFFFFFFFF) | ((x) >> 24)
349#define XTIME(x) (((x) << 1) ^ (((x) & 0x80) ? 0x1B : 0x00))
350#define MUL(x, y) (((x) && (y)) ? pow[(log[(x)]+log[(y)]) % 255] : 0)
Paul Bakker5121ce52009-01-03 21:22:43 +0000351
Dave Rodgman18ddf612023-10-04 14:03:12 +0100352MBEDTLS_MAYBE_UNUSED static int aes_init_done = 0;
Paul Bakker5121ce52009-01-03 21:22:43 +0000353
Dave Rodgman18ddf612023-10-04 14:03:12 +0100354MBEDTLS_MAYBE_UNUSED static void aes_gen_tables(void)
Paul Bakker5121ce52009-01-03 21:22:43 +0000355{
Yanray Wangfe944ce2023-06-26 18:16:01 +0800356 int i;
357 uint8_t x, y, z;
Yanray Wang5c86b172023-06-26 16:54:52 +0800358 uint8_t pow[256];
359 uint8_t log[256];
Paul Bakker5121ce52009-01-03 21:22:43 +0000360
361 /*
362 * compute pow and log tables over GF(2^8)
363 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100364 for (i = 0, x = 1; i < 256; i++) {
Paul Bakker5121ce52009-01-03 21:22:43 +0000365 pow[i] = x;
Yanray Wang5c86b172023-06-26 16:54:52 +0800366 log[x] = (uint8_t) i;
Yanray Wangfe944ce2023-06-26 18:16:01 +0800367 x ^= XTIME(x);
Paul Bakker5121ce52009-01-03 21:22:43 +0000368 }
369
370 /*
371 * calculate the round constants
372 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100373 for (i = 0, x = 1; i < 10; i++) {
Jerzy Kasenbergee62fce2023-10-11 16:36:24 +0200374 round_constants[i] = x;
Yanray Wangfe944ce2023-06-26 18:16:01 +0800375 x = XTIME(x);
Paul Bakker5121ce52009-01-03 21:22:43 +0000376 }
377
378 /*
379 * generate the forward and reverse S-boxes
380 */
381 FSb[0x00] = 0x63;
Yanray Wangdbcc0c62023-08-30 15:04:01 +0800382#if defined(MBEDTLS_AES_NEED_REVERSE_TABLES)
Paul Bakker5121ce52009-01-03 21:22:43 +0000383 RSb[0x63] = 0x00;
Yanray Wangdbcc0c62023-08-30 15:04:01 +0800384#endif
Paul Bakker5121ce52009-01-03 21:22:43 +0000385
Gilles Peskine449bd832023-01-11 14:50:10 +0100386 for (i = 1; i < 256; i++) {
Paul Bakker5121ce52009-01-03 21:22:43 +0000387 x = pow[255 - log[i]];
388
Yanray Wangfe944ce2023-06-26 18:16:01 +0800389 y = x; y = (y << 1) | (y >> 7);
390 x ^= y; y = (y << 1) | (y >> 7);
391 x ^= y; y = (y << 1) | (y >> 7);
392 x ^= y; y = (y << 1) | (y >> 7);
Paul Bakker5121ce52009-01-03 21:22:43 +0000393 x ^= y ^ 0x63;
394
Yanray Wangfe944ce2023-06-26 18:16:01 +0800395 FSb[i] = x;
Yanray Wangdbcc0c62023-08-30 15:04:01 +0800396#if defined(MBEDTLS_AES_NEED_REVERSE_TABLES)
Paul Bakker5121ce52009-01-03 21:22:43 +0000397 RSb[x] = (unsigned char) i;
Yanray Wangdbcc0c62023-08-30 15:04:01 +0800398#endif
Paul Bakker5121ce52009-01-03 21:22:43 +0000399 }
400
401 /*
402 * generate the forward and reverse tables
403 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100404 for (i = 0; i < 256; i++) {
Paul Bakker5121ce52009-01-03 21:22:43 +0000405 x = FSb[i];
Yanray Wangfe944ce2023-06-26 18:16:01 +0800406 y = XTIME(x);
407 z = y ^ x;
Paul Bakker5121ce52009-01-03 21:22:43 +0000408
Gilles Peskine449bd832023-01-11 14:50:10 +0100409 FT0[i] = ((uint32_t) y) ^
410 ((uint32_t) x << 8) ^
411 ((uint32_t) x << 16) ^
412 ((uint32_t) z << 24);
Paul Bakker5121ce52009-01-03 21:22:43 +0000413
Hanno Beckerad049a92017-06-19 16:31:54 +0100414#if !defined(MBEDTLS_AES_FEWER_TABLES)
Gilles Peskine449bd832023-01-11 14:50:10 +0100415 FT1[i] = ROTL8(FT0[i]);
416 FT2[i] = ROTL8(FT1[i]);
417 FT3[i] = ROTL8(FT2[i]);
Hanno Becker177d3cf2017-06-07 15:52:48 +0100418#endif /* !MBEDTLS_AES_FEWER_TABLES */
Paul Bakker5121ce52009-01-03 21:22:43 +0000419
Yanray Wangdbcc0c62023-08-30 15:04:01 +0800420#if defined(MBEDTLS_AES_NEED_REVERSE_TABLES)
Paul Bakker5121ce52009-01-03 21:22:43 +0000421 x = RSb[i];
422
Gilles Peskine449bd832023-01-11 14:50:10 +0100423 RT0[i] = ((uint32_t) MUL(0x0E, x)) ^
424 ((uint32_t) MUL(0x09, x) << 8) ^
425 ((uint32_t) MUL(0x0D, x) << 16) ^
426 ((uint32_t) MUL(0x0B, x) << 24);
Paul Bakker5121ce52009-01-03 21:22:43 +0000427
Hanno Beckerad049a92017-06-19 16:31:54 +0100428#if !defined(MBEDTLS_AES_FEWER_TABLES)
Gilles Peskine449bd832023-01-11 14:50:10 +0100429 RT1[i] = ROTL8(RT0[i]);
430 RT2[i] = ROTL8(RT1[i]);
431 RT3[i] = ROTL8(RT2[i]);
Hanno Becker177d3cf2017-06-07 15:52:48 +0100432#endif /* !MBEDTLS_AES_FEWER_TABLES */
Yanray Wangdbcc0c62023-08-30 15:04:01 +0800433#endif /* MBEDTLS_AES_NEED_REVERSE_TABLES */
Paul Bakker5121ce52009-01-03 21:22:43 +0000434 }
435}
436
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200437#undef ROTL8
438
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200439#endif /* MBEDTLS_AES_ROM_TABLES */
Paul Bakker5121ce52009-01-03 21:22:43 +0000440
Hanno Beckerad049a92017-06-19 16:31:54 +0100441#if defined(MBEDTLS_AES_FEWER_TABLES)
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200442
Gilles Peskine449bd832023-01-11 14:50:10 +0100443#define ROTL8(x) ((uint32_t) ((x) << 8) + (uint32_t) ((x) >> 24))
444#define ROTL16(x) ((uint32_t) ((x) << 16) + (uint32_t) ((x) >> 16))
445#define ROTL24(x) ((uint32_t) ((x) << 24) + (uint32_t) ((x) >> 8))
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200446
447#define AES_RT0(idx) RT0[idx]
Gilles Peskine449bd832023-01-11 14:50:10 +0100448#define AES_RT1(idx) ROTL8(RT0[idx])
449#define AES_RT2(idx) ROTL16(RT0[idx])
450#define AES_RT3(idx) ROTL24(RT0[idx])
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200451
452#define AES_FT0(idx) FT0[idx]
Gilles Peskine449bd832023-01-11 14:50:10 +0100453#define AES_FT1(idx) ROTL8(FT0[idx])
454#define AES_FT2(idx) ROTL16(FT0[idx])
455#define AES_FT3(idx) ROTL24(FT0[idx])
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200456
Hanno Becker177d3cf2017-06-07 15:52:48 +0100457#else /* MBEDTLS_AES_FEWER_TABLES */
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200458
459#define AES_RT0(idx) RT0[idx]
460#define AES_RT1(idx) RT1[idx]
461#define AES_RT2(idx) RT2[idx]
462#define AES_RT3(idx) RT3[idx]
463
464#define AES_FT0(idx) FT0[idx]
465#define AES_FT1(idx) FT1[idx]
466#define AES_FT2(idx) FT2[idx]
467#define AES_FT3(idx) FT3[idx]
468
Hanno Becker177d3cf2017-06-07 15:52:48 +0100469#endif /* MBEDTLS_AES_FEWER_TABLES */
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200470
Gilles Peskine449bd832023-01-11 14:50:10 +0100471void mbedtls_aes_init(mbedtls_aes_context *ctx)
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200472{
Gilles Peskine449bd832023-01-11 14:50:10 +0100473 memset(ctx, 0, sizeof(mbedtls_aes_context));
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200474}
475
Gilles Peskine449bd832023-01-11 14:50:10 +0100476void mbedtls_aes_free(mbedtls_aes_context *ctx)
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200477{
Gilles Peskine449bd832023-01-11 14:50:10 +0100478 if (ctx == NULL) {
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200479 return;
Gilles Peskine449bd832023-01-11 14:50:10 +0100480 }
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200481
Gilles Peskine449bd832023-01-11 14:50:10 +0100482 mbedtls_platform_zeroize(ctx, sizeof(mbedtls_aes_context));
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200483}
484
Jaeden Amero9366feb2018-05-29 18:55:17 +0100485#if defined(MBEDTLS_CIPHER_MODE_XTS)
Gilles Peskine449bd832023-01-11 14:50:10 +0100486void mbedtls_aes_xts_init(mbedtls_aes_xts_context *ctx)
Jaeden Amero9366feb2018-05-29 18:55:17 +0100487{
Gilles Peskine449bd832023-01-11 14:50:10 +0100488 mbedtls_aes_init(&ctx->crypt);
489 mbedtls_aes_init(&ctx->tweak);
Jaeden Amero9366feb2018-05-29 18:55:17 +0100490}
491
Gilles Peskine449bd832023-01-11 14:50:10 +0100492void mbedtls_aes_xts_free(mbedtls_aes_xts_context *ctx)
Jaeden Amero9366feb2018-05-29 18:55:17 +0100493{
Gilles Peskine449bd832023-01-11 14:50:10 +0100494 if (ctx == NULL) {
Manuel Pégourié-Gonnard44c5d582018-12-10 16:56:14 +0100495 return;
Gilles Peskine449bd832023-01-11 14:50:10 +0100496 }
Simon Butcher5201e412018-12-06 17:40:14 +0000497
Gilles Peskine449bd832023-01-11 14:50:10 +0100498 mbedtls_aes_free(&ctx->crypt);
499 mbedtls_aes_free(&ctx->tweak);
Jaeden Amero9366feb2018-05-29 18:55:17 +0100500}
501#endif /* MBEDTLS_CIPHER_MODE_XTS */
502
Gilles Peskine0de8f852023-03-16 17:14:59 +0100503/* Some implementations need the round keys to be aligned.
504 * Return an offset to be added to buf, such that (buf + offset) is
505 * correctly aligned.
506 * Note that the offset is in units of elements of buf, i.e. 32-bit words,
507 * i.e. an offset of 1 means 4 bytes and so on.
508 */
Thomas Daubneyf57a3522024-06-25 15:23:57 +0100509#if defined(MBEDTLS_AESNI_C) && MBEDTLS_AESNI_HAVE_CODE == 2
Gilles Peskine0de8f852023-03-16 17:14:59 +0100510#define MAY_NEED_TO_ALIGN
511#endif
Dave Rodgman28a539a2023-06-27 18:22:34 +0100512
Dave Rodgman18ddf612023-10-04 14:03:12 +0100513MBEDTLS_MAYBE_UNUSED static unsigned mbedtls_aes_rk_offset(uint32_t *buf)
Gilles Peskine0de8f852023-03-16 17:14:59 +0100514{
515#if defined(MAY_NEED_TO_ALIGN)
516 int align_16_bytes = 0;
517
Gilles Peskine9c682e72023-03-16 17:21:33 +0100518#if defined(MBEDTLS_AESNI_C) && MBEDTLS_AESNI_HAVE_CODE == 2
Gilles Peskine0de8f852023-03-16 17:14:59 +0100519 if (mbedtls_aesni_has_support(MBEDTLS_AESNI_AES)) {
520 align_16_bytes = 1;
521 }
522#endif
523
524 if (align_16_bytes) {
525 /* These implementations needs 16-byte alignment
526 * for the round key array. */
527 unsigned delta = ((uintptr_t) buf & 0x0000000fU) / 4;
528 if (delta == 0) {
529 return 0;
530 } else {
531 return 4 - delta; // 16 bytes = 4 uint32_t
532 }
533 }
534#else /* MAY_NEED_TO_ALIGN */
535 (void) buf;
536#endif /* MAY_NEED_TO_ALIGN */
537
538 return 0;
539}
540
Paul Bakker5121ce52009-01-03 21:22:43 +0000541/*
542 * AES key schedule (encryption)
543 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100544int mbedtls_aes_setkey_enc(mbedtls_aes_context *ctx, const unsigned char *key,
545 unsigned int keybits)
Paul Bakker5121ce52009-01-03 21:22:43 +0000546{
Paul Bakker5c2364c2012-10-01 14:41:15 +0000547 uint32_t *RK;
Paul Bakker5121ce52009-01-03 21:22:43 +0000548
Gilles Peskine449bd832023-01-11 14:50:10 +0100549 switch (keybits) {
Paul Bakker5121ce52009-01-03 21:22:43 +0000550 case 128: ctx->nr = 10; break;
Arto Kinnunen732ca322023-04-14 14:26:10 +0800551#if !defined(MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH)
Paul Bakker5121ce52009-01-03 21:22:43 +0000552 case 192: ctx->nr = 12; break;
553 case 256: ctx->nr = 14; break;
Arto Kinnunen732ca322023-04-14 14:26:10 +0800554#endif /* !MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH */
Gilles Peskine449bd832023-01-11 14:50:10 +0100555 default: return MBEDTLS_ERR_AES_INVALID_KEY_LENGTH;
Paul Bakker5121ce52009-01-03 21:22:43 +0000556 }
557
Simon Butcher5201e412018-12-06 17:40:14 +0000558#if !defined(MBEDTLS_AES_ROM_TABLES)
Gilles Peskine449bd832023-01-11 14:50:10 +0100559 if (aes_init_done == 0) {
Simon Butcher5201e412018-12-06 17:40:14 +0000560 aes_gen_tables();
561 aes_init_done = 1;
Simon Butcher5201e412018-12-06 17:40:14 +0000562 }
563#endif
564
Gilles Peskine0de8f852023-03-16 17:14:59 +0100565 ctx->rk_offset = mbedtls_aes_rk_offset(ctx->buf);
Werner Lewisdd76ef32022-05-30 12:00:21 +0100566 RK = ctx->buf + ctx->rk_offset;
Paul Bakker5121ce52009-01-03 21:22:43 +0000567
Gilles Peskine9af58cd2023-03-10 22:29:32 +0100568#if defined(MBEDTLS_AESNI_HAVE_CODE)
Gilles Peskine449bd832023-01-11 14:50:10 +0100569 if (mbedtls_aesni_has_support(MBEDTLS_AESNI_AES)) {
570 return mbedtls_aesni_setkey_enc((unsigned char *) RK, key, keybits);
571 }
Manuel Pégourié-Gonnard47a35362013-12-28 20:45:04 +0100572#endif
573
Jerry Yu72fd0bd2023-08-18 16:31:01 +0800574#if defined(MBEDTLS_AESCE_HAVE_CODE)
Dave Rodgmanf2249ec2023-08-04 14:27:58 +0100575 if (MBEDTLS_AESCE_HAS_SUPPORT()) {
Jerry Yu3f2fb712023-01-10 17:05:42 +0800576 return mbedtls_aesce_setkey_enc((unsigned char *) RK, key, keybits);
577 }
578#endif
579
Jerry Yu29c91ba2023-08-04 11:02:04 +0800580#if !defined(MBEDTLS_AES_USE_HARDWARE_ONLY)
Jerry Yu3a0f0442023-08-17 17:06:21 +0800581 for (unsigned int i = 0; i < (keybits >> 5); i++) {
Gilles Peskine449bd832023-01-11 14:50:10 +0100582 RK[i] = MBEDTLS_GET_UINT32_LE(key, i << 2);
Paul Bakker5121ce52009-01-03 21:22:43 +0000583 }
584
Gilles Peskine449bd832023-01-11 14:50:10 +0100585 switch (ctx->nr) {
Paul Bakker5121ce52009-01-03 21:22:43 +0000586 case 10:
587
Jerry Yu3a0f0442023-08-17 17:06:21 +0800588 for (unsigned int i = 0; i < 10; i++, RK += 4) {
Jerzy Kasenbergee62fce2023-10-11 16:36:24 +0200589 RK[4] = RK[0] ^ round_constants[i] ^
Gilles Peskine449bd832023-01-11 14:50:10 +0100590 ((uint32_t) FSb[MBEDTLS_BYTE_1(RK[3])]) ^
591 ((uint32_t) FSb[MBEDTLS_BYTE_2(RK[3])] << 8) ^
592 ((uint32_t) FSb[MBEDTLS_BYTE_3(RK[3])] << 16) ^
593 ((uint32_t) FSb[MBEDTLS_BYTE_0(RK[3])] << 24);
Paul Bakker5121ce52009-01-03 21:22:43 +0000594
595 RK[5] = RK[1] ^ RK[4];
596 RK[6] = RK[2] ^ RK[5];
597 RK[7] = RK[3] ^ RK[6];
598 }
599 break;
600
Arto Kinnunen732ca322023-04-14 14:26:10 +0800601#if !defined(MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH)
Paul Bakker5121ce52009-01-03 21:22:43 +0000602 case 12:
603
Jerry Yu3a0f0442023-08-17 17:06:21 +0800604 for (unsigned int i = 0; i < 8; i++, RK += 6) {
Jerzy Kasenbergee62fce2023-10-11 16:36:24 +0200605 RK[6] = RK[0] ^ round_constants[i] ^
Gilles Peskine449bd832023-01-11 14:50:10 +0100606 ((uint32_t) FSb[MBEDTLS_BYTE_1(RK[5])]) ^
607 ((uint32_t) FSb[MBEDTLS_BYTE_2(RK[5])] << 8) ^
608 ((uint32_t) FSb[MBEDTLS_BYTE_3(RK[5])] << 16) ^
609 ((uint32_t) FSb[MBEDTLS_BYTE_0(RK[5])] << 24);
Paul Bakker5121ce52009-01-03 21:22:43 +0000610
611 RK[7] = RK[1] ^ RK[6];
612 RK[8] = RK[2] ^ RK[7];
613 RK[9] = RK[3] ^ RK[8];
614 RK[10] = RK[4] ^ RK[9];
615 RK[11] = RK[5] ^ RK[10];
616 }
617 break;
618
619 case 14:
620
Jerry Yu3a0f0442023-08-17 17:06:21 +0800621 for (unsigned int i = 0; i < 7; i++, RK += 8) {
Jerzy Kasenbergee62fce2023-10-11 16:36:24 +0200622 RK[8] = RK[0] ^ round_constants[i] ^
Gilles Peskine449bd832023-01-11 14:50:10 +0100623 ((uint32_t) FSb[MBEDTLS_BYTE_1(RK[7])]) ^
624 ((uint32_t) FSb[MBEDTLS_BYTE_2(RK[7])] << 8) ^
625 ((uint32_t) FSb[MBEDTLS_BYTE_3(RK[7])] << 16) ^
626 ((uint32_t) FSb[MBEDTLS_BYTE_0(RK[7])] << 24);
Paul Bakker5121ce52009-01-03 21:22:43 +0000627
628 RK[9] = RK[1] ^ RK[8];
629 RK[10] = RK[2] ^ RK[9];
630 RK[11] = RK[3] ^ RK[10];
631
632 RK[12] = RK[4] ^
Gilles Peskine449bd832023-01-11 14:50:10 +0100633 ((uint32_t) FSb[MBEDTLS_BYTE_0(RK[11])]) ^
634 ((uint32_t) FSb[MBEDTLS_BYTE_1(RK[11])] << 8) ^
635 ((uint32_t) FSb[MBEDTLS_BYTE_2(RK[11])] << 16) ^
636 ((uint32_t) FSb[MBEDTLS_BYTE_3(RK[11])] << 24);
Paul Bakker5121ce52009-01-03 21:22:43 +0000637
638 RK[13] = RK[5] ^ RK[12];
639 RK[14] = RK[6] ^ RK[13];
640 RK[15] = RK[7] ^ RK[14];
641 }
642 break;
Arto Kinnunen732ca322023-04-14 14:26:10 +0800643#endif /* !MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH */
Paul Bakker5121ce52009-01-03 21:22:43 +0000644 }
Paul Bakker2b222c82009-07-27 21:03:45 +0000645
Gilles Peskine449bd832023-01-11 14:50:10 +0100646 return 0;
Jerry Yu29c91ba2023-08-04 11:02:04 +0800647#endif /* !MBEDTLS_AES_USE_HARDWARE_ONLY */
Paul Bakker5121ce52009-01-03 21:22:43 +0000648}
649
650/*
651 * AES key schedule (decryption)
652 */
Yanray Wangb67b4742023-10-31 17:10:32 +0800653#if !defined(MBEDTLS_AES_SETKEY_DEC_ALT) && !defined(MBEDTLS_BLOCK_CIPHER_NO_DECRYPT)
Gilles Peskine449bd832023-01-11 14:50:10 +0100654int mbedtls_aes_setkey_dec(mbedtls_aes_context *ctx, const unsigned char *key,
655 unsigned int keybits)
Paul Bakker5121ce52009-01-03 21:22:43 +0000656{
Jerry Yu29c91ba2023-08-04 11:02:04 +0800657#if !defined(MBEDTLS_AES_USE_HARDWARE_ONLY)
Jerry Yu29c91ba2023-08-04 11:02:04 +0800658 uint32_t *SK;
659#endif
660 int ret;
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200661 mbedtls_aes_context cty;
Paul Bakker5c2364c2012-10-01 14:41:15 +0000662 uint32_t *RK;
Jerry Yu29c91ba2023-08-04 11:02:04 +0800663
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200664
Gilles Peskine449bd832023-01-11 14:50:10 +0100665 mbedtls_aes_init(&cty);
Paul Bakker5121ce52009-01-03 21:22:43 +0000666
Gilles Peskine0de8f852023-03-16 17:14:59 +0100667 ctx->rk_offset = mbedtls_aes_rk_offset(ctx->buf);
Werner Lewisdd76ef32022-05-30 12:00:21 +0100668 RK = ctx->buf + ctx->rk_offset;
Paul Bakker5121ce52009-01-03 21:22:43 +0000669
Manuel Pégourié-Gonnardb8186a52015-06-18 14:58:58 +0200670 /* Also checks keybits */
Gilles Peskine449bd832023-01-11 14:50:10 +0100671 if ((ret = mbedtls_aes_setkey_enc(&cty, key, keybits)) != 0) {
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200672 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +0100673 }
Paul Bakker2b222c82009-07-27 21:03:45 +0000674
Manuel Pégourié-Gonnardafd5a082014-05-28 21:52:59 +0200675 ctx->nr = cty.nr;
676
Gilles Peskine9af58cd2023-03-10 22:29:32 +0100677#if defined(MBEDTLS_AESNI_HAVE_CODE)
Gilles Peskine449bd832023-01-11 14:50:10 +0100678 if (mbedtls_aesni_has_support(MBEDTLS_AESNI_AES)) {
679 mbedtls_aesni_inverse_key((unsigned char *) RK,
680 (const unsigned char *) (cty.buf + cty.rk_offset), ctx->nr);
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200681 goto exit;
Manuel Pégourié-Gonnard01e31bb2013-12-28 15:58:30 +0100682 }
683#endif
684
Jerry Yu72fd0bd2023-08-18 16:31:01 +0800685#if defined(MBEDTLS_AESCE_HAVE_CODE)
Dave Rodgmanf2249ec2023-08-04 14:27:58 +0100686 if (MBEDTLS_AESCE_HAS_SUPPORT()) {
Jerry Yue096da12023-01-10 17:07:01 +0800687 mbedtls_aesce_inverse_key(
688 (unsigned char *) RK,
689 (const unsigned char *) (cty.buf + cty.rk_offset),
690 ctx->nr);
691 goto exit;
692 }
693#endif
694
Jerry Yu29c91ba2023-08-04 11:02:04 +0800695#if !defined(MBEDTLS_AES_USE_HARDWARE_ONLY)
Werner Lewisdd76ef32022-05-30 12:00:21 +0100696 SK = cty.buf + cty.rk_offset + cty.nr * 4;
Paul Bakker5121ce52009-01-03 21:22:43 +0000697
698 *RK++ = *SK++;
699 *RK++ = *SK++;
700 *RK++ = *SK++;
701 *RK++ = *SK++;
Jerry Yu3a0f0442023-08-17 17:06:21 +0800702 SK -= 8;
703 for (int i = ctx->nr - 1; i > 0; i--, SK -= 8) {
704 for (int j = 0; j < 4; j++, SK++) {
Gilles Peskine449bd832023-01-11 14:50:10 +0100705 *RK++ = AES_RT0(FSb[MBEDTLS_BYTE_0(*SK)]) ^
706 AES_RT1(FSb[MBEDTLS_BYTE_1(*SK)]) ^
707 AES_RT2(FSb[MBEDTLS_BYTE_2(*SK)]) ^
708 AES_RT3(FSb[MBEDTLS_BYTE_3(*SK)]);
Paul Bakker5121ce52009-01-03 21:22:43 +0000709 }
710 }
711
712 *RK++ = *SK++;
713 *RK++ = *SK++;
714 *RK++ = *SK++;
715 *RK++ = *SK++;
Jerry Yu29c91ba2023-08-04 11:02:04 +0800716#endif /* !MBEDTLS_AES_USE_HARDWARE_ONLY */
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200717exit:
Gilles Peskine449bd832023-01-11 14:50:10 +0100718 mbedtls_aes_free(&cty);
Paul Bakker2b222c82009-07-27 21:03:45 +0000719
Gilles Peskine449bd832023-01-11 14:50:10 +0100720 return ret;
Paul Bakker5121ce52009-01-03 21:22:43 +0000721}
Yanray Wangb67b4742023-10-31 17:10:32 +0800722#endif /* !MBEDTLS_AES_SETKEY_DEC_ALT && !MBEDTLS_BLOCK_CIPHER_NO_DECRYPT */
Jaeden Amero9366feb2018-05-29 18:55:17 +0100723
724#if defined(MBEDTLS_CIPHER_MODE_XTS)
Gilles Peskine449bd832023-01-11 14:50:10 +0100725static int mbedtls_aes_xts_decode_keys(const unsigned char *key,
726 unsigned int keybits,
727 const unsigned char **key1,
728 unsigned int *key1bits,
729 const unsigned char **key2,
730 unsigned int *key2bits)
Jaeden Amero9366feb2018-05-29 18:55:17 +0100731{
732 const unsigned int half_keybits = keybits / 2;
733 const unsigned int half_keybytes = half_keybits / 8;
734
Gilles Peskine449bd832023-01-11 14:50:10 +0100735 switch (keybits) {
Jaeden Amero9366feb2018-05-29 18:55:17 +0100736 case 256: break;
737 case 512: break;
Gilles Peskine449bd832023-01-11 14:50:10 +0100738 default: return MBEDTLS_ERR_AES_INVALID_KEY_LENGTH;
Jaeden Amero9366feb2018-05-29 18:55:17 +0100739 }
740
741 *key1bits = half_keybits;
742 *key2bits = half_keybits;
743 *key1 = &key[0];
744 *key2 = &key[half_keybytes];
745
746 return 0;
747}
748
Gilles Peskine449bd832023-01-11 14:50:10 +0100749int mbedtls_aes_xts_setkey_enc(mbedtls_aes_xts_context *ctx,
750 const unsigned char *key,
751 unsigned int keybits)
Jaeden Amero9366feb2018-05-29 18:55:17 +0100752{
Janos Follath24eed8d2019-11-22 13:21:35 +0000753 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Jaeden Amero9366feb2018-05-29 18:55:17 +0100754 const unsigned char *key1, *key2;
755 unsigned int key1bits, key2bits;
756
Gilles Peskine449bd832023-01-11 14:50:10 +0100757 ret = mbedtls_aes_xts_decode_keys(key, keybits, &key1, &key1bits,
758 &key2, &key2bits);
759 if (ret != 0) {
760 return ret;
761 }
Jaeden Amero9366feb2018-05-29 18:55:17 +0100762
763 /* Set the tweak key. Always set tweak key for the encryption mode. */
Gilles Peskine449bd832023-01-11 14:50:10 +0100764 ret = mbedtls_aes_setkey_enc(&ctx->tweak, key2, key2bits);
765 if (ret != 0) {
766 return ret;
767 }
Jaeden Amero9366feb2018-05-29 18:55:17 +0100768
769 /* Set crypt key for encryption. */
Gilles Peskine449bd832023-01-11 14:50:10 +0100770 return mbedtls_aes_setkey_enc(&ctx->crypt, key1, key1bits);
Jaeden Amero9366feb2018-05-29 18:55:17 +0100771}
772
Gilles Peskine449bd832023-01-11 14:50:10 +0100773int mbedtls_aes_xts_setkey_dec(mbedtls_aes_xts_context *ctx,
774 const unsigned char *key,
775 unsigned int keybits)
Jaeden Amero9366feb2018-05-29 18:55:17 +0100776{
Janos Follath24eed8d2019-11-22 13:21:35 +0000777 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Jaeden Amero9366feb2018-05-29 18:55:17 +0100778 const unsigned char *key1, *key2;
779 unsigned int key1bits, key2bits;
780
Gilles Peskine449bd832023-01-11 14:50:10 +0100781 ret = mbedtls_aes_xts_decode_keys(key, keybits, &key1, &key1bits,
782 &key2, &key2bits);
783 if (ret != 0) {
784 return ret;
785 }
Jaeden Amero9366feb2018-05-29 18:55:17 +0100786
787 /* Set the tweak key. Always set tweak key for encryption. */
Gilles Peskine449bd832023-01-11 14:50:10 +0100788 ret = mbedtls_aes_setkey_enc(&ctx->tweak, key2, key2bits);
789 if (ret != 0) {
790 return ret;
791 }
Jaeden Amero9366feb2018-05-29 18:55:17 +0100792
793 /* Set crypt key for decryption. */
Gilles Peskine449bd832023-01-11 14:50:10 +0100794 return mbedtls_aes_setkey_dec(&ctx->crypt, key1, key1bits);
Jaeden Amero9366feb2018-05-29 18:55:17 +0100795}
796#endif /* MBEDTLS_CIPHER_MODE_XTS */
797
Gilles Peskine449bd832023-01-11 14:50:10 +0100798#define AES_FROUND(X0, X1, X2, X3, Y0, Y1, Y2, Y3) \
Joe Subbianicd84d762021-07-08 14:59:52 +0100799 do \
800 { \
Gilles Peskine449bd832023-01-11 14:50:10 +0100801 (X0) = *RK++ ^ AES_FT0(MBEDTLS_BYTE_0(Y0)) ^ \
802 AES_FT1(MBEDTLS_BYTE_1(Y1)) ^ \
803 AES_FT2(MBEDTLS_BYTE_2(Y2)) ^ \
804 AES_FT3(MBEDTLS_BYTE_3(Y3)); \
Joe Subbianicd84d762021-07-08 14:59:52 +0100805 \
Gilles Peskine449bd832023-01-11 14:50:10 +0100806 (X1) = *RK++ ^ AES_FT0(MBEDTLS_BYTE_0(Y1)) ^ \
807 AES_FT1(MBEDTLS_BYTE_1(Y2)) ^ \
808 AES_FT2(MBEDTLS_BYTE_2(Y3)) ^ \
809 AES_FT3(MBEDTLS_BYTE_3(Y0)); \
Joe Subbianicd84d762021-07-08 14:59:52 +0100810 \
Gilles Peskine449bd832023-01-11 14:50:10 +0100811 (X2) = *RK++ ^ AES_FT0(MBEDTLS_BYTE_0(Y2)) ^ \
812 AES_FT1(MBEDTLS_BYTE_1(Y3)) ^ \
813 AES_FT2(MBEDTLS_BYTE_2(Y0)) ^ \
814 AES_FT3(MBEDTLS_BYTE_3(Y1)); \
Joe Subbianicd84d762021-07-08 14:59:52 +0100815 \
Gilles Peskine449bd832023-01-11 14:50:10 +0100816 (X3) = *RK++ ^ AES_FT0(MBEDTLS_BYTE_0(Y3)) ^ \
817 AES_FT1(MBEDTLS_BYTE_1(Y0)) ^ \
818 AES_FT2(MBEDTLS_BYTE_2(Y1)) ^ \
819 AES_FT3(MBEDTLS_BYTE_3(Y2)); \
820 } while (0)
Paul Bakker5121ce52009-01-03 21:22:43 +0000821
Gilles Peskine449bd832023-01-11 14:50:10 +0100822#define AES_RROUND(X0, X1, X2, X3, Y0, Y1, Y2, Y3) \
Hanno Becker1eeca412018-10-15 12:01:35 +0100823 do \
824 { \
Gilles Peskine449bd832023-01-11 14:50:10 +0100825 (X0) = *RK++ ^ AES_RT0(MBEDTLS_BYTE_0(Y0)) ^ \
826 AES_RT1(MBEDTLS_BYTE_1(Y3)) ^ \
827 AES_RT2(MBEDTLS_BYTE_2(Y2)) ^ \
828 AES_RT3(MBEDTLS_BYTE_3(Y1)); \
Hanno Becker1eeca412018-10-15 12:01:35 +0100829 \
Gilles Peskine449bd832023-01-11 14:50:10 +0100830 (X1) = *RK++ ^ AES_RT0(MBEDTLS_BYTE_0(Y1)) ^ \
831 AES_RT1(MBEDTLS_BYTE_1(Y0)) ^ \
832 AES_RT2(MBEDTLS_BYTE_2(Y3)) ^ \
833 AES_RT3(MBEDTLS_BYTE_3(Y2)); \
Hanno Becker1eeca412018-10-15 12:01:35 +0100834 \
Gilles Peskine449bd832023-01-11 14:50:10 +0100835 (X2) = *RK++ ^ AES_RT0(MBEDTLS_BYTE_0(Y2)) ^ \
836 AES_RT1(MBEDTLS_BYTE_1(Y1)) ^ \
837 AES_RT2(MBEDTLS_BYTE_2(Y0)) ^ \
838 AES_RT3(MBEDTLS_BYTE_3(Y3)); \
Hanno Becker1eeca412018-10-15 12:01:35 +0100839 \
Gilles Peskine449bd832023-01-11 14:50:10 +0100840 (X3) = *RK++ ^ AES_RT0(MBEDTLS_BYTE_0(Y3)) ^ \
841 AES_RT1(MBEDTLS_BYTE_1(Y2)) ^ \
842 AES_RT2(MBEDTLS_BYTE_2(Y1)) ^ \
843 AES_RT3(MBEDTLS_BYTE_3(Y0)); \
844 } while (0)
Paul Bakker5121ce52009-01-03 21:22:43 +0000845
846/*
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200847 * AES-ECB block encryption
848 */
849#if !defined(MBEDTLS_AES_ENCRYPT_ALT)
Gilles Peskine449bd832023-01-11 14:50:10 +0100850int mbedtls_internal_aes_encrypt(mbedtls_aes_context *ctx,
851 const unsigned char input[16],
852 unsigned char output[16])
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200853{
854 int i;
Werner Lewisdd76ef32022-05-30 12:00:21 +0100855 uint32_t *RK = ctx->buf + ctx->rk_offset;
Gilles Peskine449bd832023-01-11 14:50:10 +0100856 struct {
Gilles Peskine5197c662020-08-26 17:03:24 +0200857 uint32_t X[4];
858 uint32_t Y[4];
859 } t;
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200860
Gilles Peskine449bd832023-01-11 14:50:10 +0100861 t.X[0] = MBEDTLS_GET_UINT32_LE(input, 0); t.X[0] ^= *RK++;
862 t.X[1] = MBEDTLS_GET_UINT32_LE(input, 4); t.X[1] ^= *RK++;
863 t.X[2] = MBEDTLS_GET_UINT32_LE(input, 8); t.X[2] ^= *RK++;
864 t.X[3] = MBEDTLS_GET_UINT32_LE(input, 12); t.X[3] ^= *RK++;
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200865
Gilles Peskine449bd832023-01-11 14:50:10 +0100866 for (i = (ctx->nr >> 1) - 1; i > 0; i--) {
867 AES_FROUND(t.Y[0], t.Y[1], t.Y[2], t.Y[3], t.X[0], t.X[1], t.X[2], t.X[3]);
868 AES_FROUND(t.X[0], t.X[1], t.X[2], t.X[3], t.Y[0], t.Y[1], t.Y[2], t.Y[3]);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200869 }
870
Gilles Peskine449bd832023-01-11 14:50:10 +0100871 AES_FROUND(t.Y[0], t.Y[1], t.Y[2], t.Y[3], t.X[0], t.X[1], t.X[2], t.X[3]);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200872
Gilles Peskine5197c662020-08-26 17:03:24 +0200873 t.X[0] = *RK++ ^ \
Gilles Peskine449bd832023-01-11 14:50:10 +0100874 ((uint32_t) FSb[MBEDTLS_BYTE_0(t.Y[0])]) ^
875 ((uint32_t) FSb[MBEDTLS_BYTE_1(t.Y[1])] << 8) ^
876 ((uint32_t) FSb[MBEDTLS_BYTE_2(t.Y[2])] << 16) ^
877 ((uint32_t) FSb[MBEDTLS_BYTE_3(t.Y[3])] << 24);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200878
Gilles Peskine5197c662020-08-26 17:03:24 +0200879 t.X[1] = *RK++ ^ \
Gilles Peskine449bd832023-01-11 14:50:10 +0100880 ((uint32_t) FSb[MBEDTLS_BYTE_0(t.Y[1])]) ^
881 ((uint32_t) FSb[MBEDTLS_BYTE_1(t.Y[2])] << 8) ^
882 ((uint32_t) FSb[MBEDTLS_BYTE_2(t.Y[3])] << 16) ^
883 ((uint32_t) FSb[MBEDTLS_BYTE_3(t.Y[0])] << 24);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200884
Gilles Peskine5197c662020-08-26 17:03:24 +0200885 t.X[2] = *RK++ ^ \
Gilles Peskine449bd832023-01-11 14:50:10 +0100886 ((uint32_t) FSb[MBEDTLS_BYTE_0(t.Y[2])]) ^
887 ((uint32_t) FSb[MBEDTLS_BYTE_1(t.Y[3])] << 8) ^
888 ((uint32_t) FSb[MBEDTLS_BYTE_2(t.Y[0])] << 16) ^
889 ((uint32_t) FSb[MBEDTLS_BYTE_3(t.Y[1])] << 24);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200890
Gilles Peskine5197c662020-08-26 17:03:24 +0200891 t.X[3] = *RK++ ^ \
Gilles Peskine449bd832023-01-11 14:50:10 +0100892 ((uint32_t) FSb[MBEDTLS_BYTE_0(t.Y[3])]) ^
893 ((uint32_t) FSb[MBEDTLS_BYTE_1(t.Y[0])] << 8) ^
894 ((uint32_t) FSb[MBEDTLS_BYTE_2(t.Y[1])] << 16) ^
895 ((uint32_t) FSb[MBEDTLS_BYTE_3(t.Y[2])] << 24);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200896
Gilles Peskine449bd832023-01-11 14:50:10 +0100897 MBEDTLS_PUT_UINT32_LE(t.X[0], output, 0);
898 MBEDTLS_PUT_UINT32_LE(t.X[1], output, 4);
899 MBEDTLS_PUT_UINT32_LE(t.X[2], output, 8);
900 MBEDTLS_PUT_UINT32_LE(t.X[3], output, 12);
Andres AGf5bf7182017-03-03 14:09:56 +0000901
Gilles Peskine449bd832023-01-11 14:50:10 +0100902 mbedtls_platform_zeroize(&t, sizeof(t));
Andrzej Kurek96ae5cd2019-11-12 03:05:51 -0500903
Gilles Peskine449bd832023-01-11 14:50:10 +0100904 return 0;
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200905}
906#endif /* !MBEDTLS_AES_ENCRYPT_ALT */
907
908/*
909 * AES-ECB block decryption
910 */
Yanray Wangb67b4742023-10-31 17:10:32 +0800911#if !defined(MBEDTLS_AES_DECRYPT_ALT) && !defined(MBEDTLS_BLOCK_CIPHER_NO_DECRYPT)
Gilles Peskine449bd832023-01-11 14:50:10 +0100912int mbedtls_internal_aes_decrypt(mbedtls_aes_context *ctx,
913 const unsigned char input[16],
914 unsigned char output[16])
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200915{
916 int i;
Werner Lewisdd76ef32022-05-30 12:00:21 +0100917 uint32_t *RK = ctx->buf + ctx->rk_offset;
Gilles Peskine449bd832023-01-11 14:50:10 +0100918 struct {
Gilles Peskine5197c662020-08-26 17:03:24 +0200919 uint32_t X[4];
920 uint32_t Y[4];
921 } t;
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200922
Gilles Peskine449bd832023-01-11 14:50:10 +0100923 t.X[0] = MBEDTLS_GET_UINT32_LE(input, 0); t.X[0] ^= *RK++;
924 t.X[1] = MBEDTLS_GET_UINT32_LE(input, 4); t.X[1] ^= *RK++;
925 t.X[2] = MBEDTLS_GET_UINT32_LE(input, 8); t.X[2] ^= *RK++;
926 t.X[3] = MBEDTLS_GET_UINT32_LE(input, 12); t.X[3] ^= *RK++;
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200927
Gilles Peskine449bd832023-01-11 14:50:10 +0100928 for (i = (ctx->nr >> 1) - 1; i > 0; i--) {
929 AES_RROUND(t.Y[0], t.Y[1], t.Y[2], t.Y[3], t.X[0], t.X[1], t.X[2], t.X[3]);
930 AES_RROUND(t.X[0], t.X[1], t.X[2], t.X[3], t.Y[0], t.Y[1], t.Y[2], t.Y[3]);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200931 }
932
Gilles Peskine449bd832023-01-11 14:50:10 +0100933 AES_RROUND(t.Y[0], t.Y[1], t.Y[2], t.Y[3], t.X[0], t.X[1], t.X[2], t.X[3]);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200934
Gilles Peskine5197c662020-08-26 17:03:24 +0200935 t.X[0] = *RK++ ^ \
Gilles Peskine449bd832023-01-11 14:50:10 +0100936 ((uint32_t) RSb[MBEDTLS_BYTE_0(t.Y[0])]) ^
937 ((uint32_t) RSb[MBEDTLS_BYTE_1(t.Y[3])] << 8) ^
938 ((uint32_t) RSb[MBEDTLS_BYTE_2(t.Y[2])] << 16) ^
939 ((uint32_t) RSb[MBEDTLS_BYTE_3(t.Y[1])] << 24);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200940
Gilles Peskine5197c662020-08-26 17:03:24 +0200941 t.X[1] = *RK++ ^ \
Gilles Peskine449bd832023-01-11 14:50:10 +0100942 ((uint32_t) RSb[MBEDTLS_BYTE_0(t.Y[1])]) ^
943 ((uint32_t) RSb[MBEDTLS_BYTE_1(t.Y[0])] << 8) ^
944 ((uint32_t) RSb[MBEDTLS_BYTE_2(t.Y[3])] << 16) ^
945 ((uint32_t) RSb[MBEDTLS_BYTE_3(t.Y[2])] << 24);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200946
Gilles Peskine5197c662020-08-26 17:03:24 +0200947 t.X[2] = *RK++ ^ \
Gilles Peskine449bd832023-01-11 14:50:10 +0100948 ((uint32_t) RSb[MBEDTLS_BYTE_0(t.Y[2])]) ^
949 ((uint32_t) RSb[MBEDTLS_BYTE_1(t.Y[1])] << 8) ^
950 ((uint32_t) RSb[MBEDTLS_BYTE_2(t.Y[0])] << 16) ^
951 ((uint32_t) RSb[MBEDTLS_BYTE_3(t.Y[3])] << 24);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200952
Gilles Peskine5197c662020-08-26 17:03:24 +0200953 t.X[3] = *RK++ ^ \
Gilles Peskine449bd832023-01-11 14:50:10 +0100954 ((uint32_t) RSb[MBEDTLS_BYTE_0(t.Y[3])]) ^
955 ((uint32_t) RSb[MBEDTLS_BYTE_1(t.Y[2])] << 8) ^
956 ((uint32_t) RSb[MBEDTLS_BYTE_2(t.Y[1])] << 16) ^
957 ((uint32_t) RSb[MBEDTLS_BYTE_3(t.Y[0])] << 24);
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200958
Gilles Peskine449bd832023-01-11 14:50:10 +0100959 MBEDTLS_PUT_UINT32_LE(t.X[0], output, 0);
960 MBEDTLS_PUT_UINT32_LE(t.X[1], output, 4);
961 MBEDTLS_PUT_UINT32_LE(t.X[2], output, 8);
962 MBEDTLS_PUT_UINT32_LE(t.X[3], output, 12);
Andres AGf5bf7182017-03-03 14:09:56 +0000963
Gilles Peskine449bd832023-01-11 14:50:10 +0100964 mbedtls_platform_zeroize(&t, sizeof(t));
Andrzej Kurek96ae5cd2019-11-12 03:05:51 -0500965
Gilles Peskine449bd832023-01-11 14:50:10 +0100966 return 0;
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200967}
Yanray Wangb67b4742023-10-31 17:10:32 +0800968#endif /* !MBEDTLS_AES_DECRYPT_ALT && !MBEDTLS_BLOCK_CIPHER_NO_DECRYPT */
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200969
Thomas Daubney62af02c2024-06-14 10:37:13 +0100970/*
Thomas Daubney4e5d1832024-06-25 15:21:48 +0100971 * Our intrinsics-based implementation of AESNI requires the round keys to be
Thomas Daubney62af02c2024-06-14 10:37:13 +0100972 * aligned on a 16-byte boundary. We take care of this before creating them,
973 * but the AES context may have moved (this can happen if the library is
974 * called from a language with managed memory), and in later calls it might
975 * have a different alignment with respect to 16-byte memory. So we may need
976 * to realign.
Gilles Peskine148cad12023-03-16 13:08:42 +0100977 */
Thomas Daubney1d08e2f2024-06-25 09:18:20 +0100978#if defined(MAY_NEED_TO_ALIGN)
Dave Rodgman18ddf612023-10-04 14:03:12 +0100979MBEDTLS_MAYBE_UNUSED static void aes_maybe_realign(mbedtls_aes_context *ctx)
Gilles Peskine148cad12023-03-16 13:08:42 +0100980{
Gilles Peskine0de8f852023-03-16 17:14:59 +0100981 unsigned new_offset = mbedtls_aes_rk_offset(ctx->buf);
982 if (new_offset != ctx->rk_offset) {
Gilles Peskine148cad12023-03-16 13:08:42 +0100983 memmove(ctx->buf + new_offset, // new address
984 ctx->buf + ctx->rk_offset, // current address
985 (ctx->nr + 1) * 16); // number of round keys * bytes per rk
986 ctx->rk_offset = new_offset;
987 }
988}
Thomas Daubney1d08e2f2024-06-25 09:18:20 +0100989#endif /* MAY_NEED_TO_ALIGN */
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200990/*
Paul Bakker5121ce52009-01-03 21:22:43 +0000991 * AES-ECB block encryption/decryption
992 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100993int mbedtls_aes_crypt_ecb(mbedtls_aes_context *ctx,
994 int mode,
995 const unsigned char input[16],
996 unsigned char output[16])
Paul Bakker5121ce52009-01-03 21:22:43 +0000997{
Gilles Peskine449bd832023-01-11 14:50:10 +0100998 if (mode != MBEDTLS_AES_ENCRYPT && mode != MBEDTLS_AES_DECRYPT) {
Tuvshinzaya Erdenekhuua8ef1562022-08-05 15:31:57 +0100999 return MBEDTLS_ERR_AES_BAD_INPUT_DATA;
Gilles Peskine449bd832023-01-11 14:50:10 +01001000 }
Manuel Pégourié-Gonnard1aca2602018-12-12 12:56:55 +01001001
Gilles Peskine0de8f852023-03-16 17:14:59 +01001002#if defined(MAY_NEED_TO_ALIGN)
1003 aes_maybe_realign(ctx);
1004#endif
1005
Gilles Peskine9af58cd2023-03-10 22:29:32 +01001006#if defined(MBEDTLS_AESNI_HAVE_CODE)
Gilles Peskine449bd832023-01-11 14:50:10 +01001007 if (mbedtls_aesni_has_support(MBEDTLS_AESNI_AES)) {
1008 return mbedtls_aesni_crypt_ecb(ctx, mode, input, output);
1009 }
Manuel Pégourié-Gonnard5b685652013-12-18 11:45:21 +01001010#endif
1011
Jerry Yu72fd0bd2023-08-18 16:31:01 +08001012#if defined(MBEDTLS_AESCE_HAVE_CODE)
Dave Rodgmanf2249ec2023-08-04 14:27:58 +01001013 if (MBEDTLS_AESCE_HAS_SUPPORT()) {
Jerry Yu2bb3d812023-01-10 17:38:26 +08001014 return mbedtls_aesce_crypt_ecb(ctx, mode, input, output);
1015 }
1016#endif
1017
Jerry Yu29c91ba2023-08-04 11:02:04 +08001018#if !defined(MBEDTLS_AES_USE_HARDWARE_ONLY)
Yanray Wang0d76b6e2023-11-02 11:54:39 +08001019#if !defined(MBEDTLS_BLOCK_CIPHER_NO_DECRYPT)
Yanray Wang111159b2023-11-10 13:41:12 +08001020 if (mode == MBEDTLS_AES_DECRYPT) {
Gilles Peskine449bd832023-01-11 14:50:10 +01001021 return mbedtls_internal_aes_decrypt(ctx, input, output);
Yanray Wang111159b2023-11-10 13:41:12 +08001022 } else
Jerry Yu29c91ba2023-08-04 11:02:04 +08001023#endif
Yanray Wang111159b2023-11-10 13:41:12 +08001024 {
1025 return mbedtls_internal_aes_encrypt(ctx, input, output);
Yanray Wang0d76b6e2023-11-02 11:54:39 +08001026 }
Yanray Wang78ee0c92023-05-15 11:23:50 +08001027#endif /* !MBEDTLS_AES_USE_HARDWARE_ONLY */
Paul Bakker5121ce52009-01-03 21:22:43 +00001028}
1029
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001030#if defined(MBEDTLS_CIPHER_MODE_CBC)
Dave Rodgmand05e7f12023-06-14 18:58:48 +01001031
Paul Bakker5121ce52009-01-03 21:22:43 +00001032/*
1033 * AES-CBC buffer encryption/decryption
1034 */
Gilles Peskine449bd832023-01-11 14:50:10 +01001035int mbedtls_aes_crypt_cbc(mbedtls_aes_context *ctx,
1036 int mode,
1037 size_t length,
1038 unsigned char iv[16],
1039 const unsigned char *input,
1040 unsigned char *output)
Paul Bakker5121ce52009-01-03 21:22:43 +00001041{
Gilles Peskine7820a572021-07-07 21:08:28 +02001042 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Paul Bakker5121ce52009-01-03 21:22:43 +00001043 unsigned char temp[16];
1044
Gilles Peskine449bd832023-01-11 14:50:10 +01001045 if (mode != MBEDTLS_AES_ENCRYPT && mode != MBEDTLS_AES_DECRYPT) {
Tuvshinzaya Erdenekhuua8ef1562022-08-05 15:31:57 +01001046 return MBEDTLS_ERR_AES_BAD_INPUT_DATA;
Gilles Peskine449bd832023-01-11 14:50:10 +01001047 }
Manuel Pégourié-Gonnard3178d1a2018-12-12 13:05:00 +01001048
Paul Elliott2ad93672023-08-11 11:07:06 +01001049 /* Nothing to do if length is zero. */
1050 if (length == 0) {
1051 return 0;
1052 }
1053
Gilles Peskine449bd832023-01-11 14:50:10 +01001054 if (length % 16) {
1055 return MBEDTLS_ERR_AES_INVALID_INPUT_LENGTH;
1056 }
Paul Bakkerf3ccc682010-03-18 21:21:02 +00001057
Dave Rodgman906c63c2023-06-14 17:53:51 +01001058 const unsigned char *ivp = iv;
1059
Gilles Peskine449bd832023-01-11 14:50:10 +01001060 if (mode == MBEDTLS_AES_DECRYPT) {
1061 while (length > 0) {
1062 memcpy(temp, input, 16);
1063 ret = mbedtls_aes_crypt_ecb(ctx, mode, input, output);
1064 if (ret != 0) {
Gilles Peskine7820a572021-07-07 21:08:28 +02001065 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +01001066 }
Dave Rodgmana0b166e2023-06-15 18:44:16 +01001067 /* Avoid using the NEON implementation of mbedtls_xor. Because of the dependency on
Dave Rodgman2dd15b32023-06-15 20:27:53 +01001068 * the result for the next block in CBC, and the cost of transferring that data from
1069 * NEON registers, NEON is slower on aarch64. */
Dave Rodgmana0b166e2023-06-15 18:44:16 +01001070 mbedtls_xor_no_simd(output, output, iv, 16);
Paul Bakker5121ce52009-01-03 21:22:43 +00001071
Gilles Peskine449bd832023-01-11 14:50:10 +01001072 memcpy(iv, temp, 16);
Paul Bakker5121ce52009-01-03 21:22:43 +00001073
1074 input += 16;
1075 output += 16;
1076 length -= 16;
1077 }
Gilles Peskine449bd832023-01-11 14:50:10 +01001078 } else {
1079 while (length > 0) {
Dave Rodgmana0b166e2023-06-15 18:44:16 +01001080 mbedtls_xor_no_simd(output, input, ivp, 16);
Paul Bakker5121ce52009-01-03 21:22:43 +00001081
Gilles Peskine449bd832023-01-11 14:50:10 +01001082 ret = mbedtls_aes_crypt_ecb(ctx, mode, output, output);
1083 if (ret != 0) {
Gilles Peskine7820a572021-07-07 21:08:28 +02001084 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +01001085 }
Dave Rodgman906c63c2023-06-14 17:53:51 +01001086 ivp = output;
Paul Bakker5121ce52009-01-03 21:22:43 +00001087
1088 input += 16;
1089 output += 16;
1090 length -= 16;
1091 }
Dave Rodgman906c63c2023-06-14 17:53:51 +01001092 memcpy(iv, ivp, 16);
Paul Bakker5121ce52009-01-03 21:22:43 +00001093 }
Gilles Peskine7820a572021-07-07 21:08:28 +02001094 ret = 0;
Paul Bakkerf3ccc682010-03-18 21:21:02 +00001095
Gilles Peskine7820a572021-07-07 21:08:28 +02001096exit:
Gilles Peskine449bd832023-01-11 14:50:10 +01001097 return ret;
Paul Bakker5121ce52009-01-03 21:22:43 +00001098}
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001099#endif /* MBEDTLS_CIPHER_MODE_CBC */
Paul Bakker5121ce52009-01-03 21:22:43 +00001100
Aorimn5f778012016-06-09 23:22:58 +02001101#if defined(MBEDTLS_CIPHER_MODE_XTS)
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001102
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001103typedef unsigned char mbedtls_be128[16];
1104
1105/*
1106 * GF(2^128) multiplication function
1107 *
Jaeden Amero5f0b06a2018-05-31 09:23:32 +01001108 * This function multiplies a field element by x in the polynomial field
1109 * representation. It uses 64-bit word operations to gain speed but compensates
Shaun Case8b0ecbc2021-12-20 21:14:10 -08001110 * for machine endianness and hence works correctly on both big and little
Jaeden Amero5f0b06a2018-05-31 09:23:32 +01001111 * endian machines.
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001112 */
Dave Rodgman4ad81cc2023-06-16 15:04:04 +01001113#if defined(MBEDTLS_AESCE_C) || defined(MBEDTLS_AESNI_C)
Dave Rodgman9bb7e6f2023-06-16 09:41:21 +01001114MBEDTLS_OPTIMIZE_FOR_PERFORMANCE
Dave Rodgman4ad81cc2023-06-16 15:04:04 +01001115#endif
Dave Rodgman6cfd9b52023-06-15 18:46:23 +01001116static inline void mbedtls_gf128mul_x_ble(unsigned char r[16],
Dave Rodgman2dd15b32023-06-15 20:27:53 +01001117 const unsigned char x[16])
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001118{
1119 uint64_t a, b, ra, rb;
1120
Gilles Peskine449bd832023-01-11 14:50:10 +01001121 a = MBEDTLS_GET_UINT64_LE(x, 0);
1122 b = MBEDTLS_GET_UINT64_LE(x, 8);
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001123
Gilles Peskine449bd832023-01-11 14:50:10 +01001124 ra = (a << 1) ^ 0x0087 >> (8 - ((b >> 63) << 3));
1125 rb = (a >> 63) | (b << 1);
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001126
Gilles Peskine449bd832023-01-11 14:50:10 +01001127 MBEDTLS_PUT_UINT64_LE(ra, r, 0);
1128 MBEDTLS_PUT_UINT64_LE(rb, r, 8);
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001129}
1130
Aorimn5f778012016-06-09 23:22:58 +02001131/*
1132 * AES-XTS buffer encryption/decryption
Dave Rodgman6cfd9b52023-06-15 18:46:23 +01001133 *
Dave Rodgman9bb7e6f2023-06-16 09:41:21 +01001134 * Use of MBEDTLS_OPTIMIZE_FOR_PERFORMANCE here and for mbedtls_gf128mul_x_ble()
Dave Rodgmanb2814bd2023-06-16 14:50:33 +01001135 * is a 3x performance improvement for gcc -Os, if we have hardware AES support.
Aorimn5f778012016-06-09 23:22:58 +02001136 */
Dave Rodgmanb2814bd2023-06-16 14:50:33 +01001137#if defined(MBEDTLS_AESCE_C) || defined(MBEDTLS_AESNI_C)
Dave Rodgman9bb7e6f2023-06-16 09:41:21 +01001138MBEDTLS_OPTIMIZE_FOR_PERFORMANCE
Dave Rodgmanb2814bd2023-06-16 14:50:33 +01001139#endif
Gilles Peskine449bd832023-01-11 14:50:10 +01001140int mbedtls_aes_crypt_xts(mbedtls_aes_xts_context *ctx,
1141 int mode,
1142 size_t length,
1143 const unsigned char data_unit[16],
1144 const unsigned char *input,
1145 unsigned char *output)
Aorimn5f778012016-06-09 23:22:58 +02001146{
Janos Follath24eed8d2019-11-22 13:21:35 +00001147 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Jaeden Amerod82cd862018-04-28 15:02:45 +01001148 size_t blocks = length / 16;
1149 size_t leftover = length % 16;
1150 unsigned char tweak[16];
1151 unsigned char prev_tweak[16];
1152 unsigned char tmp[16];
Aorimn5f778012016-06-09 23:22:58 +02001153
Gilles Peskine449bd832023-01-11 14:50:10 +01001154 if (mode != MBEDTLS_AES_ENCRYPT && mode != MBEDTLS_AES_DECRYPT) {
Tuvshinzaya Erdenekhuua8ef1562022-08-05 15:31:57 +01001155 return MBEDTLS_ERR_AES_BAD_INPUT_DATA;
Gilles Peskine449bd832023-01-11 14:50:10 +01001156 }
Manuel Pégourié-Gonnard191af132018-12-13 10:15:30 +01001157
Jaeden Amero8381fcb2018-10-11 12:06:15 +01001158 /* Data units must be at least 16 bytes long. */
Gilles Peskine449bd832023-01-11 14:50:10 +01001159 if (length < 16) {
Jaeden Amerod82cd862018-04-28 15:02:45 +01001160 return MBEDTLS_ERR_AES_INVALID_INPUT_LENGTH;
Gilles Peskine449bd832023-01-11 14:50:10 +01001161 }
Aorimn5f778012016-06-09 23:22:58 +02001162
Jaeden Ameroa74faba2018-10-11 12:07:43 +01001163 /* NIST SP 800-38E disallows data units larger than 2**20 blocks. */
Gilles Peskine449bd832023-01-11 14:50:10 +01001164 if (length > (1 << 20) * 16) {
Jaeden Amero0a8b0202018-05-30 15:36:06 +01001165 return MBEDTLS_ERR_AES_INVALID_INPUT_LENGTH;
Gilles Peskine449bd832023-01-11 14:50:10 +01001166 }
Aorimn5f778012016-06-09 23:22:58 +02001167
Jaeden Amerod82cd862018-04-28 15:02:45 +01001168 /* Compute the tweak. */
Gilles Peskine449bd832023-01-11 14:50:10 +01001169 ret = mbedtls_aes_crypt_ecb(&ctx->tweak, MBEDTLS_AES_ENCRYPT,
1170 data_unit, tweak);
1171 if (ret != 0) {
1172 return ret;
1173 }
Aorimn5f778012016-06-09 23:22:58 +02001174
Gilles Peskine449bd832023-01-11 14:50:10 +01001175 while (blocks--) {
Dave Rodgman360e04f2023-06-09 17:18:32 +01001176 if (MBEDTLS_UNLIKELY(leftover && (mode == MBEDTLS_AES_DECRYPT) && blocks == 0)) {
Jaeden Amerod82cd862018-04-28 15:02:45 +01001177 /* We are on the last block in a decrypt operation that has
1178 * leftover bytes, so we need to use the next tweak for this block,
Tom Cosgrove1797b052022-12-04 17:19:59 +00001179 * and this tweak for the leftover bytes. Save the current tweak for
Jaeden Amerod82cd862018-04-28 15:02:45 +01001180 * the leftovers and then update the current tweak for use on this,
1181 * the last full block. */
Gilles Peskine449bd832023-01-11 14:50:10 +01001182 memcpy(prev_tweak, tweak, sizeof(tweak));
1183 mbedtls_gf128mul_x_ble(tweak, tweak);
Jaeden Amerod82cd862018-04-28 15:02:45 +01001184 }
1185
Gilles Peskine449bd832023-01-11 14:50:10 +01001186 mbedtls_xor(tmp, input, tweak, 16);
Jaeden Amerod82cd862018-04-28 15:02:45 +01001187
Gilles Peskine449bd832023-01-11 14:50:10 +01001188 ret = mbedtls_aes_crypt_ecb(&ctx->crypt, mode, tmp, tmp);
1189 if (ret != 0) {
1190 return ret;
1191 }
Jaeden Amerod82cd862018-04-28 15:02:45 +01001192
Gilles Peskine449bd832023-01-11 14:50:10 +01001193 mbedtls_xor(output, tmp, tweak, 16);
Jaeden Amerod82cd862018-04-28 15:02:45 +01001194
1195 /* Update the tweak for the next block. */
Gilles Peskine449bd832023-01-11 14:50:10 +01001196 mbedtls_gf128mul_x_ble(tweak, tweak);
Jaeden Amerod82cd862018-04-28 15:02:45 +01001197
1198 output += 16;
1199 input += 16;
Aorimn5f778012016-06-09 23:22:58 +02001200 }
1201
Gilles Peskine449bd832023-01-11 14:50:10 +01001202 if (leftover) {
Jaeden Amerod82cd862018-04-28 15:02:45 +01001203 /* If we are on the leftover bytes in a decrypt operation, we need to
1204 * use the previous tweak for these bytes (as saved in prev_tweak). */
1205 unsigned char *t = mode == MBEDTLS_AES_DECRYPT ? prev_tweak : tweak;
Aorimn5f778012016-06-09 23:22:58 +02001206
Jaeden Amerod82cd862018-04-28 15:02:45 +01001207 /* We are now on the final part of the data unit, which doesn't divide
1208 * evenly by 16. It's time for ciphertext stealing. */
1209 size_t i;
1210 unsigned char *prev_output = output - 16;
Aorimn5f778012016-06-09 23:22:58 +02001211
Jaeden Amerod82cd862018-04-28 15:02:45 +01001212 /* Copy ciphertext bytes from the previous block to our output for each
Dave Rodgman069e7f42022-11-24 19:37:26 +00001213 * byte of ciphertext we won't steal. */
Gilles Peskine449bd832023-01-11 14:50:10 +01001214 for (i = 0; i < leftover; i++) {
Jaeden Amerod82cd862018-04-28 15:02:45 +01001215 output[i] = prev_output[i];
Aorimn5f778012016-06-09 23:22:58 +02001216 }
Aorimn5f778012016-06-09 23:22:58 +02001217
Dave Rodgman069e7f42022-11-24 19:37:26 +00001218 /* Copy the remainder of the input for this final round. */
Gilles Peskine449bd832023-01-11 14:50:10 +01001219 mbedtls_xor(tmp, input, t, leftover);
Dave Rodgmana8cf6072022-11-22 15:02:54 +00001220
Jaeden Amerod82cd862018-04-28 15:02:45 +01001221 /* Copy ciphertext bytes from the previous block for input in this
1222 * round. */
Gilles Peskine449bd832023-01-11 14:50:10 +01001223 mbedtls_xor(tmp + i, prev_output + i, t + i, 16 - i);
Aorimn5f778012016-06-09 23:22:58 +02001224
Gilles Peskine449bd832023-01-11 14:50:10 +01001225 ret = mbedtls_aes_crypt_ecb(&ctx->crypt, mode, tmp, tmp);
1226 if (ret != 0) {
Jaeden Amerod82cd862018-04-28 15:02:45 +01001227 return ret;
Gilles Peskine449bd832023-01-11 14:50:10 +01001228 }
Aorimn5f778012016-06-09 23:22:58 +02001229
Jaeden Amerod82cd862018-04-28 15:02:45 +01001230 /* Write the result back to the previous block, overriding the previous
1231 * output we copied. */
Gilles Peskine449bd832023-01-11 14:50:10 +01001232 mbedtls_xor(prev_output, tmp, t, 16);
Aorimn5f778012016-06-09 23:22:58 +02001233 }
1234
Gilles Peskine449bd832023-01-11 14:50:10 +01001235 return 0;
Aorimn5f778012016-06-09 23:22:58 +02001236}
1237#endif /* MBEDTLS_CIPHER_MODE_XTS */
1238
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001239#if defined(MBEDTLS_CIPHER_MODE_CFB)
Paul Bakker5121ce52009-01-03 21:22:43 +00001240/*
1241 * AES-CFB128 buffer encryption/decryption
1242 */
Gilles Peskine449bd832023-01-11 14:50:10 +01001243int mbedtls_aes_crypt_cfb128(mbedtls_aes_context *ctx,
1244 int mode,
1245 size_t length,
1246 size_t *iv_off,
1247 unsigned char iv[16],
1248 const unsigned char *input,
1249 unsigned char *output)
Paul Bakker5121ce52009-01-03 21:22:43 +00001250{
Paul Bakker27fdf462011-06-09 13:55:13 +00001251 int c;
Gilles Peskine7820a572021-07-07 21:08:28 +02001252 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Manuel Pégourié-Gonnard1677cca2018-12-13 10:27:13 +01001253 size_t n;
1254
Gilles Peskine449bd832023-01-11 14:50:10 +01001255 if (mode != MBEDTLS_AES_ENCRYPT && mode != MBEDTLS_AES_DECRYPT) {
Tuvshinzaya Erdenekhuua8ef1562022-08-05 15:31:57 +01001256 return MBEDTLS_ERR_AES_BAD_INPUT_DATA;
Gilles Peskine449bd832023-01-11 14:50:10 +01001257 }
Manuel Pégourié-Gonnard1677cca2018-12-13 10:27:13 +01001258
1259 n = *iv_off;
Paul Bakker5121ce52009-01-03 21:22:43 +00001260
Gilles Peskine449bd832023-01-11 14:50:10 +01001261 if (n > 15) {
1262 return MBEDTLS_ERR_AES_BAD_INPUT_DATA;
1263 }
Manuel Pégourié-Gonnard5b89c092018-12-18 10:03:30 +01001264
Gilles Peskine449bd832023-01-11 14:50:10 +01001265 if (mode == MBEDTLS_AES_DECRYPT) {
1266 while (length--) {
1267 if (n == 0) {
1268 ret = mbedtls_aes_crypt_ecb(ctx, MBEDTLS_AES_ENCRYPT, iv, iv);
1269 if (ret != 0) {
Gilles Peskine7820a572021-07-07 21:08:28 +02001270 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +01001271 }
Gilles Peskine7820a572021-07-07 21:08:28 +02001272 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001273
1274 c = *input++;
Gilles Peskine449bd832023-01-11 14:50:10 +01001275 *output++ = (unsigned char) (c ^ iv[n]);
Paul Bakker5121ce52009-01-03 21:22:43 +00001276 iv[n] = (unsigned char) c;
1277
Gilles Peskine449bd832023-01-11 14:50:10 +01001278 n = (n + 1) & 0x0F;
Paul Bakker5121ce52009-01-03 21:22:43 +00001279 }
Gilles Peskine449bd832023-01-11 14:50:10 +01001280 } else {
1281 while (length--) {
1282 if (n == 0) {
1283 ret = mbedtls_aes_crypt_ecb(ctx, MBEDTLS_AES_ENCRYPT, iv, iv);
1284 if (ret != 0) {
Gilles Peskine7820a572021-07-07 21:08:28 +02001285 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +01001286 }
Gilles Peskine7820a572021-07-07 21:08:28 +02001287 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001288
Gilles Peskine449bd832023-01-11 14:50:10 +01001289 iv[n] = *output++ = (unsigned char) (iv[n] ^ *input++);
Paul Bakker5121ce52009-01-03 21:22:43 +00001290
Gilles Peskine449bd832023-01-11 14:50:10 +01001291 n = (n + 1) & 0x0F;
Paul Bakker5121ce52009-01-03 21:22:43 +00001292 }
1293 }
1294
1295 *iv_off = n;
Gilles Peskine7820a572021-07-07 21:08:28 +02001296 ret = 0;
Paul Bakkerf3ccc682010-03-18 21:21:02 +00001297
Gilles Peskine7820a572021-07-07 21:08:28 +02001298exit:
Gilles Peskine449bd832023-01-11 14:50:10 +01001299 return ret;
Paul Bakker5121ce52009-01-03 21:22:43 +00001300}
Paul Bakker556efba2014-01-24 15:38:12 +01001301
1302/*
1303 * AES-CFB8 buffer encryption/decryption
1304 */
Gilles Peskine449bd832023-01-11 14:50:10 +01001305int mbedtls_aes_crypt_cfb8(mbedtls_aes_context *ctx,
1306 int mode,
1307 size_t length,
1308 unsigned char iv[16],
1309 const unsigned char *input,
1310 unsigned char *output)
Paul Bakker556efba2014-01-24 15:38:12 +01001311{
Gilles Peskine7820a572021-07-07 21:08:28 +02001312 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Paul Bakker556efba2014-01-24 15:38:12 +01001313 unsigned char c;
1314 unsigned char ov[17];
1315
Gilles Peskine449bd832023-01-11 14:50:10 +01001316 if (mode != MBEDTLS_AES_ENCRYPT && mode != MBEDTLS_AES_DECRYPT) {
Tuvshinzaya Erdenekhuua8ef1562022-08-05 15:31:57 +01001317 return MBEDTLS_ERR_AES_BAD_INPUT_DATA;
Gilles Peskine449bd832023-01-11 14:50:10 +01001318 }
1319 while (length--) {
1320 memcpy(ov, iv, 16);
1321 ret = mbedtls_aes_crypt_ecb(ctx, MBEDTLS_AES_ENCRYPT, iv, iv);
1322 if (ret != 0) {
Gilles Peskine7820a572021-07-07 21:08:28 +02001323 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +01001324 }
Paul Bakker556efba2014-01-24 15:38:12 +01001325
Gilles Peskine449bd832023-01-11 14:50:10 +01001326 if (mode == MBEDTLS_AES_DECRYPT) {
Paul Bakker556efba2014-01-24 15:38:12 +01001327 ov[16] = *input;
Gilles Peskine449bd832023-01-11 14:50:10 +01001328 }
Paul Bakker556efba2014-01-24 15:38:12 +01001329
Gilles Peskine449bd832023-01-11 14:50:10 +01001330 c = *output++ = (unsigned char) (iv[0] ^ *input++);
Paul Bakker556efba2014-01-24 15:38:12 +01001331
Gilles Peskine449bd832023-01-11 14:50:10 +01001332 if (mode == MBEDTLS_AES_ENCRYPT) {
Paul Bakker556efba2014-01-24 15:38:12 +01001333 ov[16] = c;
Gilles Peskine449bd832023-01-11 14:50:10 +01001334 }
Paul Bakker556efba2014-01-24 15:38:12 +01001335
Gilles Peskine449bd832023-01-11 14:50:10 +01001336 memcpy(iv, ov + 1, 16);
Paul Bakker556efba2014-01-24 15:38:12 +01001337 }
Gilles Peskine7820a572021-07-07 21:08:28 +02001338 ret = 0;
Paul Bakker556efba2014-01-24 15:38:12 +01001339
Gilles Peskine7820a572021-07-07 21:08:28 +02001340exit:
Gilles Peskine449bd832023-01-11 14:50:10 +01001341 return ret;
Paul Bakker556efba2014-01-24 15:38:12 +01001342}
Simon Butcher76a5b222018-04-22 22:57:27 +01001343#endif /* MBEDTLS_CIPHER_MODE_CFB */
1344
1345#if defined(MBEDTLS_CIPHER_MODE_OFB)
1346/*
1347 * AES-OFB (Output Feedback Mode) buffer encryption/decryption
1348 */
Gilles Peskine449bd832023-01-11 14:50:10 +01001349int mbedtls_aes_crypt_ofb(mbedtls_aes_context *ctx,
1350 size_t length,
1351 size_t *iv_off,
1352 unsigned char iv[16],
1353 const unsigned char *input,
1354 unsigned char *output)
Simon Butcher76a5b222018-04-22 22:57:27 +01001355{
Simon Butcherad4e4932018-04-29 00:43:47 +01001356 int ret = 0;
Manuel Pégourié-Gonnard8e41eb72018-12-13 11:00:56 +01001357 size_t n;
1358
Manuel Pégourié-Gonnard8e41eb72018-12-13 11:00:56 +01001359 n = *iv_off;
Simon Butcher76a5b222018-04-22 22:57:27 +01001360
Gilles Peskine449bd832023-01-11 14:50:10 +01001361 if (n > 15) {
1362 return MBEDTLS_ERR_AES_BAD_INPUT_DATA;
1363 }
Manuel Pégourié-Gonnard5b89c092018-12-18 10:03:30 +01001364
Gilles Peskine449bd832023-01-11 14:50:10 +01001365 while (length--) {
1366 if (n == 0) {
1367 ret = mbedtls_aes_crypt_ecb(ctx, MBEDTLS_AES_ENCRYPT, iv, iv);
1368 if (ret != 0) {
Simon Butcherad4e4932018-04-29 00:43:47 +01001369 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +01001370 }
Simon Butcherad4e4932018-04-29 00:43:47 +01001371 }
Simon Butcher76a5b222018-04-22 22:57:27 +01001372 *output++ = *input++ ^ iv[n];
1373
Gilles Peskine449bd832023-01-11 14:50:10 +01001374 n = (n + 1) & 0x0F;
Simon Butcher76a5b222018-04-22 22:57:27 +01001375 }
1376
1377 *iv_off = n;
1378
Simon Butcherad4e4932018-04-29 00:43:47 +01001379exit:
Gilles Peskine449bd832023-01-11 14:50:10 +01001380 return ret;
Simon Butcher76a5b222018-04-22 22:57:27 +01001381}
1382#endif /* MBEDTLS_CIPHER_MODE_OFB */
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001383
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001384#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001385/*
1386 * AES-CTR buffer encryption/decryption
1387 */
Gilles Peskine449bd832023-01-11 14:50:10 +01001388int mbedtls_aes_crypt_ctr(mbedtls_aes_context *ctx,
1389 size_t length,
1390 size_t *nc_off,
1391 unsigned char nonce_counter[16],
1392 unsigned char stream_block[16],
1393 const unsigned char *input,
1394 unsigned char *output)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001395{
Gilles Peskine7820a572021-07-07 21:08:28 +02001396 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Manuel Pégourié-Gonnard2bc535b2018-12-13 11:08:36 +01001397
Dave Rodgmanc4f984f2024-01-12 18:29:01 +00001398 size_t offset = *nc_off;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001399
Dave Rodgmanc4f984f2024-01-12 18:29:01 +00001400 if (offset > 0x0F) {
Gilles Peskine449bd832023-01-11 14:50:10 +01001401 return MBEDTLS_ERR_AES_BAD_INPUT_DATA;
1402 }
Mohammad Azim Khan3f7f8172017-11-23 17:49:05 +00001403
Dave Rodgmanc4f984f2024-01-12 18:29:01 +00001404 for (size_t i = 0; i < length;) {
1405 size_t n = 16;
1406 if (offset == 0) {
Gilles Peskine449bd832023-01-11 14:50:10 +01001407 ret = mbedtls_aes_crypt_ecb(ctx, MBEDTLS_AES_ENCRYPT, nonce_counter, stream_block);
1408 if (ret != 0) {
Gilles Peskine7820a572021-07-07 21:08:28 +02001409 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +01001410 }
Dave Rodgman591ff052024-01-13 16:42:38 +00001411 mbedtls_ctr_increment_counter(nonce_counter);
Dave Rodgmanc4f984f2024-01-12 18:29:01 +00001412 } else {
1413 n -= offset;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001414 }
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001415
Dave Rodgmanc4f984f2024-01-12 18:29:01 +00001416 if (n > (length - i)) {
1417 n = (length - i);
1418 }
1419 mbedtls_xor(&output[i], &input[i], &stream_block[offset], n);
1420 // offset might be non-zero for the last block, but in that case, we don't use it again
1421 offset = 0;
1422 i += n;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001423 }
1424
Dave Rodgmanc4f984f2024-01-12 18:29:01 +00001425 // capture offset for future resumption
1426 *nc_off = (*nc_off + length) % 16;
1427
Gilles Peskine7820a572021-07-07 21:08:28 +02001428 ret = 0;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001429
Gilles Peskine7820a572021-07-07 21:08:28 +02001430exit:
Gilles Peskine449bd832023-01-11 14:50:10 +01001431 return ret;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001432}
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001433#endif /* MBEDTLS_CIPHER_MODE_CTR */
Manuel Pégourié-Gonnard1ec220b2014-03-10 11:20:17 +01001434
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001435#if defined(MBEDTLS_SELF_TEST)
Paul Bakker5121ce52009-01-03 21:22:43 +00001436/*
1437 * AES test vectors from:
1438 *
1439 * http://csrc.nist.gov/archive/aes/rijndael/rijndael-vals.zip
1440 */
Yanray Wangb67b4742023-10-31 17:10:32 +08001441#if !defined(MBEDTLS_BLOCK_CIPHER_NO_DECRYPT)
Yanray Wang62c99912023-05-11 11:06:53 +08001442static const unsigned char aes_test_ecb_dec[][16] =
Paul Bakker5121ce52009-01-03 21:22:43 +00001443{
1444 { 0x44, 0x41, 0x6A, 0xC2, 0xD1, 0xF5, 0x3C, 0x58,
1445 0x33, 0x03, 0x91, 0x7E, 0x6B, 0xE9, 0xEB, 0xE0 },
Yanray Wang62c99912023-05-11 11:06:53 +08001446#if !defined(MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH)
Paul Bakker5121ce52009-01-03 21:22:43 +00001447 { 0x48, 0xE3, 0x1E, 0x9E, 0x25, 0x67, 0x18, 0xF2,
1448 0x92, 0x29, 0x31, 0x9C, 0x19, 0xF1, 0x5B, 0xA4 },
1449 { 0x05, 0x8C, 0xCF, 0xFD, 0xBB, 0xCB, 0x38, 0x2D,
1450 0x1F, 0x6F, 0x56, 0x58, 0x5D, 0x8A, 0x4A, 0xDE }
Yanray Wang62c99912023-05-11 11:06:53 +08001451#endif
Paul Bakker5121ce52009-01-03 21:22:43 +00001452};
Yanray Wang78ee0c92023-05-15 11:23:50 +08001453#endif
Paul Bakker5121ce52009-01-03 21:22:43 +00001454
Yanray Wang62c99912023-05-11 11:06:53 +08001455static const unsigned char aes_test_ecb_enc[][16] =
Paul Bakker5121ce52009-01-03 21:22:43 +00001456{
1457 { 0xC3, 0x4C, 0x05, 0x2C, 0xC0, 0xDA, 0x8D, 0x73,
1458 0x45, 0x1A, 0xFE, 0x5F, 0x03, 0xBE, 0x29, 0x7F },
Yanray Wang62c99912023-05-11 11:06:53 +08001459#if !defined(MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH)
Paul Bakker5121ce52009-01-03 21:22:43 +00001460 { 0xF3, 0xF6, 0x75, 0x2A, 0xE8, 0xD7, 0x83, 0x11,
1461 0x38, 0xF0, 0x41, 0x56, 0x06, 0x31, 0xB1, 0x14 },
1462 { 0x8B, 0x79, 0xEE, 0xCC, 0x93, 0xA0, 0xEE, 0x5D,
1463 0xFF, 0x30, 0xB4, 0xEA, 0x21, 0x63, 0x6D, 0xA4 }
Yanray Wang62c99912023-05-11 11:06:53 +08001464#endif
Paul Bakker5121ce52009-01-03 21:22:43 +00001465};
1466
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001467#if defined(MBEDTLS_CIPHER_MODE_CBC)
Yanray Wang62c99912023-05-11 11:06:53 +08001468static const unsigned char aes_test_cbc_dec[][16] =
Paul Bakker5121ce52009-01-03 21:22:43 +00001469{
1470 { 0xFA, 0xCA, 0x37, 0xE0, 0xB0, 0xC8, 0x53, 0x73,
1471 0xDF, 0x70, 0x6E, 0x73, 0xF7, 0xC9, 0xAF, 0x86 },
Yanray Wang62c99912023-05-11 11:06:53 +08001472#if !defined(MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH)
Paul Bakker5121ce52009-01-03 21:22:43 +00001473 { 0x5D, 0xF6, 0x78, 0xDD, 0x17, 0xBA, 0x4E, 0x75,
1474 0xB6, 0x17, 0x68, 0xC6, 0xAD, 0xEF, 0x7C, 0x7B },
1475 { 0x48, 0x04, 0xE1, 0x81, 0x8F, 0xE6, 0x29, 0x75,
1476 0x19, 0xA3, 0xE8, 0x8C, 0x57, 0x31, 0x04, 0x13 }
Yanray Wang62c99912023-05-11 11:06:53 +08001477#endif
Paul Bakker5121ce52009-01-03 21:22:43 +00001478};
1479
Yanray Wang62c99912023-05-11 11:06:53 +08001480static const unsigned char aes_test_cbc_enc[][16] =
Paul Bakker5121ce52009-01-03 21:22:43 +00001481{
1482 { 0x8A, 0x05, 0xFC, 0x5E, 0x09, 0x5A, 0xF4, 0x84,
1483 0x8A, 0x08, 0xD3, 0x28, 0xD3, 0x68, 0x8E, 0x3D },
Yanray Wang62c99912023-05-11 11:06:53 +08001484#if !defined(MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH)
Paul Bakker5121ce52009-01-03 21:22:43 +00001485 { 0x7B, 0xD9, 0x66, 0xD5, 0x3A, 0xD8, 0xC1, 0xBB,
1486 0x85, 0xD2, 0xAD, 0xFA, 0xE8, 0x7B, 0xB1, 0x04 },
1487 { 0xFE, 0x3C, 0x53, 0x65, 0x3E, 0x2F, 0x45, 0xB5,
1488 0x6F, 0xCD, 0x88, 0xB2, 0xCC, 0x89, 0x8F, 0xF0 }
Yanray Wang62c99912023-05-11 11:06:53 +08001489#endif
Paul Bakker5121ce52009-01-03 21:22:43 +00001490};
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001491#endif /* MBEDTLS_CIPHER_MODE_CBC */
Paul Bakker5121ce52009-01-03 21:22:43 +00001492
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001493#if defined(MBEDTLS_CIPHER_MODE_CFB)
Paul Bakker5121ce52009-01-03 21:22:43 +00001494/*
1495 * AES-CFB128 test vectors from:
1496 *
1497 * http://csrc.nist.gov/publications/nistpubs/800-38a/sp800-38a.pdf
1498 */
Yanray Wang62c99912023-05-11 11:06:53 +08001499static const unsigned char aes_test_cfb128_key[][32] =
Paul Bakker5121ce52009-01-03 21:22:43 +00001500{
1501 { 0x2B, 0x7E, 0x15, 0x16, 0x28, 0xAE, 0xD2, 0xA6,
1502 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3C },
Yanray Wang62c99912023-05-11 11:06:53 +08001503#if !defined(MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH)
Paul Bakker5121ce52009-01-03 21:22:43 +00001504 { 0x8E, 0x73, 0xB0, 0xF7, 0xDA, 0x0E, 0x64, 0x52,
1505 0xC8, 0x10, 0xF3, 0x2B, 0x80, 0x90, 0x79, 0xE5,
1506 0x62, 0xF8, 0xEA, 0xD2, 0x52, 0x2C, 0x6B, 0x7B },
1507 { 0x60, 0x3D, 0xEB, 0x10, 0x15, 0xCA, 0x71, 0xBE,
1508 0x2B, 0x73, 0xAE, 0xF0, 0x85, 0x7D, 0x77, 0x81,
1509 0x1F, 0x35, 0x2C, 0x07, 0x3B, 0x61, 0x08, 0xD7,
1510 0x2D, 0x98, 0x10, 0xA3, 0x09, 0x14, 0xDF, 0xF4 }
Yanray Wang62c99912023-05-11 11:06:53 +08001511#endif
Paul Bakker5121ce52009-01-03 21:22:43 +00001512};
1513
1514static const unsigned char aes_test_cfb128_iv[16] =
1515{
1516 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
1517 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F
1518};
1519
1520static const unsigned char aes_test_cfb128_pt[64] =
1521{
1522 0x6B, 0xC1, 0xBE, 0xE2, 0x2E, 0x40, 0x9F, 0x96,
1523 0xE9, 0x3D, 0x7E, 0x11, 0x73, 0x93, 0x17, 0x2A,
1524 0xAE, 0x2D, 0x8A, 0x57, 0x1E, 0x03, 0xAC, 0x9C,
1525 0x9E, 0xB7, 0x6F, 0xAC, 0x45, 0xAF, 0x8E, 0x51,
1526 0x30, 0xC8, 0x1C, 0x46, 0xA3, 0x5C, 0xE4, 0x11,
1527 0xE5, 0xFB, 0xC1, 0x19, 0x1A, 0x0A, 0x52, 0xEF,
1528 0xF6, 0x9F, 0x24, 0x45, 0xDF, 0x4F, 0x9B, 0x17,
1529 0xAD, 0x2B, 0x41, 0x7B, 0xE6, 0x6C, 0x37, 0x10
1530};
1531
Yanray Wang62c99912023-05-11 11:06:53 +08001532static const unsigned char aes_test_cfb128_ct[][64] =
Paul Bakker5121ce52009-01-03 21:22:43 +00001533{
1534 { 0x3B, 0x3F, 0xD9, 0x2E, 0xB7, 0x2D, 0xAD, 0x20,
1535 0x33, 0x34, 0x49, 0xF8, 0xE8, 0x3C, 0xFB, 0x4A,
1536 0xC8, 0xA6, 0x45, 0x37, 0xA0, 0xB3, 0xA9, 0x3F,
1537 0xCD, 0xE3, 0xCD, 0xAD, 0x9F, 0x1C, 0xE5, 0x8B,
1538 0x26, 0x75, 0x1F, 0x67, 0xA3, 0xCB, 0xB1, 0x40,
1539 0xB1, 0x80, 0x8C, 0xF1, 0x87, 0xA4, 0xF4, 0xDF,
1540 0xC0, 0x4B, 0x05, 0x35, 0x7C, 0x5D, 0x1C, 0x0E,
1541 0xEA, 0xC4, 0xC6, 0x6F, 0x9F, 0xF7, 0xF2, 0xE6 },
Yanray Wang62c99912023-05-11 11:06:53 +08001542#if !defined(MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH)
Paul Bakker5121ce52009-01-03 21:22:43 +00001543 { 0xCD, 0xC8, 0x0D, 0x6F, 0xDD, 0xF1, 0x8C, 0xAB,
1544 0x34, 0xC2, 0x59, 0x09, 0xC9, 0x9A, 0x41, 0x74,
1545 0x67, 0xCE, 0x7F, 0x7F, 0x81, 0x17, 0x36, 0x21,
1546 0x96, 0x1A, 0x2B, 0x70, 0x17, 0x1D, 0x3D, 0x7A,
1547 0x2E, 0x1E, 0x8A, 0x1D, 0xD5, 0x9B, 0x88, 0xB1,
1548 0xC8, 0xE6, 0x0F, 0xED, 0x1E, 0xFA, 0xC4, 0xC9,
1549 0xC0, 0x5F, 0x9F, 0x9C, 0xA9, 0x83, 0x4F, 0xA0,
1550 0x42, 0xAE, 0x8F, 0xBA, 0x58, 0x4B, 0x09, 0xFF },
1551 { 0xDC, 0x7E, 0x84, 0xBF, 0xDA, 0x79, 0x16, 0x4B,
1552 0x7E, 0xCD, 0x84, 0x86, 0x98, 0x5D, 0x38, 0x60,
1553 0x39, 0xFF, 0xED, 0x14, 0x3B, 0x28, 0xB1, 0xC8,
1554 0x32, 0x11, 0x3C, 0x63, 0x31, 0xE5, 0x40, 0x7B,
1555 0xDF, 0x10, 0x13, 0x24, 0x15, 0xE5, 0x4B, 0x92,
1556 0xA1, 0x3E, 0xD0, 0xA8, 0x26, 0x7A, 0xE2, 0xF9,
1557 0x75, 0xA3, 0x85, 0x74, 0x1A, 0xB9, 0xCE, 0xF8,
1558 0x20, 0x31, 0x62, 0x3D, 0x55, 0xB1, 0xE4, 0x71 }
Yanray Wang62c99912023-05-11 11:06:53 +08001559#endif
Paul Bakker5121ce52009-01-03 21:22:43 +00001560};
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001561#endif /* MBEDTLS_CIPHER_MODE_CFB */
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001562
Simon Butcherad4e4932018-04-29 00:43:47 +01001563#if defined(MBEDTLS_CIPHER_MODE_OFB)
1564/*
1565 * AES-OFB test vectors from:
1566 *
Simon Butcher5db13622018-06-04 22:11:25 +01001567 * https://csrc.nist.gov/publications/detail/sp/800-38a/final
Simon Butcherad4e4932018-04-29 00:43:47 +01001568 */
Yanray Wang62c99912023-05-11 11:06:53 +08001569static const unsigned char aes_test_ofb_key[][32] =
Simon Butcherad4e4932018-04-29 00:43:47 +01001570{
1571 { 0x2B, 0x7E, 0x15, 0x16, 0x28, 0xAE, 0xD2, 0xA6,
1572 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3C },
Yanray Wang62c99912023-05-11 11:06:53 +08001573#if !defined(MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH)
Simon Butcherad4e4932018-04-29 00:43:47 +01001574 { 0x8E, 0x73, 0xB0, 0xF7, 0xDA, 0x0E, 0x64, 0x52,
1575 0xC8, 0x10, 0xF3, 0x2B, 0x80, 0x90, 0x79, 0xE5,
1576 0x62, 0xF8, 0xEA, 0xD2, 0x52, 0x2C, 0x6B, 0x7B },
1577 { 0x60, 0x3D, 0xEB, 0x10, 0x15, 0xCA, 0x71, 0xBE,
1578 0x2B, 0x73, 0xAE, 0xF0, 0x85, 0x7D, 0x77, 0x81,
1579 0x1F, 0x35, 0x2C, 0x07, 0x3B, 0x61, 0x08, 0xD7,
1580 0x2D, 0x98, 0x10, 0xA3, 0x09, 0x14, 0xDF, 0xF4 }
Yanray Wang62c99912023-05-11 11:06:53 +08001581#endif
Simon Butcherad4e4932018-04-29 00:43:47 +01001582};
1583
1584static const unsigned char aes_test_ofb_iv[16] =
1585{
1586 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
1587 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F
1588};
1589
1590static const unsigned char aes_test_ofb_pt[64] =
1591{
1592 0x6B, 0xC1, 0xBE, 0xE2, 0x2E, 0x40, 0x9F, 0x96,
1593 0xE9, 0x3D, 0x7E, 0x11, 0x73, 0x93, 0x17, 0x2A,
1594 0xAE, 0x2D, 0x8A, 0x57, 0x1E, 0x03, 0xAC, 0x9C,
1595 0x9E, 0xB7, 0x6F, 0xAC, 0x45, 0xAF, 0x8E, 0x51,
1596 0x30, 0xC8, 0x1C, 0x46, 0xA3, 0x5C, 0xE4, 0x11,
1597 0xE5, 0xFB, 0xC1, 0x19, 0x1A, 0x0A, 0x52, 0xEF,
1598 0xF6, 0x9F, 0x24, 0x45, 0xDF, 0x4F, 0x9B, 0x17,
1599 0xAD, 0x2B, 0x41, 0x7B, 0xE6, 0x6C, 0x37, 0x10
1600};
1601
Yanray Wang62c99912023-05-11 11:06:53 +08001602static const unsigned char aes_test_ofb_ct[][64] =
Simon Butcherad4e4932018-04-29 00:43:47 +01001603{
1604 { 0x3B, 0x3F, 0xD9, 0x2E, 0xB7, 0x2D, 0xAD, 0x20,
1605 0x33, 0x34, 0x49, 0xF8, 0xE8, 0x3C, 0xFB, 0x4A,
1606 0x77, 0x89, 0x50, 0x8d, 0x16, 0x91, 0x8f, 0x03,
1607 0xf5, 0x3c, 0x52, 0xda, 0xc5, 0x4e, 0xd8, 0x25,
1608 0x97, 0x40, 0x05, 0x1e, 0x9c, 0x5f, 0xec, 0xf6,
1609 0x43, 0x44, 0xf7, 0xa8, 0x22, 0x60, 0xed, 0xcc,
1610 0x30, 0x4c, 0x65, 0x28, 0xf6, 0x59, 0xc7, 0x78,
1611 0x66, 0xa5, 0x10, 0xd9, 0xc1, 0xd6, 0xae, 0x5e },
Yanray Wang62c99912023-05-11 11:06:53 +08001612#if !defined(MBEDTLS_AES_ONLY_128_BIT_KEY_LENGTH)
Simon Butcherad4e4932018-04-29 00:43:47 +01001613 { 0xCD, 0xC8, 0x0D, 0x6F, 0xDD, 0xF1, 0x8C, 0xAB,
1614 0x34, 0xC2, 0x59, 0x09, 0xC9, 0x9A, 0x41, 0x74,
1615 0xfc, 0xc2, 0x8b, 0x8d, 0x4c, 0x63, 0x83, 0x7c,
1616 0x09, 0xe8, 0x17, 0x00, 0xc1, 0x10, 0x04, 0x01,
1617 0x8d, 0x9a, 0x9a, 0xea, 0xc0, 0xf6, 0x59, 0x6f,
1618 0x55, 0x9c, 0x6d, 0x4d, 0xaf, 0x59, 0xa5, 0xf2,
1619 0x6d, 0x9f, 0x20, 0x08, 0x57, 0xca, 0x6c, 0x3e,
1620 0x9c, 0xac, 0x52, 0x4b, 0xd9, 0xac, 0xc9, 0x2a },
1621 { 0xDC, 0x7E, 0x84, 0xBF, 0xDA, 0x79, 0x16, 0x4B,
1622 0x7E, 0xCD, 0x84, 0x86, 0x98, 0x5D, 0x38, 0x60,
1623 0x4f, 0xeb, 0xdc, 0x67, 0x40, 0xd2, 0x0b, 0x3a,
1624 0xc8, 0x8f, 0x6a, 0xd8, 0x2a, 0x4f, 0xb0, 0x8d,
1625 0x71, 0xab, 0x47, 0xa0, 0x86, 0xe8, 0x6e, 0xed,
1626 0xf3, 0x9d, 0x1c, 0x5b, 0xba, 0x97, 0xc4, 0x08,
1627 0x01, 0x26, 0x14, 0x1d, 0x67, 0xf3, 0x7b, 0xe8,
1628 0x53, 0x8f, 0x5a, 0x8b, 0xe7, 0x40, 0xe4, 0x84 }
Yanray Wang62c99912023-05-11 11:06:53 +08001629#endif
Simon Butcherad4e4932018-04-29 00:43:47 +01001630};
1631#endif /* MBEDTLS_CIPHER_MODE_OFB */
1632
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001633#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001634/*
1635 * AES-CTR test vectors from:
1636 *
1637 * http://www.faqs.org/rfcs/rfc3686.html
1638 */
1639
Yanray Wang62c99912023-05-11 11:06:53 +08001640static const unsigned char aes_test_ctr_key[][16] =
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001641{
1642 { 0xAE, 0x68, 0x52, 0xF8, 0x12, 0x10, 0x67, 0xCC,
1643 0x4B, 0xF7, 0xA5, 0x76, 0x55, 0x77, 0xF3, 0x9E },
1644 { 0x7E, 0x24, 0x06, 0x78, 0x17, 0xFA, 0xE0, 0xD7,
1645 0x43, 0xD6, 0xCE, 0x1F, 0x32, 0x53, 0x91, 0x63 },
1646 { 0x76, 0x91, 0xBE, 0x03, 0x5E, 0x50, 0x20, 0xA8,
1647 0xAC, 0x6E, 0x61, 0x85, 0x29, 0xF9, 0xA0, 0xDC }
1648};
1649
Yanray Wang62c99912023-05-11 11:06:53 +08001650static const unsigned char aes_test_ctr_nonce_counter[][16] =
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001651{
1652 { 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00,
1653 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01 },
1654 { 0x00, 0x6C, 0xB6, 0xDB, 0xC0, 0x54, 0x3B, 0x59,
1655 0xDA, 0x48, 0xD9, 0x0B, 0x00, 0x00, 0x00, 0x01 },
1656 { 0x00, 0xE0, 0x01, 0x7B, 0x27, 0x77, 0x7F, 0x3F,
1657 0x4A, 0x17, 0x86, 0xF0, 0x00, 0x00, 0x00, 0x01 }
1658};
1659
Yanray Wang62c99912023-05-11 11:06:53 +08001660static const unsigned char aes_test_ctr_pt[][48] =
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001661{
1662 { 0x53, 0x69, 0x6E, 0x67, 0x6C, 0x65, 0x20, 0x62,
1663 0x6C, 0x6F, 0x63, 0x6B, 0x20, 0x6D, 0x73, 0x67 },
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001664 { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
1665 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,
1666 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
1667 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F },
1668
1669 { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
1670 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,
1671 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
1672 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F,
1673 0x20, 0x21, 0x22, 0x23 }
1674};
1675
Yanray Wang62c99912023-05-11 11:06:53 +08001676static const unsigned char aes_test_ctr_ct[][48] =
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001677{
1678 { 0xE4, 0x09, 0x5D, 0x4F, 0xB7, 0xA7, 0xB3, 0x79,
1679 0x2D, 0x61, 0x75, 0xA3, 0x26, 0x13, 0x11, 0xB8 },
1680 { 0x51, 0x04, 0xA1, 0x06, 0x16, 0x8A, 0x72, 0xD9,
1681 0x79, 0x0D, 0x41, 0xEE, 0x8E, 0xDA, 0xD3, 0x88,
1682 0xEB, 0x2E, 0x1E, 0xFC, 0x46, 0xDA, 0x57, 0xC8,
1683 0xFC, 0xE6, 0x30, 0xDF, 0x91, 0x41, 0xBE, 0x28 },
1684 { 0xC1, 0xCF, 0x48, 0xA8, 0x9F, 0x2F, 0xFD, 0xD9,
1685 0xCF, 0x46, 0x52, 0xE9, 0xEF, 0xDB, 0x72, 0xD7,
1686 0x45, 0x40, 0xA4, 0x2B, 0xDE, 0x6D, 0x78, 0x36,
1687 0xD5, 0x9A, 0x5C, 0xEA, 0xAE, 0xF3, 0x10, 0x53,
1688 0x25, 0xB2, 0x07, 0x2F }
1689};
1690
1691static const int aes_test_ctr_len[3] =
Gilles Peskine449bd832023-01-11 14:50:10 +01001692{ 16, 32, 36 };
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001693#endif /* MBEDTLS_CIPHER_MODE_CTR */
Paul Bakker5121ce52009-01-03 21:22:43 +00001694
Jaeden Amero21d79cf2018-05-23 10:30:18 +01001695#if defined(MBEDTLS_CIPHER_MODE_XTS)
1696/*
1697 * AES-XTS test vectors from:
1698 *
1699 * IEEE P1619/D16 Annex B
1700 * https://web.archive.org/web/20150629024421/http://grouper.ieee.org/groups/1619/email/pdf00086.pdf
1701 * (Archived from original at http://grouper.ieee.org/groups/1619/email/pdf00086.pdf)
1702 */
1703static const unsigned char aes_test_xts_key[][32] =
1704{
1705 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1706 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1707 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1708 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
1709 { 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11,
1710 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11,
1711 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22,
1712 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22 },
1713 { 0xff, 0xfe, 0xfd, 0xfc, 0xfb, 0xfa, 0xf9, 0xf8,
1714 0xf7, 0xf6, 0xf5, 0xf4, 0xf3, 0xf2, 0xf1, 0xf0,
1715 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22,
1716 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22 },
1717};
1718
1719static const unsigned char aes_test_xts_pt32[][32] =
1720{
1721 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1722 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1723 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1724 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
1725 { 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44,
1726 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44,
1727 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44,
1728 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44 },
1729 { 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44,
1730 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44,
1731 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44,
1732 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44 },
1733};
1734
1735static const unsigned char aes_test_xts_ct32[][32] =
1736{
1737 { 0x91, 0x7c, 0xf6, 0x9e, 0xbd, 0x68, 0xb2, 0xec,
1738 0x9b, 0x9f, 0xe9, 0xa3, 0xea, 0xdd, 0xa6, 0x92,
1739 0xcd, 0x43, 0xd2, 0xf5, 0x95, 0x98, 0xed, 0x85,
1740 0x8c, 0x02, 0xc2, 0x65, 0x2f, 0xbf, 0x92, 0x2e },
1741 { 0xc4, 0x54, 0x18, 0x5e, 0x6a, 0x16, 0x93, 0x6e,
1742 0x39, 0x33, 0x40, 0x38, 0xac, 0xef, 0x83, 0x8b,
1743 0xfb, 0x18, 0x6f, 0xff, 0x74, 0x80, 0xad, 0xc4,
1744 0x28, 0x93, 0x82, 0xec, 0xd6, 0xd3, 0x94, 0xf0 },
1745 { 0xaf, 0x85, 0x33, 0x6b, 0x59, 0x7a, 0xfc, 0x1a,
1746 0x90, 0x0b, 0x2e, 0xb2, 0x1e, 0xc9, 0x49, 0xd2,
1747 0x92, 0xdf, 0x4c, 0x04, 0x7e, 0x0b, 0x21, 0x53,
1748 0x21, 0x86, 0xa5, 0x97, 0x1a, 0x22, 0x7a, 0x89 },
1749};
1750
1751static const unsigned char aes_test_xts_data_unit[][16] =
1752{
Gilles Peskine449bd832023-01-11 14:50:10 +01001753 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1754 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
1755 { 0x33, 0x33, 0x33, 0x33, 0x33, 0x00, 0x00, 0x00,
1756 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
1757 { 0x33, 0x33, 0x33, 0x33, 0x33, 0x00, 0x00, 0x00,
1758 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
Jaeden Amero21d79cf2018-05-23 10:30:18 +01001759};
1760
1761#endif /* MBEDTLS_CIPHER_MODE_XTS */
1762
Paul Bakker5121ce52009-01-03 21:22:43 +00001763/*
1764 * Checkup routine
1765 */
Gilles Peskine449bd832023-01-11 14:50:10 +01001766int mbedtls_aes_self_test(int verbose)
Paul Bakker5121ce52009-01-03 21:22:43 +00001767{
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001768 int ret = 0, i, j, u, mode;
1769 unsigned int keybits;
Paul Bakker5121ce52009-01-03 21:22:43 +00001770 unsigned char key[32];
1771 unsigned char buf[64];
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001772 const unsigned char *aes_tests;
Andrzej Kurek252283f2022-09-27 07:54:16 -04001773#if defined(MBEDTLS_CIPHER_MODE_CBC) || defined(MBEDTLS_CIPHER_MODE_CFB) || \
1774 defined(MBEDTLS_CIPHER_MODE_OFB)
Paul Bakker5121ce52009-01-03 21:22:43 +00001775 unsigned char iv[16];
Jussi Kivilinna4b541be2016-06-22 18:48:16 +03001776#endif
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001777#if defined(MBEDTLS_CIPHER_MODE_CBC)
Manuel Pégourié-Gonnard92cb1d32013-09-13 16:24:20 +02001778 unsigned char prv[16];
1779#endif
Simon Butcher2ff0e522018-06-14 09:57:07 +01001780#if defined(MBEDTLS_CIPHER_MODE_CTR) || defined(MBEDTLS_CIPHER_MODE_CFB) || \
1781 defined(MBEDTLS_CIPHER_MODE_OFB)
Paul Bakker27fdf462011-06-09 13:55:13 +00001782 size_t offset;
Paul Bakkere91d01e2011-04-19 15:55:50 +00001783#endif
Simon Butcher66a89032018-06-15 18:20:29 +01001784#if defined(MBEDTLS_CIPHER_MODE_CTR) || defined(MBEDTLS_CIPHER_MODE_XTS)
Paul Bakkere91d01e2011-04-19 15:55:50 +00001785 int len;
Simon Butcher66a89032018-06-15 18:20:29 +01001786#endif
1787#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001788 unsigned char nonce_counter[16];
1789 unsigned char stream_block[16];
1790#endif
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001791 mbedtls_aes_context ctx;
Paul Bakker5121ce52009-01-03 21:22:43 +00001792
Gilles Peskine449bd832023-01-11 14:50:10 +01001793 memset(key, 0, 32);
1794 mbedtls_aes_init(&ctx);
Paul Bakker5121ce52009-01-03 21:22:43 +00001795
Gilles Peskine7e67bd52023-03-10 22:35:24 +01001796 if (verbose != 0) {
Gilles Peskine7e67bd52023-03-10 22:35:24 +01001797#if defined(MBEDTLS_AESNI_HAVE_CODE)
Dave Rodgman96a9e6a2023-06-16 20:18:36 +01001798#if MBEDTLS_AESNI_HAVE_CODE == 1
Dave Rodgman086e1372023-06-16 20:21:39 +01001799 mbedtls_printf(" AES note: AESNI code present (assembly implementation).\n");
Dave Rodgman96a9e6a2023-06-16 20:18:36 +01001800#elif MBEDTLS_AESNI_HAVE_CODE == 2
Dave Rodgman086e1372023-06-16 20:21:39 +01001801 mbedtls_printf(" AES note: AESNI code present (intrinsics implementation).\n");
Dave Rodgman96a9e6a2023-06-16 20:18:36 +01001802#else
Antonio de Angelis1ee4d122023-08-16 12:26:37 +01001803#error "Unrecognised value for MBEDTLS_AESNI_HAVE_CODE"
Dave Rodgman96a9e6a2023-06-16 20:18:36 +01001804#endif
Gilles Peskine7e67bd52023-03-10 22:35:24 +01001805 if (mbedtls_aesni_has_support(MBEDTLS_AESNI_AES)) {
1806 mbedtls_printf(" AES note: using AESNI.\n");
1807 } else
1808#endif
Jerry Yu72fd0bd2023-08-18 16:31:01 +08001809#if defined(MBEDTLS_AESCE_HAVE_CODE)
Dave Rodgmanf2249ec2023-08-04 14:27:58 +01001810 if (MBEDTLS_AESCE_HAS_SUPPORT()) {
Gilles Peskine7e67bd52023-03-10 22:35:24 +01001811 mbedtls_printf(" AES note: using AESCE.\n");
1812 } else
1813#endif
Jerry Yu29c91ba2023-08-04 11:02:04 +08001814 {
1815#if !defined(MBEDTLS_AES_USE_HARDWARE_ONLY)
1816 mbedtls_printf(" AES note: built-in implementation.\n");
1817#endif
1818 }
Gilles Peskine7e67bd52023-03-10 22:35:24 +01001819 }
1820
Paul Bakker5121ce52009-01-03 21:22:43 +00001821 /*
1822 * ECB mode
1823 */
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001824 {
1825 static const int num_tests =
Yanray Wang78ee0c92023-05-15 11:23:50 +08001826 sizeof(aes_test_ecb_enc) / sizeof(*aes_test_ecb_enc);
Paul Bakker5121ce52009-01-03 21:22:43 +00001827
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001828 for (i = 0; i < num_tests << 1; i++) {
1829 u = i >> 1;
1830 keybits = 128 + u * 64;
1831 mode = i & 1;
Gilles Peskine449bd832023-01-11 14:50:10 +01001832
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001833 if (verbose != 0) {
1834 mbedtls_printf(" AES-ECB-%3u (%s): ", keybits,
1835 (mode == MBEDTLS_AES_DECRYPT) ? "dec" : "enc");
1836 }
Yanray Wangb67b4742023-10-31 17:10:32 +08001837#if defined(MBEDTLS_BLOCK_CIPHER_NO_DECRYPT)
Yanray Wang78ee0c92023-05-15 11:23:50 +08001838 if (mode == MBEDTLS_AES_DECRYPT) {
1839 if (verbose != 0) {
1840 mbedtls_printf("skipped\n");
1841 }
1842 continue;
1843 }
1844#endif
Arto Kinnunen0f066182023-04-20 10:02:46 +08001845
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001846 memset(buf, 0, 16);
Gilles Peskine449bd832023-01-11 14:50:10 +01001847
Yanray Wangb67b4742023-10-31 17:10:32 +08001848#if !defined(MBEDTLS_BLOCK_CIPHER_NO_DECRYPT)
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001849 if (mode == MBEDTLS_AES_DECRYPT) {
1850 ret = mbedtls_aes_setkey_dec(&ctx, key, keybits);
1851 aes_tests = aes_test_ecb_dec[u];
Yanray Wang78ee0c92023-05-15 11:23:50 +08001852 } else
1853#endif
1854 {
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001855 ret = mbedtls_aes_setkey_enc(&ctx, key, keybits);
1856 aes_tests = aes_test_ecb_enc[u];
1857 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001858
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001859 if (ret == MBEDTLS_ERR_PLATFORM_FEATURE_UNSUPPORTED && keybits == 192) {
1860 mbedtls_printf("skipped\n");
1861 continue;
1862 } else if (ret != 0) {
Paul Bakkerc7ea99a2014-06-18 11:12:03 +02001863 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +01001864 }
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001865
1866 for (j = 0; j < 10000; j++) {
1867 ret = mbedtls_aes_crypt_ecb(&ctx, mode, buf, buf);
1868 if (ret != 0) {
1869 goto exit;
1870 }
1871 }
1872
1873 if (memcmp(buf, aes_tests, 16) != 0) {
1874 ret = 1;
1875 goto exit;
1876 }
1877
1878 if (verbose != 0) {
1879 mbedtls_printf("passed\n");
1880 }
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001881 }
1882
Gilles Peskine449bd832023-01-11 14:50:10 +01001883 if (verbose != 0) {
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001884 mbedtls_printf("\n");
Gilles Peskine449bd832023-01-11 14:50:10 +01001885 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001886 }
1887
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001888#if defined(MBEDTLS_CIPHER_MODE_CBC)
Paul Bakker5121ce52009-01-03 21:22:43 +00001889 /*
1890 * CBC mode
1891 */
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001892 {
1893 static const int num_tests =
1894 sizeof(aes_test_cbc_dec) / sizeof(*aes_test_cbc_dec);
Paul Bakker5121ce52009-01-03 21:22:43 +00001895
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001896 for (i = 0; i < num_tests << 1; i++) {
1897 u = i >> 1;
1898 keybits = 128 + u * 64;
1899 mode = i & 1;
Gilles Peskine449bd832023-01-11 14:50:10 +01001900
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001901 if (verbose != 0) {
1902 mbedtls_printf(" AES-CBC-%3u (%s): ", keybits,
1903 (mode == MBEDTLS_AES_DECRYPT) ? "dec" : "enc");
Paul Bakker5121ce52009-01-03 21:22:43 +00001904 }
1905
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001906 memset(iv, 0, 16);
1907 memset(prv, 0, 16);
1908 memset(buf, 0, 16);
1909
1910 if (mode == MBEDTLS_AES_DECRYPT) {
1911 ret = mbedtls_aes_setkey_dec(&ctx, key, keybits);
1912 aes_tests = aes_test_cbc_dec[u];
1913 } else {
1914 ret = mbedtls_aes_setkey_enc(&ctx, key, keybits);
1915 aes_tests = aes_test_cbc_enc[u];
1916 }
1917
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001918 if (ret == MBEDTLS_ERR_PLATFORM_FEATURE_UNSUPPORTED && keybits == 192) {
1919 mbedtls_printf("skipped\n");
1920 continue;
1921 } else if (ret != 0) {
Paul Bakkerc7ea99a2014-06-18 11:12:03 +02001922 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +01001923 }
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001924
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001925 for (j = 0; j < 10000; j++) {
1926 if (mode == MBEDTLS_AES_ENCRYPT) {
1927 unsigned char tmp[16];
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001928
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001929 memcpy(tmp, prv, 16);
1930 memcpy(prv, buf, 16);
1931 memcpy(buf, tmp, 16);
1932 }
1933
1934 ret = mbedtls_aes_crypt_cbc(&ctx, mode, 16, iv, buf, buf);
1935 if (ret != 0) {
1936 goto exit;
1937 }
1938
1939 }
1940
1941 if (memcmp(buf, aes_tests, 16) != 0) {
1942 ret = 1;
1943 goto exit;
1944 }
1945
1946 if (verbose != 0) {
1947 mbedtls_printf("passed\n");
1948 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001949 }
1950
Gilles Peskine449bd832023-01-11 14:50:10 +01001951 if (verbose != 0) {
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001952 mbedtls_printf("\n");
Gilles Peskine449bd832023-01-11 14:50:10 +01001953 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001954 }
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001955#endif /* MBEDTLS_CIPHER_MODE_CBC */
Paul Bakker5121ce52009-01-03 21:22:43 +00001956
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001957#if defined(MBEDTLS_CIPHER_MODE_CFB)
Paul Bakker5121ce52009-01-03 21:22:43 +00001958 /*
1959 * CFB128 mode
1960 */
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001961 {
1962 static const int num_tests =
1963 sizeof(aes_test_cfb128_key) / sizeof(*aes_test_cfb128_key);
Paul Bakker5121ce52009-01-03 21:22:43 +00001964
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001965 for (i = 0; i < num_tests << 1; i++) {
1966 u = i >> 1;
1967 keybits = 128 + u * 64;
1968 mode = i & 1;
Paul Bakker5121ce52009-01-03 21:22:43 +00001969
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001970 if (verbose != 0) {
1971 mbedtls_printf(" AES-CFB128-%3u (%s): ", keybits,
1972 (mode == MBEDTLS_AES_DECRYPT) ? "dec" : "enc");
1973 }
Arto Kinnunen0f066182023-04-20 10:02:46 +08001974
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001975 memcpy(iv, aes_test_cfb128_iv, 16);
1976 memcpy(key, aes_test_cfb128_key[u], keybits / 8);
Paul Bakker5121ce52009-01-03 21:22:43 +00001977
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001978 offset = 0;
1979 ret = mbedtls_aes_setkey_enc(&ctx, key, keybits);
Thomas Daubney742a2e32024-07-18 10:54:33 +01001980
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001981 if (ret == MBEDTLS_ERR_PLATFORM_FEATURE_UNSUPPORTED && keybits == 192) {
1982 mbedtls_printf("skipped\n");
1983 continue;
1984 } else if (ret != 0) {
1985 goto exit;
1986 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001987
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001988 if (mode == MBEDTLS_AES_DECRYPT) {
1989 memcpy(buf, aes_test_cfb128_ct[u], 64);
1990 aes_tests = aes_test_cfb128_pt;
1991 } else {
1992 memcpy(buf, aes_test_cfb128_pt, 64);
1993 aes_tests = aes_test_cfb128_ct[u];
1994 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001995
Yanray Wang59c2dfa2023-05-11 12:04:23 +08001996 ret = mbedtls_aes_crypt_cfb128(&ctx, mode, 64, &offset, iv, buf, buf);
1997 if (ret != 0) {
1998 goto exit;
1999 }
Paul Bakker5121ce52009-01-03 21:22:43 +00002000
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002001 if (memcmp(buf, aes_tests, 64) != 0) {
2002 ret = 1;
2003 goto exit;
2004 }
2005
2006 if (verbose != 0) {
2007 mbedtls_printf("passed\n");
2008 }
Paul Bakker5121ce52009-01-03 21:22:43 +00002009 }
2010
Gilles Peskine449bd832023-01-11 14:50:10 +01002011 if (verbose != 0) {
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002012 mbedtls_printf("\n");
Gilles Peskine449bd832023-01-11 14:50:10 +01002013 }
Paul Bakker5121ce52009-01-03 21:22:43 +00002014 }
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002015#endif /* MBEDTLS_CIPHER_MODE_CFB */
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002016
Simon Butcherad4e4932018-04-29 00:43:47 +01002017#if defined(MBEDTLS_CIPHER_MODE_OFB)
2018 /*
2019 * OFB mode
2020 */
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002021 {
2022 static const int num_tests =
2023 sizeof(aes_test_ofb_key) / sizeof(*aes_test_ofb_key);
Simon Butcherad4e4932018-04-29 00:43:47 +01002024
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002025 for (i = 0; i < num_tests << 1; i++) {
2026 u = i >> 1;
2027 keybits = 128 + u * 64;
2028 mode = i & 1;
Simon Butcherad4e4932018-04-29 00:43:47 +01002029
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002030 if (verbose != 0) {
2031 mbedtls_printf(" AES-OFB-%3u (%s): ", keybits,
2032 (mode == MBEDTLS_AES_DECRYPT) ? "dec" : "enc");
2033 }
Arto Kinnunen0f066182023-04-20 10:02:46 +08002034
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002035 memcpy(iv, aes_test_ofb_iv, 16);
2036 memcpy(key, aes_test_ofb_key[u], keybits / 8);
Simon Butcherad4e4932018-04-29 00:43:47 +01002037
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002038 offset = 0;
2039 ret = mbedtls_aes_setkey_enc(&ctx, key, keybits);
Thomas Daubney742a2e32024-07-18 10:54:33 +01002040
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002041 if (ret == MBEDTLS_ERR_PLATFORM_FEATURE_UNSUPPORTED && keybits == 192) {
2042 mbedtls_printf("skipped\n");
2043 continue;
2044 } else if (ret != 0) {
2045 goto exit;
2046 }
Simon Butcherad4e4932018-04-29 00:43:47 +01002047
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002048 if (mode == MBEDTLS_AES_DECRYPT) {
2049 memcpy(buf, aes_test_ofb_ct[u], 64);
2050 aes_tests = aes_test_ofb_pt;
2051 } else {
2052 memcpy(buf, aes_test_ofb_pt, 64);
2053 aes_tests = aes_test_ofb_ct[u];
2054 }
Simon Butcherad4e4932018-04-29 00:43:47 +01002055
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002056 ret = mbedtls_aes_crypt_ofb(&ctx, 64, &offset, iv, buf, buf);
2057 if (ret != 0) {
2058 goto exit;
2059 }
Simon Butcherad4e4932018-04-29 00:43:47 +01002060
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002061 if (memcmp(buf, aes_tests, 64) != 0) {
2062 ret = 1;
2063 goto exit;
2064 }
2065
2066 if (verbose != 0) {
2067 mbedtls_printf("passed\n");
2068 }
Simon Butcherad4e4932018-04-29 00:43:47 +01002069 }
2070
Gilles Peskine449bd832023-01-11 14:50:10 +01002071 if (verbose != 0) {
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002072 mbedtls_printf("\n");
Gilles Peskine449bd832023-01-11 14:50:10 +01002073 }
Simon Butcherad4e4932018-04-29 00:43:47 +01002074 }
Simon Butcherad4e4932018-04-29 00:43:47 +01002075#endif /* MBEDTLS_CIPHER_MODE_OFB */
2076
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002077#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002078 /*
2079 * CTR mode
2080 */
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002081 {
2082 static const int num_tests =
2083 sizeof(aes_test_ctr_key) / sizeof(*aes_test_ctr_key);
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002084
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002085 for (i = 0; i < num_tests << 1; i++) {
2086 u = i >> 1;
2087 mode = i & 1;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002088
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002089 if (verbose != 0) {
2090 mbedtls_printf(" AES-CTR-128 (%s): ",
2091 (mode == MBEDTLS_AES_DECRYPT) ? "dec" : "enc");
2092 }
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002093
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002094 memcpy(nonce_counter, aes_test_ctr_nonce_counter[u], 16);
2095 memcpy(key, aes_test_ctr_key[u], 16);
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002096
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002097 offset = 0;
2098 if ((ret = mbedtls_aes_setkey_enc(&ctx, key, 128)) != 0) {
2099 goto exit;
2100 }
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01002101
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002102 len = aes_test_ctr_len[u];
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002103
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002104 if (mode == MBEDTLS_AES_DECRYPT) {
2105 memcpy(buf, aes_test_ctr_ct[u], len);
2106 aes_tests = aes_test_ctr_pt[u];
2107 } else {
2108 memcpy(buf, aes_test_ctr_pt[u], len);
2109 aes_tests = aes_test_ctr_ct[u];
2110 }
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002111
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002112 ret = mbedtls_aes_crypt_ctr(&ctx, len, &offset, nonce_counter,
2113 stream_block, buf, buf);
2114 if (ret != 0) {
2115 goto exit;
2116 }
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002117
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002118 if (memcmp(buf, aes_tests, len) != 0) {
2119 ret = 1;
2120 goto exit;
2121 }
2122
2123 if (verbose != 0) {
2124 mbedtls_printf("passed\n");
2125 }
Gilles Peskine449bd832023-01-11 14:50:10 +01002126 }
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002127 }
Paul Bakker5121ce52009-01-03 21:22:43 +00002128
Gilles Peskine449bd832023-01-11 14:50:10 +01002129 if (verbose != 0) {
2130 mbedtls_printf("\n");
2131 }
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002132#endif /* MBEDTLS_CIPHER_MODE_CTR */
Paul Bakker5121ce52009-01-03 21:22:43 +00002133
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002134#if defined(MBEDTLS_CIPHER_MODE_XTS)
Yanray Wang59c2dfa2023-05-11 12:04:23 +08002135 /*
2136 * XTS mode
2137 */
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002138 {
Gilles Peskine449bd832023-01-11 14:50:10 +01002139 static const int num_tests =
2140 sizeof(aes_test_xts_key) / sizeof(*aes_test_xts_key);
2141 mbedtls_aes_xts_context ctx_xts;
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002142
Gilles Peskine449bd832023-01-11 14:50:10 +01002143 mbedtls_aes_xts_init(&ctx_xts);
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002144
Gilles Peskine449bd832023-01-11 14:50:10 +01002145 for (i = 0; i < num_tests << 1; i++) {
2146 const unsigned char *data_unit;
2147 u = i >> 1;
2148 mode = i & 1;
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002149
Gilles Peskine449bd832023-01-11 14:50:10 +01002150 if (verbose != 0) {
2151 mbedtls_printf(" AES-XTS-128 (%s): ",
2152 (mode == MBEDTLS_AES_DECRYPT) ? "dec" : "enc");
2153 }
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002154
Gilles Peskine449bd832023-01-11 14:50:10 +01002155 memset(key, 0, sizeof(key));
2156 memcpy(key, aes_test_xts_key[u], 32);
2157 data_unit = aes_test_xts_data_unit[u];
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002158
Gilles Peskine449bd832023-01-11 14:50:10 +01002159 len = sizeof(*aes_test_xts_ct32);
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002160
Gilles Peskine449bd832023-01-11 14:50:10 +01002161 if (mode == MBEDTLS_AES_DECRYPT) {
2162 ret = mbedtls_aes_xts_setkey_dec(&ctx_xts, key, 256);
2163 if (ret != 0) {
2164 goto exit;
2165 }
2166 memcpy(buf, aes_test_xts_ct32[u], len);
2167 aes_tests = aes_test_xts_pt32[u];
2168 } else {
2169 ret = mbedtls_aes_xts_setkey_enc(&ctx_xts, key, 256);
2170 if (ret != 0) {
2171 goto exit;
2172 }
2173 memcpy(buf, aes_test_xts_pt32[u], len);
2174 aes_tests = aes_test_xts_ct32[u];
2175 }
2176
2177
2178 ret = mbedtls_aes_crypt_xts(&ctx_xts, mode, len, data_unit,
2179 buf, buf);
2180 if (ret != 0) {
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002181 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +01002182 }
2183
2184 if (memcmp(buf, aes_tests, len) != 0) {
2185 ret = 1;
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002186 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +01002187 }
2188
2189 if (verbose != 0) {
2190 mbedtls_printf("passed\n");
2191 }
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002192 }
2193
Gilles Peskine449bd832023-01-11 14:50:10 +01002194 if (verbose != 0) {
2195 mbedtls_printf("\n");
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002196 }
2197
Gilles Peskine449bd832023-01-11 14:50:10 +01002198 mbedtls_aes_xts_free(&ctx_xts);
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002199 }
2200#endif /* MBEDTLS_CIPHER_MODE_XTS */
2201
Paul Bakkerc7ea99a2014-06-18 11:12:03 +02002202 ret = 0;
2203
2204exit:
Gilles Peskine449bd832023-01-11 14:50:10 +01002205 if (ret != 0 && verbose != 0) {
2206 mbedtls_printf("failed\n");
2207 }
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01002208
Gilles Peskine449bd832023-01-11 14:50:10 +01002209 mbedtls_aes_free(&ctx);
Paul Bakkerc7ea99a2014-06-18 11:12:03 +02002210
Gilles Peskine449bd832023-01-11 14:50:10 +01002211 return ret;
Paul Bakker5121ce52009-01-03 21:22:43 +00002212}
2213
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002214#endif /* MBEDTLS_SELF_TEST */
Paul Bakker5121ce52009-01-03 21:22:43 +00002215
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002216#endif /* MBEDTLS_AES_C */