1/* $NetBSD: isakmp_cfg.c,v 1.12.6.1 2007/06/07 20:06:34 manu Exp $ */ 2 3/* Id: isakmp_cfg.c,v 1.55 2006/08/22 18:17:17 manubsd Exp */ 4 5/* 6 * Copyright (C) 2004-2006 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 <utmpx.h> 42#include <util.h> 43 44 45#ifdef __FreeBSD__ 46# include <libutil.h> 47#endif 48#ifdef __NetBSD__ 49# include <util.h> 50#endif 51 52#include <netinet/in.h> 53#include <arpa/inet.h> 54 55#include <stdlib.h> 56#include <stdio.h> 57#include <string.h> 58#include <errno.h> 59#if TIME_WITH_SYS_TIME 60# include <sys/time.h> 61# include <time.h> 62#else 63# if HAVE_SYS_TIME_H 64# include <sys/time.h> 65# else 66# include <time.h> 67# endif 68#endif 69#include <netdb.h> 70#ifdef HAVE_UNISTD_H 71#include <unistd.h> 72#endif 73#if HAVE_STDINT_H 74#include <stdint.h> 75#endif 76#include <ctype.h> 77#include <resolv.h> 78 79#include "var.h" 80#include "misc.h" 81#include "vmbuf.h" 82#include "plog.h" 83#include "sockmisc.h" 84#include "schedule.h" 85#include "debug.h" 86#include "fsm.h" 87 88#include "isakmp_var.h" 89#include "isakmp.h" 90#include "handler.h" 91#include "throttle.h" 92#include "remoteconf.h" 93#include "localconf.h" 94#include "crypto_openssl.h" 95#include "isakmp_inf.h" 96#include "isakmp_xauth.h" 97#include "isakmp_unity.h" 98#include "isakmp_cfg.h" 99#include "strnames.h" 100#include "vpn_control.h" 101#include "vpn_control_var.h" 102#include "ike_session.h" 103#include "ipsecSessionTracer.h" 104#include "ipsecMessageTracer.h" 105#include "nattraversal.h" 106 107struct isakmp_cfg_config isakmp_cfg_config; 108 109static vchar_t *buffer_cat (vchar_t *s, vchar_t *append); 110static vchar_t *isakmp_cfg_net (phase1_handle_t *, struct isakmp_data *); 111#if 0 112static vchar_t *isakmp_cfg_void (phase1_handle_t *, struct isakmp_data *); 113#endif 114static vchar_t *isakmp_cfg_addr4 (phase1_handle_t *, 115 struct isakmp_data *, in_addr_t *); 116static void isakmp_cfg_getaddr4 (struct isakmp_data *, struct in_addr *); 117static vchar_t *isakmp_cfg_addr4_list (phase1_handle_t *, 118 struct isakmp_data *, in_addr_t *, int); 119static void isakmp_cfg_appendaddr4 (struct isakmp_data *, 120 struct in_addr *, int *, int); 121static void isakmp_cfg_getstring (struct isakmp_data *,char *); 122void isakmp_cfg_iplist_to_str (char *, int, void *, int); 123 124#define ISAKMP_CFG_LOGIN 1 125#define ISAKMP_CFG_LOGOUT 2 126 127/* 128 * Handle an ISAKMP config mode packet 129 * We expect HDR, HASH, ATTR 130 */ 131void 132isakmp_cfg_r(iph1, msg) 133 phase1_handle_t *iph1; 134 vchar_t *msg; 135{ 136 struct isakmp *packet; 137 struct isakmp_gen *ph; 138 int tlen; 139 char *npp; 140 int np; 141 vchar_t *dmsg; 142 struct isakmp_ivm *ivm; 143 phase2_handle_t *iph2; 144 int error = -1; 145 146 /* Check that the packet is long enough to have a header */ 147 if (msg->l < sizeof(*packet)) { 148 IPSECSESSIONTRACEREVENT(iph1->parent_session, 149 IPSECSESSIONEVENTCODE_IKE_PACKET_RX_FAIL, 150 CONSTSTR("MODE-Config. Unexpected short packet"), 151 CONSTSTR("Failed to process short MODE-Config packet")); 152 plog(ASL_LEVEL_ERR, "Unexpected short packet\n"); 153 return; 154 } 155 156 packet = (struct isakmp *)msg->v; 157 158 /* Is it encrypted? It should be encrypted */ 159 if ((packet->flags & ISAKMP_FLAG_E) == 0) { 160 IPSECSESSIONTRACEREVENT(iph1->parent_session, 161 IPSECSESSIONEVENTCODE_IKE_PACKET_RX_FAIL, 162 CONSTSTR("MODE-Config. User credentials sent in cleartext"), 163 CONSTSTR("Dropped cleattext User credentials")); 164 plog(ASL_LEVEL_ERR, 165 "User credentials sent in cleartext!\n"); 166 return; 167 } 168 169 /* 170 * Decrypt the packet. If this is the beginning of a new 171 * exchange, reinitialize the IV 172 */ 173 if (iph1->mode_cfg->ivm == NULL || 174 iph1->mode_cfg->last_msgid != packet->msgid ) 175 iph1->mode_cfg->ivm = 176 isakmp_cfg_newiv(iph1, packet->msgid); 177 ivm = iph1->mode_cfg->ivm; 178 179 dmsg = oakley_do_decrypt(iph1, msg, ivm->iv, ivm->ive); 180 if (dmsg == NULL) { 181 IPSECSESSIONTRACEREVENT(iph1->parent_session, 182 IPSECSESSIONEVENTCODE_IKE_PACKET_RX_FAIL, 183 CONSTSTR("MODE-Config. Failed to decrypt packet"), 184 CONSTSTR("Failed to decrypt MODE-Config packet")); 185 plog(ASL_LEVEL_ERR, 186 "failed to decrypt message\n"); 187 return; 188 } 189 190 plog(ASL_LEVEL_DEBUG, "MODE_CFG packet\n"); 191 192 /* Now work with the decrypted packet */ 193 packet = (struct isakmp *)dmsg->v; 194 tlen = dmsg->l - sizeof(*packet); 195 ph = (struct isakmp_gen *)(packet + 1); 196 197 np = packet->np; 198 while ((tlen > 0) && (np != ISAKMP_NPTYPE_NONE)) { 199 /* Check that the payload header fits in the packet */ 200 if (tlen < sizeof(*ph)) { 201 plog(ASL_LEVEL_WARNING, 202 "Short payload header\n"); 203 goto out; 204 } 205 206 /* Check that the payload fits in the packet */ 207 if (tlen < ntohs(ph->len)) { 208 plog(ASL_LEVEL_WARNING, 209 "Short payload\n"); 210 goto out; 211 } 212 213 plog(ASL_LEVEL_DEBUG, "Seen payload %d\n", np); 214 215 switch(np) { 216 case ISAKMP_NPTYPE_HASH: { 217 vchar_t *check; 218 vchar_t *payload; 219 size_t plen; 220 struct isakmp_gen *nph; 221 222 plen = ntohs(ph->len); 223 nph = (struct isakmp_gen *)((char *)ph + plen); 224 plen = ntohs(nph->len); 225 /* Check that the hash payload fits in the packet */ 226 if (tlen < (plen + ntohs(ph->len))) { 227 plog(ASL_LEVEL_WARNING, 228 "Invalid Hash payload. len %d, overall-len %d\n", 229 ntohs(nph->len), 230 (int)plen); 231 goto out; 232 } 233 234 if ((payload = vmalloc(plen)) == NULL) { 235 plog(ASL_LEVEL_ERR, 236 "Cannot allocate memory\n"); 237 goto out; 238 } 239 memcpy(payload->v, nph, plen); 240 241 if ((check = oakley_compute_hash1(iph1, 242 packet->msgid, payload)) == NULL) { 243 plog(ASL_LEVEL_ERR, 244 "Cannot compute hash\n"); 245 vfree(payload); 246 goto out; 247 } 248 249 if (memcmp(ph + 1, check->v, check->l) != 0) { 250 plog(ASL_LEVEL_ERR, 251 "Hash verification failed\n"); 252 vfree(payload); 253 vfree(check); 254 goto out; 255 } 256 vfree(payload); 257 vfree(check); 258 break; 259 } 260 case ISAKMP_NPTYPE_ATTR: { 261 struct isakmp_pl_attr *attrpl; 262 263 attrpl = (struct isakmp_pl_attr *)ph; 264 isakmp_cfg_attr_r(iph1, packet->msgid, attrpl, msg); 265 266 break; 267 } 268 default: 269 plog(ASL_LEVEL_WARNING, 270 "Unexpected next payload %d\n", np); 271 /* Skip to the next payload */ 272 break; 273 } 274 275 /* Move to the next payload */ 276 np = ph->np; 277 tlen -= ntohs(ph->len); 278 npp = (char *)ph; 279 ph = (struct isakmp_gen *)(npp + ntohs(ph->len)); 280 } 281 282 error = 0; 283 /* find phase 2 in case pkt scheduled for resend */ 284 iph2 = ike_session_getph2bymsgid(iph1, packet->msgid); 285 if (iph2 == NULL) 286 goto out; /* no resend scheduled */ 287 SCHED_KILL(iph2->scr); /* turn off schedule */ 288 ike_session_unlink_phase2(iph2); 289 290 IPSECSESSIONTRACEREVENT(iph1->parent_session, 291 IPSECSESSIONEVENTCODE_IKE_PACKET_RX_SUCC, 292 CONSTSTR("MODE-Config"), 293 CONSTSTR(NULL)); 294out: 295 if (error) { 296 IPSECSESSIONTRACEREVENT(iph1->parent_session, 297 IPSECSESSIONEVENTCODE_IKE_PACKET_RX_FAIL, 298 CONSTSTR("MODE-Config"), 299 CONSTSTR("Failed to process Mode-Config packet")); 300 } 301 vfree(dmsg); 302} 303 304int 305isakmp_cfg_attr_r(iph1, msgid, attrpl, msg) 306 phase1_handle_t *iph1; 307 u_int32_t msgid; 308 struct isakmp_pl_attr *attrpl; 309 vchar_t *msg; 310{ 311 int type = attrpl->type; 312 313 plog(ASL_LEVEL_DEBUG, 314 "Configuration exchange type %s\n", s_isakmp_cfg_ptype(type)); 315 switch (type) { 316 case ISAKMP_CFG_ACK: 317 /* ignore, but this is the time to reinit the IV */ 318 oakley_delivm(iph1->mode_cfg->ivm); 319 iph1->mode_cfg->ivm = NULL; 320 return 0; 321 break; 322 323 case ISAKMP_CFG_REPLY: 324 return isakmp_cfg_reply(iph1, attrpl); 325 break; 326 327 case ISAKMP_CFG_REQUEST: 328 iph1->msgid = msgid; 329 return isakmp_cfg_request(iph1, attrpl, msg); 330 break; 331 332 case ISAKMP_CFG_SET: 333 iph1->msgid = msgid; 334 return isakmp_cfg_set(iph1, attrpl, msg); 335 break; 336 337 default: 338 plog(ASL_LEVEL_WARNING, 339 "Unepected configuration exchange type %d\n", type); 340 return -1; 341 break; 342 } 343 344 return 0; 345} 346 347int 348isakmp_cfg_reply(iph1, attrpl) 349 phase1_handle_t *iph1; 350 struct isakmp_pl_attr *attrpl; 351{ 352 struct isakmp_data *attr; 353 int tlen; 354 size_t alen; 355 char *npp; 356 int type; 357 int error; 358 359 if (iph1->mode_cfg->flags & ISAKMP_CFG_GOT_REPLY) 360 return 0; /* already received this - duplicate packet */ 361 362 tlen = ntohs(attrpl->h.len); 363 attr = (struct isakmp_data *)(attrpl + 1); 364 tlen -= sizeof(*attrpl); 365 366 while (tlen > 0) { 367 type = ntohs(attr->type); 368 369 /* Handle short attributes */ 370 if ((type & ISAKMP_GEN_MASK) == ISAKMP_GEN_TV) { 371 type &= ~ISAKMP_GEN_MASK; 372 373 plog(ASL_LEVEL_DEBUG, 374 "Short attribute %s = %d\n", 375 s_isakmp_cfg_type(type), ntohs(attr->lorv)); 376 377 switch (type) { 378 case XAUTH_TYPE: 379 if ((error = xauth_attr_reply(iph1, 380 attr, ntohs(attrpl->id))) != 0) 381 return error; 382 break; 383 384 break; 385 386 default: 387 plog(ASL_LEVEL_WARNING, 388 "Ignored short attribute %s\n", 389 s_isakmp_cfg_type(type)); 390 break; 391 } 392 393 tlen -= sizeof(*attr); 394 attr++; 395 continue; 396 } 397 398 type = ntohs(attr->type); 399 alen = ntohs(attr->lorv); 400 401 /* Check that the attribute fit in the packet */ 402 if (tlen < alen) { 403 plog(ASL_LEVEL_ERR, 404 "Short attribute %s\n", 405 s_isakmp_cfg_type(type)); 406 return -1; 407 } 408 409 plog(ASL_LEVEL_DEBUG, 410 "Attribute %s, len %zu\n", 411 s_isakmp_cfg_type(type), alen); 412 413 switch(type) { 414 case XAUTH_TYPE: 415 case XAUTH_USER_NAME: 416 case XAUTH_USER_PASSWORD: 417 case XAUTH_PASSCODE: 418 case XAUTH_MESSAGE: 419 case XAUTH_CHALLENGE: 420 case XAUTH_DOMAIN: 421 case XAUTH_STATUS: 422 case XAUTH_NEXT_PIN: 423 case XAUTH_ANSWER: 424 if ((error = xauth_attr_reply(iph1, 425 attr, ntohs(attrpl->id))) != 0) 426 return error; 427 break; 428 case INTERNAL_IP4_ADDRESS: 429 if ((iph1->mode_cfg->flags & ISAKMP_CFG_GOT_ADDR4) == 0) { 430 isakmp_cfg_getaddr4(attr, &iph1->mode_cfg->addr4); 431 iph1->mode_cfg->flags |= ISAKMP_CFG_GOT_ADDR4; 432 } 433 break; 434 case INTERNAL_IP4_NETMASK: 435 if ((iph1->mode_cfg->flags & ISAKMP_CFG_GOT_MASK4) == 0) { 436 isakmp_cfg_getaddr4(attr, &iph1->mode_cfg->mask4); 437 iph1->mode_cfg->flags |= ISAKMP_CFG_GOT_MASK4; 438 } 439 break; 440 case INTERNAL_IP4_DNS: 441 if ((iph1->mode_cfg->flags & ISAKMP_CFG_GOT_DNS4) == 0) { 442 isakmp_cfg_appendaddr4(attr, 443 &iph1->mode_cfg->dns4[iph1->mode_cfg->dns4_index], 444 &iph1->mode_cfg->dns4_index, MAXNS); 445 iph1->mode_cfg->flags |= ISAKMP_CFG_GOT_DNS4; 446 } 447 break; 448 case INTERNAL_IP4_NBNS: 449 if ((iph1->mode_cfg->flags & ISAKMP_CFG_GOT_WINS4) == 0) { 450 isakmp_cfg_appendaddr4(attr, 451 &iph1->mode_cfg->wins4[iph1->mode_cfg->wins4_index], 452 &iph1->mode_cfg->wins4_index, MAXNS); 453 iph1->mode_cfg->flags |= ISAKMP_CFG_GOT_WINS4; 454 } 455 break; 456 case UNITY_DEF_DOMAIN: 457 if ((iph1->mode_cfg->flags & ISAKMP_CFG_GOT_DEFAULT_DOMAIN) == 0) { 458 isakmp_cfg_getstring(attr, 459 iph1->mode_cfg->default_domain); 460 iph1->mode_cfg->flags |= ISAKMP_CFG_GOT_DEFAULT_DOMAIN; 461 } 462 break; 463 case UNITY_SPLIT_INCLUDE: 464 case UNITY_LOCAL_LAN: 465 case UNITY_SPLITDNS_NAME: 466 case UNITY_BANNER: 467 case UNITY_SAVE_PASSWD: 468 case UNITY_NATT_PORT: 469 case UNITY_FW_TYPE: 470 case UNITY_BACKUP_SERVERS: 471 case UNITY_DDNS_HOSTNAME: 472 case APPLICATION_VERSION: 473 case UNITY_PFS: 474 isakmp_unity_reply(iph1, attr); 475 break; 476 case INTERNAL_IP4_SUBNET: 477 case INTERNAL_ADDRESS_EXPIRY: 478 if (iph1->started_by_api) 479 break; /* not actually ignored - don't fall thru */ 480 // else fall thru 481 default: 482 plog(ASL_LEVEL_WARNING, 483 "Ignored attribute %s\n", 484 s_isakmp_cfg_type(type)); 485 break; 486 } 487 488 npp = (char *)attr; 489 attr = (struct isakmp_data *)(npp + sizeof(*attr) + alen); 490 tlen -= (sizeof(*attr) + alen); 491 } 492 iph1->mode_cfg->flags |= ISAKMP_CFG_GOT_REPLY; 493 494 if (iph1->started_by_api || (iph1->is_rekey && iph1->parent_session && iph1->parent_session->is_client)) { 495 /* connection was started by API - save attr list for passing to VPN controller */ 496 if (iph1->mode_cfg->attr_list != NULL) /* shouldn't happen */ 497 vfree(iph1->mode_cfg->attr_list); 498 if (ntohs(attrpl->h.len) < sizeof(*attrpl)) { 499 plog(ASL_LEVEL_ERR, 500 "invalid cfg-attr-list, attr-len %d\n", 501 ntohs(attrpl->h.len)); 502 return -1; 503 } 504 alen = ntohs(attrpl->h.len) - sizeof(*attrpl); 505 if ((iph1->mode_cfg->attr_list = vmalloc(alen)) == NULL) { 506 plog(ASL_LEVEL_ERR, 507 "Cannot allocate memory for mode-cfg attribute list\n"); 508 return -1; 509 } 510 memcpy(iph1->mode_cfg->attr_list->v, attrpl + 1, alen); 511 } 512 513 514#ifdef ENABLE_VPNCONTROL_PORT 515 if (FSM_STATE_IS_ESTABLISHED(iph1->status)) 516 vpncontrol_notify_phase_change(0, FROM_LOCAL, iph1, NULL); 517#endif 518 519 return 0; 520} 521 522int 523isakmp_cfg_request(iph1, attrpl, msg) 524 phase1_handle_t *iph1; 525 struct isakmp_pl_attr *attrpl; 526 vchar_t *msg; 527{ 528 struct isakmp_data *attr; 529 int tlen; 530 size_t alen; 531 char *npp; 532 vchar_t *payload = NULL; 533 struct isakmp_pl_attr *reply; 534 vchar_t *reply_attr; 535 int type; 536 int error = -1; 537 538 tlen = ntohs(attrpl->h.len); 539 attr = (struct isakmp_data *)(attrpl + 1); 540 tlen -= sizeof(*attrpl); 541 542 /* 543 * if started_by_api then we are a VPN client and if we receive 544 * a mode-cfg request it needs to go to the VPN controller to 545 * retrieve the appropriate data (name, pw, pin, etc.) 546 */ 547 if (iph1->started_by_api || ike_session_is_client_ph1_rekey(iph1)) { 548 /* 549 * if we already received this one - ignore it 550 * we are waiting for a reply from the vpn control socket 551 */ 552 if (iph1->xauth_awaiting_userinput) 553 return 0; 554 555 /* otherwise - save the msg id and call and send the status notification */ 556 iph1->pended_xauth_id = attrpl->id; /* network byte order */ 557 if (vpncontrol_notify_need_authinfo(iph1, attrpl + 1, tlen)) 558 goto end; 559 iph1->xauth_awaiting_userinput = 1; 560 iph1->xauth_awaiting_userinput_msg = vdup(msg); // dup the message for later 561 ike_session_start_xauth_timer(iph1); 562 563 IPSECLOGASLMSG("IPSec Extended Authentication requested.\n"); 564 565 return 0; 566 } 567 568 if ((payload = vmalloc(sizeof(*reply))) == NULL) { 569 plog(ASL_LEVEL_ERR, "Cannot allocate memory\n"); 570 return -1; 571 } 572 memset(payload->v, 0, sizeof(*reply)); 573 574 while (tlen > 0) { 575 reply_attr = NULL; 576 type = ntohs(attr->type); 577 578 /* Handle short attributes */ 579 if ((type & ISAKMP_GEN_MASK) == ISAKMP_GEN_TV) { 580 type &= ~ISAKMP_GEN_MASK; 581 582 plog(ASL_LEVEL_DEBUG, 583 "Short attribute %s = %d\n", 584 s_isakmp_cfg_type(type), ntohs(attr->lorv)); 585 586 switch (type) { 587 case XAUTH_TYPE: 588 reply_attr = isakmp_xauth_req(iph1, attr); 589 break; 590 default: 591 plog(ASL_LEVEL_WARNING, 592 "Ignored short attribute %s\n", 593 s_isakmp_cfg_type(type)); 594 break; 595 } 596 597 tlen -= sizeof(*attr); 598 attr++; 599 600 if (reply_attr != NULL) { 601 payload = buffer_cat(payload, reply_attr); 602 vfree(reply_attr); 603 } 604 605 continue; 606 } 607 608 type = ntohs(attr->type); 609 alen = ntohs(attr->lorv); 610 611 /* Check that the attribute fit in the packet */ 612 if (tlen < alen) { 613 plog(ASL_LEVEL_ERR, 614 "Short attribute %s\n", 615 s_isakmp_cfg_type(type)); 616 goto end; 617 } 618 619 plog(ASL_LEVEL_DEBUG, 620 "Attribute %s, len %zu\n", 621 s_isakmp_cfg_type(type), alen); 622 623 switch(type) { 624 case INTERNAL_IP4_ADDRESS: 625 case INTERNAL_IP4_NETMASK: 626 case INTERNAL_IP4_DNS: 627 case INTERNAL_IP4_NBNS: 628 case INTERNAL_IP4_SUBNET: 629 reply_attr = isakmp_cfg_net(iph1, attr); 630 break; 631 632 case XAUTH_TYPE: 633 case XAUTH_USER_NAME: 634 case XAUTH_USER_PASSWORD: 635 case XAUTH_PASSCODE: 636 case XAUTH_MESSAGE: 637 case XAUTH_CHALLENGE: 638 case XAUTH_DOMAIN: 639 case XAUTH_STATUS: 640 case XAUTH_NEXT_PIN: 641 case XAUTH_ANSWER: 642 reply_attr = isakmp_xauth_req(iph1, attr); 643 break; 644 645 case APPLICATION_VERSION: 646 reply_attr = isakmp_cfg_string(iph1, 647 attr, ISAKMP_CFG_RACOON_VERSION); 648 break; 649 650 case UNITY_BANNER: 651 case UNITY_PFS: 652 case UNITY_SAVE_PASSWD: 653 case UNITY_DEF_DOMAIN: 654 case UNITY_DDNS_HOSTNAME: 655 case UNITY_FW_TYPE: 656 case UNITY_SPLITDNS_NAME: 657 case UNITY_SPLIT_INCLUDE: 658 case UNITY_LOCAL_LAN: 659 case UNITY_NATT_PORT: 660 case UNITY_BACKUP_SERVERS: 661 reply_attr = isakmp_unity_req(iph1, attr); 662 break; 663 664 case INTERNAL_ADDRESS_EXPIRY: 665 default: 666 plog(ASL_LEVEL_WARNING, 667 "Ignored attribute %s\n", 668 s_isakmp_cfg_type(type)); 669 break; 670 } 671 672 npp = (char *)attr; 673 attr = (struct isakmp_data *)(npp + sizeof(*attr) + alen); 674 tlen -= (sizeof(*attr) + alen); 675 676 if (reply_attr != NULL) { 677 payload = buffer_cat(payload, reply_attr); 678 vfree(reply_attr); 679 } 680 } 681 682 reply = (struct isakmp_pl_attr *)payload->v; 683 reply->h.len = htons(payload->l); 684 reply->type = ISAKMP_CFG_REPLY; 685 reply->id = attrpl->id; 686 687 plog(ASL_LEVEL_DEBUG, 688 "Sending MODE_CFG REPLY\n"); 689 690 error = isakmp_cfg_send(iph1, payload, 691 ISAKMP_NPTYPE_ATTR, ISAKMP_FLAG_E, 0, 0, msg); 692 693 694end: 695 vfree(payload); 696 697 return error; 698} 699 700int 701isakmp_cfg_set(iph1, attrpl, msg) 702 phase1_handle_t *iph1; 703 struct isakmp_pl_attr *attrpl; 704 vchar_t *msg; 705{ 706 struct isakmp_data *attr; 707 int tlen; 708 size_t alen; 709 char *npp; 710 vchar_t *payload; 711 struct isakmp_pl_attr *reply; 712 vchar_t *reply_attr; 713 int type; 714 int error = -1; 715 716 if ((payload = vmalloc(sizeof(*reply))) == NULL) { 717 plog(ASL_LEVEL_ERR, "Cannot allocate memory\n"); 718 return -1; 719 } 720 memset(payload->v, 0, sizeof(*reply)); 721 722 tlen = ntohs(attrpl->h.len); 723 attr = (struct isakmp_data *)(attrpl + 1); 724 tlen -= sizeof(*attrpl); 725 726 /* 727 * We should send ack for the attributes we accepted 728 */ 729 while (tlen > 0) { 730 reply_attr = NULL; 731 type = ntohs(attr->type); 732 733 plog(ASL_LEVEL_DEBUG, 734 "Attribute %s\n", 735 s_isakmp_cfg_type(type & ~ISAKMP_GEN_MASK)); 736 737 switch (type & ~ISAKMP_GEN_MASK) { 738 case XAUTH_STATUS: 739 reply_attr = isakmp_xauth_set(iph1, attr); 740 break; 741 default: 742 plog(ASL_LEVEL_DEBUG, 743 "Unexpected SET attribute %s\n", 744 s_isakmp_cfg_type(type & ~ISAKMP_GEN_MASK)); 745 break; 746 } 747 748 if (reply_attr != NULL) { 749 payload = buffer_cat(payload, reply_attr); 750 vfree(reply_attr); 751 } 752 753 /* 754 * Move to next attribute. If we run out of the packet, 755 * tlen becomes negative and we exit. 756 */ 757 if ((type & ISAKMP_GEN_MASK) == ISAKMP_GEN_TV) { 758 tlen -= sizeof(*attr); 759 attr++; 760 } else { 761 alen = ntohs(attr->lorv); 762 tlen -= (sizeof(*attr) + alen); 763 npp = (char *)attr; 764 attr = (struct isakmp_data *) 765 (npp + sizeof(*attr) + alen); 766 } 767 } 768 769 reply = (struct isakmp_pl_attr *)payload->v; 770 reply->h.len = htons(payload->l); 771 reply->type = ISAKMP_CFG_ACK; 772 reply->id = attrpl->id; 773 774 plog(ASL_LEVEL_DEBUG, 775 "Sending MODE_CFG ACK\n"); 776 777 error = isakmp_cfg_send(iph1, payload, 778 ISAKMP_NPTYPE_ATTR, ISAKMP_FLAG_E, 0, 0, msg); 779 780 if (iph1->mode_cfg->flags & ISAKMP_CFG_DELETE_PH1) { 781 if (FSM_STATE_IS_ESTABLISHED(iph1->status)) 782 isakmp_info_send_d1(iph1); 783 isakmp_ph1expire(iph1); 784 iph1 = NULL; 785 } 786 vfree(payload); 787 788 /* 789 * If required, request ISAKMP mode config information: ignore rekeys 790 */ 791 if ((iph1 != NULL) && (!iph1->is_rekey) && (iph1->rmconf->mode_cfg) && (error == 0)) 792 error = isakmp_cfg_getconfig(iph1); 793 794 return error; 795} 796 797 798static vchar_t * 799buffer_cat(s, append) 800 vchar_t *s; 801 vchar_t *append; 802{ 803 vchar_t *new; 804 805 new = vmalloc(s->l + append->l); 806 if (new == NULL) { 807 plog(ASL_LEVEL_ERR, 808 "Cannot allocate memory\n"); 809 return s; 810 } 811 812 memcpy(new->v, s->v, s->l); 813 memcpy(new->v + s->l, append->v, append->l); 814 815 vfree(s); 816 return new; 817} 818 819static vchar_t * 820isakmp_cfg_net(iph1, attr) 821 phase1_handle_t *iph1; 822 struct isakmp_data *attr; 823{ 824 int type; 825 int confsource; 826 827 type = ntohs(attr->type); 828 829 /* 830 * Don't give an address to a peer that did not succeed Xauth 831 */ 832 if (xauth_check(iph1) != 0) { 833 plog(ASL_LEVEL_ERR, 834 "Attempt to start phase config whereas Xauth failed\n"); 835 return NULL; 836 } 837 838 confsource = isakmp_cfg_config.confsource; 839 /* 840 * If we have to fall back to a local 841 * configuration source, we will jump 842 * back to this point. 843 */ 844 845 switch(type) { 846 case INTERNAL_IP4_ADDRESS: 847 switch(confsource) { 848 case ISAKMP_CFG_CONF_LOCAL: 849 if (isakmp_cfg_getport(iph1) == -1) { 850 plog(ASL_LEVEL_ERR, 851 "Port pool depleted\n"); 852 break; 853 } 854 855 iph1->mode_cfg->addr4.s_addr = 856 htonl(ntohl(isakmp_cfg_config.network4) 857 + iph1->mode_cfg->port); 858 iph1->mode_cfg->flags |= ISAKMP_CFG_ADDR4_LOCAL; 859 break; 860 861 default: 862 plog(ASL_LEVEL_ERR, 863 "Unexpected confsource\n"); 864 } 865 866 return isakmp_cfg_addr4(iph1, 867 attr, &iph1->mode_cfg->addr4.s_addr); 868 break; 869 870 case INTERNAL_IP4_NETMASK: 871 switch(confsource) { 872 case ISAKMP_CFG_CONF_LOCAL: 873 iph1->mode_cfg->mask4.s_addr 874 = isakmp_cfg_config.netmask4; 875 iph1->mode_cfg->flags |= ISAKMP_CFG_MASK4_LOCAL; 876 break; 877 878 default: 879 plog(ASL_LEVEL_ERR, 880 "Unexpected confsource\n"); 881 } 882 return isakmp_cfg_addr4(iph1, attr, 883 &iph1->mode_cfg->mask4.s_addr); 884 break; 885 886 case INTERNAL_IP4_DNS: 887 return isakmp_cfg_addr4_list(iph1, 888 attr, &isakmp_cfg_config.dns4[0], 889 isakmp_cfg_config.dns4_index); 890 break; 891 892 case INTERNAL_IP4_NBNS: 893 return isakmp_cfg_addr4_list(iph1, 894 attr, &isakmp_cfg_config.nbns4[0], 895 isakmp_cfg_config.nbns4_index); 896 break; 897 898 case INTERNAL_IP4_SUBNET: 899 return isakmp_cfg_addr4(iph1, 900 attr, &isakmp_cfg_config.network4); 901 break; 902 903 default: 904 plog(ASL_LEVEL_ERR, "Unexpected type %d\n", type); 905 break; 906 } 907 return NULL; 908} 909 910#if 0 911static vchar_t * 912isakmp_cfg_void(iph1, attr) 913 phase1_handle_t *iph1; 914 struct isakmp_data *attr; 915{ 916 vchar_t *buffer; 917 struct isakmp_data *new; 918 919 if ((buffer = vmalloc(sizeof(*attr))) == NULL) { 920 plog(ASL_LEVEL_ERR, "Cannot allocate memory\n"); 921 return NULL; 922 } 923 924 new = (struct isakmp_data *)buffer->v; 925 926 new->type = attr->type; 927 new->lorv = htons(0); 928 929 return buffer; 930} 931#endif 932 933vchar_t * 934isakmp_cfg_copy(iph1, attr) 935 phase1_handle_t *iph1; 936 struct isakmp_data *attr; 937{ 938 vchar_t *buffer; 939 size_t len = 0; 940 941 if ((ntohs(attr->type) & ISAKMP_GEN_MASK) == ISAKMP_GEN_TLV) 942 len = ntohs(attr->lorv); 943 944 if ((buffer = vmalloc(sizeof(*attr) + len)) == NULL) { 945 plog(ASL_LEVEL_ERR, "Cannot allocate memory\n"); 946 return NULL; 947 } 948 949 memcpy(buffer->v, attr, sizeof(*attr) + ntohs(attr->lorv)); 950 951 return buffer; 952} 953 954vchar_t * 955isakmp_cfg_short(iph1, attr, value) 956 phase1_handle_t *iph1; 957 struct isakmp_data *attr; 958 int value; 959{ 960 vchar_t *buffer; 961 struct isakmp_data *new; 962 int type; 963 964 if ((buffer = vmalloc(sizeof(*attr))) == NULL) { 965 plog(ASL_LEVEL_ERR, "Cannot allocate memory\n"); 966 return NULL; 967 } 968 969 new = (struct isakmp_data *)buffer->v; 970 type = ntohs(attr->type) & ~ISAKMP_GEN_MASK; 971 972 new->type = htons(type | ISAKMP_GEN_TV); 973 new->lorv = htons(value); 974 975 return buffer; 976} 977 978vchar_t * 979isakmp_cfg_varlen(iph1, attr, string, len) 980 phase1_handle_t *iph1; 981 struct isakmp_data *attr; 982 char *string; 983 size_t len; 984{ 985 vchar_t *buffer; 986 struct isakmp_data *new; 987 char *data; 988 989 if ((buffer = vmalloc(sizeof(*attr) + len)) == NULL) { 990 plog(ASL_LEVEL_ERR, "Cannot allocate memory\n"); 991 return NULL; 992 } 993 994 new = (struct isakmp_data *)buffer->v; 995 996 new->type = attr->type; 997 new->lorv = htons(len); 998 data = (char *)(new + 1); 999 1000 memcpy(data, string, len); 1001 1002 return buffer; 1003} 1004vchar_t * 1005isakmp_cfg_string(iph1, attr, string) 1006 phase1_handle_t *iph1; 1007 struct isakmp_data *attr; 1008 char *string; 1009{ 1010 size_t len = strlen(string); 1011 return isakmp_cfg_varlen(iph1, attr, string, len); 1012} 1013 1014static vchar_t * 1015isakmp_cfg_addr4(iph1, attr, addr) 1016 phase1_handle_t *iph1; 1017 struct isakmp_data *attr; 1018 in_addr_t *addr; 1019{ 1020 vchar_t *buffer; 1021 struct isakmp_data *new; 1022 size_t len; 1023 1024 len = sizeof(*addr); 1025 if ((buffer = vmalloc(sizeof(*attr) + len)) == NULL) { 1026 plog(ASL_LEVEL_ERR, "Cannot allocate memory\n"); 1027 return NULL; 1028 } 1029 1030 new = (struct isakmp_data *)buffer->v; 1031 1032 new->type = attr->type; 1033 new->lorv = htons(len); 1034 memcpy(new + 1, addr, len); 1035 1036 return buffer; 1037} 1038 1039static vchar_t * 1040isakmp_cfg_addr4_list(iph1, attr, addr, nbr) 1041 phase1_handle_t *iph1; 1042 struct isakmp_data *attr; 1043 in_addr_t *addr; 1044 int nbr; 1045{ 1046 int error = -1; 1047 vchar_t *buffer = NULL; 1048 vchar_t *bufone = NULL; 1049 struct isakmp_data *new; 1050 size_t len; 1051 int i; 1052 1053 len = sizeof(*addr); 1054 if ((buffer = vmalloc(0)) == NULL) { 1055 plog(ASL_LEVEL_ERR, "Cannot allocate memory\n"); 1056 goto out; 1057 } 1058 for(i = 0; i < nbr; i++) { 1059 if ((bufone = vmalloc(sizeof(*attr) + len)) == NULL) { 1060 plog(ASL_LEVEL_ERR, 1061 "Cannot allocate memory\n"); 1062 goto out; 1063 } 1064 new = (struct isakmp_data *)bufone->v; 1065 new->type = attr->type; 1066 new->lorv = htons(len); 1067 memcpy(new + 1, &addr[i], len); 1068 new += (len + sizeof(*attr)); 1069 buffer = buffer_cat(buffer, bufone); 1070 vfree(bufone); 1071 } 1072 1073 error = 0; 1074 1075out: 1076 if ((error != 0) && (buffer != NULL)) { 1077 vfree(buffer); 1078 buffer = NULL; 1079 } 1080 1081 return buffer; 1082} 1083 1084struct isakmp_ivm * 1085isakmp_cfg_newiv(iph1, msgid) 1086 phase1_handle_t *iph1; 1087 u_int32_t msgid; 1088{ 1089 struct isakmp_cfg_state *ics = iph1->mode_cfg; 1090 1091 if (ics == NULL) { 1092 plog(ASL_LEVEL_ERR, 1093 "isakmp_cfg_newiv called without mode config state\n"); 1094 return NULL; 1095 } 1096 1097 if (ics->ivm != NULL) 1098 oakley_delivm(ics->ivm); 1099 1100 ics->ivm = oakley_newiv2(iph1, msgid); 1101 ics->last_msgid = msgid; 1102 1103 return ics->ivm; 1104} 1105 1106/* Derived from isakmp_info_send_common */ 1107int 1108isakmp_cfg_send(iph1, payload, np, flags, new_exchange, retry_count, msg) 1109 phase1_handle_t *iph1; 1110 vchar_t *payload; 1111 u_int32_t np; 1112 int flags; 1113 int new_exchange; 1114 int retry_count; 1115 vchar_t *msg; 1116{ 1117 phase2_handle_t *iph2 = NULL; 1118 vchar_t *hash = NULL; 1119 struct isakmp *isakmp; 1120 struct isakmp_gen *gen; 1121 char *p; 1122 int tlen; 1123 int error = -1; 1124 struct isakmp_cfg_state *ics = iph1->mode_cfg; 1125 1126 /* Check if phase 1 is established */ 1127 if ((!FSM_STATE_IS_ESTABLISHED(iph1->status)) || 1128 (iph1->local == NULL) || 1129 (iph1->remote == NULL)) { 1130 plog(ASL_LEVEL_ERR, 1131 "ISAKMP mode config exchange with immature phase 1\n"); 1132 goto end; 1133 } 1134 1135 /* add new entry to isakmp status table */ 1136 iph2 = ike_session_newph2(ISAKMP_VERSION_NUMBER_IKEV1, PHASE2_TYPE_CFG); 1137 if (iph2 == NULL) { 1138 plog(ASL_LEVEL_ERR, 1139 "failed to allocate ph2"); 1140 goto end; 1141 } 1142 1143 iph2->dst = dupsaddr(iph1->remote); 1144 if (iph2->dst == NULL) { 1145 plog(ASL_LEVEL_ERR, 1146 "failed to duplicate remote address"); 1147 ike_session_delph2(iph2); 1148 goto end; 1149 } 1150 iph2->src = dupsaddr(iph1->local); 1151 if (iph2->src == NULL) { 1152 plog(ASL_LEVEL_ERR, 1153 "failed to duplicate local address"); 1154 ike_session_delph2(iph2); 1155 goto end; 1156 } 1157 1158 switch (iph1->remote->ss_family) { 1159 case AF_INET: 1160#if (!defined(ENABLE_NATT)) || (defined(BROKEN_NATT)) 1161 ((struct sockaddr_in *)iph2->dst)->sin_port = 0; 1162 ((struct sockaddr_in *)iph2->src)->sin_port = 0; 1163#endif 1164 break; 1165#ifdef INET6 1166 case AF_INET6: 1167#if (!defined(ENABLE_NATT)) || (defined(BROKEN_NATT)) 1168 ((struct sockaddr_in6 *)iph2->dst)->sin6_port = 0; 1169 ((struct sockaddr_in6 *)iph2->src)->sin6_port = 0; 1170#endif 1171 break; 1172#endif 1173 default: 1174 plog(ASL_LEVEL_ERR, 1175 "invalid family: %d\n", iph1->remote->ss_family); 1176 ike_session_delph2(iph2); 1177 goto end; 1178 } 1179 iph2->side = INITIATOR; 1180 fsm_set_state(&iph2->status, IKEV1_STATE_INFO); 1181 1182 if (new_exchange) 1183 iph2->msgid = isakmp_newmsgid2(iph1); 1184 else 1185 iph2->msgid = iph1->msgid; 1186 1187 /* get IV and HASH(1) if skeyid_a was generated. */ 1188 if (iph1->skeyid_a != NULL) { 1189 if (new_exchange) { 1190 if (isakmp_cfg_newiv(iph1, iph2->msgid) == NULL) { 1191 plog(ASL_LEVEL_ERR, 1192 "failed to generate IV"); 1193 ike_session_delph2(iph2); 1194 goto end; 1195 } 1196 } 1197 1198 /* generate HASH(1) */ 1199 hash = oakley_compute_hash1(iph1, iph2->msgid, payload); 1200 if (hash == NULL) { 1201 plog(ASL_LEVEL_ERR, 1202 "failed to generate HASH"); 1203 ike_session_delph2(iph2); 1204 goto end; 1205 } 1206 1207 /* initialized total buffer length */ 1208 tlen = hash->l; 1209 tlen += sizeof(*gen); 1210 } else { 1211 /* IKE-SA is not established */ 1212 hash = NULL; 1213 1214 /* initialized total buffer length */ 1215 tlen = 0; 1216 } 1217 if ((flags & ISAKMP_FLAG_A) == 0) 1218 iph2->flags = (hash == NULL ? 0 : ISAKMP_FLAG_E); 1219 else 1220 iph2->flags = (hash == NULL ? 0 : ISAKMP_FLAG_A); 1221 1222 ike_session_link_ph2_to_ph1(iph1, iph2); 1223 1224 tlen += sizeof(*isakmp) + payload->l; 1225 1226 /* create buffer for isakmp payload */ 1227 iph2->sendbuf = vmalloc(tlen); 1228 if (iph2->sendbuf == NULL) { 1229 plog(ASL_LEVEL_ERR, 1230 "failed to get buffer to send.\n"); 1231 goto err; 1232 } 1233 1234 /* create isakmp header */ 1235 isakmp = (struct isakmp *)iph2->sendbuf->v; 1236 memcpy(&isakmp->i_ck, &iph1->index.i_ck, sizeof(cookie_t)); 1237 memcpy(&isakmp->r_ck, &iph1->index.r_ck, sizeof(cookie_t)); 1238 isakmp->np = hash == NULL ? (np & 0xff) : ISAKMP_NPTYPE_HASH; 1239 isakmp->v = iph1->version; 1240 isakmp->etype = ISAKMP_ETYPE_CFG; 1241 isakmp->flags = iph2->flags; 1242 memcpy(&isakmp->msgid, &iph2->msgid, sizeof(isakmp->msgid)); 1243 isakmp->len = htonl(tlen); 1244 p = (char *)(isakmp + 1); 1245 1246 /* create HASH payload */ 1247 if (hash != NULL) { 1248 gen = (struct isakmp_gen *)p; 1249 gen->np = np & 0xff; 1250 gen->len = htons(sizeof(*gen) + hash->l); 1251 p += sizeof(*gen); 1252 memcpy(p, hash->v, hash->l); 1253 p += hash->l; 1254 } 1255 1256 /* add payload */ 1257 memcpy(p, payload->v, payload->l); 1258 p += payload->l; 1259 1260#ifdef HAVE_PRINT_ISAKMP_C 1261 isakmp_printpacket(iph2->sendbuf, iph1->local, iph1->remote, 1); 1262#endif 1263 1264 plog(ASL_LEVEL_DEBUG, "MODE_CFG packet to send\n"); 1265 1266 /* encoding */ 1267 if (ISSET(isakmp->flags, ISAKMP_FLAG_E)) { 1268 vchar_t *tmp; 1269 1270 tmp = oakley_do_encrypt(iph1, iph2->sendbuf, 1271 ics->ivm->ive, ics->ivm->iv); 1272 VPTRINIT(iph2->sendbuf); 1273 if (tmp == NULL) { 1274 plog(ASL_LEVEL_ERR, 1275 "failed to encrypt packet"); 1276 goto err; 1277 } 1278 iph2->sendbuf = tmp; 1279 } 1280 1281 /* HDR*, HASH(1), ATTR */ 1282 1283 if (retry_count > 0) { 1284 iph2->retry_counter = retry_count; 1285 if (isakmp_ph2resend(iph2) < 0) { 1286 plog(ASL_LEVEL_ERR, 1287 "failed to resend packet"); 1288 VPTRINIT(iph2->sendbuf); 1289 goto err; 1290 } 1291 IPSECSESSIONTRACEREVENT(iph1->parent_session, 1292 IPSECSESSIONEVENTCODE_IKEV1_CFG_RETRANSMIT, 1293 CONSTSTR("Mode-Config retransmit"), 1294 CONSTSTR(NULL)); 1295 error = 0; 1296 goto end; 1297 } 1298 1299 if (isakmp_send(iph2->ph1, iph2->sendbuf) < 0) { 1300 plog(ASL_LEVEL_ERR, 1301 "failed to send packet"); 1302 VPTRINIT(iph2->sendbuf); 1303 goto err; 1304 } 1305 if (msg) { 1306 /* the sending message is added to the received-list. */ 1307 if (ike_session_add_recvdpkt(iph1->remote, iph1->local, iph2->sendbuf, msg, 1308 PH2_NON_ESP_EXTRA_LEN(iph2, iph2->sendbuf), PH1_FRAG_FLAGS(iph1)) == -1) { 1309 plog(ASL_LEVEL_ERR , 1310 "failed to add a response packet to the tree.\n"); 1311 } 1312 } 1313 1314 plog(ASL_LEVEL_DEBUG, 1315 "sendto mode config %s.\n", s_isakmp_nptype(np)); 1316 1317 /* 1318 * XXX We might need to resend the message... 1319 */ 1320 1321 error = 0; 1322 VPTRINIT(iph2->sendbuf); 1323 1324 IPSECSESSIONTRACEREVENT(iph1->parent_session, 1325 IPSECSESSIONEVENTCODE_IKE_PACKET_TX_SUCC, 1326 CONSTSTR("Mode-Config message"), 1327 CONSTSTR(NULL)); 1328 1329err: 1330 if (error) { 1331 IPSECSESSIONTRACEREVENT(iph1->parent_session, 1332 IPSECSESSIONEVENTCODE_IKE_PACKET_TX_FAIL, 1333 CONSTSTR("Mode-Config message"), 1334 CONSTSTR("Failed to transmit Mode-Config message")); 1335 } 1336 ike_session_unlink_phase2(iph2); 1337end: 1338 if (hash) 1339 vfree(hash); 1340 return error; 1341} 1342 1343 1344void 1345isakmp_cfg_rmstate(phase1_handle_t *iph1) 1346{ 1347 struct isakmp_cfg_state **state = &iph1->mode_cfg; 1348 1349 1350 if (*state == NULL) 1351 return; 1352 1353 if ((*state)->flags & ISAKMP_CFG_PORT_ALLOCATED) 1354 isakmp_cfg_putport(iph1, (*state)->port); 1355 1356 /* Delete the IV if it's still there */ 1357 if((*state)->ivm) { 1358 oakley_delivm((*state)->ivm); 1359 (*state)->ivm = NULL; 1360 } 1361 1362 /* Free any allocated splitnet lists */ 1363 if((*state)->split_include != NULL) 1364 splitnet_list_free((*state)->split_include, 1365 &(*state)->include_count); 1366 if((*state)->split_local != NULL) 1367 splitnet_list_free((*state)->split_local, 1368 &(*state)->local_count); 1369 1370 xauth_rmstate(&(*state)->xauth); 1371 1372 if ((*state)->attr_list) 1373 vfree((*state)->attr_list); 1374 1375 racoon_free((*state)); 1376 (*state) = NULL; 1377 1378 return; 1379} 1380 1381struct isakmp_cfg_state * 1382isakmp_cfg_mkstate(void) 1383{ 1384 struct isakmp_cfg_state *state; 1385 1386 if ((state = racoon_malloc(sizeof(*state))) == NULL) { 1387 plog(ASL_LEVEL_ERR, 1388 "Cannot allocate memory for mode config state\n"); 1389 return NULL; 1390 } 1391 memset(state, 0, sizeof(*state)); 1392 1393 return state; 1394} 1395 1396int 1397isakmp_cfg_getport(iph1) 1398 phase1_handle_t *iph1; 1399{ 1400 unsigned int i; 1401 size_t size = isakmp_cfg_config.pool_size; 1402 1403 if (iph1->mode_cfg->flags & ISAKMP_CFG_PORT_ALLOCATED) 1404 return iph1->mode_cfg->port; 1405 1406 if (isakmp_cfg_config.port_pool == NULL) { 1407 plog(ASL_LEVEL_ERR, 1408 "isakmp_cfg_config.port_pool == NULL\n"); 1409 return -1; 1410 } 1411 1412 for (i = 0; i < size; i++) { 1413 if (isakmp_cfg_config.port_pool[i].used == 0) 1414 break; 1415 } 1416 1417 if (i == size) { 1418 plog(ASL_LEVEL_ERR, 1419 "No more addresses available\n"); 1420 return -1; 1421 } 1422 1423 isakmp_cfg_config.port_pool[i].used = 1; 1424 1425 plog(ASL_LEVEL_INFO, "Using port %d\n", i); 1426 1427 iph1->mode_cfg->flags |= ISAKMP_CFG_PORT_ALLOCATED; 1428 iph1->mode_cfg->port = i; 1429 1430 return i; 1431} 1432 1433int 1434isakmp_cfg_putport(iph1, index) 1435 phase1_handle_t *iph1; 1436 unsigned int index; 1437{ 1438 if (isakmp_cfg_config.port_pool == NULL) { 1439 plog(ASL_LEVEL_ERR, 1440 "isakmp_cfg_config.port_pool == NULL\n"); 1441 return -1; 1442 } 1443 1444 if (isakmp_cfg_config.port_pool[index].used == 0) { 1445 plog(ASL_LEVEL_ERR, 1446 "Attempt to release an unallocated address (port %d)\n", 1447 index); 1448 return -1; 1449 } 1450 1451 isakmp_cfg_config.port_pool[index].used = 0; 1452 iph1->mode_cfg->flags &= ISAKMP_CFG_PORT_ALLOCATED; 1453 1454 plog(ASL_LEVEL_INFO, "Released port %d\n", index); 1455 1456 return 0; 1457} 1458 1459 1460int 1461isakmp_cfg_getconfig(iph1) 1462 phase1_handle_t *iph1; 1463{ 1464 vchar_t *buffer; 1465 struct isakmp_pl_attr *attrpl; 1466 struct isakmp_data *attr; 1467 size_t len; 1468 vchar_t *version = NULL; 1469 int error; 1470 int attrcount; 1471 int i; 1472 int attrlist[] = { 1473 INTERNAL_IP4_ADDRESS, 1474 INTERNAL_IP4_NETMASK, 1475 INTERNAL_IP4_DNS, 1476 INTERNAL_IP4_NBNS, 1477 INTERNAL_ADDRESS_EXPIRY, 1478 APPLICATION_VERSION, 1479 UNITY_BANNER, 1480 UNITY_DEF_DOMAIN, 1481 UNITY_SPLITDNS_NAME, 1482 UNITY_SPLIT_INCLUDE, 1483 UNITY_LOCAL_LAN, 1484 }; 1485 1486 attrcount = sizeof(attrlist) / sizeof(*attrlist); 1487 len = sizeof(*attrpl) + sizeof(*attr) * attrcount; 1488 1489 if (iph1->started_by_api) { 1490 if (iph1->remote->ss_family == AF_INET) { 1491 struct vpnctl_socket_elem *sock_elem; 1492 struct bound_addr *bound_addr; 1493 u_int32_t address; 1494 1495 address = ((struct sockaddr_in *)iph1->remote)->sin_addr.s_addr; 1496 LIST_FOREACH(sock_elem, &lcconf->vpnctl_comm_socks, chain) { 1497 LIST_FOREACH(bound_addr, &sock_elem->bound_addresses, chain) { 1498 if (bound_addr->address == address) { 1499 if ((version = bound_addr->version)) 1500 len += bound_addr->version->l; 1501 break; 1502 } 1503 } 1504 } 1505 } 1506 } 1507 1508 if ((buffer = vmalloc(len)) == NULL) { 1509 plog(ASL_LEVEL_ERR, "Cannot allocate memory\n"); 1510 return -1; 1511 } 1512 1513 attrpl = (struct isakmp_pl_attr *)buffer->v; 1514 attrpl->h.len = htons(len); 1515 attrpl->type = ISAKMP_CFG_REQUEST; 1516 attrpl->id = htons((u_int16_t)(eay_random() & 0xffff)); 1517 1518 attr = (struct isakmp_data *)(attrpl + 1); 1519 1520 for (i = 0; i < attrcount; i++) { 1521 switch (attrlist[i]) { 1522 case APPLICATION_VERSION: 1523 if (version) { 1524 attr->type = htons(attrlist[i]); 1525 attr->lorv = htons(version->l); 1526 memcpy(attr + 1, version->v, version->l); 1527 attr = (struct isakmp_data *)(((char *)(attr + 1)) + version->l); 1528 break; 1529 } else /* fall thru */; 1530 default: 1531 attr->type = htons(attrlist[i]); 1532 attr->lorv = htons(0); 1533 attr++; 1534 break; 1535 } 1536 } 1537 1538 plog(ASL_LEVEL_DEBUG, 1539 "Sending MODE_CFG REQUEST\n"); 1540 1541 error = isakmp_cfg_send(iph1, buffer, 1542 ISAKMP_NPTYPE_ATTR, ISAKMP_FLAG_E, 1, iph1->rmconf->retry_counter, NULL); 1543 1544 vfree(buffer); 1545 1546 IPSECLOGASLMSG("IPSec Network Configuration requested.\n"); 1547 1548 return error; 1549} 1550 1551static void 1552isakmp_cfg_getaddr4(attr, ip) 1553 struct isakmp_data *attr; 1554 struct in_addr *ip; 1555{ 1556 size_t alen = ntohs(attr->lorv); 1557 in_addr_t *addr; 1558 1559 if (alen != sizeof(*ip)) { 1560 plog(ASL_LEVEL_ERR, "Bad IPv4 address len\n"); 1561 return; 1562 } 1563 1564 addr = ALIGNED_CAST(in_addr_t *)(attr + 1); // Wcast-align fix (void*) - attr comes from packet data in a vchar_t 1565 ip->s_addr = *addr; 1566 1567 return; 1568} 1569 1570static void 1571isakmp_cfg_appendaddr4(attr, ip, num, max) 1572 struct isakmp_data *attr; 1573 struct in_addr *ip; 1574 int *num; 1575 int max; 1576{ 1577 size_t alen = ntohs(attr->lorv); 1578 in_addr_t *addr; 1579 1580 if (alen != sizeof(*ip)) { 1581 plog(ASL_LEVEL_ERR, "Bad IPv4 address len\n"); 1582 return; 1583 } 1584 if (*num == max) { 1585 plog(ASL_LEVEL_ERR, "Too many addresses given\n"); 1586 return; 1587 } 1588 1589 addr = ALIGNED_CAST(in_addr_t *)(attr + 1); // Wcast-align fix (void*) - attr comes from packet data in a vchar_t 1590 ip->s_addr = *addr; 1591 (*num)++; 1592 1593 return; 1594} 1595 1596static void 1597isakmp_cfg_getstring(attr, str) 1598 struct isakmp_data *attr; 1599 char *str; 1600{ 1601 size_t alen = ntohs(attr->lorv); 1602 char *src; 1603 src = (char *)(attr + 1); 1604 1605 memcpy(str, src, (alen > MAXPATHLEN ? MAXPATHLEN : alen)); 1606 1607 return; 1608} 1609 1610#define IP_MAX 40 1611 1612void 1613isakmp_cfg_iplist_to_str(dest, count, addr, withmask) 1614 char *dest; 1615 int count; 1616 void *addr; 1617 int withmask; 1618{ 1619 int i; 1620 int p; 1621 int l; 1622 struct unity_network tmp; 1623 for(i = 0, p = 0; i < count; i++) { 1624 if(withmask == 1) 1625 l = sizeof(struct unity_network); 1626 else 1627 l = sizeof(struct in_addr); 1628 memcpy(&tmp, addr, l); 1629 addr += l; 1630 if((uint32_t)tmp.addr4.s_addr == 0) 1631 break; 1632 1633 inet_ntop(AF_INET, &tmp.addr4, dest + p, IP_MAX); 1634 p += strlen(dest + p); 1635 if(withmask == 1) { 1636 dest[p] = '/'; 1637 p++; 1638 inet_ntop(AF_INET, &tmp.mask4, dest + p, IP_MAX); 1639 p += strlen(dest + p); 1640 } 1641 dest[p] = ' '; 1642 p++; 1643 } 1644 if(p > 0) 1645 dest[p-1] = '\0'; 1646 else 1647 dest[0] = '\0'; 1648} 1649 1650int 1651isakmp_cfg_resize_pool(size) 1652 int size; 1653{ 1654 struct isakmp_cfg_port *new_pool; 1655 size_t len; 1656 int i; 1657 1658 if (size == isakmp_cfg_config.pool_size) 1659 return 0; 1660 1661 plog(ASL_LEVEL_INFO, 1662 "Resize address pool from %zu to %d\n", 1663 isakmp_cfg_config.pool_size, size); 1664 1665 /* If a pool already exists, check if we can shrink it */ 1666 if ((isakmp_cfg_config.port_pool != NULL) && 1667 (size < isakmp_cfg_config.pool_size)) { 1668 for (i = isakmp_cfg_config.pool_size-1; i >= size; --i) { 1669 if (isakmp_cfg_config.port_pool[i].used) { 1670 plog(ASL_LEVEL_ERR, 1671 "resize pool from %zu to %d impossible " 1672 "port %d is in use\n", 1673 isakmp_cfg_config.pool_size, size, i); 1674 size = i; 1675 break; 1676 } 1677 } 1678 } 1679 1680 len = size * sizeof(*isakmp_cfg_config.port_pool); 1681 new_pool = racoon_realloc(isakmp_cfg_config.port_pool, len); 1682 if (new_pool == NULL) { 1683 plog(ASL_LEVEL_ERR, 1684 "resize pool from %zu to %d impossible: %s", 1685 isakmp_cfg_config.pool_size, size, strerror(errno)); 1686 return -1; 1687 } 1688 1689 /* If size increase, intialize correctly the new records */ 1690 if (size > isakmp_cfg_config.pool_size) { 1691 size_t unit; 1692 size_t old_size; 1693 1694 unit = sizeof(*isakmp_cfg_config.port_pool); 1695 old_size = isakmp_cfg_config.pool_size; 1696 1697 bzero((char *)new_pool + (old_size * unit), 1698 (size - old_size) * unit); 1699 } 1700 1701 isakmp_cfg_config.port_pool = new_pool; 1702 isakmp_cfg_config.pool_size = size; 1703 1704 return 0; 1705} 1706 1707int 1708isakmp_cfg_init(cold) 1709 int cold; 1710{ 1711 int i; 1712#if 0 1713 int error; 1714#endif 1715 1716 isakmp_cfg_config.network4 = (in_addr_t)0x00000000; 1717 isakmp_cfg_config.netmask4 = (in_addr_t)0x00000000; 1718 for (i = 0; i < MAXNS; i++) 1719 isakmp_cfg_config.dns4[i] = (in_addr_t)0x00000000; 1720 isakmp_cfg_config.dns4_index = 0; 1721 for (i = 0; i < MAXWINS; i++) 1722 isakmp_cfg_config.nbns4[i] = (in_addr_t)0x00000000; 1723 isakmp_cfg_config.nbns4_index = 0; 1724 if (cold != ISAKMP_CFG_INIT_COLD) { 1725 if (isakmp_cfg_config.port_pool) { 1726 racoon_free(isakmp_cfg_config.port_pool); 1727 } 1728 } 1729 isakmp_cfg_config.port_pool = NULL; 1730 isakmp_cfg_config.pool_size = 0; 1731 isakmp_cfg_config.authsource = ISAKMP_CFG_AUTH_SYSTEM; 1732 isakmp_cfg_config.groupsource = ISAKMP_CFG_GROUP_SYSTEM; 1733 if (cold != ISAKMP_CFG_INIT_COLD) { 1734 if (isakmp_cfg_config.grouplist != NULL) { 1735 for (i = 0; i < isakmp_cfg_config.groupcount; i++) 1736 racoon_free(isakmp_cfg_config.grouplist[i]); 1737 racoon_free(isakmp_cfg_config.grouplist); 1738 } 1739 } 1740 isakmp_cfg_config.grouplist = NULL; 1741 isakmp_cfg_config.groupcount = 0; 1742 isakmp_cfg_config.confsource = ISAKMP_CFG_CONF_LOCAL; 1743 isakmp_cfg_config.accounting = ISAKMP_CFG_ACCT_NONE; 1744 isakmp_cfg_config.auth_throttle = THROTTLE_PENALTY; 1745 strlcpy(isakmp_cfg_config.default_domain, ISAKMP_CFG_DEFAULT_DOMAIN, 1746 sizeof(isakmp_cfg_config.default_domain)); 1747 strlcpy(isakmp_cfg_config.motd, ISAKMP_CFG_MOTD, sizeof(isakmp_cfg_config.motd)); 1748 1749 if (cold != ISAKMP_CFG_INIT_COLD ) 1750 if (isakmp_cfg_config.splitnet_list != NULL) 1751 splitnet_list_free(isakmp_cfg_config.splitnet_list, 1752 &isakmp_cfg_config.splitnet_count); 1753 isakmp_cfg_config.splitnet_list = NULL; 1754 isakmp_cfg_config.splitnet_count = 0; 1755 isakmp_cfg_config.splitnet_type = 0; 1756 1757 isakmp_cfg_config.pfs_group = 0; 1758 isakmp_cfg_config.save_passwd = 0; 1759 1760 if (cold != ISAKMP_CFG_INIT_COLD ) 1761 if (isakmp_cfg_config.splitdns_list != NULL) 1762 racoon_free(isakmp_cfg_config.splitdns_list); 1763 isakmp_cfg_config.splitdns_list = NULL; 1764 isakmp_cfg_config.splitdns_len = 0; 1765 1766#if 0 1767 if (cold == ISAKMP_CFG_INIT_COLD) { 1768 if ((error = isakmp_cfg_resize_pool(ISAKMP_CFG_MAX_CNX)) != 0) 1769 return error; 1770 } 1771#endif 1772 1773 return 0; 1774} 1775 1776