blob: 409727d04258410dd85b86ed70a2a29f69be1806 [file] [log] [blame]
Paul Bakker38119b12009-01-10 23:31:23 +00001/*
2 * Camellia 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 Bakker38119b12009-01-10 23:31:23 +000018 */
19/*
Paul Bakkerb5ef0ba2009-01-11 20:25:36 +000020 * The Camellia block cipher was designed by NTT and Mitsubishi Electric
21 * Corporation.
Paul Bakker38119b12009-01-10 23:31:23 +000022 *
Paul Bakkerb5ef0ba2009-01-11 20:25:36 +000023 * http://info.isl.ntt.co.jp/crypt/eng/camellia/dl/01espec.pdf
Paul Bakker38119b12009-01-10 23:31:23 +000024 */
25
Gilles Peskinedb09ef62020-06-03 01:43:33 +020026#include "common.h"
Paul Bakker38119b12009-01-10 23:31:23 +000027
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020028#if defined(MBEDTLS_CAMELLIA_C)
Paul Bakker38119b12009-01-10 23:31:23 +000029
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000030#include "mbedtls/camellia.h"
Andres Amaya Garcia1f6301b2018-04-17 09:51:09 -050031#include "mbedtls/platform_util.h"
Paul Bakker38119b12009-01-10 23:31:23 +000032
Rich Evans00ab4702015-02-06 13:43:58 +000033#include <string.h>
Manuel Pégourié-Gonnard394608e2015-02-17 16:01:07 +010034
Manuel Pégourié-Gonnard7f809972015-03-09 17:05:11 +000035#include "mbedtls/platform.h"
Paul Bakker7dc4c442014-02-01 22:50:26 +010036
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020037#if !defined(MBEDTLS_CAMELLIA_ALT)
Paul Bakker90995b52013-06-24 19:20:35 +020038
Paul Bakker38119b12009-01-10 23:31:23 +000039static const unsigned char SIGMA_CHARS[6][8] =
40{
Paul Bakkerc81f6c32009-05-03 13:09:15 +000041 { 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 }
Paul Bakker38119b12009-01-10 23:31:23 +000047};
48
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020049#if defined(MBEDTLS_CAMELLIA_SMALL_MEMORY)
Paul Bakkerfa049db2009-01-12 22:12:03 +000050
51static const unsigned char FSb[256] =
Paul Bakker38119b12009-01-10 23:31:23 +000052{
Gilles Peskine449bd832023-01-11 14:50:10 +010053 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
Paul Bakker38119b12009-01-10 23:31:23 +000069};
70
71#define SBOX1(n) FSb[(n)]
Gilles Peskine449bd832023-01-11 14:50:10 +010072#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)
Paul Bakkerfa049db2009-01-12 22:12:03 +000074#define SBOX4(n) FSb[((n) << 1 ^ (n) >> 7) &0xff]
75
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +020076#else /* MBEDTLS_CAMELLIA_SMALL_MEMORY */
Paul Bakkerfa049db2009-01-12 22:12:03 +000077
Paul Bakkerc32c6b52009-01-11 21:36:43 +000078static const unsigned char FSb[256] =
79{
Gilles Peskine449bd832023-01-11 14:50:10 +010080 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
Paul Bakkerc32c6b52009-01-11 21:36:43 +000096};
97
98static const unsigned char FSb2[256] =
99{
Gilles Peskine449bd832023-01-11 14:50:10 +0100100 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
Paul Bakkerc32c6b52009-01-11 21:36:43 +0000116};
117
118static const unsigned char FSb3[256] =
119{
Gilles Peskine449bd832023-01-11 14:50:10 +0100120 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
Paul Bakkerc32c6b52009-01-11 21:36:43 +0000136};
137
138static const unsigned char FSb4[256] =
139{
Gilles Peskine449bd832023-01-11 14:50:10 +0100140 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
Paul Bakkerc32c6b52009-01-11 21:36:43 +0000156};
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)]
Paul Bakker38119b12009-01-10 23:31:23 +0000162
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200163#endif /* MBEDTLS_CAMELLIA_SMALL_MEMORY */
Paul Bakkerfa049db2009-01-12 22:12:03 +0000164
Paul Bakker38119b12009-01-10 23:31:23 +0000165static const unsigned char shifts[2][4][4] =
166{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000167 {
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 }
Paul Bakker38119b12009-01-10 23:31:23 +0000179};
180
Paul Bakker026c03b2009-03-28 17:53:03 +0000181static const signed char indexes[2][4][20] =
Paul Bakker38119b12009-01-10 23:31:23 +0000182{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000183 {
184 { 0, 1, 2, 3, 8, 9, 10, 11, 38, 39,
Gilles Peskine449bd832023-01-11 14:50:10 +0100185 36, 37, 23, 20, 21, 22, 27, -1, -1, 26 }, /* KL -> RK */
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000186 { -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,
Gilles Peskine449bd832023-01-11 14:50:10 +0100189 18, 19, -1, 24, 25, -1, 31, 28, 29, 30 }, /* KA -> RK */
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000190 { -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,
Gilles Peskine449bd832023-01-11 14:50:10 +0100195 -1, -1, 27, 24, 25, 26, 35, 32, 33, 34 }, /* KL -> RK */
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000196 { -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,
Gilles Peskine449bd832023-01-11 14:50:10 +0100201 22, 23, -1, -1, -1, -1, 43, 40, 41, 42 } /* KB -> RK */
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000202 }
Paul Bakker38119b12009-01-10 23:31:23 +0000203};
204
Paul Bakker026c03b2009-03-28 17:53:03 +0000205static const signed char transposes[2][20] =
Paul Bakker38119b12009-01-10 23:31:23 +0000206{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000207 {
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 }
Paul Bakker38119b12009-01-10 23:31:23 +0000221};
222
Paul Bakkerc32c6b52009-01-11 21:36:43 +0000223/* Shift macro for 128 bit strings with rotation smaller than 32 bits (!) */
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000224#define ROTL(DEST, SRC, SHIFT) \
Gilles Peskine449bd832023-01-11 14:50:10 +0100225 { \
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 }
Paul Bakker38119b12009-01-10 23:31:23 +0000231
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000232#define FL(XL, XR, KL, KR) \
Gilles Peskine449bd832023-01-11 14:50:10 +0100233 { \
234 (XR) = ((((XL) &(KL)) << 1) | (((XL) &(KL)) >> 31)) ^ (XR); \
235 (XL) = ((XR) | (KR)) ^ (XL); \
236 }
Paul Bakker9af723c2014-05-01 13:03:14 +0200237
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000238#define FLInv(YL, YR, KL, KR) \
Gilles Peskine449bd832023-01-11 14:50:10 +0100239 { \
240 (YL) = ((YR) | (KR)) ^ (YL); \
241 (YR) = ((((YL) &(KL)) << 1) | (((YL) &(KL)) >> 31)) ^ (YR); \
242 }
Paul Bakker9af723c2014-05-01 13:03:14 +0200243
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000244#define SHIFT_AND_PLACE(INDEX, OFFSET) \
Gilles Peskine449bd832023-01-11 14:50:10 +0100245 { \
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]; \
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000250 \
Gilles Peskine449bd832023-01-11 14:50:10 +0100251 for (i = 1; i <= 4; i++) \
252 if (shifts[(INDEX)][(OFFSET)][i -1]) \
253 ROTL(TK + i * 4, TK, (15 * i) % 32); \
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000254 \
Gilles Peskine449bd832023-01-11 14:50:10 +0100255 for (i = 0; i < 20; i++) \
256 if (indexes[(INDEX)][(OFFSET)][i] != -1) { \
257 RK[indexes[(INDEX)][(OFFSET)][i]] = TK[i]; \
Paul Bakker66d5d072014-06-17 16:39:18 +0200258 } \
Gilles Peskine449bd832023-01-11 14:50:10 +0100259 }
Paul Bakker38119b12009-01-10 23:31:23 +0000260
Gilles Peskine449bd832023-01-11 14:50:10 +0100261static void camellia_feistel(const uint32_t x[2], const uint32_t k[2],
262 uint32_t z[2])
Paul Bakker38119b12009-01-10 23:31:23 +0000263{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000264 uint32_t I0, I1;
265 I0 = x[0] ^ k[0];
266 I1 = x[1] ^ k[1];
Paul Bakker38119b12009-01-10 23:31:23 +0000267
Gilles Peskine449bd832023-01-11 14:50:10 +0100268 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)));
Paul Bakker38119b12009-01-10 23:31:23 +0000276
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000277 I0 ^= (I1 << 8) | (I1 >> 24);
278 I1 ^= (I0 << 16) | (I0 >> 16);
279 I0 ^= (I1 >> 8) | (I1 << 24);
280 I1 ^= (I0 >> 8) | (I0 << 24);
Paul Bakker38119b12009-01-10 23:31:23 +0000281
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000282 z[0] ^= I1;
283 z[1] ^= I0;
Paul Bakker38119b12009-01-10 23:31:23 +0000284}
285
Gilles Peskine449bd832023-01-11 14:50:10 +0100286void mbedtls_camellia_init(mbedtls_camellia_context *ctx)
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200287{
Gilles Peskine449bd832023-01-11 14:50:10 +0100288 memset(ctx, 0, sizeof(mbedtls_camellia_context));
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200289}
290
Gilles Peskine449bd832023-01-11 14:50:10 +0100291void mbedtls_camellia_free(mbedtls_camellia_context *ctx)
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200292{
Gilles Peskine449bd832023-01-11 14:50:10 +0100293 if (ctx == NULL) {
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200294 return;
Gilles Peskine449bd832023-01-11 14:50:10 +0100295 }
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200296
Gilles Peskine449bd832023-01-11 14:50:10 +0100297 mbedtls_platform_zeroize(ctx, sizeof(mbedtls_camellia_context));
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200298}
299
Paul Bakker38119b12009-01-10 23:31:23 +0000300/*
301 * Camellia key schedule (encryption)
302 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100303int mbedtls_camellia_setkey_enc(mbedtls_camellia_context *ctx,
304 const unsigned char *key,
305 unsigned int keybits)
Paul Bakker38119b12009-01-10 23:31:23 +0000306{
Paul Bakker23986e52011-04-24 08:57:21 +0000307 int idx;
308 size_t i;
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000309 uint32_t *RK;
Paul Bakker38119b12009-01-10 23:31:23 +0000310 unsigned char t[64];
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000311 uint32_t SIGMA[6][2];
312 uint32_t KC[16];
313 uint32_t TK[20];
Paul Bakker38119b12009-01-10 23:31:23 +0000314
315 RK = ctx->rk;
316
Gilles Peskine449bd832023-01-11 14:50:10 +0100317 memset(t, 0, 64);
318 memset(RK, 0, sizeof(ctx->rk));
Paul Bakker38119b12009-01-10 23:31:23 +0000319
Gilles Peskine449bd832023-01-11 14:50:10 +0100320 switch (keybits) {
Paul Bakker38119b12009-01-10 23:31:23 +0000321 case 128: ctx->nr = 3; idx = 0; break;
322 case 192:
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000323 case 256: ctx->nr = 4; idx = 1; break;
Gilles Peskine449bd832023-01-11 14:50:10 +0100324 default: return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
Paul Bakker38119b12009-01-10 23:31:23 +0000325 }
326
Gilles Peskine449bd832023-01-11 14:50:10 +0100327 for (i = 0; i < keybits / 8; ++i) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000328 t[i] = key[i];
Gilles Peskine449bd832023-01-11 14:50:10 +0100329 }
Paul Bakker38119b12009-01-10 23:31:23 +0000330
Gilles Peskine449bd832023-01-11 14:50:10 +0100331 if (keybits == 192) {
332 for (i = 0; i < 8; i++) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000333 t[24 + i] = ~t[16 + i];
Gilles Peskine449bd832023-01-11 14:50:10 +0100334 }
Paul Bakker38119b12009-01-10 23:31:23 +0000335 }
336
Paul Bakker38119b12009-01-10 23:31:23 +0000337 /*
338 * Prepare SIGMA values
339 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100340 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);
Paul Bakker38119b12009-01-10 23:31:23 +0000343 }
344
345 /*
346 * Key storage in KC
347 * Order: KL, KR, KA, KB
348 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100349 memset(KC, 0, sizeof(KC));
Paul Bakker38119b12009-01-10 23:31:23 +0000350
351 /* Store KL, KR */
Gilles Peskine449bd832023-01-11 14:50:10 +0100352 for (i = 0; i < 8; i++) {
353 KC[i] = MBEDTLS_GET_UINT32_BE(t, i * 4);
354 }
Paul Bakker38119b12009-01-10 23:31:23 +0000355
356 /* Generate KA */
Gilles Peskine449bd832023-01-11 14:50:10 +0100357 for (i = 0; i < 4; ++i) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000358 KC[8 + i] = KC[i] ^ KC[4 + i];
Gilles Peskine449bd832023-01-11 14:50:10 +0100359 }
Paul Bakker38119b12009-01-10 23:31:23 +0000360
Gilles Peskine449bd832023-01-11 14:50:10 +0100361 camellia_feistel(KC + 8, SIGMA[0], KC + 10);
362 camellia_feistel(KC + 10, SIGMA[1], KC + 8);
Paul Bakker38119b12009-01-10 23:31:23 +0000363
Gilles Peskine449bd832023-01-11 14:50:10 +0100364 for (i = 0; i < 4; ++i) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000365 KC[8 + i] ^= KC[i];
Gilles Peskine449bd832023-01-11 14:50:10 +0100366 }
Paul Bakker38119b12009-01-10 23:31:23 +0000367
Gilles Peskine449bd832023-01-11 14:50:10 +0100368 camellia_feistel(KC + 8, SIGMA[2], KC + 10);
369 camellia_feistel(KC + 10, SIGMA[3], KC + 8);
Paul Bakker38119b12009-01-10 23:31:23 +0000370
Gilles Peskine449bd832023-01-11 14:50:10 +0100371 if (keybits > 128) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000372 /* Generate KB */
Gilles Peskine449bd832023-01-11 14:50:10 +0100373 for (i = 0; i < 4; ++i) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000374 KC[12 + i] = KC[4 + i] ^ KC[8 + i];
Gilles Peskine449bd832023-01-11 14:50:10 +0100375 }
Paul Bakker38119b12009-01-10 23:31:23 +0000376
Gilles Peskine449bd832023-01-11 14:50:10 +0100377 camellia_feistel(KC + 12, SIGMA[4], KC + 14);
378 camellia_feistel(KC + 14, SIGMA[5], KC + 12);
Paul Bakker38119b12009-01-10 23:31:23 +0000379 }
380
381 /*
382 * Generating subkeys
Paul Bakker9af723c2014-05-01 13:03:14 +0200383 */
Paul Bakker38119b12009-01-10 23:31:23 +0000384
385 /* Manipulating KL */
Gilles Peskine449bd832023-01-11 14:50:10 +0100386 SHIFT_AND_PLACE(idx, 0);
Paul Bakker38119b12009-01-10 23:31:23 +0000387
388 /* Manipulating KR */
Gilles Peskine449bd832023-01-11 14:50:10 +0100389 if (keybits > 128) {
390 SHIFT_AND_PLACE(idx, 1);
Paul Bakker38119b12009-01-10 23:31:23 +0000391 }
392
393 /* Manipulating KA */
Gilles Peskine449bd832023-01-11 14:50:10 +0100394 SHIFT_AND_PLACE(idx, 2);
Paul Bakker38119b12009-01-10 23:31:23 +0000395
396 /* Manipulating KB */
Gilles Peskine449bd832023-01-11 14:50:10 +0100397 if (keybits > 128) {
398 SHIFT_AND_PLACE(idx, 3);
Paul Bakker38119b12009-01-10 23:31:23 +0000399 }
400
401 /* Do transpositions */
Gilles Peskine449bd832023-01-11 14:50:10 +0100402 for (i = 0; i < 20; i++) {
403 if (transposes[idx][i] != -1) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000404 RK[32 + 12 * idx + i] = RK[transposes[idx][i]];
405 }
Paul Bakker38119b12009-01-10 23:31:23 +0000406 }
Paul Bakker2b222c82009-07-27 21:03:45 +0000407
Gilles Peskine449bd832023-01-11 14:50:10 +0100408 return 0;
Paul Bakker38119b12009-01-10 23:31:23 +0000409}
410
411/*
412 * Camellia key schedule (decryption)
413 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100414int mbedtls_camellia_setkey_dec(mbedtls_camellia_context *ctx,
415 const unsigned char *key,
416 unsigned int keybits)
Paul Bakker38119b12009-01-10 23:31:23 +0000417{
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200418 int idx, ret;
Paul Bakker23986e52011-04-24 08:57:21 +0000419 size_t i;
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200420 mbedtls_camellia_context cty;
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000421 uint32_t *RK;
422 uint32_t *SK;
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200423
Gilles Peskine449bd832023-01-11 14:50:10 +0100424 mbedtls_camellia_init(&cty);
Paul Bakker38119b12009-01-10 23:31:23 +0000425
Manuel Pégourié-Gonnardb8186a52015-06-18 14:58:58 +0200426 /* Also checks keybits */
Gilles Peskine449bd832023-01-11 14:50:10 +0100427 if ((ret = mbedtls_camellia_setkey_enc(&cty, key, keybits)) != 0) {
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200428 goto exit;
Gilles Peskine449bd832023-01-11 14:50:10 +0100429 }
Paul Bakker38119b12009-01-10 23:31:23 +0000430
Manuel Pégourié-Gonnard3ac6a2b2014-05-28 22:04:25 +0200431 ctx->nr = cty.nr;
Gilles Peskine449bd832023-01-11 14:50:10 +0100432 idx = (ctx->nr == 4);
Manuel Pégourié-Gonnard3ac6a2b2014-05-28 22:04:25 +0200433
434 RK = ctx->rk;
Paul Bakker38119b12009-01-10 23:31:23 +0000435 SK = cty.rk + 24 * 2 + 8 * idx * 2;
436
437 *RK++ = *SK++;
438 *RK++ = *SK++;
439 *RK++ = *SK++;
440 *RK++ = *SK++;
441
Gilles Peskine449bd832023-01-11 14:50:10 +0100442 for (i = 22 + 8 * idx, SK -= 6; i > 0; i--, SK -= 4) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000443 *RK++ = *SK++;
444 *RK++ = *SK++;
Paul Bakker38119b12009-01-10 23:31:23 +0000445 }
446
447 SK -= 2;
448
449 *RK++ = *SK++;
450 *RK++ = *SK++;
451 *RK++ = *SK++;
452 *RK++ = *SK++;
453
Paul Bakkerc7ea99a2014-06-18 11:12:03 +0200454exit:
Gilles Peskine449bd832023-01-11 14:50:10 +0100455 mbedtls_camellia_free(&cty);
Paul Bakker2b222c82009-07-27 21:03:45 +0000456
Gilles Peskine449bd832023-01-11 14:50:10 +0100457 return ret;
Paul Bakker38119b12009-01-10 23:31:23 +0000458}
459
460/*
461 * Camellia-ECB block encryption/decryption
462 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100463int mbedtls_camellia_crypt_ecb(mbedtls_camellia_context *ctx,
464 int mode,
465 const unsigned char input[16],
466 unsigned char output[16])
Paul Bakker38119b12009-01-10 23:31:23 +0000467{
Paul Bakker026c03b2009-03-28 17:53:03 +0000468 int NR;
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000469 uint32_t *RK, X[4];
Gilles Peskine449bd832023-01-11 14:50:10 +0100470 if (mode != MBEDTLS_CAMELLIA_ENCRYPT && mode != MBEDTLS_CAMELLIA_DECRYPT) {
Tuvshinzaya Erdenekhuu1fd7f982022-08-05 15:31:57 +0100471 return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
Gilles Peskine449bd832023-01-11 14:50:10 +0100472 }
Paul Bakker38119b12009-01-10 23:31:23 +0000473
Gilles Peskine449bd832023-01-11 14:50:10 +0100474 ((void) mode);
Paul Bakkerc2547b02009-07-20 20:40:52 +0000475
Paul Bakker38119b12009-01-10 23:31:23 +0000476 NR = ctx->nr;
477 RK = ctx->rk;
478
Gilles Peskine449bd832023-01-11 14:50:10 +0100479 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);
Paul Bakker38119b12009-01-10 23:31:23 +0000483
484 X[0] ^= *RK++;
485 X[1] ^= *RK++;
486 X[2] ^= *RK++;
487 X[3] ^= *RK++;
488
Gilles Peskine449bd832023-01-11 14:50:10 +0100489 while (NR) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000490 --NR;
Gilles Peskine449bd832023-01-11 14:50:10 +0100491 camellia_feistel(X, RK, X + 2);
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000492 RK += 2;
Gilles Peskine449bd832023-01-11 14:50:10 +0100493 camellia_feistel(X + 2, RK, X);
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000494 RK += 2;
Gilles Peskine449bd832023-01-11 14:50:10 +0100495 camellia_feistel(X, RK, X + 2);
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000496 RK += 2;
Gilles Peskine449bd832023-01-11 14:50:10 +0100497 camellia_feistel(X + 2, RK, X);
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000498 RK += 2;
Gilles Peskine449bd832023-01-11 14:50:10 +0100499 camellia_feistel(X, RK, X + 2);
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000500 RK += 2;
Gilles Peskine449bd832023-01-11 14:50:10 +0100501 camellia_feistel(X + 2, RK, X);
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000502 RK += 2;
Paul Bakker38119b12009-01-10 23:31:23 +0000503
Gilles Peskine449bd832023-01-11 14:50:10 +0100504 if (NR) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000505 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 }
Paul Bakker38119b12009-01-10 23:31:23 +0000510 }
511
512 X[2] ^= *RK++;
513 X[3] ^= *RK++;
514 X[0] ^= *RK++;
515 X[1] ^= *RK++;
516
Gilles Peskine449bd832023-01-11 14:50:10 +0100517 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);
Paul Bakkerf3ccc682010-03-18 21:21:02 +0000521
Gilles Peskine449bd832023-01-11 14:50:10 +0100522 return 0;
Paul Bakker38119b12009-01-10 23:31:23 +0000523}
524
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200525#if defined(MBEDTLS_CIPHER_MODE_CBC)
Paul Bakker38119b12009-01-10 23:31:23 +0000526/*
527 * Camellia-CBC buffer encryption/decryption
528 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100529int 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)
Paul Bakker38119b12009-01-10 23:31:23 +0000535{
Paul Bakker38119b12009-01-10 23:31:23 +0000536 unsigned char temp[16];
Gilles Peskine449bd832023-01-11 14:50:10 +0100537 if (mode != MBEDTLS_CAMELLIA_ENCRYPT && mode != MBEDTLS_CAMELLIA_DECRYPT) {
Tuvshinzaya Erdenekhuu1fd7f982022-08-05 15:31:57 +0100538 return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
Gilles Peskine449bd832023-01-11 14:50:10 +0100539 }
Paul Bakker38119b12009-01-10 23:31:23 +0000540
Gilles Peskine449bd832023-01-11 14:50:10 +0100541 if (length % 16) {
542 return MBEDTLS_ERR_CAMELLIA_INVALID_INPUT_LENGTH;
543 }
Paul Bakkerf3ccc682010-03-18 21:21:02 +0000544
Gilles Peskine449bd832023-01-11 14:50:10 +0100545 if (mode == MBEDTLS_CAMELLIA_DECRYPT) {
546 while (length > 0) {
547 memcpy(temp, input, 16);
548 mbedtls_camellia_crypt_ecb(ctx, mode, input, output);
Paul Bakker38119b12009-01-10 23:31:23 +0000549
Gilles Peskine449bd832023-01-11 14:50:10 +0100550 mbedtls_xor(output, output, iv, 16);
Paul Bakker38119b12009-01-10 23:31:23 +0000551
Gilles Peskine449bd832023-01-11 14:50:10 +0100552 memcpy(iv, temp, 16);
Paul Bakker38119b12009-01-10 23:31:23 +0000553
554 input += 16;
555 output += 16;
556 length -= 16;
557 }
Gilles Peskine449bd832023-01-11 14:50:10 +0100558 } else {
559 while (length > 0) {
560 mbedtls_xor(output, input, iv, 16);
Paul Bakker38119b12009-01-10 23:31:23 +0000561
Gilles Peskine449bd832023-01-11 14:50:10 +0100562 mbedtls_camellia_crypt_ecb(ctx, mode, output, output);
563 memcpy(iv, output, 16);
Paul Bakker38119b12009-01-10 23:31:23 +0000564
565 input += 16;
566 output += 16;
567 length -= 16;
568 }
569 }
Paul Bakkerf3ccc682010-03-18 21:21:02 +0000570
Gilles Peskine449bd832023-01-11 14:50:10 +0100571 return 0;
Paul Bakker38119b12009-01-10 23:31:23 +0000572}
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200573#endif /* MBEDTLS_CIPHER_MODE_CBC */
Paul Bakker38119b12009-01-10 23:31:23 +0000574
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200575#if defined(MBEDTLS_CIPHER_MODE_CFB)
Paul Bakker38119b12009-01-10 23:31:23 +0000576/*
577 * Camellia-CFB128 buffer encryption/decryption
578 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100579int 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)
Paul Bakker38119b12009-01-10 23:31:23 +0000586{
Paul Bakker1ef71df2011-06-09 14:14:58 +0000587 int c;
Andrzej Kurekc470b6b2019-01-31 08:20:20 -0500588 size_t n;
Gilles Peskine449bd832023-01-11 14:50:10 +0100589 if (mode != MBEDTLS_CAMELLIA_ENCRYPT && mode != MBEDTLS_CAMELLIA_DECRYPT) {
Tuvshinzaya Erdenekhuu1fd7f982022-08-05 15:31:57 +0100590 return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
Gilles Peskine449bd832023-01-11 14:50:10 +0100591 }
Andrzej Kurekc470b6b2019-01-31 08:20:20 -0500592
593 n = *iv_off;
Gilles Peskine449bd832023-01-11 14:50:10 +0100594 if (n >= 16) {
595 return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
596 }
Paul Bakker38119b12009-01-10 23:31:23 +0000597
Gilles Peskine449bd832023-01-11 14:50:10 +0100598 if (mode == MBEDTLS_CAMELLIA_DECRYPT) {
599 while (length--) {
600 if (n == 0) {
601 mbedtls_camellia_crypt_ecb(ctx, MBEDTLS_CAMELLIA_ENCRYPT, iv, iv);
602 }
Paul Bakker38119b12009-01-10 23:31:23 +0000603
604 c = *input++;
Gilles Peskine449bd832023-01-11 14:50:10 +0100605 *output++ = (unsigned char) (c ^ iv[n]);
Paul Bakker38119b12009-01-10 23:31:23 +0000606 iv[n] = (unsigned char) c;
607
Gilles Peskine449bd832023-01-11 14:50:10 +0100608 n = (n + 1) & 0x0F;
Paul Bakker38119b12009-01-10 23:31:23 +0000609 }
Gilles Peskine449bd832023-01-11 14:50:10 +0100610 } else {
611 while (length--) {
612 if (n == 0) {
613 mbedtls_camellia_crypt_ecb(ctx, MBEDTLS_CAMELLIA_ENCRYPT, iv, iv);
614 }
Paul Bakker38119b12009-01-10 23:31:23 +0000615
Gilles Peskine449bd832023-01-11 14:50:10 +0100616 iv[n] = *output++ = (unsigned char) (iv[n] ^ *input++);
Paul Bakker38119b12009-01-10 23:31:23 +0000617
Gilles Peskine449bd832023-01-11 14:50:10 +0100618 n = (n + 1) & 0x0F;
Paul Bakker38119b12009-01-10 23:31:23 +0000619 }
620 }
621
622 *iv_off = n;
Paul Bakkerf3ccc682010-03-18 21:21:02 +0000623
Gilles Peskine449bd832023-01-11 14:50:10 +0100624 return 0;
Paul Bakker38119b12009-01-10 23:31:23 +0000625}
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200626#endif /* MBEDTLS_CIPHER_MODE_CFB */
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000627
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200628#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000629/*
630 * Camellia-CTR buffer encryption/decryption
631 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100632int 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)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000639{
Paul Bakker369e14b2012-04-18 14:16:09 +0000640 int c, i;
Andrzej Kurekc470b6b2019-01-31 08:20:20 -0500641 size_t n;
Andrzej Kurekc470b6b2019-01-31 08:20:20 -0500642
643 n = *nc_off;
Gilles Peskine449bd832023-01-11 14:50:10 +0100644 if (n >= 16) {
645 return MBEDTLS_ERR_CAMELLIA_BAD_INPUT_DATA;
646 }
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000647
Gilles Peskine449bd832023-01-11 14:50:10 +0100648 while (length--) {
649 if (n == 0) {
650 mbedtls_camellia_crypt_ecb(ctx, MBEDTLS_CAMELLIA_ENCRYPT, nonce_counter,
651 stream_block);
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000652
Gilles Peskine449bd832023-01-11 14:50:10 +0100653 for (i = 16; i > 0; i--) {
654 if (++nonce_counter[i - 1] != 0) {
Paul Bakker369e14b2012-04-18 14:16:09 +0000655 break;
Gilles Peskine449bd832023-01-11 14:50:10 +0100656 }
657 }
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000658 }
659 c = *input++;
Gilles Peskine449bd832023-01-11 14:50:10 +0100660 *output++ = (unsigned char) (c ^ stream_block[n]);
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000661
Gilles Peskine449bd832023-01-11 14:50:10 +0100662 n = (n + 1) & 0x0F;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000663 }
664
665 *nc_off = n;
666
Gilles Peskine449bd832023-01-11 14:50:10 +0100667 return 0;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000668}
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200669#endif /* MBEDTLS_CIPHER_MODE_CTR */
670#endif /* !MBEDTLS_CAMELLIA_ALT */
Paul Bakker38119b12009-01-10 23:31:23 +0000671
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200672#if defined(MBEDTLS_SELF_TEST)
Paul Bakker38119b12009-01-10 23:31:23 +0000673
Paul Bakker38119b12009-01-10 23:31:23 +0000674/*
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
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000680 * (For each bitlength: Key 0, Nr 39)
Paul Bakker38119b12009-01-10 23:31:23 +0000681 */
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000682#define CAMELLIA_TESTS_ECB 2
Paul Bakker38119b12009-01-10 23:31:23 +0000683
684static const unsigned char camellia_test_ecb_key[3][CAMELLIA_TESTS_ECB][32] =
685{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000686 {
687 { 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef,
688 0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54, 0x32, 0x10 },
Paul Bakker9af723c2014-05-01 13:03:14 +0200689 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000690 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 },
Paul Bakker9af723c2014-05-01 13:03:14 +0200696 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000697 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 },
Paul Bakker9af723c2014-05-01 13:03:14 +0200705 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000706 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 },
Paul Bakker38119b12009-01-10 23:31:23 +0000710};
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 },
Paul Bakker9af723c2014-05-01 13:03:14 +0200716 { 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
Paul Bakker38119b12009-01-10 23:31:23 +0000717 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
718};
719
720static const unsigned char camellia_test_ecb_cipher[3][CAMELLIA_TESTS_ECB][16] =
721{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000722 {
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 }
Paul Bakker38119b12009-01-10 23:31:23 +0000740};
741
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200742#if defined(MBEDTLS_CIPHER_MODE_CBC)
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000743#define CAMELLIA_TESTS_CBC 3
Paul Bakker38119b12009-01-10 23:31:23 +0000744
745static const unsigned char camellia_test_cbc_key[3][32] =
746{
Gilles Peskine449bd832023-01-11 14:50:10 +0100747 { 0x2B, 0x7E, 0x15, 0x16, 0x28, 0xAE, 0xD2, 0xA6,
748 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3C }
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000749 ,
Gilles Peskine449bd832023-01-11 14:50:10 +0100750 { 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 }
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000753 ,
Gilles Peskine449bd832023-01-11 14:50:10 +0100754 { 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 }
Paul Bakker38119b12009-01-10 23:31:23 +0000758};
759
760static const unsigned char camellia_test_cbc_iv[16] =
761
Gilles Peskine449bd832023-01-11 14:50:10 +0100762{ 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
763 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F }
Paul Bakker38119b12009-01-10 23:31:23 +0000764;
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{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000779 {
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 }
Paul Bakker38119b12009-01-10 23:31:23 +0000803};
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200804#endif /* MBEDTLS_CIPHER_MODE_CBC */
Paul Bakker38119b12009-01-10 23:31:23 +0000805
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200806#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000807/*
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] =
Gilles Peskine449bd832023-01-11 14:50:10 +0100866{ 16, 32, 36 };
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200867#endif /* MBEDTLS_CIPHER_MODE_CTR */
Paul Bakker38119b12009-01-10 23:31:23 +0000868
869/*
870 * Checkup routine
871 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100872int mbedtls_camellia_self_test(int verbose)
Paul Bakker38119b12009-01-10 23:31:23 +0000873{
Paul Bakker026c03b2009-03-28 17:53:03 +0000874 int i, j, u, v;
Paul Bakker38119b12009-01-10 23:31:23 +0000875 unsigned char key[32];
876 unsigned char buf[64];
Paul Bakker38119b12009-01-10 23:31:23 +0000877 unsigned char src[16];
878 unsigned char dst[16];
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200879#if defined(MBEDTLS_CIPHER_MODE_CBC)
Paul Bakker38119b12009-01-10 23:31:23 +0000880 unsigned char iv[16];
Manuel Pégourié-Gonnard92cb1d32013-09-13 16:24:20 +0200881#endif
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200882#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakker1ef71df2011-06-09 14:14:58 +0000883 size_t offset, len;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000884 unsigned char nonce_counter[16];
885 unsigned char stream_block[16];
886#endif
Gilles Peskinec537aa82021-05-25 09:17:46 +0200887 int ret = 1;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000888
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200889 mbedtls_camellia_context ctx;
Paul Bakker38119b12009-01-10 23:31:23 +0000890
Gilles Peskine449bd832023-01-11 14:50:10 +0100891 mbedtls_camellia_init(&ctx);
892 memset(key, 0, 32);
Paul Bakker38119b12009-01-10 23:31:23 +0000893
Gilles Peskine449bd832023-01-11 14:50:10 +0100894 for (j = 0; j < 6; j++) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000895 u = j >> 1;
Gilles Peskine449bd832023-01-11 14:50:10 +0100896 v = j & 1;
Paul Bakker38119b12009-01-10 23:31:23 +0000897
Gilles Peskine449bd832023-01-11 14:50:10 +0100898 if (verbose != 0) {
899 mbedtls_printf(" CAMELLIA-ECB-%3d (%s): ", 128 + u * 64,
900 (v == MBEDTLS_CAMELLIA_DECRYPT) ? "dec" : "enc");
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000901 }
Paul Bakker38119b12009-01-10 23:31:23 +0000902
Gilles Peskine449bd832023-01-11 14:50:10 +0100903 for (i = 0; i < CAMELLIA_TESTS_ECB; i++) {
904 memcpy(key, camellia_test_ecb_key[u][i], 16 + 8 * u);
Paul Bakker38119b12009-01-10 23:31:23 +0000905
Gilles Peskine449bd832023-01-11 14:50:10 +0100906 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");
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000928 }
929 }
Paul Bakker38119b12009-01-10 23:31:23 +0000930
Gilles Peskine449bd832023-01-11 14:50:10 +0100931 if (verbose != 0) {
932 mbedtls_printf("\n");
Paul Bakker38119b12009-01-10 23:31:23 +0000933 }
934
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200935#if defined(MBEDTLS_CIPHER_MODE_CBC)
Paul Bakker38119b12009-01-10 23:31:23 +0000936 /*
937 * CBC mode
938 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100939 for (j = 0; j < 6; j++) {
Paul Bakker38119b12009-01-10 23:31:23 +0000940 u = j >> 1;
941 v = j & 1;
942
Gilles Peskine449bd832023-01-11 14:50:10 +0100943 if (verbose != 0) {
944 mbedtls_printf(" CAMELLIA-CBC-%3d (%s): ", 128 + u * 64,
945 (v == MBEDTLS_CAMELLIA_DECRYPT) ? "dec" : "enc");
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000946 }
Paul Bakker38119b12009-01-10 23:31:23 +0000947
Gilles Peskine449bd832023-01-11 14:50:10 +0100948 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);
Paul Bakker38119b12009-01-10 23:31:23 +0000951
Gilles Peskine449bd832023-01-11 14:50:10 +0100952 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);
Janos Follath98e28a72016-05-31 14:03:54 +0100964 } else { /* MBEDTLS_CAMELLIA_ENCRYPT */
Gilles Peskine449bd832023-01-11 14:50:10 +0100965 memcpy(iv, dst, 16);
966 memcpy(src, camellia_test_cbc_plain[i], 16);
967 memcpy(dst, camellia_test_cbc_cipher[u][i], 16);
Janos Follath98e28a72016-05-31 14:03:54 +0100968 }
Paul Bakker38119b12009-01-10 23:31:23 +0000969
Gilles Peskine449bd832023-01-11 14:50:10 +0100970 mbedtls_camellia_crypt_cbc(&ctx, v, 16, iv, src, buf);
Janos Follath98e28a72016-05-31 14:03:54 +0100971
Gilles Peskine449bd832023-01-11 14:50:10 +0100972 if (memcmp(buf, dst, 16) != 0) {
973 if (verbose != 0) {
974 mbedtls_printf("failed\n");
975 }
Gilles Peskinec537aa82021-05-25 09:17:46 +0200976 goto exit;
Janos Follath98e28a72016-05-31 14:03:54 +0100977 }
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000978 }
Paul Bakker38119b12009-01-10 23:31:23 +0000979
Gilles Peskine449bd832023-01-11 14:50:10 +0100980 if (verbose != 0) {
981 mbedtls_printf("passed\n");
982 }
Paul Bakker38119b12009-01-10 23:31:23 +0000983 }
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200984#endif /* MBEDTLS_CIPHER_MODE_CBC */
Paul Bakker38119b12009-01-10 23:31:23 +0000985
Gilles Peskine449bd832023-01-11 14:50:10 +0100986 if (verbose != 0) {
987 mbedtls_printf("\n");
988 }
Paul Bakker38119b12009-01-10 23:31:23 +0000989
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +0200990#if defined(MBEDTLS_CIPHER_MODE_CTR)
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000991 /*
992 * CTR mode
993 */
Gilles Peskine449bd832023-01-11 14:50:10 +0100994 for (i = 0; i < 6; i++) {
Paul Bakkerb6ecaf52011-04-19 14:29:23 +0000995 u = i >> 1;
996 v = i & 1;
997
Gilles Peskine449bd832023-01-11 14:50:10 +0100998 if (verbose != 0) {
999 mbedtls_printf(" CAMELLIA-CTR-128 (%s): ",
1000 (v == MBEDTLS_CAMELLIA_DECRYPT) ? "dec" : "enc");
1001 }
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001002
Gilles Peskine449bd832023-01-11 14:50:10 +01001003 memcpy(nonce_counter, camellia_test_ctr_nonce_counter[u], 16);
1004 memcpy(key, camellia_test_ctr_key[u], 16);
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001005
1006 offset = 0;
Gilles Peskine449bd832023-01-11 14:50:10 +01001007 mbedtls_camellia_setkey_enc(&ctx, key, 128);
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001008
Gilles Peskine449bd832023-01-11 14:50:10 +01001009 if (v == MBEDTLS_CAMELLIA_DECRYPT) {
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001010 len = camellia_test_ctr_len[u];
Gilles Peskine449bd832023-01-11 14:50:10 +01001011 memcpy(buf, camellia_test_ctr_ct[u], len);
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001012
Gilles Peskine449bd832023-01-11 14:50:10 +01001013 mbedtls_camellia_crypt_ctr(&ctx, len, &offset, nonce_counter, stream_block,
1014 buf, buf);
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001015
Gilles Peskine449bd832023-01-11 14:50:10 +01001016 if (memcmp(buf, camellia_test_ctr_pt[u], len) != 0) {
1017 if (verbose != 0) {
1018 mbedtls_printf("failed\n");
1019 }
Gilles Peskinec537aa82021-05-25 09:17:46 +02001020 goto exit;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001021 }
Gilles Peskine449bd832023-01-11 14:50:10 +01001022 } else {
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001023 len = camellia_test_ctr_len[u];
Gilles Peskine449bd832023-01-11 14:50:10 +01001024 memcpy(buf, camellia_test_ctr_pt[u], len);
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001025
Gilles Peskine449bd832023-01-11 14:50:10 +01001026 mbedtls_camellia_crypt_ctr(&ctx, len, &offset, nonce_counter, stream_block,
1027 buf, buf);
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001028
Gilles Peskine449bd832023-01-11 14:50:10 +01001029 if (memcmp(buf, camellia_test_ctr_ct[u], len) != 0) {
1030 if (verbose != 0) {
1031 mbedtls_printf("failed\n");
1032 }
Gilles Peskinec537aa82021-05-25 09:17:46 +02001033 goto exit;
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001034 }
1035 }
1036
Gilles Peskine449bd832023-01-11 14:50:10 +01001037 if (verbose != 0) {
1038 mbedtls_printf("passed\n");
1039 }
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001040 }
1041
Gilles Peskine449bd832023-01-11 14:50:10 +01001042 if (verbose != 0) {
1043 mbedtls_printf("\n");
1044 }
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001045#endif /* MBEDTLS_CIPHER_MODE_CTR */
Paul Bakkerb6ecaf52011-04-19 14:29:23 +00001046
Gilles Peskinec537aa82021-05-25 09:17:46 +02001047 ret = 0;
1048
1049exit:
Gilles Peskine449bd832023-01-11 14:50:10 +01001050 mbedtls_camellia_free(&ctx);
1051 return ret;
Paul Bakker38119b12009-01-10 23:31:23 +00001052}
1053
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001054#endif /* MBEDTLS_SELF_TEST */
Paul Bakker38119b12009-01-10 23:31:23 +00001055
Manuel Pégourié-Gonnard2cf5a7c2015-04-08 12:49:31 +02001056#endif /* MBEDTLS_CAMELLIA_C */