netwerk/srtp/src/crypto/cipher/aes_icm.c

Wed, 31 Dec 2014 06:09:35 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Wed, 31 Dec 2014 06:09:35 +0100
changeset 0
6474c204b198
permissions
-rw-r--r--

Cloned upstream origin tor-browser at tor-browser-31.3.0esr-4.5-1-build1
revision ID fc1c9ff7c1b2defdbc039f12214767608f46423f for hacking purpose.

michael@0 1 /*
michael@0 2 * aes_icm.c
michael@0 3 *
michael@0 4 * AES Integer Counter Mode
michael@0 5 *
michael@0 6 * David A. McGrew
michael@0 7 * Cisco Systems, Inc.
michael@0 8 */
michael@0 9
michael@0 10 /*
michael@0 11 *
michael@0 12 * Copyright (c) 2001-2006, Cisco Systems, Inc.
michael@0 13 * All rights reserved.
michael@0 14 *
michael@0 15 * Redistribution and use in source and binary forms, with or without
michael@0 16 * modification, are permitted provided that the following conditions
michael@0 17 * are met:
michael@0 18 *
michael@0 19 * Redistributions of source code must retain the above copyright
michael@0 20 * notice, this list of conditions and the following disclaimer.
michael@0 21 *
michael@0 22 * Redistributions in binary form must reproduce the above
michael@0 23 * copyright notice, this list of conditions and the following
michael@0 24 * disclaimer in the documentation and/or other materials provided
michael@0 25 * with the distribution.
michael@0 26 *
michael@0 27 * Neither the name of the Cisco Systems, Inc. nor the names of its
michael@0 28 * contributors may be used to endorse or promote products derived
michael@0 29 * from this software without specific prior written permission.
michael@0 30 *
michael@0 31 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
michael@0 32 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
michael@0 33 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
michael@0 34 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
michael@0 35 * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
michael@0 36 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
michael@0 37 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
michael@0 38 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
michael@0 39 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
michael@0 40 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
michael@0 41 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
michael@0 42 * OF THE POSSIBILITY OF SUCH DAMAGE.
michael@0 43 *
michael@0 44 */
michael@0 45
michael@0 46
michael@0 47 #define ALIGN_32 0
michael@0 48
michael@0 49 #include "aes_icm.h"
michael@0 50 #include "alloc.h"
michael@0 51
michael@0 52
michael@0 53 debug_module_t mod_aes_icm = {
michael@0 54 0, /* debugging is off by default */
michael@0 55 "aes icm" /* printable module name */
michael@0 56 };
michael@0 57
michael@0 58 /*
michael@0 59 * integer counter mode works as follows:
michael@0 60 *
michael@0 61 * 16 bits
michael@0 62 * <----->
michael@0 63 * +------+------+------+------+------+------+------+------+
michael@0 64 * | nonce | pakcet index | ctr |---+
michael@0 65 * +------+------+------+------+------+------+------+------+ |
michael@0 66 * |
michael@0 67 * +------+------+------+------+------+------+------+------+ v
michael@0 68 * | salt |000000|->(+)
michael@0 69 * +------+------+------+------+------+------+------+------+ |
michael@0 70 * |
michael@0 71 * +---------+
michael@0 72 * | encrypt |
michael@0 73 * +---------+
michael@0 74 * |
michael@0 75 * +------+------+------+------+------+------+------+------+ |
michael@0 76 * | keystream block |<--+
michael@0 77 * +------+------+------+------+------+------+------+------+
michael@0 78 *
michael@0 79 * All fields are big-endian
michael@0 80 *
michael@0 81 * ctr is the block counter, which increments from zero for
michael@0 82 * each packet (16 bits wide)
michael@0 83 *
michael@0 84 * packet index is distinct for each packet (48 bits wide)
michael@0 85 *
michael@0 86 * nonce can be distinct across many uses of the same key, or
michael@0 87 * can be a fixed value per key, or can be per-packet randomness
michael@0 88 * (64 bits)
michael@0 89 *
michael@0 90 */
michael@0 91
michael@0 92 err_status_t
michael@0 93 aes_icm_alloc_ismacryp(cipher_t **c, int key_len, int forIsmacryp) {
michael@0 94 extern cipher_type_t aes_icm;
michael@0 95 uint8_t *pointer;
michael@0 96 int tmp;
michael@0 97
michael@0 98 debug_print(mod_aes_icm,
michael@0 99 "allocating cipher with key length %d", key_len);
michael@0 100
michael@0 101 /*
michael@0 102 * Ismacryp, for example, uses 16 byte key + 8 byte
michael@0 103 * salt so this function is called with key_len = 24.
michael@0 104 * The check for key_len = 30/38/46 does not apply. Our usage
michael@0 105 * of aes functions with key_len = values other than 30
michael@0 106 * has not broken anything. Don't know what would be the
michael@0 107 * effect of skipping this check for srtp in general.
michael@0 108 */
michael@0 109 if (!(forIsmacryp && key_len > 16 && key_len < 30) &&
michael@0 110 key_len != 30 && key_len != 38 && key_len != 46)
michael@0 111 return err_status_bad_param;
michael@0 112
michael@0 113 /* allocate memory a cipher of type aes_icm */
michael@0 114 tmp = (sizeof(aes_icm_ctx_t) + sizeof(cipher_t));
michael@0 115 pointer = (uint8_t*)crypto_alloc(tmp);
michael@0 116 if (pointer == NULL)
michael@0 117 return err_status_alloc_fail;
michael@0 118
michael@0 119 /* set pointers */
michael@0 120 *c = (cipher_t *)pointer;
michael@0 121 (*c)->type = &aes_icm;
michael@0 122 (*c)->state = pointer + sizeof(cipher_t);
michael@0 123
michael@0 124 /* increment ref_count */
michael@0 125 aes_icm.ref_count++;
michael@0 126
michael@0 127 /* set key size */
michael@0 128 (*c)->key_len = key_len;
michael@0 129
michael@0 130 return err_status_ok;
michael@0 131 }
michael@0 132
michael@0 133 err_status_t aes_icm_alloc(cipher_t **c, int key_len, int forIsmacryp) {
michael@0 134 return aes_icm_alloc_ismacryp(c, key_len, 0);
michael@0 135 }
michael@0 136
michael@0 137 err_status_t
michael@0 138 aes_icm_dealloc(cipher_t *c) {
michael@0 139 extern cipher_type_t aes_icm;
michael@0 140
michael@0 141 /* zeroize entire state*/
michael@0 142 octet_string_set_to_zero((uint8_t *)c,
michael@0 143 sizeof(aes_icm_ctx_t) + sizeof(cipher_t));
michael@0 144
michael@0 145 /* free memory */
michael@0 146 crypto_free(c);
michael@0 147
michael@0 148 /* decrement ref_count */
michael@0 149 aes_icm.ref_count--;
michael@0 150
michael@0 151 return err_status_ok;
michael@0 152 }
michael@0 153
michael@0 154
michael@0 155 /*
michael@0 156 * aes_icm_context_init(...) initializes the aes_icm_context
michael@0 157 * using the value in key[].
michael@0 158 *
michael@0 159 * the key is the secret key
michael@0 160 *
michael@0 161 * the salt is unpredictable (but not necessarily secret) data which
michael@0 162 * randomizes the starting point in the keystream
michael@0 163 */
michael@0 164
michael@0 165 err_status_t
michael@0 166 aes_icm_context_init(aes_icm_ctx_t *c, const uint8_t *key, int key_len) {
michael@0 167 err_status_t status;
michael@0 168 int base_key_len, copy_len;
michael@0 169
michael@0 170 if (key_len > 16 && key_len < 30) /* Ismacryp */
michael@0 171 base_key_len = 16;
michael@0 172 else if (key_len == 30 || key_len == 38 || key_len == 46)
michael@0 173 base_key_len = key_len - 14;
michael@0 174 else
michael@0 175 return err_status_bad_param;
michael@0 176
michael@0 177 /*
michael@0 178 * set counter and initial values to 'offset' value, being careful not to
michael@0 179 * go past the end of the key buffer
michael@0 180 */
michael@0 181 v128_set_to_zero(&c->counter);
michael@0 182 v128_set_to_zero(&c->offset);
michael@0 183
michael@0 184 copy_len = key_len - base_key_len;
michael@0 185 /* force last two octets of the offset to be left zero (for srtp compatibility) */
michael@0 186 if (copy_len > 14)
michael@0 187 copy_len = 14;
michael@0 188
michael@0 189 memcpy(&c->counter, key + base_key_len, copy_len);
michael@0 190 memcpy(&c->offset, key + base_key_len, copy_len);
michael@0 191
michael@0 192 debug_print(mod_aes_icm,
michael@0 193 "key: %s", octet_string_hex_string(key, base_key_len));
michael@0 194 debug_print(mod_aes_icm,
michael@0 195 "offset: %s", v128_hex_string(&c->offset));
michael@0 196
michael@0 197 /* expand key */
michael@0 198 status = aes_expand_encryption_key(key, base_key_len, &c->expanded_key);
michael@0 199 if (status) {
michael@0 200 v128_set_to_zero(&c->counter);
michael@0 201 v128_set_to_zero(&c->offset);
michael@0 202 return status;
michael@0 203 }
michael@0 204
michael@0 205 /* indicate that the keystream_buffer is empty */
michael@0 206 c->bytes_in_buffer = 0;
michael@0 207
michael@0 208 return err_status_ok;
michael@0 209 }
michael@0 210
michael@0 211 /*
michael@0 212 * aes_icm_set_octet(c, i) sets the counter of the context which it is
michael@0 213 * passed so that the next octet of keystream that will be generated
michael@0 214 * is the ith octet
michael@0 215 */
michael@0 216
michael@0 217 err_status_t
michael@0 218 aes_icm_set_octet(aes_icm_ctx_t *c,
michael@0 219 uint64_t octet_num) {
michael@0 220
michael@0 221 #ifdef NO_64BIT_MATH
michael@0 222 int tail_num = low32(octet_num) & 0x0f;
michael@0 223 /* 64-bit right-shift 4 */
michael@0 224 uint64_t block_num = make64(high32(octet_num) >> 4,
michael@0 225 ((high32(octet_num) & 0x0f)<<(32-4)) |
michael@0 226 (low32(octet_num) >> 4));
michael@0 227 #else
michael@0 228 int tail_num = (int)(octet_num % 16);
michael@0 229 uint64_t block_num = octet_num / 16;
michael@0 230 #endif
michael@0 231
michael@0 232
michael@0 233 /* set counter value */
michael@0 234 /* FIX - There's no way this is correct */
michael@0 235 c->counter.v64[0] = c->offset.v64[0];
michael@0 236 #ifdef NO_64BIT_MATH
michael@0 237 c->counter.v64[0] = make64(high32(c->offset.v64[0]) ^ high32(block_num),
michael@0 238 low32(c->offset.v64[0]) ^ low32(block_num));
michael@0 239 #else
michael@0 240 c->counter.v64[0] = c->offset.v64[0] ^ block_num;
michael@0 241 #endif
michael@0 242
michael@0 243 debug_print(mod_aes_icm,
michael@0 244 "set_octet: %s", v128_hex_string(&c->counter));
michael@0 245
michael@0 246 /* fill keystream buffer, if needed */
michael@0 247 if (tail_num) {
michael@0 248 v128_copy(&c->keystream_buffer, &c->counter);
michael@0 249 aes_encrypt(&c->keystream_buffer, &c->expanded_key);
michael@0 250 c->bytes_in_buffer = sizeof(v128_t);
michael@0 251
michael@0 252 debug_print(mod_aes_icm, "counter: %s",
michael@0 253 v128_hex_string(&c->counter));
michael@0 254 debug_print(mod_aes_icm, "ciphertext: %s",
michael@0 255 v128_hex_string(&c->keystream_buffer));
michael@0 256
michael@0 257 /* indicate number of bytes in keystream_buffer */
michael@0 258 c->bytes_in_buffer = sizeof(v128_t) - tail_num;
michael@0 259
michael@0 260 } else {
michael@0 261
michael@0 262 /* indicate that keystream_buffer is empty */
michael@0 263 c->bytes_in_buffer = 0;
michael@0 264 }
michael@0 265
michael@0 266 return err_status_ok;
michael@0 267 }
michael@0 268
michael@0 269 /*
michael@0 270 * aes_icm_set_iv(c, iv) sets the counter value to the exor of iv with
michael@0 271 * the offset
michael@0 272 */
michael@0 273
michael@0 274 err_status_t
michael@0 275 aes_icm_set_iv(aes_icm_ctx_t *c, void *iv) {
michael@0 276 v128_t *nonce = (v128_t *) iv;
michael@0 277
michael@0 278 debug_print(mod_aes_icm,
michael@0 279 "setting iv: %s", v128_hex_string(nonce));
michael@0 280
michael@0 281 v128_xor(&c->counter, &c->offset, nonce);
michael@0 282
michael@0 283 debug_print(mod_aes_icm,
michael@0 284 "set_counter: %s", v128_hex_string(&c->counter));
michael@0 285
michael@0 286 /* indicate that the keystream_buffer is empty */
michael@0 287 c->bytes_in_buffer = 0;
michael@0 288
michael@0 289 return err_status_ok;
michael@0 290 }
michael@0 291
michael@0 292
michael@0 293
michael@0 294 /*
michael@0 295 * aes_icm_advance(...) refills the keystream_buffer and
michael@0 296 * advances the block index of the sicm_context forward by one
michael@0 297 *
michael@0 298 * this is an internal, hopefully inlined function
michael@0 299 */
michael@0 300
michael@0 301 static inline void
michael@0 302 aes_icm_advance_ismacryp(aes_icm_ctx_t *c, uint8_t forIsmacryp) {
michael@0 303 /* fill buffer with new keystream */
michael@0 304 v128_copy(&c->keystream_buffer, &c->counter);
michael@0 305 aes_encrypt(&c->keystream_buffer, &c->expanded_key);
michael@0 306 c->bytes_in_buffer = sizeof(v128_t);
michael@0 307
michael@0 308 debug_print(mod_aes_icm, "counter: %s",
michael@0 309 v128_hex_string(&c->counter));
michael@0 310 debug_print(mod_aes_icm, "ciphertext: %s",
michael@0 311 v128_hex_string(&c->keystream_buffer));
michael@0 312
michael@0 313 /* clock counter forward */
michael@0 314
michael@0 315 if (forIsmacryp) {
michael@0 316 uint32_t temp;
michael@0 317 //alex's clock counter forward
michael@0 318 temp = ntohl(c->counter.v32[3]);
michael@0 319 c->counter.v32[3] = htonl(++temp);
michael@0 320 } else {
michael@0 321 if (!++(c->counter.v8[15]))
michael@0 322 ++(c->counter.v8[14]);
michael@0 323 }
michael@0 324 }
michael@0 325
michael@0 326 static inline void aes_icm_advance(aes_icm_ctx_t *c) {
michael@0 327 aes_icm_advance_ismacryp(c, 0);
michael@0 328 }
michael@0 329
michael@0 330
michael@0 331 /*e
michael@0 332 * icm_encrypt deals with the following cases:
michael@0 333 *
michael@0 334 * bytes_to_encr < bytes_in_buffer
michael@0 335 * - add keystream into data
michael@0 336 *
michael@0 337 * bytes_to_encr > bytes_in_buffer
michael@0 338 * - add keystream into data until keystream_buffer is depleted
michael@0 339 * - loop over blocks, filling keystream_buffer and then
michael@0 340 * adding keystream into data
michael@0 341 * - fill buffer then add in remaining (< 16) bytes of keystream
michael@0 342 */
michael@0 343
michael@0 344 err_status_t
michael@0 345 aes_icm_encrypt_ismacryp(aes_icm_ctx_t *c,
michael@0 346 unsigned char *buf, unsigned int *enc_len,
michael@0 347 int forIsmacryp) {
michael@0 348 unsigned int bytes_to_encr = *enc_len;
michael@0 349 unsigned int i;
michael@0 350 uint32_t *b;
michael@0 351
michael@0 352 /* check that there's enough segment left but not for ismacryp*/
michael@0 353 if (!forIsmacryp && (bytes_to_encr + htons(c->counter.v16[7])) > 0xffff)
michael@0 354 return err_status_terminus;
michael@0 355
michael@0 356 debug_print(mod_aes_icm, "block index: %d",
michael@0 357 htons(c->counter.v16[7]));
michael@0 358 if (bytes_to_encr <= (unsigned int)c->bytes_in_buffer) {
michael@0 359
michael@0 360 /* deal with odd case of small bytes_to_encr */
michael@0 361 for (i = (sizeof(v128_t) - c->bytes_in_buffer);
michael@0 362 i < (sizeof(v128_t) - c->bytes_in_buffer + bytes_to_encr); i++)
michael@0 363 {
michael@0 364 *buf++ ^= c->keystream_buffer.v8[i];
michael@0 365 }
michael@0 366
michael@0 367 c->bytes_in_buffer -= bytes_to_encr;
michael@0 368
michael@0 369 /* return now to avoid the main loop */
michael@0 370 return err_status_ok;
michael@0 371
michael@0 372 } else {
michael@0 373
michael@0 374 /* encrypt bytes until the remaining data is 16-byte aligned */
michael@0 375 for (i=(sizeof(v128_t) - c->bytes_in_buffer); i < sizeof(v128_t); i++)
michael@0 376 *buf++ ^= c->keystream_buffer.v8[i];
michael@0 377
michael@0 378 bytes_to_encr -= c->bytes_in_buffer;
michael@0 379 c->bytes_in_buffer = 0;
michael@0 380
michael@0 381 }
michael@0 382
michael@0 383 /* now loop over entire 16-byte blocks of keystream */
michael@0 384 for (i=0; i < (bytes_to_encr/sizeof(v128_t)); i++) {
michael@0 385
michael@0 386 /* fill buffer with new keystream */
michael@0 387 aes_icm_advance_ismacryp(c, forIsmacryp);
michael@0 388
michael@0 389 /*
michael@0 390 * add keystream into the data buffer (this would be a lot faster
michael@0 391 * if we could assume 32-bit alignment!)
michael@0 392 */
michael@0 393
michael@0 394 #if ALIGN_32
michael@0 395 b = (uint32_t *)buf;
michael@0 396 *b++ ^= c->keystream_buffer.v32[0];
michael@0 397 *b++ ^= c->keystream_buffer.v32[1];
michael@0 398 *b++ ^= c->keystream_buffer.v32[2];
michael@0 399 *b++ ^= c->keystream_buffer.v32[3];
michael@0 400 buf = (uint8_t *)b;
michael@0 401 #else
michael@0 402 if ((((unsigned long) buf) & 0x03) != 0) {
michael@0 403 *buf++ ^= c->keystream_buffer.v8[0];
michael@0 404 *buf++ ^= c->keystream_buffer.v8[1];
michael@0 405 *buf++ ^= c->keystream_buffer.v8[2];
michael@0 406 *buf++ ^= c->keystream_buffer.v8[3];
michael@0 407 *buf++ ^= c->keystream_buffer.v8[4];
michael@0 408 *buf++ ^= c->keystream_buffer.v8[5];
michael@0 409 *buf++ ^= c->keystream_buffer.v8[6];
michael@0 410 *buf++ ^= c->keystream_buffer.v8[7];
michael@0 411 *buf++ ^= c->keystream_buffer.v8[8];
michael@0 412 *buf++ ^= c->keystream_buffer.v8[9];
michael@0 413 *buf++ ^= c->keystream_buffer.v8[10];
michael@0 414 *buf++ ^= c->keystream_buffer.v8[11];
michael@0 415 *buf++ ^= c->keystream_buffer.v8[12];
michael@0 416 *buf++ ^= c->keystream_buffer.v8[13];
michael@0 417 *buf++ ^= c->keystream_buffer.v8[14];
michael@0 418 *buf++ ^= c->keystream_buffer.v8[15];
michael@0 419 } else {
michael@0 420 b = (uint32_t *)buf;
michael@0 421 *b++ ^= c->keystream_buffer.v32[0];
michael@0 422 *b++ ^= c->keystream_buffer.v32[1];
michael@0 423 *b++ ^= c->keystream_buffer.v32[2];
michael@0 424 *b++ ^= c->keystream_buffer.v32[3];
michael@0 425 buf = (uint8_t *)b;
michael@0 426 }
michael@0 427 #endif /* #if ALIGN_32 */
michael@0 428
michael@0 429 }
michael@0 430
michael@0 431 /* if there is a tail end of the data, process it */
michael@0 432 if ((bytes_to_encr & 0xf) != 0) {
michael@0 433
michael@0 434 /* fill buffer with new keystream */
michael@0 435 aes_icm_advance_ismacryp(c, forIsmacryp);
michael@0 436
michael@0 437 for (i=0; i < (bytes_to_encr & 0xf); i++)
michael@0 438 *buf++ ^= c->keystream_buffer.v8[i];
michael@0 439
michael@0 440 /* reset the keystream buffer size to right value */
michael@0 441 c->bytes_in_buffer = sizeof(v128_t) - i;
michael@0 442 } else {
michael@0 443
michael@0 444 /* no tail, so just reset the keystream buffer size to zero */
michael@0 445 c->bytes_in_buffer = 0;
michael@0 446
michael@0 447 }
michael@0 448
michael@0 449 return err_status_ok;
michael@0 450 }
michael@0 451
michael@0 452 err_status_t
michael@0 453 aes_icm_encrypt(aes_icm_ctx_t *c, unsigned char *buf, unsigned int *enc_len) {
michael@0 454 return aes_icm_encrypt_ismacryp(c, buf, enc_len, 0);
michael@0 455 }
michael@0 456
michael@0 457 err_status_t
michael@0 458 aes_icm_output(aes_icm_ctx_t *c, uint8_t *buffer, int num_octets_to_output) {
michael@0 459 unsigned int len = num_octets_to_output;
michael@0 460
michael@0 461 /* zeroize the buffer */
michael@0 462 octet_string_set_to_zero(buffer, num_octets_to_output);
michael@0 463
michael@0 464 /* exor keystream into buffer */
michael@0 465 return aes_icm_encrypt(c, buffer, &len);
michael@0 466 }
michael@0 467
michael@0 468
michael@0 469 char
michael@0 470 aes_icm_description[] = "aes integer counter mode";
michael@0 471
michael@0 472 uint8_t aes_icm_test_case_0_key[30] = {
michael@0 473 0x2b, 0x7e, 0x15, 0x16, 0x28, 0xae, 0xd2, 0xa6,
michael@0 474 0xab, 0xf7, 0x15, 0x88, 0x09, 0xcf, 0x4f, 0x3c,
michael@0 475 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7,
michael@0 476 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd
michael@0 477 };
michael@0 478
michael@0 479 uint8_t aes_icm_test_case_0_nonce[16] = {
michael@0 480 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
michael@0 481 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
michael@0 482 };
michael@0 483
michael@0 484 uint8_t aes_icm_test_case_0_plaintext[32] = {
michael@0 485 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
michael@0 486 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
michael@0 487 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
michael@0 488 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
michael@0 489 };
michael@0 490
michael@0 491 uint8_t aes_icm_test_case_0_ciphertext[32] = {
michael@0 492 0xe0, 0x3e, 0xad, 0x09, 0x35, 0xc9, 0x5e, 0x80,
michael@0 493 0xe1, 0x66, 0xb1, 0x6d, 0xd9, 0x2b, 0x4e, 0xb4,
michael@0 494 0xd2, 0x35, 0x13, 0x16, 0x2b, 0x02, 0xd0, 0xf7,
michael@0 495 0x2a, 0x43, 0xa2, 0xfe, 0x4a, 0x5f, 0x97, 0xab
michael@0 496 };
michael@0 497
michael@0 498 cipher_test_case_t aes_icm_test_case_0 = {
michael@0 499 30, /* octets in key */
michael@0 500 aes_icm_test_case_0_key, /* key */
michael@0 501 aes_icm_test_case_0_nonce, /* packet index */
michael@0 502 32, /* octets in plaintext */
michael@0 503 aes_icm_test_case_0_plaintext, /* plaintext */
michael@0 504 32, /* octets in ciphertext */
michael@0 505 aes_icm_test_case_0_ciphertext, /* ciphertext */
michael@0 506 NULL /* pointer to next testcase */
michael@0 507 };
michael@0 508
michael@0 509 uint8_t aes_icm_test_case_1_key[46] = {
michael@0 510 0x57, 0xf8, 0x2f, 0xe3, 0x61, 0x3f, 0xd1, 0x70,
michael@0 511 0xa8, 0x5e, 0xc9, 0x3c, 0x40, 0xb1, 0xf0, 0x92,
michael@0 512 0x2e, 0xc4, 0xcb, 0x0d, 0xc0, 0x25, 0xb5, 0x82,
michael@0 513 0x72, 0x14, 0x7c, 0xc4, 0x38, 0x94, 0x4a, 0x98,
michael@0 514 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7,
michael@0 515 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd
michael@0 516 };
michael@0 517
michael@0 518 uint8_t aes_icm_test_case_1_nonce[16] = {
michael@0 519 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
michael@0 520 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
michael@0 521 };
michael@0 522
michael@0 523 uint8_t aes_icm_test_case_1_plaintext[32] = {
michael@0 524 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
michael@0 525 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
michael@0 526 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
michael@0 527 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
michael@0 528 };
michael@0 529
michael@0 530 uint8_t aes_icm_test_case_1_ciphertext[32] = {
michael@0 531 0x92, 0xbd, 0xd2, 0x8a, 0x93, 0xc3, 0xf5, 0x25,
michael@0 532 0x11, 0xc6, 0x77, 0xd0, 0x8b, 0x55, 0x15, 0xa4,
michael@0 533 0x9d, 0xa7, 0x1b, 0x23, 0x78, 0xa8, 0x54, 0xf6,
michael@0 534 0x70, 0x50, 0x75, 0x6d, 0xed, 0x16, 0x5b, 0xac
michael@0 535 };
michael@0 536
michael@0 537 cipher_test_case_t aes_icm_test_case_1 = {
michael@0 538 46, /* octets in key */
michael@0 539 aes_icm_test_case_1_key, /* key */
michael@0 540 aes_icm_test_case_1_nonce, /* packet index */
michael@0 541 32, /* octets in plaintext */
michael@0 542 aes_icm_test_case_1_plaintext, /* plaintext */
michael@0 543 32, /* octets in ciphertext */
michael@0 544 aes_icm_test_case_1_ciphertext, /* ciphertext */
michael@0 545 &aes_icm_test_case_0 /* pointer to next testcase */
michael@0 546 };
michael@0 547
michael@0 548
michael@0 549
michael@0 550 /*
michael@0 551 * note: the encrypt function is identical to the decrypt function
michael@0 552 */
michael@0 553
michael@0 554 cipher_type_t aes_icm = {
michael@0 555 (cipher_alloc_func_t) aes_icm_alloc,
michael@0 556 (cipher_dealloc_func_t) aes_icm_dealloc,
michael@0 557 (cipher_init_func_t) aes_icm_context_init,
michael@0 558 (cipher_encrypt_func_t) aes_icm_encrypt,
michael@0 559 (cipher_decrypt_func_t) aes_icm_encrypt,
michael@0 560 (cipher_set_iv_func_t) aes_icm_set_iv,
michael@0 561 (char *) aes_icm_description,
michael@0 562 (int) 0, /* instance count */
michael@0 563 (cipher_test_case_t *) &aes_icm_test_case_1,
michael@0 564 (debug_module_t *) &mod_aes_icm,
michael@0 565 (cipher_type_id_t) AES_ICM
michael@0 566 };
michael@0 567

mercurial