blob: 409727d04258410dd85b86ed70a2a29f69be1806 [file] [log] [blame]
Jens Wiklander817466c2018-05-22 13:49:31 +02001/*
2 * Camellia implementation
3 *
Jerome Forissier79013242021-07-28 10:24:04 +02004 * Copyright The Mbed TLS Contributors
5 * SPDX-License-Identifier: Apache-2.0
Jens Wiklander817466c2018-05-22 13:49:31 +02006 *
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.
Jens Wiklander817466c2018-05-22 13:49:31 +020018 */
19/*
20 * The Camellia block cipher was designed by NTT and Mitsubishi Electric
21 * Corporation.
22 *
23 * http://info.isl.ntt.co.jp/crypt/eng/camellia/dl/01espec.pdf
24 */
25
Jerome Forissier79013242021-07-28 10:24:04 +020026#include "common.h"
Jens Wiklander817466c2018-05-22 13:49:31 +020027
28#if defined(MBEDTLS_CAMELLIA_C)
29
30#include "mbedtls/camellia.h"
Jens Wiklander3d3b0592019-03-20 15:30:29 +010031#include "mbedtls/platform_util.h"
Jens Wiklander817466c2018-05-22 13:49:31 +020032
33#include <string.h>
34
Jens Wiklander817466c2018-05-22 13:49:31 +020035#include "mbedtls/platform.h"
Jens Wiklander817466c2018-05-22 13:49:31 +020036
37#if !defined(MBEDTLS_CAMELLIA_ALT)
38
Jens Wiklander817466c2018-05-22 13:49:31 +020039static const unsigned char SIGMA_CHARS[6][8] =
40{
41 { 0xa0, 0x9e, 0x66, 0x7f, 0x3b, 0xcc, 0x90, 0x8b },
42 { 0xb6, 0x7a, 0xe8, 0x58, 0x4c, 0xaa, 0x73, 0xb2 },
43 { 0xc6, 0xef, 0x37, 0x2f, 0xe9, 0x4f, 0x82, 0xbe },
44 { 0x54, 0xff, 0x53, 0xa5, 0xf1, 0xd3, 0x6f, 0x1c },
45 { 0x10, 0xe5, 0x27, 0xfa, 0xde, 0x68, 0x2d, 0x1d },
46 { 0xb0, 0x56, 0x88, 0xc2, 0xb3, 0xe6, 0xc1, 0xfd }
47};
48
49#if defined(MBEDTLS_CAMELLIA_SMALL_MEMORY)
50
51static const unsigned char FSb[256] =
52{
Jens Wiklander32b31802023-10-06 16:59:46 +020053 112, 130, 44, 236, 179, 39, 192, 229, 228, 133, 87, 53, 234, 12, 174, 65,
54 35, 239, 107, 147, 69, 25, 165, 33, 237, 14, 79, 78, 29, 101, 146, 189,
55 134, 184, 175, 143, 124, 235, 31, 206, 62, 48, 220, 95, 94, 197, 11, 26,
56 166, 225, 57, 202, 213, 71, 93, 61, 217, 1, 90, 214, 81, 86, 108, 77,
57 139, 13, 154, 102, 251, 204, 176, 45, 116, 18, 43, 32, 240, 177, 132, 153,
58 223, 76, 203, 194, 52, 126, 118, 5, 109, 183, 169, 49, 209, 23, 4, 215,
59 20, 88, 58, 97, 222, 27, 17, 28, 50, 15, 156, 22, 83, 24, 242, 34,
60 254, 68, 207, 178, 195, 181, 122, 145, 36, 8, 232, 168, 96, 252, 105, 80,
61 170, 208, 160, 125, 161, 137, 98, 151, 84, 91, 30, 149, 224, 255, 100, 210,
62 16, 196, 0, 72, 163, 247, 117, 219, 138, 3, 230, 218, 9, 63, 221, 148,
63 135, 92, 131, 2, 205, 74, 144, 51, 115, 103, 246, 243, 157, 127, 191, 226,
64 82, 155, 216, 38, 200, 55, 198, 59, 129, 150, 111, 75, 19, 190, 99, 46,
65 233, 121, 167, 140, 159, 110, 188, 142, 41, 245, 249, 182, 47, 253, 180, 89,
66 120, 152, 6, 106, 231, 70, 113, 186, 212, 37, 171, 66, 136, 162, 141, 250,
67 114, 7, 185, 85, 248, 238, 172, 10, 54, 73, 42, 104, 60, 56, 241, 164,
68 64, 40, 211, 123, 187, 201, 67, 193, 21, 227, 173, 244, 119, 199, 128, 158
Jens Wiklander817466c2018-05-22 13:49:31 +020069};
70
71#define SBOX1(n) FSb[(n)]
Jens Wiklander32b31802023-10-06 16:59:46 +020072#define SBOX2(n) (unsigned char) ((FSb[(n)] >> 7 ^ FSb[(n)] << 1) & 0xff)
73#define SBOX3(n) (unsigned char) ((FSb[(n)] >> 1 ^ FSb[(n)] << 7) & 0xff)
Jens Wiklander817466c2018-05-22 13:49:31 +020074#define SBOX4(n) FSb[((n) << 1 ^ (n) >> 7) &0xff]
75
76#else /* MBEDTLS_CAMELLIA_SMALL_MEMORY */
77
78static const unsigned char FSb[256] =
79{
Jens Wiklander32b31802023-10-06 16:59:46 +020080 112, 130, 44, 236, 179, 39, 192, 229, 228, 133, 87, 53, 234, 12, 174, 65,
81 35, 239, 107, 147, 69, 25, 165, 33, 237, 14, 79, 78, 29, 101, 146, 189,
82 134, 184, 175, 143, 124, 235, 31, 206, 62, 48, 220, 95, 94, 197, 11, 26,
83 166, 225, 57, 202, 213, 71, 93, 61, 217, 1, 90, 214, 81, 86, 108, 77,
84 139, 13, 154, 102, 251, 204, 176, 45, 116, 18, 43, 32, 240, 177, 132, 153,
85 223, 76, 203, 194, 52, 126, 118, 5, 109, 183, 169, 49, 209, 23, 4, 215,
86 20, 88, 58, 97, 222, 27, 17, 28, 50, 15, 156, 22, 83, 24, 242, 34,
87 254, 68, 207, 178, 195, 181, 122, 145, 36, 8, 232, 168, 96, 252, 105, 80,
88 170, 208, 160, 125, 161, 137, 98, 151, 84, 91, 30, 149, 224, 255, 100, 210,
89 16, 196, 0, 72, 163, 247, 117, 219, 138, 3, 230, 218, 9, 63, 221, 148,
90 135, 92, 131, 2, 205, 74, 144, 51, 115, 103, 246, 243, 157, 127, 191, 226,
91 82, 155, 216, 38, 200, 55, 198, 59, 129, 150, 111, 75, 19, 190, 99, 46,
92 233, 121, 167, 140, 159, 110, 188, 142, 41, 245, 249, 182, 47, 253, 180, 89,
93 120, 152, 6, 106, 231, 70, 113, 186, 212, 37, 171, 66, 136, 162, 141, 250,
94 114, 7, 185, 85, 248, 238, 172, 10, 54, 73, 42, 104, 60, 56, 241, 164,
95 64, 40, 211, 123, 187, 201, 67, 193, 21, 227, 173, 244, 119, 199, 128, 158
Jens Wiklander817466c2018-05-22 13:49:31 +020096};
97
98static const unsigned char FSb2[256] =
99{
Jens Wiklander32b31802023-10-06 16:59:46 +0200100 224, 5, 88, 217, 103, 78, 129, 203, 201, 11, 174, 106, 213, 24, 93, 130,
101 70, 223, 214, 39, 138, 50, 75, 66, 219, 28, 158, 156, 58, 202, 37, 123,
102 13, 113, 95, 31, 248, 215, 62, 157, 124, 96, 185, 190, 188, 139, 22, 52,
103 77, 195, 114, 149, 171, 142, 186, 122, 179, 2, 180, 173, 162, 172, 216, 154,
104 23, 26, 53, 204, 247, 153, 97, 90, 232, 36, 86, 64, 225, 99, 9, 51,
105 191, 152, 151, 133, 104, 252, 236, 10, 218, 111, 83, 98, 163, 46, 8, 175,
106 40, 176, 116, 194, 189, 54, 34, 56, 100, 30, 57, 44, 166, 48, 229, 68,
107 253, 136, 159, 101, 135, 107, 244, 35, 72, 16, 209, 81, 192, 249, 210, 160,
108 85, 161, 65, 250, 67, 19, 196, 47, 168, 182, 60, 43, 193, 255, 200, 165,
109 32, 137, 0, 144, 71, 239, 234, 183, 21, 6, 205, 181, 18, 126, 187, 41,
110 15, 184, 7, 4, 155, 148, 33, 102, 230, 206, 237, 231, 59, 254, 127, 197,
111 164, 55, 177, 76, 145, 110, 141, 118, 3, 45, 222, 150, 38, 125, 198, 92,
112 211, 242, 79, 25, 63, 220, 121, 29, 82, 235, 243, 109, 94, 251, 105, 178,
113 240, 49, 12, 212, 207, 140, 226, 117, 169, 74, 87, 132, 17, 69, 27, 245,
114 228, 14, 115, 170, 241, 221, 89, 20, 108, 146, 84, 208, 120, 112, 227, 73,
115 128, 80, 167, 246, 119, 147, 134, 131, 42, 199, 91, 233, 238, 143, 1, 61
Jens Wiklander817466c2018-05-22 13:49:31 +0200116};
117
118static const unsigned char FSb3[256] =
119{
Jens Wiklander32b31802023-10-06 16:59:46 +0200120 56, 65, 22, 118, 217, 147, 96, 242, 114, 194, 171, 154, 117, 6, 87, 160,
121 145, 247, 181, 201, 162, 140, 210, 144, 246, 7, 167, 39, 142, 178, 73, 222,
122 67, 92, 215, 199, 62, 245, 143, 103, 31, 24, 110, 175, 47, 226, 133, 13,
123 83, 240, 156, 101, 234, 163, 174, 158, 236, 128, 45, 107, 168, 43, 54, 166,
124 197, 134, 77, 51, 253, 102, 88, 150, 58, 9, 149, 16, 120, 216, 66, 204,
125 239, 38, 229, 97, 26, 63, 59, 130, 182, 219, 212, 152, 232, 139, 2, 235,
126 10, 44, 29, 176, 111, 141, 136, 14, 25, 135, 78, 11, 169, 12, 121, 17,
127 127, 34, 231, 89, 225, 218, 61, 200, 18, 4, 116, 84, 48, 126, 180, 40,
128 85, 104, 80, 190, 208, 196, 49, 203, 42, 173, 15, 202, 112, 255, 50, 105,
129 8, 98, 0, 36, 209, 251, 186, 237, 69, 129, 115, 109, 132, 159, 238, 74,
130 195, 46, 193, 1, 230, 37, 72, 153, 185, 179, 123, 249, 206, 191, 223, 113,
131 41, 205, 108, 19, 100, 155, 99, 157, 192, 75, 183, 165, 137, 95, 177, 23,
132 244, 188, 211, 70, 207, 55, 94, 71, 148, 250, 252, 91, 151, 254, 90, 172,
133 60, 76, 3, 53, 243, 35, 184, 93, 106, 146, 213, 33, 68, 81, 198, 125,
134 57, 131, 220, 170, 124, 119, 86, 5, 27, 164, 21, 52, 30, 28, 248, 82,
135 32, 20, 233, 189, 221, 228, 161, 224, 138, 241, 214, 122, 187, 227, 64, 79
Jens Wiklander817466c2018-05-22 13:49:31 +0200136};
137
138static const unsigned char FSb4[256] =
139{
Jens Wiklander32b31802023-10-06 16:59:46 +0200140 112, 44, 179, 192, 228, 87, 234, 174, 35, 107, 69, 165, 237, 79, 29, 146,
141 134, 175, 124, 31, 62, 220, 94, 11, 166, 57, 213, 93, 217, 90, 81, 108,
142 139, 154, 251, 176, 116, 43, 240, 132, 223, 203, 52, 118, 109, 169, 209, 4,
143 20, 58, 222, 17, 50, 156, 83, 242, 254, 207, 195, 122, 36, 232, 96, 105,
144 170, 160, 161, 98, 84, 30, 224, 100, 16, 0, 163, 117, 138, 230, 9, 221,
145 135, 131, 205, 144, 115, 246, 157, 191, 82, 216, 200, 198, 129, 111, 19, 99,
146 233, 167, 159, 188, 41, 249, 47, 180, 120, 6, 231, 113, 212, 171, 136, 141,
147 114, 185, 248, 172, 54, 42, 60, 241, 64, 211, 187, 67, 21, 173, 119, 128,
148 130, 236, 39, 229, 133, 53, 12, 65, 239, 147, 25, 33, 14, 78, 101, 189,
149 184, 143, 235, 206, 48, 95, 197, 26, 225, 202, 71, 61, 1, 214, 86, 77,
150 13, 102, 204, 45, 18, 32, 177, 153, 76, 194, 126, 5, 183, 49, 23, 215,
151 88, 97, 27, 28, 15, 22, 24, 34, 68, 178, 181, 145, 8, 168, 252, 80,
152 208, 125, 137, 151, 91, 149, 255, 210, 196, 72, 247, 219, 3, 218, 63, 148,
153 92, 2, 74, 51, 103, 243, 127, 226, 155, 38, 55, 59, 150, 75, 190, 46,
154 121, 140, 110, 142, 245, 182, 253, 89, 152, 106, 70, 186, 37, 66, 162, 250,
155 7, 85, 238, 10, 73, 104, 56, 164, 40, 123, 201, 193, 227, 244, 199, 158
Jens Wiklander817466c2018-05-22 13:49:31 +0200156};
157
158#define SBOX1(n) FSb[(n)]
159#define SBOX2(n) FSb2[(n)]
160#define SBOX3(n) FSb3[(n)]
161#define SBOX4(n) FSb4[(n)]
162
163#endif /* MBEDTLS_CAMELLIA_SMALL_MEMORY */
164
165static const unsigned char shifts[2][4][4] =
166{
167 {
168 { 1, 1, 1, 1 }, /* KL */
169 { 0, 0, 0, 0 }, /* KR */
170 { 1, 1, 1, 1 }, /* KA */
171 { 0, 0, 0, 0 } /* KB */
172 },
173 {
174 { 1, 0, 1, 1 }, /* KL */
175 { 1, 1, 0, 1 }, /* KR */
176 { 1, 1, 1, 0 }, /* KA */
177 { 1, 1, 0, 1 } /* KB */
178 }
179};
180
181static const signed char indexes[2][4][20] =
182{
183 {
184 { 0, 1, 2, 3, 8, 9, 10, 11, 38, 39,
Jens Wiklander32b31802023-10-06 16:59:46 +0200185 36, 37, 23, 20, 21, 22, 27, -1, -1, 26 }, /* KL -> RK */
Jens Wiklander817466c2018-05-22 13:49:31 +0200186 { -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
187 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1 }, /* KR -> RK */
188 { 4, 5, 6, 7, 12, 13, 14, 15, 16, 17,
Jens Wiklander32b31802023-10-06 16:59:46 +0200189 18, 19, -1, 24, 25, -1, 31, 28, 29, 30 }, /* KA -> RK */
Jens Wiklander817466c2018-05-22 13:49:31 +0200190 { -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
191 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1 } /* KB -> RK */
192 },
193 {
194 { 0, 1, 2, 3, 61, 62, 63, 60, -1, -1,
Jens Wiklander32b31802023-10-06 16:59:46 +0200195 -1, -1, 27, 24, 25, 26, 35, 32, 33, 34 }, /* KL -> RK */
Jens Wiklander817466c2018-05-22 13:49:31 +0200196 { -1, -1, -1, -1, 8, 9, 10, 11, 16, 17,
197 18, 19, -1, -1, -1, -1, 39, 36, 37, 38 }, /* KR -> RK */
198 { -1, -1, -1, -1, 12, 13, 14, 15, 58, 59,
199 56, 57, 31, 28, 29, 30, -1, -1, -1, -1 }, /* KA -> RK */
200 { 4, 5, 6, 7, 65, 66, 67, 64, 20, 21,
Jens Wiklander32b31802023-10-06 16:59:46 +0200201 22, 23, -1, -1, -1, -1, 43, 40, 41, 42 } /* KB -> RK */
Jens Wiklander817466c2018-05-22 13:49:31 +0200202 }
203};
204
205static const signed char transposes[2][20] =
206{
207 {
208 21, 22, 23, 20,
209 -1, -1, -1, -1,
210 18, 19, 16, 17,
211 11, 8, 9, 10,
212 15, 12, 13, 14
213 },
214 {
215 25, 26, 27, 24,
216 29, 30, 31, 28,
217 18, 19, 16, 17,
218 -1, -1, -1, -1,
219 -1, -1, -1, -1
220 }
221};
222
223/* Shift macro for 128 bit strings with rotation smaller than 32 bits (!) */
224#define ROTL(DEST, SRC, SHIFT) \
Jens Wiklander32b31802023-10-06 16:59:46 +0200225 { \
226 (DEST)[0] = (SRC)[0] << (SHIFT) ^ (SRC)[1] >> (32 - (SHIFT)); \
227 (DEST)[1] = (SRC)[1] << (SHIFT) ^ (SRC)[2] >> (32 - (SHIFT)); \
228 (DEST)[2] = (SRC)[2] << (SHIFT) ^ (SRC)[3] >> (32 - (SHIFT)); \
229 (DEST)[3] = (SRC)[3] << (SHIFT) ^ (SRC)[0] >> (32 - (SHIFT)); \
230 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200231
232#define FL(XL, XR, KL, KR) \
Jens Wiklander32b31802023-10-06 16:59:46 +0200233 { \
234 (XR) = ((((XL) &(KL)) << 1) | (((XL) &(KL)) >> 31)) ^ (XR); \
235 (XL) = ((XR) | (KR)) ^ (XL); \
236 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200237
238#define FLInv(YL, YR, KL, KR) \
Jens Wiklander32b31802023-10-06 16:59:46 +0200239 { \
240 (YL) = ((YR) | (KR)) ^ (YL); \
241 (YR) = ((((YL) &(KL)) << 1) | (((YL) &(KL)) >> 31)) ^ (YR); \
242 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200243
244#define SHIFT_AND_PLACE(INDEX, OFFSET) \
Jens Wiklander32b31802023-10-06 16:59:46 +0200245 { \
246 TK[0] = KC[(OFFSET) * 4 + 0]; \
247 TK[1] = KC[(OFFSET) * 4 + 1]; \
248 TK[2] = KC[(OFFSET) * 4 + 2]; \
249 TK[3] = KC[(OFFSET) * 4 + 3]; \
Jens Wiklander817466c2018-05-22 13:49:31 +0200250 \
Jens Wiklander32b31802023-10-06 16:59:46 +0200251 for (i = 1; i <= 4; i++) \
252 if (shifts[(INDEX)][(OFFSET)][i -1]) \
253 ROTL(TK + i * 4, TK, (15 * i) % 32); \
Jens Wiklander817466c2018-05-22 13:49:31 +0200254 \
Jens Wiklander32b31802023-10-06 16:59:46 +0200255 for (i = 0; i < 20; i++) \
256 if (indexes[(INDEX)][(OFFSET)][i] != -1) { \
257 RK[indexes[(INDEX)][(OFFSET)][i]] = TK[i]; \
Jens Wiklander817466c2018-05-22 13:49:31 +0200258 } \
Jens Wiklander32b31802023-10-06 16:59:46 +0200259 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200260
Jens Wiklander32b31802023-10-06 16:59:46 +0200261static void camellia_feistel(const uint32_t x[2], const uint32_t k[2],
262 uint32_t z[2])
Jens Wiklander817466c2018-05-22 13:49:31 +0200263{
264 uint32_t I0, I1;
265 I0 = x[0] ^ k[0];
266 I1 = x[1] ^ k[1];
267
Jens Wiklander32b31802023-10-06 16:59:46 +0200268 I0 = ((uint32_t) SBOX1(MBEDTLS_BYTE_3(I0)) << 24) |
269 ((uint32_t) SBOX2(MBEDTLS_BYTE_2(I0)) << 16) |
270 ((uint32_t) SBOX3(MBEDTLS_BYTE_1(I0)) << 8) |
271 ((uint32_t) SBOX4(MBEDTLS_BYTE_0(I0)));
272 I1 = ((uint32_t) SBOX2(MBEDTLS_BYTE_3(I1)) << 24) |
273 ((uint32_t) SBOX3(MBEDTLS_BYTE_2(I1)) << 16) |
274 ((uint32_t) SBOX4(MBEDTLS_BYTE_1(I1)) << 8) |
275 ((uint32_t) SBOX1(MBEDTLS_BYTE_0(I1)));
Jens Wiklander817466c2018-05-22 13:49:31 +0200276
277 I0 ^= (I1 << 8) | (I1 >> 24);
278 I1 ^= (I0 << 16) | (I0 >> 16);
279 I0 ^= (I1 >> 8) | (I1 << 24);
280 I1 ^= (I0 >> 8) | (I0 << 24);
281
282 z[0] ^= I1;
283 z[1] ^= I0;
284}
285
Jens Wiklander32b31802023-10-06 16:59:46 +0200286void mbedtls_camellia_init(mbedtls_camellia_context *ctx)
Jens Wiklander817466c2018-05-22 13:49:31 +0200287{
Jens Wiklander32b31802023-10-06 16:59:46 +0200288 memset(ctx, 0, sizeof(mbedtls_camellia_context));
Jens Wiklander817466c2018-05-22 13:49:31 +0200289}
290
Jens Wiklander32b31802023-10-06 16:59:46 +0200291void mbedtls_camellia_free(mbedtls_camellia_context *ctx)
Jens Wiklander817466c2018-05-22 13:49:31 +0200292{
Jens Wiklander32b31802023-10-06 16:59:46 +0200293 if (ctx == NULL) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200294 return;
Jens Wiklander32b31802023-10-06 16:59:46 +0200295 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200296
Jens Wiklander32b31802023-10-06 16:59:46 +0200297 mbedtls_platform_zeroize(ctx, sizeof(mbedtls_camellia_context));
Jens Wiklander817466c2018-05-22 13:49:31 +0200298}
299
300/*
301 * Camellia key schedule (encryption)
302 */
Jens Wiklander32b31802023-10-06 16:59:46 +0200303int mbedtls_camellia_setkey_enc(mbedtls_camellia_context *ctx,
304 const unsigned char *key,
305 unsigned int keybits)
Jens Wiklander817466c2018-05-22 13:49:31 +0200306{
307 int idx;
308 size_t i;
309 uint32_t *RK;
310 unsigned char t[64];
311 uint32_t SIGMA[6][2];
312 uint32_t KC[16];
313 uint32_t TK[20];
314
315 RK = ctx->rk;
316
Jens Wiklander32b31802023-10-06 16:59:46 +0200317 memset(t, 0, 64);
318 memset(RK, 0, sizeof(ctx->rk));
Jens Wiklander817466c2018-05-22 13:49:31 +0200319
Jens Wiklander32b31802023-10-06 16:59:46 +0200320 switch (keybits) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200321 case 128: ctx->nr = 3; idx = 0; break;
322 case 192:
323 case 256: ctx->nr = 4; idx = 1; break;
Jens Wiklander32b31802023-10-06 16:59:46 +0200324 default: return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
Jens Wiklander817466c2018-05-22 13:49:31 +0200325 }
326
Jens Wiklander32b31802023-10-06 16:59:46 +0200327 for (i = 0; i < keybits / 8; ++i) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200328 t[i] = key[i];
Jens Wiklander32b31802023-10-06 16:59:46 +0200329 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200330
Jens Wiklander32b31802023-10-06 16:59:46 +0200331 if (keybits == 192) {
332 for (i = 0; i < 8; i++) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200333 t[24 + i] = ~t[16 + i];
Jens Wiklander32b31802023-10-06 16:59:46 +0200334 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200335 }
336
337 /*
338 * Prepare SIGMA values
339 */
Jens Wiklander32b31802023-10-06 16:59:46 +0200340 for (i = 0; i < 6; i++) {
341 SIGMA[i][0] = MBEDTLS_GET_UINT32_BE(SIGMA_CHARS[i], 0);
342 SIGMA[i][1] = MBEDTLS_GET_UINT32_BE(SIGMA_CHARS[i], 4);
Jens Wiklander817466c2018-05-22 13:49:31 +0200343 }
344
345 /*
346 * Key storage in KC
347 * Order: KL, KR, KA, KB
348 */
Jens Wiklander32b31802023-10-06 16:59:46 +0200349 memset(KC, 0, sizeof(KC));
Jens Wiklander817466c2018-05-22 13:49:31 +0200350
351 /* Store KL, KR */
Jens Wiklander32b31802023-10-06 16:59:46 +0200352 for (i = 0; i < 8; i++) {
353 KC[i] = MBEDTLS_GET_UINT32_BE(t, i * 4);
354 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200355
356 /* Generate KA */
Jens Wiklander32b31802023-10-06 16:59:46 +0200357 for (i = 0; i < 4; ++i) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200358 KC[8 + i] = KC[i] ^ KC[4 + i];
Jens Wiklander32b31802023-10-06 16:59:46 +0200359 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200360
Jens Wiklander32b31802023-10-06 16:59:46 +0200361 camellia_feistel(KC + 8, SIGMA[0], KC + 10);
362 camellia_feistel(KC + 10, SIGMA[1], KC + 8);
Jens Wiklander817466c2018-05-22 13:49:31 +0200363
Jens Wiklander32b31802023-10-06 16:59:46 +0200364 for (i = 0; i < 4; ++i) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200365 KC[8 + i] ^= KC[i];
Jens Wiklander32b31802023-10-06 16:59:46 +0200366 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200367
Jens Wiklander32b31802023-10-06 16:59:46 +0200368 camellia_feistel(KC + 8, SIGMA[2], KC + 10);
369 camellia_feistel(KC + 10, SIGMA[3], KC + 8);
Jens Wiklander817466c2018-05-22 13:49:31 +0200370
Jens Wiklander32b31802023-10-06 16:59:46 +0200371 if (keybits > 128) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200372 /* Generate KB */
Jens Wiklander32b31802023-10-06 16:59:46 +0200373 for (i = 0; i < 4; ++i) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200374 KC[12 + i] = KC[4 + i] ^ KC[8 + i];
Jens Wiklander32b31802023-10-06 16:59:46 +0200375 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200376
Jens Wiklander32b31802023-10-06 16:59:46 +0200377 camellia_feistel(KC + 12, SIGMA[4], KC + 14);
378 camellia_feistel(KC + 14, SIGMA[5], KC + 12);
Jens Wiklander817466c2018-05-22 13:49:31 +0200379 }
380
381 /*
382 * Generating subkeys
383 */
384
385 /* Manipulating KL */
Jens Wiklander32b31802023-10-06 16:59:46 +0200386 SHIFT_AND_PLACE(idx, 0);
Jens Wiklander817466c2018-05-22 13:49:31 +0200387
388 /* Manipulating KR */
Jens Wiklander32b31802023-10-06 16:59:46 +0200389 if (keybits > 128) {
390 SHIFT_AND_PLACE(idx, 1);
Jens Wiklander817466c2018-05-22 13:49:31 +0200391 }
392
393 /* Manipulating KA */
Jens Wiklander32b31802023-10-06 16:59:46 +0200394 SHIFT_AND_PLACE(idx, 2);
Jens Wiklander817466c2018-05-22 13:49:31 +0200395
396 /* Manipulating KB */
Jens Wiklander32b31802023-10-06 16:59:46 +0200397 if (keybits > 128) {
398 SHIFT_AND_PLACE(idx, 3);
Jens Wiklander817466c2018-05-22 13:49:31 +0200399 }
400
401 /* Do transpositions */
Jens Wiklander32b31802023-10-06 16:59:46 +0200402 for (i = 0; i < 20; i++) {
403 if (transposes[idx][i] != -1) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200404 RK[32 + 12 * idx + i] = RK[transposes[idx][i]];
405 }
406 }
407
Jens Wiklander32b31802023-10-06 16:59:46 +0200408 return 0;
Jens Wiklander817466c2018-05-22 13:49:31 +0200409}
410
411/*
412 * Camellia key schedule (decryption)
413 */
Jens Wiklander32b31802023-10-06 16:59:46 +0200414int mbedtls_camellia_setkey_dec(mbedtls_camellia_context *ctx,
415 const unsigned char *key,
416 unsigned int keybits)
Jens Wiklander817466c2018-05-22 13:49:31 +0200417{
418 int idx, ret;
419 size_t i;
420 mbedtls_camellia_context cty;
421 uint32_t *RK;
422 uint32_t *SK;
423
Jens Wiklander32b31802023-10-06 16:59:46 +0200424 mbedtls_camellia_init(&cty);
Jens Wiklander817466c2018-05-22 13:49:31 +0200425
426 /* Also checks keybits */
Jens Wiklander32b31802023-10-06 16:59:46 +0200427 if ((ret = mbedtls_camellia_setkey_enc(&cty, key, keybits)) != 0) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200428 goto exit;
Jens Wiklander32b31802023-10-06 16:59:46 +0200429 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200430
431 ctx->nr = cty.nr;
Jens Wiklander32b31802023-10-06 16:59:46 +0200432 idx = (ctx->nr == 4);
Jens Wiklander817466c2018-05-22 13:49:31 +0200433
434 RK = ctx->rk;
435 SK = cty.rk + 24 * 2 + 8 * idx * 2;
436
437 *RK++ = *SK++;
438 *RK++ = *SK++;
439 *RK++ = *SK++;
440 *RK++ = *SK++;
441
Jens Wiklander32b31802023-10-06 16:59:46 +0200442 for (i = 22 + 8 * idx, SK -= 6; i > 0; i--, SK -= 4) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200443 *RK++ = *SK++;
444 *RK++ = *SK++;
445 }
446
447 SK -= 2;
448
449 *RK++ = *SK++;
450 *RK++ = *SK++;
451 *RK++ = *SK++;
452 *RK++ = *SK++;
453
454exit:
Jens Wiklander32b31802023-10-06 16:59:46 +0200455 mbedtls_camellia_free(&cty);
Jens Wiklander817466c2018-05-22 13:49:31 +0200456
Jens Wiklander32b31802023-10-06 16:59:46 +0200457 return ret;
Jens Wiklander817466c2018-05-22 13:49:31 +0200458}
459
460/*
461 * Camellia-ECB block encryption/decryption
462 */
Jens Wiklander32b31802023-10-06 16:59:46 +0200463int mbedtls_camellia_crypt_ecb(mbedtls_camellia_context *ctx,
464 int mode,
465 const unsigned char input[16],
466 unsigned char output[16])
Jens Wiklander817466c2018-05-22 13:49:31 +0200467{
468 int NR;
469 uint32_t *RK, X[4];
Jens Wiklander32b31802023-10-06 16:59:46 +0200470 if (mode != MBEDTLS_CAMELLIA_ENCRYPT && mode != MBEDTLS_CAMELLIA_DECRYPT) {
471 return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
472 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200473
Jens Wiklander32b31802023-10-06 16:59:46 +0200474 ((void) mode);
Jens Wiklander817466c2018-05-22 13:49:31 +0200475
476 NR = ctx->nr;
477 RK = ctx->rk;
478
Jens Wiklander32b31802023-10-06 16:59:46 +0200479 X[0] = MBEDTLS_GET_UINT32_BE(input, 0);
480 X[1] = MBEDTLS_GET_UINT32_BE(input, 4);
481 X[2] = MBEDTLS_GET_UINT32_BE(input, 8);
482 X[3] = MBEDTLS_GET_UINT32_BE(input, 12);
Jens Wiklander817466c2018-05-22 13:49:31 +0200483
484 X[0] ^= *RK++;
485 X[1] ^= *RK++;
486 X[2] ^= *RK++;
487 X[3] ^= *RK++;
488
Jens Wiklander32b31802023-10-06 16:59:46 +0200489 while (NR) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200490 --NR;
Jens Wiklander32b31802023-10-06 16:59:46 +0200491 camellia_feistel(X, RK, X + 2);
Jens Wiklander817466c2018-05-22 13:49:31 +0200492 RK += 2;
Jens Wiklander32b31802023-10-06 16:59:46 +0200493 camellia_feistel(X + 2, RK, X);
Jens Wiklander817466c2018-05-22 13:49:31 +0200494 RK += 2;
Jens Wiklander32b31802023-10-06 16:59:46 +0200495 camellia_feistel(X, RK, X + 2);
Jens Wiklander817466c2018-05-22 13:49:31 +0200496 RK += 2;
Jens Wiklander32b31802023-10-06 16:59:46 +0200497 camellia_feistel(X + 2, RK, X);
Jens Wiklander817466c2018-05-22 13:49:31 +0200498 RK += 2;
Jens Wiklander32b31802023-10-06 16:59:46 +0200499 camellia_feistel(X, RK, X + 2);
Jens Wiklander817466c2018-05-22 13:49:31 +0200500 RK += 2;
Jens Wiklander32b31802023-10-06 16:59:46 +0200501 camellia_feistel(X + 2, RK, X);
Jens Wiklander817466c2018-05-22 13:49:31 +0200502 RK += 2;
503
Jens Wiklander32b31802023-10-06 16:59:46 +0200504 if (NR) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200505 FL(X[0], X[1], RK[0], RK[1]);
506 RK += 2;
507 FLInv(X[2], X[3], RK[0], RK[1]);
508 RK += 2;
509 }
510 }
511
512 X[2] ^= *RK++;
513 X[3] ^= *RK++;
514 X[0] ^= *RK++;
515 X[1] ^= *RK++;
516
Jens Wiklander32b31802023-10-06 16:59:46 +0200517 MBEDTLS_PUT_UINT32_BE(X[2], output, 0);
518 MBEDTLS_PUT_UINT32_BE(X[3], output, 4);
519 MBEDTLS_PUT_UINT32_BE(X[0], output, 8);
520 MBEDTLS_PUT_UINT32_BE(X[1], output, 12);
Jens Wiklander817466c2018-05-22 13:49:31 +0200521
Jens Wiklander32b31802023-10-06 16:59:46 +0200522 return 0;
Jens Wiklander817466c2018-05-22 13:49:31 +0200523}
524
525#if defined(MBEDTLS_CIPHER_MODE_CBC)
526/*
527 * Camellia-CBC buffer encryption/decryption
528 */
Jens Wiklander32b31802023-10-06 16:59:46 +0200529int mbedtls_camellia_crypt_cbc(mbedtls_camellia_context *ctx,
530 int mode,
531 size_t length,
532 unsigned char iv[16],
533 const unsigned char *input,
534 unsigned char *output)
Jens Wiklander817466c2018-05-22 13:49:31 +0200535{
Jens Wiklander817466c2018-05-22 13:49:31 +0200536 unsigned char temp[16];
Jens Wiklander32b31802023-10-06 16:59:46 +0200537 if (mode != MBEDTLS_CAMELLIA_ENCRYPT && mode != MBEDTLS_CAMELLIA_DECRYPT) {
538 return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
539 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200540
Jens Wiklander32b31802023-10-06 16:59:46 +0200541 if (length % 16) {
542 return MBEDTLS_ERR_CAMELLIA_INVALID_INPUT_LENGTH;
543 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200544
Jens Wiklander32b31802023-10-06 16:59:46 +0200545 if (mode == MBEDTLS_CAMELLIA_DECRYPT) {
546 while (length > 0) {
547 memcpy(temp, input, 16);
548 mbedtls_camellia_crypt_ecb(ctx, mode, input, output);
Jens Wiklander817466c2018-05-22 13:49:31 +0200549
Jens Wiklander32b31802023-10-06 16:59:46 +0200550 mbedtls_xor(output, output, iv, 16);
Jens Wiklander817466c2018-05-22 13:49:31 +0200551
Jens Wiklander32b31802023-10-06 16:59:46 +0200552 memcpy(iv, temp, 16);
Jens Wiklander817466c2018-05-22 13:49:31 +0200553
554 input += 16;
555 output += 16;
556 length -= 16;
557 }
Jens Wiklander32b31802023-10-06 16:59:46 +0200558 } else {
559 while (length > 0) {
560 mbedtls_xor(output, input, iv, 16);
Jens Wiklander817466c2018-05-22 13:49:31 +0200561
Jens Wiklander32b31802023-10-06 16:59:46 +0200562 mbedtls_camellia_crypt_ecb(ctx, mode, output, output);
563 memcpy(iv, output, 16);
Jens Wiklander817466c2018-05-22 13:49:31 +0200564
565 input += 16;
566 output += 16;
567 length -= 16;
568 }
569 }
570
Jens Wiklander32b31802023-10-06 16:59:46 +0200571 return 0;
Jens Wiklander817466c2018-05-22 13:49:31 +0200572}
573#endif /* MBEDTLS_CIPHER_MODE_CBC */
574
575#if defined(MBEDTLS_CIPHER_MODE_CFB)
576/*
577 * Camellia-CFB128 buffer encryption/decryption
578 */
Jens Wiklander32b31802023-10-06 16:59:46 +0200579int mbedtls_camellia_crypt_cfb128(mbedtls_camellia_context *ctx,
580 int mode,
581 size_t length,
582 size_t *iv_off,
583 unsigned char iv[16],
584 const unsigned char *input,
585 unsigned char *output)
Jens Wiklander817466c2018-05-22 13:49:31 +0200586{
587 int c;
Jens Wiklander3d3b0592019-03-20 15:30:29 +0100588 size_t n;
Jens Wiklander32b31802023-10-06 16:59:46 +0200589 if (mode != MBEDTLS_CAMELLIA_ENCRYPT && mode != MBEDTLS_CAMELLIA_DECRYPT) {
590 return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
591 }
Jens Wiklander3d3b0592019-03-20 15:30:29 +0100592
593 n = *iv_off;
Jens Wiklander32b31802023-10-06 16:59:46 +0200594 if (n >= 16) {
595 return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
596 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200597
Jens Wiklander32b31802023-10-06 16:59:46 +0200598 if (mode == MBEDTLS_CAMELLIA_DECRYPT) {
599 while (length--) {
600 if (n == 0) {
601 mbedtls_camellia_crypt_ecb(ctx, MBEDTLS_CAMELLIA_ENCRYPT, iv, iv);
602 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200603
604 c = *input++;
Jens Wiklander32b31802023-10-06 16:59:46 +0200605 *output++ = (unsigned char) (c ^ iv[n]);
Jens Wiklander817466c2018-05-22 13:49:31 +0200606 iv[n] = (unsigned char) c;
607
Jens Wiklander32b31802023-10-06 16:59:46 +0200608 n = (n + 1) & 0x0F;
Jens Wiklander817466c2018-05-22 13:49:31 +0200609 }
Jens Wiklander32b31802023-10-06 16:59:46 +0200610 } else {
611 while (length--) {
612 if (n == 0) {
613 mbedtls_camellia_crypt_ecb(ctx, MBEDTLS_CAMELLIA_ENCRYPT, iv, iv);
614 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200615
Jens Wiklander32b31802023-10-06 16:59:46 +0200616 iv[n] = *output++ = (unsigned char) (iv[n] ^ *input++);
Jens Wiklander817466c2018-05-22 13:49:31 +0200617
Jens Wiklander32b31802023-10-06 16:59:46 +0200618 n = (n + 1) & 0x0F;
Jens Wiklander817466c2018-05-22 13:49:31 +0200619 }
620 }
621
622 *iv_off = n;
623
Jens Wiklander32b31802023-10-06 16:59:46 +0200624 return 0;
Jens Wiklander817466c2018-05-22 13:49:31 +0200625}
626#endif /* MBEDTLS_CIPHER_MODE_CFB */
627
628#if defined(MBEDTLS_CIPHER_MODE_CTR)
629/*
630 * Camellia-CTR buffer encryption/decryption
631 */
Jens Wiklander32b31802023-10-06 16:59:46 +0200632int mbedtls_camellia_crypt_ctr(mbedtls_camellia_context *ctx,
633 size_t length,
634 size_t *nc_off,
635 unsigned char nonce_counter[16],
636 unsigned char stream_block[16],
637 const unsigned char *input,
638 unsigned char *output)
Jens Wiklander817466c2018-05-22 13:49:31 +0200639{
640 int c, i;
Jens Wiklander3d3b0592019-03-20 15:30:29 +0100641 size_t n;
Jens Wiklander3d3b0592019-03-20 15:30:29 +0100642
643 n = *nc_off;
Jens Wiklander32b31802023-10-06 16:59:46 +0200644 if (n >= 16) {
645 return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
646 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200647
Jens Wiklander32b31802023-10-06 16:59:46 +0200648 while (length--) {
649 if (n == 0) {
650 mbedtls_camellia_crypt_ecb(ctx, MBEDTLS_CAMELLIA_ENCRYPT, nonce_counter,
651 stream_block);
Jens Wiklander817466c2018-05-22 13:49:31 +0200652
Jens Wiklander32b31802023-10-06 16:59:46 +0200653 for (i = 16; i > 0; i--) {
654 if (++nonce_counter[i - 1] != 0) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200655 break;
Jens Wiklander32b31802023-10-06 16:59:46 +0200656 }
657 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200658 }
659 c = *input++;
Jens Wiklander32b31802023-10-06 16:59:46 +0200660 *output++ = (unsigned char) (c ^ stream_block[n]);
Jens Wiklander817466c2018-05-22 13:49:31 +0200661
Jens Wiklander32b31802023-10-06 16:59:46 +0200662 n = (n + 1) & 0x0F;
Jens Wiklander817466c2018-05-22 13:49:31 +0200663 }
664
665 *nc_off = n;
666
Jens Wiklander32b31802023-10-06 16:59:46 +0200667 return 0;
Jens Wiklander817466c2018-05-22 13:49:31 +0200668}
669#endif /* MBEDTLS_CIPHER_MODE_CTR */
670#endif /* !MBEDTLS_CAMELLIA_ALT */
671
672#if defined(MBEDTLS_SELF_TEST)
673
674/*
675 * Camellia test vectors from:
676 *
677 * http://info.isl.ntt.co.jp/crypt/eng/camellia/technology.html:
678 * http://info.isl.ntt.co.jp/crypt/eng/camellia/dl/cryptrec/intermediate.txt
679 * http://info.isl.ntt.co.jp/crypt/eng/camellia/dl/cryptrec/t_camellia.txt
680 * (For each bitlength: Key 0, Nr 39)
681 */
682#define CAMELLIA_TESTS_ECB 2
683
684static const unsigned char camellia_test_ecb_key[3][CAMELLIA_TESTS_ECB][32] =
685{
686 {
687 { 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef,
688 0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54, 0x32, 0x10 },
689 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
690 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
691 },
692 {
693 { 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef,
694 0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54, 0x32, 0x10,
695 0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77 },
696 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
697 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
698 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
699 },
700 {
701 { 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef,
702 0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54, 0x32, 0x10,
703 0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77,
704 0x88, 0x99, 0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff },
705 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
706 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
707 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
708 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
709 },
710};
711
712static const unsigned char camellia_test_ecb_plain[CAMELLIA_TESTS_ECB][16] =
713{
714 { 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef,
715 0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54, 0x32, 0x10 },
716 { 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
717 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
718};
719
720static const unsigned char camellia_test_ecb_cipher[3][CAMELLIA_TESTS_ECB][16] =
721{
722 {
723 { 0x67, 0x67, 0x31, 0x38, 0x54, 0x96, 0x69, 0x73,
724 0x08, 0x57, 0x06, 0x56, 0x48, 0xea, 0xbe, 0x43 },
725 { 0x38, 0x3C, 0x6C, 0x2A, 0xAB, 0xEF, 0x7F, 0xDE,
726 0x25, 0xCD, 0x47, 0x0B, 0xF7, 0x74, 0xA3, 0x31 }
727 },
728 {
729 { 0xb4, 0x99, 0x34, 0x01, 0xb3, 0xe9, 0x96, 0xf8,
730 0x4e, 0xe5, 0xce, 0xe7, 0xd7, 0x9b, 0x09, 0xb9 },
731 { 0xD1, 0x76, 0x3F, 0xC0, 0x19, 0xD7, 0x7C, 0xC9,
732 0x30, 0xBF, 0xF2, 0xA5, 0x6F, 0x7C, 0x93, 0x64 }
733 },
734 {
735 { 0x9a, 0xcc, 0x23, 0x7d, 0xff, 0x16, 0xd7, 0x6c,
736 0x20, 0xef, 0x7c, 0x91, 0x9e, 0x3a, 0x75, 0x09 },
737 { 0x05, 0x03, 0xFB, 0x10, 0xAB, 0x24, 0x1E, 0x7C,
738 0xF4, 0x5D, 0x8C, 0xDE, 0xEE, 0x47, 0x43, 0x35 }
739 }
740};
741
742#if defined(MBEDTLS_CIPHER_MODE_CBC)
743#define CAMELLIA_TESTS_CBC 3
744
745static const unsigned char camellia_test_cbc_key[3][32] =
746{
Jens Wiklander32b31802023-10-06 16:59:46 +0200747 { 0x2B, 0x7E, 0x15, 0x16, 0x28, 0xAE, 0xD2, 0xA6,
748 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3C }
Jens Wiklander817466c2018-05-22 13:49:31 +0200749 ,
Jens Wiklander32b31802023-10-06 16:59:46 +0200750 { 0x8E, 0x73, 0xB0, 0xF7, 0xDA, 0x0E, 0x64, 0x52,
751 0xC8, 0x10, 0xF3, 0x2B, 0x80, 0x90, 0x79, 0xE5,
752 0x62, 0xF8, 0xEA, 0xD2, 0x52, 0x2C, 0x6B, 0x7B }
Jens Wiklander817466c2018-05-22 13:49:31 +0200753 ,
Jens Wiklander32b31802023-10-06 16:59:46 +0200754 { 0x60, 0x3D, 0xEB, 0x10, 0x15, 0xCA, 0x71, 0xBE,
755 0x2B, 0x73, 0xAE, 0xF0, 0x85, 0x7D, 0x77, 0x81,
756 0x1F, 0x35, 0x2C, 0x07, 0x3B, 0x61, 0x08, 0xD7,
757 0x2D, 0x98, 0x10, 0xA3, 0x09, 0x14, 0xDF, 0xF4 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200758};
759
760static const unsigned char camellia_test_cbc_iv[16] =
761
Jens Wiklander32b31802023-10-06 16:59:46 +0200762{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
763 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F }
Jens Wiklander817466c2018-05-22 13:49:31 +0200764;
765
766static const unsigned char camellia_test_cbc_plain[CAMELLIA_TESTS_CBC][16] =
767{
768 { 0x6B, 0xC1, 0xBE, 0xE2, 0x2E, 0x40, 0x9F, 0x96,
769 0xE9, 0x3D, 0x7E, 0x11, 0x73, 0x93, 0x17, 0x2A },
770 { 0xAE, 0x2D, 0x8A, 0x57, 0x1E, 0x03, 0xAC, 0x9C,
771 0x9E, 0xB7, 0x6F, 0xAC, 0x45, 0xAF, 0x8E, 0x51 },
772 { 0x30, 0xC8, 0x1C, 0x46, 0xA3, 0x5C, 0xE4, 0x11,
773 0xE5, 0xFB, 0xC1, 0x19, 0x1A, 0x0A, 0x52, 0xEF }
774
775};
776
777static const unsigned char camellia_test_cbc_cipher[3][CAMELLIA_TESTS_CBC][16] =
778{
779 {
780 { 0x16, 0x07, 0xCF, 0x49, 0x4B, 0x36, 0xBB, 0xF0,
781 0x0D, 0xAE, 0xB0, 0xB5, 0x03, 0xC8, 0x31, 0xAB },
782 { 0xA2, 0xF2, 0xCF, 0x67, 0x16, 0x29, 0xEF, 0x78,
783 0x40, 0xC5, 0xA5, 0xDF, 0xB5, 0x07, 0x48, 0x87 },
784 { 0x0F, 0x06, 0x16, 0x50, 0x08, 0xCF, 0x8B, 0x8B,
785 0x5A, 0x63, 0x58, 0x63, 0x62, 0x54, 0x3E, 0x54 }
786 },
787 {
788 { 0x2A, 0x48, 0x30, 0xAB, 0x5A, 0xC4, 0xA1, 0xA2,
789 0x40, 0x59, 0x55, 0xFD, 0x21, 0x95, 0xCF, 0x93 },
790 { 0x5D, 0x5A, 0x86, 0x9B, 0xD1, 0x4C, 0xE5, 0x42,
791 0x64, 0xF8, 0x92, 0xA6, 0xDD, 0x2E, 0xC3, 0xD5 },
792 { 0x37, 0xD3, 0x59, 0xC3, 0x34, 0x98, 0x36, 0xD8,
793 0x84, 0xE3, 0x10, 0xAD, 0xDF, 0x68, 0xC4, 0x49 }
794 },
795 {
796 { 0xE6, 0xCF, 0xA3, 0x5F, 0xC0, 0x2B, 0x13, 0x4A,
797 0x4D, 0x2C, 0x0B, 0x67, 0x37, 0xAC, 0x3E, 0xDA },
798 { 0x36, 0xCB, 0xEB, 0x73, 0xBD, 0x50, 0x4B, 0x40,
799 0x70, 0xB1, 0xB7, 0xDE, 0x2B, 0x21, 0xEB, 0x50 },
800 { 0xE3, 0x1A, 0x60, 0x55, 0x29, 0x7D, 0x96, 0xCA,
801 0x33, 0x30, 0xCD, 0xF1, 0xB1, 0x86, 0x0A, 0x83 }
802 }
803};
804#endif /* MBEDTLS_CIPHER_MODE_CBC */
805
806#if defined(MBEDTLS_CIPHER_MODE_CTR)
807/*
808 * Camellia-CTR test vectors from:
809 *
810 * http://www.faqs.org/rfcs/rfc5528.html
811 */
812
813static const unsigned char camellia_test_ctr_key[3][16] =
814{
815 { 0xAE, 0x68, 0x52, 0xF8, 0x12, 0x10, 0x67, 0xCC,
816 0x4B, 0xF7, 0xA5, 0x76, 0x55, 0x77, 0xF3, 0x9E },
817 { 0x7E, 0x24, 0x06, 0x78, 0x17, 0xFA, 0xE0, 0xD7,
818 0x43, 0xD6, 0xCE, 0x1F, 0x32, 0x53, 0x91, 0x63 },
819 { 0x76, 0x91, 0xBE, 0x03, 0x5E, 0x50, 0x20, 0xA8,
820 0xAC, 0x6E, 0x61, 0x85, 0x29, 0xF9, 0xA0, 0xDC }
821};
822
823static const unsigned char camellia_test_ctr_nonce_counter[3][16] =
824{
825 { 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x00,
826 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01 },
827 { 0x00, 0x6C, 0xB6, 0xDB, 0xC0, 0x54, 0x3B, 0x59,
828 0xDA, 0x48, 0xD9, 0x0B, 0x00, 0x00, 0x00, 0x01 },
829 { 0x00, 0xE0, 0x01, 0x7B, 0x27, 0x77, 0x7F, 0x3F,
830 0x4A, 0x17, 0x86, 0xF0, 0x00, 0x00, 0x00, 0x01 }
831};
832
833static const unsigned char camellia_test_ctr_pt[3][48] =
834{
835 { 0x53, 0x69, 0x6E, 0x67, 0x6C, 0x65, 0x20, 0x62,
836 0x6C, 0x6F, 0x63, 0x6B, 0x20, 0x6D, 0x73, 0x67 },
837
838 { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
839 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,
840 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
841 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F },
842
843 { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
844 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,
845 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
846 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F,
847 0x20, 0x21, 0x22, 0x23 }
848};
849
850static const unsigned char camellia_test_ctr_ct[3][48] =
851{
852 { 0xD0, 0x9D, 0xC2, 0x9A, 0x82, 0x14, 0x61, 0x9A,
853 0x20, 0x87, 0x7C, 0x76, 0xDB, 0x1F, 0x0B, 0x3F },
854 { 0xDB, 0xF3, 0xC7, 0x8D, 0xC0, 0x83, 0x96, 0xD4,
855 0xDA, 0x7C, 0x90, 0x77, 0x65, 0xBB, 0xCB, 0x44,
856 0x2B, 0x8E, 0x8E, 0x0F, 0x31, 0xF0, 0xDC, 0xA7,
857 0x2C, 0x74, 0x17, 0xE3, 0x53, 0x60, 0xE0, 0x48 },
858 { 0xB1, 0x9D, 0x1F, 0xCD, 0xCB, 0x75, 0xEB, 0x88,
859 0x2F, 0x84, 0x9C, 0xE2, 0x4D, 0x85, 0xCF, 0x73,
860 0x9C, 0xE6, 0x4B, 0x2B, 0x5C, 0x9D, 0x73, 0xF1,
861 0x4F, 0x2D, 0x5D, 0x9D, 0xCE, 0x98, 0x89, 0xCD,
862 0xDF, 0x50, 0x86, 0x96 }
863};
864
865static const int camellia_test_ctr_len[3] =
Jens Wiklander32b31802023-10-06 16:59:46 +0200866{ 16, 32, 36 };
Jens Wiklander817466c2018-05-22 13:49:31 +0200867#endif /* MBEDTLS_CIPHER_MODE_CTR */
868
869/*
870 * Checkup routine
871 */
Jens Wiklander32b31802023-10-06 16:59:46 +0200872int mbedtls_camellia_self_test(int verbose)
Jens Wiklander817466c2018-05-22 13:49:31 +0200873{
874 int i, j, u, v;
875 unsigned char key[32];
876 unsigned char buf[64];
877 unsigned char src[16];
878 unsigned char dst[16];
879#if defined(MBEDTLS_CIPHER_MODE_CBC)
880 unsigned char iv[16];
881#endif
882#if defined(MBEDTLS_CIPHER_MODE_CTR)
883 size_t offset, len;
884 unsigned char nonce_counter[16];
885 unsigned char stream_block[16];
886#endif
Jerome Forissier79013242021-07-28 10:24:04 +0200887 int ret = 1;
Jens Wiklander817466c2018-05-22 13:49:31 +0200888
889 mbedtls_camellia_context ctx;
890
Jens Wiklander32b31802023-10-06 16:59:46 +0200891 mbedtls_camellia_init(&ctx);
892 memset(key, 0, 32);
Jens Wiklander817466c2018-05-22 13:49:31 +0200893
Jens Wiklander32b31802023-10-06 16:59:46 +0200894 for (j = 0; j < 6; j++) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200895 u = j >> 1;
Jens Wiklander32b31802023-10-06 16:59:46 +0200896 v = j & 1;
Jens Wiklander817466c2018-05-22 13:49:31 +0200897
Jens Wiklander32b31802023-10-06 16:59:46 +0200898 if (verbose != 0) {
899 mbedtls_printf(" CAMELLIA-ECB-%3d (%s): ", 128 + u * 64,
900 (v == MBEDTLS_CAMELLIA_DECRYPT) ? "dec" : "enc");
Jens Wiklander817466c2018-05-22 13:49:31 +0200901 }
902
Jens Wiklander32b31802023-10-06 16:59:46 +0200903 for (i = 0; i < CAMELLIA_TESTS_ECB; i++) {
904 memcpy(key, camellia_test_ecb_key[u][i], 16 + 8 * u);
Jens Wiklander817466c2018-05-22 13:49:31 +0200905
Jens Wiklander32b31802023-10-06 16:59:46 +0200906 if (v == MBEDTLS_CAMELLIA_DECRYPT) {
907 mbedtls_camellia_setkey_dec(&ctx, key, 128 + u * 64);
908 memcpy(src, camellia_test_ecb_cipher[u][i], 16);
909 memcpy(dst, camellia_test_ecb_plain[i], 16);
910 } else { /* MBEDTLS_CAMELLIA_ENCRYPT */
911 mbedtls_camellia_setkey_enc(&ctx, key, 128 + u * 64);
912 memcpy(src, camellia_test_ecb_plain[i], 16);
913 memcpy(dst, camellia_test_ecb_cipher[u][i], 16);
914 }
915
916 mbedtls_camellia_crypt_ecb(&ctx, v, src, buf);
917
918 if (memcmp(buf, dst, 16) != 0) {
919 if (verbose != 0) {
920 mbedtls_printf("failed\n");
921 }
922 goto exit;
923 }
924 }
925
926 if (verbose != 0) {
927 mbedtls_printf("passed\n");
Jens Wiklander817466c2018-05-22 13:49:31 +0200928 }
929 }
930
Jens Wiklander32b31802023-10-06 16:59:46 +0200931 if (verbose != 0) {
932 mbedtls_printf("\n");
Jens Wiklander817466c2018-05-22 13:49:31 +0200933 }
934
Jens Wiklander817466c2018-05-22 13:49:31 +0200935#if defined(MBEDTLS_CIPHER_MODE_CBC)
936 /*
937 * CBC mode
938 */
Jens Wiklander32b31802023-10-06 16:59:46 +0200939 for (j = 0; j < 6; j++) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200940 u = j >> 1;
941 v = j & 1;
942
Jens Wiklander32b31802023-10-06 16:59:46 +0200943 if (verbose != 0) {
944 mbedtls_printf(" CAMELLIA-CBC-%3d (%s): ", 128 + u * 64,
945 (v == MBEDTLS_CAMELLIA_DECRYPT) ? "dec" : "enc");
Jens Wiklander817466c2018-05-22 13:49:31 +0200946 }
947
Jens Wiklander32b31802023-10-06 16:59:46 +0200948 memcpy(src, camellia_test_cbc_iv, 16);
949 memcpy(dst, camellia_test_cbc_iv, 16);
950 memcpy(key, camellia_test_cbc_key[u], 16 + 8 * u);
Jens Wiklander817466c2018-05-22 13:49:31 +0200951
Jens Wiklander32b31802023-10-06 16:59:46 +0200952 if (v == MBEDTLS_CAMELLIA_DECRYPT) {
953 mbedtls_camellia_setkey_dec(&ctx, key, 128 + u * 64);
954 } else {
955 mbedtls_camellia_setkey_enc(&ctx, key, 128 + u * 64);
956 }
957
958 for (i = 0; i < CAMELLIA_TESTS_CBC; i++) {
959
960 if (v == MBEDTLS_CAMELLIA_DECRYPT) {
961 memcpy(iv, src, 16);
962 memcpy(src, camellia_test_cbc_cipher[u][i], 16);
963 memcpy(dst, camellia_test_cbc_plain[i], 16);
Jens Wiklander817466c2018-05-22 13:49:31 +0200964 } else { /* MBEDTLS_CAMELLIA_ENCRYPT */
Jens Wiklander32b31802023-10-06 16:59:46 +0200965 memcpy(iv, dst, 16);
966 memcpy(src, camellia_test_cbc_plain[i], 16);
967 memcpy(dst, camellia_test_cbc_cipher[u][i], 16);
Jens Wiklander817466c2018-05-22 13:49:31 +0200968 }
969
Jens Wiklander32b31802023-10-06 16:59:46 +0200970 mbedtls_camellia_crypt_cbc(&ctx, v, 16, iv, src, buf);
Jens Wiklander817466c2018-05-22 13:49:31 +0200971
Jens Wiklander32b31802023-10-06 16:59:46 +0200972 if (memcmp(buf, dst, 16) != 0) {
973 if (verbose != 0) {
974 mbedtls_printf("failed\n");
975 }
Jerome Forissier79013242021-07-28 10:24:04 +0200976 goto exit;
Jens Wiklander817466c2018-05-22 13:49:31 +0200977 }
978 }
979
Jens Wiklander32b31802023-10-06 16:59:46 +0200980 if (verbose != 0) {
981 mbedtls_printf("passed\n");
982 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200983 }
984#endif /* MBEDTLS_CIPHER_MODE_CBC */
985
Jens Wiklander32b31802023-10-06 16:59:46 +0200986 if (verbose != 0) {
987 mbedtls_printf("\n");
988 }
Jens Wiklander817466c2018-05-22 13:49:31 +0200989
990#if defined(MBEDTLS_CIPHER_MODE_CTR)
991 /*
992 * CTR mode
993 */
Jens Wiklander32b31802023-10-06 16:59:46 +0200994 for (i = 0; i < 6; i++) {
Jens Wiklander817466c2018-05-22 13:49:31 +0200995 u = i >> 1;
996 v = i & 1;
997
Jens Wiklander32b31802023-10-06 16:59:46 +0200998 if (verbose != 0) {
999 mbedtls_printf(" CAMELLIA-CTR-128 (%s): ",
1000 (v == MBEDTLS_CAMELLIA_DECRYPT) ? "dec" : "enc");
1001 }
Jens Wiklander817466c2018-05-22 13:49:31 +02001002
Jens Wiklander32b31802023-10-06 16:59:46 +02001003 memcpy(nonce_counter, camellia_test_ctr_nonce_counter[u], 16);
1004 memcpy(key, camellia_test_ctr_key[u], 16);
Jens Wiklander817466c2018-05-22 13:49:31 +02001005
1006 offset = 0;
Jens Wiklander32b31802023-10-06 16:59:46 +02001007 mbedtls_camellia_setkey_enc(&ctx, key, 128);
Jens Wiklander817466c2018-05-22 13:49:31 +02001008
Jens Wiklander32b31802023-10-06 16:59:46 +02001009 if (v == MBEDTLS_CAMELLIA_DECRYPT) {
Jens Wiklander817466c2018-05-22 13:49:31 +02001010 len = camellia_test_ctr_len[u];
Jens Wiklander32b31802023-10-06 16:59:46 +02001011 memcpy(buf, camellia_test_ctr_ct[u], len);
Jens Wiklander817466c2018-05-22 13:49:31 +02001012
Jens Wiklander32b31802023-10-06 16:59:46 +02001013 mbedtls_camellia_crypt_ctr(&ctx, len, &offset, nonce_counter, stream_block,
1014 buf, buf);
Jens Wiklander817466c2018-05-22 13:49:31 +02001015
Jens Wiklander32b31802023-10-06 16:59:46 +02001016 if (memcmp(buf, camellia_test_ctr_pt[u], len) != 0) {
1017 if (verbose != 0) {
1018 mbedtls_printf("failed\n");
1019 }
Jerome Forissier79013242021-07-28 10:24:04 +02001020 goto exit;
Jens Wiklander817466c2018-05-22 13:49:31 +02001021 }
Jens Wiklander32b31802023-10-06 16:59:46 +02001022 } else {
Jens Wiklander817466c2018-05-22 13:49:31 +02001023 len = camellia_test_ctr_len[u];
Jens Wiklander32b31802023-10-06 16:59:46 +02001024 memcpy(buf, camellia_test_ctr_pt[u], len);
Jens Wiklander817466c2018-05-22 13:49:31 +02001025
Jens Wiklander32b31802023-10-06 16:59:46 +02001026 mbedtls_camellia_crypt_ctr(&ctx, len, &offset, nonce_counter, stream_block,
1027 buf, buf);
Jens Wiklander817466c2018-05-22 13:49:31 +02001028
Jens Wiklander32b31802023-10-06 16:59:46 +02001029 if (memcmp(buf, camellia_test_ctr_ct[u], len) != 0) {
1030 if (verbose != 0) {
1031 mbedtls_printf("failed\n");
1032 }
Jerome Forissier79013242021-07-28 10:24:04 +02001033 goto exit;
Jens Wiklander817466c2018-05-22 13:49:31 +02001034 }
1035 }
1036
Jens Wiklander32b31802023-10-06 16:59:46 +02001037 if (verbose != 0) {
1038 mbedtls_printf("passed\n");
1039 }
Jens Wiklander817466c2018-05-22 13:49:31 +02001040 }
1041
Jens Wiklander32b31802023-10-06 16:59:46 +02001042 if (verbose != 0) {
1043 mbedtls_printf("\n");
1044 }
Jens Wiklander817466c2018-05-22 13:49:31 +02001045#endif /* MBEDTLS_CIPHER_MODE_CTR */
1046
Jerome Forissier79013242021-07-28 10:24:04 +02001047 ret = 0;
1048
1049exit:
Jens Wiklander32b31802023-10-06 16:59:46 +02001050 mbedtls_camellia_free(&ctx);
1051 return ret;
Jens Wiklander817466c2018-05-22 13:49:31 +02001052}
1053
1054#endif /* MBEDTLS_SELF_TEST */
1055
1056#endif /* MBEDTLS_CAMELLIA_C */