1/* 2 * AES Key Wrap Algorithm (128-bit KEK) (RFC3394) 3 * 4 * Copyright (c) 2003-2007, Jouni Malinen <j@w1.fi> 5 * 6 * This software may be distributed under the terms of the BSD license. 7 * See README for more details. 8 */ 9 10#include "includes.h" 11 12#include "common.h" 13#include "aes.h" 14#include "aes_wrap.h" 15 16/** 17 * aes_wrap - Wrap keys with AES Key Wrap Algorithm (128-bit KEK) (RFC3394) 18 * @kek: 16-octet Key encryption key (KEK) 19 * @n: Length of the plaintext key in 64-bit units; e.g., 2 = 128-bit = 16 20 * bytes 21 * @plain: Plaintext key to be wrapped, n * 64 bits 22 * @cipher: Wrapped key, (n + 1) * 64 bits 23 * Returns: 0 on success, -1 on failure 24 */ 25int aes_wrap(const u8 *kek, int n, const u8 *plain, u8 *cipher) 26{ 27 u8 *a, *r, b[16]; 28 int i, j; 29 void *ctx; 30 31 a = cipher; 32 r = cipher + 8; 33 34 /* 1) Initialize variables. */ 35 os_memset(a, 0xa6, 8); 36 os_memcpy(r, plain, 8 * n); 37 38 ctx = aes_encrypt_init(kek, 16); 39 if (ctx == NULL) 40 return -1; 41 42 /* 2) Calculate intermediate values. 43 * For j = 0 to 5 44 * For i=1 to n 45 * B = AES(K, A | R[i]) 46 * A = MSB(64, B) ^ t where t = (n*j)+i 47 * R[i] = LSB(64, B) 48 */ 49 for (j = 0; j <= 5; j++) { 50 r = cipher + 8; 51 for (i = 1; i <= n; i++) { 52 os_memcpy(b, a, 8); 53 os_memcpy(b + 8, r, 8); 54 aes_encrypt(ctx, b, b); 55 os_memcpy(a, b, 8); 56 a[7] ^= n * j + i; 57 os_memcpy(r, b + 8, 8); 58 r += 8; 59 } 60 } 61 aes_encrypt_deinit(ctx); 62 63 /* 3) Output the results. 64 * 65 * These are already in @cipher due to the location of temporary 66 * variables. 67 */ 68 69 return 0; 70} 71