1 /* -----------------------------------------------------------------------
2  *
3  * umac.c -- C Implementation UMAC Message Authentication
4  *
5  * Version 0.93b of rfc4418.txt -- 2006 July 18
6  *
7  * For a full description of UMAC message authentication see the UMAC
8  * world-wide-web page at http://www.cs.ucdavis.edu/~rogaway/umac
9  * Please report bugs and suggestions to the UMAC webpage.
10  *
11  * Copyright (c) 1999-2006 Ted Krovetz
12  *
13  * Permission to use, copy, modify, and distribute this software and
14  * its documentation for any purpose and with or without fee, is hereby
15  * granted provided that the above copyright notice appears in all copies
16  * and in supporting documentation, and that the name of the copyright
17  * holder not be used in advertising or publicity pertaining to
18  * distribution of the software without specific, written prior permission.
19  *
20  * Comments should be directed to Ted Krovetz (tdk@acm.org)
21  *
22  * ---------------------------------------------------------------------- */
23 
24  /* ////////////////////// IMPORTANT NOTES /////////////////////////////////
25   *
26   * 1) This version does not work properly on messages larger than 16MB
27   *
28   * 2) If you set the switch to use SSE2, then all data must be 16-byte
29   *    aligned
30   *
31   * 3) When calling the function umac(), it is assumed that msg is in
32   * a writable buffer of length divisible by 32 bytes. The message itself
33   * does not have to fill the entire buffer, but bytes beyond msg may be
34   * zeroed.
35   *
36   * 4) Three free AES implementations are supported by this implementation of
37   * UMAC. Paulo Barreto's version is in the public domain and can be found
38   * at http://www.esat.kuleuven.ac.be/~rijmen/rijndael/ (search for
39   * "Barreto"). The only two files needed are rijndael-alg-fst.c and
40   * rijndael-alg-fst.h. Brian Gladman's version is distributed with the GNU
41   * Public Licence at http://fp.gladman.plus.com/AES/index.htm. It
42   * includes a fast IA-32 assembly version. The OpenSSL crypo library is
43   * the third.
44   *
45   * 5) With FORCE_C_ONLY flags set to 0, incorrect results are sometimes
46   * produced under gcc with optimizations set -O3 or higher. Dunno why.
47   *
48   /////////////////////////////////////////////////////////////////////// */
49 
50 /* ---------------------------------------------------------------------- */
51 /* --- User Switches ---------------------------------------------------- */
52 /* ---------------------------------------------------------------------- */
53 
54 #ifndef UMAC_OUTPUT_LEN
55 # define UMAC_OUTPUT_LEN       8  /* Alowable: 4, 8, 12, 16               */
56 #endif
57 
58 #if UMAC_OUTPUT_LEN != 4 && UMAC_OUTPUT_LEN != 8 && \
59     UMAC_OUTPUT_LEN != 12 && UMAC_OUTPUT_LEN != 16
60 # error UMAC_OUTPUT_LEN must be defined to 4, 8, 12 or 16
61 #endif
62 
63 /* #define FORCE_C_ONLY        1  ANSI C and 64-bit integers req'd        */
64 /* #define AES_IMPLEMENTAION   1  1 = OpenSSL, 2 = Barreto, 3 = Gladman   */
65 /* #define SSE2                0  Is SSE2 is available?                   */
66 /* #define RUN_TESTS           0  Run basic correctness/speed tests       */
67 /* #define UMAC_AE_SUPPORT     0  Enable auhthenticated encryption        */
68 
69 /* ---------------------------------------------------------------------- */
70 /* -- Global Includes --------------------------------------------------- */
71 /* ---------------------------------------------------------------------- */
72 
73 #include "mod_sftp.h"
74 #include "umac.h"
75 #include <string.h>
76 #include <stdlib.h>
77 #include <stddef.h>
78 
79 #if OPENSSL_VERSION_NUMBER > 0x000907000L
80 
81 /* ---------------------------------------------------------------------- */
82 /* --- Primitive Data Types ---                                           */
83 /* ---------------------------------------------------------------------- */
84 
85 /* The following assumptions may need change on your system */
86 typedef uint8_t		UINT8;  /* 1 byte   */
87 typedef uint16_t	UINT16; /* 2 byte   */
88 typedef uint32_t	UINT32; /* 4 byte   */
89 typedef uint64_t	UINT64; /* 8 bytes  */
90 typedef unsigned int	UWORD;  /* Register */
91 
92 /* ---------------------------------------------------------------------- */
93 /* --- Constants -------------------------------------------------------- */
94 /* ---------------------------------------------------------------------- */
95 
96 #define UMAC_KEY_LEN           16  /* UMAC takes 16 bytes of external key */
97 
98 /* Message "words" are read from memory in an endian-specific manner.     */
99 /* For this implementation to behave correctly, __LITTLE_ENDIAN__ must    */
100 /* be set true if the host computer is little-endian.                     */
101 
102 #if BYTE_ORDER == LITTLE_ENDIAN
103 #define __LITTLE_ENDIAN__ 1
104 #else
105 #define __LITTLE_ENDIAN__ 0
106 #endif
107 
108 /* ---------------------------------------------------------------------- */
109 /* ---------------------------------------------------------------------- */
110 /* ----- Architecture Specific ------------------------------------------ */
111 /* ---------------------------------------------------------------------- */
112 /* ---------------------------------------------------------------------- */
113 
114 
115 /* ---------------------------------------------------------------------- */
116 /* ---------------------------------------------------------------------- */
117 /* ----- Primitive Routines --------------------------------------------- */
118 /* ---------------------------------------------------------------------- */
119 /* ---------------------------------------------------------------------- */
120 
121 
122 /* ---------------------------------------------------------------------- */
123 /* --- 32-bit by 32-bit to 64-bit Multiplication ------------------------ */
124 /* ---------------------------------------------------------------------- */
125 
126 #define MUL64(a,b) ((UINT64)((UINT64)(UINT32)(a) * (UINT64)(UINT32)(b)))
127 
128 /* ---------------------------------------------------------------------- */
129 /* --- Endian Conversion --- Forcing assembly on some platforms           */
130 /* ---------------------------------------------------------------------- */
131 
132 #if defined(HAVE_SWAP32)
133 #define LOAD_UINT32_REVERSED(p)		(swap32(*(UINT32 *)(p)))
134 #define STORE_UINT32_REVERSED(p,v) 	(*(UINT32 *)(p) = swap32(v))
135 #else /* HAVE_SWAP32 */
136 
LOAD_UINT32_REVERSED(void * ptr)137 static UINT32 LOAD_UINT32_REVERSED(void *ptr)
138 {
139     UINT32 temp = *(UINT32 *)ptr;
140     temp = (temp >> 24) | ((temp & 0x00FF0000) >> 8 )
141          | ((temp & 0x0000FF00) << 8 ) | (temp << 24);
142     return (UINT32)temp;
143 }
144 
145 # if (__LITTLE_ENDIAN__)
STORE_UINT32_REVERSED(void * ptr,UINT32 x)146 static void STORE_UINT32_REVERSED(void *ptr, UINT32 x)
147 {
148     UINT32 i = (UINT32)x;
149     *(UINT32 *)ptr = (i >> 24) | ((i & 0x00FF0000) >> 8 )
150                    | ((i & 0x0000FF00) << 8 ) | (i << 24);
151 }
152 # endif /* __LITTLE_ENDIAN */
153 #endif /* HAVE_SWAP32 */
154 
155 /* The following definitions use the above reversal-primitives to do the right
156  * thing on endian specific load and stores.
157  */
158 
159 #if (__LITTLE_ENDIAN__)
160 #define LOAD_UINT32_LITTLE(ptr)     (*(UINT32 *)(ptr))
161 #define STORE_UINT32_BIG(ptr,x)     STORE_UINT32_REVERSED(ptr,x)
162 #else
163 #define LOAD_UINT32_LITTLE(ptr)     LOAD_UINT32_REVERSED(ptr)
164 #define STORE_UINT32_BIG(ptr,x)     (*(UINT32 *)(ptr) = (UINT32)(x))
165 #endif
166 
167 /* ---------------------------------------------------------------------- */
168 /* ---------------------------------------------------------------------- */
169 /* ----- Begin KDF & PDF Section ---------------------------------------- */
170 /* ---------------------------------------------------------------------- */
171 /* ---------------------------------------------------------------------- */
172 
173 /* UMAC uses AES with 16 byte block and key lengths */
174 #define AES_BLOCK_LEN  16
175 
176 /* OpenSSL's AES */
177 typedef AES_KEY aes_int_key[1];
178 #define aes_encryption(in,out,int_key)                  \
179   AES_encrypt((unsigned char *)(in),(unsigned char *)(out),(AES_KEY *)int_key)
180 #define aes_key_setup(key,int_key)                      \
181   AES_set_encrypt_key((unsigned char *)(key),UMAC_KEY_LEN*8,int_key)
182 
183 /* The user-supplied UMAC key is stretched using AES in a counter
184  * mode to supply all random bits needed by UMAC. The kdf function takes
185  * an AES internal key representation 'key' and writes a stream of
186  * 'nbytes' bytes to the memory pointed at by 'bufp'. Each distinct
187  * 'ndx' causes a distinct byte stream.
188  */
kdf(void * bufp,aes_int_key key,UINT8 ndx,int nbytes)189 static void kdf(void *bufp, aes_int_key key, UINT8 ndx, int nbytes)
190 {
191     UINT8 in_buf[AES_BLOCK_LEN] = {0};
192     UINT8 out_buf[AES_BLOCK_LEN];
193     UINT8 *dst_buf = (UINT8 *)bufp;
194     int i;
195 
196     /* Setup the initial value */
197     in_buf[AES_BLOCK_LEN-9] = ndx;
198     in_buf[AES_BLOCK_LEN-1] = i = 1;
199 
200     while (nbytes >= AES_BLOCK_LEN) {
201         aes_encryption(in_buf, out_buf, key);
202         memcpy(dst_buf,out_buf,AES_BLOCK_LEN);
203         in_buf[AES_BLOCK_LEN-1] = ++i;
204         nbytes -= AES_BLOCK_LEN;
205         dst_buf += AES_BLOCK_LEN;
206     }
207     if (nbytes) {
208         aes_encryption(in_buf, out_buf, key);
209         memcpy(dst_buf,out_buf,nbytes);
210     }
211 }
212 
213 /* The final UHASH result is XOR'd with the output of a pseudorandom
214  * function. Here, we use AES to generate random output and
215  * xor the appropriate bytes depending on the last bits of nonce.
216  * This scheme is optimized for sequential, increasing big-endian nonces.
217  */
218 
219 typedef struct {
220     UINT8 cache[AES_BLOCK_LEN];  /* Previous AES output is saved      */
221     UINT8 nonce[AES_BLOCK_LEN];  /* The AES input making above cache  */
222     aes_int_key prf_key;         /* Expanded AES key for PDF          */
223 } pdf_ctx;
224 
pdf_init(pdf_ctx * pc,aes_int_key prf_key)225 static void pdf_init(pdf_ctx *pc, aes_int_key prf_key)
226 {
227     UINT8 buf[UMAC_KEY_LEN];
228 
229     kdf(buf, prf_key, 0, UMAC_KEY_LEN);
230     aes_key_setup(buf, pc->prf_key);
231 
232     /* Initialize pdf and cache */
233     memset(pc->nonce, 0, sizeof(pc->nonce));
234     aes_encryption(pc->nonce, pc->cache, pc->prf_key);
235 }
236 
pdf_gen_xor(pdf_ctx * pc,UINT8 nonce[8],UINT8 buf[8])237 static void pdf_gen_xor(pdf_ctx *pc, UINT8 nonce[8], UINT8 buf[8])
238 {
239     /* 'ndx' indicates that we'll be using the 0th or 1st eight bytes
240      * of the AES output. If last time around we returned the ndx-1st
241      * element, then we may have the result in the cache already.
242      */
243 
244 #if (UMAC_OUTPUT_LEN == 4)
245 #define LOW_BIT_MASK 3
246 #elif (UMAC_OUTPUT_LEN == 8)
247 #define LOW_BIT_MASK 1
248 #elif (UMAC_OUTPUT_LEN > 8)
249 #define LOW_BIT_MASK 0
250 #endif
251 
252     UINT8 tmp_nonce_lo[4];
253 #if LOW_BIT_MASK != 0
254     int ndx = nonce[7] & LOW_BIT_MASK;
255 #endif
256     memcpy(tmp_nonce_lo, &(nonce[4]), sizeof(UINT32));
257     tmp_nonce_lo[3] &= ~LOW_BIT_MASK; /* zero last bit */
258 
259     /* ProFTPD Note: We've changed the original code where, which used explicit
260      * typecasting to treat the nonce[8] as a UINT32, to memcpy(3)/memcmp(3),
261      * to avoid strict aliasing gcc warnings when -O2 or higher is used.
262      */
263 
264     if ( (memcmp(tmp_nonce_lo, &(pc->nonce[4]), sizeof(UINT32)) != 0) ||
265          (memcmp(nonce, pc->nonce, sizeof(UINT32)) != 0) )
266     {
267         memmove(pc->nonce, nonce, sizeof(UINT32));
268         memmove(&(pc->nonce[4]), tmp_nonce_lo, sizeof(UINT32));
269         aes_encryption(pc->nonce, pc->cache, pc->prf_key);
270     }
271 
272 #if (UMAC_OUTPUT_LEN == 4)
273     *((UINT32 *)buf) ^= ((UINT32 *)pc->cache)[ndx];
274 #elif (UMAC_OUTPUT_LEN == 8)
275     *((UINT64 *)buf) ^= ((UINT64 *)pc->cache)[ndx];
276 #elif (UMAC_OUTPUT_LEN == 12)
277     ((UINT64 *)buf)[0] ^= ((UINT64 *)pc->cache)[0];
278     ((UINT32 *)buf)[2] ^= ((UINT32 *)pc->cache)[2];
279 #elif (UMAC_OUTPUT_LEN == 16)
280     ((UINT64 *)buf)[0] ^= ((UINT64 *)pc->cache)[0];
281     ((UINT64 *)buf)[1] ^= ((UINT64 *)pc->cache)[1];
282 #endif
283 }
284 
285 /* ---------------------------------------------------------------------- */
286 /* ---------------------------------------------------------------------- */
287 /* ----- Begin NH Hash Section ------------------------------------------ */
288 /* ---------------------------------------------------------------------- */
289 /* ---------------------------------------------------------------------- */
290 
291 /* The NH-based hash functions used in UMAC are described in the UMAC paper
292  * and specification, both of which can be found at the UMAC website.
293  * The interface to this implementation has two
294  * versions, one expects the entire message being hashed to be passed
295  * in a single buffer and returns the hash result immediately. The second
296  * allows the message to be passed in a sequence of buffers. In the
297  * muliple-buffer interface, the client calls the routine nh_update() as
298  * many times as necessary. When there is no more data to be fed to the
299  * hash, the client calls nh_final() which calculates the hash output.
300  * Before beginning another hash calculation the nh_reset() routine
301  * must be called. The single-buffer routine, nh(), is equivalent to
302  * the sequence of calls nh_update() and nh_final(); however it is
303  * optimized and should be preferred whenever the multiple-buffer interface
304  * is not necessary. When using either interface, it is the client's
305  * responsibility to pass no more than L1_KEY_LEN bytes per hash result.
306  *
307  * The routine nh_init() initializes the nh_ctx data structure and
308  * must be called once, before any other PDF routine.
309  */
310 
311  /* The "nh_aux" routines do the actual NH hashing work. They
312   * expect buffers to be multiples of L1_PAD_BOUNDARY. These routines
313   * produce output for all STREAMS NH iterations in one call,
314   * allowing the parallel implementation of the streams.
315   */
316 
317 #define STREAMS (UMAC_OUTPUT_LEN / 4) /* Number of times hash is applied  */
318 #define L1_KEY_LEN         1024     /* Internal key bytes                 */
319 #define L1_KEY_SHIFT         16     /* Toeplitz key shift between streams */
320 #define L1_PAD_BOUNDARY      32     /* pad message to boundary multiple   */
321 #define ALLOC_BOUNDARY       16     /* Keep buffers aligned to this       */
322 #define HASH_BUF_BYTES       64     /* nh_aux_hb buffer multiple          */
323 
324 typedef struct {
325     UINT8  nh_key [L1_KEY_LEN + L1_KEY_SHIFT * (STREAMS - 1)]; /* NH Key  */
326     UINT8  data   [HASH_BUF_BYTES];    /* Incoming data buffer            */
327     int next_data_empty;    /* Bookkeeping variable for data buffer.      */
328     int bytes_hashed;        /* Bytes (out of L1_KEY_LEN) incorporated.   */
329     UINT64 state[STREAMS];               /* on-line state     */
330 } nh_ctx;
331 
332 
333 #if (UMAC_OUTPUT_LEN == 4)
334 
nh_aux(void * kp,void * dp,void * hp,UINT32 dlen)335 static void nh_aux(void *kp, void *dp, void *hp, UINT32 dlen)
336 /* NH hashing primitive. Previous (partial) hash result is loaded and
337 * then stored via hp pointer. The length of the data pointed at by "dp",
338 * "dlen", is guaranteed to be divisible by L1_PAD_BOUNDARY (32).  Key
339 * is expected to be endian compensated in memory at key setup.
340 */
341 {
342     UINT64 h;
343     UWORD c = dlen / 32;
344     UINT32 *k = (UINT32 *)kp;
345     UINT32 *d = (UINT32 *)dp;
346     UINT32 d0,d1,d2,d3,d4,d5,d6,d7;
347     UINT32 k0,k1,k2,k3,k4,k5,k6,k7;
348 
349     h = *((UINT64 *)hp);
350     do {
351         d0 = LOAD_UINT32_LITTLE(d+0); d1 = LOAD_UINT32_LITTLE(d+1);
352         d2 = LOAD_UINT32_LITTLE(d+2); d3 = LOAD_UINT32_LITTLE(d+3);
353         d4 = LOAD_UINT32_LITTLE(d+4); d5 = LOAD_UINT32_LITTLE(d+5);
354         d6 = LOAD_UINT32_LITTLE(d+6); d7 = LOAD_UINT32_LITTLE(d+7);
355         k0 = *(k+0); k1 = *(k+1); k2 = *(k+2); k3 = *(k+3);
356         k4 = *(k+4); k5 = *(k+5); k6 = *(k+6); k7 = *(k+7);
357         h += MUL64((k0 + d0), (k4 + d4));
358         h += MUL64((k1 + d1), (k5 + d5));
359         h += MUL64((k2 + d2), (k6 + d6));
360         h += MUL64((k3 + d3), (k7 + d7));
361 
362         d += 8;
363         k += 8;
364     } while (--c);
365   *((UINT64 *)hp) = h;
366 }
367 
368 #elif (UMAC_OUTPUT_LEN == 8)
369 
nh_aux(void * kp,void * dp,void * hp,UINT32 dlen)370 static void nh_aux(void *kp, void *dp, void *hp, UINT32 dlen)
371 /* Same as previous nh_aux, but two streams are handled in one pass,
372  * reading and writing 16 bytes of hash-state per call.
373  */
374 {
375   UINT64 h1,h2;
376   UWORD c = dlen / 32;
377   UINT32 *k = (UINT32 *)kp;
378   UINT32 *d = (UINT32 *)dp;
379   UINT32 d0,d1,d2,d3,d4,d5,d6,d7;
380   UINT32 k0,k1,k2,k3,k4,k5,k6,k7,
381         k8,k9,k10,k11;
382 
383   h1 = *((UINT64 *)hp);
384   h2 = *((UINT64 *)hp + 1);
385   k0 = *(k+0); k1 = *(k+1); k2 = *(k+2); k3 = *(k+3);
386   do {
387     d0 = LOAD_UINT32_LITTLE(d+0); d1 = LOAD_UINT32_LITTLE(d+1);
388     d2 = LOAD_UINT32_LITTLE(d+2); d3 = LOAD_UINT32_LITTLE(d+3);
389     d4 = LOAD_UINT32_LITTLE(d+4); d5 = LOAD_UINT32_LITTLE(d+5);
390     d6 = LOAD_UINT32_LITTLE(d+6); d7 = LOAD_UINT32_LITTLE(d+7);
391     k4 = *(k+4); k5 = *(k+5); k6 = *(k+6); k7 = *(k+7);
392     k8 = *(k+8); k9 = *(k+9); k10 = *(k+10); k11 = *(k+11);
393 
394     h1 += MUL64((k0 + d0), (k4 + d4));
395     h2 += MUL64((k4 + d0), (k8 + d4));
396 
397     h1 += MUL64((k1 + d1), (k5 + d5));
398     h2 += MUL64((k5 + d1), (k9 + d5));
399 
400     h1 += MUL64((k2 + d2), (k6 + d6));
401     h2 += MUL64((k6 + d2), (k10 + d6));
402 
403     h1 += MUL64((k3 + d3), (k7 + d7));
404     h2 += MUL64((k7 + d3), (k11 + d7));
405 
406     k0 = k8; k1 = k9; k2 = k10; k3 = k11;
407 
408     d += 8;
409     k += 8;
410   } while (--c);
411   ((UINT64 *)hp)[0] = h1;
412   ((UINT64 *)hp)[1] = h2;
413 }
414 
415 #elif (UMAC_OUTPUT_LEN == 12)
416 
nh_aux(void * kp,void * dp,void * hp,UINT32 dlen)417 static void nh_aux(void *kp, void *dp, void *hp, UINT32 dlen)
418 /* Same as previous nh_aux, but two streams are handled in one pass,
419  * reading and writing 24 bytes of hash-state per call.
420 */
421 {
422     UINT64 h1,h2,h3;
423     UWORD c = dlen / 32;
424     UINT32 *k = (UINT32 *)kp;
425     UINT32 *d = (UINT32 *)dp;
426     UINT32 d0,d1,d2,d3,d4,d5,d6,d7;
427     UINT32 k0,k1,k2,k3,k4,k5,k6,k7,
428         k8,k9,k10,k11,k12,k13,k14,k15;
429 
430     h1 = *((UINT64 *)hp);
431     h2 = *((UINT64 *)hp + 1);
432     h3 = *((UINT64 *)hp + 2);
433     k0 = *(k+0); k1 = *(k+1); k2 = *(k+2); k3 = *(k+3);
434     k4 = *(k+4); k5 = *(k+5); k6 = *(k+6); k7 = *(k+7);
435     do {
436         d0 = LOAD_UINT32_LITTLE(d+0); d1 = LOAD_UINT32_LITTLE(d+1);
437         d2 = LOAD_UINT32_LITTLE(d+2); d3 = LOAD_UINT32_LITTLE(d+3);
438         d4 = LOAD_UINT32_LITTLE(d+4); d5 = LOAD_UINT32_LITTLE(d+5);
439         d6 = LOAD_UINT32_LITTLE(d+6); d7 = LOAD_UINT32_LITTLE(d+7);
440         k8 = *(k+8); k9 = *(k+9); k10 = *(k+10); k11 = *(k+11);
441         k12 = *(k+12); k13 = *(k+13); k14 = *(k+14); k15 = *(k+15);
442 
443         h1 += MUL64((k0 + d0), (k4 + d4));
444         h2 += MUL64((k4 + d0), (k8 + d4));
445         h3 += MUL64((k8 + d0), (k12 + d4));
446 
447         h1 += MUL64((k1 + d1), (k5 + d5));
448         h2 += MUL64((k5 + d1), (k9 + d5));
449         h3 += MUL64((k9 + d1), (k13 + d5));
450 
451         h1 += MUL64((k2 + d2), (k6 + d6));
452         h2 += MUL64((k6 + d2), (k10 + d6));
453         h3 += MUL64((k10 + d2), (k14 + d6));
454 
455         h1 += MUL64((k3 + d3), (k7 + d7));
456         h2 += MUL64((k7 + d3), (k11 + d7));
457         h3 += MUL64((k11 + d3), (k15 + d7));
458 
459         k0 = k8; k1 = k9; k2 = k10; k3 = k11;
460         k4 = k12; k5 = k13; k6 = k14; k7 = k15;
461 
462         d += 8;
463         k += 8;
464     } while (--c);
465     ((UINT64 *)hp)[0] = h1;
466     ((UINT64 *)hp)[1] = h2;
467     ((UINT64 *)hp)[2] = h3;
468 }
469 
470 #elif (UMAC_OUTPUT_LEN == 16)
471 
nh_aux(void * kp,void * dp,void * hp,UINT32 dlen)472 static void nh_aux(void *kp, void *dp, void *hp, UINT32 dlen)
473 /* Same as previous nh_aux, but two streams are handled in one pass,
474  * reading and writing 24 bytes of hash-state per call.
475 */
476 {
477     UINT64 h1,h2,h3,h4;
478     UWORD c = dlen / 32;
479     UINT32 *k = (UINT32 *)kp;
480     UINT32 *d = (UINT32 *)dp;
481     UINT32 d0,d1,d2,d3,d4,d5,d6,d7;
482     UINT32 k0,k1,k2,k3,k4,k5,k6,k7,
483         k8,k9,k10,k11,k12,k13,k14,k15,
484         k16,k17,k18,k19;
485 
486     h1 = *((UINT64 *)hp);
487     h2 = *((UINT64 *)hp + 1);
488     h3 = *((UINT64 *)hp + 2);
489     h4 = *((UINT64 *)hp + 3);
490     k0 = *(k+0); k1 = *(k+1); k2 = *(k+2); k3 = *(k+3);
491     k4 = *(k+4); k5 = *(k+5); k6 = *(k+6); k7 = *(k+7);
492     do {
493         d0 = LOAD_UINT32_LITTLE(d+0); d1 = LOAD_UINT32_LITTLE(d+1);
494         d2 = LOAD_UINT32_LITTLE(d+2); d3 = LOAD_UINT32_LITTLE(d+3);
495         d4 = LOAD_UINT32_LITTLE(d+4); d5 = LOAD_UINT32_LITTLE(d+5);
496         d6 = LOAD_UINT32_LITTLE(d+6); d7 = LOAD_UINT32_LITTLE(d+7);
497         k8 = *(k+8); k9 = *(k+9); k10 = *(k+10); k11 = *(k+11);
498         k12 = *(k+12); k13 = *(k+13); k14 = *(k+14); k15 = *(k+15);
499         k16 = *(k+16); k17 = *(k+17); k18 = *(k+18); k19 = *(k+19);
500 
501         h1 += MUL64((k0 + d0), (k4 + d4));
502         h2 += MUL64((k4 + d0), (k8 + d4));
503         h3 += MUL64((k8 + d0), (k12 + d4));
504         h4 += MUL64((k12 + d0), (k16 + d4));
505 
506         h1 += MUL64((k1 + d1), (k5 + d5));
507         h2 += MUL64((k5 + d1), (k9 + d5));
508         h3 += MUL64((k9 + d1), (k13 + d5));
509         h4 += MUL64((k13 + d1), (k17 + d5));
510 
511         h1 += MUL64((k2 + d2), (k6 + d6));
512         h2 += MUL64((k6 + d2), (k10 + d6));
513         h3 += MUL64((k10 + d2), (k14 + d6));
514         h4 += MUL64((k14 + d2), (k18 + d6));
515 
516         h1 += MUL64((k3 + d3), (k7 + d7));
517         h2 += MUL64((k7 + d3), (k11 + d7));
518         h3 += MUL64((k11 + d3), (k15 + d7));
519         h4 += MUL64((k15 + d3), (k19 + d7));
520 
521         k0 = k8; k1 = k9; k2 = k10; k3 = k11;
522         k4 = k12; k5 = k13; k6 = k14; k7 = k15;
523         k8 = k16; k9 = k17; k10 = k18; k11 = k19;
524 
525         d += 8;
526         k += 8;
527     } while (--c);
528     ((UINT64 *)hp)[0] = h1;
529     ((UINT64 *)hp)[1] = h2;
530     ((UINT64 *)hp)[2] = h3;
531     ((UINT64 *)hp)[3] = h4;
532 }
533 
534 /* ---------------------------------------------------------------------- */
535 #endif  /* UMAC_OUTPUT_LENGTH */
536 /* ---------------------------------------------------------------------- */
537 
538 
539 /* ---------------------------------------------------------------------- */
540 
nh_transform(nh_ctx * hc,UINT8 * buf,UINT32 nbytes)541 static void nh_transform(nh_ctx *hc, UINT8 *buf, UINT32 nbytes)
542 /* This function is a wrapper for the primitive NH hash functions. It takes
543  * as argument "hc" the current hash context and a buffer which must be a
544  * multiple of L1_PAD_BOUNDARY. The key passed to nh_aux is offset
545  * appropriately according to how much message has been hashed already.
546  */
547 {
548     UINT8 *key;
549 
550     key = hc->nh_key + hc->bytes_hashed;
551     nh_aux(key, buf, hc->state, nbytes);
552 }
553 
554 /* ---------------------------------------------------------------------- */
555 
556 #if (__LITTLE_ENDIAN__)
endian_convert(void * buf,UWORD bpw,UINT32 num_bytes)557 static void endian_convert(void *buf, UWORD bpw, UINT32 num_bytes)
558 /* We endian convert the keys on little-endian computers to               */
559 /* compensate for the lack of big-endian memory reads during hashing.     */
560 {
561     UWORD iters = num_bytes / bpw;
562     if (bpw == 4) {
563         UINT32 *p = (UINT32 *)buf;
564         do {
565             *p = LOAD_UINT32_REVERSED(p);
566             p++;
567         } while (--iters);
568     } else if (bpw == 8) {
569         UINT32 *p = (UINT32 *)buf;
570         UINT32 t;
571         do {
572             t = LOAD_UINT32_REVERSED(p+1);
573             p[1] = LOAD_UINT32_REVERSED(p);
574             p[0] = t;
575             p += 2;
576         } while (--iters);
577     }
578 }
579 #define endian_convert_if_le(x,y,z) endian_convert((x),(y),(z))
580 #else
581 #define endian_convert_if_le(x,y,z) do{}while(0)  /* Do nothing */
582 #endif
583 
584 /* ---------------------------------------------------------------------- */
585 
nh_reset(nh_ctx * hc)586 static void nh_reset(nh_ctx *hc)
587 /* Reset nh_ctx to ready for hashing of new data */
588 {
589     hc->bytes_hashed = 0;
590     hc->next_data_empty = 0;
591     hc->state[0] = 0;
592 #if (UMAC_OUTPUT_LEN >= 8)
593     hc->state[1] = 0;
594 #endif
595 #if (UMAC_OUTPUT_LEN >= 12)
596     hc->state[2] = 0;
597 #endif
598 #if (UMAC_OUTPUT_LEN == 16)
599     hc->state[3] = 0;
600 #endif
601 
602 }
603 
604 /* ---------------------------------------------------------------------- */
605 
nh_init(nh_ctx * hc,aes_int_key prf_key)606 static void nh_init(nh_ctx *hc, aes_int_key prf_key)
607 /* Generate nh_key, endian convert and reset to be ready for hashing.   */
608 {
609     kdf(hc->nh_key, prf_key, 1, sizeof(hc->nh_key));
610     endian_convert_if_le(hc->nh_key, 4, sizeof(hc->nh_key));
611     nh_reset(hc);
612 }
613 
614 /* ---------------------------------------------------------------------- */
615 
nh_update(nh_ctx * hc,UINT8 * buf,UINT32 nbytes)616 static void nh_update(nh_ctx *hc, UINT8 *buf, UINT32 nbytes)
617 /* Incorporate nbytes of data into a nh_ctx, buffer whatever is not an    */
618 /* even multiple of HASH_BUF_BYTES.                                       */
619 {
620     UINT32 i,j;
621 
622     j = hc->next_data_empty;
623     if ((j + nbytes) >= HASH_BUF_BYTES) {
624         if (j) {
625             i = HASH_BUF_BYTES - j;
626             memcpy(hc->data+j, buf, i);
627             nh_transform(hc,hc->data,HASH_BUF_BYTES);
628             nbytes -= i;
629             buf += i;
630             hc->bytes_hashed += HASH_BUF_BYTES;
631         }
632         if (nbytes >= HASH_BUF_BYTES) {
633             i = nbytes & ~(HASH_BUF_BYTES - 1);
634             nh_transform(hc, buf, i);
635             nbytes -= i;
636             buf += i;
637             hc->bytes_hashed += i;
638         }
639         j = 0;
640     }
641     memcpy(hc->data + j, buf, nbytes);
642     hc->next_data_empty = j + nbytes;
643 }
644 
645 /* ---------------------------------------------------------------------- */
646 
zero_pad(UINT8 * p,int nbytes)647 static void zero_pad(UINT8 *p, int nbytes)
648 {
649 /* Write "nbytes" of zeroes, beginning at "p" */
650     if (nbytes >= (int)sizeof(UWORD)) {
651         while ((ptrdiff_t)p % sizeof(UWORD)) {
652             *p = 0;
653             nbytes--;
654             p++;
655         }
656         while (nbytes >= (int)sizeof(UWORD)) {
657             *(UWORD *)p = 0;
658             nbytes -= sizeof(UWORD);
659             p += sizeof(UWORD);
660         }
661     }
662     while (nbytes) {
663         *p = 0;
664         nbytes--;
665         p++;
666     }
667 }
668 
669 /* ---------------------------------------------------------------------- */
670 
nh_final(nh_ctx * hc,UINT8 * result)671 static void nh_final(nh_ctx *hc, UINT8 *result)
672 /* After passing some number of data buffers to nh_update() for integration
673  * into an NH context, nh_final is called to produce a hash result. If any
674  * bytes are in the buffer hc->data, incorporate them into the
675  * NH context. Finally, add into the NH accumulation "state" the total number
676  * of bits hashed. The resulting numbers are written to the buffer "result".
677  * If nh_update was never called, L1_PAD_BOUNDARY zeroes are incorporated.
678  */
679 {
680     int nh_len, nbits;
681 
682     if (hc->next_data_empty != 0) {
683         nh_len = ((hc->next_data_empty + (L1_PAD_BOUNDARY - 1)) &
684                                                 ~(L1_PAD_BOUNDARY - 1));
685         zero_pad(hc->data + hc->next_data_empty,
686                                           nh_len - hc->next_data_empty);
687         nh_transform(hc, hc->data, nh_len);
688         hc->bytes_hashed += hc->next_data_empty;
689     } else if (hc->bytes_hashed == 0) {
690     	nh_len = L1_PAD_BOUNDARY;
691         zero_pad(hc->data, L1_PAD_BOUNDARY);
692         nh_transform(hc, hc->data, nh_len);
693     }
694 
695     nbits = (hc->bytes_hashed << 3);
696     ((UINT64 *)result)[0] = ((UINT64 *)hc->state)[0] + nbits;
697 #if (UMAC_OUTPUT_LEN >= 8)
698     ((UINT64 *)result)[1] = ((UINT64 *)hc->state)[1] + nbits;
699 #endif
700 #if (UMAC_OUTPUT_LEN >= 12)
701     ((UINT64 *)result)[2] = ((UINT64 *)hc->state)[2] + nbits;
702 #endif
703 #if (UMAC_OUTPUT_LEN == 16)
704     ((UINT64 *)result)[3] = ((UINT64 *)hc->state)[3] + nbits;
705 #endif
706     nh_reset(hc);
707 }
708 
709 /* ---------------------------------------------------------------------- */
710 
nh(nh_ctx * hc,UINT8 * buf,UINT32 padded_len,UINT32 unpadded_len,UINT8 * result)711 static void nh(nh_ctx *hc, UINT8 *buf, UINT32 padded_len,
712                UINT32 unpadded_len, UINT8 *result)
713 /* All-in-one nh_update() and nh_final() equivalent.
714  * Assumes that padded_len is divisible by L1_PAD_BOUNDARY and result is
715  * well aligned
716  */
717 {
718     UINT32 nbits;
719 
720     /* Initialize the hash state */
721     nbits = (unpadded_len << 3);
722 
723     ((UINT64 *)result)[0] = nbits;
724 #if (UMAC_OUTPUT_LEN >= 8)
725     ((UINT64 *)result)[1] = nbits;
726 #endif
727 #if (UMAC_OUTPUT_LEN >= 12)
728     ((UINT64 *)result)[2] = nbits;
729 #endif
730 #if (UMAC_OUTPUT_LEN == 16)
731     ((UINT64 *)result)[3] = nbits;
732 #endif
733 
734     nh_aux(hc->nh_key, buf, result, padded_len);
735 }
736 
737 /* ---------------------------------------------------------------------- */
738 /* ---------------------------------------------------------------------- */
739 /* ----- Begin UHASH Section -------------------------------------------- */
740 /* ---------------------------------------------------------------------- */
741 /* ---------------------------------------------------------------------- */
742 
743 /* UHASH is a multi-layered algorithm. Data presented to UHASH is first
744  * hashed by NH. The NH output is then hashed by a polynomial-hash layer
745  * unless the initial data to be hashed is short. After the polynomial-
746  * layer, an inner-product hash is used to produce the final UHASH output.
747  *
748  * UHASH provides two interfaces, one all-at-once and another where data
749  * buffers are presented sequentially. In the sequential interface, the
750  * UHASH client calls the routine uhash_update() as many times as necessary.
751  * When there is no more data to be fed to UHASH, the client calls
752  * uhash_final() which
753  * calculates the UHASH output. Before beginning another UHASH calculation
754  * the uhash_reset() routine must be called. The all-at-once UHASH routine,
755  * uhash(), is equivalent to the sequence of calls uhash_update() and
756  * uhash_final(); however it is optimized and should be
757  * used whenever the sequential interface is not necessary.
758  *
759  * The routine uhash_init() initializes the uhash_ctx data structure and
760  * must be called once, before any other UHASH routine.
761  */
762 
763 /* ---------------------------------------------------------------------- */
764 /* ----- Constants and uhash_ctx ---------------------------------------- */
765 /* ---------------------------------------------------------------------- */
766 
767 /* ---------------------------------------------------------------------- */
768 /* ----- Poly hash and Inner-Product hash Constants --------------------- */
769 /* ---------------------------------------------------------------------- */
770 
771 /* Primes and masks */
772 #define p36    ((UINT64)0x0000000FFFFFFFFBull)              /* 2^36 -  5 */
773 #define p64    ((UINT64)0xFFFFFFFFFFFFFFC5ull)              /* 2^64 - 59 */
774 #define m36    ((UINT64)0x0000000FFFFFFFFFull)  /* The low 36 of 64 bits */
775 
776 
777 /* ---------------------------------------------------------------------- */
778 
779 typedef struct uhash_ctx {
780     nh_ctx hash;                          /* Hash context for L1 NH hash  */
781     UINT64 poly_key_8[STREAMS];           /* p64 poly keys                */
782     UINT64 poly_accum[STREAMS];           /* poly hash result             */
783     UINT64 ip_keys[STREAMS*4];            /* Inner-product keys           */
784     UINT32 ip_trans[STREAMS];             /* Inner-product translation    */
785     UINT32 msg_len;                       /* Total length of data passed  */
786                                           /* to uhash */
787 } uhash_ctx;
788 typedef struct uhash_ctx *uhash_ctx_t;
789 
790 /* ---------------------------------------------------------------------- */
791 
792 
793 /* The polynomial hashes use Horner's rule to evaluate a polynomial one
794  * word at a time. As described in the specification, poly32 and poly64
795  * require keys from special domains. The following implementations exploit
796  * the special domains to avoid overflow. The results are not guaranteed to
797  * be within Z_p32 and Z_p64, but the Inner-Product hash implementation
798  * patches any errant values.
799  */
800 
poly64(UINT64 cur,UINT64 key,UINT64 data)801 static UINT64 poly64(UINT64 cur, UINT64 key, UINT64 data)
802 {
803     UINT32 key_hi = (UINT32)(key >> 32),
804            key_lo = (UINT32)key,
805            cur_hi = (UINT32)(cur >> 32),
806            cur_lo = (UINT32)cur,
807            x_lo,
808            x_hi;
809     UINT64 X,T,res;
810 
811     X =  MUL64(key_hi, cur_lo) + MUL64(cur_hi, key_lo);
812     x_lo = (UINT32)X;
813     x_hi = (UINT32)(X >> 32);
814 
815     res = (MUL64(key_hi, cur_hi) + x_hi) * 59 + MUL64(key_lo, cur_lo);
816 
817     T = ((UINT64)x_lo << 32);
818     res += T;
819     if (res < T)
820         res += 59;
821 
822     res += data;
823     if (res < data)
824         res += 59;
825 
826     return res;
827 }
828 
829 
830 /* Although UMAC is specified to use a ramped polynomial hash scheme, this
831  * implementation does not handle all ramp levels. Because we don't handle
832  * the ramp up to p128 modulus in this implementation, we are limited to
833  * 2^14 poly_hash() invocations per stream (for a total capacity of 2^24
834  * bytes input to UMAC per tag, ie. 16MB).
835  */
poly_hash(uhash_ctx_t hc,UINT32 data_in[])836 static void poly_hash(uhash_ctx_t hc, UINT32 data_in[])
837 {
838     int i;
839     UINT64 *data=(UINT64*)data_in;
840 
841     for (i = 0; i < STREAMS; i++) {
842         if ((UINT32)(data[i] >> 32) == 0xfffffffful) {
843             hc->poly_accum[i] = poly64(hc->poly_accum[i],
844                                        hc->poly_key_8[i], p64 - 1);
845             hc->poly_accum[i] = poly64(hc->poly_accum[i],
846                                        hc->poly_key_8[i], (data[i] - 59));
847         } else {
848             hc->poly_accum[i] = poly64(hc->poly_accum[i],
849                                        hc->poly_key_8[i], data[i]);
850         }
851     }
852 }
853 
854 
855 /* ---------------------------------------------------------------------- */
856 
857 
858 /* The final step in UHASH is an inner-product hash. The poly hash
859  * produces a result not necessarily WORD_LEN bytes long. The inner-
860  * product hash breaks the polyhash output into 16-bit chunks and
861  * multiplies each with a 36 bit key.
862  */
863 
ip_aux(UINT64 t,UINT64 * ipkp,UINT64 data)864 static UINT64 ip_aux(UINT64 t, UINT64 *ipkp, UINT64 data)
865 {
866     t = t + ipkp[0] * (UINT64)(UINT16)(data >> 48);
867     t = t + ipkp[1] * (UINT64)(UINT16)(data >> 32);
868     t = t + ipkp[2] * (UINT64)(UINT16)(data >> 16);
869     t = t + ipkp[3] * (UINT64)(UINT16)(data);
870 
871     return t;
872 }
873 
ip_reduce_p36(UINT64 t)874 static UINT32 ip_reduce_p36(UINT64 t)
875 {
876 /* Divisionless modular reduction */
877     UINT64 ret;
878 
879     ret = (t & m36) + 5 * (t >> 36);
880     if (ret >= p36)
881         ret -= p36;
882 
883     /* return least significant 32 bits */
884     return (UINT32)(ret);
885 }
886 
887 
888 /* If the data being hashed by UHASH is no longer than L1_KEY_LEN, then
889  * the polyhash stage is skipped and ip_short is applied directly to the
890  * NH output.
891  */
ip_short(uhash_ctx_t ahc,UINT8 * nh_res,unsigned char * res)892 static void ip_short(uhash_ctx_t ahc, UINT8 *nh_res, unsigned char *res)
893 {
894     UINT64 t;
895     UINT64 *nhp = (UINT64 *)nh_res;
896 
897     t  = ip_aux(0,ahc->ip_keys, nhp[0]);
898     STORE_UINT32_BIG((UINT32 *)res+0, ip_reduce_p36(t) ^ ahc->ip_trans[0]);
899 #if (UMAC_OUTPUT_LEN >= 8)
900     t  = ip_aux(0,ahc->ip_keys+4, nhp[1]);
901     STORE_UINT32_BIG((UINT32 *)res+1, ip_reduce_p36(t) ^ ahc->ip_trans[1]);
902 #endif
903 #if (UMAC_OUTPUT_LEN >= 12)
904     t  = ip_aux(0,ahc->ip_keys+8, nhp[2]);
905     STORE_UINT32_BIG((UINT32 *)res+2, ip_reduce_p36(t) ^ ahc->ip_trans[2]);
906 #endif
907 #if (UMAC_OUTPUT_LEN == 16)
908     t  = ip_aux(0,ahc->ip_keys+12, nhp[3]);
909     STORE_UINT32_BIG((UINT32 *)res+3, ip_reduce_p36(t) ^ ahc->ip_trans[3]);
910 #endif
911 }
912 
913 /* If the data being hashed by UHASH is longer than L1_KEY_LEN, then
914  * the polyhash stage is not skipped and ip_long is applied to the
915  * polyhash output.
916  */
ip_long(uhash_ctx_t ahc,unsigned char * res)917 static void ip_long(uhash_ctx_t ahc, unsigned char *res)
918 {
919     int i;
920     UINT64 t;
921 
922     for (i = 0; i < STREAMS; i++) {
923         /* fix polyhash output not in Z_p64 */
924         if (ahc->poly_accum[i] >= p64)
925             ahc->poly_accum[i] -= p64;
926         t  = ip_aux(0,ahc->ip_keys+(i*4), ahc->poly_accum[i]);
927         STORE_UINT32_BIG((UINT32 *)res+i,
928                          ip_reduce_p36(t) ^ ahc->ip_trans[i]);
929     }
930 }
931 
932 
933 /* ---------------------------------------------------------------------- */
934 
935 /* ---------------------------------------------------------------------- */
936 
937 /* Reset uhash context for next hash session */
uhash_reset(uhash_ctx_t pc)938 static int uhash_reset(uhash_ctx_t pc)
939 {
940     nh_reset(&pc->hash);
941     pc->msg_len = 0;
942     pc->poly_accum[0] = 1;
943 #if (UMAC_OUTPUT_LEN >= 8)
944     pc->poly_accum[1] = 1;
945 #endif
946 #if (UMAC_OUTPUT_LEN >= 12)
947     pc->poly_accum[2] = 1;
948 #endif
949 #if (UMAC_OUTPUT_LEN == 16)
950     pc->poly_accum[3] = 1;
951 #endif
952     return 1;
953 }
954 
955 /* ---------------------------------------------------------------------- */
956 
957 /* Given a pointer to the internal key needed by kdf() and a uhash context,
958  * initialize the NH context and generate keys needed for poly and inner-
959  * product hashing. All keys are endian adjusted in memory so that native
960  * loads cause correct keys to be in registers during calculation.
961  */
uhash_init(uhash_ctx_t ahc,aes_int_key prf_key)962 static void uhash_init(uhash_ctx_t ahc, aes_int_key prf_key)
963 {
964     int i;
965     UINT8 buf[(8*STREAMS+4)*sizeof(UINT64)];
966 
967     /* Zero the entire uhash context */
968     memset(ahc, 0, sizeof(uhash_ctx));
969 
970     /* Initialize the L1 hash */
971     nh_init(&ahc->hash, prf_key);
972 
973     /* Setup L2 hash variables */
974     kdf(buf, prf_key, 2, sizeof(buf));    /* Fill buffer with index 1 key */
975     for (i = 0; i < STREAMS; i++) {
976         /* Fill keys from the buffer, skipping bytes in the buffer not
977          * used by this implementation. Endian reverse the keys if on a
978          * little-endian computer.
979          */
980         memcpy(ahc->poly_key_8+i, buf+24*i, 8);
981         endian_convert_if_le(ahc->poly_key_8+i, 8, 8);
982         /* Mask the 64-bit keys to their special domain */
983         ahc->poly_key_8[i] &= ((UINT64)0x01ffffffu << 32) + 0x01ffffffu;
984         ahc->poly_accum[i] = 1;  /* Our polyhash prepends a non-zero word */
985     }
986 
987     /* Setup L3-1 hash variables */
988     kdf(buf, prf_key, 3, sizeof(buf)); /* Fill buffer with index 2 key */
989     for (i = 0; i < STREAMS; i++)
990           memcpy(ahc->ip_keys+4*i, buf+(8*i+4)*sizeof(UINT64),
991                                                  4*sizeof(UINT64));
992     endian_convert_if_le(ahc->ip_keys, sizeof(UINT64),
993                                                   sizeof(ahc->ip_keys));
994     for (i = 0; i < STREAMS*4; i++)
995         ahc->ip_keys[i] %= p36;  /* Bring into Z_p36 */
996 
997     /* Setup L3-2 hash variables    */
998     /* Fill buffer with index 4 key */
999     kdf(ahc->ip_trans, prf_key, 4, STREAMS * sizeof(UINT32));
1000     endian_convert_if_le(ahc->ip_trans, sizeof(UINT32),
1001                          STREAMS * sizeof(UINT32));
1002 }
1003 
1004 /* ---------------------------------------------------------------------- */
1005 
uhash_update(uhash_ctx_t ctx,unsigned char * input,long len)1006 static int uhash_update(uhash_ctx_t ctx, unsigned char *input, long len)
1007 /* Given len bytes of data, we parse it into L1_KEY_LEN chunks and
1008  * hash each one with NH, calling the polyhash on each NH output.
1009  */
1010 {
1011     UWORD bytes_hashed, bytes_remaining;
1012     UINT64 result_buf[STREAMS];
1013     UINT8 *nh_result = (UINT8 *)&result_buf;
1014 
1015     if (ctx->msg_len + len <= L1_KEY_LEN) {
1016         nh_update(&ctx->hash, (UINT8 *)input, len);
1017         ctx->msg_len += len;
1018     } else {
1019 
1020          bytes_hashed = ctx->msg_len % L1_KEY_LEN;
1021          if (ctx->msg_len == L1_KEY_LEN)
1022              bytes_hashed = L1_KEY_LEN;
1023 
1024          if (bytes_hashed + len >= L1_KEY_LEN) {
1025 
1026              /* If some bytes have been passed to the hash function      */
1027              /* then we want to pass at most (L1_KEY_LEN - bytes_hashed) */
1028              /* bytes to complete the current nh_block.                  */
1029              if (bytes_hashed) {
1030                  bytes_remaining = (L1_KEY_LEN - bytes_hashed);
1031                  nh_update(&ctx->hash, (UINT8 *)input, bytes_remaining);
1032                  nh_final(&ctx->hash, nh_result);
1033                  ctx->msg_len += bytes_remaining;
1034                  poly_hash(ctx,(UINT32 *)nh_result);
1035                  len -= bytes_remaining;
1036                  input += bytes_remaining;
1037              }
1038 
1039              /* Hash directly from input stream if enough bytes */
1040              while (len >= L1_KEY_LEN) {
1041                  nh(&ctx->hash, (UINT8 *)input, L1_KEY_LEN,
1042                                    L1_KEY_LEN, nh_result);
1043                  ctx->msg_len += L1_KEY_LEN;
1044                  len -= L1_KEY_LEN;
1045                  input += L1_KEY_LEN;
1046                  poly_hash(ctx,(UINT32 *)nh_result);
1047              }
1048          }
1049 
1050          /* pass remaining < L1_KEY_LEN bytes of input data to NH */
1051          if (len) {
1052              nh_update(&ctx->hash, (UINT8 *)input, len);
1053              ctx->msg_len += len;
1054          }
1055      }
1056 
1057     return (1);
1058 }
1059 
1060 /* ---------------------------------------------------------------------- */
1061 
uhash_final(uhash_ctx_t ctx,unsigned char * res)1062 static int uhash_final(uhash_ctx_t ctx, unsigned char *res)
1063 /* Incorporate any pending data, pad, and generate tag */
1064 {
1065     UINT64 result_buf[STREAMS];
1066     UINT8 *nh_result = (UINT8 *)&result_buf;
1067 
1068     if (ctx->msg_len > L1_KEY_LEN) {
1069         if (ctx->msg_len % L1_KEY_LEN) {
1070             nh_final(&ctx->hash, nh_result);
1071             poly_hash(ctx,(UINT32 *)nh_result);
1072         }
1073         ip_long(ctx, res);
1074     } else {
1075         nh_final(&ctx->hash, nh_result);
1076         ip_short(ctx,nh_result, res);
1077     }
1078     uhash_reset(ctx);
1079     return (1);
1080 }
1081 
1082 /* ---------------------------------------------------------------------- */
1083 /* ---------------------------------------------------------------------- */
1084 /* ----- Begin UMAC Section --------------------------------------------- */
1085 /* ---------------------------------------------------------------------- */
1086 /* ---------------------------------------------------------------------- */
1087 
1088 /* The UMAC interface has two interfaces, an all-at-once interface where
1089  * the entire message to be authenticated is passed to UMAC in one buffer,
1090  * and a sequential interface where the message is presented a little at a
1091  * time. The all-at-once is more optimaized than the sequential version and
1092  * should be preferred when the sequential interface is not required.
1093  */
1094 struct umac_ctx {
1095     uhash_ctx hash;          /* Hash function for message compression    */
1096     pdf_ctx pdf;             /* PDF for hashed output                    */
1097     void *free_ptr;          /* Address to free this struct via          */
1098 };
1099 
1100 /* ---------------------------------------------------------------------- */
1101 
umac_reset(struct umac_ctx * ctx)1102 int umac_reset(struct umac_ctx *ctx)
1103 /* Reset the hash function to begin a new authentication.        */
1104 {
1105     uhash_reset(&ctx->hash);
1106     return (1);
1107 }
1108 
1109 /* ---------------------------------------------------------------------- */
1110 
umac_delete(struct umac_ctx * ctx)1111 int umac_delete(struct umac_ctx *ctx)
1112 /* Deallocate the ctx structure */
1113 {
1114     if (ctx) {
1115         if (ALLOC_BOUNDARY)
1116             ctx = (struct umac_ctx *)ctx->free_ptr;
1117         free(ctx);
1118     }
1119     return (1);
1120 }
1121 
1122 /* ---------------------------------------------------------------------- */
1123 
umac_alloc(void)1124 struct umac_ctx *umac_alloc(void) {
1125     struct umac_ctx *ctx, *octx;
1126     size_t bytes_to_add;
1127 
1128     octx = ctx = malloc(sizeof(struct umac_ctx) + ALLOC_BOUNDARY);
1129     if (ctx) {
1130         if (ALLOC_BOUNDARY) {
1131             bytes_to_add = ALLOC_BOUNDARY -
1132                               ((ptrdiff_t)ctx & (ALLOC_BOUNDARY - 1));
1133             ctx = (struct umac_ctx *)((unsigned char *)ctx + bytes_to_add);
1134         }
1135         ctx->free_ptr = octx;
1136     }
1137 
1138     return (ctx);
1139 }
1140 
umac_init(struct umac_ctx * ctx,unsigned char key[])1141 void umac_init(struct umac_ctx *ctx, unsigned char key[]) {
1142     aes_int_key prf_key;
1143 
1144     aes_key_setup(key, prf_key);
1145     pdf_init(&ctx->pdf, prf_key);
1146     uhash_init(&ctx->hash, prf_key);
1147 }
1148 
umac_new(unsigned char key[])1149 struct umac_ctx *umac_new(unsigned char key[])
1150 /* Dynamically allocate a umac_ctx struct, initialize variables,
1151  * generate subkeys from key. Align to 16-byte boundary.
1152  */
1153 {
1154     struct umac_ctx *ctx;
1155 
1156     ctx = umac_alloc();
1157     if (ctx) {
1158         umac_init(ctx, key);
1159     }
1160 
1161     return (ctx);
1162 }
1163 
1164 /* ---------------------------------------------------------------------- */
1165 
umac_final(struct umac_ctx * ctx,unsigned char tag[],unsigned char nonce[8])1166 int umac_final(struct umac_ctx *ctx, unsigned char tag[], unsigned char nonce[8])
1167 /* Incorporate any pending data, pad, and generate tag */
1168 {
1169     uhash_final(&ctx->hash, (unsigned char *)tag);
1170     pdf_gen_xor(&ctx->pdf, (UINT8 *)nonce, (UINT8 *)tag);
1171 
1172     return (1);
1173 }
1174 
1175 /* ---------------------------------------------------------------------- */
1176 
umac_update(struct umac_ctx * ctx,unsigned char * input,long len)1177 int umac_update(struct umac_ctx *ctx, unsigned char *input, long len)
1178 /* Given len bytes of data, we parse it into L1_KEY_LEN chunks and   */
1179 /* hash each one, calling the PDF on the hashed output whenever the hash- */
1180 /* output buffer is full.                                                 */
1181 {
1182     uhash_update(&ctx->hash, input, len);
1183     return (1);
1184 }
1185 
1186 #else
1187 
1188 struct umac_ctx {
1189     void *free_ptr;          /* Address to free this struct via          */
1190 };
1191 
umac_reset(struct umac_ctx * ctx)1192 int umac_reset(struct umac_ctx *ctx)
1193 /* Reset the hash function to begin a new authentication.        */
1194 {
1195     return (0);
1196 }
1197 
1198 /* ---------------------------------------------------------------------- */
1199 
umac_delete(struct umac_ctx * ctx)1200 int umac_delete(struct umac_ctx *ctx)
1201 /* Deallocate the ctx structure */
1202 {
1203     return (0);
1204 }
1205 
1206 /* ---------------------------------------------------------------------- */
1207 
umac_alloc(void)1208 struct umac_ctx *umac_alloc(void) {
1209     return (NULL);
1210 }
1211 
umac_init(struct umac_ctx * ctx,unsigned char key[])1212 void umac_init(struct umac_ctx *ctx, unsigned char key[]) {
1213 }
1214 
umac_new(unsigned char key[])1215 struct umac_ctx *umac_new(unsigned char key[])
1216 /* Dynamically allocate a umac_ctx struct, initialize variables,
1217  * generate subkeys from key. Align to 16-byte boundary.
1218  */
1219 {
1220     return (NULL);
1221 }
1222 
1223 /* ---------------------------------------------------------------------- */
1224 
umac_final(struct umac_ctx * ctx,unsigned char tag[],unsigned char nonce[8])1225 int umac_final(struct umac_ctx *ctx, unsigned char tag[], unsigned char nonce[8])
1226 {
1227     return (0);
1228 }
1229 
1230 /* ---------------------------------------------------------------------- */
1231 
umac_update(struct umac_ctx * ctx,unsigned char * input,long len)1232 int umac_update(struct umac_ctx *ctx, unsigned char *input, long len)
1233 /* Given len bytes of data, we parse it into L1_KEY_LEN chunks and   */
1234 /* hash each one, calling the PDF on the hashed output whenever the hash- */
1235 /* output buffer is full.                                                 */
1236 {
1237     return (0);
1238 }
1239 
1240 #endif /* OpenSSL-0.9.7 or later */
1241 
1242 /* ---------------------------------------------------------------------- */
1243 /* ---------------------------------------------------------------------- */
1244 /* ----- End UMAC Section ----------------------------------------------- */
1245 /* ---------------------------------------------------------------------- */
1246 /* ---------------------------------------------------------------------- */
1247 
1248