blob: 11c0a236a49e1588454f1f8ed7feb1800bbec4eb [file] [log] [blame]
Paul Bakker38119b12009-01-10 23:31:23 +00001/*
2 * Camellia implementation
3 *
Paul Bakker84f12b72010-07-18 10:13:04 +00004 * Copyright (C) 2006-2010, Brainspark B.V.
5 * Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
Paul Bakker77b385e2009-07-28 17:23:11 +00006 * All rights reserved.
Paul Bakker38119b12009-01-10 23:31:23 +00007 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License along
19 * with this program; if not, write to the Free Software Foundation, Inc.,
20 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
21 */
22/*
Paul Bakkerb5ef0ba2009-01-11 20:25:36 +000023 * The Camellia block cipher was designed by NTT and Mitsubishi Electric
24 * Corporation.
Paul Bakker38119b12009-01-10 23:31:23 +000025 *
Paul Bakkerb5ef0ba2009-01-11 20:25:36 +000026 * http://info.isl.ntt.co.jp/crypt/eng/camellia/dl/01espec.pdf
Paul Bakker38119b12009-01-10 23:31:23 +000027 */
28
29#include "polarssl/config.h"
30
31#if defined(POLARSSL_CAMELLIA_C)
32
33#include "polarssl/camellia.h"
34
35#include <string.h>
36
Paul Bakker38119b12009-01-10 23:31:23 +000037/*
38 * 32-bit integer manipulation macros (big endian)
39 */
40#ifndef GET_ULONG_BE
41#define GET_ULONG_BE(n,b,i) \
42{ \
43 (n) = ( (unsigned long) (b)[(i) ] << 24 ) \
Paul Bakkerc81f6c32009-05-03 13:09:15 +000044 | ( (unsigned long) (b)[(i) + 1] << 16 ) \
45 | ( (unsigned long) (b)[(i) + 2] << 8 ) \
46 | ( (unsigned long) (b)[(i) + 3] ); \
Paul Bakker38119b12009-01-10 23:31:23 +000047}
48#endif
49
50#ifndef PUT_ULONG_BE
51#define PUT_ULONG_BE(n,b,i) \
52{ \
53 (b)[(i) ] = (unsigned char) ( (n) >> 24 ); \
54 (b)[(i) + 1] = (unsigned char) ( (n) >> 16 ); \
55 (b)[(i) + 2] = (unsigned char) ( (n) >> 8 ); \
56 (b)[(i) + 3] = (unsigned char) ( (n) ); \
57}
58#endif
59
60static const unsigned char SIGMA_CHARS[6][8] =
61{
Paul Bakkerc81f6c32009-05-03 13:09:15 +000062 { 0xa0, 0x9e, 0x66, 0x7f, 0x3b, 0xcc, 0x90, 0x8b },
63 { 0xb6, 0x7a, 0xe8, 0x58, 0x4c, 0xaa, 0x73, 0xb2 },
64 { 0xc6, 0xef, 0x37, 0x2f, 0xe9, 0x4f, 0x82, 0xbe },
65 { 0x54, 0xff, 0x53, 0xa5, 0xf1, 0xd3, 0x6f, 0x1c },
66 { 0x10, 0xe5, 0x27, 0xfa, 0xde, 0x68, 0x2d, 0x1d },
67 { 0xb0, 0x56, 0x88, 0xc2, 0xb3, 0xe6, 0xc1, 0xfd }
Paul Bakker38119b12009-01-10 23:31:23 +000068};
69
Paul Bakkerfa049db2009-01-12 22:12:03 +000070#ifdef POLARSSL_CAMELLIA_SMALL_MEMORY
71
72static const unsigned char FSb[256] =
Paul Bakker38119b12009-01-10 23:31:23 +000073{
Paul Bakkerc81f6c32009-05-03 13:09:15 +000074 112,130, 44,236,179, 39,192,229,228,133, 87, 53,234, 12,174, 65,
75 35,239,107,147, 69, 25,165, 33,237, 14, 79, 78, 29,101,146,189,
76 134,184,175,143,124,235, 31,206, 62, 48,220, 95, 94,197, 11, 26,
77 166,225, 57,202,213, 71, 93, 61,217, 1, 90,214, 81, 86,108, 77,
78 139, 13,154,102,251,204,176, 45,116, 18, 43, 32,240,177,132,153,
79 223, 76,203,194, 52,126,118, 5,109,183,169, 49,209, 23, 4,215,
80 20, 88, 58, 97,222, 27, 17, 28, 50, 15,156, 22, 83, 24,242, 34,
81 254, 68,207,178,195,181,122,145, 36, 8,232,168, 96,252,105, 80,
82 170,208,160,125,161,137, 98,151, 84, 91, 30,149,224,255,100,210,
83 16,196, 0, 72,163,247,117,219,138, 3,230,218, 9, 63,221,148,
84 135, 92,131, 2,205, 74,144, 51,115,103,246,243,157,127,191,226,
85 82,155,216, 38,200, 55,198, 59,129,150,111, 75, 19,190, 99, 46,
86 233,121,167,140,159,110,188,142, 41,245,249,182, 47,253,180, 89,
87 120,152, 6,106,231, 70,113,186,212, 37,171, 66,136,162,141,250,
88 114, 7,185, 85,248,238,172, 10, 54, 73, 42,104, 60, 56,241,164,
89 64, 40,211,123,187,201, 67,193, 21,227,173,244,119,199,128,158
Paul Bakker38119b12009-01-10 23:31:23 +000090};
91
92#define SBOX1(n) FSb[(n)]
93#define SBOX2(n) (unsigned char)((FSb[(n)] >> 7 ^ FSb[(n)] << 1) & 0xff)
94#define SBOX3(n) (unsigned char)((FSb[(n)] >> 1 ^ FSb[(n)] << 7) & 0xff)
Paul Bakkerfa049db2009-01-12 22:12:03 +000095#define SBOX4(n) FSb[((n) << 1 ^ (n) >> 7) &0xff]
96
97#else
98
Paul Bakkerc32c6b52009-01-11 21:36:43 +000099static const unsigned char FSb[256] =
100{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000101 112, 130, 44, 236, 179, 39, 192, 229, 228, 133, 87, 53, 234, 12, 174, 65,
102 35, 239, 107, 147, 69, 25, 165, 33, 237, 14, 79, 78, 29, 101, 146, 189,
103 134, 184, 175, 143, 124, 235, 31, 206, 62, 48, 220, 95, 94, 197, 11, 26,
104 166, 225, 57, 202, 213, 71, 93, 61, 217, 1, 90, 214, 81, 86, 108, 77,
105 139, 13, 154, 102, 251, 204, 176, 45, 116, 18, 43, 32, 240, 177, 132, 153,
106 223, 76, 203, 194, 52, 126, 118, 5, 109, 183, 169, 49, 209, 23, 4, 215,
107 20, 88, 58, 97, 222, 27, 17, 28, 50, 15, 156, 22, 83, 24, 242, 34,
108 254, 68, 207, 178, 195, 181, 122, 145, 36, 8, 232, 168, 96, 252, 105, 80,
109 170, 208, 160, 125, 161, 137, 98, 151, 84, 91, 30, 149, 224, 255, 100, 210,
110 16, 196, 0, 72, 163, 247, 117, 219, 138, 3, 230, 218, 9, 63, 221, 148,
111 135, 92, 131, 2, 205, 74, 144, 51, 115, 103, 246, 243, 157, 127, 191, 226,
112 82, 155, 216, 38, 200, 55, 198, 59, 129, 150, 111, 75, 19, 190, 99, 46,
113 233, 121, 167, 140, 159, 110, 188, 142, 41, 245, 249, 182, 47, 253, 180, 89,
114 120, 152, 6, 106, 231, 70, 113, 186, 212, 37, 171, 66, 136, 162, 141, 250,
115 114, 7, 185, 85, 248, 238, 172, 10, 54, 73, 42, 104, 60, 56, 241, 164,
116 64, 40, 211, 123, 187, 201, 67, 193, 21, 227, 173, 244, 119, 199, 128, 158
Paul Bakkerc32c6b52009-01-11 21:36:43 +0000117};
118
119static const unsigned char FSb2[256] =
120{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000121 224, 5, 88, 217, 103, 78, 129, 203, 201, 11, 174, 106, 213, 24, 93, 130,
122 70, 223, 214, 39, 138, 50, 75, 66, 219, 28, 158, 156, 58, 202, 37, 123,
123 13, 113, 95, 31, 248, 215, 62, 157, 124, 96, 185, 190, 188, 139, 22, 52,
124 77, 195, 114, 149, 171, 142, 186, 122, 179, 2, 180, 173, 162, 172, 216, 154,
125 23, 26, 53, 204, 247, 153, 97, 90, 232, 36, 86, 64, 225, 99, 9, 51,
126 191, 152, 151, 133, 104, 252, 236, 10, 218, 111, 83, 98, 163, 46, 8, 175,
127 40, 176, 116, 194, 189, 54, 34, 56, 100, 30, 57, 44, 166, 48, 229, 68,
128 253, 136, 159, 101, 135, 107, 244, 35, 72, 16, 209, 81, 192, 249, 210, 160,
129 85, 161, 65, 250, 67, 19, 196, 47, 168, 182, 60, 43, 193, 255, 200, 165,
130 32, 137, 0, 144, 71, 239, 234, 183, 21, 6, 205, 181, 18, 126, 187, 41,
131 15, 184, 7, 4, 155, 148, 33, 102, 230, 206, 237, 231, 59, 254, 127, 197,
132 164, 55, 177, 76, 145, 110, 141, 118, 3, 45, 222, 150, 38, 125, 198, 92,
133 211, 242, 79, 25, 63, 220, 121, 29, 82, 235, 243, 109, 94, 251, 105, 178,
134 240, 49, 12, 212, 207, 140, 226, 117, 169, 74, 87, 132, 17, 69, 27, 245,
135 228, 14, 115, 170, 241, 221, 89, 20, 108, 146, 84, 208, 120, 112, 227, 73,
136 128, 80, 167, 246, 119, 147, 134, 131, 42, 199, 91, 233, 238, 143, 1, 61
Paul Bakkerc32c6b52009-01-11 21:36:43 +0000137};
138
139static const unsigned char FSb3[256] =
140{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000141 56, 65, 22, 118, 217, 147, 96, 242, 114, 194, 171, 154, 117, 6, 87, 160,
142 145, 247, 181, 201, 162, 140, 210, 144, 246, 7, 167, 39, 142, 178, 73, 222,
143 67, 92, 215, 199, 62, 245, 143, 103, 31, 24, 110, 175, 47, 226, 133, 13,
144 83, 240, 156, 101, 234, 163, 174, 158, 236, 128, 45, 107, 168, 43, 54, 166,
145 197, 134, 77, 51, 253, 102, 88, 150, 58, 9, 149, 16, 120, 216, 66, 204,
146 239, 38, 229, 97, 26, 63, 59, 130, 182, 219, 212, 152, 232, 139, 2, 235,
147 10, 44, 29, 176, 111, 141, 136, 14, 25, 135, 78, 11, 169, 12, 121, 17,
148 127, 34, 231, 89, 225, 218, 61, 200, 18, 4, 116, 84, 48, 126, 180, 40,
149 85, 104, 80, 190, 208, 196, 49, 203, 42, 173, 15, 202, 112, 255, 50, 105,
150 8, 98, 0, 36, 209, 251, 186, 237, 69, 129, 115, 109, 132, 159, 238, 74,
151 195, 46, 193, 1, 230, 37, 72, 153, 185, 179, 123, 249, 206, 191, 223, 113,
152 41, 205, 108, 19, 100, 155, 99, 157, 192, 75, 183, 165, 137, 95, 177, 23,
153 244, 188, 211, 70, 207, 55, 94, 71, 148, 250, 252, 91, 151, 254, 90, 172,
154 60, 76, 3, 53, 243, 35, 184, 93, 106, 146, 213, 33, 68, 81, 198, 125,
155 57, 131, 220, 170, 124, 119, 86, 5, 27, 164, 21, 52, 30, 28, 248, 82,
156 32, 20, 233, 189, 221, 228, 161, 224, 138, 241, 214, 122, 187, 227, 64, 79
Paul Bakkerc32c6b52009-01-11 21:36:43 +0000157};
158
159static const unsigned char FSb4[256] =
160{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000161 112, 44, 179, 192, 228, 87, 234, 174, 35, 107, 69, 165, 237, 79, 29, 146,
162 134, 175, 124, 31, 62, 220, 94, 11, 166, 57, 213, 93, 217, 90, 81, 108,
163 139, 154, 251, 176, 116, 43, 240, 132, 223, 203, 52, 118, 109, 169, 209, 4,
164 20, 58, 222, 17, 50, 156, 83, 242, 254, 207, 195, 122, 36, 232, 96, 105,
165 170, 160, 161, 98, 84, 30, 224, 100, 16, 0, 163, 117, 138, 230, 9, 221,
166 135, 131, 205, 144, 115, 246, 157, 191, 82, 216, 200, 198, 129, 111, 19, 99,
167 233, 167, 159, 188, 41, 249, 47, 180, 120, 6, 231, 113, 212, 171, 136, 141,
168 114, 185, 248, 172, 54, 42, 60, 241, 64, 211, 187, 67, 21, 173, 119, 128,
169 130, 236, 39, 229, 133, 53, 12, 65, 239, 147, 25, 33, 14, 78, 101, 189,
170 184, 143, 235, 206, 48, 95, 197, 26, 225, 202, 71, 61, 1, 214, 86, 77,
171 13, 102, 204, 45, 18, 32, 177, 153, 76, 194, 126, 5, 183, 49, 23, 215,
172 88, 97, 27, 28, 15, 22, 24, 34, 68, 178, 181, 145, 8, 168, 252, 80,
173 208, 125, 137, 151, 91, 149, 255, 210, 196, 72, 247, 219, 3, 218, 63, 148,
174 92, 2, 74, 51, 103, 243, 127, 226, 155, 38, 55, 59, 150, 75, 190, 46,
175 121, 140, 110, 142, 245, 182, 253, 89, 152, 106, 70, 186, 37, 66, 162, 250,
176 7, 85, 238, 10, 73, 104, 56, 164, 40, 123, 201, 193, 227, 244, 199, 158
Paul Bakkerc32c6b52009-01-11 21:36:43 +0000177};
178
179#define SBOX1(n) FSb[(n)]
180#define SBOX2(n) FSb2[(n)]
181#define SBOX3(n) FSb3[(n)]
182#define SBOX4(n) FSb4[(n)]
Paul Bakker38119b12009-01-10 23:31:23 +0000183
Paul Bakkerfa049db2009-01-12 22:12:03 +0000184#endif
185
Paul Bakker38119b12009-01-10 23:31:23 +0000186static const unsigned char shifts[2][4][4] =
187{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000188 {
189 { 1, 1, 1, 1 }, /* KL */
190 { 0, 0, 0, 0 }, /* KR */
191 { 1, 1, 1, 1 }, /* KA */
192 { 0, 0, 0, 0 } /* KB */
193 },
194 {
195 { 1, 0, 1, 1 }, /* KL */
196 { 1, 1, 0, 1 }, /* KR */
197 { 1, 1, 1, 0 }, /* KA */
198 { 1, 1, 0, 1 } /* KB */
199 }
Paul Bakker38119b12009-01-10 23:31:23 +0000200};
201
Paul Bakker026c03b2009-03-28 17:53:03 +0000202static const signed char indexes[2][4][20] =
Paul Bakker38119b12009-01-10 23:31:23 +0000203{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000204 {
205 { 0, 1, 2, 3, 8, 9, 10, 11, 38, 39,
206 36, 37, 23, 20, 21, 22, 27, -1, -1, 26 }, /* KL -> RK */
207 { -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
208 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1 }, /* KR -> RK */
209 { 4, 5, 6, 7, 12, 13, 14, 15, 16, 17,
210 18, 19, -1, 24, 25, -1, 31, 28, 29, 30 }, /* KA -> RK */
211 { -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
212 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1 } /* KB -> RK */
213 },
214 {
215 { 0, 1, 2, 3, 61, 62, 63, 60, -1, -1,
216 -1, -1, 27, 24, 25, 26, 35, 32, 33, 34 }, /* KL -> RK */
217 { -1, -1, -1, -1, 8, 9, 10, 11, 16, 17,
218 18, 19, -1, -1, -1, -1, 39, 36, 37, 38 }, /* KR -> RK */
219 { -1, -1, -1, -1, 12, 13, 14, 15, 58, 59,
220 56, 57, 31, 28, 29, 30, -1, -1, -1, -1 }, /* KA -> RK */
221 { 4, 5, 6, 7, 65, 66, 67, 64, 20, 21,
222 22, 23, -1, -1, -1, -1, 43, 40, 41, 42 } /* KB -> RK */
223 }
Paul Bakker38119b12009-01-10 23:31:23 +0000224};
225
Paul Bakker026c03b2009-03-28 17:53:03 +0000226static const signed char transposes[2][20] =
Paul Bakker38119b12009-01-10 23:31:23 +0000227{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000228 {
229 21, 22, 23, 20,
230 -1, -1, -1, -1,
231 18, 19, 16, 17,
232 11, 8, 9, 10,
233 15, 12, 13, 14
234 },
235 {
236 25, 26, 27, 24,
237 29, 30, 31, 28,
238 18, 19, 16, 17,
239 -1, -1, -1, -1,
240 -1, -1, -1, -1
241 }
Paul Bakker38119b12009-01-10 23:31:23 +0000242};
243
Paul Bakkerc32c6b52009-01-11 21:36:43 +0000244/* Shift macro for 128 bit strings with rotation smaller than 32 bits (!) */
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000245#define ROTL(DEST, SRC, SHIFT) \
246{ \
247 (DEST)[0] = (SRC)[0] << (SHIFT) ^ (SRC)[1] >> (32 - (SHIFT)); \
248 (DEST)[1] = (SRC)[1] << (SHIFT) ^ (SRC)[2] >> (32 - (SHIFT)); \
249 (DEST)[2] = (SRC)[2] << (SHIFT) ^ (SRC)[3] >> (32 - (SHIFT)); \
250 (DEST)[3] = (SRC)[3] << (SHIFT) ^ (SRC)[0] >> (32 - (SHIFT)); \
Paul Bakker38119b12009-01-10 23:31:23 +0000251}
252
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000253#define FL(XL, XR, KL, KR) \
254{ \
255 (XR) = ((((XL) & (KL)) << 1) | (((XL) & (KL)) >> 31)) ^ (XR); \
256 (XL) = ((XR) | (KR)) ^ (XL); \
Paul Bakker38119b12009-01-10 23:31:23 +0000257}
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000258
259#define FLInv(YL, YR, KL, KR) \
260{ \
261 (YL) = ((YR) | (KR)) ^ (YL); \
262 (YR) = ((((YL) & (KL)) << 1) | (((YL) & (KL)) >> 31)) ^ (YR); \
Paul Bakker38119b12009-01-10 23:31:23 +0000263}
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000264
265#define SHIFT_AND_PLACE(INDEX, OFFSET) \
266{ \
267 TK[0] = KC[(OFFSET) * 4 + 0]; \
268 TK[1] = KC[(OFFSET) * 4 + 1]; \
269 TK[2] = KC[(OFFSET) * 4 + 2]; \
270 TK[3] = KC[(OFFSET) * 4 + 3]; \
271 \
272 for ( i = 1; i <= 4; i++ ) \
273 if (shifts[(INDEX)][(OFFSET)][i -1]) \
274 ROTL(TK + i * 4, TK, (15 * i) % 32); \
275 \
276 for ( i = 0; i < 20; i++ ) \
277 if (indexes[(INDEX)][(OFFSET)][i] != -1) { \
278 RK[indexes[(INDEX)][(OFFSET)][i]] = TK[ i ]; \
279 } \
Paul Bakker38119b12009-01-10 23:31:23 +0000280}
281
Paul Bakkerff60ee62010-03-16 21:09:09 +0000282static void camellia_feistel(const uint32_t x[2], const uint32_t k[2], uint32_t z[2])
Paul Bakker38119b12009-01-10 23:31:23 +0000283{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000284 uint32_t I0, I1;
285 I0 = x[0] ^ k[0];
286 I1 = x[1] ^ k[1];
Paul Bakker38119b12009-01-10 23:31:23 +0000287
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000288 I0 = (SBOX1((I0 >> 24) & 0xFF) << 24) |
289 (SBOX2((I0 >> 16) & 0xFF) << 16) |
290 (SBOX3((I0 >> 8) & 0xFF) << 8) |
291 (SBOX4((I0 ) & 0xFF) );
292 I1 = (SBOX2((I1 >> 24) & 0xFF) << 24) |
293 (SBOX3((I1 >> 16) & 0xFF) << 16) |
294 (SBOX4((I1 >> 8) & 0xFF) << 8) |
295 (SBOX1((I1 ) & 0xFF) );
Paul Bakker38119b12009-01-10 23:31:23 +0000296
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000297 I0 ^= (I1 << 8) | (I1 >> 24);
298 I1 ^= (I0 << 16) | (I0 >> 16);
299 I0 ^= (I1 >> 8) | (I1 << 24);
300 I1 ^= (I0 >> 8) | (I0 << 24);
Paul Bakker38119b12009-01-10 23:31:23 +0000301
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000302 z[0] ^= I1;
303 z[1] ^= I0;
Paul Bakker38119b12009-01-10 23:31:23 +0000304}
305
306/*
307 * Camellia key schedule (encryption)
308 */
Paul Bakkerff60ee62010-03-16 21:09:09 +0000309int camellia_setkey_enc( camellia_context *ctx, const unsigned char *key, int keysize )
Paul Bakker38119b12009-01-10 23:31:23 +0000310{
311 int i, idx;
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000312 uint32_t *RK;
Paul Bakker38119b12009-01-10 23:31:23 +0000313 unsigned char t[64];
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000314 uint32_t SIGMA[6][2];
315 uint32_t KC[16];
316 uint32_t TK[20];
Paul Bakker38119b12009-01-10 23:31:23 +0000317
318 RK = ctx->rk;
319
320 memset(t, 0, 64);
321 memset(RK, 0, sizeof(ctx->rk));
322
323 switch( keysize )
324 {
325 case 128: ctx->nr = 3; idx = 0; break;
326 case 192:
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000327 case 256: ctx->nr = 4; idx = 1; break;
Paul Bakker2b222c82009-07-27 21:03:45 +0000328 default : return( POLARSSL_ERR_CAMELLIA_INVALID_KEY_LENGTH );
Paul Bakker38119b12009-01-10 23:31:23 +0000329 }
330
331 for( i = 0; i < keysize / 8; ++i)
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000332 t[i] = key[i];
Paul Bakker38119b12009-01-10 23:31:23 +0000333
334 if (keysize == 192) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000335 for (i = 0; i < 8; i++)
336 t[24 + i] = ~t[16 + i];
Paul Bakker38119b12009-01-10 23:31:23 +0000337 }
338
Paul Bakker38119b12009-01-10 23:31:23 +0000339 /*
340 * Prepare SIGMA values
341 */
Paul Bakker38119b12009-01-10 23:31:23 +0000342 for (i = 0; i < 6; i++) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000343 GET_ULONG_BE(SIGMA[i][0], SIGMA_CHARS[i], 0);
344 GET_ULONG_BE(SIGMA[i][1], SIGMA_CHARS[i], 4);
Paul Bakker38119b12009-01-10 23:31:23 +0000345 }
346
347 /*
348 * Key storage in KC
349 * Order: KL, KR, KA, KB
350 */
Paul Bakker38119b12009-01-10 23:31:23 +0000351 memset(KC, 0, sizeof(KC));
352
353 /* Store KL, KR */
354 for (i = 0; i < 8; i++)
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000355 GET_ULONG_BE(KC[i], t, i * 4);
Paul Bakker38119b12009-01-10 23:31:23 +0000356
357 /* Generate KA */
358 for( i = 0; i < 4; ++i)
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000359 KC[8 + i] = KC[i] ^ KC[4 + i];
Paul Bakker38119b12009-01-10 23:31:23 +0000360
361 camellia_feistel(KC + 8, SIGMA[0], KC + 10);
362 camellia_feistel(KC + 10, SIGMA[1], KC + 8);
363
364 for( i = 0; i < 4; ++i)
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000365 KC[8 + i] ^= KC[i];
Paul Bakker38119b12009-01-10 23:31:23 +0000366
367 camellia_feistel(KC + 8, SIGMA[2], KC + 10);
368 camellia_feistel(KC + 10, SIGMA[3], KC + 8);
369
370 if (keysize > 128) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000371 /* Generate KB */
372 for( i = 0; i < 4; ++i)
373 KC[12 + i] = KC[4 + i] ^ KC[8 + i];
Paul Bakker38119b12009-01-10 23:31:23 +0000374
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000375 camellia_feistel(KC + 12, SIGMA[4], KC + 14);
376 camellia_feistel(KC + 14, SIGMA[5], KC + 12);
Paul Bakker38119b12009-01-10 23:31:23 +0000377 }
378
379 /*
380 * Generating subkeys
381 */
Paul Bakker38119b12009-01-10 23:31:23 +0000382
383 /* Manipulating KL */
384 SHIFT_AND_PLACE(idx, 0);
385
386 /* Manipulating KR */
387 if (keysize > 128) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000388 SHIFT_AND_PLACE(idx, 1);
Paul Bakker38119b12009-01-10 23:31:23 +0000389 }
390
391 /* Manipulating KA */
392 SHIFT_AND_PLACE(idx, 2);
393
394 /* Manipulating KB */
395 if (keysize > 128) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000396 SHIFT_AND_PLACE(idx, 3);
Paul Bakker38119b12009-01-10 23:31:23 +0000397 }
398
399 /* Do transpositions */
400 for ( i = 0; i < 20; i++ ) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000401 if (transposes[idx][i] != -1) {
402 RK[32 + 12 * idx + i] = RK[transposes[idx][i]];
403 }
Paul Bakker38119b12009-01-10 23:31:23 +0000404 }
Paul Bakker2b222c82009-07-27 21:03:45 +0000405
406 return( 0 );
Paul Bakker38119b12009-01-10 23:31:23 +0000407}
408
409/*
410 * Camellia key schedule (decryption)
411 */
Paul Bakkerff60ee62010-03-16 21:09:09 +0000412int camellia_setkey_dec( camellia_context *ctx, const unsigned char *key, int keysize )
Paul Bakker38119b12009-01-10 23:31:23 +0000413{
414 int i, idx;
415 camellia_context cty;
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000416 uint32_t *RK;
417 uint32_t *SK;
Paul Bakker2b222c82009-07-27 21:03:45 +0000418 int ret;
Paul Bakker38119b12009-01-10 23:31:23 +0000419
420 switch( keysize )
421 {
422 case 128: ctx->nr = 3; idx = 0; break;
423 case 192:
424 case 256: ctx->nr = 4; idx = 1; break;
Paul Bakker2b222c82009-07-27 21:03:45 +0000425 default : return( POLARSSL_ERR_CAMELLIA_INVALID_KEY_LENGTH );
Paul Bakker38119b12009-01-10 23:31:23 +0000426 }
427
428 RK = ctx->rk;
429
Paul Bakker2b222c82009-07-27 21:03:45 +0000430 ret = camellia_setkey_enc(&cty, key, keysize);
431 if( ret != 0 )
432 return( ret );
Paul Bakker38119b12009-01-10 23:31:23 +0000433
434 SK = cty.rk + 24 * 2 + 8 * idx * 2;
435
436 *RK++ = *SK++;
437 *RK++ = *SK++;
438 *RK++ = *SK++;
439 *RK++ = *SK++;
440
441 for (i = 22 + 8 * idx, SK -= 6; i > 0; i--, SK -= 4)
442 {
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
454 memset( &cty, 0, sizeof( camellia_context ) );
Paul Bakker2b222c82009-07-27 21:03:45 +0000455
456 return( 0 );
Paul Bakker38119b12009-01-10 23:31:23 +0000457}
458
459/*
460 * Camellia-ECB block encryption/decryption
461 */
Paul Bakkerf3ccc682010-03-18 21:21:02 +0000462int camellia_crypt_ecb( camellia_context *ctx,
Paul Bakker38119b12009-01-10 23:31:23 +0000463 int mode,
Paul Bakkerff60ee62010-03-16 21:09:09 +0000464 const unsigned char input[16],
Paul Bakker38119b12009-01-10 23:31:23 +0000465 unsigned char output[16] )
466{
Paul Bakker026c03b2009-03-28 17:53:03 +0000467 int NR;
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000468 uint32_t *RK, X[4];
Paul Bakker38119b12009-01-10 23:31:23 +0000469
Paul Bakkerc2547b02009-07-20 20:40:52 +0000470 ( (void) mode );
471
Paul Bakker38119b12009-01-10 23:31:23 +0000472 NR = ctx->nr;
473 RK = ctx->rk;
474
Paul Bakker38119b12009-01-10 23:31:23 +0000475 GET_ULONG_BE( X[0], input, 0 );
476 GET_ULONG_BE( X[1], input, 4 );
477 GET_ULONG_BE( X[2], input, 8 );
478 GET_ULONG_BE( X[3], input, 12 );
479
480 X[0] ^= *RK++;
481 X[1] ^= *RK++;
482 X[2] ^= *RK++;
483 X[3] ^= *RK++;
484
485 while (NR) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000486 --NR;
487 camellia_feistel(X, RK, X + 2);
488 RK += 2;
489 camellia_feistel(X + 2, RK, X);
490 RK += 2;
491 camellia_feistel(X, RK, X + 2);
492 RK += 2;
493 camellia_feistel(X + 2, RK, X);
494 RK += 2;
495 camellia_feistel(X, RK, X + 2);
496 RK += 2;
497 camellia_feistel(X + 2, RK, X);
498 RK += 2;
Paul Bakker38119b12009-01-10 23:31:23 +0000499
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000500 if (NR) {
501 FL(X[0], X[1], RK[0], RK[1]);
502 RK += 2;
503 FLInv(X[2], X[3], RK[0], RK[1]);
504 RK += 2;
505 }
Paul Bakker38119b12009-01-10 23:31:23 +0000506 }
507
508 X[2] ^= *RK++;
509 X[3] ^= *RK++;
510 X[0] ^= *RK++;
511 X[1] ^= *RK++;
512
513 PUT_ULONG_BE( X[2], output, 0 );
514 PUT_ULONG_BE( X[3], output, 4 );
515 PUT_ULONG_BE( X[0], output, 8 );
516 PUT_ULONG_BE( X[1], output, 12 );
Paul Bakkerf3ccc682010-03-18 21:21:02 +0000517
518 return( 0 );
Paul Bakker38119b12009-01-10 23:31:23 +0000519}
520
521/*
522 * Camellia-CBC buffer encryption/decryption
523 */
Paul Bakkerf3ccc682010-03-18 21:21:02 +0000524int camellia_crypt_cbc( camellia_context *ctx,
Paul Bakker38119b12009-01-10 23:31:23 +0000525 int mode,
526 int length,
527 unsigned char iv[16],
Paul Bakkerff60ee62010-03-16 21:09:09 +0000528 const unsigned char *input,
Paul Bakker38119b12009-01-10 23:31:23 +0000529 unsigned char *output )
530{
531 int i;
532 unsigned char temp[16];
533
Paul Bakkerf3ccc682010-03-18 21:21:02 +0000534 if( length % 16 )
535 return( POLARSSL_ERR_CAMELLIA_INVALID_INPUT_LENGTH );
536
Paul Bakker38119b12009-01-10 23:31:23 +0000537 if( mode == CAMELLIA_DECRYPT )
538 {
539 while( length > 0 )
540 {
541 memcpy( temp, input, 16 );
542 camellia_crypt_ecb( ctx, mode, input, output );
543
544 for( i = 0; i < 16; i++ )
545 output[i] = (unsigned char)( output[i] ^ iv[i] );
546
547 memcpy( iv, temp, 16 );
548
549 input += 16;
550 output += 16;
551 length -= 16;
552 }
553 }
554 else
555 {
556 while( length > 0 )
557 {
558 for( i = 0; i < 16; i++ )
559 output[i] = (unsigned char)( input[i] ^ iv[i] );
560
561 camellia_crypt_ecb( ctx, mode, output, output );
562 memcpy( iv, output, 16 );
563
564 input += 16;
565 output += 16;
566 length -= 16;
567 }
568 }
Paul Bakkerf3ccc682010-03-18 21:21:02 +0000569
570 return( 0 );
Paul Bakker38119b12009-01-10 23:31:23 +0000571}
572
573/*
574 * Camellia-CFB128 buffer encryption/decryption
575 */
Paul Bakkerf3ccc682010-03-18 21:21:02 +0000576int camellia_crypt_cfb128( camellia_context *ctx,
Paul Bakker38119b12009-01-10 23:31:23 +0000577 int mode,
578 int length,
579 int *iv_off,
580 unsigned char iv[16],
Paul Bakkerff60ee62010-03-16 21:09:09 +0000581 const unsigned char *input,
Paul Bakker38119b12009-01-10 23:31:23 +0000582 unsigned char *output )
583{
584 int c, n = *iv_off;
585
586 if( mode == CAMELLIA_DECRYPT )
587 {
588 while( length-- )
589 {
590 if( n == 0 )
591 camellia_crypt_ecb( ctx, CAMELLIA_ENCRYPT, iv, iv );
592
593 c = *input++;
594 *output++ = (unsigned char)( c ^ iv[n] );
595 iv[n] = (unsigned char) c;
596
597 n = (n + 1) & 0x0F;
598 }
599 }
600 else
601 {
602 while( length-- )
603 {
604 if( n == 0 )
605 camellia_crypt_ecb( ctx, CAMELLIA_ENCRYPT, iv, iv );
606
607 iv[n] = *output++ = (unsigned char)( iv[n] ^ *input++ );
608
609 n = (n + 1) & 0x0F;
610 }
611 }
612
613 *iv_off = n;
Paul Bakkerf3ccc682010-03-18 21:21:02 +0000614
615 return( 0 );
Paul Bakker38119b12009-01-10 23:31:23 +0000616}
617
618#if defined(POLARSSL_SELF_TEST)
619
620#include <stdio.h>
621
622/*
623 * Camellia test vectors from:
624 *
625 * http://info.isl.ntt.co.jp/crypt/eng/camellia/technology.html:
626 * http://info.isl.ntt.co.jp/crypt/eng/camellia/dl/cryptrec/intermediate.txt
627 * http://info.isl.ntt.co.jp/crypt/eng/camellia/dl/cryptrec/t_camellia.txt
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000628 * (For each bitlength: Key 0, Nr 39)
Paul Bakker38119b12009-01-10 23:31:23 +0000629 */
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000630#define CAMELLIA_TESTS_ECB 2
Paul Bakker38119b12009-01-10 23:31:23 +0000631
632static const unsigned char camellia_test_ecb_key[3][CAMELLIA_TESTS_ECB][32] =
633{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000634 {
635 { 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef,
636 0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54, 0x32, 0x10 },
637 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
638 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
639 },
640 {
641 { 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef,
642 0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54, 0x32, 0x10,
643 0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77 },
644 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
645 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
646 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
647 },
648 {
649 { 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef,
650 0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54, 0x32, 0x10,
651 0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77,
652 0x88, 0x99, 0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff },
653 { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
654 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
655 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
656 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
657 },
Paul Bakker38119b12009-01-10 23:31:23 +0000658};
659
660static const unsigned char camellia_test_ecb_plain[CAMELLIA_TESTS_ECB][16] =
661{
662 { 0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef,
663 0xfe, 0xdc, 0xba, 0x98, 0x76, 0x54, 0x32, 0x10 },
664 { 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
665 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }
666};
667
668static const unsigned char camellia_test_ecb_cipher[3][CAMELLIA_TESTS_ECB][16] =
669{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000670 {
671 { 0x67, 0x67, 0x31, 0x38, 0x54, 0x96, 0x69, 0x73,
672 0x08, 0x57, 0x06, 0x56, 0x48, 0xea, 0xbe, 0x43 },
673 { 0x38, 0x3C, 0x6C, 0x2A, 0xAB, 0xEF, 0x7F, 0xDE,
674 0x25, 0xCD, 0x47, 0x0B, 0xF7, 0x74, 0xA3, 0x31 }
675 },
676 {
677 { 0xb4, 0x99, 0x34, 0x01, 0xb3, 0xe9, 0x96, 0xf8,
678 0x4e, 0xe5, 0xce, 0xe7, 0xd7, 0x9b, 0x09, 0xb9 },
679 { 0xD1, 0x76, 0x3F, 0xC0, 0x19, 0xD7, 0x7C, 0xC9,
680 0x30, 0xBF, 0xF2, 0xA5, 0x6F, 0x7C, 0x93, 0x64 }
681 },
682 {
683 { 0x9a, 0xcc, 0x23, 0x7d, 0xff, 0x16, 0xd7, 0x6c,
684 0x20, 0xef, 0x7c, 0x91, 0x9e, 0x3a, 0x75, 0x09 },
685 { 0x05, 0x03, 0xFB, 0x10, 0xAB, 0x24, 0x1E, 0x7C,
686 0xF4, 0x5D, 0x8C, 0xDE, 0xEE, 0x47, 0x43, 0x35 }
687 }
Paul Bakker38119b12009-01-10 23:31:23 +0000688};
689
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000690#define CAMELLIA_TESTS_CBC 3
Paul Bakker38119b12009-01-10 23:31:23 +0000691
692static const unsigned char camellia_test_cbc_key[3][32] =
693{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000694 { 0x2B, 0x7E, 0x15, 0x16, 0x28, 0xAE, 0xD2, 0xA6,
695 0xAB, 0xF7, 0x15, 0x88, 0x09, 0xCF, 0x4F, 0x3C }
696 ,
697 { 0x8E, 0x73, 0xB0, 0xF7, 0xDA, 0x0E, 0x64, 0x52,
698 0xC8, 0x10, 0xF3, 0x2B, 0x80, 0x90, 0x79, 0xE5,
699 0x62, 0xF8, 0xEA, 0xD2, 0x52, 0x2C, 0x6B, 0x7B }
700 ,
701 { 0x60, 0x3D, 0xEB, 0x10, 0x15, 0xCA, 0x71, 0xBE,
702 0x2B, 0x73, 0xAE, 0xF0, 0x85, 0x7D, 0x77, 0x81,
703 0x1F, 0x35, 0x2C, 0x07, 0x3B, 0x61, 0x08, 0xD7,
704 0x2D, 0x98, 0x10, 0xA3, 0x09, 0x14, 0xDF, 0xF4 }
Paul Bakker38119b12009-01-10 23:31:23 +0000705};
706
707static const unsigned char camellia_test_cbc_iv[16] =
708
709 { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
710 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F }
711;
712
713static const unsigned char camellia_test_cbc_plain[CAMELLIA_TESTS_CBC][16] =
714{
715 { 0x6B, 0xC1, 0xBE, 0xE2, 0x2E, 0x40, 0x9F, 0x96,
716 0xE9, 0x3D, 0x7E, 0x11, 0x73, 0x93, 0x17, 0x2A },
717 { 0xAE, 0x2D, 0x8A, 0x57, 0x1E, 0x03, 0xAC, 0x9C,
718 0x9E, 0xB7, 0x6F, 0xAC, 0x45, 0xAF, 0x8E, 0x51 },
719 { 0x30, 0xC8, 0x1C, 0x46, 0xA3, 0x5C, 0xE4, 0x11,
720 0xE5, 0xFB, 0xC1, 0x19, 0x1A, 0x0A, 0x52, 0xEF }
721
722};
723
724static const unsigned char camellia_test_cbc_cipher[3][CAMELLIA_TESTS_CBC][16] =
725{
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000726 {
727 { 0x16, 0x07, 0xCF, 0x49, 0x4B, 0x36, 0xBB, 0xF0,
728 0x0D, 0xAE, 0xB0, 0xB5, 0x03, 0xC8, 0x31, 0xAB },
729 { 0xA2, 0xF2, 0xCF, 0x67, 0x16, 0x29, 0xEF, 0x78,
730 0x40, 0xC5, 0xA5, 0xDF, 0xB5, 0x07, 0x48, 0x87 },
731 { 0x0F, 0x06, 0x16, 0x50, 0x08, 0xCF, 0x8B, 0x8B,
732 0x5A, 0x63, 0x58, 0x63, 0x62, 0x54, 0x3E, 0x54 }
733 },
734 {
735 { 0x2A, 0x48, 0x30, 0xAB, 0x5A, 0xC4, 0xA1, 0xA2,
736 0x40, 0x59, 0x55, 0xFD, 0x21, 0x95, 0xCF, 0x93 },
737 { 0x5D, 0x5A, 0x86, 0x9B, 0xD1, 0x4C, 0xE5, 0x42,
738 0x64, 0xF8, 0x92, 0xA6, 0xDD, 0x2E, 0xC3, 0xD5 },
739 { 0x37, 0xD3, 0x59, 0xC3, 0x34, 0x98, 0x36, 0xD8,
740 0x84, 0xE3, 0x10, 0xAD, 0xDF, 0x68, 0xC4, 0x49 }
741 },
742 {
743 { 0xE6, 0xCF, 0xA3, 0x5F, 0xC0, 0x2B, 0x13, 0x4A,
744 0x4D, 0x2C, 0x0B, 0x67, 0x37, 0xAC, 0x3E, 0xDA },
745 { 0x36, 0xCB, 0xEB, 0x73, 0xBD, 0x50, 0x4B, 0x40,
746 0x70, 0xB1, 0xB7, 0xDE, 0x2B, 0x21, 0xEB, 0x50 },
747 { 0xE3, 0x1A, 0x60, 0x55, 0x29, 0x7D, 0x96, 0xCA,
748 0x33, 0x30, 0xCD, 0xF1, 0xB1, 0x86, 0x0A, 0x83 }
749 }
Paul Bakker38119b12009-01-10 23:31:23 +0000750};
751
752
753/*
754 * Checkup routine
755 */
756int camellia_self_test( int verbose )
757{
Paul Bakker026c03b2009-03-28 17:53:03 +0000758 int i, j, u, v;
Paul Bakker38119b12009-01-10 23:31:23 +0000759 unsigned char key[32];
760 unsigned char buf[64];
Paul Bakker38119b12009-01-10 23:31:23 +0000761 unsigned char src[16];
762 unsigned char dst[16];
763 unsigned char iv[16];
764 camellia_context ctx;
765
766 memset( key, 0, 32 );
767
768 for (j = 0; j < 6; j++) {
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000769 u = j >> 1;
770 v = j & 1;
Paul Bakker38119b12009-01-10 23:31:23 +0000771
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000772 if( verbose != 0 )
773 printf( " CAMELLIA-ECB-%3d (%s): ", 128 + u * 64,
774 (v == CAMELLIA_DECRYPT) ? "dec" : "enc");
Paul Bakker38119b12009-01-10 23:31:23 +0000775
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000776 for (i = 0; i < CAMELLIA_TESTS_ECB; i++ ) {
777 memcpy( key, camellia_test_ecb_key[u][i], 16 + 8 * u);
Paul Bakker38119b12009-01-10 23:31:23 +0000778
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000779 if (v == CAMELLIA_DECRYPT) {
780 camellia_setkey_dec(&ctx, key, 128 + u * 64);
781 memcpy(src, camellia_test_ecb_cipher[u][i], 16);
782 memcpy(dst, camellia_test_ecb_plain[i], 16);
783 } else { /* CAMELLIA_ENCRYPT */
784 camellia_setkey_enc(&ctx, key, 128 + u * 64);
785 memcpy(src, camellia_test_ecb_plain[i], 16);
786 memcpy(dst, camellia_test_ecb_cipher[u][i], 16);
787 }
Paul Bakker38119b12009-01-10 23:31:23 +0000788
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000789 camellia_crypt_ecb(&ctx, v, src, buf);
Paul Bakker38119b12009-01-10 23:31:23 +0000790
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000791 if( memcmp( buf, dst, 16 ) != 0 )
792 {
793 if( verbose != 0 )
794 printf( "failed\n" );
Paul Bakker38119b12009-01-10 23:31:23 +0000795
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000796 return( 1 );
797 }
798 }
Paul Bakker38119b12009-01-10 23:31:23 +0000799
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000800 if( verbose != 0 )
801 printf( "passed\n" );
Paul Bakker38119b12009-01-10 23:31:23 +0000802 }
803
804 if( verbose != 0 )
805 printf( "\n" );
806
807 /*
808 * CBC mode
809 */
810 for( j = 0; j < 6; j++ )
811 {
812 u = j >> 1;
813 v = j & 1;
814
815 if( verbose != 0 )
816 printf( " CAMELLIA-CBC-%3d (%s): ", 128 + u * 64,
817 ( v == CAMELLIA_DECRYPT ) ? "dec" : "enc" );
818
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000819 memcpy( src, camellia_test_cbc_iv, 16);
820 memcpy( dst, camellia_test_cbc_iv, 16);
821 memcpy( key, camellia_test_cbc_key[u], 16 + 8 * u);
Paul Bakker38119b12009-01-10 23:31:23 +0000822
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000823 if (v == CAMELLIA_DECRYPT) {
824 camellia_setkey_dec(&ctx, key, 128 + u * 64);
825 } else {
826 camellia_setkey_enc(&ctx, key, 128 + u * 64);
827 }
Paul Bakker38119b12009-01-10 23:31:23 +0000828
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000829 for (i = 0; i < CAMELLIA_TESTS_CBC; i++ ) {
Paul Bakker38119b12009-01-10 23:31:23 +0000830
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000831 if (v == CAMELLIA_DECRYPT) {
832 memcpy( iv , src, 16 );
833 memcpy(src, camellia_test_cbc_cipher[u][i], 16);
834 memcpy(dst, camellia_test_cbc_plain[i], 16);
835 } else { /* CAMELLIA_ENCRYPT */
836 memcpy( iv , dst, 16 );
837 memcpy(src, camellia_test_cbc_plain[i], 16);
838 memcpy(dst, camellia_test_cbc_cipher[u][i], 16);
839 }
Paul Bakker38119b12009-01-10 23:31:23 +0000840
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000841 camellia_crypt_cbc(&ctx, v, 16, iv, src, buf);
Paul Bakker38119b12009-01-10 23:31:23 +0000842
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000843 if( memcmp( buf, dst, 16 ) != 0 )
844 {
845 if( verbose != 0 )
846 printf( "failed\n" );
Paul Bakker38119b12009-01-10 23:31:23 +0000847
Paul Bakkerc81f6c32009-05-03 13:09:15 +0000848 return( 1 );
849 }
850 }
Paul Bakker38119b12009-01-10 23:31:23 +0000851
852 if( verbose != 0 )
853 printf( "passed\n" );
854 }
855
856 if( verbose != 0 )
857 printf( "\n" );
858
859 return ( 0 );
Paul Bakker38119b12009-01-10 23:31:23 +0000860}
861
862#endif
863
864#endif