]> git.saurik.com Git - apple/ipsec.git/blob - ipsec-tools/racoon/isakmp_xauth.c
ipsec-332.100.1.tar.gz
[apple/ipsec.git] / ipsec-tools / racoon / isakmp_xauth.c
1 /* $NetBSD: isakmp_xauth.c,v 1.11.6.1 2007/08/07 04:49:24 manu Exp $ */
2
3 /* Id: isakmp_xauth.c,v 1.38 2006/08/22 18:17:17 manubsd Exp */
4
5 /*
6 * Copyright (C) 2004-2005 Emmanuel Dreyfus
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 #include "config.h"
35
36 #include <sys/types.h>
37 #include <sys/param.h>
38 #include <sys/socket.h>
39 #include <sys/queue.h>
40
41 #include <netinet/in.h>
42
43 #include <stdlib.h>
44 #include <stdio.h>
45 #include <string.h>
46 #include <errno.h>
47 #include <pwd.h>
48 #include <grp.h>
49 #if TIME_WITH_SYS_TIME
50 # include <sys/time.h>
51 # include <time.h>
52 #else
53 # if HAVE_SYS_TIME_H
54 # include <sys/time.h>
55 # else
56 # include <time.h>
57 # endif
58 #endif
59 #include <netdb.h>
60 #ifdef HAVE_UNISTD_H
61 #include <unistd.h>
62 #endif
63 #include <ctype.h>
64
65 #ifdef HAVE_SHADOW_H
66 #include <shadow.h>
67 #endif
68
69 #include "var.h"
70 #include "misc.h"
71 #include "vmbuf.h"
72 #include "plog.h"
73 #include "sockmisc.h"
74 #include "schedule.h"
75 #include "debug.h"
76 #include "fsm.h"
77
78 #include "crypto_openssl.h"
79 #include "isakmp_var.h"
80 #include "isakmp.h"
81 #include "handler.h"
82 #include "throttle.h"
83 #include "remoteconf.h"
84 #include "isakmp_inf.h"
85 #include "isakmp_xauth.h"
86 #include "isakmp_unity.h"
87 #include "isakmp_cfg.h"
88 #include "strnames.h"
89 #include "ipsec_doi.h"
90 #include "remoteconf.h"
91 #include "localconf.h"
92 #include "vpn_control.h"
93 #include "vpn_control_var.h"
94
95 void
96 xauth_sendreq(iph1)
97 phase1_handle_t *iph1;
98 {
99 vchar_t *buffer;
100 struct isakmp_pl_attr *attr;
101 struct isakmp_data *typeattr;
102 struct isakmp_data *usrattr;
103 struct isakmp_data *pwdattr;
104 struct xauth_state *xst = &iph1->mode_cfg->xauth;
105 size_t tlen;
106
107 /* Status checks */
108 if (!FSM_STATE_IS_ESTABLISHED(iph1->status)) {
109 plog(ASL_LEVEL_ERR,
110 "Xauth request while phase 1 is not completed\n");
111 return;
112 }
113
114 if (xst->status != XAUTHST_NOTYET) {
115 plog(ASL_LEVEL_ERR,
116 "Xauth request whith Xauth state %d\n", xst->status);
117 return;
118 }
119
120 plog(ASL_LEVEL_NOTICE, "Sending Xauth request\n");
121
122 tlen = sizeof(*attr) +
123 + sizeof(*typeattr) +
124 + sizeof(*usrattr) +
125 + sizeof(*pwdattr);
126
127 if ((buffer = vmalloc(tlen)) == NULL) {
128 plog(ASL_LEVEL_ERR, "Cannot allocate buffer\n");
129 return;
130 }
131
132 attr = (struct isakmp_pl_attr *)buffer->v;
133 memset(attr, 0, tlen);
134
135 attr->h.len = htons(tlen);
136 attr->type = ISAKMP_CFG_REQUEST;
137 attr->id = htons(eay_random());
138
139 typeattr = (struct isakmp_data *)(attr + 1);
140 typeattr->type = htons(XAUTH_TYPE | ISAKMP_GEN_TV);
141 typeattr->lorv = htons(XAUTH_TYPE_GENERIC);
142
143 usrattr = (struct isakmp_data *)(typeattr + 1);
144 usrattr->type = htons(XAUTH_USER_NAME | ISAKMP_GEN_TLV);
145 usrattr->lorv = htons(0);
146
147 pwdattr = (struct isakmp_data *)(usrattr + 1);
148 pwdattr->type = htons(XAUTH_USER_PASSWORD | ISAKMP_GEN_TLV);
149 pwdattr->lorv = htons(0);
150
151 isakmp_cfg_send(iph1, buffer,
152 ISAKMP_NPTYPE_ATTR, ISAKMP_FLAG_E, 1, 0, NULL);
153
154 vfree(buffer);
155
156 xst->status = XAUTHST_REQSENT;
157
158 return;
159 }
160
161 int
162 xauth_attr_reply(iph1, attr, id)
163 phase1_handle_t *iph1;
164 struct isakmp_data *attr;
165 int id;
166 {
167 char **outlet = NULL;
168 size_t alen = 0;
169 int type;
170 struct xauth_state *xst = &iph1->mode_cfg->xauth;
171
172 if ((iph1->mode_cfg->flags & ISAKMP_CFG_VENDORID_XAUTH) == 0) {
173 plog(ASL_LEVEL_ERR,
174 "Xauth reply but peer did not declare "
175 "itself as Xauth capable\n");
176 return -1;
177 }
178
179 if (xst->status != XAUTHST_REQSENT) {
180 plog(ASL_LEVEL_ERR,
181 "Xauth reply while Xauth state is %d\n", xst->status);
182 return -1;
183 }
184
185 type = ntohs(attr->type) & ~ISAKMP_GEN_MASK;
186 switch (type) {
187 case XAUTH_TYPE:
188 switch (ntohs(attr->lorv)) {
189 case XAUTH_TYPE_GENERIC:
190 xst->authtype = XAUTH_TYPE_GENERIC;
191 break;
192 default:
193 plog(ASL_LEVEL_WARNING,
194 "Unexpected authentication type %d\n",
195 ntohs(type));
196 return -1;
197 }
198 break;
199
200 case XAUTH_USER_NAME:
201 outlet = &xst->authdata.generic.usr;
202 break;
203
204 case XAUTH_USER_PASSWORD:
205 outlet = &xst->authdata.generic.pwd;
206 break;
207
208 default:
209 plog(ASL_LEVEL_WARNING,
210 "ignored Xauth attribute %d\n", type);
211 break;
212 }
213
214 if (outlet != NULL) {
215 alen = ntohs(attr->lorv);
216
217 if ((*outlet = racoon_realloc(*outlet, alen + 1)) == NULL) {
218 plog(ASL_LEVEL_ERR,
219 "Cannot allocate memory for Xauth Data\n");
220 return -1;
221 }
222
223 memcpy(*outlet, attr + 1, alen);
224 (*outlet)[alen] = '\0';
225 outlet = NULL;
226 }
227
228
229 if ((xst->authdata.generic.usr != NULL) &&
230 (xst->authdata.generic.pwd != NULL)) {
231 int port;
232 int res;
233 char *usr = xst->authdata.generic.usr;
234 char *pwd = xst->authdata.generic.pwd;
235 time_t throttle_delay = 0;
236
237 #if 0 /* Real debug, don't do that at home */
238 plog(ASL_LEVEL_DEBUG,
239 "Got username \"%s\", password \"%s\"\n", usr, pwd);
240 #endif
241 strlcpy(iph1->mode_cfg->login, usr, sizeof(iph1->mode_cfg->login));
242
243 res = -1;
244 if ((port = isakmp_cfg_getport(iph1)) == -1) {
245 plog(ASL_LEVEL_ERR,
246 "Port pool depleted\n");
247 goto skip_auth;
248 }
249
250 switch (isakmp_cfg_config.authsource) {
251 case ISAKMP_CFG_AUTH_SYSTEM:
252 res = xauth_login_system(usr, pwd);
253 break;
254
255 default:
256 plog(ASL_LEVEL_ERR,
257 "Unexpected authentication source\n");
258 res = -1;
259 break;
260 }
261
262 /*
263 * Optional group authentication
264 */
265 if (!res && (isakmp_cfg_config.groupcount))
266 res = group_check(iph1,
267 isakmp_cfg_config.grouplist,
268 isakmp_cfg_config.groupcount);
269
270 /*
271 * On failure, throttle the connexion for the remote host
272 * in order to make password attacks more difficult.
273 */
274 throttle_delay = throttle_host(iph1->remote, res) - time(NULL);
275 if (throttle_delay > 0) {
276 char *str;
277
278 str = saddrwop2str((struct sockaddr *)iph1->remote);
279
280 plog(ASL_LEVEL_ERR,
281 "Throttling in action for %s: delay %lds\n",
282 str, (unsigned long)throttle_delay);
283 res = -1;
284 } else {
285 throttle_delay = 0;
286 }
287
288 skip_auth:
289 if (throttle_delay != 0) {
290 struct xauth_reply_arg *xra;
291
292 if ((xra = racoon_malloc(sizeof(*xra))) == NULL) {
293 plog(ASL_LEVEL_ERR,
294 "malloc failed, bypass throttling\n");
295 return xauth_reply(iph1, port, id, res);
296 }
297
298 /*
299 * We need to store the ph1, but it might have
300 * disapeared when xauth_reply is called, so
301 * store the index instead.
302 */
303 xra->index = iph1->index;
304 xra->port = port;
305 xra->id = id;
306 xra->res = res;
307 sched_new(throttle_delay, xauth_reply_stub, xra);
308 } else {
309 return xauth_reply(iph1, port, id, res);
310 }
311 }
312
313 return 0;
314 }
315
316 void
317 xauth_reply_stub(args)
318 void *args;
319 {
320 struct xauth_reply_arg *xra = (struct xauth_reply_arg *)args;
321 phase1_handle_t *iph1;
322
323 if ((iph1 = ike_session_getph1byindex(NULL, &xra->index)) != NULL)
324 (void)xauth_reply(iph1, xra->port, xra->id, xra->res);
325 else
326 plog(ASL_LEVEL_ERR,
327 "Delayed Xauth reply: phase 1 no longer exists.\n");
328
329 racoon_free(xra);
330 return;
331 }
332
333 int
334 xauth_reply(iph1, port, id, res)
335 phase1_handle_t *iph1;
336 int port;
337 int id;
338 {
339 struct xauth_state *xst = &iph1->mode_cfg->xauth;
340 char *usr = xst->authdata.generic.usr;
341
342 if (iph1->is_dying) {
343 plog(ASL_LEVEL_NOTICE,
344 "dropped login for user \"%s\"\n", usr);
345 return -1;
346 }
347
348 if (res != 0) {
349 if (port != -1)
350 isakmp_cfg_putport(iph1, port);
351
352 plog(ASL_LEVEL_NOTICE,
353 "login failed for user \"%s\"\n", usr);
354
355 xauth_sendstatus(iph1, XAUTH_STATUS_FAIL, id);
356 xst->status = XAUTHST_NOTYET;
357
358 /* Delete Phase 1 SA */
359 if (FSM_STATE_IS_ESTABLISHED(iph1->status))
360 isakmp_info_send_d1(iph1);
361 isakmp_ph1expire(iph1);
362
363 return -1;
364 }
365
366 xst->status = XAUTHST_OK;
367 plog(ASL_LEVEL_NOTICE,
368 "login succeeded for user \"%s\"\n", usr);
369
370 xauth_sendstatus(iph1, XAUTH_STATUS_OK, id);
371
372 return 0;
373 }
374
375 void
376 xauth_sendstatus(iph1, status, id)
377 phase1_handle_t *iph1;
378 int status;
379 int id;
380 {
381 vchar_t *buffer;
382 struct isakmp_pl_attr *attr;
383 struct isakmp_data *stattr;
384 size_t tlen;
385
386 tlen = sizeof(*attr) +
387 + sizeof(*stattr);
388
389 if ((buffer = vmalloc(tlen)) == NULL) {
390 plog(ASL_LEVEL_ERR, "Cannot allocate buffer\n");
391 return;
392 }
393
394 attr = (struct isakmp_pl_attr *)buffer->v;
395 memset(attr, 0, tlen);
396
397 attr->h.len = htons(tlen);
398 attr->type = ISAKMP_CFG_SET;
399 attr->id = htons(id);
400
401 stattr = (struct isakmp_data *)(attr + 1);
402 stattr->type = htons(XAUTH_STATUS | ISAKMP_GEN_TV);
403 stattr->lorv = htons(status);
404
405 isakmp_cfg_send(iph1, buffer,
406 ISAKMP_NPTYPE_ATTR, ISAKMP_FLAG_E, 1, 0, NULL);
407
408 vfree(buffer);
409
410 return;
411 }
412
413
414 int
415 xauth_login_system(usr, pwd)
416 char *usr;
417 char *pwd;
418 {
419 struct passwd *pw;
420 char *cryptpwd;
421 char *syscryptpwd;
422 #ifdef HAVE_SHADOW_H
423 struct spwd *spw;
424
425 if ((spw = getspnam(usr)) == NULL)
426 return -1;
427
428 syscryptpwd = spw->sp_pwdp;
429 #endif
430
431 if ((pw = getpwnam(usr)) == NULL)
432 return -1;
433
434 #ifndef HAVE_SHADOW_H
435 syscryptpwd = pw->pw_passwd;
436 #endif
437
438 /* No root login. Ever. */
439 if (pw->pw_uid == 0)
440 return -1;
441
442 if ((cryptpwd = crypt(pwd, syscryptpwd)) == NULL)
443 return -1;
444
445 if (strcmp(cryptpwd, syscryptpwd) == 0)
446 return 0;
447
448 return -1;
449 }
450
451 int
452 xauth_group_system(usr, grp)
453 char * usr;
454 char * grp;
455 {
456 struct group * gr;
457 char * member;
458 int index = 0;
459
460 gr = getgrnam(grp);
461 if (gr == NULL) {
462 plog(ASL_LEVEL_ERR,
463 "the system group name \'%s\' is unknown\n",
464 grp);
465 return -1;
466 }
467
468 while ((member = gr->gr_mem[index++])!=NULL) {
469 if (!strcmp(member,usr)) {
470 plog(ASL_LEVEL_NOTICE,
471 "membership validated\n");
472 return 0;
473 }
474 }
475
476 return -1;
477 }
478
479 int
480 xauth_check(iph1)
481 phase1_handle_t *iph1;
482 {
483 struct xauth_state *xst = &iph1->mode_cfg->xauth;
484
485 /*
486 * Only the server side (edge device) really check for Xauth
487 * status. It does it if the chose authmethod is using Xauth.
488 * On the client side (roadwarrior), we don't check anything.
489 */
490 switch (AUTHMETHOD(iph1)) {
491 case OAKLEY_ATTR_AUTH_METHOD_HYBRID_RSA_R:
492 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSASIG_R:
493 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_PSKEY_R:
494 /* The following are not yet implemented */
495 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSAENC_R:
496 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSAREV_R:
497 if ((iph1->mode_cfg->flags & ISAKMP_CFG_VENDORID_XAUTH) == 0) {
498 plog(ASL_LEVEL_ERR,
499 "Hybrid auth negotiated but peer did not "
500 "announced as Xauth capable\n");
501 return -1;
502 }
503
504 if (xst->status != XAUTHST_OK) {
505 plog(ASL_LEVEL_ERR,
506 "Hybrid auth negotiated but peer did not "
507 "succeed Xauth exchange\n");
508 return -1;
509 }
510
511 return 0;
512 break;
513 default:
514 return 0;
515 break;
516 }
517
518 return 0;
519 }
520
521 int
522 group_check(iph1, grp_list, grp_count)
523 phase1_handle_t *iph1;
524 char **grp_list;
525 int grp_count;
526 {
527 int res = -1;
528 int grp_index = 0;
529 char * usr = NULL;
530
531 /* check for presence of modecfg data */
532
533 if(iph1->mode_cfg == NULL) {
534 plog(ASL_LEVEL_ERR,
535 "xauth group specified but modecfg not found\n");
536 return res;
537 }
538
539 /* loop through our group list */
540
541 for(; grp_index < grp_count; grp_index++) {
542
543 /* check for presence of xauth data */
544
545 usr = iph1->mode_cfg->xauth.authdata.generic.usr;
546
547 if(usr == NULL) {
548 plog(ASL_LEVEL_ERR,
549 "xauth group specified but xauth not found\n");
550 return res;
551 }
552
553 /* call appropriate group validation funtion */
554
555 switch (isakmp_cfg_config.groupsource) {
556
557 case ISAKMP_CFG_GROUP_SYSTEM:
558 res = xauth_group_system(
559 usr,
560 grp_list[grp_index]);
561 break;
562
563 default:
564 /* we should never get here */
565 plog(ASL_LEVEL_ERR,
566 "Unknown group auth source\n");
567 break;
568 }
569
570 if( !res ) {
571 plog(ASL_LEVEL_NOTICE,
572 "user \"%s\" is a member of group \"%s\"\n",
573 usr,
574 grp_list[grp_index]);
575 break;
576 } else {
577 plog(ASL_LEVEL_NOTICE,
578 "user \"%s\" is not a member of group \"%s\"\n",
579 usr,
580 grp_list[grp_index]);
581 }
582 }
583
584 return res;
585 }
586
587 vchar_t *
588 isakmp_xauth_req(iph1, attr)
589 phase1_handle_t *iph1;
590 struct isakmp_data *attr;
591 {
592 int type;
593 size_t dlen = 0;
594 int ashort = 0;
595 int value = 0;
596 vchar_t *buffer = NULL;
597 char* mraw = NULL;
598 vchar_t *mdata = NULL;
599 char *data;
600 vchar_t *usr = NULL;
601 vchar_t *pwd = NULL;
602 size_t skip = 0;
603 int freepwd = 0;
604
605 if ((iph1->mode_cfg->flags & ISAKMP_CFG_VENDORID_XAUTH) == 0) {
606 plog(ASL_LEVEL_ERR,
607 "Xauth mode config request but peer "
608 "did not declare itself as Xauth capable\n");
609 return NULL;
610 }
611
612 type = ntohs(attr->type) & ~ISAKMP_GEN_MASK;
613
614 /* Sanity checks */
615 switch(type) {
616 case XAUTH_TYPE:
617 if ((ntohs(attr->type) & ISAKMP_GEN_TV) == 0) {
618 plog(ASL_LEVEL_ERR,
619 "Unexpected long XAUTH_TYPE attribute\n");
620 return NULL;
621 }
622 if (ntohs(attr->lorv) != XAUTH_TYPE_GENERIC) {
623 plog(ASL_LEVEL_ERR,
624 "Unsupported Xauth authentication %d\n",
625 ntohs(attr->lorv));
626 return NULL;
627 }
628 ashort = 1;
629 dlen = 0;
630 value = XAUTH_TYPE_GENERIC;
631 break;
632
633 case XAUTH_USER_NAME:
634 if (!iph1->rmconf->xauth || !iph1->rmconf->xauth->login) {
635 plog(ASL_LEVEL_ERR, "Xauth performed "
636 "with no login supplied\n");
637 return NULL;
638 }
639
640 dlen = iph1->rmconf->xauth->login->l - 1;
641 iph1->rmconf->xauth->state |= XAUTH_SENT_USERNAME;
642 break;
643
644 case XAUTH_USER_PASSWORD:
645 case XAUTH_PASSCODE:
646 if (!iph1->rmconf->xauth || !iph1->rmconf->xauth->login)
647 return NULL;
648
649 skip = sizeof(struct ipsecdoi_id_b);
650 usr = vmalloc(iph1->rmconf->xauth->login->l - 1 + skip);
651 if (usr == NULL) {
652 plog(ASL_LEVEL_ERR,
653 "Cannot allocate memory\n");
654 return NULL;
655 }
656 memset(usr->v, 0, skip);
657 memcpy(usr->v + skip,
658 iph1->rmconf->xauth->login->v,
659 iph1->rmconf->xauth->login->l - 1);
660
661 if (iph1->rmconf->xauth->pass) {
662 /* A key given through racoonctl */
663 pwd = iph1->rmconf->xauth->pass;
664 } else {
665 if ((pwd = getpskbyname(usr)) == NULL) {
666 plog(ASL_LEVEL_ERR,
667 "No password was found for login %s\n",
668 iph1->rmconf->xauth->login->v);
669 vfree(usr);
670 return NULL;
671 }
672 /* We have to free it before returning */
673 freepwd = 1;
674 }
675 vfree(usr);
676
677 iph1->rmconf->xauth->state |= XAUTH_SENT_PASSWORD;
678 dlen = pwd->l - 1;
679
680 break;
681
682 case XAUTH_MESSAGE:
683 if ((ntohs(attr->type) & ISAKMP_GEN_TV) == 0) {
684 dlen = ntohs(attr->lorv);
685 if (dlen > 0) {
686 mraw = (char*)(attr + 1);
687 if ((mdata = vmalloc(dlen)) == NULL) {
688 plog(ASL_LEVEL_ERR,
689 "Cannot allocate memory\n");
690 return NULL;
691 }
692 memcpy(mdata->v, mraw, mdata->l);
693 plog(ASL_LEVEL_NOTICE, "XAUTH Message: '%s'.\n",
694 binsanitize(mdata->v, mdata->l));
695 vfree(mdata);
696 }
697 }
698 return NULL;
699 default:
700 plog(ASL_LEVEL_WARNING,
701 "Ignored attribute %s\n", s_isakmp_cfg_type(type));
702 return NULL;
703 break;
704 }
705
706 if ((buffer = vmalloc(sizeof(*attr) + dlen)) == NULL) {
707 plog(ASL_LEVEL_ERR,
708 "Cannot allocate memory\n");
709 goto out;
710 }
711
712 attr = (struct isakmp_data *)buffer->v;
713 if (ashort) {
714 attr->type = htons(type | ISAKMP_GEN_TV);
715 attr->lorv = htons(value);
716 goto out;
717 }
718
719 attr->type = htons(type | ISAKMP_GEN_TLV);
720 attr->lorv = htons(dlen);
721 data = (char *)(attr + 1);
722
723 switch(type) {
724 case XAUTH_USER_NAME:
725 /*
726 * iph1->rmconf->xauth->login->v is valid,
727 * we just checked it in the previous switch case
728 */
729 memcpy(data, iph1->rmconf->xauth->login->v, dlen);
730 break;
731 case XAUTH_USER_PASSWORD:
732 case XAUTH_PASSCODE:
733 memcpy(data, pwd->v, dlen);
734 break;
735 default:
736 break;
737 }
738
739 out:
740 if (freepwd)
741 vfree(pwd);
742
743 return buffer;
744 }
745
746 vchar_t *
747 isakmp_xauth_set(iph1, attr)
748 phase1_handle_t *iph1;
749 struct isakmp_data *attr;
750 {
751 int type;
752 vchar_t *buffer = NULL;
753 struct xauth_state *xst;
754 size_t dlen = 0;
755 char* mraw = NULL;
756 vchar_t *mdata = NULL;
757
758 if ((iph1->mode_cfg->flags & ISAKMP_CFG_VENDORID_XAUTH) == 0) {
759 plog(ASL_LEVEL_ERR,
760 "Xauth mode config set but peer "
761 "did not declare itself as Xauth capable\n");
762 return NULL;
763 }
764
765 type = ntohs(attr->type) & ~ISAKMP_GEN_MASK;
766
767 switch(type) {
768 case XAUTH_STATUS:
769 /*
770 * We should only receive ISAKMP mode_cfg SET XAUTH_STATUS
771 * when running as a client (initiator).
772 */
773 xst = &iph1->mode_cfg->xauth;
774 switch(AUTHMETHOD(iph1)) {
775 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_PSKEY_R:
776 if (!iph1->is_rekey) {
777 plog(ASL_LEVEL_ERR,
778 "Unexpected XAUTH_STATUS_OK... not a Phase 1 rekey\n");
779 return NULL;
780 }
781 case OAKLEY_ATTR_AUTH_METHOD_HYBRID_RSA_I:
782 case FICTIVE_AUTH_METHOD_XAUTH_PSKEY_I:
783 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSASIG_I:
784 /* Not implemented ... */
785 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSAENC_I:
786 case OAKLEY_ATTR_AUTH_METHOD_XAUTH_RSAREV_I:
787 break;
788 default:
789 plog(ASL_LEVEL_ERR,
790 "Unexpected XAUTH_STATUS_OK\n");
791 return NULL;
792 break;
793 }
794
795 /* If we got a failure, delete iph1 */
796 if (ntohs(attr->lorv) != XAUTH_STATUS_OK) {
797 plog(ASL_LEVEL_ERR,
798 "Xauth authentication failed\n");
799
800 vpncontrol_notify_ike_failed(VPNCTL_NTYPE_AUTHENTICATION_FAILED, FROM_LOCAL,
801 iph1_get_remote_v4_address(iph1), 0, NULL);
802
803 iph1->mode_cfg->flags |= ISAKMP_CFG_DELETE_PH1;
804
805 IPSECLOGASLMSG("IPSec Extended Authentication Failed.\n");
806 } else {
807 if (iph1->is_rekey) {
808 xst->status = XAUTHST_OK;
809 }
810
811 IPSECLOGASLMSG("IPSec Extended Authentication Passed.\n");
812 }
813
814
815 /* We acknowledge it */
816 break;
817 case XAUTH_MESSAGE:
818 if ((ntohs(attr->type) & ISAKMP_GEN_TV) == 0) {
819 dlen = ntohs(attr->lorv);
820 if (dlen > 0) {
821 mraw = (char*)(attr + 1);
822 if ((mdata = vmalloc(dlen)) == NULL) {
823 plog(ASL_LEVEL_ERR,
824 "Cannot allocate memory\n");
825 return NULL;
826 }
827 memcpy(mdata->v, mraw, mdata->l);
828 plog(ASL_LEVEL_NOTICE, "XAUTH Message: '%s'.\n",
829 binsanitize(mdata->v, mdata->l));
830 vfree(mdata);
831 }
832 }
833
834 default:
835 plog(ASL_LEVEL_WARNING,
836 "Ignored attribute %s\n", s_isakmp_cfg_type(type));
837 return NULL;
838 break;
839 }
840
841 if ((buffer = vmalloc(sizeof(*attr))) == NULL) {
842 plog(ASL_LEVEL_ERR,
843 "Cannot allocate memory\n");
844 return NULL;
845 }
846
847 attr = (struct isakmp_data *)buffer->v;
848 attr->type = htons(type | ISAKMP_GEN_TV);
849 attr->lorv = htons(0);
850
851 return buffer;
852 }
853
854
855 void
856 xauth_rmstate(xst)
857 struct xauth_state *xst;
858 {
859 switch (xst->authtype) {
860 case XAUTH_TYPE_GENERIC:
861 if (xst->authdata.generic.usr)
862 racoon_free(xst->authdata.generic.usr);
863
864 if (xst->authdata.generic.pwd)
865 racoon_free(xst->authdata.generic.pwd);
866
867 break;
868
869 case XAUTH_TYPE_CHAP:
870 case XAUTH_TYPE_OTP:
871 case XAUTH_TYPE_SKEY:
872 plog(ASL_LEVEL_WARNING,
873 "Unsupported authtype %d\n", xst->authtype);
874 break;
875
876 default:
877 plog(ASL_LEVEL_WARNING,
878 "Unexpected authtype %d\n", xst->authtype);
879 break;
880 }
881
882 return;
883 }
884
885 int
886 xauth_rmconf_used(xauth_rmconf)
887 struct xauth_rmconf **xauth_rmconf;
888 {
889 if (*xauth_rmconf == NULL) {
890 *xauth_rmconf = racoon_malloc(sizeof(**xauth_rmconf));
891 if (*xauth_rmconf == NULL) {
892 plog(ASL_LEVEL_ERR,
893 "xauth_rmconf_used: malloc failed\n");
894 return -1;
895 }
896
897 (*xauth_rmconf)->login = NULL;
898 (*xauth_rmconf)->pass = NULL;
899 (*xauth_rmconf)->state = 0;
900 } else {
901 if ((*xauth_rmconf)->login) {
902 vfree((*xauth_rmconf)->login);
903 (*xauth_rmconf)->login = NULL;
904 }
905 if ((*xauth_rmconf)->pass != NULL) {
906 vfree((*xauth_rmconf)->pass);
907 (*xauth_rmconf)->pass = NULL;
908 }
909 (*xauth_rmconf)->state = 0;
910 }
911
912 return 0;
913 }
914
915 void
916 xauth_rmconf_delete(xauth_rmconf)
917 struct xauth_rmconf **xauth_rmconf;
918 {
919 if (*xauth_rmconf != NULL) {
920 if ((*xauth_rmconf)->login != NULL)
921 vfree((*xauth_rmconf)->login);
922 if ((*xauth_rmconf)->pass != NULL)
923 vfree((*xauth_rmconf)->pass);
924
925 racoon_free(*xauth_rmconf);
926 *xauth_rmconf = NULL;
927 }
928
929 return;
930 }