blob: 1d3cef6faae6fc25e93d5809e33c6fe5aaa57068 [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
Manuel Pégourié-Gonnard37ff1402015-09-04 14:21:07 +02005 * SPDX-License-Identifier: Apache-2.0
6 *
7 * Licensed under the Apache License, Version 2.0 (the "License"); you may
8 * not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
15 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
Paul Bakker5121ce52009-01-03 21:22:43 +000018 */
19/*
20 * The AES block cipher was designed by Vincent Rijmen and Joan Daemen.
21 *
22 * http://csrc.nist.gov/encryption/aes/rijndael/Rijndael.pdf
23 * http://csrc.nist.gov/publications/fips/fips197/fips-197.pdf
24 */
25
Gilles Peskinedb09ef62020-06-03 01:43:33 +020026#include "common.h"
Paul Bakker5121ce52009-01-03 21:22:43 +000027
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020028#if defined(MBEDTLS_AES_C)
Paul Bakker5121ce52009-01-03 21:22:43 +000029
Rich Evans00ab4702015-02-06 13:43:58 +000030#include <string.h>
31
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000032#include "mbedtls/aes.h"
Ron Eldor9924bdc2018-10-04 10:59:13 +030033#include "mbedtls/platform.h"
Andres Amaya Garcia1f6301b2018-04-17 09:51:09 -050034#include "mbedtls/platform_util.h"
Janos Follath24eed8d2019-11-22 13:21:35 +000035#include "mbedtls/error.h"
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020036#if defined(MBEDTLS_PADLOCK_C)
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000037#include "mbedtls/padlock.h"
Paul Bakker67820bd2012-06-04 12:47:23 +000038#endif
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020039#if defined(MBEDTLS_AESNI_C)
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000040#include "mbedtls/aesni.h"
Manuel Pégourié-Gonnard5b685652013-12-18 11:45:21 +010041#endif
Paul Bakker5121ce52009-01-03 21:22:43 +000042
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020043#if defined(MBEDTLS_SELF_TEST)
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000044#include "mbedtls/platform.h"
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020045#endif /* MBEDTLS_SELF_TEST */
Paul Bakker7dc4c442014-02-01 22:50:26 +010046
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020047#if !defined(MBEDTLS_AES_ALT)
Paul Bakker90995b52013-06-24 19:20:35 +020048
Manuel Pégourié-Gonnard0e9cddb2018-12-10 16:37:51 +010049/* Parameter validation macros based on platform_util.h */
50#define AES_VALIDATE_RET( cond ) \
Manuel Pégourié-Gonnard44c5d582018-12-10 16:56:14 +010051 MBEDTLS_INTERNAL_VALIDATE_RET( cond, MBEDTLS_ERR_AES_BAD_INPUT_DATA )
Manuel Pégourié-Gonnard0e9cddb2018-12-10 16:37:51 +010052#define AES_VALIDATE( cond ) \
53 MBEDTLS_INTERNAL_VALIDATE( cond )
54
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020055#if defined(MBEDTLS_PADLOCK_C) && \
56 ( defined(MBEDTLS_HAVE_X86) || defined(MBEDTLS_PADLOCK_ALIGN16) )
Paul Bakker048d04e2012-02-12 17:31:04 +000057static int aes_padlock_ace = -1;
58#endif
59
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020060#if defined(MBEDTLS_AES_ROM_TABLES)
Paul Bakker5121ce52009-01-03 21:22:43 +000061/*
62 * Forward S-box
63 */
64static const unsigned char FSb[256] =
65{
66 0x63, 0x7C, 0x77, 0x7B, 0xF2, 0x6B, 0x6F, 0xC5,
67 0x30, 0x01, 0x67, 0x2B, 0xFE, 0xD7, 0xAB, 0x76,
68 0xCA, 0x82, 0xC9, 0x7D, 0xFA, 0x59, 0x47, 0xF0,
69 0xAD, 0xD4, 0xA2, 0xAF, 0x9C, 0xA4, 0x72, 0xC0,
70 0xB7, 0xFD, 0x93, 0x26, 0x36, 0x3F, 0xF7, 0xCC,
71 0x34, 0xA5, 0xE5, 0xF1, 0x71, 0xD8, 0x31, 0x15,
72 0x04, 0xC7, 0x23, 0xC3, 0x18, 0x96, 0x05, 0x9A,
73 0x07, 0x12, 0x80, 0xE2, 0xEB, 0x27, 0xB2, 0x75,
74 0x09, 0x83, 0x2C, 0x1A, 0x1B, 0x6E, 0x5A, 0xA0,
75 0x52, 0x3B, 0xD6, 0xB3, 0x29, 0xE3, 0x2F, 0x84,
76 0x53, 0xD1, 0x00, 0xED, 0x20, 0xFC, 0xB1, 0x5B,
77 0x6A, 0xCB, 0xBE, 0x39, 0x4A, 0x4C, 0x58, 0xCF,
78 0xD0, 0xEF, 0xAA, 0xFB, 0x43, 0x4D, 0x33, 0x85,
79 0x45, 0xF9, 0x02, 0x7F, 0x50, 0x3C, 0x9F, 0xA8,
80 0x51, 0xA3, 0x40, 0x8F, 0x92, 0x9D, 0x38, 0xF5,
81 0xBC, 0xB6, 0xDA, 0x21, 0x10, 0xFF, 0xF3, 0xD2,
82 0xCD, 0x0C, 0x13, 0xEC, 0x5F, 0x97, 0x44, 0x17,
83 0xC4, 0xA7, 0x7E, 0x3D, 0x64, 0x5D, 0x19, 0x73,
84 0x60, 0x81, 0x4F, 0xDC, 0x22, 0x2A, 0x90, 0x88,
85 0x46, 0xEE, 0xB8, 0x14, 0xDE, 0x5E, 0x0B, 0xDB,
86 0xE0, 0x32, 0x3A, 0x0A, 0x49, 0x06, 0x24, 0x5C,
87 0xC2, 0xD3, 0xAC, 0x62, 0x91, 0x95, 0xE4, 0x79,
88 0xE7, 0xC8, 0x37, 0x6D, 0x8D, 0xD5, 0x4E, 0xA9,
89 0x6C, 0x56, 0xF4, 0xEA, 0x65, 0x7A, 0xAE, 0x08,
90 0xBA, 0x78, 0x25, 0x2E, 0x1C, 0xA6, 0xB4, 0xC6,
91 0xE8, 0xDD, 0x74, 0x1F, 0x4B, 0xBD, 0x8B, 0x8A,
92 0x70, 0x3E, 0xB5, 0x66, 0x48, 0x03, 0xF6, 0x0E,
93 0x61, 0x35, 0x57, 0xB9, 0x86, 0xC1, 0x1D, 0x9E,
94 0xE1, 0xF8, 0x98, 0x11, 0x69, 0xD9, 0x8E, 0x94,
95 0x9B, 0x1E, 0x87, 0xE9, 0xCE, 0x55, 0x28, 0xDF,
96 0x8C, 0xA1, 0x89, 0x0D, 0xBF, 0xE6, 0x42, 0x68,
97 0x41, 0x99, 0x2D, 0x0F, 0xB0, 0x54, 0xBB, 0x16
98};
99
100/*
101 * Forward tables
102 */
103#define FT \
104\
105 V(A5,63,63,C6), V(84,7C,7C,F8), V(99,77,77,EE), V(8D,7B,7B,F6), \
106 V(0D,F2,F2,FF), V(BD,6B,6B,D6), V(B1,6F,6F,DE), V(54,C5,C5,91), \
107 V(50,30,30,60), V(03,01,01,02), V(A9,67,67,CE), V(7D,2B,2B,56), \
108 V(19,FE,FE,E7), V(62,D7,D7,B5), V(E6,AB,AB,4D), V(9A,76,76,EC), \
109 V(45,CA,CA,8F), V(9D,82,82,1F), V(40,C9,C9,89), V(87,7D,7D,FA), \
110 V(15,FA,FA,EF), V(EB,59,59,B2), V(C9,47,47,8E), V(0B,F0,F0,FB), \
111 V(EC,AD,AD,41), V(67,D4,D4,B3), V(FD,A2,A2,5F), V(EA,AF,AF,45), \
112 V(BF,9C,9C,23), V(F7,A4,A4,53), V(96,72,72,E4), V(5B,C0,C0,9B), \
113 V(C2,B7,B7,75), V(1C,FD,FD,E1), V(AE,93,93,3D), V(6A,26,26,4C), \
114 V(5A,36,36,6C), V(41,3F,3F,7E), V(02,F7,F7,F5), V(4F,CC,CC,83), \
115 V(5C,34,34,68), V(F4,A5,A5,51), V(34,E5,E5,D1), V(08,F1,F1,F9), \
116 V(93,71,71,E2), V(73,D8,D8,AB), V(53,31,31,62), V(3F,15,15,2A), \
117 V(0C,04,04,08), V(52,C7,C7,95), V(65,23,23,46), V(5E,C3,C3,9D), \
118 V(28,18,18,30), V(A1,96,96,37), V(0F,05,05,0A), V(B5,9A,9A,2F), \
119 V(09,07,07,0E), V(36,12,12,24), V(9B,80,80,1B), V(3D,E2,E2,DF), \
120 V(26,EB,EB,CD), V(69,27,27,4E), V(CD,B2,B2,7F), V(9F,75,75,EA), \
121 V(1B,09,09,12), V(9E,83,83,1D), V(74,2C,2C,58), V(2E,1A,1A,34), \
122 V(2D,1B,1B,36), V(B2,6E,6E,DC), V(EE,5A,5A,B4), V(FB,A0,A0,5B), \
123 V(F6,52,52,A4), V(4D,3B,3B,76), V(61,D6,D6,B7), V(CE,B3,B3,7D), \
124 V(7B,29,29,52), V(3E,E3,E3,DD), V(71,2F,2F,5E), V(97,84,84,13), \
125 V(F5,53,53,A6), V(68,D1,D1,B9), V(00,00,00,00), V(2C,ED,ED,C1), \
126 V(60,20,20,40), V(1F,FC,FC,E3), V(C8,B1,B1,79), V(ED,5B,5B,B6), \
127 V(BE,6A,6A,D4), V(46,CB,CB,8D), V(D9,BE,BE,67), V(4B,39,39,72), \
128 V(DE,4A,4A,94), V(D4,4C,4C,98), V(E8,58,58,B0), V(4A,CF,CF,85), \
129 V(6B,D0,D0,BB), V(2A,EF,EF,C5), V(E5,AA,AA,4F), V(16,FB,FB,ED), \
130 V(C5,43,43,86), V(D7,4D,4D,9A), V(55,33,33,66), V(94,85,85,11), \
131 V(CF,45,45,8A), V(10,F9,F9,E9), V(06,02,02,04), V(81,7F,7F,FE), \
132 V(F0,50,50,A0), V(44,3C,3C,78), V(BA,9F,9F,25), V(E3,A8,A8,4B), \
133 V(F3,51,51,A2), V(FE,A3,A3,5D), V(C0,40,40,80), V(8A,8F,8F,05), \
134 V(AD,92,92,3F), V(BC,9D,9D,21), V(48,38,38,70), V(04,F5,F5,F1), \
135 V(DF,BC,BC,63), V(C1,B6,B6,77), V(75,DA,DA,AF), V(63,21,21,42), \
136 V(30,10,10,20), V(1A,FF,FF,E5), V(0E,F3,F3,FD), V(6D,D2,D2,BF), \
137 V(4C,CD,CD,81), V(14,0C,0C,18), V(35,13,13,26), V(2F,EC,EC,C3), \
138 V(E1,5F,5F,BE), V(A2,97,97,35), V(CC,44,44,88), V(39,17,17,2E), \
139 V(57,C4,C4,93), V(F2,A7,A7,55), V(82,7E,7E,FC), V(47,3D,3D,7A), \
140 V(AC,64,64,C8), V(E7,5D,5D,BA), V(2B,19,19,32), V(95,73,73,E6), \
141 V(A0,60,60,C0), V(98,81,81,19), V(D1,4F,4F,9E), V(7F,DC,DC,A3), \
142 V(66,22,22,44), V(7E,2A,2A,54), V(AB,90,90,3B), V(83,88,88,0B), \
143 V(CA,46,46,8C), V(29,EE,EE,C7), V(D3,B8,B8,6B), V(3C,14,14,28), \
144 V(79,DE,DE,A7), V(E2,5E,5E,BC), V(1D,0B,0B,16), V(76,DB,DB,AD), \
145 V(3B,E0,E0,DB), V(56,32,32,64), V(4E,3A,3A,74), V(1E,0A,0A,14), \
146 V(DB,49,49,92), V(0A,06,06,0C), V(6C,24,24,48), V(E4,5C,5C,B8), \
147 V(5D,C2,C2,9F), V(6E,D3,D3,BD), V(EF,AC,AC,43), V(A6,62,62,C4), \
148 V(A8,91,91,39), V(A4,95,95,31), V(37,E4,E4,D3), V(8B,79,79,F2), \
149 V(32,E7,E7,D5), V(43,C8,C8,8B), V(59,37,37,6E), V(B7,6D,6D,DA), \
150 V(8C,8D,8D,01), V(64,D5,D5,B1), V(D2,4E,4E,9C), V(E0,A9,A9,49), \
151 V(B4,6C,6C,D8), V(FA,56,56,AC), V(07,F4,F4,F3), V(25,EA,EA,CF), \
152 V(AF,65,65,CA), V(8E,7A,7A,F4), V(E9,AE,AE,47), V(18,08,08,10), \
153 V(D5,BA,BA,6F), V(88,78,78,F0), V(6F,25,25,4A), V(72,2E,2E,5C), \
154 V(24,1C,1C,38), V(F1,A6,A6,57), V(C7,B4,B4,73), V(51,C6,C6,97), \
155 V(23,E8,E8,CB), V(7C,DD,DD,A1), V(9C,74,74,E8), V(21,1F,1F,3E), \
156 V(DD,4B,4B,96), V(DC,BD,BD,61), V(86,8B,8B,0D), V(85,8A,8A,0F), \
157 V(90,70,70,E0), V(42,3E,3E,7C), V(C4,B5,B5,71), V(AA,66,66,CC), \
158 V(D8,48,48,90), V(05,03,03,06), V(01,F6,F6,F7), V(12,0E,0E,1C), \
159 V(A3,61,61,C2), V(5F,35,35,6A), V(F9,57,57,AE), V(D0,B9,B9,69), \
160 V(91,86,86,17), V(58,C1,C1,99), V(27,1D,1D,3A), V(B9,9E,9E,27), \
161 V(38,E1,E1,D9), V(13,F8,F8,EB), V(B3,98,98,2B), V(33,11,11,22), \
162 V(BB,69,69,D2), V(70,D9,D9,A9), V(89,8E,8E,07), V(A7,94,94,33), \
163 V(B6,9B,9B,2D), V(22,1E,1E,3C), V(92,87,87,15), V(20,E9,E9,C9), \
164 V(49,CE,CE,87), V(FF,55,55,AA), V(78,28,28,50), V(7A,DF,DF,A5), \
165 V(8F,8C,8C,03), V(F8,A1,A1,59), V(80,89,89,09), V(17,0D,0D,1A), \
166 V(DA,BF,BF,65), V(31,E6,E6,D7), V(C6,42,42,84), V(B8,68,68,D0), \
167 V(C3,41,41,82), V(B0,99,99,29), V(77,2D,2D,5A), V(11,0F,0F,1E), \
168 V(CB,B0,B0,7B), V(FC,54,54,A8), V(D6,BB,BB,6D), V(3A,16,16,2C)
169
170#define V(a,b,c,d) 0x##a##b##c##d
Paul Bakker5c2364c2012-10-01 14:41:15 +0000171static const uint32_t FT0[256] = { FT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000172#undef V
173
Hanno Beckerad049a92017-06-19 16:31:54 +0100174#if !defined(MBEDTLS_AES_FEWER_TABLES)
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200175
Paul Bakker5121ce52009-01-03 21:22:43 +0000176#define V(a,b,c,d) 0x##b##c##d##a
Paul Bakker5c2364c2012-10-01 14:41:15 +0000177static const uint32_t FT1[256] = { FT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000178#undef V
179
180#define V(a,b,c,d) 0x##c##d##a##b
Paul Bakker5c2364c2012-10-01 14:41:15 +0000181static const uint32_t FT2[256] = { FT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000182#undef V
183
184#define V(a,b,c,d) 0x##d##a##b##c
Paul Bakker5c2364c2012-10-01 14:41:15 +0000185static const uint32_t FT3[256] = { FT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000186#undef V
187
Hanno Becker177d3cf2017-06-07 15:52:48 +0100188#endif /* !MBEDTLS_AES_FEWER_TABLES */
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200189
Paul Bakker5121ce52009-01-03 21:22:43 +0000190#undef FT
191
192/*
193 * Reverse S-box
194 */
195static const unsigned char RSb[256] =
196{
197 0x52, 0x09, 0x6A, 0xD5, 0x30, 0x36, 0xA5, 0x38,
198 0xBF, 0x40, 0xA3, 0x9E, 0x81, 0xF3, 0xD7, 0xFB,
199 0x7C, 0xE3, 0x39, 0x82, 0x9B, 0x2F, 0xFF, 0x87,
200 0x34, 0x8E, 0x43, 0x44, 0xC4, 0xDE, 0xE9, 0xCB,
201 0x54, 0x7B, 0x94, 0x32, 0xA6, 0xC2, 0x23, 0x3D,
202 0xEE, 0x4C, 0x95, 0x0B, 0x42, 0xFA, 0xC3, 0x4E,
203 0x08, 0x2E, 0xA1, 0x66, 0x28, 0xD9, 0x24, 0xB2,
204 0x76, 0x5B, 0xA2, 0x49, 0x6D, 0x8B, 0xD1, 0x25,
205 0x72, 0xF8, 0xF6, 0x64, 0x86, 0x68, 0x98, 0x16,
206 0xD4, 0xA4, 0x5C, 0xCC, 0x5D, 0x65, 0xB6, 0x92,
207 0x6C, 0x70, 0x48, 0x50, 0xFD, 0xED, 0xB9, 0xDA,
208 0x5E, 0x15, 0x46, 0x57, 0xA7, 0x8D, 0x9D, 0x84,
209 0x90, 0xD8, 0xAB, 0x00, 0x8C, 0xBC, 0xD3, 0x0A,
210 0xF7, 0xE4, 0x58, 0x05, 0xB8, 0xB3, 0x45, 0x06,
211 0xD0, 0x2C, 0x1E, 0x8F, 0xCA, 0x3F, 0x0F, 0x02,
212 0xC1, 0xAF, 0xBD, 0x03, 0x01, 0x13, 0x8A, 0x6B,
213 0x3A, 0x91, 0x11, 0x41, 0x4F, 0x67, 0xDC, 0xEA,
214 0x97, 0xF2, 0xCF, 0xCE, 0xF0, 0xB4, 0xE6, 0x73,
215 0x96, 0xAC, 0x74, 0x22, 0xE7, 0xAD, 0x35, 0x85,
216 0xE2, 0xF9, 0x37, 0xE8, 0x1C, 0x75, 0xDF, 0x6E,
217 0x47, 0xF1, 0x1A, 0x71, 0x1D, 0x29, 0xC5, 0x89,
218 0x6F, 0xB7, 0x62, 0x0E, 0xAA, 0x18, 0xBE, 0x1B,
219 0xFC, 0x56, 0x3E, 0x4B, 0xC6, 0xD2, 0x79, 0x20,
220 0x9A, 0xDB, 0xC0, 0xFE, 0x78, 0xCD, 0x5A, 0xF4,
221 0x1F, 0xDD, 0xA8, 0x33, 0x88, 0x07, 0xC7, 0x31,
222 0xB1, 0x12, 0x10, 0x59, 0x27, 0x80, 0xEC, 0x5F,
223 0x60, 0x51, 0x7F, 0xA9, 0x19, 0xB5, 0x4A, 0x0D,
224 0x2D, 0xE5, 0x7A, 0x9F, 0x93, 0xC9, 0x9C, 0xEF,
225 0xA0, 0xE0, 0x3B, 0x4D, 0xAE, 0x2A, 0xF5, 0xB0,
226 0xC8, 0xEB, 0xBB, 0x3C, 0x83, 0x53, 0x99, 0x61,
227 0x17, 0x2B, 0x04, 0x7E, 0xBA, 0x77, 0xD6, 0x26,
228 0xE1, 0x69, 0x14, 0x63, 0x55, 0x21, 0x0C, 0x7D
229};
230
231/*
232 * Reverse tables
233 */
234#define RT \
235\
236 V(50,A7,F4,51), V(53,65,41,7E), V(C3,A4,17,1A), V(96,5E,27,3A), \
237 V(CB,6B,AB,3B), V(F1,45,9D,1F), V(AB,58,FA,AC), V(93,03,E3,4B), \
238 V(55,FA,30,20), V(F6,6D,76,AD), V(91,76,CC,88), V(25,4C,02,F5), \
239 V(FC,D7,E5,4F), V(D7,CB,2A,C5), V(80,44,35,26), V(8F,A3,62,B5), \
240 V(49,5A,B1,DE), V(67,1B,BA,25), V(98,0E,EA,45), V(E1,C0,FE,5D), \
241 V(02,75,2F,C3), V(12,F0,4C,81), V(A3,97,46,8D), V(C6,F9,D3,6B), \
242 V(E7,5F,8F,03), V(95,9C,92,15), V(EB,7A,6D,BF), V(DA,59,52,95), \
243 V(2D,83,BE,D4), V(D3,21,74,58), V(29,69,E0,49), V(44,C8,C9,8E), \
244 V(6A,89,C2,75), V(78,79,8E,F4), V(6B,3E,58,99), V(DD,71,B9,27), \
245 V(B6,4F,E1,BE), V(17,AD,88,F0), V(66,AC,20,C9), V(B4,3A,CE,7D), \
246 V(18,4A,DF,63), V(82,31,1A,E5), V(60,33,51,97), V(45,7F,53,62), \
247 V(E0,77,64,B1), V(84,AE,6B,BB), V(1C,A0,81,FE), V(94,2B,08,F9), \
248 V(58,68,48,70), V(19,FD,45,8F), V(87,6C,DE,94), V(B7,F8,7B,52), \
249 V(23,D3,73,AB), V(E2,02,4B,72), V(57,8F,1F,E3), V(2A,AB,55,66), \
250 V(07,28,EB,B2), V(03,C2,B5,2F), V(9A,7B,C5,86), V(A5,08,37,D3), \
251 V(F2,87,28,30), V(B2,A5,BF,23), V(BA,6A,03,02), V(5C,82,16,ED), \
252 V(2B,1C,CF,8A), V(92,B4,79,A7), V(F0,F2,07,F3), V(A1,E2,69,4E), \
253 V(CD,F4,DA,65), V(D5,BE,05,06), V(1F,62,34,D1), V(8A,FE,A6,C4), \
254 V(9D,53,2E,34), V(A0,55,F3,A2), V(32,E1,8A,05), V(75,EB,F6,A4), \
255 V(39,EC,83,0B), V(AA,EF,60,40), V(06,9F,71,5E), V(51,10,6E,BD), \
256 V(F9,8A,21,3E), V(3D,06,DD,96), V(AE,05,3E,DD), V(46,BD,E6,4D), \
257 V(B5,8D,54,91), V(05,5D,C4,71), V(6F,D4,06,04), V(FF,15,50,60), \
258 V(24,FB,98,19), V(97,E9,BD,D6), V(CC,43,40,89), V(77,9E,D9,67), \
259 V(BD,42,E8,B0), V(88,8B,89,07), V(38,5B,19,E7), V(DB,EE,C8,79), \
260 V(47,0A,7C,A1), V(E9,0F,42,7C), V(C9,1E,84,F8), V(00,00,00,00), \
261 V(83,86,80,09), V(48,ED,2B,32), V(AC,70,11,1E), V(4E,72,5A,6C), \
262 V(FB,FF,0E,FD), V(56,38,85,0F), V(1E,D5,AE,3D), V(27,39,2D,36), \
263 V(64,D9,0F,0A), V(21,A6,5C,68), V(D1,54,5B,9B), V(3A,2E,36,24), \
264 V(B1,67,0A,0C), V(0F,E7,57,93), V(D2,96,EE,B4), V(9E,91,9B,1B), \
265 V(4F,C5,C0,80), V(A2,20,DC,61), V(69,4B,77,5A), V(16,1A,12,1C), \
266 V(0A,BA,93,E2), V(E5,2A,A0,C0), V(43,E0,22,3C), V(1D,17,1B,12), \
267 V(0B,0D,09,0E), V(AD,C7,8B,F2), V(B9,A8,B6,2D), V(C8,A9,1E,14), \
268 V(85,19,F1,57), V(4C,07,75,AF), V(BB,DD,99,EE), V(FD,60,7F,A3), \
269 V(9F,26,01,F7), V(BC,F5,72,5C), V(C5,3B,66,44), V(34,7E,FB,5B), \
270 V(76,29,43,8B), V(DC,C6,23,CB), V(68,FC,ED,B6), V(63,F1,E4,B8), \
271 V(CA,DC,31,D7), V(10,85,63,42), V(40,22,97,13), V(20,11,C6,84), \
272 V(7D,24,4A,85), V(F8,3D,BB,D2), V(11,32,F9,AE), V(6D,A1,29,C7), \
273 V(4B,2F,9E,1D), V(F3,30,B2,DC), V(EC,52,86,0D), V(D0,E3,C1,77), \
274 V(6C,16,B3,2B), V(99,B9,70,A9), V(FA,48,94,11), V(22,64,E9,47), \
275 V(C4,8C,FC,A8), V(1A,3F,F0,A0), V(D8,2C,7D,56), V(EF,90,33,22), \
276 V(C7,4E,49,87), V(C1,D1,38,D9), V(FE,A2,CA,8C), V(36,0B,D4,98), \
277 V(CF,81,F5,A6), V(28,DE,7A,A5), V(26,8E,B7,DA), V(A4,BF,AD,3F), \
278 V(E4,9D,3A,2C), V(0D,92,78,50), V(9B,CC,5F,6A), V(62,46,7E,54), \
279 V(C2,13,8D,F6), V(E8,B8,D8,90), V(5E,F7,39,2E), V(F5,AF,C3,82), \
280 V(BE,80,5D,9F), V(7C,93,D0,69), V(A9,2D,D5,6F), V(B3,12,25,CF), \
281 V(3B,99,AC,C8), V(A7,7D,18,10), V(6E,63,9C,E8), V(7B,BB,3B,DB), \
282 V(09,78,26,CD), V(F4,18,59,6E), V(01,B7,9A,EC), V(A8,9A,4F,83), \
283 V(65,6E,95,E6), V(7E,E6,FF,AA), V(08,CF,BC,21), V(E6,E8,15,EF), \
284 V(D9,9B,E7,BA), V(CE,36,6F,4A), V(D4,09,9F,EA), V(D6,7C,B0,29), \
285 V(AF,B2,A4,31), V(31,23,3F,2A), V(30,94,A5,C6), V(C0,66,A2,35), \
286 V(37,BC,4E,74), V(A6,CA,82,FC), V(B0,D0,90,E0), V(15,D8,A7,33), \
287 V(4A,98,04,F1), V(F7,DA,EC,41), V(0E,50,CD,7F), V(2F,F6,91,17), \
288 V(8D,D6,4D,76), V(4D,B0,EF,43), V(54,4D,AA,CC), V(DF,04,96,E4), \
289 V(E3,B5,D1,9E), V(1B,88,6A,4C), V(B8,1F,2C,C1), V(7F,51,65,46), \
290 V(04,EA,5E,9D), V(5D,35,8C,01), V(73,74,87,FA), V(2E,41,0B,FB), \
291 V(5A,1D,67,B3), V(52,D2,DB,92), V(33,56,10,E9), V(13,47,D6,6D), \
292 V(8C,61,D7,9A), V(7A,0C,A1,37), V(8E,14,F8,59), V(89,3C,13,EB), \
293 V(EE,27,A9,CE), V(35,C9,61,B7), V(ED,E5,1C,E1), V(3C,B1,47,7A), \
294 V(59,DF,D2,9C), V(3F,73,F2,55), V(79,CE,14,18), V(BF,37,C7,73), \
295 V(EA,CD,F7,53), V(5B,AA,FD,5F), V(14,6F,3D,DF), V(86,DB,44,78), \
296 V(81,F3,AF,CA), V(3E,C4,68,B9), V(2C,34,24,38), V(5F,40,A3,C2), \
297 V(72,C3,1D,16), V(0C,25,E2,BC), V(8B,49,3C,28), V(41,95,0D,FF), \
298 V(71,01,A8,39), V(DE,B3,0C,08), V(9C,E4,B4,D8), V(90,C1,56,64), \
299 V(61,84,CB,7B), V(70,B6,32,D5), V(74,5C,6C,48), V(42,57,B8,D0)
300
301#define V(a,b,c,d) 0x##a##b##c##d
Paul Bakker5c2364c2012-10-01 14:41:15 +0000302static const uint32_t RT0[256] = { RT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000303#undef V
304
Hanno Beckerad049a92017-06-19 16:31:54 +0100305#if !defined(MBEDTLS_AES_FEWER_TABLES)
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200306
Paul Bakker5121ce52009-01-03 21:22:43 +0000307#define V(a,b,c,d) 0x##b##c##d##a
Paul Bakker5c2364c2012-10-01 14:41:15 +0000308static const uint32_t RT1[256] = { RT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000309#undef V
310
311#define V(a,b,c,d) 0x##c##d##a##b
Paul Bakker5c2364c2012-10-01 14:41:15 +0000312static const uint32_t RT2[256] = { RT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000313#undef V
314
315#define V(a,b,c,d) 0x##d##a##b##c
Paul Bakker5c2364c2012-10-01 14:41:15 +0000316static const uint32_t RT3[256] = { RT };
Paul Bakker5121ce52009-01-03 21:22:43 +0000317#undef V
318
Hanno Becker177d3cf2017-06-07 15:52:48 +0100319#endif /* !MBEDTLS_AES_FEWER_TABLES */
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200320
Paul Bakker5121ce52009-01-03 21:22:43 +0000321#undef RT
322
323/*
324 * Round constants
325 */
Paul Bakker5c2364c2012-10-01 14:41:15 +0000326static const uint32_t RCON[10] =
Paul Bakker5121ce52009-01-03 21:22:43 +0000327{
328 0x00000001, 0x00000002, 0x00000004, 0x00000008,
329 0x00000010, 0x00000020, 0x00000040, 0x00000080,
330 0x0000001B, 0x00000036
331};
332
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200333#else /* MBEDTLS_AES_ROM_TABLES */
Paul Bakker5121ce52009-01-03 21:22:43 +0000334
335/*
336 * Forward S-box & tables
337 */
338static unsigned char FSb[256];
Paul Bakker9af723c2014-05-01 13:03:14 +0200339static uint32_t FT0[256];
Hanno Beckerad049a92017-06-19 16:31:54 +0100340#if !defined(MBEDTLS_AES_FEWER_TABLES)
Paul Bakker9af723c2014-05-01 13:03:14 +0200341static uint32_t FT1[256];
342static uint32_t FT2[256];
343static uint32_t FT3[256];
Hanno Becker177d3cf2017-06-07 15:52:48 +0100344#endif /* !MBEDTLS_AES_FEWER_TABLES */
Paul Bakker5121ce52009-01-03 21:22:43 +0000345
346/*
347 * Reverse S-box & tables
348 */
349static unsigned char RSb[256];
Paul Bakker5c2364c2012-10-01 14:41:15 +0000350static uint32_t RT0[256];
Hanno Beckerad049a92017-06-19 16:31:54 +0100351#if !defined(MBEDTLS_AES_FEWER_TABLES)
Paul Bakker5c2364c2012-10-01 14:41:15 +0000352static uint32_t RT1[256];
353static uint32_t RT2[256];
354static uint32_t RT3[256];
Hanno Becker177d3cf2017-06-07 15:52:48 +0100355#endif /* !MBEDTLS_AES_FEWER_TABLES */
Paul Bakker5121ce52009-01-03 21:22:43 +0000356
357/*
358 * Round constants
359 */
Paul Bakker5c2364c2012-10-01 14:41:15 +0000360static uint32_t RCON[10];
Paul Bakker5121ce52009-01-03 21:22:43 +0000361
362/*
363 * Tables generation code
364 */
Hanno Becker1eeca412018-10-15 12:01:35 +0100365#define ROTL8(x) ( ( (x) << 8 ) & 0xFFFFFFFF ) | ( (x) >> 24 )
366#define XTIME(x) ( ( (x) << 1 ) ^ ( ( (x) & 0x80 ) ? 0x1B : 0x00 ) )
Hanno Becker818bac52018-10-26 09:13:26 +0100367#define MUL(x,y) ( ( (x) && (y) ) ? pow[(log[(x)]+log[(y)]) % 255] : 0 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000368
369static int aes_init_done = 0;
370
371static void aes_gen_tables( void )
372{
373 int i, x, y, z;
374 int pow[256];
375 int log[256];
376
377 /*
378 * compute pow and log tables over GF(2^8)
379 */
380 for( i = 0, x = 1; i < 256; i++ )
381 {
382 pow[i] = x;
383 log[x] = i;
Joe Subbiani6b897c92021-07-08 14:59:52 +0100384 x = MBEDTLS_BYTE_0( x ^ XTIME( x ) );
Paul Bakker5121ce52009-01-03 21:22:43 +0000385 }
386
387 /*
388 * calculate the round constants
389 */
390 for( i = 0, x = 1; i < 10; i++ )
391 {
Paul Bakker5c2364c2012-10-01 14:41:15 +0000392 RCON[i] = (uint32_t) x;
Joe Subbiani6b897c92021-07-08 14:59:52 +0100393 x = MBEDTLS_BYTE_0( XTIME( x ) );
Paul Bakker5121ce52009-01-03 21:22:43 +0000394 }
395
396 /*
397 * generate the forward and reverse S-boxes
398 */
399 FSb[0x00] = 0x63;
400 RSb[0x63] = 0x00;
401
402 for( i = 1; i < 256; i++ )
403 {
404 x = pow[255 - log[i]];
405
Joe Subbiani6b897c92021-07-08 14:59:52 +0100406 y = x; y = MBEDTLS_BYTE_0( ( y << 1 ) | ( y >> 7 ) );
407 x ^= y; y = MBEDTLS_BYTE_0( ( y << 1 ) | ( y >> 7 ) );
408 x ^= y; y = MBEDTLS_BYTE_0( ( y << 1 ) | ( y >> 7 ) );
409 x ^= y; y = MBEDTLS_BYTE_0( ( y << 1 ) | ( y >> 7 ) );
Paul Bakker5121ce52009-01-03 21:22:43 +0000410 x ^= y ^ 0x63;
411
412 FSb[i] = (unsigned char) x;
413 RSb[x] = (unsigned char) i;
414 }
415
416 /*
417 * generate the forward and reverse tables
418 */
419 for( i = 0; i < 256; i++ )
420 {
421 x = FSb[i];
Joe Subbiani6b897c92021-07-08 14:59:52 +0100422 y = MBEDTLS_BYTE_0( XTIME( x ) );
423 z = MBEDTLS_BYTE_0( y ^ x );
Paul Bakker5121ce52009-01-03 21:22:43 +0000424
Paul Bakker5c2364c2012-10-01 14:41:15 +0000425 FT0[i] = ( (uint32_t) y ) ^
426 ( (uint32_t) x << 8 ) ^
427 ( (uint32_t) x << 16 ) ^
428 ( (uint32_t) z << 24 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000429
Hanno Beckerad049a92017-06-19 16:31:54 +0100430#if !defined(MBEDTLS_AES_FEWER_TABLES)
Paul Bakker5121ce52009-01-03 21:22:43 +0000431 FT1[i] = ROTL8( FT0[i] );
432 FT2[i] = ROTL8( FT1[i] );
433 FT3[i] = ROTL8( FT2[i] );
Hanno Becker177d3cf2017-06-07 15:52:48 +0100434#endif /* !MBEDTLS_AES_FEWER_TABLES */
Paul Bakker5121ce52009-01-03 21:22:43 +0000435
436 x = RSb[i];
437
Paul Bakker5c2364c2012-10-01 14:41:15 +0000438 RT0[i] = ( (uint32_t) MUL( 0x0E, x ) ) ^
439 ( (uint32_t) MUL( 0x09, x ) << 8 ) ^
440 ( (uint32_t) MUL( 0x0D, x ) << 16 ) ^
441 ( (uint32_t) MUL( 0x0B, x ) << 24 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000442
Hanno Beckerad049a92017-06-19 16:31:54 +0100443#if !defined(MBEDTLS_AES_FEWER_TABLES)
Paul Bakker5121ce52009-01-03 21:22:43 +0000444 RT1[i] = ROTL8( RT0[i] );
445 RT2[i] = ROTL8( RT1[i] );
446 RT3[i] = ROTL8( RT2[i] );
Hanno Becker177d3cf2017-06-07 15:52:48 +0100447#endif /* !MBEDTLS_AES_FEWER_TABLES */
Paul Bakker5121ce52009-01-03 21:22:43 +0000448 }
449}
450
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200451#undef ROTL8
452
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200453#endif /* MBEDTLS_AES_ROM_TABLES */
Paul Bakker5121ce52009-01-03 21:22:43 +0000454
Hanno Beckerad049a92017-06-19 16:31:54 +0100455#if defined(MBEDTLS_AES_FEWER_TABLES)
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200456
457#define ROTL8(x) ( (uint32_t)( ( x ) << 8 ) + (uint32_t)( ( x ) >> 24 ) )
458#define ROTL16(x) ( (uint32_t)( ( x ) << 16 ) + (uint32_t)( ( x ) >> 16 ) )
459#define ROTL24(x) ( (uint32_t)( ( x ) << 24 ) + (uint32_t)( ( x ) >> 8 ) )
460
461#define AES_RT0(idx) RT0[idx]
462#define AES_RT1(idx) ROTL8( RT0[idx] )
463#define AES_RT2(idx) ROTL16( RT0[idx] )
464#define AES_RT3(idx) ROTL24( RT0[idx] )
465
466#define AES_FT0(idx) FT0[idx]
467#define AES_FT1(idx) ROTL8( FT0[idx] )
468#define AES_FT2(idx) ROTL16( FT0[idx] )
469#define AES_FT3(idx) ROTL24( FT0[idx] )
470
Hanno Becker177d3cf2017-06-07 15:52:48 +0100471#else /* MBEDTLS_AES_FEWER_TABLES */
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200472
473#define AES_RT0(idx) RT0[idx]
474#define AES_RT1(idx) RT1[idx]
475#define AES_RT2(idx) RT2[idx]
476#define AES_RT3(idx) RT3[idx]
477
478#define AES_FT0(idx) FT0[idx]
479#define AES_FT1(idx) FT1[idx]
480#define AES_FT2(idx) FT2[idx]
481#define AES_FT3(idx) FT3[idx]
482
Hanno Becker177d3cf2017-06-07 15:52:48 +0100483#endif /* MBEDTLS_AES_FEWER_TABLES */
Jussi Kivilinna2fd1bb82015-11-12 16:38:31 +0200484
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200485void mbedtls_aes_init( mbedtls_aes_context *ctx )
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200486{
Manuel Pégourié-Gonnard0e9cddb2018-12-10 16:37:51 +0100487 AES_VALIDATE( ctx != NULL );
Simon Butcher5201e412018-12-06 17:40:14 +0000488
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200489 memset( ctx, 0, sizeof( mbedtls_aes_context ) );
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200490}
491
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200492void mbedtls_aes_free( mbedtls_aes_context *ctx )
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200493{
494 if( ctx == NULL )
495 return;
496
Andres Amaya Garcia1f6301b2018-04-17 09:51:09 -0500497 mbedtls_platform_zeroize( ctx, sizeof( mbedtls_aes_context ) );
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200498}
499
Jaeden Amero9366feb2018-05-29 18:55:17 +0100500#if defined(MBEDTLS_CIPHER_MODE_XTS)
501void mbedtls_aes_xts_init( mbedtls_aes_xts_context *ctx )
502{
Manuel Pégourié-Gonnard0e9cddb2018-12-10 16:37:51 +0100503 AES_VALIDATE( ctx != NULL );
Simon Butcher5201e412018-12-06 17:40:14 +0000504
Jaeden Amero9366feb2018-05-29 18:55:17 +0100505 mbedtls_aes_init( &ctx->crypt );
506 mbedtls_aes_init( &ctx->tweak );
507}
508
509void mbedtls_aes_xts_free( mbedtls_aes_xts_context *ctx )
510{
Manuel Pégourié-Gonnard44c5d582018-12-10 16:56:14 +0100511 if( ctx == NULL )
512 return;
Simon Butcher5201e412018-12-06 17:40:14 +0000513
Jaeden Amero9366feb2018-05-29 18:55:17 +0100514 mbedtls_aes_free( &ctx->crypt );
515 mbedtls_aes_free( &ctx->tweak );
516}
517#endif /* MBEDTLS_CIPHER_MODE_XTS */
518
Paul Bakker5121ce52009-01-03 21:22:43 +0000519/*
520 * AES key schedule (encryption)
521 */
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200522#if !defined(MBEDTLS_AES_SETKEY_ENC_ALT)
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200523int mbedtls_aes_setkey_enc( mbedtls_aes_context *ctx, const unsigned char *key,
Manuel Pégourié-Gonnardb8186a52015-06-18 14:58:58 +0200524 unsigned int keybits )
Paul Bakker5121ce52009-01-03 21:22:43 +0000525{
Paul Bakker23986e52011-04-24 08:57:21 +0000526 unsigned int i;
Paul Bakker5c2364c2012-10-01 14:41:15 +0000527 uint32_t *RK;
Paul Bakker5121ce52009-01-03 21:22:43 +0000528
Manuel Pégourié-Gonnard44c5d582018-12-10 16:56:14 +0100529 AES_VALIDATE_RET( ctx != NULL );
530 AES_VALIDATE_RET( key != NULL );
Paul Bakker5121ce52009-01-03 21:22:43 +0000531
Manuel Pégourié-Gonnardb8186a52015-06-18 14:58:58 +0200532 switch( keybits )
Paul Bakker5121ce52009-01-03 21:22:43 +0000533 {
534 case 128: ctx->nr = 10; break;
535 case 192: ctx->nr = 12; break;
536 case 256: ctx->nr = 14; break;
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200537 default : return( MBEDTLS_ERR_AES_INVALID_KEY_LENGTH );
Paul Bakker5121ce52009-01-03 21:22:43 +0000538 }
539
Simon Butcher5201e412018-12-06 17:40:14 +0000540#if !defined(MBEDTLS_AES_ROM_TABLES)
541 if( aes_init_done == 0 )
542 {
543 aes_gen_tables();
544 aes_init_done = 1;
Simon Butcher5201e412018-12-06 17:40:14 +0000545 }
546#endif
547
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200548#if defined(MBEDTLS_PADLOCK_C) && defined(MBEDTLS_PADLOCK_ALIGN16)
Paul Bakker048d04e2012-02-12 17:31:04 +0000549 if( aes_padlock_ace == -1 )
Manuel Pégourié-Gonnardc730ed32015-06-02 10:38:50 +0100550 aes_padlock_ace = mbedtls_padlock_has_support( MBEDTLS_PADLOCK_ACE );
Paul Bakker048d04e2012-02-12 17:31:04 +0000551
552 if( aes_padlock_ace )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200553 ctx->rk = RK = MBEDTLS_PADLOCK_ALIGN16( ctx->buf );
Paul Bakker048d04e2012-02-12 17:31:04 +0000554 else
Paul Bakker5121ce52009-01-03 21:22:43 +0000555#endif
Paul Bakker048d04e2012-02-12 17:31:04 +0000556 ctx->rk = RK = ctx->buf;
Paul Bakker5121ce52009-01-03 21:22:43 +0000557
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200558#if defined(MBEDTLS_AESNI_C) && defined(MBEDTLS_HAVE_X86_64)
Manuel Pégourié-Gonnardc730ed32015-06-02 10:38:50 +0100559 if( mbedtls_aesni_has_support( MBEDTLS_AESNI_AES ) )
Manuel Pégourié-Gonnardb8186a52015-06-18 14:58:58 +0200560 return( mbedtls_aesni_setkey_enc( (unsigned char *) ctx->rk, key, keybits ) );
Manuel Pégourié-Gonnard47a35362013-12-28 20:45:04 +0100561#endif
562
Manuel Pégourié-Gonnardb8186a52015-06-18 14:58:58 +0200563 for( i = 0; i < ( keybits >> 5 ); i++ )
Paul Bakker5121ce52009-01-03 21:22:43 +0000564 {
Joe Subbiani9231d5f2021-07-07 16:56:29 +0100565 RK[i] = MBEDTLS_GET_UINT32_LE( key, i << 2 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000566 }
567
568 switch( ctx->nr )
569 {
570 case 10:
571
572 for( i = 0; i < 10; i++, RK += 4 )
573 {
574 RK[4] = RK[0] ^ RCON[i] ^
Joe Subbiani6b897c92021-07-08 14:59:52 +0100575 ( (uint32_t) FSb[ MBEDTLS_BYTE_1( RK[3] ) ] ) ^
576 ( (uint32_t) FSb[ MBEDTLS_BYTE_2( RK[3] ) ] << 8 ) ^
577 ( (uint32_t) FSb[ MBEDTLS_BYTE_3( RK[3] ) ] << 16 ) ^
578 ( (uint32_t) FSb[ MBEDTLS_BYTE_0( RK[3] ) ] << 24 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000579
580 RK[5] = RK[1] ^ RK[4];
581 RK[6] = RK[2] ^ RK[5];
582 RK[7] = RK[3] ^ RK[6];
583 }
584 break;
585
586 case 12:
587
588 for( i = 0; i < 8; i++, RK += 6 )
589 {
590 RK[6] = RK[0] ^ RCON[i] ^
Joe Subbiani6b897c92021-07-08 14:59:52 +0100591 ( (uint32_t) FSb[ MBEDTLS_BYTE_1( RK[5] ) ] ) ^
592 ( (uint32_t) FSb[ MBEDTLS_BYTE_2( RK[5] ) ] << 8 ) ^
593 ( (uint32_t) FSb[ MBEDTLS_BYTE_3( RK[5] ) ] << 16 ) ^
594 ( (uint32_t) FSb[ MBEDTLS_BYTE_0( RK[5] ) ] << 24 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000595
596 RK[7] = RK[1] ^ RK[6];
597 RK[8] = RK[2] ^ RK[7];
598 RK[9] = RK[3] ^ RK[8];
599 RK[10] = RK[4] ^ RK[9];
600 RK[11] = RK[5] ^ RK[10];
601 }
602 break;
603
604 case 14:
605
606 for( i = 0; i < 7; i++, RK += 8 )
607 {
608 RK[8] = RK[0] ^ RCON[i] ^
Joe Subbiani6b897c92021-07-08 14:59:52 +0100609 ( (uint32_t) FSb[ MBEDTLS_BYTE_1( RK[7] ) ] ) ^
610 ( (uint32_t) FSb[ MBEDTLS_BYTE_2( RK[7] ) ] << 8 ) ^
611 ( (uint32_t) FSb[ MBEDTLS_BYTE_3( RK[7] ) ] << 16 ) ^
612 ( (uint32_t) FSb[ MBEDTLS_BYTE_0( RK[7] ) ] << 24 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000613
614 RK[9] = RK[1] ^ RK[8];
615 RK[10] = RK[2] ^ RK[9];
616 RK[11] = RK[3] ^ RK[10];
617
618 RK[12] = RK[4] ^
Joe Subbiani6b897c92021-07-08 14:59:52 +0100619 ( (uint32_t) FSb[ MBEDTLS_BYTE_0( RK[11] ) ] ) ^
620 ( (uint32_t) FSb[ MBEDTLS_BYTE_1( RK[11] ) ] << 8 ) ^
621 ( (uint32_t) FSb[ MBEDTLS_BYTE_2( RK[11] ) ] << 16 ) ^
622 ( (uint32_t) FSb[ MBEDTLS_BYTE_3( RK[11] ) ] << 24 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000623
624 RK[13] = RK[5] ^ RK[12];
625 RK[14] = RK[6] ^ RK[13];
626 RK[15] = RK[7] ^ RK[14];
627 }
628 break;
Paul Bakker5121ce52009-01-03 21:22:43 +0000629 }
Paul Bakker2b222c82009-07-27 21:03:45 +0000630
631 return( 0 );
Paul Bakker5121ce52009-01-03 21:22:43 +0000632}
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200633#endif /* !MBEDTLS_AES_SETKEY_ENC_ALT */
Paul Bakker5121ce52009-01-03 21:22:43 +0000634
635/*
636 * AES key schedule (decryption)
637 */
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200638#if !defined(MBEDTLS_AES_SETKEY_DEC_ALT)
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200639int mbedtls_aes_setkey_dec( mbedtls_aes_context *ctx, const unsigned char *key,
Manuel Pégourié-Gonnardb8186a52015-06-18 14:58:58 +0200640 unsigned int keybits )
Paul Bakker5121ce52009-01-03 21:22:43 +0000641{
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200642 int i, j, ret;
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200643 mbedtls_aes_context cty;
Paul Bakker5c2364c2012-10-01 14:41:15 +0000644 uint32_t *RK;
645 uint32_t *SK;
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200646
Manuel Pégourié-Gonnard44c5d582018-12-10 16:56:14 +0100647 AES_VALIDATE_RET( ctx != NULL );
648 AES_VALIDATE_RET( key != NULL );
Simon Butcher5201e412018-12-06 17:40:14 +0000649
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200650 mbedtls_aes_init( &cty );
Paul Bakker5121ce52009-01-03 21:22:43 +0000651
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200652#if defined(MBEDTLS_PADLOCK_C) && defined(MBEDTLS_PADLOCK_ALIGN16)
Paul Bakker048d04e2012-02-12 17:31:04 +0000653 if( aes_padlock_ace == -1 )
Manuel Pégourié-Gonnardc730ed32015-06-02 10:38:50 +0100654 aes_padlock_ace = mbedtls_padlock_has_support( MBEDTLS_PADLOCK_ACE );
Paul Bakker048d04e2012-02-12 17:31:04 +0000655
656 if( aes_padlock_ace )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200657 ctx->rk = RK = MBEDTLS_PADLOCK_ALIGN16( ctx->buf );
Paul Bakker048d04e2012-02-12 17:31:04 +0000658 else
Paul Bakker5121ce52009-01-03 21:22:43 +0000659#endif
Paul Bakker048d04e2012-02-12 17:31:04 +0000660 ctx->rk = RK = ctx->buf;
Paul Bakker5121ce52009-01-03 21:22:43 +0000661
Manuel Pégourié-Gonnardb8186a52015-06-18 14:58:58 +0200662 /* Also checks keybits */
663 if( ( ret = mbedtls_aes_setkey_enc( &cty, key, keybits ) ) != 0 )
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200664 goto exit;
Paul Bakker2b222c82009-07-27 21:03:45 +0000665
Manuel Pégourié-Gonnardafd5a082014-05-28 21:52:59 +0200666 ctx->nr = cty.nr;
667
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200668#if defined(MBEDTLS_AESNI_C) && defined(MBEDTLS_HAVE_X86_64)
Manuel Pégourié-Gonnardc730ed32015-06-02 10:38:50 +0100669 if( mbedtls_aesni_has_support( MBEDTLS_AESNI_AES ) )
Manuel Pégourié-Gonnard01e31bb2013-12-28 15:58:30 +0100670 {
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200671 mbedtls_aesni_inverse_key( (unsigned char *) ctx->rk,
Manuel Pégourié-Gonnard01e31bb2013-12-28 15:58:30 +0100672 (const unsigned char *) cty.rk, ctx->nr );
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200673 goto exit;
Manuel Pégourié-Gonnard01e31bb2013-12-28 15:58:30 +0100674 }
675#endif
676
Paul Bakker5121ce52009-01-03 21:22:43 +0000677 SK = cty.rk + cty.nr * 4;
678
679 *RK++ = *SK++;
680 *RK++ = *SK++;
681 *RK++ = *SK++;
682 *RK++ = *SK++;
683
684 for( i = ctx->nr - 1, SK -= 8; i > 0; i--, SK -= 8 )
685 {
686 for( j = 0; j < 4; j++, SK++ )
687 {
Joe Subbiani6b897c92021-07-08 14:59:52 +0100688 *RK++ = AES_RT0( FSb[ MBEDTLS_BYTE_0( *SK ) ] ) ^
689 AES_RT1( FSb[ MBEDTLS_BYTE_1( *SK ) ] ) ^
690 AES_RT2( FSb[ MBEDTLS_BYTE_2( *SK ) ] ) ^
691 AES_RT3( FSb[ MBEDTLS_BYTE_3( *SK ) ] );
Paul Bakker5121ce52009-01-03 21:22:43 +0000692 }
693 }
694
695 *RK++ = *SK++;
696 *RK++ = *SK++;
697 *RK++ = *SK++;
698 *RK++ = *SK++;
699
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200700exit:
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200701 mbedtls_aes_free( &cty );
Paul Bakker2b222c82009-07-27 21:03:45 +0000702
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200703 return( ret );
Paul Bakker5121ce52009-01-03 21:22:43 +0000704}
gabor-mezei-arm95db3012020-10-26 11:35:23 +0100705#endif /* !MBEDTLS_AES_SETKEY_DEC_ALT */
Jaeden Amero9366feb2018-05-29 18:55:17 +0100706
707#if defined(MBEDTLS_CIPHER_MODE_XTS)
708static int mbedtls_aes_xts_decode_keys( const unsigned char *key,
709 unsigned int keybits,
710 const unsigned char **key1,
711 unsigned int *key1bits,
712 const unsigned char **key2,
713 unsigned int *key2bits )
714{
715 const unsigned int half_keybits = keybits / 2;
716 const unsigned int half_keybytes = half_keybits / 8;
717
718 switch( keybits )
719 {
720 case 256: break;
721 case 512: break;
722 default : return( MBEDTLS_ERR_AES_INVALID_KEY_LENGTH );
723 }
724
725 *key1bits = half_keybits;
726 *key2bits = half_keybits;
727 *key1 = &key[0];
728 *key2 = &key[half_keybytes];
729
730 return 0;
731}
732
733int mbedtls_aes_xts_setkey_enc( mbedtls_aes_xts_context *ctx,
734 const unsigned char *key,
735 unsigned int keybits)
736{
Janos Follath24eed8d2019-11-22 13:21:35 +0000737 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Jaeden Amero9366feb2018-05-29 18:55:17 +0100738 const unsigned char *key1, *key2;
739 unsigned int key1bits, key2bits;
740
Manuel Pégourié-Gonnard68e3dff2018-12-12 12:48:04 +0100741 AES_VALIDATE_RET( ctx != NULL );
742 AES_VALIDATE_RET( key != NULL );
743
Jaeden Amero9366feb2018-05-29 18:55:17 +0100744 ret = mbedtls_aes_xts_decode_keys( key, keybits, &key1, &key1bits,
745 &key2, &key2bits );
746 if( ret != 0 )
747 return( ret );
748
749 /* Set the tweak key. Always set tweak key for the encryption mode. */
750 ret = mbedtls_aes_setkey_enc( &ctx->tweak, key2, key2bits );
751 if( ret != 0 )
752 return( ret );
753
754 /* Set crypt key for encryption. */
755 return mbedtls_aes_setkey_enc( &ctx->crypt, key1, key1bits );
756}
757
758int mbedtls_aes_xts_setkey_dec( mbedtls_aes_xts_context *ctx,
759 const unsigned char *key,
760 unsigned int keybits)
761{
Janos Follath24eed8d2019-11-22 13:21:35 +0000762 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Jaeden Amero9366feb2018-05-29 18:55:17 +0100763 const unsigned char *key1, *key2;
764 unsigned int key1bits, key2bits;
765
Manuel Pégourié-Gonnard68e3dff2018-12-12 12:48:04 +0100766 AES_VALIDATE_RET( ctx != NULL );
767 AES_VALIDATE_RET( key != NULL );
768
Jaeden Amero9366feb2018-05-29 18:55:17 +0100769 ret = mbedtls_aes_xts_decode_keys( key, keybits, &key1, &key1bits,
770 &key2, &key2bits );
771 if( ret != 0 )
772 return( ret );
773
774 /* Set the tweak key. Always set tweak key for encryption. */
775 ret = mbedtls_aes_setkey_enc( &ctx->tweak, key2, key2bits );
776 if( ret != 0 )
777 return( ret );
778
779 /* Set crypt key for decryption. */
780 return mbedtls_aes_setkey_dec( &ctx->crypt, key1, key1bits );
781}
782#endif /* MBEDTLS_CIPHER_MODE_XTS */
783
Joe Subbiani6b897c92021-07-08 14:59:52 +0100784#define AES_FROUND(X0,X1,X2,X3,Y0,Y1,Y2,Y3) \
785 do \
786 { \
787 (X0) = *RK++ ^ AES_FT0( MBEDTLS_BYTE_0( Y0 ) ) ^ \
788 AES_FT1( MBEDTLS_BYTE_1( Y1 ) ) ^ \
789 AES_FT2( MBEDTLS_BYTE_2( Y2 ) ) ^ \
790 AES_FT3( MBEDTLS_BYTE_3( Y3 ) ); \
791 \
792 (X1) = *RK++ ^ AES_FT0( MBEDTLS_BYTE_0( Y1 ) ) ^ \
793 AES_FT1( MBEDTLS_BYTE_1( Y2 ) ) ^ \
794 AES_FT2( MBEDTLS_BYTE_2( Y3 ) ) ^ \
795 AES_FT3( MBEDTLS_BYTE_3( Y0 ) ); \
796 \
797 (X2) = *RK++ ^ AES_FT0( MBEDTLS_BYTE_0( Y2 ) ) ^ \
798 AES_FT1( MBEDTLS_BYTE_1( Y3 ) ) ^ \
799 AES_FT2( MBEDTLS_BYTE_2( Y0 ) ) ^ \
800 AES_FT3( MBEDTLS_BYTE_3( Y1 ) ); \
801 \
802 (X3) = *RK++ ^ AES_FT0( MBEDTLS_BYTE_0( Y3 ) ) ^ \
803 AES_FT1( MBEDTLS_BYTE_1( Y0 ) ) ^ \
804 AES_FT2( MBEDTLS_BYTE_2( Y1 ) ) ^ \
805 AES_FT3( MBEDTLS_BYTE_3( Y2 ) ); \
Hanno Becker1eeca412018-10-15 12:01:35 +0100806 } while( 0 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000807
Hanno Becker1eeca412018-10-15 12:01:35 +0100808#define AES_RROUND(X0,X1,X2,X3,Y0,Y1,Y2,Y3) \
809 do \
810 { \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100811 (X0) = *RK++ ^ AES_RT0( MBEDTLS_BYTE_0( Y0 ) ) ^ \
812 AES_RT1( MBEDTLS_BYTE_1( Y3 ) ) ^ \
813 AES_RT2( MBEDTLS_BYTE_2( Y2 ) ) ^ \
814 AES_RT3( MBEDTLS_BYTE_3( Y1 ) ); \
Hanno Becker1eeca412018-10-15 12:01:35 +0100815 \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100816 (X1) = *RK++ ^ AES_RT0( MBEDTLS_BYTE_0( Y1 ) ) ^ \
817 AES_RT1( MBEDTLS_BYTE_1( Y0 ) ) ^ \
818 AES_RT2( MBEDTLS_BYTE_2( Y3 ) ) ^ \
819 AES_RT3( MBEDTLS_BYTE_3( Y2 ) ); \
Hanno Becker1eeca412018-10-15 12:01:35 +0100820 \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100821 (X2) = *RK++ ^ AES_RT0( MBEDTLS_BYTE_0( Y2 ) ) ^ \
822 AES_RT1( MBEDTLS_BYTE_1( Y1 ) ) ^ \
823 AES_RT2( MBEDTLS_BYTE_2( Y0 ) ) ^ \
824 AES_RT3( MBEDTLS_BYTE_3( Y3 ) ); \
Hanno Becker1eeca412018-10-15 12:01:35 +0100825 \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100826 (X3) = *RK++ ^ AES_RT0( MBEDTLS_BYTE_0( Y3 ) ) ^ \
827 AES_RT1( MBEDTLS_BYTE_1( Y2 ) ) ^ \
828 AES_RT2( MBEDTLS_BYTE_2( Y1 ) ) ^ \
829 AES_RT3( MBEDTLS_BYTE_3( Y0 ) ); \
Hanno Becker1eeca412018-10-15 12:01:35 +0100830 } while( 0 )
Paul Bakker5121ce52009-01-03 21:22:43 +0000831
832/*
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200833 * AES-ECB block encryption
834 */
835#if !defined(MBEDTLS_AES_ENCRYPT_ALT)
Andres AGf5bf7182017-03-03 14:09:56 +0000836int mbedtls_internal_aes_encrypt( mbedtls_aes_context *ctx,
837 const unsigned char input[16],
838 unsigned char output[16] )
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200839{
840 int i;
Gilles Peskine5197c662020-08-26 17:03:24 +0200841 uint32_t *RK = ctx->rk;
842 struct
843 {
844 uint32_t X[4];
845 uint32_t Y[4];
846 } t;
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200847
Joe Subbiani9231d5f2021-07-07 16:56:29 +0100848 t.X[0] = MBEDTLS_GET_UINT32_LE( input, 0 ); t.X[0] ^= *RK++;
849 t.X[1] = MBEDTLS_GET_UINT32_LE( input, 4 ); t.X[1] ^= *RK++;
850 t.X[2] = MBEDTLS_GET_UINT32_LE( input, 8 ); t.X[2] ^= *RK++;
851 t.X[3] = MBEDTLS_GET_UINT32_LE( input, 12 ); t.X[3] ^= *RK++;
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200852
853 for( i = ( ctx->nr >> 1 ) - 1; i > 0; i-- )
854 {
Gilles Peskine5197c662020-08-26 17:03:24 +0200855 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] );
856 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 +0200857 }
858
Gilles Peskine5197c662020-08-26 17:03:24 +0200859 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 +0200860
Gilles Peskine5197c662020-08-26 17:03:24 +0200861 t.X[0] = *RK++ ^ \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100862 ( (uint32_t) FSb[ MBEDTLS_BYTE_0( t.Y[0] ) ] ) ^
863 ( (uint32_t) FSb[ MBEDTLS_BYTE_1( t.Y[1] ) ] << 8 ) ^
864 ( (uint32_t) FSb[ MBEDTLS_BYTE_2( t.Y[2] ) ] << 16 ) ^
865 ( (uint32_t) FSb[ MBEDTLS_BYTE_3( t.Y[3] ) ] << 24 );
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200866
Gilles Peskine5197c662020-08-26 17:03:24 +0200867 t.X[1] = *RK++ ^ \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100868 ( (uint32_t) FSb[ MBEDTLS_BYTE_0( t.Y[1] ) ] ) ^
869 ( (uint32_t) FSb[ MBEDTLS_BYTE_1( t.Y[2] ) ] << 8 ) ^
870 ( (uint32_t) FSb[ MBEDTLS_BYTE_2( t.Y[3] ) ] << 16 ) ^
871 ( (uint32_t) FSb[ MBEDTLS_BYTE_3( t.Y[0] ) ] << 24 );
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200872
Gilles Peskine5197c662020-08-26 17:03:24 +0200873 t.X[2] = *RK++ ^ \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100874 ( (uint32_t) FSb[ MBEDTLS_BYTE_0( t.Y[2] ) ] ) ^
875 ( (uint32_t) FSb[ MBEDTLS_BYTE_1( t.Y[3] ) ] << 8 ) ^
876 ( (uint32_t) FSb[ MBEDTLS_BYTE_2( t.Y[0] ) ] << 16 ) ^
877 ( (uint32_t) FSb[ MBEDTLS_BYTE_3( t.Y[1] ) ] << 24 );
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200878
Gilles Peskine5197c662020-08-26 17:03:24 +0200879 t.X[3] = *RK++ ^ \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100880 ( (uint32_t) FSb[ MBEDTLS_BYTE_0( t.Y[3] ) ] ) ^
881 ( (uint32_t) FSb[ MBEDTLS_BYTE_1( t.Y[0] ) ] << 8 ) ^
882 ( (uint32_t) FSb[ MBEDTLS_BYTE_2( t.Y[1] ) ] << 16 ) ^
883 ( (uint32_t) FSb[ MBEDTLS_BYTE_3( t.Y[2] ) ] << 24 );
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200884
Joe Subbiani2bbafda2021-06-24 13:00:03 +0100885 MBEDTLS_PUT_UINT32_LE( t.X[0], output, 0 );
886 MBEDTLS_PUT_UINT32_LE( t.X[1], output, 4 );
887 MBEDTLS_PUT_UINT32_LE( t.X[2], output, 8 );
888 MBEDTLS_PUT_UINT32_LE( t.X[3], output, 12 );
Andres AGf5bf7182017-03-03 14:09:56 +0000889
Gilles Peskine5197c662020-08-26 17:03:24 +0200890 mbedtls_platform_zeroize( &t, sizeof( t ) );
Andrzej Kurek96ae5cd2019-11-12 03:05:51 -0500891
Andres AGf5bf7182017-03-03 14:09:56 +0000892 return( 0 );
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200893}
894#endif /* !MBEDTLS_AES_ENCRYPT_ALT */
895
Gilles Peskine8db3efb2018-02-21 19:16:20 +0100896#if !defined(MBEDTLS_DEPRECATED_REMOVED)
Hanno Beckerbedc2052017-06-26 12:46:56 +0100897void mbedtls_aes_encrypt( mbedtls_aes_context *ctx,
898 const unsigned char input[16],
899 unsigned char output[16] )
900{
Mateusz Starzyk15a74202021-08-05 13:56:48 +0200901 MBEDTLS_IGNORE_RETURN( mbedtls_internal_aes_encrypt( ctx, input, output ) );
Hanno Beckerbedc2052017-06-26 12:46:56 +0100902}
Gilles Peskine8db3efb2018-02-21 19:16:20 +0100903#endif /* !MBEDTLS_DEPRECATED_REMOVED */
Hanno Beckerbedc2052017-06-26 12:46:56 +0100904
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200905/*
906 * AES-ECB block decryption
907 */
908#if !defined(MBEDTLS_AES_DECRYPT_ALT)
Andres AGf5bf7182017-03-03 14:09:56 +0000909int mbedtls_internal_aes_decrypt( mbedtls_aes_context *ctx,
910 const unsigned char input[16],
911 unsigned char output[16] )
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200912{
913 int i;
Gilles Peskine5197c662020-08-26 17:03:24 +0200914 uint32_t *RK = ctx->rk;
915 struct
916 {
917 uint32_t X[4];
918 uint32_t Y[4];
919 } t;
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200920
Joe Subbiani9231d5f2021-07-07 16:56:29 +0100921 t.X[0] = MBEDTLS_GET_UINT32_LE( input, 0 ); t.X[0] ^= *RK++;
922 t.X[1] = MBEDTLS_GET_UINT32_LE( input, 4 ); t.X[1] ^= *RK++;
923 t.X[2] = MBEDTLS_GET_UINT32_LE( input, 8 ); t.X[2] ^= *RK++;
924 t.X[3] = MBEDTLS_GET_UINT32_LE( input, 12 ); t.X[3] ^= *RK++;
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200925
926 for( i = ( ctx->nr >> 1 ) - 1; i > 0; i-- )
927 {
Gilles Peskine5197c662020-08-26 17:03:24 +0200928 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] );
929 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 +0200930 }
931
Gilles Peskine5197c662020-08-26 17:03:24 +0200932 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 +0200933
Gilles Peskine5197c662020-08-26 17:03:24 +0200934 t.X[0] = *RK++ ^ \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100935 ( (uint32_t) RSb[ MBEDTLS_BYTE_0( t.Y[0] ) ] ) ^
936 ( (uint32_t) RSb[ MBEDTLS_BYTE_1( t.Y[3] ) ] << 8 ) ^
937 ( (uint32_t) RSb[ MBEDTLS_BYTE_2( t.Y[2] ) ] << 16 ) ^
938 ( (uint32_t) RSb[ MBEDTLS_BYTE_3( t.Y[1] ) ] << 24 );
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200939
Gilles Peskine5197c662020-08-26 17:03:24 +0200940 t.X[1] = *RK++ ^ \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100941 ( (uint32_t) RSb[ MBEDTLS_BYTE_0( t.Y[1] ) ] ) ^
942 ( (uint32_t) RSb[ MBEDTLS_BYTE_1( t.Y[0] ) ] << 8 ) ^
943 ( (uint32_t) RSb[ MBEDTLS_BYTE_2( t.Y[3] ) ] << 16 ) ^
944 ( (uint32_t) RSb[ MBEDTLS_BYTE_3( t.Y[2] ) ] << 24 );
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200945
Gilles Peskine5197c662020-08-26 17:03:24 +0200946 t.X[2] = *RK++ ^ \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100947 ( (uint32_t) RSb[ MBEDTLS_BYTE_0( t.Y[2] ) ] ) ^
948 ( (uint32_t) RSb[ MBEDTLS_BYTE_1( t.Y[1] ) ] << 8 ) ^
949 ( (uint32_t) RSb[ MBEDTLS_BYTE_2( t.Y[0] ) ] << 16 ) ^
950 ( (uint32_t) RSb[ MBEDTLS_BYTE_3( t.Y[3] ) ] << 24 );
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200951
Gilles Peskine5197c662020-08-26 17:03:24 +0200952 t.X[3] = *RK++ ^ \
Joe Subbiani6b897c92021-07-08 14:59:52 +0100953 ( (uint32_t) RSb[ MBEDTLS_BYTE_0( t.Y[3] ) ] ) ^
954 ( (uint32_t) RSb[ MBEDTLS_BYTE_1( t.Y[2] ) ] << 8 ) ^
955 ( (uint32_t) RSb[ MBEDTLS_BYTE_2( t.Y[1] ) ] << 16 ) ^
956 ( (uint32_t) RSb[ MBEDTLS_BYTE_3( t.Y[0] ) ] << 24 );
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200957
Joe Subbiani2bbafda2021-06-24 13:00:03 +0100958 MBEDTLS_PUT_UINT32_LE( t.X[0], output, 0 );
959 MBEDTLS_PUT_UINT32_LE( t.X[1], output, 4 );
960 MBEDTLS_PUT_UINT32_LE( t.X[2], output, 8 );
961 MBEDTLS_PUT_UINT32_LE( t.X[3], output, 12 );
Andres AGf5bf7182017-03-03 14:09:56 +0000962
Gilles Peskine5197c662020-08-26 17:03:24 +0200963 mbedtls_platform_zeroize( &t, sizeof( t ) );
Andrzej Kurek96ae5cd2019-11-12 03:05:51 -0500964
Andres AGf5bf7182017-03-03 14:09:56 +0000965 return( 0 );
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200966}
967#endif /* !MBEDTLS_AES_DECRYPT_ALT */
968
Gilles Peskine8db3efb2018-02-21 19:16:20 +0100969#if !defined(MBEDTLS_DEPRECATED_REMOVED)
Hanno Beckerbedc2052017-06-26 12:46:56 +0100970void mbedtls_aes_decrypt( mbedtls_aes_context *ctx,
971 const unsigned char input[16],
972 unsigned char output[16] )
973{
Mateusz Starzyk15a74202021-08-05 13:56:48 +0200974 MBEDTLS_IGNORE_RETURN( mbedtls_internal_aes_decrypt( ctx, input, output ) );
Hanno Beckerbedc2052017-06-26 12:46:56 +0100975}
Gilles Peskine8db3efb2018-02-21 19:16:20 +0100976#endif /* !MBEDTLS_DEPRECATED_REMOVED */
Hanno Beckerbedc2052017-06-26 12:46:56 +0100977
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +0200978/*
Paul Bakker5121ce52009-01-03 21:22:43 +0000979 * AES-ECB block encryption/decryption
980 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200981int mbedtls_aes_crypt_ecb( mbedtls_aes_context *ctx,
Manuel Pégourié-Gonnardeb6d3962018-12-18 09:59:35 +0100982 int mode,
983 const unsigned char input[16],
984 unsigned char output[16] )
Paul Bakker5121ce52009-01-03 21:22:43 +0000985{
Manuel Pégourié-Gonnard1aca2602018-12-12 12:56:55 +0100986 AES_VALIDATE_RET( ctx != NULL );
987 AES_VALIDATE_RET( input != NULL );
988 AES_VALIDATE_RET( output != NULL );
989 AES_VALIDATE_RET( mode == MBEDTLS_AES_ENCRYPT ||
990 mode == MBEDTLS_AES_DECRYPT );
991
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200992#if defined(MBEDTLS_AESNI_C) && defined(MBEDTLS_HAVE_X86_64)
Manuel Pégourié-Gonnardc730ed32015-06-02 10:38:50 +0100993 if( mbedtls_aesni_has_support( MBEDTLS_AESNI_AES ) )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200994 return( mbedtls_aesni_crypt_ecb( ctx, mode, input, output ) );
Manuel Pégourié-Gonnard5b685652013-12-18 11:45:21 +0100995#endif
996
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200997#if defined(MBEDTLS_PADLOCK_C) && defined(MBEDTLS_HAVE_X86)
Paul Bakker048d04e2012-02-12 17:31:04 +0000998 if( aes_padlock_ace )
Paul Bakker5121ce52009-01-03 21:22:43 +0000999 {
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001000 if( mbedtls_padlock_xcryptecb( ctx, mode, input, output ) == 0 )
Paul Bakkerf3ccc682010-03-18 21:21:02 +00001001 return( 0 );
1002
1003 // If padlock data misaligned, we just fall back to
1004 // unaccelerated mode
1005 //
Paul Bakker5121ce52009-01-03 21:22:43 +00001006 }
1007#endif
1008
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +02001009 if( mode == MBEDTLS_AES_ENCRYPT )
Andres AGf5bf7182017-03-03 14:09:56 +00001010 return( mbedtls_internal_aes_encrypt( ctx, input, output ) );
Manuel Pégourié-Gonnard31993f22015-05-12 15:41:08 +02001011 else
Andres AGf5bf7182017-03-03 14:09:56 +00001012 return( mbedtls_internal_aes_decrypt( ctx, input, output ) );
Paul Bakker5121ce52009-01-03 21:22:43 +00001013}
1014
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001015#if defined(MBEDTLS_CIPHER_MODE_CBC)
Paul Bakker5121ce52009-01-03 21:22:43 +00001016/*
1017 * AES-CBC buffer encryption/decryption
1018 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001019int mbedtls_aes_crypt_cbc( mbedtls_aes_context *ctx,
Paul Bakker5121ce52009-01-03 21:22:43 +00001020 int mode,
Paul Bakker23986e52011-04-24 08:57:21 +00001021 size_t length,
Paul Bakker5121ce52009-01-03 21:22:43 +00001022 unsigned char iv[16],
Paul Bakkerff60ee62010-03-16 21:09:09 +00001023 const unsigned char *input,
Paul Bakker5121ce52009-01-03 21:22:43 +00001024 unsigned char *output )
1025{
1026 int i;
Gilles Peskine377a3102021-07-07 21:08:28 +02001027 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Paul Bakker5121ce52009-01-03 21:22:43 +00001028 unsigned char temp[16];
1029
Manuel Pégourié-Gonnard3178d1a2018-12-12 13:05:00 +01001030 AES_VALIDATE_RET( ctx != NULL );
1031 AES_VALIDATE_RET( mode == MBEDTLS_AES_ENCRYPT ||
1032 mode == MBEDTLS_AES_DECRYPT );
1033 AES_VALIDATE_RET( iv != NULL );
1034 AES_VALIDATE_RET( input != NULL );
1035 AES_VALIDATE_RET( output != NULL );
1036
Paul Bakkerf3ccc682010-03-18 21:21:02 +00001037 if( length % 16 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001038 return( MBEDTLS_ERR_AES_INVALID_INPUT_LENGTH );
Paul Bakkerf3ccc682010-03-18 21:21:02 +00001039
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001040#if defined(MBEDTLS_PADLOCK_C) && defined(MBEDTLS_HAVE_X86)
Paul Bakker048d04e2012-02-12 17:31:04 +00001041 if( aes_padlock_ace )
Paul Bakker5121ce52009-01-03 21:22:43 +00001042 {
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001043 if( mbedtls_padlock_xcryptcbc( ctx, mode, length, iv, input, output ) == 0 )
Paul Bakkerf3ccc682010-03-18 21:21:02 +00001044 return( 0 );
Paul Bakker9af723c2014-05-01 13:03:14 +02001045
Paul Bakkerf3ccc682010-03-18 21:21:02 +00001046 // If padlock data misaligned, we just fall back to
1047 // unaccelerated mode
1048 //
Paul Bakker5121ce52009-01-03 21:22:43 +00001049 }
1050#endif
1051
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001052 if( mode == MBEDTLS_AES_DECRYPT )
Paul Bakker5121ce52009-01-03 21:22:43 +00001053 {
1054 while( length > 0 )
1055 {
1056 memcpy( temp, input, 16 );
Gilles Peskine377a3102021-07-07 21:08:28 +02001057 ret = mbedtls_aes_crypt_ecb( ctx, mode, input, output );
1058 if( ret != 0 )
1059 goto exit;
Paul Bakker5121ce52009-01-03 21:22:43 +00001060
1061 for( i = 0; i < 16; i++ )
1062 output[i] = (unsigned char)( output[i] ^ iv[i] );
1063
1064 memcpy( iv, temp, 16 );
1065
1066 input += 16;
1067 output += 16;
1068 length -= 16;
1069 }
1070 }
1071 else
1072 {
1073 while( length > 0 )
1074 {
1075 for( i = 0; i < 16; i++ )
1076 output[i] = (unsigned char)( input[i] ^ iv[i] );
1077
Gilles Peskine377a3102021-07-07 21:08:28 +02001078 ret = mbedtls_aes_crypt_ecb( ctx, mode, output, output );
1079 if( ret != 0 )
1080 goto exit;
Paul Bakker5121ce52009-01-03 21:22:43 +00001081 memcpy( iv, output, 16 );
1082
1083 input += 16;
1084 output += 16;
1085 length -= 16;
1086 }
1087 }
Gilles Peskine377a3102021-07-07 21:08:28 +02001088 ret = 0;
Paul Bakkerf3ccc682010-03-18 21:21:02 +00001089
Gilles Peskine377a3102021-07-07 21:08:28 +02001090exit:
1091 return( ret );
Paul Bakker5121ce52009-01-03 21:22:43 +00001092}
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001093#endif /* MBEDTLS_CIPHER_MODE_CBC */
Paul Bakker5121ce52009-01-03 21:22:43 +00001094
Aorimn5f778012016-06-09 23:22:58 +02001095#if defined(MBEDTLS_CIPHER_MODE_XTS)
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001096
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001097typedef unsigned char mbedtls_be128[16];
1098
1099/*
1100 * GF(2^128) multiplication function
1101 *
Jaeden Amero5f0b06a2018-05-31 09:23:32 +01001102 * This function multiplies a field element by x in the polynomial field
1103 * representation. It uses 64-bit word operations to gain speed but compensates
Shaun Case0e7791f2021-12-20 21:14:10 -08001104 * for machine endianness and hence works correctly on both big and little
Jaeden Amero5f0b06a2018-05-31 09:23:32 +01001105 * endian machines.
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001106 */
1107static void mbedtls_gf128mul_x_ble( unsigned char r[16],
Jaeden Amero8cfc75f2018-05-31 16:53:08 +01001108 const unsigned char x[16] )
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001109{
1110 uint64_t a, b, ra, rb;
1111
Joe Subbiani1bd5d7d2021-07-16 12:29:49 +01001112 a = MBEDTLS_GET_UINT64_LE( x, 0 );
1113 b = MBEDTLS_GET_UINT64_LE( x, 8 );
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001114
Jaeden Amero8cfc75f2018-05-31 16:53:08 +01001115 ra = ( a << 1 ) ^ 0x0087 >> ( 8 - ( ( b >> 63 ) << 3 ) );
1116 rb = ( a >> 63 ) | ( b << 1 );
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001117
Joe Subbiani1bd5d7d2021-07-16 12:29:49 +01001118 MBEDTLS_PUT_UINT64_LE( ra, r, 0 );
1119 MBEDTLS_PUT_UINT64_LE( rb, r, 8 );
Jaeden Amero010c2cb2018-05-29 17:00:47 +01001120}
1121
Aorimn5f778012016-06-09 23:22:58 +02001122/*
1123 * AES-XTS buffer encryption/decryption
1124 */
Jaeden Amero9366feb2018-05-29 18:55:17 +01001125int mbedtls_aes_crypt_xts( mbedtls_aes_xts_context *ctx,
1126 int mode,
Jaeden Amero5162b932018-05-29 12:55:24 +01001127 size_t length,
Jaeden Amerocd9fc5e2018-05-30 15:23:24 +01001128 const unsigned char data_unit[16],
Jaeden Amero9366feb2018-05-29 18:55:17 +01001129 const unsigned char *input,
1130 unsigned char *output )
Aorimn5f778012016-06-09 23:22:58 +02001131{
Janos Follath24eed8d2019-11-22 13:21:35 +00001132 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Jaeden Amerod82cd862018-04-28 15:02:45 +01001133 size_t blocks = length / 16;
1134 size_t leftover = length % 16;
1135 unsigned char tweak[16];
1136 unsigned char prev_tweak[16];
1137 unsigned char tmp[16];
Aorimn5f778012016-06-09 23:22:58 +02001138
Manuel Pégourié-Gonnard191af132018-12-13 10:15:30 +01001139 AES_VALIDATE_RET( ctx != NULL );
1140 AES_VALIDATE_RET( mode == MBEDTLS_AES_ENCRYPT ||
1141 mode == MBEDTLS_AES_DECRYPT );
Manuel Pégourié-Gonnard998a3582018-12-18 10:03:13 +01001142 AES_VALIDATE_RET( data_unit != NULL );
Manuel Pégourié-Gonnard191af132018-12-13 10:15:30 +01001143 AES_VALIDATE_RET( input != NULL );
1144 AES_VALIDATE_RET( output != NULL );
1145
Jaeden Amero8381fcb2018-10-11 12:06:15 +01001146 /* Data units must be at least 16 bytes long. */
Aorimn5f778012016-06-09 23:22:58 +02001147 if( length < 16 )
Jaeden Amerod82cd862018-04-28 15:02:45 +01001148 return MBEDTLS_ERR_AES_INVALID_INPUT_LENGTH;
Aorimn5f778012016-06-09 23:22:58 +02001149
Jaeden Ameroa74faba2018-10-11 12:07:43 +01001150 /* NIST SP 800-38E disallows data units larger than 2**20 blocks. */
Jaeden Amero0a8b0202018-05-30 15:36:06 +01001151 if( length > ( 1 << 20 ) * 16 )
1152 return MBEDTLS_ERR_AES_INVALID_INPUT_LENGTH;
Aorimn5f778012016-06-09 23:22:58 +02001153
Jaeden Amerod82cd862018-04-28 15:02:45 +01001154 /* Compute the tweak. */
Jaeden Amerocd9fc5e2018-05-30 15:23:24 +01001155 ret = mbedtls_aes_crypt_ecb( &ctx->tweak, MBEDTLS_AES_ENCRYPT,
1156 data_unit, tweak );
Jaeden Amerod82cd862018-04-28 15:02:45 +01001157 if( ret != 0 )
1158 return( ret );
Aorimn5f778012016-06-09 23:22:58 +02001159
Jaeden Amerod82cd862018-04-28 15:02:45 +01001160 while( blocks-- )
Aorimn5f778012016-06-09 23:22:58 +02001161 {
Jaeden Amerod82cd862018-04-28 15:02:45 +01001162 size_t i;
1163
1164 if( leftover && ( mode == MBEDTLS_AES_DECRYPT ) && blocks == 0 )
1165 {
1166 /* We are on the last block in a decrypt operation that has
1167 * leftover bytes, so we need to use the next tweak for this block,
1168 * and this tweak for the lefover bytes. Save the current tweak for
1169 * the leftovers and then update the current tweak for use on this,
1170 * the last full block. */
1171 memcpy( prev_tweak, tweak, sizeof( tweak ) );
1172 mbedtls_gf128mul_x_ble( tweak, tweak );
1173 }
1174
1175 for( i = 0; i < 16; i++ )
1176 tmp[i] = input[i] ^ tweak[i];
1177
1178 ret = mbedtls_aes_crypt_ecb( &ctx->crypt, mode, tmp, tmp );
1179 if( ret != 0 )
1180 return( ret );
1181
1182 for( i = 0; i < 16; i++ )
1183 output[i] = tmp[i] ^ tweak[i];
1184
1185 /* Update the tweak for the next block. */
1186 mbedtls_gf128mul_x_ble( tweak, tweak );
1187
1188 output += 16;
1189 input += 16;
Aorimn5f778012016-06-09 23:22:58 +02001190 }
1191
Jaeden Amerod82cd862018-04-28 15:02:45 +01001192 if( leftover )
Aorimn5f778012016-06-09 23:22:58 +02001193 {
Jaeden Amerod82cd862018-04-28 15:02:45 +01001194 /* If we are on the leftover bytes in a decrypt operation, we need to
1195 * use the previous tweak for these bytes (as saved in prev_tweak). */
1196 unsigned char *t = mode == MBEDTLS_AES_DECRYPT ? prev_tweak : tweak;
Aorimn5f778012016-06-09 23:22:58 +02001197
Jaeden Amerod82cd862018-04-28 15:02:45 +01001198 /* We are now on the final part of the data unit, which doesn't divide
1199 * evenly by 16. It's time for ciphertext stealing. */
1200 size_t i;
1201 unsigned char *prev_output = output - 16;
Aorimn5f778012016-06-09 23:22:58 +02001202
Jaeden Amerod82cd862018-04-28 15:02:45 +01001203 /* Copy ciphertext bytes from the previous block to our output for each
Shaun Case0e7791f2021-12-20 21:14:10 -08001204 * byte of ciphertext we won't steal. At the same time, copy the
Jaeden Amerod82cd862018-04-28 15:02:45 +01001205 * remainder of the input for this final round (since the loop bounds
1206 * are the same). */
1207 for( i = 0; i < leftover; i++ )
Aorimn5f778012016-06-09 23:22:58 +02001208 {
Jaeden Amerod82cd862018-04-28 15:02:45 +01001209 output[i] = prev_output[i];
1210 tmp[i] = input[i] ^ t[i];
Aorimn5f778012016-06-09 23:22:58 +02001211 }
Aorimn5f778012016-06-09 23:22:58 +02001212
Jaeden Amerod82cd862018-04-28 15:02:45 +01001213 /* Copy ciphertext bytes from the previous block for input in this
1214 * round. */
1215 for( ; i < 16; i++ )
1216 tmp[i] = prev_output[i] ^ t[i];
Aorimn5f778012016-06-09 23:22:58 +02001217
Jaeden Amerod82cd862018-04-28 15:02:45 +01001218 ret = mbedtls_aes_crypt_ecb( &ctx->crypt, mode, tmp, tmp );
1219 if( ret != 0 )
1220 return ret;
Aorimn5f778012016-06-09 23:22:58 +02001221
Jaeden Amerod82cd862018-04-28 15:02:45 +01001222 /* Write the result back to the previous block, overriding the previous
1223 * output we copied. */
1224 for( i = 0; i < 16; i++ )
1225 prev_output[i] = tmp[i] ^ t[i];
Aorimn5f778012016-06-09 23:22:58 +02001226 }
1227
1228 return( 0 );
1229}
1230#endif /* MBEDTLS_CIPHER_MODE_XTS */
1231
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001232#if defined(MBEDTLS_CIPHER_MODE_CFB)
Paul Bakker5121ce52009-01-03 21:22:43 +00001233/*
1234 * AES-CFB128 buffer encryption/decryption
1235 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001236int mbedtls_aes_crypt_cfb128( mbedtls_aes_context *ctx,
Paul Bakker5121ce52009-01-03 21:22:43 +00001237 int mode,
Paul Bakker23986e52011-04-24 08:57:21 +00001238 size_t length,
Paul Bakker27fdf462011-06-09 13:55:13 +00001239 size_t *iv_off,
Paul Bakker5121ce52009-01-03 21:22:43 +00001240 unsigned char iv[16],
Paul Bakkerff60ee62010-03-16 21:09:09 +00001241 const unsigned char *input,
Paul Bakker5121ce52009-01-03 21:22:43 +00001242 unsigned char *output )
1243{
Paul Bakker27fdf462011-06-09 13:55:13 +00001244 int c;
Gilles Peskine377a3102021-07-07 21:08:28 +02001245 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Manuel Pégourié-Gonnard1677cca2018-12-13 10:27:13 +01001246 size_t n;
1247
1248 AES_VALIDATE_RET( ctx != NULL );
1249 AES_VALIDATE_RET( mode == MBEDTLS_AES_ENCRYPT ||
1250 mode == MBEDTLS_AES_DECRYPT );
1251 AES_VALIDATE_RET( iv_off != NULL );
1252 AES_VALIDATE_RET( iv != NULL );
1253 AES_VALIDATE_RET( input != NULL );
1254 AES_VALIDATE_RET( output != NULL );
1255
1256 n = *iv_off;
Paul Bakker5121ce52009-01-03 21:22:43 +00001257
Manuel Pégourié-Gonnarde55e1032018-12-18 12:09:02 +01001258 if( n > 15 )
Manuel Pégourié-Gonnard5b89c092018-12-18 10:03:30 +01001259 return( MBEDTLS_ERR_AES_BAD_INPUT_DATA );
1260
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001261 if( mode == MBEDTLS_AES_DECRYPT )
Paul Bakker5121ce52009-01-03 21:22:43 +00001262 {
1263 while( length-- )
1264 {
1265 if( n == 0 )
Gilles Peskine377a3102021-07-07 21:08:28 +02001266 {
1267 ret = mbedtls_aes_crypt_ecb( ctx, MBEDTLS_AES_ENCRYPT, iv, iv );
1268 if( ret != 0 )
1269 goto exit;
1270 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001271
1272 c = *input++;
1273 *output++ = (unsigned char)( c ^ iv[n] );
1274 iv[n] = (unsigned char) c;
1275
Paul Bakker66d5d072014-06-17 16:39:18 +02001276 n = ( n + 1 ) & 0x0F;
Paul Bakker5121ce52009-01-03 21:22:43 +00001277 }
1278 }
1279 else
1280 {
1281 while( length-- )
1282 {
1283 if( n == 0 )
Gilles Peskine377a3102021-07-07 21:08:28 +02001284 {
1285 ret = mbedtls_aes_crypt_ecb( ctx, MBEDTLS_AES_ENCRYPT, iv, iv );
1286 if( ret != 0 )
1287 goto exit;
1288 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001289
1290 iv[n] = *output++ = (unsigned char)( iv[n] ^ *input++ );
1291
Paul Bakker66d5d072014-06-17 16:39:18 +02001292 n = ( n + 1 ) & 0x0F;
Paul Bakker5121ce52009-01-03 21:22:43 +00001293 }
1294 }
1295
1296 *iv_off = n;
Gilles Peskine377a3102021-07-07 21:08:28 +02001297 ret = 0;
Paul Bakkerf3ccc682010-03-18 21:21:02 +00001298
Gilles Peskine377a3102021-07-07 21:08:28 +02001299exit:
1300 return( ret );
Paul Bakker5121ce52009-01-03 21:22:43 +00001301}
Paul Bakker556efba2014-01-24 15:38:12 +01001302
1303/*
1304 * AES-CFB8 buffer encryption/decryption
1305 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001306int mbedtls_aes_crypt_cfb8( mbedtls_aes_context *ctx,
Manuel Pégourié-Gonnardeb6d3962018-12-18 09:59:35 +01001307 int mode,
1308 size_t length,
1309 unsigned char iv[16],
1310 const unsigned char *input,
1311 unsigned char *output )
Paul Bakker556efba2014-01-24 15:38:12 +01001312{
Gilles Peskine377a3102021-07-07 21:08:28 +02001313 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Paul Bakker556efba2014-01-24 15:38:12 +01001314 unsigned char c;
1315 unsigned char ov[17];
1316
Manuel Pégourié-Gonnard1677cca2018-12-13 10:27:13 +01001317 AES_VALIDATE_RET( ctx != NULL );
1318 AES_VALIDATE_RET( mode == MBEDTLS_AES_ENCRYPT ||
1319 mode == MBEDTLS_AES_DECRYPT );
1320 AES_VALIDATE_RET( iv != NULL );
1321 AES_VALIDATE_RET( input != NULL );
1322 AES_VALIDATE_RET( output != NULL );
Paul Bakker556efba2014-01-24 15:38:12 +01001323 while( length-- )
1324 {
Paul Bakker66d5d072014-06-17 16:39:18 +02001325 memcpy( ov, iv, 16 );
Gilles Peskine377a3102021-07-07 21:08:28 +02001326 ret = mbedtls_aes_crypt_ecb( ctx, MBEDTLS_AES_ENCRYPT, iv, iv );
1327 if( ret != 0 )
1328 goto exit;
Paul Bakker556efba2014-01-24 15:38:12 +01001329
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001330 if( mode == MBEDTLS_AES_DECRYPT )
Paul Bakker556efba2014-01-24 15:38:12 +01001331 ov[16] = *input;
1332
1333 c = *output++ = (unsigned char)( iv[0] ^ *input++ );
1334
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001335 if( mode == MBEDTLS_AES_ENCRYPT )
Paul Bakker556efba2014-01-24 15:38:12 +01001336 ov[16] = c;
1337
Paul Bakker66d5d072014-06-17 16:39:18 +02001338 memcpy( iv, ov + 1, 16 );
Paul Bakker556efba2014-01-24 15:38:12 +01001339 }
Gilles Peskine377a3102021-07-07 21:08:28 +02001340 ret = 0;
Paul Bakker556efba2014-01-24 15:38:12 +01001341
Gilles Peskine377a3102021-07-07 21:08:28 +02001342exit:
1343 return( ret );
Paul Bakker556efba2014-01-24 15:38:12 +01001344}
Simon Butcher76a5b222018-04-22 22:57:27 +01001345#endif /* MBEDTLS_CIPHER_MODE_CFB */
1346
1347#if defined(MBEDTLS_CIPHER_MODE_OFB)
1348/*
1349 * AES-OFB (Output Feedback Mode) buffer encryption/decryption
1350 */
1351int mbedtls_aes_crypt_ofb( mbedtls_aes_context *ctx,
Simon Butcher00131442018-05-22 22:40:36 +01001352 size_t length,
1353 size_t *iv_off,
1354 unsigned char iv[16],
1355 const unsigned char *input,
1356 unsigned char *output )
Simon Butcher76a5b222018-04-22 22:57:27 +01001357{
Simon Butcherad4e4932018-04-29 00:43:47 +01001358 int ret = 0;
Manuel Pégourié-Gonnard8e41eb72018-12-13 11:00:56 +01001359 size_t n;
1360
1361 AES_VALIDATE_RET( ctx != NULL );
1362 AES_VALIDATE_RET( iv_off != NULL );
1363 AES_VALIDATE_RET( iv != NULL );
1364 AES_VALIDATE_RET( input != NULL );
1365 AES_VALIDATE_RET( output != NULL );
1366
1367 n = *iv_off;
Simon Butcher76a5b222018-04-22 22:57:27 +01001368
Manuel Pégourié-Gonnarde55e1032018-12-18 12:09:02 +01001369 if( n > 15 )
Manuel Pégourié-Gonnard5b89c092018-12-18 10:03:30 +01001370 return( MBEDTLS_ERR_AES_BAD_INPUT_DATA );
1371
Simon Butcher76a5b222018-04-22 22:57:27 +01001372 while( length-- )
1373 {
1374 if( n == 0 )
Simon Butcherad4e4932018-04-29 00:43:47 +01001375 {
1376 ret = mbedtls_aes_crypt_ecb( ctx, MBEDTLS_AES_ENCRYPT, iv, iv );
1377 if( ret != 0 )
1378 goto exit;
1379 }
Simon Butcher76a5b222018-04-22 22:57:27 +01001380 *output++ = *input++ ^ iv[n];
1381
1382 n = ( n + 1 ) & 0x0F;
1383 }
1384
1385 *iv_off = n;
1386
Simon Butcherad4e4932018-04-29 00:43:47 +01001387exit:
1388 return( ret );
Simon Butcher76a5b222018-04-22 22:57:27 +01001389}
1390#endif /* MBEDTLS_CIPHER_MODE_OFB */
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001391
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001392#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001393/*
1394 * AES-CTR buffer encryption/decryption
1395 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001396int mbedtls_aes_crypt_ctr( mbedtls_aes_context *ctx,
Paul Bakker27fdf462011-06-09 13:55:13 +00001397 size_t length,
1398 size_t *nc_off,
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001399 unsigned char nonce_counter[16],
1400 unsigned char stream_block[16],
1401 const unsigned char *input,
1402 unsigned char *output )
1403{
Paul Bakker369e14b2012-04-18 14:16:09 +00001404 int c, i;
Gilles Peskine377a3102021-07-07 21:08:28 +02001405 int ret = MBEDTLS_ERR_ERROR_CORRUPTION_DETECTED;
Manuel Pégourié-Gonnard2bc535b2018-12-13 11:08:36 +01001406 size_t n;
1407
1408 AES_VALIDATE_RET( ctx != NULL );
1409 AES_VALIDATE_RET( nc_off != NULL );
1410 AES_VALIDATE_RET( nonce_counter != NULL );
1411 AES_VALIDATE_RET( stream_block != NULL );
1412 AES_VALIDATE_RET( input != NULL );
1413 AES_VALIDATE_RET( output != NULL );
1414
1415 n = *nc_off;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001416
Mohammad Azim Khan3f7f8172017-11-23 17:49:05 +00001417 if ( n > 0x0F )
1418 return( MBEDTLS_ERR_AES_BAD_INPUT_DATA );
1419
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001420 while( length-- )
1421 {
1422 if( n == 0 ) {
Gilles Peskine377a3102021-07-07 21:08:28 +02001423 ret = mbedtls_aes_crypt_ecb( ctx, MBEDTLS_AES_ENCRYPT, nonce_counter, stream_block );
1424 if( ret != 0 )
1425 goto exit;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001426
Paul Bakker369e14b2012-04-18 14:16:09 +00001427 for( i = 16; i > 0; i-- )
1428 if( ++nonce_counter[i - 1] != 0 )
1429 break;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001430 }
1431 c = *input++;
1432 *output++ = (unsigned char)( c ^ stream_block[n] );
1433
Paul Bakker66d5d072014-06-17 16:39:18 +02001434 n = ( n + 1 ) & 0x0F;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001435 }
1436
1437 *nc_off = n;
Gilles Peskine377a3102021-07-07 21:08:28 +02001438 ret = 0;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001439
Gilles Peskine377a3102021-07-07 21:08:28 +02001440exit:
1441 return( ret );
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001442}
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001443#endif /* MBEDTLS_CIPHER_MODE_CTR */
Manuel Pégourié-Gonnard1ec220b2014-03-10 11:20:17 +01001444
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001445#endif /* !MBEDTLS_AES_ALT */
Paul Bakker5121ce52009-01-03 21:22:43 +00001446
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001447#if defined(MBEDTLS_SELF_TEST)
Paul Bakker5121ce52009-01-03 21:22:43 +00001448/*
1449 * AES test vectors from:
1450 *
1451 * http://csrc.nist.gov/archive/aes/rijndael/rijndael-vals.zip
1452 */
1453static const unsigned char aes_test_ecb_dec[3][16] =
1454{
1455 { 0x44, 0x41, 0x6A, 0xC2, 0xD1, 0xF5, 0x3C, 0x58,
1456 0x33, 0x03, 0x91, 0x7E, 0x6B, 0xE9, 0xEB, 0xE0 },
1457 { 0x48, 0xE3, 0x1E, 0x9E, 0x25, 0x67, 0x18, 0xF2,
1458 0x92, 0x29, 0x31, 0x9C, 0x19, 0xF1, 0x5B, 0xA4 },
1459 { 0x05, 0x8C, 0xCF, 0xFD, 0xBB, 0xCB, 0x38, 0x2D,
1460 0x1F, 0x6F, 0x56, 0x58, 0x5D, 0x8A, 0x4A, 0xDE }
1461};
1462
1463static const unsigned char aes_test_ecb_enc[3][16] =
1464{
1465 { 0xC3, 0x4C, 0x05, 0x2C, 0xC0, 0xDA, 0x8D, 0x73,
1466 0x45, 0x1A, 0xFE, 0x5F, 0x03, 0xBE, 0x29, 0x7F },
1467 { 0xF3, 0xF6, 0x75, 0x2A, 0xE8, 0xD7, 0x83, 0x11,
1468 0x38, 0xF0, 0x41, 0x56, 0x06, 0x31, 0xB1, 0x14 },
1469 { 0x8B, 0x79, 0xEE, 0xCC, 0x93, 0xA0, 0xEE, 0x5D,
1470 0xFF, 0x30, 0xB4, 0xEA, 0x21, 0x63, 0x6D, 0xA4 }
1471};
1472
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001473#if defined(MBEDTLS_CIPHER_MODE_CBC)
Paul Bakker5121ce52009-01-03 21:22:43 +00001474static const unsigned char aes_test_cbc_dec[3][16] =
1475{
1476 { 0xFA, 0xCA, 0x37, 0xE0, 0xB0, 0xC8, 0x53, 0x73,
1477 0xDF, 0x70, 0x6E, 0x73, 0xF7, 0xC9, 0xAF, 0x86 },
1478 { 0x5D, 0xF6, 0x78, 0xDD, 0x17, 0xBA, 0x4E, 0x75,
1479 0xB6, 0x17, 0x68, 0xC6, 0xAD, 0xEF, 0x7C, 0x7B },
1480 { 0x48, 0x04, 0xE1, 0x81, 0x8F, 0xE6, 0x29, 0x75,
1481 0x19, 0xA3, 0xE8, 0x8C, 0x57, 0x31, 0x04, 0x13 }
1482};
1483
1484static const unsigned char aes_test_cbc_enc[3][16] =
1485{
1486 { 0x8A, 0x05, 0xFC, 0x5E, 0x09, 0x5A, 0xF4, 0x84,
1487 0x8A, 0x08, 0xD3, 0x28, 0xD3, 0x68, 0x8E, 0x3D },
1488 { 0x7B, 0xD9, 0x66, 0xD5, 0x3A, 0xD8, 0xC1, 0xBB,
1489 0x85, 0xD2, 0xAD, 0xFA, 0xE8, 0x7B, 0xB1, 0x04 },
1490 { 0xFE, 0x3C, 0x53, 0x65, 0x3E, 0x2F, 0x45, 0xB5,
1491 0x6F, 0xCD, 0x88, 0xB2, 0xCC, 0x89, 0x8F, 0xF0 }
1492};
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001493#endif /* MBEDTLS_CIPHER_MODE_CBC */
Paul Bakker5121ce52009-01-03 21:22:43 +00001494
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001495#if defined(MBEDTLS_CIPHER_MODE_CFB)
Paul Bakker5121ce52009-01-03 21:22:43 +00001496/*
1497 * AES-CFB128 test vectors from:
1498 *
1499 * http://csrc.nist.gov/publications/nistpubs/800-38a/sp800-38a.pdf
1500 */
1501static const unsigned char aes_test_cfb128_key[3][32] =
1502{
1503 { 0x2B, 0x7E, 0x15, 0x16, 0x28, 0xAE, 0xD2, 0xA6,
1504 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3C },
1505 { 0x8E, 0x73, 0xB0, 0xF7, 0xDA, 0x0E, 0x64, 0x52,
1506 0xC8, 0x10, 0xF3, 0x2B, 0x80, 0x90, 0x79, 0xE5,
1507 0x62, 0xF8, 0xEA, 0xD2, 0x52, 0x2C, 0x6B, 0x7B },
1508 { 0x60, 0x3D, 0xEB, 0x10, 0x15, 0xCA, 0x71, 0xBE,
1509 0x2B, 0x73, 0xAE, 0xF0, 0x85, 0x7D, 0x77, 0x81,
1510 0x1F, 0x35, 0x2C, 0x07, 0x3B, 0x61, 0x08, 0xD7,
1511 0x2D, 0x98, 0x10, 0xA3, 0x09, 0x14, 0xDF, 0xF4 }
1512};
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
1532static const unsigned char aes_test_cfb128_ct[3][64] =
1533{
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 },
1542 { 0xCD, 0xC8, 0x0D, 0x6F, 0xDD, 0xF1, 0x8C, 0xAB,
1543 0x34, 0xC2, 0x59, 0x09, 0xC9, 0x9A, 0x41, 0x74,
1544 0x67, 0xCE, 0x7F, 0x7F, 0x81, 0x17, 0x36, 0x21,
1545 0x96, 0x1A, 0x2B, 0x70, 0x17, 0x1D, 0x3D, 0x7A,
1546 0x2E, 0x1E, 0x8A, 0x1D, 0xD5, 0x9B, 0x88, 0xB1,
1547 0xC8, 0xE6, 0x0F, 0xED, 0x1E, 0xFA, 0xC4, 0xC9,
1548 0xC0, 0x5F, 0x9F, 0x9C, 0xA9, 0x83, 0x4F, 0xA0,
1549 0x42, 0xAE, 0x8F, 0xBA, 0x58, 0x4B, 0x09, 0xFF },
1550 { 0xDC, 0x7E, 0x84, 0xBF, 0xDA, 0x79, 0x16, 0x4B,
1551 0x7E, 0xCD, 0x84, 0x86, 0x98, 0x5D, 0x38, 0x60,
1552 0x39, 0xFF, 0xED, 0x14, 0x3B, 0x28, 0xB1, 0xC8,
1553 0x32, 0x11, 0x3C, 0x63, 0x31, 0xE5, 0x40, 0x7B,
1554 0xDF, 0x10, 0x13, 0x24, 0x15, 0xE5, 0x4B, 0x92,
1555 0xA1, 0x3E, 0xD0, 0xA8, 0x26, 0x7A, 0xE2, 0xF9,
1556 0x75, 0xA3, 0x85, 0x74, 0x1A, 0xB9, 0xCE, 0xF8,
1557 0x20, 0x31, 0x62, 0x3D, 0x55, 0xB1, 0xE4, 0x71 }
1558};
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001559#endif /* MBEDTLS_CIPHER_MODE_CFB */
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001560
Simon Butcherad4e4932018-04-29 00:43:47 +01001561#if defined(MBEDTLS_CIPHER_MODE_OFB)
1562/*
1563 * AES-OFB test vectors from:
1564 *
Simon Butcher5db13622018-06-04 22:11:25 +01001565 * https://csrc.nist.gov/publications/detail/sp/800-38a/final
Simon Butcherad4e4932018-04-29 00:43:47 +01001566 */
1567static const unsigned char aes_test_ofb_key[3][32] =
1568{
1569 { 0x2B, 0x7E, 0x15, 0x16, 0x28, 0xAE, 0xD2, 0xA6,
1570 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3C },
1571 { 0x8E, 0x73, 0xB0, 0xF7, 0xDA, 0x0E, 0x64, 0x52,
1572 0xC8, 0x10, 0xF3, 0x2B, 0x80, 0x90, 0x79, 0xE5,
1573 0x62, 0xF8, 0xEA, 0xD2, 0x52, 0x2C, 0x6B, 0x7B },
1574 { 0x60, 0x3D, 0xEB, 0x10, 0x15, 0xCA, 0x71, 0xBE,
1575 0x2B, 0x73, 0xAE, 0xF0, 0x85, 0x7D, 0x77, 0x81,
1576 0x1F, 0x35, 0x2C, 0x07, 0x3B, 0x61, 0x08, 0xD7,
1577 0x2D, 0x98, 0x10, 0xA3, 0x09, 0x14, 0xDF, 0xF4 }
1578};
1579
1580static const unsigned char aes_test_ofb_iv[16] =
1581{
1582 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
1583 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F
1584};
1585
1586static const unsigned char aes_test_ofb_pt[64] =
1587{
1588 0x6B, 0xC1, 0xBE, 0xE2, 0x2E, 0x40, 0x9F, 0x96,
1589 0xE9, 0x3D, 0x7E, 0x11, 0x73, 0x93, 0x17, 0x2A,
1590 0xAE, 0x2D, 0x8A, 0x57, 0x1E, 0x03, 0xAC, 0x9C,
1591 0x9E, 0xB7, 0x6F, 0xAC, 0x45, 0xAF, 0x8E, 0x51,
1592 0x30, 0xC8, 0x1C, 0x46, 0xA3, 0x5C, 0xE4, 0x11,
1593 0xE5, 0xFB, 0xC1, 0x19, 0x1A, 0x0A, 0x52, 0xEF,
1594 0xF6, 0x9F, 0x24, 0x45, 0xDF, 0x4F, 0x9B, 0x17,
1595 0xAD, 0x2B, 0x41, 0x7B, 0xE6, 0x6C, 0x37, 0x10
1596};
1597
1598static const unsigned char aes_test_ofb_ct[3][64] =
1599{
1600 { 0x3B, 0x3F, 0xD9, 0x2E, 0xB7, 0x2D, 0xAD, 0x20,
1601 0x33, 0x34, 0x49, 0xF8, 0xE8, 0x3C, 0xFB, 0x4A,
1602 0x77, 0x89, 0x50, 0x8d, 0x16, 0x91, 0x8f, 0x03,
1603 0xf5, 0x3c, 0x52, 0xda, 0xc5, 0x4e, 0xd8, 0x25,
1604 0x97, 0x40, 0x05, 0x1e, 0x9c, 0x5f, 0xec, 0xf6,
1605 0x43, 0x44, 0xf7, 0xa8, 0x22, 0x60, 0xed, 0xcc,
1606 0x30, 0x4c, 0x65, 0x28, 0xf6, 0x59, 0xc7, 0x78,
1607 0x66, 0xa5, 0x10, 0xd9, 0xc1, 0xd6, 0xae, 0x5e },
1608 { 0xCD, 0xC8, 0x0D, 0x6F, 0xDD, 0xF1, 0x8C, 0xAB,
1609 0x34, 0xC2, 0x59, 0x09, 0xC9, 0x9A, 0x41, 0x74,
1610 0xfc, 0xc2, 0x8b, 0x8d, 0x4c, 0x63, 0x83, 0x7c,
1611 0x09, 0xe8, 0x17, 0x00, 0xc1, 0x10, 0x04, 0x01,
1612 0x8d, 0x9a, 0x9a, 0xea, 0xc0, 0xf6, 0x59, 0x6f,
1613 0x55, 0x9c, 0x6d, 0x4d, 0xaf, 0x59, 0xa5, 0xf2,
1614 0x6d, 0x9f, 0x20, 0x08, 0x57, 0xca, 0x6c, 0x3e,
1615 0x9c, 0xac, 0x52, 0x4b, 0xd9, 0xac, 0xc9, 0x2a },
1616 { 0xDC, 0x7E, 0x84, 0xBF, 0xDA, 0x79, 0x16, 0x4B,
1617 0x7E, 0xCD, 0x84, 0x86, 0x98, 0x5D, 0x38, 0x60,
1618 0x4f, 0xeb, 0xdc, 0x67, 0x40, 0xd2, 0x0b, 0x3a,
1619 0xc8, 0x8f, 0x6a, 0xd8, 0x2a, 0x4f, 0xb0, 0x8d,
1620 0x71, 0xab, 0x47, 0xa0, 0x86, 0xe8, 0x6e, 0xed,
1621 0xf3, 0x9d, 0x1c, 0x5b, 0xba, 0x97, 0xc4, 0x08,
1622 0x01, 0x26, 0x14, 0x1d, 0x67, 0xf3, 0x7b, 0xe8,
1623 0x53, 0x8f, 0x5a, 0x8b, 0xe7, 0x40, 0xe4, 0x84 }
1624};
1625#endif /* MBEDTLS_CIPHER_MODE_OFB */
1626
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001627#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001628/*
1629 * AES-CTR test vectors from:
1630 *
1631 * http://www.faqs.org/rfcs/rfc3686.html
1632 */
1633
1634static const unsigned char aes_test_ctr_key[3][16] =
1635{
1636 { 0xAE, 0x68, 0x52, 0xF8, 0x12, 0x10, 0x67, 0xCC,
1637 0x4B, 0xF7, 0xA5, 0x76, 0x55, 0x77, 0xF3, 0x9E },
1638 { 0x7E, 0x24, 0x06, 0x78, 0x17, 0xFA, 0xE0, 0xD7,
1639 0x43, 0xD6, 0xCE, 0x1F, 0x32, 0x53, 0x91, 0x63 },
1640 { 0x76, 0x91, 0xBE, 0x03, 0x5E, 0x50, 0x20, 0xA8,
1641 0xAC, 0x6E, 0x61, 0x85, 0x29, 0xF9, 0xA0, 0xDC }
1642};
1643
1644static const unsigned char aes_test_ctr_nonce_counter[3][16] =
1645{
1646 { 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00,
1647 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01 },
1648 { 0x00, 0x6C, 0xB6, 0xDB, 0xC0, 0x54, 0x3B, 0x59,
1649 0xDA, 0x48, 0xD9, 0x0B, 0x00, 0x00, 0x00, 0x01 },
1650 { 0x00, 0xE0, 0x01, 0x7B, 0x27, 0x77, 0x7F, 0x3F,
1651 0x4A, 0x17, 0x86, 0xF0, 0x00, 0x00, 0x00, 0x01 }
1652};
1653
1654static const unsigned char aes_test_ctr_pt[3][48] =
1655{
1656 { 0x53, 0x69, 0x6E, 0x67, 0x6C, 0x65, 0x20, 0x62,
1657 0x6C, 0x6F, 0x63, 0x6B, 0x20, 0x6D, 0x73, 0x67 },
1658
1659 { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
1660 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,
1661 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
1662 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F },
1663
1664 { 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 0x20, 0x21, 0x22, 0x23 }
1669};
1670
1671static const unsigned char aes_test_ctr_ct[3][48] =
1672{
1673 { 0xE4, 0x09, 0x5D, 0x4F, 0xB7, 0xA7, 0xB3, 0x79,
1674 0x2D, 0x61, 0x75, 0xA3, 0x26, 0x13, 0x11, 0xB8 },
1675 { 0x51, 0x04, 0xA1, 0x06, 0x16, 0x8A, 0x72, 0xD9,
1676 0x79, 0x0D, 0x41, 0xEE, 0x8E, 0xDA, 0xD3, 0x88,
1677 0xEB, 0x2E, 0x1E, 0xFC, 0x46, 0xDA, 0x57, 0xC8,
1678 0xFC, 0xE6, 0x30, 0xDF, 0x91, 0x41, 0xBE, 0x28 },
1679 { 0xC1, 0xCF, 0x48, 0xA8, 0x9F, 0x2F, 0xFD, 0xD9,
1680 0xCF, 0x46, 0x52, 0xE9, 0xEF, 0xDB, 0x72, 0xD7,
1681 0x45, 0x40, 0xA4, 0x2B, 0xDE, 0x6D, 0x78, 0x36,
1682 0xD5, 0x9A, 0x5C, 0xEA, 0xAE, 0xF3, 0x10, 0x53,
1683 0x25, 0xB2, 0x07, 0x2F }
1684};
1685
1686static const int aes_test_ctr_len[3] =
1687 { 16, 32, 36 };
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001688#endif /* MBEDTLS_CIPHER_MODE_CTR */
Paul Bakker5121ce52009-01-03 21:22:43 +00001689
Jaeden Amero21d79cf2018-05-23 10:30:18 +01001690#if defined(MBEDTLS_CIPHER_MODE_XTS)
1691/*
1692 * AES-XTS test vectors from:
1693 *
1694 * IEEE P1619/D16 Annex B
1695 * https://web.archive.org/web/20150629024421/http://grouper.ieee.org/groups/1619/email/pdf00086.pdf
1696 * (Archived from original at http://grouper.ieee.org/groups/1619/email/pdf00086.pdf)
1697 */
1698static const unsigned char aes_test_xts_key[][32] =
1699{
1700 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1701 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1702 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1703 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
1704 { 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11,
1705 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11,
1706 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22,
1707 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22 },
1708 { 0xff, 0xfe, 0xfd, 0xfc, 0xfb, 0xfa, 0xf9, 0xf8,
1709 0xf7, 0xf6, 0xf5, 0xf4, 0xf3, 0xf2, 0xf1, 0xf0,
1710 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22,
1711 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22 },
1712};
1713
1714static const unsigned char aes_test_xts_pt32[][32] =
1715{
1716 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1717 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1718 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1719 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
1720 { 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44,
1721 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44,
1722 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44,
1723 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44 },
1724 { 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44, 0x44,
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};
1729
1730static const unsigned char aes_test_xts_ct32[][32] =
1731{
1732 { 0x91, 0x7c, 0xf6, 0x9e, 0xbd, 0x68, 0xb2, 0xec,
1733 0x9b, 0x9f, 0xe9, 0xa3, 0xea, 0xdd, 0xa6, 0x92,
1734 0xcd, 0x43, 0xd2, 0xf5, 0x95, 0x98, 0xed, 0x85,
1735 0x8c, 0x02, 0xc2, 0x65, 0x2f, 0xbf, 0x92, 0x2e },
1736 { 0xc4, 0x54, 0x18, 0x5e, 0x6a, 0x16, 0x93, 0x6e,
1737 0x39, 0x33, 0x40, 0x38, 0xac, 0xef, 0x83, 0x8b,
1738 0xfb, 0x18, 0x6f, 0xff, 0x74, 0x80, 0xad, 0xc4,
1739 0x28, 0x93, 0x82, 0xec, 0xd6, 0xd3, 0x94, 0xf0 },
1740 { 0xaf, 0x85, 0x33, 0x6b, 0x59, 0x7a, 0xfc, 0x1a,
1741 0x90, 0x0b, 0x2e, 0xb2, 0x1e, 0xc9, 0x49, 0xd2,
1742 0x92, 0xdf, 0x4c, 0x04, 0x7e, 0x0b, 0x21, 0x53,
1743 0x21, 0x86, 0xa5, 0x97, 0x1a, 0x22, 0x7a, 0x89 },
1744};
1745
1746static const unsigned char aes_test_xts_data_unit[][16] =
1747{
1748 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1749 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
1750 { 0x33, 0x33, 0x33, 0x33, 0x33, 0x00, 0x00, 0x00,
1751 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
1752 { 0x33, 0x33, 0x33, 0x33, 0x33, 0x00, 0x00, 0x00,
1753 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
1754};
1755
1756#endif /* MBEDTLS_CIPHER_MODE_XTS */
1757
Paul Bakker5121ce52009-01-03 21:22:43 +00001758/*
1759 * Checkup routine
1760 */
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001761int mbedtls_aes_self_test( int verbose )
Paul Bakker5121ce52009-01-03 21:22:43 +00001762{
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001763 int ret = 0, i, j, u, mode;
1764 unsigned int keybits;
Paul Bakker5121ce52009-01-03 21:22:43 +00001765 unsigned char key[32];
1766 unsigned char buf[64];
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001767 const unsigned char *aes_tests;
Jussi Kivilinna4b541be2016-06-22 18:48:16 +03001768#if defined(MBEDTLS_CIPHER_MODE_CBC) || defined(MBEDTLS_CIPHER_MODE_CFB)
Paul Bakker5121ce52009-01-03 21:22:43 +00001769 unsigned char iv[16];
Jussi Kivilinna4b541be2016-06-22 18:48:16 +03001770#endif
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001771#if defined(MBEDTLS_CIPHER_MODE_CBC)
Manuel Pégourié-Gonnard92cb1d32013-09-13 16:24:20 +02001772 unsigned char prv[16];
1773#endif
Simon Butcher2ff0e522018-06-14 09:57:07 +01001774#if defined(MBEDTLS_CIPHER_MODE_CTR) || defined(MBEDTLS_CIPHER_MODE_CFB) || \
1775 defined(MBEDTLS_CIPHER_MODE_OFB)
Paul Bakker27fdf462011-06-09 13:55:13 +00001776 size_t offset;
Paul Bakkere91d01e2011-04-19 15:55:50 +00001777#endif
Simon Butcher66a89032018-06-15 18:20:29 +01001778#if defined(MBEDTLS_CIPHER_MODE_CTR) || defined(MBEDTLS_CIPHER_MODE_XTS)
Paul Bakkere91d01e2011-04-19 15:55:50 +00001779 int len;
Simon Butcher66a89032018-06-15 18:20:29 +01001780#endif
1781#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001782 unsigned char nonce_counter[16];
1783 unsigned char stream_block[16];
1784#endif
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001785 mbedtls_aes_context ctx;
Paul Bakker5121ce52009-01-03 21:22:43 +00001786
1787 memset( key, 0, 32 );
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001788 mbedtls_aes_init( &ctx );
Paul Bakker5121ce52009-01-03 21:22:43 +00001789
1790 /*
1791 * ECB mode
1792 */
1793 for( i = 0; i < 6; i++ )
1794 {
1795 u = i >> 1;
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001796 keybits = 128 + u * 64;
1797 mode = i & 1;
Paul Bakker5121ce52009-01-03 21:22:43 +00001798
1799 if( verbose != 0 )
Kenneth Soerensen518d4352020-04-01 17:22:45 +02001800 mbedtls_printf( " AES-ECB-%3u (%s): ", keybits,
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001801 ( mode == MBEDTLS_AES_DECRYPT ) ? "dec" : "enc" );
Paul Bakker5121ce52009-01-03 21:22:43 +00001802
1803 memset( buf, 0, 16 );
1804
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001805 if( mode == MBEDTLS_AES_DECRYPT )
Paul Bakker5121ce52009-01-03 21:22:43 +00001806 {
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001807 ret = mbedtls_aes_setkey_dec( &ctx, key, keybits );
1808 aes_tests = aes_test_ecb_dec[u];
Paul Bakker5121ce52009-01-03 21:22:43 +00001809 }
1810 else
1811 {
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001812 ret = mbedtls_aes_setkey_enc( &ctx, key, keybits );
1813 aes_tests = aes_test_ecb_enc[u];
1814 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001815
Andres Amaya Garciad3e7e7d2017-06-15 16:17:46 +01001816 /*
1817 * AES-192 is an optional feature that may be unavailable when
1818 * there is an alternative underlying implementation i.e. when
1819 * MBEDTLS_AES_ALT is defined.
1820 */
Ron Eldor9924bdc2018-10-04 10:59:13 +03001821 if( ret == MBEDTLS_ERR_PLATFORM_FEATURE_UNSUPPORTED && keybits == 192 )
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001822 {
1823 mbedtls_printf( "skipped\n" );
1824 continue;
1825 }
1826 else if( ret != 0 )
1827 {
1828 goto exit;
1829 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001830
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001831 for( j = 0; j < 10000; j++ )
1832 {
1833 ret = mbedtls_aes_crypt_ecb( &ctx, mode, buf, buf );
1834 if( ret != 0 )
Paul Bakkerc7ea99a2014-06-18 11:12:03 +02001835 goto exit;
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001836 }
1837
1838 if( memcmp( buf, aes_tests, 16 ) != 0 )
1839 {
1840 ret = 1;
1841 goto exit;
Paul Bakker5121ce52009-01-03 21:22:43 +00001842 }
1843
1844 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001845 mbedtls_printf( "passed\n" );
Paul Bakker5121ce52009-01-03 21:22:43 +00001846 }
1847
1848 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001849 mbedtls_printf( "\n" );
Paul Bakker5121ce52009-01-03 21:22:43 +00001850
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001851#if defined(MBEDTLS_CIPHER_MODE_CBC)
Paul Bakker5121ce52009-01-03 21:22:43 +00001852 /*
1853 * CBC mode
1854 */
1855 for( i = 0; i < 6; i++ )
1856 {
1857 u = i >> 1;
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001858 keybits = 128 + u * 64;
1859 mode = i & 1;
Paul Bakker5121ce52009-01-03 21:22:43 +00001860
1861 if( verbose != 0 )
Kenneth Soerensen518d4352020-04-01 17:22:45 +02001862 mbedtls_printf( " AES-CBC-%3u (%s): ", keybits,
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001863 ( mode == MBEDTLS_AES_DECRYPT ) ? "dec" : "enc" );
Paul Bakker5121ce52009-01-03 21:22:43 +00001864
1865 memset( iv , 0, 16 );
1866 memset( prv, 0, 16 );
1867 memset( buf, 0, 16 );
1868
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001869 if( mode == MBEDTLS_AES_DECRYPT )
Paul Bakker5121ce52009-01-03 21:22:43 +00001870 {
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001871 ret = mbedtls_aes_setkey_dec( &ctx, key, keybits );
1872 aes_tests = aes_test_cbc_dec[u];
Paul Bakker5121ce52009-01-03 21:22:43 +00001873 }
1874 else
1875 {
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001876 ret = mbedtls_aes_setkey_enc( &ctx, key, keybits );
1877 aes_tests = aes_test_cbc_enc[u];
1878 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001879
Andres Amaya Garciad3e7e7d2017-06-15 16:17:46 +01001880 /*
1881 * AES-192 is an optional feature that may be unavailable when
1882 * there is an alternative underlying implementation i.e. when
1883 * MBEDTLS_AES_ALT is defined.
1884 */
Ron Eldor9924bdc2018-10-04 10:59:13 +03001885 if( ret == MBEDTLS_ERR_PLATFORM_FEATURE_UNSUPPORTED && keybits == 192 )
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001886 {
1887 mbedtls_printf( "skipped\n" );
1888 continue;
1889 }
1890 else if( ret != 0 )
1891 {
1892 goto exit;
1893 }
1894
1895 for( j = 0; j < 10000; j++ )
1896 {
1897 if( mode == MBEDTLS_AES_ENCRYPT )
Paul Bakker5121ce52009-01-03 21:22:43 +00001898 {
1899 unsigned char tmp[16];
1900
Paul Bakker5121ce52009-01-03 21:22:43 +00001901 memcpy( tmp, prv, 16 );
1902 memcpy( prv, buf, 16 );
1903 memcpy( buf, tmp, 16 );
1904 }
1905
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001906 ret = mbedtls_aes_crypt_cbc( &ctx, mode, 16, iv, buf, buf );
1907 if( ret != 0 )
Paul Bakkerc7ea99a2014-06-18 11:12:03 +02001908 goto exit;
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001909
1910 }
1911
1912 if( memcmp( buf, aes_tests, 16 ) != 0 )
1913 {
1914 ret = 1;
1915 goto exit;
Paul Bakker5121ce52009-01-03 21:22:43 +00001916 }
1917
1918 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001919 mbedtls_printf( "passed\n" );
Paul Bakker5121ce52009-01-03 21:22:43 +00001920 }
1921
1922 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001923 mbedtls_printf( "\n" );
1924#endif /* MBEDTLS_CIPHER_MODE_CBC */
Paul Bakker5121ce52009-01-03 21:22:43 +00001925
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001926#if defined(MBEDTLS_CIPHER_MODE_CFB)
Paul Bakker5121ce52009-01-03 21:22:43 +00001927 /*
1928 * CFB128 mode
1929 */
1930 for( i = 0; i < 6; i++ )
1931 {
1932 u = i >> 1;
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001933 keybits = 128 + u * 64;
1934 mode = i & 1;
Paul Bakker5121ce52009-01-03 21:22:43 +00001935
1936 if( verbose != 0 )
Kenneth Soerensen518d4352020-04-01 17:22:45 +02001937 mbedtls_printf( " AES-CFB128-%3u (%s): ", keybits,
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001938 ( mode == MBEDTLS_AES_DECRYPT ) ? "dec" : "enc" );
Paul Bakker5121ce52009-01-03 21:22:43 +00001939
1940 memcpy( iv, aes_test_cfb128_iv, 16 );
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001941 memcpy( key, aes_test_cfb128_key[u], keybits / 8 );
Paul Bakker5121ce52009-01-03 21:22:43 +00001942
1943 offset = 0;
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001944 ret = mbedtls_aes_setkey_enc( &ctx, key, keybits );
Andres Amaya Garciad3e7e7d2017-06-15 16:17:46 +01001945 /*
1946 * AES-192 is an optional feature that may be unavailable when
1947 * there is an alternative underlying implementation i.e. when
1948 * MBEDTLS_AES_ALT is defined.
1949 */
Ron Eldor9924bdc2018-10-04 10:59:13 +03001950 if( ret == MBEDTLS_ERR_PLATFORM_FEATURE_UNSUPPORTED && keybits == 192 )
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001951 {
1952 mbedtls_printf( "skipped\n" );
1953 continue;
1954 }
1955 else if( ret != 0 )
1956 {
1957 goto exit;
1958 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001959
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001960 if( mode == MBEDTLS_AES_DECRYPT )
Paul Bakker5121ce52009-01-03 21:22:43 +00001961 {
1962 memcpy( buf, aes_test_cfb128_ct[u], 64 );
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001963 aes_tests = aes_test_cfb128_pt;
Paul Bakker5121ce52009-01-03 21:22:43 +00001964 }
1965 else
1966 {
1967 memcpy( buf, aes_test_cfb128_pt, 64 );
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001968 aes_tests = aes_test_cfb128_ct[u];
1969 }
Paul Bakker5121ce52009-01-03 21:22:43 +00001970
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001971 ret = mbedtls_aes_crypt_cfb128( &ctx, mode, 64, &offset, iv, buf, buf );
1972 if( ret != 0 )
1973 goto exit;
Paul Bakker5121ce52009-01-03 21:22:43 +00001974
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01001975 if( memcmp( buf, aes_tests, 64 ) != 0 )
1976 {
1977 ret = 1;
1978 goto exit;
Paul Bakker5121ce52009-01-03 21:22:43 +00001979 }
1980
1981 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001982 mbedtls_printf( "passed\n" );
Paul Bakker5121ce52009-01-03 21:22:43 +00001983 }
1984
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001985 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001986 mbedtls_printf( "\n" );
1987#endif /* MBEDTLS_CIPHER_MODE_CFB */
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001988
Simon Butcherad4e4932018-04-29 00:43:47 +01001989#if defined(MBEDTLS_CIPHER_MODE_OFB)
1990 /*
1991 * OFB mode
1992 */
1993 for( i = 0; i < 6; i++ )
1994 {
1995 u = i >> 1;
1996 keybits = 128 + u * 64;
1997 mode = i & 1;
1998
1999 if( verbose != 0 )
Kenneth Soerensen518d4352020-04-01 17:22:45 +02002000 mbedtls_printf( " AES-OFB-%3u (%s): ", keybits,
Simon Butcherad4e4932018-04-29 00:43:47 +01002001 ( mode == MBEDTLS_AES_DECRYPT ) ? "dec" : "enc" );
2002
2003 memcpy( iv, aes_test_ofb_iv, 16 );
2004 memcpy( key, aes_test_ofb_key[u], keybits / 8 );
2005
2006 offset = 0;
2007 ret = mbedtls_aes_setkey_enc( &ctx, key, keybits );
2008 /*
2009 * AES-192 is an optional feature that may be unavailable when
2010 * there is an alternative underlying implementation i.e. when
2011 * MBEDTLS_AES_ALT is defined.
2012 */
Ron Eldor9924bdc2018-10-04 10:59:13 +03002013 if( ret == MBEDTLS_ERR_PLATFORM_FEATURE_UNSUPPORTED && keybits == 192 )
Simon Butcherad4e4932018-04-29 00:43:47 +01002014 {
2015 mbedtls_printf( "skipped\n" );
2016 continue;
2017 }
2018 else if( ret != 0 )
2019 {
2020 goto exit;
2021 }
2022
2023 if( mode == MBEDTLS_AES_DECRYPT )
2024 {
2025 memcpy( buf, aes_test_ofb_ct[u], 64 );
2026 aes_tests = aes_test_ofb_pt;
2027 }
2028 else
2029 {
2030 memcpy( buf, aes_test_ofb_pt, 64 );
2031 aes_tests = aes_test_ofb_ct[u];
2032 }
2033
2034 ret = mbedtls_aes_crypt_ofb( &ctx, 64, &offset, iv, buf, buf );
2035 if( ret != 0 )
2036 goto exit;
2037
2038 if( memcmp( buf, aes_tests, 64 ) != 0 )
2039 {
2040 ret = 1;
2041 goto exit;
2042 }
2043
2044 if( verbose != 0 )
2045 mbedtls_printf( "passed\n" );
2046 }
2047
2048 if( verbose != 0 )
2049 mbedtls_printf( "\n" );
2050#endif /* MBEDTLS_CIPHER_MODE_OFB */
2051
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002052#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002053 /*
2054 * CTR mode
2055 */
2056 for( i = 0; i < 6; i++ )
2057 {
2058 u = i >> 1;
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01002059 mode = i & 1;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002060
2061 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002062 mbedtls_printf( " AES-CTR-128 (%s): ",
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01002063 ( mode == MBEDTLS_AES_DECRYPT ) ? "dec" : "enc" );
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002064
2065 memcpy( nonce_counter, aes_test_ctr_nonce_counter[u], 16 );
2066 memcpy( key, aes_test_ctr_key[u], 16 );
2067
2068 offset = 0;
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01002069 if( ( ret = mbedtls_aes_setkey_enc( &ctx, key, 128 ) ) != 0 )
2070 goto exit;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002071
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01002072 len = aes_test_ctr_len[u];
2073
2074 if( mode == MBEDTLS_AES_DECRYPT )
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002075 {
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002076 memcpy( buf, aes_test_ctr_ct[u], len );
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01002077 aes_tests = aes_test_ctr_pt[u];
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002078 }
2079 else
2080 {
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002081 memcpy( buf, aes_test_ctr_pt[u], len );
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01002082 aes_tests = aes_test_ctr_ct[u];
2083 }
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002084
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01002085 ret = mbedtls_aes_crypt_ctr( &ctx, len, &offset, nonce_counter,
2086 stream_block, buf, buf );
2087 if( ret != 0 )
2088 goto exit;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002089
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01002090 if( memcmp( buf, aes_tests, len ) != 0 )
2091 {
2092 ret = 1;
2093 goto exit;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002094 }
2095
2096 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002097 mbedtls_printf( "passed\n" );
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00002098 }
Paul Bakker5121ce52009-01-03 21:22:43 +00002099
2100 if( verbose != 0 )
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002101 mbedtls_printf( "\n" );
2102#endif /* MBEDTLS_CIPHER_MODE_CTR */
Paul Bakker5121ce52009-01-03 21:22:43 +00002103
Jaeden Amero21d79cf2018-05-23 10:30:18 +01002104#if defined(MBEDTLS_CIPHER_MODE_XTS)
2105 {
2106 static const int num_tests =
2107 sizeof(aes_test_xts_key) / sizeof(*aes_test_xts_key);
2108 mbedtls_aes_xts_context ctx_xts;
2109
2110 /*
2111 * XTS mode
2112 */
2113 mbedtls_aes_xts_init( &ctx_xts );
2114
2115 for( i = 0; i < num_tests << 1; i++ )
2116 {
2117 const unsigned char *data_unit;
2118 u = i >> 1;
2119 mode = i & 1;
2120
2121 if( verbose != 0 )
2122 mbedtls_printf( " AES-XTS-128 (%s): ",
2123 ( mode == MBEDTLS_AES_DECRYPT ) ? "dec" : "enc" );
2124
2125 memset( key, 0, sizeof( key ) );
2126 memcpy( key, aes_test_xts_key[u], 32 );
2127 data_unit = aes_test_xts_data_unit[u];
2128
2129 len = sizeof( *aes_test_xts_ct32 );
2130
2131 if( mode == MBEDTLS_AES_DECRYPT )
2132 {
2133 ret = mbedtls_aes_xts_setkey_dec( &ctx_xts, key, 256 );
2134 if( ret != 0)
2135 goto exit;
2136 memcpy( buf, aes_test_xts_ct32[u], len );
2137 aes_tests = aes_test_xts_pt32[u];
2138 }
2139 else
2140 {
2141 ret = mbedtls_aes_xts_setkey_enc( &ctx_xts, key, 256 );
2142 if( ret != 0)
2143 goto exit;
2144 memcpy( buf, aes_test_xts_pt32[u], len );
2145 aes_tests = aes_test_xts_ct32[u];
2146 }
2147
2148
2149 ret = mbedtls_aes_crypt_xts( &ctx_xts, mode, len, data_unit,
2150 buf, buf );
2151 if( ret != 0 )
2152 goto exit;
2153
2154 if( memcmp( buf, aes_tests, len ) != 0 )
2155 {
2156 ret = 1;
2157 goto exit;
2158 }
2159
2160 if( verbose != 0 )
2161 mbedtls_printf( "passed\n" );
2162 }
2163
2164 if( verbose != 0 )
2165 mbedtls_printf( "\n" );
2166
2167 mbedtls_aes_xts_free( &ctx_xts );
2168 }
2169#endif /* MBEDTLS_CIPHER_MODE_XTS */
2170
Paul Bakkerc7ea99a2014-06-18 11:12:03 +02002171 ret = 0;
2172
2173exit:
Andres Amaya Garcia58f98c22017-06-14 16:19:42 +01002174 if( ret != 0 && verbose != 0 )
2175 mbedtls_printf( "failed\n" );
2176
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002177 mbedtls_aes_free( &ctx );
Paul Bakkerc7ea99a2014-06-18 11:12:03 +02002178
2179 return( ret );
Paul Bakker5121ce52009-01-03 21:22:43 +00002180}
2181
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002182#endif /* MBEDTLS_SELF_TEST */
Paul Bakker5121ce52009-01-03 21:22:43 +00002183
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02002184#endif /* MBEDTLS_AES_C */