1 /* $FreeBSD$ */
2 /* $KAME: ah_core.c,v 1.44 2001/03/12 11:24:39 itojun Exp $ */
3
4 /*
5 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
6 * All rights reserved.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
10 * are met:
11 * 1. Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in the
15 * documentation and/or other materials provided with the distribution.
16 * 3. Neither the name of the project nor the names of its contributors
17 * may be used to endorse or promote products derived from this software
18 * without specific prior written permission.
19 *
20 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
21 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
23 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
24 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
25 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
26 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
28 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
29 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
30 * SUCH DAMAGE.
31 */
32
33 /*
34 * RFC1826/2402 authentication header.
35 */
36
37 /* TODO: have shared routines for hmac-* algorithms */
38
39 #include "opt_inet.h"
40 #include "opt_inet6.h"
41 #include "opt_ipsec.h"
42
43 #include <sys/param.h>
44 #include <sys/systm.h>
45 #include <sys/malloc.h>
46 #include <sys/mbuf.h>
47 #include <sys/domain.h>
48 #include <sys/protosw.h>
49 #include <sys/socket.h>
50 #include <sys/socketvar.h>
51 #include <sys/errno.h>
52 #include <sys/time.h>
53 #include <sys/syslog.h>
54
55 #include <net/if.h>
56 #include <net/route.h>
57
58 #include <netinet/in.h>
59 #include <netinet/in_systm.h>
60 #include <netinet/ip.h>
61 #include <netinet/in_var.h>
62
63 #ifdef INET6
64 #include <netinet/ip6.h>
65 #include <netinet6/ip6_var.h>
66 #include <netinet/icmp6.h>
67 #endif
68
69 #include <netinet6/ipsec.h>
70 #ifdef INET6
71 #include <netinet6/ipsec6.h>
72 #endif
73 #include <netinet6/ah.h>
74 #ifdef INET6
75 #include <netinet6/ah6.h>
76 #endif
77 #ifdef IPSEC_ESP
78 #include <netinet6/esp.h>
79 #ifdef INET6
80 #include <netinet6/esp6.h>
81 #endif
82 #endif
83 #include <net/pfkeyv2.h>
84 #include <netkey/keydb.h>
85 #include <sys/md5.h>
86 #include <crypto/sha1.h>
87 #include <crypto/sha2/sha2.h>
88
89 #include <net/net_osdep.h>
90
91 #define HMACSIZE 16
92
93 static int ah_sumsiz_1216 __P((struct secasvar *));
94 static int ah_sumsiz_zero __P((struct secasvar *));
95 static int ah_none_mature __P((struct secasvar *));
96 static int ah_none_init __P((struct ah_algorithm_state *, struct secasvar *));
97 static void ah_none_loop __P((struct ah_algorithm_state *, caddr_t, size_t));
98 static void ah_none_result __P((struct ah_algorithm_state *, caddr_t));
99 static int ah_keyed_md5_mature __P((struct secasvar *));
100 static int ah_keyed_md5_init __P((struct ah_algorithm_state *,
101 struct secasvar *));
102 static void ah_keyed_md5_loop __P((struct ah_algorithm_state *, caddr_t,
103 size_t));
104 static void ah_keyed_md5_result __P((struct ah_algorithm_state *, caddr_t));
105 static int ah_keyed_sha1_mature __P((struct secasvar *));
106 static int ah_keyed_sha1_init __P((struct ah_algorithm_state *,
107 struct secasvar *));
108 static void ah_keyed_sha1_loop __P((struct ah_algorithm_state *, caddr_t,
109 size_t));
110 static void ah_keyed_sha1_result __P((struct ah_algorithm_state *, caddr_t));
111 static int ah_hmac_md5_mature __P((struct secasvar *));
112 static int ah_hmac_md5_init __P((struct ah_algorithm_state *,
113 struct secasvar *));
114 static void ah_hmac_md5_loop __P((struct ah_algorithm_state *, caddr_t,
115 size_t));
116 static void ah_hmac_md5_result __P((struct ah_algorithm_state *, caddr_t));
117 static int ah_hmac_sha1_mature __P((struct secasvar *));
118 static int ah_hmac_sha1_init __P((struct ah_algorithm_state *,
119 struct secasvar *));
120 static void ah_hmac_sha1_loop __P((struct ah_algorithm_state *, caddr_t,
121 size_t));
122 static void ah_hmac_sha1_result __P((struct ah_algorithm_state *, caddr_t));
123 static int ah_hmac_sha2_256_mature __P((struct secasvar *));
124 static int ah_hmac_sha2_256_init __P((struct ah_algorithm_state *,
125 struct secasvar *));
126 static void ah_hmac_sha2_256_loop __P((struct ah_algorithm_state *, caddr_t,
127 size_t));
128 static void ah_hmac_sha2_256_result __P((struct ah_algorithm_state *, caddr_t));
129 static int ah_hmac_sha2_384_mature __P((struct secasvar *));
130 static int ah_hmac_sha2_384_init __P((struct ah_algorithm_state *,
131 struct secasvar *));
132 static void ah_hmac_sha2_384_loop __P((struct ah_algorithm_state *, caddr_t,
133 size_t));
134 static void ah_hmac_sha2_384_result __P((struct ah_algorithm_state *, caddr_t));
135 static int ah_hmac_sha2_512_mature __P((struct secasvar *));
136 static int ah_hmac_sha2_512_init __P((struct ah_algorithm_state *,
137 struct secasvar *));
138 static void ah_hmac_sha2_512_loop __P((struct ah_algorithm_state *, caddr_t,
139 size_t));
140 static void ah_hmac_sha2_512_result __P((struct ah_algorithm_state *, caddr_t));
141
142 static void ah_update_mbuf __P((struct mbuf *, int, int,
143 const struct ah_algorithm *, struct ah_algorithm_state *));
144
145 const struct ah_algorithm *
146 ah_algorithm_lookup(idx)
147 int idx;
148 {
149 /* checksum algorithms */
150 static struct ah_algorithm ah_algorithms[] = {
151 { ah_sumsiz_1216, ah_hmac_md5_mature, 128, 128, "hmac-md5",
152 ah_hmac_md5_init, ah_hmac_md5_loop,
153 ah_hmac_md5_result, },
154 { ah_sumsiz_1216, ah_hmac_sha1_mature, 160, 160, "hmac-sha1",
155 ah_hmac_sha1_init, ah_hmac_sha1_loop,
156 ah_hmac_sha1_result, },
157 { ah_sumsiz_1216, ah_keyed_md5_mature, 128, 128, "keyed-md5",
158 ah_keyed_md5_init, ah_keyed_md5_loop,
159 ah_keyed_md5_result, },
160 { ah_sumsiz_1216, ah_keyed_sha1_mature, 160, 160, "keyed-sha1",
161 ah_keyed_sha1_init, ah_keyed_sha1_loop,
162 ah_keyed_sha1_result, },
163 { ah_sumsiz_zero, ah_none_mature, 0, 2048, "none",
164 ah_none_init, ah_none_loop, ah_none_result, },
165 { ah_sumsiz_1216, ah_hmac_sha2_256_mature, 256, 256,
166 "hmac-sha2-256",
167 ah_hmac_sha2_256_init, ah_hmac_sha2_256_loop,
168 ah_hmac_sha2_256_result, },
169 { ah_sumsiz_1216, ah_hmac_sha2_384_mature, 384, 384,
170 "hmac-sha2-384",
171 ah_hmac_sha2_384_init, ah_hmac_sha2_384_loop,
172 ah_hmac_sha2_384_result, },
173 { ah_sumsiz_1216, ah_hmac_sha2_512_mature, 512, 512,
174 "hmac-sha2-512",
175 ah_hmac_sha2_512_init, ah_hmac_sha2_512_loop,
176 ah_hmac_sha2_512_result, },
177 };
178
179 switch (idx) {
180 case SADB_AALG_MD5HMAC:
181 return &ah_algorithms[0];
182 case SADB_AALG_SHA1HMAC:
183 return &ah_algorithms[1];
184 case SADB_X_AALG_MD5:
185 return &ah_algorithms[2];
186 case SADB_X_AALG_SHA:
187 return &ah_algorithms[3];
188 case SADB_X_AALG_NULL:
189 return &ah_algorithms[4];
190 case SADB_X_AALG_SHA2_256:
191 return &ah_algorithms[5];
192 case SADB_X_AALG_SHA2_384:
193 return &ah_algorithms[6];
194 case SADB_X_AALG_SHA2_512:
195 return &ah_algorithms[7];
196 default:
197 return NULL;
198 }
199 }
200
201
202 static int
203 ah_sumsiz_1216(sav)
204 struct secasvar *sav;
205 {
206 if (!sav)
207 return -1;
208 if (sav->flags & SADB_X_EXT_OLD)
209 return 16;
210 else
211 return 12;
212 }
213
214 static int
215 ah_sumsiz_zero(sav)
216 struct secasvar *sav;
217 {
218 if (!sav)
219 return -1;
220 return 0;
221 }
222
223 static int
224 ah_none_mature(sav)
225 struct secasvar *sav;
226 {
227 if (sav->sah->saidx.proto == IPPROTO_AH) {
228 ipseclog((LOG_ERR,
229 "ah_none_mature: protocol and algorithm mismatch.\n"));
230 return 1;
231 }
232 return 0;
233 }
234
235 static int
236 ah_none_init(state, sav)
237 struct ah_algorithm_state *state;
238 struct secasvar *sav;
239 {
240 state->foo = NULL;
241 return 0;
242 }
243
244 static void
245 ah_none_loop(state, addr, len)
246 struct ah_algorithm_state *state;
247 caddr_t addr;
248 size_t len;
249 {
250 }
251
252 static void
253 ah_none_result(state, addr)
254 struct ah_algorithm_state *state;
255 caddr_t addr;
256 {
257 }
258
259 static int
260 ah_keyed_md5_mature(sav)
261 struct secasvar *sav;
262 {
263 /* anything is okay */
264 return 0;
265 }
266
267 static int
268 ah_keyed_md5_init(state, sav)
269 struct ah_algorithm_state *state;
270 struct secasvar *sav;
271 {
272 size_t padlen;
273 size_t keybitlen;
274 u_int8_t buf[32];
275
276 if (!state)
277 panic("ah_keyed_md5_init: what?");
278
279 state->sav = sav;
280 state->foo = (void *)malloc(sizeof(MD5_CTX), M_TEMP, M_NOWAIT);
281 if (state->foo == NULL)
282 return ENOBUFS;
283
284 MD5Init((MD5_CTX *)state->foo);
285 if (state->sav) {
286 MD5Update((MD5_CTX *)state->foo,
287 (u_int8_t *)_KEYBUF(state->sav->key_auth),
288 (u_int)_KEYLEN(state->sav->key_auth));
289
290 /*
291 * Pad after the key.
292 * We cannot simply use md5_pad() since the function
293 * won't update the total length.
294 */
295 if (_KEYLEN(state->sav->key_auth) < 56)
296 padlen = 64 - 8 - _KEYLEN(state->sav->key_auth);
297 else
298 padlen = 64 + 64 - 8 - _KEYLEN(state->sav->key_auth);
299 keybitlen = _KEYLEN(state->sav->key_auth);
300 keybitlen *= 8;
301
302 buf[0] = 0x80;
303 MD5Update((MD5_CTX *)state->foo, &buf[0], 1);
304 padlen--;
305
306 bzero(buf, sizeof(buf));
307 while (sizeof(buf) < padlen) {
308 MD5Update((MD5_CTX *)state->foo, &buf[0], sizeof(buf));
309 padlen -= sizeof(buf);
310 }
311 if (padlen) {
312 MD5Update((MD5_CTX *)state->foo, &buf[0], padlen);
313 }
314
315 buf[0] = (keybitlen >> 0) & 0xff;
316 buf[1] = (keybitlen >> 8) & 0xff;
317 buf[2] = (keybitlen >> 16) & 0xff;
318 buf[3] = (keybitlen >> 24) & 0xff;
319 MD5Update((MD5_CTX *)state->foo, buf, 8);
320 }
321
322 return 0;
323 }
324
325 static void
326 ah_keyed_md5_loop(state, addr, len)
327 struct ah_algorithm_state *state;
328 caddr_t addr;
329 size_t len;
330 {
331 if (!state)
332 panic("ah_keyed_md5_loop: what?");
333
334 MD5Update((MD5_CTX *)state->foo, addr, len);
335 }
336
337 static void
338 ah_keyed_md5_result(state, addr)
339 struct ah_algorithm_state *state;
340 caddr_t addr;
341 {
342 u_char digest[16];
343
344 if (!state)
345 panic("ah_keyed_md5_result: what?");
346
347 if (state->sav) {
348 MD5Update((MD5_CTX *)state->foo,
349 (u_int8_t *)_KEYBUF(state->sav->key_auth),
350 (u_int)_KEYLEN(state->sav->key_auth));
351 }
352 MD5Final(&digest[0], (MD5_CTX *)state->foo);
353 free(state->foo, M_TEMP);
354 bcopy(&digest[0], (void *)addr, sizeof(digest));
355 }
356
357 static int
358 ah_keyed_sha1_mature(sav)
359 struct secasvar *sav;
360 {
361 const struct ah_algorithm *algo;
362
363 if (!sav->key_auth) {
364 ipseclog((LOG_ERR, "ah_keyed_sha1_mature: no key is given.\n"));
365 return 1;
366 }
367
368 algo = ah_algorithm_lookup(sav->alg_auth);
369 if (!algo) {
370 ipseclog((LOG_ERR, "ah_keyed_sha1_mature: unsupported algorithm.\n"));
371 return 1;
372 }
373
374 if (sav->key_auth->sadb_key_bits < algo->keymin
375 || algo->keymax < sav->key_auth->sadb_key_bits) {
376 ipseclog((LOG_ERR,
377 "ah_keyed_sha1_mature: invalid key length %d.\n",
378 sav->key_auth->sadb_key_bits));
379 return 1;
380 }
381
382 return 0;
383 }
384
385 static int
386 ah_keyed_sha1_init(state, sav)
387 struct ah_algorithm_state *state;
388 struct secasvar *sav;
389 {
390 SHA1_CTX *ctxt;
391 size_t padlen;
392 size_t keybitlen;
393 u_int8_t buf[32];
394
395 if (!state)
396 panic("ah_keyed_sha1_init: what?");
397
398 state->sav = sav;
399 state->foo = (void *)malloc(sizeof(SHA1_CTX), M_TEMP, M_NOWAIT);
400 if (!state->foo)
401 return ENOBUFS;
402
403 ctxt = (SHA1_CTX *)state->foo;
404 SHA1Init(ctxt);
405
406 if (state->sav) {
407 SHA1Update(ctxt, (u_int8_t *)_KEYBUF(state->sav->key_auth),
408 (u_int)_KEYLEN(state->sav->key_auth));
409
410 /*
411 * Pad after the key.
412 */
413 if (_KEYLEN(state->sav->key_auth) < 56)
414 padlen = 64 - 8 - _KEYLEN(state->sav->key_auth);
415 else
416 padlen = 64 + 64 - 8 - _KEYLEN(state->sav->key_auth);
417 keybitlen = _KEYLEN(state->sav->key_auth);
418 keybitlen *= 8;
419
420 buf[0] = 0x80;
421 SHA1Update(ctxt, &buf[0], 1);
422 padlen--;
423
424 bzero(buf, sizeof(buf));
425 while (sizeof(buf) < padlen) {
426 SHA1Update(ctxt, &buf[0], sizeof(buf));
427 padlen -= sizeof(buf);
428 }
429 if (padlen) {
430 SHA1Update(ctxt, &buf[0], padlen);
431 }
432
433 buf[0] = (keybitlen >> 0) & 0xff;
434 buf[1] = (keybitlen >> 8) & 0xff;
435 buf[2] = (keybitlen >> 16) & 0xff;
436 buf[3] = (keybitlen >> 24) & 0xff;
437 SHA1Update(ctxt, buf, 8);
438 }
439
440 return 0;
441 }
442
443 static void
444 ah_keyed_sha1_loop(state, addr, len)
445 struct ah_algorithm_state *state;
446 caddr_t addr;
447 size_t len;
448 {
449 SHA1_CTX *ctxt;
450
451 if (!state || !state->foo)
452 panic("ah_keyed_sha1_loop: what?");
453 ctxt = (SHA1_CTX *)state->foo;
454
455 SHA1Update(ctxt, (caddr_t)addr, (size_t)len);
456 }
457
458 static void
459 ah_keyed_sha1_result(state, addr)
460 struct ah_algorithm_state *state;
461 caddr_t addr;
462 {
463 u_char digest[SHA1_RESULTLEN]; /* SHA-1 generates 160 bits */
464 SHA1_CTX *ctxt;
465
466 if (!state || !state->foo)
467 panic("ah_keyed_sha1_result: what?");
468 ctxt = (SHA1_CTX *)state->foo;
469
470 if (state->sav) {
471 SHA1Update(ctxt, (u_int8_t *)_KEYBUF(state->sav->key_auth),
472 (u_int)_KEYLEN(state->sav->key_auth));
473 }
474 SHA1Final((caddr_t)&digest[0], ctxt);
475 bcopy(&digest[0], (void *)addr, HMACSIZE);
476
477 free(state->foo, M_TEMP);
478 }
479
480 static int
481 ah_hmac_md5_mature(sav)
482 struct secasvar *sav;
483 {
484 const struct ah_algorithm *algo;
485
486 if (!sav->key_auth) {
487 ipseclog((LOG_ERR, "ah_hmac_md5_mature: no key is given.\n"));
488 return 1;
489 }
490
491 algo = ah_algorithm_lookup(sav->alg_auth);
492 if (!algo) {
493 ipseclog((LOG_ERR, "ah_hmac_md5_mature: unsupported algorithm.\n"));
494 return 1;
495 }
496
497 if (sav->key_auth->sadb_key_bits < algo->keymin
498 || algo->keymax < sav->key_auth->sadb_key_bits) {
499 ipseclog((LOG_ERR,
500 "ah_hmac_md5_mature: invalid key length %d.\n",
501 sav->key_auth->sadb_key_bits));
502 return 1;
503 }
504
505 return 0;
506 }
507
508 static int
509 ah_hmac_md5_init(state, sav)
510 struct ah_algorithm_state *state;
511 struct secasvar *sav;
512 {
513 u_char *ipad;
514 u_char *opad;
515 u_char tk[16];
516 u_char *key;
517 size_t keylen;
518 size_t i;
519 MD5_CTX *ctxt;
520
521 if (!state)
522 panic("ah_hmac_md5_init: what?");
523
524 state->sav = sav;
525 state->foo = (void *)malloc(64 + 64 + sizeof(MD5_CTX), M_TEMP, M_NOWAIT);
526 if (!state->foo)
527 return ENOBUFS;
528
529 ipad = (u_char *)state->foo;
530 opad = (u_char *)(ipad + 64);
531 ctxt = (MD5_CTX *)(opad + 64);
532
533 /* compress the key if necessery */
534 if (64 < _KEYLEN(state->sav->key_auth)) {
535 MD5Init(ctxt);
536 MD5Update(ctxt, _KEYBUF(state->sav->key_auth),
537 _KEYLEN(state->sav->key_auth));
538 MD5Final(&tk[0], ctxt);
539 key = &tk[0];
540 keylen = 16;
541 } else {
542 key = _KEYBUF(state->sav->key_auth);
543 keylen = _KEYLEN(state->sav->key_auth);
544 }
545
546 bzero(ipad, 64);
547 bzero(opad, 64);
548 bcopy(key, ipad, keylen);
549 bcopy(key, opad, keylen);
550 for (i = 0; i < 64; i++) {
551 ipad[i] ^= 0x36;
552 opad[i] ^= 0x5c;
553 }
554
555 MD5Init(ctxt);
556 MD5Update(ctxt, ipad, 64);
557
558 return 0;
559 }
560
561 static void
562 ah_hmac_md5_loop(state, addr, len)
563 struct ah_algorithm_state *state;
564 caddr_t addr;
565 size_t len;
566 {
567 MD5_CTX *ctxt;
568
569 if (!state || !state->foo)
570 panic("ah_hmac_md5_loop: what?");
571 ctxt = (MD5_CTX *)(((caddr_t)state->foo) + 128);
572 MD5Update(ctxt, addr, len);
573 }
574
575 static void
576 ah_hmac_md5_result(state, addr)
577 struct ah_algorithm_state *state;
578 caddr_t addr;
579 {
580 u_char digest[16];
581 u_char *ipad;
582 u_char *opad;
583 MD5_CTX *ctxt;
584
585 if (!state || !state->foo)
586 panic("ah_hmac_md5_result: what?");
587
588 ipad = (u_char *)state->foo;
589 opad = (u_char *)(ipad + 64);
590 ctxt = (MD5_CTX *)(opad + 64);
591
592 MD5Final(&digest[0], ctxt);
593
594 MD5Init(ctxt);
595 MD5Update(ctxt, opad, 64);
596 MD5Update(ctxt, &digest[0], sizeof(digest));
597 MD5Final(&digest[0], ctxt);
598
599 bcopy(&digest[0], (void *)addr, HMACSIZE);
600
601 free(state->foo, M_TEMP);
602 }
603
604 static int
605 ah_hmac_sha1_mature(sav)
606 struct secasvar *sav;
607 {
608 const struct ah_algorithm *algo;
609
610 if (!sav->key_auth) {
611 ipseclog((LOG_ERR, "ah_hmac_sha1_mature: no key is given.\n"));
612 return 1;
613 }
614
615 algo = ah_algorithm_lookup(sav->alg_auth);
616 if (!algo) {
617 ipseclog((LOG_ERR, "ah_hmac_sha1_mature: unsupported algorithm.\n"));
618 return 1;
619 }
620
621 if (sav->key_auth->sadb_key_bits < algo->keymin
622 || algo->keymax < sav->key_auth->sadb_key_bits) {
623 ipseclog((LOG_ERR,
624 "ah_hmac_sha1_mature: invalid key length %d.\n",
625 sav->key_auth->sadb_key_bits));
626 return 1;
627 }
628
629 return 0;
630 }
631
632 static int
633 ah_hmac_sha1_init(state, sav)
634 struct ah_algorithm_state *state;
635 struct secasvar *sav;
636 {
637 u_char *ipad;
638 u_char *opad;
639 SHA1_CTX *ctxt;
640 u_char tk[SHA1_RESULTLEN]; /* SHA-1 generates 160 bits */
641 u_char *key;
642 size_t keylen;
643 size_t i;
644
645 if (!state)
646 panic("ah_hmac_sha1_init: what?");
647
648 state->sav = sav;
649 state->foo = (void *)malloc(64 + 64 + sizeof(SHA1_CTX),
650 M_TEMP, M_NOWAIT);
651 if (!state->foo)
652 return ENOBUFS;
653
654 ipad = (u_char *)state->foo;
655 opad = (u_char *)(ipad + 64);
656 ctxt = (SHA1_CTX *)(opad + 64);
657
658 /* compress the key if necessery */
659 if (64 < _KEYLEN(state->sav->key_auth)) {
660 SHA1Init(ctxt);
661 SHA1Update(ctxt, _KEYBUF(state->sav->key_auth),
662 _KEYLEN(state->sav->key_auth));
663 SHA1Final(&tk[0], ctxt);
664 key = &tk[0];
665 keylen = SHA1_RESULTLEN;
666 } else {
667 key = _KEYBUF(state->sav->key_auth);
668 keylen = _KEYLEN(state->sav->key_auth);
669 }
670
671 bzero(ipad, 64);
672 bzero(opad, 64);
673 bcopy(key, ipad, keylen);
674 bcopy(key, opad, keylen);
675 for (i = 0; i < 64; i++) {
676 ipad[i] ^= 0x36;
677 opad[i] ^= 0x5c;
678 }
679
680 SHA1Init(ctxt);
681 SHA1Update(ctxt, ipad, 64);
682
683 return 0;
684 }
685
686 static void
687 ah_hmac_sha1_loop(state, addr, len)
688 struct ah_algorithm_state *state;
689 caddr_t addr;
690 size_t len;
691 {
692 SHA1_CTX *ctxt;
693
694 if (!state || !state->foo)
695 panic("ah_hmac_sha1_loop: what?");
696
697 ctxt = (SHA1_CTX *)(((u_char *)state->foo) + 128);
698 SHA1Update(ctxt, (caddr_t)addr, (size_t)len);
699 }
700
701 static void
702 ah_hmac_sha1_result(state, addr)
703 struct ah_algorithm_state *state;
704 caddr_t addr;
705 {
706 u_char digest[SHA1_RESULTLEN]; /* SHA-1 generates 160 bits */
707 u_char *ipad;
708 u_char *opad;
709 SHA1_CTX *ctxt;
710
711 if (!state || !state->foo)
712 panic("ah_hmac_sha1_result: what?");
713
714 ipad = (u_char *)state->foo;
715 opad = (u_char *)(ipad + 64);
716 ctxt = (SHA1_CTX *)(opad + 64);
717
718 SHA1Final((caddr_t)&digest[0], ctxt);
719
720 SHA1Init(ctxt);
721 SHA1Update(ctxt, opad, 64);
722 SHA1Update(ctxt, (caddr_t)&digest[0], sizeof(digest));
723 SHA1Final((caddr_t)&digest[0], ctxt);
724
725 bcopy(&digest[0], (void *)addr, HMACSIZE);
726
727 free(state->foo, M_TEMP);
728 }
729
730 static int
731 ah_hmac_sha2_256_mature(sav)
732 struct secasvar *sav;
733 {
734 const struct ah_algorithm *algo;
735
736 if (!sav->key_auth) {
737 ipseclog((LOG_ERR,
738 "ah_hmac_sha2_256_mature: no key is given.\n"));
739 return 1;
740 }
741
742 algo = ah_algorithm_lookup(sav->alg_auth);
743 if (!algo) {
744 ipseclog((LOG_ERR,
745 "ah_hmac_sha2_256_mature: unsupported algorithm.\n"));
746 return 1;
747 }
748
749 if (sav->key_auth->sadb_key_bits < algo->keymin ||
750 algo->keymax < sav->key_auth->sadb_key_bits) {
751 ipseclog((LOG_ERR,
752 "ah_hmac_sha2_256_mature: invalid key length %d.\n",
753 sav->key_auth->sadb_key_bits));
754 return 1;
755 }
756
757 return 0;
758 }
759
760 static int
761 ah_hmac_sha2_256_init(state, sav)
762 struct ah_algorithm_state *state;
763 struct secasvar *sav;
764 {
765 u_char *ipad;
766 u_char *opad;
767 SHA256_CTX *ctxt;
768 u_char tk[SHA256_DIGEST_LENGTH];
769 u_char *key;
770 size_t keylen;
771 size_t i;
772
773 if (!state)
774 panic("ah_hmac_sha2_256_init: what?");
775
776 state->sav = sav;
777 state->foo = (void *)malloc(64 + 64 + sizeof(SHA256_CTX),
778 M_TEMP, M_NOWAIT);
779 if (!state->foo)
780 return ENOBUFS;
781
782 ipad = (u_char *)state->foo;
783 opad = (u_char *)(ipad + 64);
784 ctxt = (SHA256_CTX *)(opad + 64);
785
786 /* compress the key if necessery */
787 if (64 < _KEYLEN(state->sav->key_auth)) {
788 bzero(tk, sizeof(tk));
789 bzero(ctxt, sizeof(*ctxt));
790 SHA256_Init(ctxt);
791 SHA256_Update(ctxt, _KEYBUF(state->sav->key_auth),
792 _KEYLEN(state->sav->key_auth));
793 SHA256_Final(&tk[0], ctxt);
794 key = &tk[0];
795 keylen = sizeof(tk) < 64 ? sizeof(tk) : 64;
796 } else {
797 key = _KEYBUF(state->sav->key_auth);
798 keylen = _KEYLEN(state->sav->key_auth);
799 }
800
801 bzero(ipad, 64);
802 bzero(opad, 64);
803 bcopy(key, ipad, keylen);
804 bcopy(key, opad, keylen);
805 for (i = 0; i < 64; i++) {
806 ipad[i] ^= 0x36;
807 opad[i] ^= 0x5c;
808 }
809
810 bzero(ctxt, sizeof(*ctxt));
811 SHA256_Init(ctxt);
812 SHA256_Update(ctxt, ipad, 64);
813
814 return 0;
815 }
816
817 static void
818 ah_hmac_sha2_256_loop(state, addr, len)
819 struct ah_algorithm_state *state;
820 caddr_t addr;
821 size_t len;
822 {
823 SHA256_CTX *ctxt;
824
825 if (!state || !state->foo)
826 panic("ah_hmac_sha2_256_loop: what?");
827
828 ctxt = (SHA256_CTX *)(((u_char *)state->foo) + 128);
829 SHA256_Update(ctxt, (caddr_t)addr, (size_t)len);
830 }
831
832 static void
833 ah_hmac_sha2_256_result(state, addr)
834 struct ah_algorithm_state *state;
835 caddr_t addr;
836 {
837 u_char digest[SHA256_DIGEST_LENGTH];
838 u_char *ipad;
839 u_char *opad;
840 SHA256_CTX *ctxt;
841
842 if (!state || !state->foo)
843 panic("ah_hmac_sha2_256_result: what?");
844
845 ipad = (u_char *)state->foo;
846 opad = (u_char *)(ipad + 64);
847 ctxt = (SHA256_CTX *)(opad + 64);
848
849 SHA256_Final((caddr_t)&digest[0], ctxt);
850
851 bzero(ctxt, sizeof(*ctxt));
852 SHA256_Init(ctxt);
853 SHA256_Update(ctxt, opad, 64);
854 SHA256_Update(ctxt, (caddr_t)&digest[0], sizeof(digest));
855 SHA256_Final((caddr_t)&digest[0], ctxt);
856
857 bcopy(&digest[0], (void *)addr, HMACSIZE);
858
859 free(state->foo, M_TEMP);
860 }
861
862 static int
863 ah_hmac_sha2_384_mature(sav)
864 struct secasvar *sav;
865 {
866 const struct ah_algorithm *algo;
867
868 if (!sav->key_auth) {
869 ipseclog((LOG_ERR,
870 "ah_hmac_sha2_384_mature: no key is given.\n"));
871 return 1;
872 }
873
874 algo = ah_algorithm_lookup(sav->alg_auth);
875 if (!algo) {
876 ipseclog((LOG_ERR,
877 "ah_hmac_sha2_384_mature: unsupported algorithm.\n"));
878 return 1;
879 }
880
881 if (sav->key_auth->sadb_key_bits < algo->keymin ||
882 algo->keymax < sav->key_auth->sadb_key_bits) {
883 ipseclog((LOG_ERR,
884 "ah_hmac_sha2_384_mature: invalid key length %d.\n",
885 sav->key_auth->sadb_key_bits));
886 return 1;
887 }
888
889 return 0;
890 }
891
892 static int
893 ah_hmac_sha2_384_init(state, sav)
894 struct ah_algorithm_state *state;
895 struct secasvar *sav;
896 {
897 u_char *ipad;
898 u_char *opad;
899 SHA384_CTX *ctxt;
900 u_char tk[SHA384_DIGEST_LENGTH];
901 u_char *key;
902 size_t keylen;
903 size_t i;
904
905 if (!state)
906 panic("ah_hmac_sha2_384_init: what?");
907
908 state->sav = sav;
909 state->foo = (void *)malloc(64 + 64 + sizeof(SHA384_CTX),
910 M_TEMP, M_NOWAIT);
911 if (!state->foo)
912 return ENOBUFS;
913 bzero(state->foo, 64 + 64 + sizeof(SHA384_CTX));
914
915 ipad = (u_char *)state->foo;
916 opad = (u_char *)(ipad + 64);
917 ctxt = (SHA384_CTX *)(opad + 64);
918
919 /* compress the key if necessery */
920 if (64 < _KEYLEN(state->sav->key_auth)) {
921 bzero(tk, sizeof(tk));
922 bzero(ctxt, sizeof(*ctxt));
923 SHA384_Init(ctxt);
924 SHA384_Update(ctxt, _KEYBUF(state->sav->key_auth),
925 _KEYLEN(state->sav->key_auth));
926 SHA384_Final(&tk[0], ctxt);
927 key = &tk[0];
928 keylen = sizeof(tk) < 64 ? sizeof(tk) : 64;
929 } else {
930 key = _KEYBUF(state->sav->key_auth);
931 keylen = _KEYLEN(state->sav->key_auth);
932 }
933
934 bzero(ipad, 64);
935 bzero(opad, 64);
936 bcopy(key, ipad, keylen);
937 bcopy(key, opad, keylen);
938 for (i = 0; i < 64; i++) {
939 ipad[i] ^= 0x36;
940 opad[i] ^= 0x5c;
941 }
942
943 bzero(ctxt, sizeof(*ctxt));
944 SHA384_Init(ctxt);
945 SHA384_Update(ctxt, ipad, 64);
946
947 return 0;
948 }
949
950 static void
951 ah_hmac_sha2_384_loop(state, addr, len)
952 struct ah_algorithm_state *state;
953 caddr_t addr;
954 size_t len;
955 {
956 SHA384_CTX *ctxt;
957
958 if (!state || !state->foo)
959 panic("ah_hmac_sha2_384_loop: what?");
960
961 ctxt = (SHA384_CTX *)(((u_char *)state->foo) + 128);
962 SHA384_Update(ctxt, (caddr_t)addr, (size_t)len);
963 }
964
965 static void
966 ah_hmac_sha2_384_result(state, addr)
967 struct ah_algorithm_state *state;
968 caddr_t addr;
969 {
970 u_char digest[SHA384_DIGEST_LENGTH];
971 u_char *ipad;
972 u_char *opad;
973 SHA384_CTX *ctxt;
974
975 if (!state || !state->foo)
976 panic("ah_hmac_sha2_384_result: what?");
977
978 ipad = (u_char *)state->foo;
979 opad = (u_char *)(ipad + 64);
980 ctxt = (SHA384_CTX *)(opad + 64);
981
982 SHA384_Final((caddr_t)&digest[0], ctxt);
983
984 bzero(ctxt, sizeof(*ctxt));
985 SHA384_Init(ctxt);
986 SHA384_Update(ctxt, opad, 64);
987 SHA384_Update(ctxt, (caddr_t)&digest[0], sizeof(digest));
988 SHA384_Final((caddr_t)&digest[0], ctxt);
989
990 bcopy(&digest[0], (void *)addr, HMACSIZE);
991
992 free(state->foo, M_TEMP);
993 }
994
995 static int
996 ah_hmac_sha2_512_mature(sav)
997 struct secasvar *sav;
998 {
999 const struct ah_algorithm *algo;
1000
1001 if (!sav->key_auth) {
1002 ipseclog((LOG_ERR,
1003 "ah_hmac_sha2_512_mature: no key is given.\n"));
1004 return 1;
1005 }
1006
1007 algo = ah_algorithm_lookup(sav->alg_auth);
1008 if (!algo) {
1009 ipseclog((LOG_ERR,
1010 "ah_hmac_sha2_512_mature: unsupported algorithm.\n"));
1011 return 1;
1012 }
1013
1014 if (sav->key_auth->sadb_key_bits < algo->keymin ||
1015 algo->keymax < sav->key_auth->sadb_key_bits) {
1016 ipseclog((LOG_ERR,
1017 "ah_hmac_sha2_512_mature: invalid key length %d.\n",
1018 sav->key_auth->sadb_key_bits));
1019 return 1;
1020 }
1021
1022 return 0;
1023 }
1024
1025 static int
1026 ah_hmac_sha2_512_init(state, sav)
1027 struct ah_algorithm_state *state;
1028 struct secasvar *sav;
1029 {
1030 u_char *ipad;
1031 u_char *opad;
1032 SHA512_CTX *ctxt;
1033 u_char tk[SHA512_DIGEST_LENGTH];
1034 u_char *key;
1035 size_t keylen;
1036 size_t i;
1037
1038 if (!state)
1039 panic("ah_hmac_sha2_512_init: what?");
1040
1041 state->sav = sav;
1042 state->foo = (void *)malloc(64 + 64 + sizeof(SHA512_CTX),
1043 M_TEMP, M_NOWAIT);
1044 if (!state->foo)
1045 return ENOBUFS;
1046 bzero(state->foo, 64 + 64 + sizeof(SHA512_CTX));
1047
1048 ipad = (u_char *)state->foo;
1049 opad = (u_char *)(ipad + 64);
1050 ctxt = (SHA512_CTX *)(opad + 64);
1051
1052 /* compress the key if necessery */
1053 if (64 < _KEYLEN(state->sav->key_auth)) {
1054 bzero(tk, sizeof(tk));
1055 bzero(ctxt, sizeof(*ctxt));
1056 SHA512_Init(ctxt);
1057 SHA512_Update(ctxt, _KEYBUF(state->sav->key_auth),
1058 _KEYLEN(state->sav->key_auth));
1059 SHA512_Final(&tk[0], ctxt);
1060 key = &tk[0];
1061 keylen = sizeof(tk) < 64 ? sizeof(tk) : 64;
1062 } else {
1063 key = _KEYBUF(state->sav->key_auth);
1064 keylen = _KEYLEN(state->sav->key_auth);
1065 }
1066
1067 bzero(ipad, 64);
1068 bzero(opad, 64);
1069 bcopy(key, ipad, keylen);
1070 bcopy(key, opad, keylen);
1071 for (i = 0; i < 64; i++) {
1072 ipad[i] ^= 0x36;
1073 opad[i] ^= 0x5c;
1074 }
1075
1076 bzero(ctxt, sizeof(*ctxt));
1077 SHA512_Init(ctxt);
1078 SHA512_Update(ctxt, ipad, 64);
1079
1080 return 0;
1081 }
1082
1083 static void
1084 ah_hmac_sha2_512_loop(state, addr, len)
1085 struct ah_algorithm_state *state;
1086 caddr_t addr;
1087 size_t len;
1088 {
1089 SHA512_CTX *ctxt;
1090
1091 if (!state || !state->foo)
1092 panic("ah_hmac_sha2_512_loop: what?");
1093
1094 ctxt = (SHA512_CTX *)(((u_char *)state->foo) + 128);
1095 SHA512_Update(ctxt, (caddr_t)addr, (size_t)len);
1096 }
1097
1098 static void
1099 ah_hmac_sha2_512_result(state, addr)
1100 struct ah_algorithm_state *state;
1101 caddr_t addr;
1102 {
1103 u_char digest[SHA512_DIGEST_LENGTH];
1104 u_char *ipad;
1105 u_char *opad;
1106 SHA512_CTX *ctxt;
1107
1108 if (!state || !state->foo)
1109 panic("ah_hmac_sha2_512_result: what?");
1110
1111 ipad = (u_char *)state->foo;
1112 opad = (u_char *)(ipad + 64);
1113 ctxt = (SHA512_CTX *)(opad + 64);
1114
1115 SHA512_Final((caddr_t)&digest[0], ctxt);
1116
1117 bzero(ctxt, sizeof(*ctxt));
1118 SHA512_Init(ctxt);
1119 SHA512_Update(ctxt, opad, 64);
1120 SHA512_Update(ctxt, (caddr_t)&digest[0], sizeof(digest));
1121 SHA512_Final((caddr_t)&digest[0], ctxt);
1122
1123 bcopy(&digest[0], (void *)addr, HMACSIZE);
1124
1125 free(state->foo, M_TEMP);
1126 }
1127
1128 /*------------------------------------------------------------*/
1129
1130 /*
1131 * go generate the checksum.
1132 */
1133 static void
1134 ah_update_mbuf(m, off, len, algo, algos)
1135 struct mbuf *m;
1136 int off;
1137 int len;
1138 const struct ah_algorithm *algo;
1139 struct ah_algorithm_state *algos;
1140 {
1141 struct mbuf *n;
1142 int tlen;
1143
1144 /* easy case first */
1145 if (off + len <= m->m_len) {
1146 (algo->update)(algos, mtod(m, caddr_t) + off, len);
1147 return;
1148 }
1149
1150 for (n = m; n; n = n->m_next) {
1151 if (off < n->m_len)
1152 break;
1153
1154 off -= n->m_len;
1155 }
1156
1157 if (!n)
1158 panic("ah_update_mbuf: wrong offset specified");
1159
1160 for (/* nothing */; n && len > 0; n = n->m_next) {
1161 if (n->m_len == 0)
1162 continue;
1163 if (n->m_len - off < len)
1164 tlen = n->m_len - off;
1165 else
1166 tlen = len;
1167
1168 (algo->update)(algos, mtod(n, caddr_t) + off, tlen);
1169
1170 len -= tlen;
1171 off = 0;
1172 }
1173 }
1174
1175 #ifdef INET
1176 /*
1177 * Go generate the checksum. This function won't modify the mbuf chain
1178 * except AH itself.
1179 *
1180 * NOTE: the function does not free mbuf on failure.
1181 * Don't use m_copy(), it will try to share cluster mbuf by using refcnt.
1182 */
1183 int
1184 ah4_calccksum(m, ahdat, len, algo, sav)
1185 struct mbuf *m;
1186 caddr_t ahdat;
1187 size_t len;
1188 const struct ah_algorithm *algo;
1189 struct secasvar *sav;
1190 {
1191 int off;
1192 int hdrtype;
1193 size_t advancewidth;
1194 struct ah_algorithm_state algos;
1195 u_char sumbuf[AH_MAXSUMSIZE];
1196 int error = 0;
1197 int ahseen;
1198 struct mbuf *n = NULL;
1199
1200 if ((m->m_flags & M_PKTHDR) == 0)
1201 return EINVAL;
1202
1203 ahseen = 0;
1204 hdrtype = -1; /* dummy, it is called IPPROTO_IP */
1205
1206 off = 0;
1207
1208 error = (algo->init)(&algos, sav);
1209 if (error)
1210 return error;
1211
1212 advancewidth = 0; /* safety */
1213
1214 again:
1215 /* gory. */
1216 switch (hdrtype) {
1217 case -1: /* first one only */
1218 {
1219 /*
1220 * copy ip hdr, modify to fit the AH checksum rule,
1221 * then take a checksum.
1222 */
1223 struct ip iphdr;
1224 size_t hlen;
1225
1226 m_copydata(m, off, sizeof(iphdr), (caddr_t)&iphdr);
1227 #ifdef _IP_VHL
1228 hlen = IP_VHL_HL(iphdr.ip_vhl) << 2;
1229 #else
1230 hlen = iphdr.ip_hl << 2;
1231 #endif
1232 iphdr.ip_ttl = 0;
1233 iphdr.ip_sum = htons(0);
1234 if (ip4_ah_cleartos)
1235 iphdr.ip_tos = 0;
1236 iphdr.ip_off = htons(ntohs(iphdr.ip_off) & ip4_ah_offsetmask);
1237 (algo->update)(&algos, (caddr_t)&iphdr, sizeof(struct ip));
1238
1239 if (hlen != sizeof(struct ip)) {
1240 u_char *p;
1241 int i, l, skip;
1242
1243 if (hlen > MCLBYTES) {
1244 error = EMSGSIZE;
1245 goto fail;
1246 }
1247 MGET(n, M_DONTWAIT, MT_DATA);
1248 if (n && hlen > MLEN) {
1249 MCLGET(n, M_DONTWAIT);
1250 if ((n->m_flags & M_EXT) == 0) {
1251 m_free(n);
1252 n = NULL;
1253 }
1254 }
1255 if (n == NULL) {
1256 error = ENOBUFS;
1257 goto fail;
1258 }
1259 m_copydata(m, off, hlen, mtod(n, caddr_t));
1260
1261 /*
1262 * IP options processing.
1263 * See RFC2402 appendix A.
1264 */
1265 p = mtod(n, u_char *);
1266 i = sizeof(struct ip);
1267 while (i < hlen) {
1268 if (i + IPOPT_OPTVAL >= hlen) {
1269 ipseclog((LOG_ERR, "ah4_calccksum: "
1270 "invalid IP option\n"));
1271 error = EINVAL;
1272 goto fail;
1273 }
1274 if (p[i + IPOPT_OPTVAL] == IPOPT_EOL ||
1275 p[i + IPOPT_OPTVAL] == IPOPT_NOP ||
1276 i + IPOPT_OLEN < hlen)
1277 ;
1278 else {
1279 ipseclog((LOG_ERR,
1280 "ah4_calccksum: invalid IP option "
1281 "(type=%02x)\n",
1282 p[i + IPOPT_OPTVAL]));
1283 error = EINVAL;
1284 goto fail;
1285 }
1286
1287 skip = 1;
1288 switch (p[i + IPOPT_OPTVAL]) {
1289 case IPOPT_EOL:
1290 case IPOPT_NOP:
1291 l = 1;
1292 skip = 0;
1293 break;
1294 case IPOPT_SECURITY: /* 0x82 */
1295 case 0x85: /* Extended security */
1296 case 0x86: /* Commercial security */
1297 case 0x94: /* Router alert */
1298 case 0x95: /* RFC1770 */
1299 l = p[i + IPOPT_OLEN];
1300 if (l < 2)
1301 goto invalopt;
1302 skip = 0;
1303 break;
1304 default:
1305 l = p[i + IPOPT_OLEN];
1306 if (l < 2)
1307 goto invalopt;
1308 skip = 1;
1309 break;
1310 }
1311 if (l < 1 || hlen - i < l) {
1312 invalopt:
1313 ipseclog((LOG_ERR,
1314 "ah4_calccksum: invalid IP option "
1315 "(type=%02x len=%02x)\n",
1316 p[i + IPOPT_OPTVAL],
1317 p[i + IPOPT_OLEN]));
1318 error = EINVAL;
1319 goto fail;
1320 }
1321 if (skip)
1322 bzero(p + i, l);
1323 if (p[i + IPOPT_OPTVAL] == IPOPT_EOL)
1324 break;
1325 i += l;
1326 }
1327 p = mtod(n, u_char *) + sizeof(struct ip);
1328 (algo->update)(&algos, p, hlen - sizeof(struct ip));
1329
1330 m_free(n);
1331 n = NULL;
1332 }
1333
1334 hdrtype = (iphdr.ip_p) & 0xff;
1335 advancewidth = hlen;
1336 break;
1337 }
1338
1339 case IPPROTO_AH:
1340 {
1341 struct ah ah;
1342 int siz;
1343 int hdrsiz;
1344 int totlen;
1345
1346 m_copydata(m, off, sizeof(ah), (caddr_t)&ah);
1347 hdrsiz = (sav->flags & SADB_X_EXT_OLD)
1348 ? sizeof(struct ah)
1349 : sizeof(struct newah);
1350 siz = (*algo->sumsiz)(sav);
1351 totlen = (ah.ah_len + 2) << 2;
1352
1353 /*
1354 * special treatment is necessary for the first one, not others
1355 */
1356 if (!ahseen) {
1357 if (totlen > m->m_pkthdr.len - off ||
1358 totlen > MCLBYTES) {
1359 error = EMSGSIZE;
1360 goto fail;
1361 }
1362 MGET(n, M_DONTWAIT, MT_DATA);
1363 if (n && totlen > MLEN) {
1364 MCLGET(n, M_DONTWAIT);
1365 if ((n->m_flags & M_EXT) == 0) {
1366 m_free(n);
1367 n = NULL;
1368 }
1369 }
1370 if (n == NULL) {
1371 error = ENOBUFS;
1372 goto fail;
1373 }
1374 m_copydata(m, off, totlen, mtod(n, caddr_t));
1375 n->m_len = totlen;
1376 bzero(mtod(n, caddr_t) + hdrsiz, siz);
1377 (algo->update)(&algos, mtod(n, caddr_t), n->m_len);
1378 m_free(n);
1379 n = NULL;
1380 } else
1381 ah_update_mbuf(m, off, totlen, algo, &algos);
1382 ahseen++;
1383
1384 hdrtype = ah.ah_nxt;
1385 advancewidth = totlen;
1386 break;
1387 }
1388
1389 default:
1390 ah_update_mbuf(m, off, m->m_pkthdr.len - off, algo, &algos);
1391 advancewidth = m->m_pkthdr.len - off;
1392 break;
1393 }
1394
1395 off += advancewidth;
1396 if (off < m->m_pkthdr.len)
1397 goto again;
1398
1399 if (len < (*algo->sumsiz)(sav)) {
1400 error = EINVAL;
1401 goto fail;
1402 }
1403
1404 (algo->result)(&algos, &sumbuf[0]);
1405 bcopy(&sumbuf[0], ahdat, (*algo->sumsiz)(sav));
1406
1407 if (n)
1408 m_free(n);
1409 return error;
1410
1411 fail:
1412 if (n)
1413 m_free(n);
1414 return error;
1415 }
1416 #endif
1417
1418 #ifdef INET6
1419 /*
1420 * Go generate the checksum. This function won't modify the mbuf chain
1421 * except AH itself.
1422 *
1423 * NOTE: the function does not free mbuf on failure.
1424 * Don't use m_copy(), it will try to share cluster mbuf by using refcnt.
1425 */
1426 int
1427 ah6_calccksum(m, ahdat, len, algo, sav)
1428 struct mbuf *m;
1429 caddr_t ahdat;
1430 size_t len;
1431 const struct ah_algorithm *algo;
1432 struct secasvar *sav;
1433 {
1434 int newoff, off;
1435 int proto, nxt;
1436 struct mbuf *n = NULL;
1437 int error;
1438 int ahseen;
1439 struct ah_algorithm_state algos;
1440 u_char sumbuf[AH_MAXSUMSIZE];
1441
1442 if ((m->m_flags & M_PKTHDR) == 0)
1443 return EINVAL;
1444
1445 error = (algo->init)(&algos, sav);
1446 if (error)
1447 return error;
1448
1449 off = 0;
1450 proto = IPPROTO_IPV6;
1451 nxt = -1;
1452 ahseen = 0;
1453
1454 again:
1455 newoff = ip6_nexthdr(m, off, proto, &nxt);
1456 if (newoff < 0)
1457 newoff = m->m_pkthdr.len;
1458 else if (newoff <= off) {
1459 error = EINVAL;
1460 goto fail;
1461 }
1462
1463 switch (proto) {
1464 case IPPROTO_IPV6:
1465 /*
1466 * special treatment is necessary for the first one, not others
1467 */
1468 if (off == 0) {
1469 struct ip6_hdr ip6copy;
1470
1471 if (newoff - off != sizeof(struct ip6_hdr)) {
1472 error = EINVAL;
1473 goto fail;
1474 }
1475
1476 m_copydata(m, off, newoff - off, (caddr_t)&ip6copy);
1477 /* RFC2402 */
1478 ip6copy.ip6_flow = 0;
1479 ip6copy.ip6_vfc &= ~IPV6_VERSION_MASK;
1480 ip6copy.ip6_vfc |= IPV6_VERSION;
1481 ip6copy.ip6_hlim = 0;
1482 if (IN6_IS_ADDR_LINKLOCAL(&ip6copy.ip6_src))
1483 ip6copy.ip6_src.s6_addr16[1] = 0x0000;
1484 if (IN6_IS_ADDR_LINKLOCAL(&ip6copy.ip6_dst))
1485 ip6copy.ip6_dst.s6_addr16[1] = 0x0000;
1486 (algo->update)(&algos, (caddr_t)&ip6copy,
1487 sizeof(struct ip6_hdr));
1488 } else {
1489 newoff = m->m_pkthdr.len;
1490 ah_update_mbuf(m, off, m->m_pkthdr.len - off, algo,
1491 &algos);
1492 }
1493 break;
1494
1495 case IPPROTO_AH:
1496 {
1497 int siz;
1498 int hdrsiz;
1499
1500 hdrsiz = (sav->flags & SADB_X_EXT_OLD)
1501 ? sizeof(struct ah)
1502 : sizeof(struct newah);
1503 siz = (*algo->sumsiz)(sav);
1504
1505 /*
1506 * special treatment is necessary for the first one, not others
1507 */
1508 if (!ahseen) {
1509 if (newoff - off > MCLBYTES) {
1510 error = EMSGSIZE;
1511 goto fail;
1512 }
1513 MGET(n, M_DONTWAIT, MT_DATA);
1514 if (n && newoff - off > MLEN) {
1515 MCLGET(n, M_DONTWAIT);
1516 if ((n->m_flags & M_EXT) == 0) {
1517 m_free(n);
1518 n = NULL;
1519 }
1520 }
1521 if (n == NULL) {
1522 error = ENOBUFS;
1523 goto fail;
1524 }
1525 m_copydata(m, off, newoff - off, mtod(n, caddr_t));
1526 n->m_len = newoff - off;
1527 bzero(mtod(n, caddr_t) + hdrsiz, siz);
1528 (algo->update)(&algos, mtod(n, caddr_t), n->m_len);
1529 m_free(n);
1530 n = NULL;
1531 } else
1532 ah_update_mbuf(m, off, newoff - off, algo, &algos);
1533 ahseen++;
1534 break;
1535 }
1536
1537 case IPPROTO_HOPOPTS:
1538 case IPPROTO_DSTOPTS:
1539 {
1540 struct ip6_ext *ip6e;
1541 int hdrlen, optlen;
1542 u_int8_t *p, *optend, *optp;
1543
1544 if (newoff - off > MCLBYTES) {
1545 error = EMSGSIZE;
1546 goto fail;
1547 }
1548 MGET(n, M_DONTWAIT, MT_DATA);
1549 if (n && newoff - off > MLEN) {
1550 MCLGET(n, M_DONTWAIT);
1551 if ((n->m_flags & M_EXT) == 0) {
1552 m_free(n);
1553 n = NULL;
1554 }
1555 }
1556 if (n == NULL) {
1557 error = ENOBUFS;
1558 goto fail;
1559 }
1560 m_copydata(m, off, newoff - off, mtod(n, caddr_t));
1561 n->m_len = newoff - off;
1562
1563 ip6e = mtod(n, struct ip6_ext *);
1564 hdrlen = (ip6e->ip6e_len + 1) << 3;
1565 if (newoff - off < hdrlen) {
1566 error = EINVAL;
1567 m_free(n);
1568 n = NULL;
1569 goto fail;
1570 }
1571 p = mtod(n, u_int8_t *);
1572 optend = p + hdrlen;
1573
1574 /*
1575 * ICV calculation for the options header including all
1576 * options. This part is a little tricky since there are
1577 * two type of options; mutable and immutable. We try to
1578 * null-out mutable ones here.
1579 */
1580 optp = p + 2;
1581 while (optp < optend) {
1582 if (optp[0] == IP6OPT_PAD1)
1583 optlen = 1;
1584 else {
1585 if (optp + 2 > optend) {
1586 error = EINVAL;
1587 m_free(n);
1588 n = NULL;
1589 goto fail;
1590 }
1591 optlen = optp[1] + 2;
1592
1593 if (optp[0] & IP6OPT_MUTABLE)
1594 bzero(optp + 2, optlen - 2);
1595 }
1596
1597 optp += optlen;
1598 }
1599
1600 (algo->update)(&algos, mtod(n, caddr_t), n->m_len);
1601 m_free(n);
1602 n = NULL;
1603 break;
1604 }
1605
1606 case IPPROTO_ROUTING:
1607 /*
1608 * For an input packet, we can just calculate `as is'.
1609 * For an output packet, we assume ip6_output have already
1610 * made packet how it will be received at the final
1611 * destination.
1612 */
1613 /* FALLTHROUGH */
1614
1615 default:
1616 ah_update_mbuf(m, off, newoff - off, algo, &algos);
1617 break;
1618 }
1619
1620 if (newoff < m->m_pkthdr.len) {
1621 proto = nxt;
1622 off = newoff;
1623 goto again;
1624 }
1625
1626 if (len < (*algo->sumsiz)(sav)) {
1627 error = EINVAL;
1628 goto fail;
1629 }
1630
1631 (algo->result)(&algos, &sumbuf[0]);
1632 bcopy(&sumbuf[0], ahdat, (*algo->sumsiz)(sav));
1633
1634 /* just in case */
1635 if (n)
1636 m_free(n);
1637 return 0;
1638 fail:
1639 /* just in case */
1640 if (n)
1641 m_free(n);
1642 return error;
1643 }
1644 #endif
Cache object: 55ab45f5838479e7b52253df69de3b09
|