1 /* $NetBSD: isakmp_agg.c,v 1.18 2025/03/07 15:55:29 christos Exp $ */
2
3 /* Id: isakmp_agg.c,v 1.28 2006/04/06 16:46:08 manubsd Exp */
4
5 /*
6 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
7 * All rights reserved.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions
11 * are met:
12 * 1. Redistributions of source code must retain the above copyright
13 * notice, this list of conditions and the following disclaimer.
14 * 2. Redistributions in binary form must reproduce the above copyright
15 * notice, this list of conditions and the following disclaimer in the
16 * documentation and/or other materials provided with the distribution.
17 * 3. Neither the name of the project nor the names of its contributors
18 * may be used to endorse or promote products derived from this software
19 * without specific prior written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
22 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
25 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31 * SUCH DAMAGE.
32 */
33
34 /* Aggressive Exchange (Aggressive Mode) */
35
36 #include "config.h"
37
38 #include <sys/types.h>
39 #include <sys/param.h>
40
41 #include <stdlib.h>
42 #include <stdio.h>
43 #include <string.h>
44 #include <errno.h>
45 #if TIME_WITH_SYS_TIME
46 # include <sys/time.h>
47 # include <time.h>
48 #else
49 # if HAVE_SYS_TIME_H
50 # include <sys/time.h>
51 # else
52 # include <time.h>
53 # endif
54 #endif
55
56 #include "var.h"
57 #include "misc.h"
58 #include "vmbuf.h"
59 #include "plog.h"
60 #include "sockmisc.h"
61 #include "schedule.h"
62 #include "debug.h"
63
64 #ifdef ENABLE_HYBRID
65 #include <resolv.h>
66 #endif
67
68 #include "localconf.h"
69 #include "remoteconf.h"
70 #include "isakmp_var.h"
71 #include "isakmp.h"
72 #include "evt.h"
73 #include "oakley.h"
74 #include "handler.h"
75 #include "ipsec_doi.h"
76 #include "crypto_openssl.h"
77 #include "pfkey.h"
78 #include "isakmp_agg.h"
79 #include "isakmp_inf.h"
80 #ifdef ENABLE_HYBRID
81 #include "isakmp_xauth.h"
82 #include "isakmp_cfg.h"
83 #endif
84 #ifdef ENABLE_FRAG
85 #include "isakmp_frag.h"
86 #endif
87 #include "vendorid.h"
88 #include "strnames.h"
89
90 #ifdef ENABLE_NATT
91 #include "nattraversal.h"
92 #endif
93
94 #ifdef HAVE_GSSAPI
95 #include "gssapi.h"
96 #endif
97
98 /*
99 * begin Aggressive Mode as initiator.
100 */
101 /*
102 * send to responder
103 * psk: HDR, SA, KE, Ni, IDi1
104 * sig: HDR, SA, KE, Ni, IDi1 [, CR ]
105 * gssapi: HDR, SA, KE, Ni, IDi1, GSSi
106 * rsa: HDR, SA, [ HASH(1),] KE, <IDi1_b>Pubkey_r, <Ni_b>Pubkey_r
107 * rev: HDR, SA, [ HASH(1),] <Ni_b>Pubkey_r, <KE_b>Ke_i,
108 * <IDii_b>Ke_i [, <Cert-I_b>Ke_i ]
109 */
110 int
agg_i1send(struct ph1handle * iph1,vchar_t * msg)111 agg_i1send(struct ph1handle *iph1, vchar_t *msg) /* must be null */
112 {
113 struct payload_list *plist = NULL;
114 int error = -1;
115 #ifdef ENABLE_NATT
116 vchar_t *vid_natt[MAX_NATT_VID_COUNT] = { NULL };
117 int i;
118 #endif
119 #ifdef ENABLE_HYBRID
120 vchar_t *vid_xauth = NULL;
121 vchar_t *vid_unity = NULL;
122 #endif
123 #ifdef ENABLE_FRAG
124 vchar_t *vid_frag = NULL;
125 #endif
126 #ifdef HAVE_GSSAPI
127 vchar_t *gsstoken = NULL;
128 int len;
129 #endif
130 #ifdef ENABLE_DPD
131 vchar_t *vid_dpd = NULL;
132 #endif
133
134 /* validity check */
135 if (msg != NULL) {
136 plog(LLV_ERROR, LOCATION, NULL,
137 "msg has to be NULL in this function.\n");
138 goto end;
139 }
140 if (iph1->status != PHASE1ST_START) {
141 plog(LLV_ERROR, LOCATION, NULL,
142 "status mismatched %d.\n", iph1->status);
143 goto end;
144 }
145
146 /* create isakmp index */
147 memset(&iph1->index, 0, sizeof(iph1->index));
148 isakmp_newcookie((caddr_t)&iph1->index, iph1->remote, iph1->local);
149
150 /* make ID payload into isakmp status */
151 if (ipsecdoi_setid1(iph1) < 0)
152 goto end;
153
154 /* create SA payload for my proposal */
155 iph1->sa = ipsecdoi_setph1proposal(iph1->rmconf, iph1->rmconf->proposal);
156 if (iph1->sa == NULL)
157 goto end;
158
159 /* consistency check of proposals */
160 if (iph1->rmconf->dhgrp == NULL) {
161 plog(LLV_ERROR, LOCATION, NULL,
162 "configuration failure about DH group.\n");
163 goto end;
164 }
165
166 /* generate DH public value */
167 if (oakley_dh_generate(iph1->rmconf->dhgrp,
168 &iph1->dhpub, &iph1->dhpriv) < 0)
169 goto end;
170
171 /* generate NONCE value */
172 iph1->nonce = eay_set_random(iph1->rmconf->nonce_size);
173 if (iph1->nonce == NULL)
174 goto end;
175
176 #ifdef ENABLE_HYBRID
177 /* Do we need Xauth VID? */
178 switch (iph1->rmconf->proposal->authmethod) {
179 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_PSKEY_I:
180 case OAKLEY_ATTR_AUTH_METHOD_HYBRID_RSA_I:
181 case OAKLEY_ATTR_AUTH_METHOD_HYBRID_DSS_I:
182 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSASIG_I:
183 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_DSSSIG_I:
184 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSAENC_I:
185 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSAREV_I:
186 if ((vid_xauth = set_vendorid(VENDORID_XAUTH)) == NULL)
187 plog(LLV_ERROR, LOCATION, NULL,
188 "Xauth vendor ID generation failed\n");
189 if ((vid_unity = set_vendorid(VENDORID_UNITY)) == NULL)
190 plog(LLV_ERROR, LOCATION, NULL,
191 "Unity vendor ID generation failed\n");
192 break;
193 default:
194 break;
195 }
196 #endif
197
198 #ifdef ENABLE_FRAG
199 if (iph1->rmconf->ike_frag) {
200 vid_frag = set_vendorid(VENDORID_FRAG);
201 if (vid_frag != NULL)
202 vid_frag = isakmp_frag_addcap(vid_frag,
203 VENDORID_FRAG_AGG);
204 if (vid_frag == NULL)
205 plog(LLV_ERROR, LOCATION, NULL,
206 "Frag vendorID construction failed\n");
207 }
208 #endif
209
210 plog(LLV_DEBUG, LOCATION, NULL, "authmethod is %s\n",
211 s_oakley_attr_method(iph1->rmconf->proposal->authmethod));
212 #ifdef HAVE_GSSAPI
213 if (iph1->rmconf->proposal->authmethod == OAKLEY_ATTR_AUTH_METHOD_GSSAPI_KRB)
214 gssapi_get_itoken(iph1, &len);
215 #endif
216
217 /* set SA payload to propose */
218 plist = isakmp_plist_append(plist, iph1->sa, ISAKMP_NPTYPE_SA);
219
220 /* create isakmp KE payload */
221 plist = isakmp_plist_append(plist, iph1->dhpub, ISAKMP_NPTYPE_KE);
222
223 /* create isakmp NONCE payload */
224 plist = isakmp_plist_append(plist, iph1->nonce, ISAKMP_NPTYPE_NONCE);
225
226 /* create isakmp ID payload */
227 plist = isakmp_plist_append(plist, iph1->id, ISAKMP_NPTYPE_ID);
228
229 #ifdef HAVE_GSSAPI
230 if (iph1->rmconf->proposal->authmethod == OAKLEY_ATTR_AUTH_METHOD_GSSAPI_KRB) {
231 if (gssapi_get_token_to_send(iph1, &gsstoken) < 0) {
232 plog(LLV_ERROR, LOCATION, NULL,
233 "Failed to get gssapi token.\n");
234 goto end;
235 }
236 plist = isakmp_plist_append(plist, gsstoken, ISAKMP_NPTYPE_GSS);
237 }
238 #endif
239 /* create isakmp CR payload */
240 if (oakley_needcr(iph1->rmconf->proposal->authmethod))
241 plist = oakley_append_cr(plist, iph1);
242
243 #ifdef ENABLE_FRAG
244 if (vid_frag)
245 plist = isakmp_plist_append(plist, vid_frag, ISAKMP_NPTYPE_VID);
246 #endif
247 #ifdef ENABLE_NATT
248 /*
249 * set VID payload for NAT-T if NAT-T
250 * support allowed in the config file
251 */
252 if (iph1->rmconf->nat_traversal)
253 plist = isakmp_plist_append_natt_vids(plist, vid_natt);
254 #endif
255 #ifdef ENABLE_HYBRID
256 if (vid_xauth)
257 plist = isakmp_plist_append(plist,
258 vid_xauth, ISAKMP_NPTYPE_VID);
259 if (vid_unity)
260 plist = isakmp_plist_append(plist,
261 vid_unity, ISAKMP_NPTYPE_VID);
262 #endif
263 #ifdef ENABLE_DPD
264 if(iph1->rmconf->dpd){
265 vid_dpd = set_vendorid(VENDORID_DPD);
266 if (vid_dpd != NULL)
267 plist = isakmp_plist_append(plist, vid_dpd, ISAKMP_NPTYPE_VID);
268 }
269 #endif
270
271 iph1->sendbuf = isakmp_plist_set_all (&plist, iph1);
272
273 #ifdef HAVE_PRINT_ISAKMP_C
274 isakmp_printpacket(iph1->sendbuf, iph1->local, iph1->remote, 0);
275 #endif
276
277 /* send the packet, add to the schedule to resend */
278 if (isakmp_ph1send(iph1) == -1)
279 goto end;
280
281 iph1->status = PHASE1ST_MSG1SENT;
282
283 error = 0;
284
285 end:
286 #ifdef HAVE_GSSAPI
287 if (gsstoken)
288 vfree(gsstoken);
289 #endif
290 #ifdef ENABLE_FRAG
291 if (vid_frag)
292 vfree(vid_frag);
293 #endif
294 #ifdef ENABLE_NATT
295 for (i = 0; i < MAX_NATT_VID_COUNT && vid_natt[i] != NULL; i++)
296 vfree(vid_natt[i]);
297 #endif
298 #ifdef ENABLE_HYBRID
299 if (vid_xauth != NULL)
300 vfree(vid_xauth);
301 if (vid_unity != NULL)
302 vfree(vid_unity);
303 #endif
304 #ifdef ENABLE_DPD
305 if (vid_dpd != NULL)
306 vfree(vid_dpd);
307 #endif
308
309 return error;
310 }
311
312 /*
313 * receive from responder
314 * psk: HDR, SA, KE, Nr, IDr1, HASH_R
315 * sig: HDR, SA, KE, Nr, IDr1, [ CR, ] [ CERT, ] SIG_R
316 * gssapi: HDR, SA, KE, Nr, IDr1, GSSr, HASH_R
317 * rsa: HDR, SA, KE, <IDr1_b>PubKey_i, <Nr_b>PubKey_i, HASH_R
318 * rev: HDR, SA, <Nr_b>PubKey_i, <KE_b>Ke_r, <IDir_b>Ke_r, HASH_R
319 */
320 int
agg_i2recv(struct ph1handle * iph1,vchar_t * msg)321 agg_i2recv(struct ph1handle *iph1, vchar_t *msg)
322 {
323 vchar_t *pbuf = NULL;
324 struct isakmp_parse_t *pa;
325 vchar_t *satmp = NULL;
326 int error = -1;
327 int ptype;
328 #ifdef HAVE_GSSAPI
329 vchar_t *gsstoken = NULL;
330 #endif
331
332 #ifdef ENABLE_NATT
333 int natd_seq = 0;
334 struct natd_payload {
335 int seq;
336 vchar_t *payload;
337 TAILQ_ENTRY(natd_payload) chain;
338 };
339 TAILQ_HEAD(_natd_payload, natd_payload) natd_tree;
340 TAILQ_INIT(&natd_tree);
341 #endif
342
343 /* validity check */
344 if (iph1->status != PHASE1ST_MSG1SENT) {
345 plog(LLV_ERROR, LOCATION, NULL,
346 "status mismatched %d.\n", iph1->status);
347 goto end;
348 }
349
350 /* validate the type of next payload */
351 pbuf = isakmp_parse(msg);
352 if (pbuf == NULL)
353 goto end;
354 pa = (struct isakmp_parse_t *)pbuf->v;
355
356 iph1->pl_hash = NULL;
357
358 /* SA payload is fixed postion */
359 if (pa->type != ISAKMP_NPTYPE_SA) {
360 plog(LLV_ERROR, LOCATION, iph1->remote,
361 "received invalid next payload type %d, "
362 "expecting %d.\n",
363 pa->type, ISAKMP_NPTYPE_SA);
364 goto end;
365 }
366
367 if (isakmp_p2ph(&satmp, pa->ptr) < 0)
368 goto end;
369 pa++;
370
371 for (/*nothing*/;
372 pa->type != ISAKMP_NPTYPE_NONE;
373 pa++) {
374
375 switch (pa->type) {
376 case ISAKMP_NPTYPE_KE:
377 if (isakmp_p2ph(&iph1->dhpub_p, pa->ptr) < 0)
378 goto end;
379 break;
380 case ISAKMP_NPTYPE_NONCE:
381 if (isakmp_p2ph(&iph1->nonce_p, pa->ptr) < 0)
382 goto end;
383 break;
384 case ISAKMP_NPTYPE_ID:
385 if (isakmp_p2ph(&iph1->id_p, pa->ptr) < 0)
386 goto end;
387 break;
388 case ISAKMP_NPTYPE_HASH:
389 iph1->pl_hash = (struct isakmp_pl_hash *)pa->ptr;
390 break;
391 case ISAKMP_NPTYPE_CR:
392 if (oakley_savecr(iph1, pa->ptr) < 0)
393 goto end;
394 break;
395 case ISAKMP_NPTYPE_CERT:
396 if (oakley_savecert(iph1, pa->ptr) < 0)
397 goto end;
398 break;
399 case ISAKMP_NPTYPE_SIG:
400 if (isakmp_p2ph(&iph1->sig_p, pa->ptr) < 0)
401 goto end;
402 break;
403 case ISAKMP_NPTYPE_VID:
404 handle_vendorid(iph1, pa->ptr);
405 break;
406 case ISAKMP_NPTYPE_N:
407 isakmp_log_notify(iph1,
408 (struct isakmp_pl_n *) pa->ptr,
409 "aggressive exchange");
410 break;
411 #ifdef HAVE_GSSAPI
412 case ISAKMP_NPTYPE_GSS:
413 if (isakmp_p2ph(&gsstoken, pa->ptr) < 0)
414 goto end;
415 gssapi_save_received_token(iph1, gsstoken);
416 break;
417 #endif
418
419 #ifdef ENABLE_NATT
420 case ISAKMP_NPTYPE_NATD_DRAFT:
421 case ISAKMP_NPTYPE_NATD_RFC:
422 if (NATT_AVAILABLE(iph1) && iph1->natt_options != NULL &&
423 pa->type == iph1->natt_options->payload_nat_d) {
424 struct natd_payload *natd;
425 natd = (struct natd_payload *)racoon_malloc(sizeof(*natd));
426 if (!natd)
427 goto end;
428
429 natd->payload = NULL;
430
431 if (isakmp_p2ph (&natd->payload, pa->ptr) < 0)
432 goto end;
433
434 natd->seq = natd_seq++;
435
436 TAILQ_INSERT_TAIL(&natd_tree, natd, chain);
437 break;
438 }
439 /* passthrough to default... */
440 #endif
441 /*FALLTHROUGH*/
442 default:
443 /* don't send information, see isakmp_ident_r1() */
444 plog(LLV_ERROR, LOCATION, iph1->remote,
445 "ignore the packet, "
446 "received unexpecting payload type %d.\n",
447 pa->type);
448 goto end;
449 }
450 }
451
452 /* payload existency check */
453 if (iph1->dhpub_p == NULL || iph1->nonce_p == NULL) {
454 plog(LLV_ERROR, LOCATION, iph1->remote,
455 "few isakmp message received.\n");
456 goto end;
457 }
458
459 /* verify identifier */
460 if (ipsecdoi_checkid1(iph1) != 0) {
461 plog(LLV_ERROR, LOCATION, iph1->remote,
462 "invalid ID payload.\n");
463 goto end;
464 }
465
466 /* check SA payload and set approval SA for use */
467 if (ipsecdoi_checkph1proposal(satmp, iph1) < 0) {
468 plog(LLV_ERROR, LOCATION, iph1->remote,
469 "failed to get valid proposal.\n");
470 /* XXX send information */
471 goto end;
472 }
473 VPTRINIT(iph1->sa_ret);
474
475 /* fix isakmp index */
476 memcpy(&iph1->index.r_ck, &((struct isakmp *)msg->v)->r_ck,
477 sizeof(cookie_t));
478
479 #ifdef ENABLE_NATT
480 if (NATT_AVAILABLE(iph1)) {
481 struct natd_payload *natd = NULL;
482 int natd_verified;
483
484 plog(LLV_INFO, LOCATION, iph1->remote,
485 "Selected NAT-T version: %s\n",
486 vid_string_by_id(iph1->natt_options->version));
487
488 /* set both bits first so that we can clear them
489 upon verifying hashes */
490 iph1->natt_flags |= NAT_DETECTED;
491
492 while ((natd = TAILQ_FIRST(&natd_tree)) != NULL) {
493 /* this function will clear appropriate bits bits
494 from iph1->natt_flags */
495 natd_verified = natt_compare_addr_hash (iph1,
496 natd->payload, natd->seq);
497
498 plog (LLV_INFO, LOCATION, NULL, "NAT-D payload #%d %s\n",
499 natd->seq - 1,
500 natd_verified ? "verified" : "doesn't match");
501
502 vfree (natd->payload);
503
504 TAILQ_REMOVE(&natd_tree, natd, chain);
505 racoon_free (natd);
506 }
507
508 plog (LLV_INFO, LOCATION, NULL, "NAT %s %s%s\n",
509 iph1->natt_flags & NAT_DETECTED ?
510 "detected:" : "not detected",
511 iph1->natt_flags & NAT_DETECTED_ME ? "ME " : "",
512 iph1->natt_flags & NAT_DETECTED_PEER ? "PEER" : "");
513
514 if (iph1->natt_flags & NAT_DETECTED)
515 natt_float_ports (iph1);
516 }
517 #endif
518
519 /* compute sharing secret of DH */
520 if (oakley_dh_compute(iph1->rmconf->dhgrp, iph1->dhpub,
521 iph1->dhpriv, iph1->dhpub_p, &iph1->dhgxy) < 0)
522 goto end;
523
524 /* generate SKEYIDs & IV & final cipher key */
525 if (oakley_skeyid(iph1) < 0)
526 goto end;
527 if (oakley_skeyid_dae(iph1) < 0)
528 goto end;
529 if (oakley_compute_enckey(iph1) < 0)
530 goto end;
531 if (oakley_newiv(iph1) < 0)
532 goto end;
533
534 /* validate authentication value */
535 ptype = oakley_validate_auth(iph1);
536 if (ptype != 0) {
537 if (ptype == -1) {
538 /* message printed inner oakley_validate_auth() */
539 goto end;
540 }
541 evt_phase1(iph1, EVT_PHASE1_AUTH_FAILED, NULL);
542 isakmp_info_send_n1(iph1, ptype, NULL);
543 goto end;
544 }
545
546 if (oakley_checkcr(iph1) < 0) {
547 /* Ignore this error in order to be interoperability. */
548 ;
549 }
550
551 /* change status of isakmp status entry */
552 iph1->status = PHASE1ST_MSG2RECEIVED;
553
554 error = 0;
555
556 end:
557 #ifdef HAVE_GSSAPI
558 if (gsstoken)
559 vfree(gsstoken);
560 #endif
561 if (pbuf)
562 vfree(pbuf);
563 if (satmp)
564 vfree(satmp);
565 if (error) {
566 VPTRINIT(iph1->dhpub_p);
567 VPTRINIT(iph1->nonce_p);
568 VPTRINIT(iph1->id_p);
569 VPTRINIT(iph1->cert_p);
570 VPTRINIT(iph1->crl_p);
571 VPTRINIT(iph1->sig_p);
572 VPTRINIT(iph1->cr_p);
573 }
574
575 return error;
576 }
577
578 /*
579 * send to responder
580 * psk: HDR, HASH_I
581 * gssapi: HDR, HASH_I
582 * sig: HDR, [ CERT, ] SIG_I
583 * rsa: HDR, HASH_I
584 * rev: HDR, HASH_I
585 */
586 int
agg_i2send(struct ph1handle * iph1,vchar_t * msg)587 agg_i2send(struct ph1handle *iph1, vchar_t *msg)
588 {
589 struct payload_list *plist = NULL;
590 int need_cert = 0;
591 int error = -1;
592 vchar_t *gsshash = NULL;
593
594 /* validity check */
595 if (iph1->status != PHASE1ST_MSG2RECEIVED) {
596 plog(LLV_ERROR, LOCATION, NULL,
597 "status mismatched %d.\n", iph1->status);
598 goto end;
599 }
600
601 /* generate HASH to send */
602 plog(LLV_DEBUG, LOCATION, NULL, "generate HASH_I\n");
603 iph1->hash = oakley_ph1hash_common(iph1, GENERATE);
604 if (iph1->hash == NULL) {
605 #ifdef HAVE_GSSAPI
606 if (gssapi_more_tokens(iph1) &&
607 #ifdef ENABLE_HYBRID
608 !iph1->rmconf->xauth &&
609 #endif
610 1)
611 isakmp_info_send_n1(iph1,
612 ISAKMP_NTYPE_INVALID_EXCHANGE_TYPE, NULL);
613 #endif
614 goto end;
615 }
616
617 switch (iph1->approval->authmethod) {
618 case OAKLEY_ATTR_AUTH_METHOD_PSKEY:
619 #ifdef ENABLE_HYBRID
620 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_PSKEY_I:
621 case OAKLEY_ATTR_AUTH_METHOD_HYBRID_RSA_I:
622 case OAKLEY_ATTR_AUTH_METHOD_HYBRID_DSS_I:
623 #endif
624 /* set HASH payload */
625 plist = isakmp_plist_append(plist,
626 iph1->hash, ISAKMP_NPTYPE_HASH);
627 break;
628
629 case OAKLEY_ATTR_AUTH_METHOD_DSSSIG:
630 case OAKLEY_ATTR_AUTH_METHOD_RSASIG:
631 #ifdef ENABLE_HYBRID
632 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSASIG_I:
633 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_DSSSIG_I:
634 #endif
635 /* XXX if there is CR or not ? */
636
637 if (oakley_getmycert(iph1) < 0)
638 goto end;
639
640 if (oakley_getsign(iph1) < 0)
641 goto end;
642
643 if (iph1->cert != NULL && iph1->rmconf->send_cert)
644 need_cert = 1;
645
646 /* add CERT payload if there */
647 if (need_cert)
648 plist = isakmp_plist_append(plist, iph1->cert,
649 ISAKMP_NPTYPE_CERT);
650
651 /* add SIG payload */
652 plist = isakmp_plist_append(plist,
653 iph1->sig, ISAKMP_NPTYPE_SIG);
654 break;
655
656 case OAKLEY_ATTR_AUTH_METHOD_RSAENC:
657 case OAKLEY_ATTR_AUTH_METHOD_RSAREV:
658 #ifdef ENABLE_HYBRID
659 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSAENC_I:
660 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSAREV_I:
661 #endif
662 break;
663 #ifdef HAVE_GSSAPI
664 case OAKLEY_ATTR_AUTH_METHOD_GSSAPI_KRB:
665 gsshash = gssapi_wraphash(iph1);
666 if (gsshash == NULL) {
667 plog(LLV_ERROR, LOCATION, NULL,
668 "failed to wrap hash\n");
669 isakmp_info_send_n1(iph1,
670 ISAKMP_NTYPE_INVALID_EXCHANGE_TYPE, NULL);
671 goto end;
672 }
673
674 plist = isakmp_plist_append(plist,
675 gsshash, ISAKMP_NPTYPE_HASH);
676 break;
677 #endif
678 }
679
680 #ifdef ENABLE_NATT
681 /* generate NAT-D payloads */
682 if (NATT_AVAILABLE(iph1)) {
683 vchar_t *natd[2] = { NULL, NULL };
684
685 plog(LLV_INFO, LOCATION,
686 NULL, "Adding remote and local NAT-D payloads.\n");
687
688 if ((natd[0] = natt_hash_addr (iph1, iph1->remote)) == NULL) {
689 plog(LLV_ERROR, LOCATION, NULL,
690 "NAT-D hashing failed for %s\n",
691 saddr2str(iph1->remote));
692 goto end;
693 }
694
695 if ((natd[1] = natt_hash_addr (iph1, iph1->local)) == NULL) {
696 plog(LLV_ERROR, LOCATION, NULL,
697 "NAT-D hashing failed for %s\n",
698 saddr2str(iph1->local));
699 goto end;
700 }
701
702 plist = isakmp_plist_append(plist,
703 natd[0], iph1->natt_options->payload_nat_d);
704 plist = isakmp_plist_append(plist,
705 natd[1], iph1->natt_options->payload_nat_d);
706 }
707 #endif
708
709 iph1->sendbuf = isakmp_plist_set_all (&plist, iph1);
710
711 #ifdef HAVE_PRINT_ISAKMP_C
712 isakmp_printpacket(iph1->sendbuf, iph1->local, iph1->remote, 0);
713 #endif
714
715 /* send to responder */
716 if (isakmp_send(iph1, iph1->sendbuf) < 0)
717 goto end;
718
719 /* the sending message is added to the received-list. */
720 if (add_recvdpkt(iph1->remote, iph1->local, iph1->sendbuf, msg) == -1) {
721 plog(LLV_ERROR , LOCATION, NULL,
722 "failed to add a response packet to the tree.\n");
723 goto end;
724 }
725
726 /* set encryption flag */
727 iph1->flags |= ISAKMP_FLAG_E;
728
729 iph1->status = PHASE1ST_ESTABLISHED;
730
731 error = 0;
732
733 end:
734 if (gsshash)
735 vfree(gsshash);
736 return error;
737 }
738
739 /*
740 * receive from initiator
741 * psk: HDR, SA, KE, Ni, IDi1
742 * sig: HDR, SA, KE, Ni, IDi1 [, CR ]
743 * gssapi: HDR, SA, KE, Ni, IDi1 , GSSi
744 * rsa: HDR, SA, [ HASH(1),] KE, <IDi1_b>Pubkey_r, <Ni_b>Pubkey_r
745 * rev: HDR, SA, [ HASH(1),] <Ni_b>Pubkey_r, <KE_b>Ke_i,
746 * <IDii_b>Ke_i [, <Cert-I_b>Ke_i ]
747 */
748 int
agg_r1recv(struct ph1handle * iph1,vchar_t * msg)749 agg_r1recv(struct ph1handle *iph1, vchar_t *msg)
750 {
751 int error = -1;
752 vchar_t *pbuf = NULL;
753 struct isakmp_parse_t *pa;
754 int vid_numeric;
755 #ifdef HAVE_GSSAPI
756 vchar_t *gsstoken = NULL;
757 #endif
758
759 /* validity check */
760 if (iph1->status != PHASE1ST_START) {
761 plog(LLV_ERROR, LOCATION, NULL,
762 "status mismatched %d.\n", iph1->status);
763 goto end;
764 }
765
766 /* validate the type of next payload */
767 pbuf = isakmp_parse(msg);
768 if (pbuf == NULL)
769 goto end;
770 pa = (struct isakmp_parse_t *)pbuf->v;
771
772 /* SA payload is fixed postion */
773 if (pa->type != ISAKMP_NPTYPE_SA) {
774 plog(LLV_ERROR, LOCATION, iph1->remote,
775 "received invalid next payload type %d, "
776 "expecting %d.\n",
777 pa->type, ISAKMP_NPTYPE_SA);
778 goto end;
779 }
780 if (isakmp_p2ph(&iph1->sa, pa->ptr) < 0)
781 goto end;
782 pa++;
783
784 for (/*nothing*/;
785 pa->type != ISAKMP_NPTYPE_NONE;
786 pa++) {
787
788 plog(LLV_DEBUG, LOCATION, NULL,
789 "received payload of type %s\n",
790 s_isakmp_nptype(pa->type));
791
792 switch (pa->type) {
793 case ISAKMP_NPTYPE_KE:
794 if (isakmp_p2ph(&iph1->dhpub_p, pa->ptr) < 0)
795 goto end;
796 break;
797 case ISAKMP_NPTYPE_NONCE:
798 if (isakmp_p2ph(&iph1->nonce_p, pa->ptr) < 0)
799 goto end;
800 break;
801 case ISAKMP_NPTYPE_ID:
802 if (isakmp_p2ph(&iph1->id_p, pa->ptr) < 0)
803 goto end;
804 break;
805 case ISAKMP_NPTYPE_VID:
806 vid_numeric = handle_vendorid(iph1, pa->ptr);
807 #ifdef ENABLE_FRAG
808 if ((vid_numeric == VENDORID_FRAG) &&
809 (vendorid_frag_cap(pa->ptr) & VENDORID_FRAG_AGG))
810 iph1->frag = 1;
811 #endif
812 break;
813
814 case ISAKMP_NPTYPE_CR:
815 if (oakley_savecr(iph1, pa->ptr) < 0)
816 goto end;
817 break;
818
819 #ifdef HAVE_GSSAPI
820 case ISAKMP_NPTYPE_GSS:
821 if (isakmp_p2ph(&gsstoken, pa->ptr) < 0)
822 goto end;
823 gssapi_save_received_token(iph1, gsstoken);
824 break;
825 #endif
826 default:
827 /* don't send information, see isakmp_ident_r1() */
828 plog(LLV_ERROR, LOCATION, iph1->remote,
829 "ignore the packet, "
830 "received unexpecting payload type %d.\n",
831 pa->type);
832 goto end;
833 }
834 }
835
836 /* payload existency check */
837 if (iph1->dhpub_p == NULL || iph1->nonce_p == NULL) {
838 plog(LLV_ERROR, LOCATION, iph1->remote,
839 "few isakmp message received.\n");
840 goto end;
841 }
842
843 /* verify identifier */
844 if (ipsecdoi_checkid1(iph1) != 0) {
845 plog(LLV_ERROR, LOCATION, iph1->remote,
846 "invalid ID payload.\n");
847 goto end;
848 }
849
850 #ifdef ENABLE_NATT
851 if (NATT_AVAILABLE(iph1))
852 plog(LLV_INFO, LOCATION, iph1->remote,
853 "Selected NAT-T version: %s\n",
854 vid_string_by_id(iph1->natt_options->version));
855 #endif
856
857 /* check SA payload and set approval SA for use */
858 if (ipsecdoi_checkph1proposal(iph1->sa, iph1) < 0) {
859 plog(LLV_ERROR, LOCATION, iph1->remote,
860 "failed to get valid proposal.\n");
861 /* XXX send information */
862 goto end;
863 }
864
865 if (oakley_checkcr(iph1) < 0) {
866 /* Ignore this error in order to be interoperability. */
867 ;
868 }
869
870 iph1->status = PHASE1ST_MSG1RECEIVED;
871
872 error = 0;
873
874 end:
875 #ifdef HAVE_GSSAPI
876 if (gsstoken)
877 vfree(gsstoken);
878 #endif
879 if (pbuf)
880 vfree(pbuf);
881 if (error) {
882 VPTRINIT(iph1->sa);
883 VPTRINIT(iph1->dhpub_p);
884 VPTRINIT(iph1->nonce_p);
885 VPTRINIT(iph1->id_p);
886 VPTRINIT(iph1->cr_p);
887 }
888
889 return error;
890 }
891
892 /*
893 * send to initiator
894 * psk: HDR, SA, KE, Nr, IDr1, HASH_R
895 * sig: HDR, SA, KE, Nr, IDr1, [ CR, ] [ CERT, ] SIG_R
896 * gssapi: HDR, SA, KE, Nr, IDr1, GSSr, HASH_R
897 * rsa: HDR, SA, KE, <IDr1_b>PubKey_i, <Nr_b>PubKey_i, HASH_R
898 * rev: HDR, SA, <Nr_b>PubKey_i, <KE_b>Ke_r, <IDir_b>Ke_r, HASH_R
899 */
900 int
agg_r1send(struct ph1handle * iph1,vchar_t * msg)901 agg_r1send(struct ph1handle *iph1, vchar_t *msg)
902 {
903 struct payload_list *plist = NULL;
904 int need_cert = 0;
905 int error = -1;
906 #ifdef ENABLE_HYBRID
907 vchar_t *xauth_vid = NULL;
908 vchar_t *unity_vid = NULL;
909 #endif
910 #ifdef ENABLE_NATT
911 vchar_t *vid_natt = NULL;
912 vchar_t *natd[2] = { NULL, NULL };
913 #endif
914 #ifdef ENABLE_DPD
915 vchar_t *vid_dpd = NULL;
916 #endif
917 #ifdef ENABLE_FRAG
918 vchar_t *vid_frag = NULL;
919 #endif
920
921 #ifdef HAVE_GSSAPI
922 int gsslen;
923 vchar_t *gsstoken = NULL, *gsshash = NULL;
924 vchar_t *gss_sa = NULL;
925 int free_gss_sa = 0;
926 #endif
927
928 /* validity check */
929 if (iph1->status != PHASE1ST_MSG1RECEIVED) {
930 plog(LLV_ERROR, LOCATION, NULL,
931 "status mismatched %d.\n", iph1->status);
932 goto end;
933 }
934
935 /* set responder's cookie */
936 isakmp_newcookie((caddr_t)&iph1->index.r_ck, iph1->remote, iph1->local);
937
938 /* make ID payload into isakmp status */
939 if (ipsecdoi_setid1(iph1) < 0)
940 goto end;
941
942 /* generate DH public value */
943 if (oakley_dh_generate(iph1->rmconf->dhgrp,
944 &iph1->dhpub, &iph1->dhpriv) < 0)
945 goto end;
946
947 /* generate NONCE value */
948 iph1->nonce = eay_set_random(iph1->rmconf->nonce_size);
949 if (iph1->nonce == NULL)
950 goto end;
951
952 /* compute sharing secret of DH */
953 if (oakley_dh_compute(iph1->approval->dhgrp, iph1->dhpub,
954 iph1->dhpriv, iph1->dhpub_p, &iph1->dhgxy) < 0)
955 goto end;
956
957 /* generate SKEYIDs & IV & final cipher key */
958 if (oakley_skeyid(iph1) < 0)
959 goto end;
960 if (oakley_skeyid_dae(iph1) < 0)
961 goto end;
962 if (oakley_compute_enckey(iph1) < 0)
963 goto end;
964 if (oakley_newiv(iph1) < 0)
965 goto end;
966
967 #ifdef HAVE_GSSAPI
968 if (iph1->rmconf->proposal->authmethod == OAKLEY_ATTR_AUTH_METHOD_GSSAPI_KRB)
969 gssapi_get_rtoken(iph1, &gsslen);
970 #endif
971
972 /* generate HASH to send */
973 plog(LLV_DEBUG, LOCATION, NULL, "generate HASH_R\n");
974 iph1->hash = oakley_ph1hash_common(iph1, GENERATE);
975 if (iph1->hash == NULL) {
976 #ifdef HAVE_GSSAPI
977 if (gssapi_more_tokens(iph1))
978 isakmp_info_send_n1(iph1,
979 ISAKMP_NTYPE_INVALID_EXCHANGE_TYPE, NULL);
980 #endif
981 goto end;
982 }
983
984 #ifdef ENABLE_NATT
985 /* Has the peer announced NAT-T? */
986 if (NATT_AVAILABLE(iph1)) {
987 /* set chosen VID */
988 vid_natt = set_vendorid(iph1->natt_options->version);
989
990 /* generate NAT-D payloads */
991 plog (LLV_INFO, LOCATION, NULL, "Adding remote and local NAT-D payloads.\n");
992 if ((natd[0] = natt_hash_addr (iph1, iph1->remote)) == NULL) {
993 plog(LLV_ERROR, LOCATION, NULL,
994 "NAT-D hashing failed for %s\n", saddr2str(iph1->remote));
995 goto end;
996 }
997
998 if ((natd[1] = natt_hash_addr (iph1, iph1->local)) == NULL) {
999 plog(LLV_ERROR, LOCATION, NULL,
1000 "NAT-D hashing failed for %s\n", saddr2str(iph1->local));
1001 goto end;
1002 }
1003 }
1004 #endif
1005 #ifdef ENABLE_DPD
1006 /* Only send DPD support if remote announced DPD and if DPD support is active */
1007 if (iph1->dpd_support && iph1->rmconf->dpd)
1008 vid_dpd = set_vendorid(VENDORID_DPD);
1009 #endif
1010 #ifdef ENABLE_FRAG
1011 if (iph1->frag) {
1012 vid_frag = set_vendorid(VENDORID_FRAG);
1013 if (vid_frag != NULL)
1014 vid_frag = isakmp_frag_addcap(vid_frag,
1015 VENDORID_FRAG_AGG);
1016 if (vid_frag == NULL)
1017 plog(LLV_ERROR, LOCATION, NULL,
1018 "Frag vendorID construction failed\n");
1019 }
1020 #endif
1021
1022 switch (iph1->approval->authmethod) {
1023 case OAKLEY_ATTR_AUTH_METHOD_PSKEY:
1024 #ifdef ENABLE_HYBRID
1025 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_PSKEY_R:
1026 #endif
1027 /* set SA payload to reply */
1028 plist = isakmp_plist_append(plist,
1029 iph1->sa_ret, ISAKMP_NPTYPE_SA);
1030
1031 /* create isakmp KE payload */
1032 plist = isakmp_plist_append(plist,
1033 iph1->dhpub, ISAKMP_NPTYPE_KE);
1034
1035 /* create isakmp NONCE payload */
1036 plist = isakmp_plist_append(plist,
1037 iph1->nonce, ISAKMP_NPTYPE_NONCE);
1038
1039 /* create isakmp ID payload */
1040 plist = isakmp_plist_append(plist,
1041 iph1->id, ISAKMP_NPTYPE_ID);
1042
1043 /* create isakmp HASH payload */
1044 plist = isakmp_plist_append(plist,
1045 iph1->hash, ISAKMP_NPTYPE_HASH);
1046
1047 /* create isakmp CR payload if needed */
1048 if (oakley_needcr(iph1->approval->authmethod))
1049 plist = oakley_append_cr(plist, iph1);
1050 break;
1051 case OAKLEY_ATTR_AUTH_METHOD_DSSSIG:
1052 case OAKLEY_ATTR_AUTH_METHOD_RSASIG:
1053 #ifdef ENABLE_HYBRID
1054 case OAKLEY_ATTR_AUTH_METHOD_HYBRID_RSA_R:
1055 case OAKLEY_ATTR_AUTH_METHOD_HYBRID_DSS_R:
1056 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSASIG_R:
1057 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_DSSSIG_R:
1058 #endif
1059 /* XXX if there is CR or not ? */
1060
1061 if (oakley_getmycert(iph1) < 0)
1062 goto end;
1063
1064 if (oakley_getsign(iph1) < 0)
1065 goto end;
1066
1067 if (iph1->cert != NULL && iph1->rmconf->send_cert)
1068 need_cert = 1;
1069
1070 /* set SA payload to reply */
1071 plist = isakmp_plist_append(plist,
1072 iph1->sa_ret, ISAKMP_NPTYPE_SA);
1073
1074 /* create isakmp KE payload */
1075 plist = isakmp_plist_append(plist,
1076 iph1->dhpub, ISAKMP_NPTYPE_KE);
1077
1078 /* create isakmp NONCE payload */
1079 plist = isakmp_plist_append(plist,
1080 iph1->nonce, ISAKMP_NPTYPE_NONCE);
1081
1082 /* add ID payload */
1083 plist = isakmp_plist_append(plist,
1084 iph1->id, ISAKMP_NPTYPE_ID);
1085
1086 /* add CERT payload if there */
1087 if (need_cert)
1088 plist = isakmp_plist_append(plist, iph1->cert,
1089 ISAKMP_NPTYPE_CERT);
1090
1091 /* add SIG payload */
1092 plist = isakmp_plist_append(plist,
1093 iph1->sig, ISAKMP_NPTYPE_SIG);
1094
1095 /* create isakmp CR payload if needed */
1096 if (oakley_needcr(iph1->approval->authmethod))
1097 plist = oakley_append_cr(plist, iph1);
1098 break;
1099
1100 case OAKLEY_ATTR_AUTH_METHOD_RSAENC:
1101 case OAKLEY_ATTR_AUTH_METHOD_RSAREV:
1102 #ifdef ENABLE_HYBRID
1103 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSAENC_R:
1104 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSAREV_R:
1105 #endif
1106 break;
1107 #ifdef HAVE_GSSAPI
1108 case OAKLEY_ATTR_AUTH_METHOD_GSSAPI_KRB:
1109 /* create buffer to send isakmp payload */
1110 gsshash = gssapi_wraphash(iph1);
1111 if (gsshash == NULL) {
1112 plog(LLV_ERROR, LOCATION, NULL,
1113 "failed to wrap hash\n");
1114 /*
1115 * This is probably due to the GSS
1116 * roundtrips not being finished yet.
1117 * Return this error in the hope that
1118 * a fallback to main mode will be done.
1119 */
1120 isakmp_info_send_n1(iph1,
1121 ISAKMP_NTYPE_INVALID_EXCHANGE_TYPE, NULL);
1122 goto end;
1123 }
1124 if (iph1->approval->gssid != NULL)
1125 gss_sa = ipsecdoi_setph1proposal(iph1->rmconf,
1126 iph1->approval);
1127 else
1128 gss_sa = iph1->sa_ret;
1129
1130 if (gss_sa != iph1->sa_ret)
1131 free_gss_sa = 1;
1132
1133 /* set SA payload to reply */
1134 plist = isakmp_plist_append(plist,
1135 gss_sa, ISAKMP_NPTYPE_SA);
1136
1137 /* create isakmp KE payload */
1138 plist = isakmp_plist_append(plist,
1139 iph1->dhpub, ISAKMP_NPTYPE_KE);
1140
1141 /* create isakmp NONCE payload */
1142 plist = isakmp_plist_append(plist,
1143 iph1->nonce, ISAKMP_NPTYPE_NONCE);
1144
1145 /* create isakmp ID payload */
1146 plist = isakmp_plist_append(plist,
1147 iph1->id, ISAKMP_NPTYPE_ID);
1148
1149 /* create GSS payload */
1150 if (gssapi_get_token_to_send(iph1, &gsstoken) < 0) {
1151 plog(LLV_ERROR, LOCATION, NULL,
1152 "Failed to get gssapi token.\n");
1153 goto end;
1154 }
1155 plist = isakmp_plist_append(plist,
1156 gsstoken, ISAKMP_NPTYPE_GSS);
1157
1158 /* create isakmp HASH payload */
1159 plist = isakmp_plist_append(plist,
1160 gsshash, ISAKMP_NPTYPE_HASH);
1161
1162 /* append vendor id, if needed */
1163 break;
1164 #endif
1165 }
1166
1167 #ifdef ENABLE_HYBRID
1168 if (iph1->mode_cfg->flags & ISAKMP_CFG_VENDORID_XAUTH) {
1169 plog (LLV_INFO, LOCATION, NULL, "Adding xauth VID payload.\n");
1170 if ((xauth_vid = set_vendorid(VENDORID_XAUTH)) == NULL) {
1171 plog(LLV_ERROR, LOCATION, NULL,
1172 "Cannot create Xauth vendor ID\n");
1173 goto end;
1174 }
1175 plist = isakmp_plist_append(plist,
1176 xauth_vid, ISAKMP_NPTYPE_VID);
1177 }
1178
1179 if (iph1->mode_cfg->flags & ISAKMP_CFG_VENDORID_UNITY) {
1180 if ((unity_vid = set_vendorid(VENDORID_UNITY)) == NULL) {
1181 plog(LLV_ERROR, LOCATION, NULL,
1182 "Cannot create Unity vendor ID\n");
1183 goto end;
1184 }
1185 plist = isakmp_plist_append(plist,
1186 unity_vid, ISAKMP_NPTYPE_VID);
1187 }
1188 #endif
1189
1190 #ifdef ENABLE_NATT
1191 /* append NAT-T payloads */
1192 if (vid_natt) {
1193 /* chosen VID */
1194 plist = isakmp_plist_append(plist, vid_natt, ISAKMP_NPTYPE_VID);
1195 /* NAT-D */
1196 plist = isakmp_plist_append(plist, natd[0], iph1->natt_options->payload_nat_d);
1197 plist = isakmp_plist_append(plist, natd[1], iph1->natt_options->payload_nat_d);
1198 }
1199 #endif
1200
1201 #ifdef ENABLE_FRAG
1202 if (vid_frag)
1203 plist = isakmp_plist_append(plist, vid_frag, ISAKMP_NPTYPE_VID);
1204 #endif
1205
1206 #ifdef ENABLE_DPD
1207 if (vid_dpd)
1208 plist = isakmp_plist_append(plist, vid_dpd, ISAKMP_NPTYPE_VID);
1209 #endif
1210
1211 iph1->sendbuf = isakmp_plist_set_all (&plist, iph1);
1212
1213 #ifdef HAVE_PRINT_ISAKMP_C
1214 isakmp_printpacket(iph1->sendbuf, iph1->local, iph1->remote, 1);
1215 #endif
1216
1217 /* send the packet, add to the schedule to resend */
1218 if (isakmp_ph1send(iph1) == -1)
1219 goto end;
1220
1221 /* the sending message is added to the received-list. */
1222 if (add_recvdpkt(iph1->remote, iph1->local, iph1->sendbuf, msg) == -1) {
1223 plog(LLV_ERROR , LOCATION, NULL,
1224 "failed to add a response packet to the tree.\n");
1225 goto end;
1226 }
1227
1228 iph1->status = PHASE1ST_MSG1SENT;
1229
1230 error = 0;
1231
1232 end:
1233 #ifdef ENABLE_HYBRID
1234 if (xauth_vid)
1235 vfree(xauth_vid);
1236 if (unity_vid)
1237 vfree(unity_vid);
1238 #endif
1239 #ifdef HAVE_GSSAPI
1240 if (gsstoken)
1241 vfree(gsstoken);
1242 if (gsshash)
1243 vfree(gsshash);
1244 if (free_gss_sa)
1245 vfree(gss_sa);
1246 #endif
1247 #ifdef ENABLE_DPD
1248 if (vid_dpd)
1249 vfree(vid_dpd);
1250 #endif
1251 #ifdef ENABLE_FRAG
1252 if (vid_frag)
1253 vfree(vid_frag);
1254 #endif
1255
1256 return error;
1257 }
1258
1259 /*
1260 * receive from initiator
1261 * psk: HDR, HASH_I
1262 * gssapi: HDR, HASH_I
1263 * sig: HDR, [ CERT, ] SIG_I
1264 * rsa: HDR, HASH_I
1265 * rev: HDR, HASH_I
1266 */
1267 int
agg_r2recv(struct ph1handle * iph1,vchar_t * msg0)1268 agg_r2recv(struct ph1handle *iph1, vchar_t *msg0)
1269 {
1270 vchar_t *msg = NULL;
1271 vchar_t *pbuf = NULL;
1272 struct isakmp_parse_t *pa;
1273 int error = -1, ptype;
1274 #ifdef ENABLE_NATT
1275 int natd_seq = 0;
1276 #endif
1277
1278 /* validity check */
1279 if (iph1->status != PHASE1ST_MSG1SENT) {
1280 plog(LLV_ERROR, LOCATION, NULL,
1281 "status mismatched %d.\n", iph1->status);
1282 goto end;
1283 }
1284
1285 /* decrypting if need. */
1286 /* XXX configurable ? */
1287 if (ISSET(((struct isakmp *)msg0->v)->flags, ISAKMP_FLAG_E)) {
1288 msg = oakley_do_decrypt(iph1, msg0,
1289 iph1->ivm->iv, iph1->ivm->ive);
1290 if (msg == NULL)
1291 goto end;
1292 } else
1293 msg = vdup(msg0);
1294
1295 /* validate the type of next payload */
1296 pbuf = isakmp_parse(msg);
1297 if (pbuf == NULL)
1298 goto end;
1299
1300 iph1->pl_hash = NULL;
1301
1302 for (pa = (struct isakmp_parse_t *)pbuf->v;
1303 pa->type != ISAKMP_NPTYPE_NONE;
1304 pa++) {
1305
1306 switch (pa->type) {
1307 case ISAKMP_NPTYPE_HASH:
1308 iph1->pl_hash = (struct isakmp_pl_hash *)pa->ptr;
1309 break;
1310 case ISAKMP_NPTYPE_VID:
1311 handle_vendorid(iph1, pa->ptr);
1312 break;
1313 case ISAKMP_NPTYPE_CERT:
1314 if (oakley_savecert(iph1, pa->ptr) < 0)
1315 goto end;
1316 break;
1317 case ISAKMP_NPTYPE_SIG:
1318 if (isakmp_p2ph(&iph1->sig_p, pa->ptr) < 0)
1319 goto end;
1320 break;
1321 case ISAKMP_NPTYPE_N:
1322 isakmp_log_notify(iph1,
1323 (struct isakmp_pl_n *) pa->ptr,
1324 "aggressive exchange");
1325 break;
1326
1327 #ifdef ENABLE_NATT
1328 case ISAKMP_NPTYPE_NATD_DRAFT:
1329 case ISAKMP_NPTYPE_NATD_RFC:
1330 if (NATT_AVAILABLE(iph1) && iph1->natt_options != NULL &&
1331 pa->type == iph1->natt_options->payload_nat_d)
1332 {
1333 vchar_t *natd_received = NULL;
1334 int natd_verified;
1335
1336 if (isakmp_p2ph (&natd_received, pa->ptr) < 0)
1337 goto end;
1338
1339 if (natd_seq == 0)
1340 iph1->natt_flags |= NAT_DETECTED;
1341
1342 natd_verified = natt_compare_addr_hash (iph1,
1343 natd_received, natd_seq++);
1344
1345 plog (LLV_INFO, LOCATION, NULL, "NAT-D payload #%d %s\n",
1346 natd_seq - 1,
1347 natd_verified ? "verified" : "doesn't match");
1348
1349 vfree (natd_received);
1350 break;
1351 }
1352 /* passthrough to default... */
1353 #endif
1354 /*FALLTHROUGH*/
1355 default:
1356 /* don't send information, see isakmp_ident_r1() */
1357 plog(LLV_ERROR, LOCATION, iph1->remote,
1358 "ignore the packet, "
1359 "received unexpecting payload type %d.\n",
1360 pa->type);
1361 goto end;
1362 }
1363 }
1364
1365 #ifdef ENABLE_NATT
1366 if (NATT_AVAILABLE(iph1))
1367 plog (LLV_INFO, LOCATION, NULL, "NAT %s %s%s\n",
1368 iph1->natt_flags & NAT_DETECTED ?
1369 "detected:" : "not detected",
1370 iph1->natt_flags & NAT_DETECTED_ME ? "ME " : "",
1371 iph1->natt_flags & NAT_DETECTED_PEER ? "PEER" : "");
1372 #endif
1373
1374 /* validate authentication value */
1375 ptype = oakley_validate_auth(iph1);
1376 if (ptype != 0) {
1377 if (ptype == -1) {
1378 /* message printed inner oakley_validate_auth() */
1379 goto end;
1380 }
1381 evt_phase1(iph1, EVT_PHASE1_AUTH_FAILED, NULL);
1382 isakmp_info_send_n1(iph1, ptype, NULL);
1383 goto end;
1384 }
1385
1386 iph1->status = PHASE1ST_MSG2RECEIVED;
1387
1388 error = 0;
1389
1390 end:
1391 if (pbuf)
1392 vfree(pbuf);
1393 if (msg)
1394 vfree(msg);
1395 if (error) {
1396 VPTRINIT(iph1->cert_p);
1397 VPTRINIT(iph1->crl_p);
1398 VPTRINIT(iph1->sig_p);
1399 }
1400
1401 return error;
1402 }
1403
1404 /*
1405 * status update and establish isakmp sa.
1406 */
1407 int
agg_r2send(struct ph1handle * iph1,vchar_t * msg)1408 agg_r2send(struct ph1handle *iph1, vchar_t *msg)
1409 {
1410 int error = -1;
1411
1412 /* validity check */
1413 if (iph1->status != PHASE1ST_MSG2RECEIVED) {
1414 plog(LLV_ERROR, LOCATION, NULL,
1415 "status mismatched %d.\n", iph1->status);
1416 goto end;
1417 }
1418
1419 /* IV synchronized when packet encrypted. */
1420 /* see handler.h about IV synchronization. */
1421 if (ISSET(((struct isakmp *)msg->v)->flags, ISAKMP_FLAG_E))
1422 memcpy(iph1->ivm->iv->v, iph1->ivm->ive->v, iph1->ivm->iv->l);
1423
1424 /* set encryption flag */
1425 iph1->flags |= ISAKMP_FLAG_E;
1426
1427 iph1->status = PHASE1ST_ESTABLISHED;
1428
1429 error = 0;
1430
1431 end:
1432 return error;
1433 }
1434