Home | History | Annotate | Download | only in racoon
      1 /*	$NetBSD: localconf.c,v 1.4 2006/09/09 16:22:09 manu Exp $	*/
      2 
      3 /*	$KAME: localconf.c,v 1.33 2001/08/09 07:32:19 sakane 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 #include "config.h"
     35 
     36 #include <sys/types.h>
     37 #include <sys/param.h>
     38 
     39 #include <stdlib.h>
     40 #include <stdio.h>
     41 #include <string.h>
     42 #include <errno.h>
     43 #include <ctype.h>
     44 #include <err.h>
     45 
     46 #include "var.h"
     47 #include "misc.h"
     48 #include "vmbuf.h"
     49 #include "plog.h"
     50 #include "debug.h"
     51 
     52 #include "localconf.h"
     53 #include "algorithm.h"
     54 #include "admin.h"
     55 #include "privsep.h"
     56 #include "isakmp_var.h"
     57 #include "isakmp.h"
     58 #include "ipsec_doi.h"
     59 #include "grabmyaddr.h"
     60 #include "vendorid.h"
     61 #include "str2val.h"
     62 #include "safefile.h"
     63 #include "admin.h"
     64 #include "gcmalloc.h"
     65 
     66 struct localconf *lcconf;
     67 
     68 static void setdefault __P((void));
     69 
     70 void
     71 initlcconf()
     72 {
     73 	lcconf = racoon_calloc(1, sizeof(*lcconf));
     74 	if (lcconf == NULL)
     75 		errx(1, "failed to allocate local conf.");
     76 
     77 	setdefault();
     78 
     79 	lcconf->racoon_conf = LC_DEFAULT_CF;
     80 }
     81 
     82 void
     83 flushlcconf()
     84 {
     85 	int i;
     86 
     87 	setdefault();
     88 	clear_myaddr(&lcconf->myaddrs);
     89 	for (i = 0; i < LC_PATHTYPE_MAX; i++) {
     90 		if (lcconf->pathinfo[i]) {
     91 			racoon_free(lcconf->pathinfo[i]);
     92 			lcconf->pathinfo[i] = NULL;
     93 		}
     94 	}
     95 	for (i = 0; i < LC_IDENTTYPE_MAX; i++) {
     96 		if (lcconf->ident[i])
     97 			vfree(lcconf->ident[i]);
     98 		lcconf->ident[i] = NULL;
     99 	}
    100 }
    101 
    102 static void
    103 setdefault()
    104 {
    105 	lcconf->uid = 0;
    106 	lcconf->gid = 0;
    107 	lcconf->chroot = NULL;
    108 	lcconf->autograbaddr = 1;
    109 	lcconf->port_isakmp = PORT_ISAKMP;
    110 	lcconf->port_isakmp_natt = PORT_ISAKMP_NATT;
    111 	lcconf->default_af = AF_INET;
    112 	lcconf->pad_random = LC_DEFAULT_PAD_RANDOM;
    113 	lcconf->pad_randomlen = LC_DEFAULT_PAD_RANDOMLEN;
    114 	lcconf->pad_maxsize = LC_DEFAULT_PAD_MAXSIZE;
    115 	lcconf->pad_strict = LC_DEFAULT_PAD_STRICT;
    116 	lcconf->pad_excltail = LC_DEFAULT_PAD_EXCLTAIL;
    117 	lcconf->retry_counter = LC_DEFAULT_RETRY_COUNTER;
    118 	lcconf->retry_interval = LC_DEFAULT_RETRY_INTERVAL;
    119 	lcconf->count_persend = LC_DEFAULT_COUNT_PERSEND;
    120 	lcconf->secret_size = LC_DEFAULT_SECRETSIZE;
    121 	lcconf->retry_checkph1 = LC_DEFAULT_RETRY_CHECKPH1;
    122 	lcconf->wait_ph2complete = LC_DEFAULT_WAIT_PH2COMPLETE;
    123 	lcconf->strict_address = FALSE;
    124 	lcconf->complex_bundle = TRUE; /*XXX FALSE;*/
    125 	lcconf->gss_id_enc = LC_GSSENC_UTF16LE; /* Windows compatibility */
    126 	lcconf->natt_ka_interval = LC_DEFAULT_NATT_KA_INTERVAL;
    127 }
    128 
    129 /*
    130  * get PSK by string.
    131  */
    132 vchar_t *
    133 getpskbyname(id0)
    134 	vchar_t *id0;
    135 {
    136 	char *id;
    137 	vchar_t *key = NULL;
    138 
    139 	id = racoon_calloc(1, 1 + id0->l - sizeof(struct ipsecdoi_id_b));
    140 	if (id == NULL) {
    141 		plog(LLV_ERROR, LOCATION, NULL,
    142 			"failed to get psk buffer.\n");
    143 		goto end;
    144 	}
    145 	memcpy(id, id0->v + sizeof(struct ipsecdoi_id_b),
    146 		id0->l - sizeof(struct ipsecdoi_id_b));
    147 	id[id0->l - sizeof(struct ipsecdoi_id_b)] = '\0';
    148 
    149 	key = privsep_getpsk(id, id0->l - sizeof(struct ipsecdoi_id_b));
    150 
    151 end:
    152 	if (id)
    153 		racoon_free(id);
    154 	return key;
    155 }
    156 
    157 /*
    158  * get PSK by address.
    159  */
    160 vchar_t *
    161 getpskbyaddr(remote)
    162 	struct sockaddr *remote;
    163 {
    164 	vchar_t *key = NULL;
    165 	char addr[NI_MAXHOST], port[NI_MAXSERV];
    166 
    167 	GETNAMEINFO(remote, addr, port);
    168 
    169 	key = privsep_getpsk(addr, strlen(addr));
    170 
    171 	return key;
    172 }
    173 
    174 vchar_t *
    175 getpsk(str, len)
    176 	const char *str;
    177 	const int len;
    178 {
    179 	FILE *fp;
    180 	char buf[1024];	/* XXX how is variable length ? */
    181 	vchar_t *key = NULL;
    182 	char *p, *q;
    183 	size_t keylen;
    184 	char *k = NULL;
    185 
    186 	if (safefile(lcconf->pathinfo[LC_PATHTYPE_PSK], 1) == 0)
    187 		fp = fopen(lcconf->pathinfo[LC_PATHTYPE_PSK], "r");
    188 	else
    189 		fp = NULL;
    190 	if (fp == NULL) {
    191 		plog(LLV_ERROR, LOCATION, NULL,
    192 			"failed to open pre_share_key file %s\n",
    193 			lcconf->pathinfo[LC_PATHTYPE_PSK]);
    194 		return NULL;
    195 	}
    196 
    197 	while (fgets(buf, sizeof(buf), fp) != NULL) {
    198 		/* comment line */
    199 		if (buf[0] == '#')
    200 			continue;
    201 
    202 		/* search the end of 1st string. */
    203 		for (p = buf; *p != '\0' && !isspace((int)*p); p++)
    204 			;
    205 		if (*p == '\0')
    206 			continue;	/* no 2nd parameter */
    207 		*p = '\0';
    208 		/* search the 1st of 2nd string. */
    209 		while (isspace((int)*++p))
    210 			;
    211 		if (*p == '\0')
    212 			continue;	/* no 2nd parameter */
    213 		p--;
    214 		if (strncmp(buf, str, len) == 0 && buf[len] == '\0') {
    215 			p++;
    216 			keylen = 0;
    217 			for (q = p; *q != '\0' && *q != '\n'; q++)
    218 				keylen++;
    219 			*q = '\0';
    220 
    221 			/* fix key if hex string */
    222 			if (strncmp(p, "0x", 2) == 0) {
    223 				k = str2val(p + 2, 16, &keylen);
    224 				if (k == NULL) {
    225 					plog(LLV_ERROR, LOCATION, NULL,
    226 						"failed to get psk buffer.\n");
    227 					goto end;
    228 				}
    229 				p = k;
    230 			}
    231 
    232 			key = vmalloc(keylen);
    233 			if (key == NULL) {
    234 				plog(LLV_ERROR, LOCATION, NULL,
    235 					"failed to allocate key buffer.\n");
    236 				goto end;
    237 			}
    238 			memcpy(key->v, p, key->l);
    239 			if (k)
    240 				racoon_free(k);
    241 			goto end;
    242 		}
    243 	}
    244 
    245 end:
    246 	fclose(fp);
    247 	return key;
    248 }
    249 
    250 /*
    251  * get a file name of a type specified.
    252  */
    253 void
    254 getpathname(path, len, type, name)
    255 	char *path;
    256 	int len, type;
    257 	const char *name;
    258 {
    259 	snprintf(path, len, "%s%s%s",
    260 		name[0] == '/' ? "" : lcconf->pathinfo[type],
    261 		name[0] == '/' ? "" : "/",
    262 		name);
    263 
    264 	plog(LLV_DEBUG, LOCATION, NULL, "filename: %s\n", path);
    265 }
    266 
    267 #if 0 /* DELETEIT */
    268 static int lc_doi2idtype[] = {
    269 	-1,
    270 	-1,
    271 	LC_IDENTTYPE_FQDN,
    272 	LC_IDENTTYPE_USERFQDN,
    273 	-1,
    274 	-1,
    275 	-1,
    276 	-1,
    277 	-1,
    278 	LC_IDENTTYPE_CERTNAME,
    279 	-1,
    280 	LC_IDENTTYPE_KEYID,
    281 };
    282 
    283 /*
    284  * convert DOI value to idtype
    285  * OUT	-1   : NG
    286  *	other: converted.
    287  */
    288 int
    289 doi2idtype(idtype)
    290 	int idtype;
    291 {
    292 	if (ARRAYLEN(lc_doi2idtype) > idtype)
    293 		return lc_doi2idtype[idtype];
    294 	return -1;
    295 }
    296 #endif
    297 
    298 static int lc_sittype2doi[] = {
    299 	IPSECDOI_SIT_IDENTITY_ONLY,
    300 	IPSECDOI_SIT_SECRECY,
    301 	IPSECDOI_SIT_INTEGRITY,
    302 };
    303 
    304 /*
    305  * convert sittype to DOI value.
    306  * OUT	-1   : NG
    307  *	other: converted.
    308  */
    309 int
    310 sittype2doi(sittype)
    311 	int sittype;
    312 {
    313 	if (ARRAYLEN(lc_sittype2doi) > sittype)
    314 		return lc_sittype2doi[sittype];
    315 	return -1;
    316 }
    317 
    318 static int lc_doitype2doi[] = {
    319 	IPSEC_DOI,
    320 };
    321 
    322 /*
    323  * convert doitype to DOI value.
    324  * OUT	-1   : NG
    325  *	other: converted.
    326  */
    327 int
    328 doitype2doi(doitype)
    329 	int doitype;
    330 {
    331 	if (ARRAYLEN(lc_doitype2doi) > doitype)
    332 		return lc_doitype2doi[doitype];
    333 	return -1;
    334 }
    335 
    336 
    337 
    338 static void
    339 saverestore_params(f)
    340 	int f;
    341 {
    342 	static u_int16_t s_port_isakmp;
    343 #ifdef ENABLE_ADMINPORT
    344 	static u_int16_t s_port_admin;
    345 #endif
    346 
    347 	/* 0: save, 1: restore */
    348 	if (f) {
    349 		lcconf->port_isakmp = s_port_isakmp;
    350 #ifdef ENABLE_ADMINPORT
    351 		lcconf->port_admin = s_port_admin;
    352 #endif
    353 	} else {
    354 		s_port_isakmp = lcconf->port_isakmp;
    355 #ifdef ENABLE_ADMINPORT
    356 		s_port_admin = lcconf->port_admin;
    357 #endif
    358 	}
    359 }
    360 
    361 void
    362 restore_params()
    363 {
    364 	saverestore_params(1);
    365 }
    366 
    367 void
    368 save_params()
    369 {
    370 	saverestore_params(0);
    371 }
    372