1*c3b6f8f2SDavid van Moolenbroek /* $NetBSD: ipsec.c,v 1.4 2012/01/04 16:09:43 drochner Exp $ */
2*c3b6f8f2SDavid van Moolenbroek
3*c3b6f8f2SDavid van Moolenbroek /*
4*c3b6f8f2SDavid van Moolenbroek * Copyright (C) 1999 WIDE Project.
5*c3b6f8f2SDavid van Moolenbroek * All rights reserved.
6*c3b6f8f2SDavid van Moolenbroek *
7*c3b6f8f2SDavid van Moolenbroek * Redistribution and use in source and binary forms, with or without
8*c3b6f8f2SDavid van Moolenbroek * modification, are permitted provided that the following conditions
9*c3b6f8f2SDavid van Moolenbroek * are met:
10*c3b6f8f2SDavid van Moolenbroek * 1. Redistributions of source code must retain the above copyright
11*c3b6f8f2SDavid van Moolenbroek * notice, this list of conditions and the following disclaimer.
12*c3b6f8f2SDavid van Moolenbroek * 2. Redistributions in binary form must reproduce the above copyright
13*c3b6f8f2SDavid van Moolenbroek * notice, this list of conditions and the following disclaimer in the
14*c3b6f8f2SDavid van Moolenbroek * documentation and/or other materials provided with the distribution.
15*c3b6f8f2SDavid van Moolenbroek * 3. Neither the name of the project nor the names of its contributors
16*c3b6f8f2SDavid van Moolenbroek * may be used to endorse or promote products derived from this software
17*c3b6f8f2SDavid van Moolenbroek * without specific prior written permission.
18*c3b6f8f2SDavid van Moolenbroek *
19*c3b6f8f2SDavid van Moolenbroek * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
20*c3b6f8f2SDavid van Moolenbroek * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21*c3b6f8f2SDavid van Moolenbroek * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22*c3b6f8f2SDavid van Moolenbroek * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
23*c3b6f8f2SDavid van Moolenbroek * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
24*c3b6f8f2SDavid van Moolenbroek * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
25*c3b6f8f2SDavid van Moolenbroek * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
26*c3b6f8f2SDavid van Moolenbroek * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
27*c3b6f8f2SDavid van Moolenbroek * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
28*c3b6f8f2SDavid van Moolenbroek * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
29*c3b6f8f2SDavid van Moolenbroek * SUCH DAMAGE.
30*c3b6f8f2SDavid van Moolenbroek */
31*c3b6f8f2SDavid van Moolenbroek
32*c3b6f8f2SDavid van Moolenbroek #include <sys/param.h>
33*c3b6f8f2SDavid van Moolenbroek #include <sys/stat.h>
34*c3b6f8f2SDavid van Moolenbroek #include <sys/socket.h>
35*c3b6f8f2SDavid van Moolenbroek
36*c3b6f8f2SDavid van Moolenbroek #include <netinet/in.h>
37*c3b6f8f2SDavid van Moolenbroek #include <arpa/inet.h>
38*c3b6f8f2SDavid van Moolenbroek
39*c3b6f8f2SDavid van Moolenbroek #include <stdio.h>
40*c3b6f8f2SDavid van Moolenbroek #include <stdlib.h>
41*c3b6f8f2SDavid van Moolenbroek #include <string.h>
42*c3b6f8f2SDavid van Moolenbroek #include <unistd.h>
43*c3b6f8f2SDavid van Moolenbroek #include <ctype.h>
44*c3b6f8f2SDavid van Moolenbroek
45*c3b6f8f2SDavid van Moolenbroek #ifdef IPSEC
46*c3b6f8f2SDavid van Moolenbroek #include <netipsec/ipsec.h>
47*c3b6f8f2SDavid van Moolenbroek #ifndef IPSEC_POLICY_IPSEC /* no ipsec support on old ipsec */
48*c3b6f8f2SDavid van Moolenbroek #undef IPSEC
49*c3b6f8f2SDavid van Moolenbroek #endif
50*c3b6f8f2SDavid van Moolenbroek #endif
51*c3b6f8f2SDavid van Moolenbroek
52*c3b6f8f2SDavid van Moolenbroek #include "ipsec.h"
53*c3b6f8f2SDavid van Moolenbroek
54*c3b6f8f2SDavid van Moolenbroek #ifdef IPSEC
55*c3b6f8f2SDavid van Moolenbroek int
ipsecsetup(int af,int fd,const char * policy)56*c3b6f8f2SDavid van Moolenbroek ipsecsetup(int af, int fd, const char *policy)
57*c3b6f8f2SDavid van Moolenbroek {
58*c3b6f8f2SDavid van Moolenbroek char *p0, *p;
59*c3b6f8f2SDavid van Moolenbroek int error;
60*c3b6f8f2SDavid van Moolenbroek
61*c3b6f8f2SDavid van Moolenbroek if (!policy || policy == '\0')
62*c3b6f8f2SDavid van Moolenbroek p0 = p = strdup("in entrust; out entrust");
63*c3b6f8f2SDavid van Moolenbroek else
64*c3b6f8f2SDavid van Moolenbroek p0 = p = strdup(policy);
65*c3b6f8f2SDavid van Moolenbroek
66*c3b6f8f2SDavid van Moolenbroek error = 0;
67*c3b6f8f2SDavid van Moolenbroek for (;;) {
68*c3b6f8f2SDavid van Moolenbroek p = strtok(p, ";");
69*c3b6f8f2SDavid van Moolenbroek if (p == NULL)
70*c3b6f8f2SDavid van Moolenbroek break;
71*c3b6f8f2SDavid van Moolenbroek while (*p && isspace((unsigned char)*p))
72*c3b6f8f2SDavid van Moolenbroek p++;
73*c3b6f8f2SDavid van Moolenbroek if (!*p) {
74*c3b6f8f2SDavid van Moolenbroek p = NULL;
75*c3b6f8f2SDavid van Moolenbroek continue;
76*c3b6f8f2SDavid van Moolenbroek }
77*c3b6f8f2SDavid van Moolenbroek error = ipsecsetup0(af, fd, p, 1);
78*c3b6f8f2SDavid van Moolenbroek if (error < 0)
79*c3b6f8f2SDavid van Moolenbroek break;
80*c3b6f8f2SDavid van Moolenbroek p = NULL;
81*c3b6f8f2SDavid van Moolenbroek }
82*c3b6f8f2SDavid van Moolenbroek
83*c3b6f8f2SDavid van Moolenbroek free(p0);
84*c3b6f8f2SDavid van Moolenbroek return error;
85*c3b6f8f2SDavid van Moolenbroek }
86*c3b6f8f2SDavid van Moolenbroek
87*c3b6f8f2SDavid van Moolenbroek int
ipsecsetup_test(const char * policy)88*c3b6f8f2SDavid van Moolenbroek ipsecsetup_test(const char *policy)
89*c3b6f8f2SDavid van Moolenbroek {
90*c3b6f8f2SDavid van Moolenbroek char *p0, *p;
91*c3b6f8f2SDavid van Moolenbroek char *buf;
92*c3b6f8f2SDavid van Moolenbroek int error;
93*c3b6f8f2SDavid van Moolenbroek
94*c3b6f8f2SDavid van Moolenbroek if (!policy)
95*c3b6f8f2SDavid van Moolenbroek return -1;
96*c3b6f8f2SDavid van Moolenbroek p0 = p = strdup(policy);
97*c3b6f8f2SDavid van Moolenbroek if (p == NULL)
98*c3b6f8f2SDavid van Moolenbroek return -1;
99*c3b6f8f2SDavid van Moolenbroek
100*c3b6f8f2SDavid van Moolenbroek error = 0;
101*c3b6f8f2SDavid van Moolenbroek for (;;) {
102*c3b6f8f2SDavid van Moolenbroek p = strtok(p, ";");
103*c3b6f8f2SDavid van Moolenbroek if (p == NULL)
104*c3b6f8f2SDavid van Moolenbroek break;
105*c3b6f8f2SDavid van Moolenbroek while (*p && isspace((unsigned char)*p))
106*c3b6f8f2SDavid van Moolenbroek p++;
107*c3b6f8f2SDavid van Moolenbroek if (!*p) {
108*c3b6f8f2SDavid van Moolenbroek p = NULL;
109*c3b6f8f2SDavid van Moolenbroek continue;
110*c3b6f8f2SDavid van Moolenbroek }
111*c3b6f8f2SDavid van Moolenbroek buf = ipsec_set_policy(p, (int)strlen(p));
112*c3b6f8f2SDavid van Moolenbroek if (buf == NULL) {
113*c3b6f8f2SDavid van Moolenbroek error = -1;
114*c3b6f8f2SDavid van Moolenbroek break;
115*c3b6f8f2SDavid van Moolenbroek }
116*c3b6f8f2SDavid van Moolenbroek free(buf);
117*c3b6f8f2SDavid van Moolenbroek p = NULL;
118*c3b6f8f2SDavid van Moolenbroek }
119*c3b6f8f2SDavid van Moolenbroek
120*c3b6f8f2SDavid van Moolenbroek free(p0);
121*c3b6f8f2SDavid van Moolenbroek return error;
122*c3b6f8f2SDavid van Moolenbroek }
123*c3b6f8f2SDavid van Moolenbroek
124*c3b6f8f2SDavid van Moolenbroek int
ipsecsetup0(int af,int fd,const char * policy,int commit)125*c3b6f8f2SDavid van Moolenbroek ipsecsetup0(int af, int fd, const char *policy, int commit)
126*c3b6f8f2SDavid van Moolenbroek {
127*c3b6f8f2SDavid van Moolenbroek int level;
128*c3b6f8f2SDavid van Moolenbroek int opt;
129*c3b6f8f2SDavid van Moolenbroek char *buf;
130*c3b6f8f2SDavid van Moolenbroek int error;
131*c3b6f8f2SDavid van Moolenbroek
132*c3b6f8f2SDavid van Moolenbroek switch (af) {
133*c3b6f8f2SDavid van Moolenbroek case AF_INET:
134*c3b6f8f2SDavid van Moolenbroek level = IPPROTO_IP;
135*c3b6f8f2SDavid van Moolenbroek opt = IP_IPSEC_POLICY;
136*c3b6f8f2SDavid van Moolenbroek break;
137*c3b6f8f2SDavid van Moolenbroek #ifdef INET6
138*c3b6f8f2SDavid van Moolenbroek case AF_INET6:
139*c3b6f8f2SDavid van Moolenbroek level = IPPROTO_IPV6;
140*c3b6f8f2SDavid van Moolenbroek opt = IPV6_IPSEC_POLICY;
141*c3b6f8f2SDavid van Moolenbroek break;
142*c3b6f8f2SDavid van Moolenbroek #endif
143*c3b6f8f2SDavid van Moolenbroek default:
144*c3b6f8f2SDavid van Moolenbroek return -1;
145*c3b6f8f2SDavid van Moolenbroek }
146*c3b6f8f2SDavid van Moolenbroek
147*c3b6f8f2SDavid van Moolenbroek buf = ipsec_set_policy(policy, (int)strlen(policy));
148*c3b6f8f2SDavid van Moolenbroek if (buf != NULL) {
149*c3b6f8f2SDavid van Moolenbroek error = 0;
150*c3b6f8f2SDavid van Moolenbroek if (commit && setsockopt(fd, level, opt,
151*c3b6f8f2SDavid van Moolenbroek buf, (socklen_t)ipsec_get_policylen(buf)) < 0) {
152*c3b6f8f2SDavid van Moolenbroek error = -1;
153*c3b6f8f2SDavid van Moolenbroek }
154*c3b6f8f2SDavid van Moolenbroek free(buf);
155*c3b6f8f2SDavid van Moolenbroek } else
156*c3b6f8f2SDavid van Moolenbroek error = -1;
157*c3b6f8f2SDavid van Moolenbroek return error;
158*c3b6f8f2SDavid van Moolenbroek }
159*c3b6f8f2SDavid van Moolenbroek #endif
160