2 * Copyright (c) 2008-2015 Apple Inc. All rights reserved.
4 * @APPLE_OSREFERENCE_LICENSE_HEADER_START@
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. The rights granted to you under the License
10 * may not be used to create, or enable the creation or redistribution of,
11 * unlawful or unlicensed copies of an Apple operating system, or to
12 * circumvent, violate, or enable the circumvention or violation of, any
13 * terms of an Apple operating system software license agreement.
15 * Please obtain a copy of the License at
16 * http://www.opensource.apple.com/apsl/ and read it before using this file.
18 * The Original Code and all software distributed under the License are
19 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
20 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
21 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
22 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
23 * Please see the License for the specific language governing rights and
24 * limitations under the License.
26 * @APPLE_OSREFERENCE_LICENSE_HEADER_END@
29 /* $FreeBSD: src/sys/netinet6/ipsec.c,v 1.3.2.7 2001/07/19 06:37:23 kris Exp $ */
30 /* $KAME: ipsec.c,v 1.103 2001/05/24 07:14:18 sakane Exp $ */
33 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
34 * All rights reserved.
36 * Redistribution and use in source and binary forms, with or without
37 * modification, are permitted provided that the following conditions
39 * 1. Redistributions of source code must retain the above copyright
40 * notice, this list of conditions and the following disclaimer.
41 * 2. Redistributions in binary form must reproduce the above copyright
42 * notice, this list of conditions and the following disclaimer in the
43 * documentation and/or other materials provided with the distribution.
44 * 3. Neither the name of the project nor the names of its contributors
45 * may be used to endorse or promote products derived from this software
46 * without specific prior written permission.
48 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
49 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
50 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
51 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
52 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
53 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
54 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
55 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
56 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
57 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
62 * IPsec controller part.
65 #include <sys/param.h>
66 #include <sys/systm.h>
67 #include <sys/malloc.h>
69 #include <sys/mcache.h>
70 #include <sys/domain.h>
71 #include <sys/protosw.h>
72 #include <sys/socket.h>
73 #include <sys/socketvar.h>
74 #include <sys/errno.h>
76 #include <sys/kernel.h>
77 #include <sys/syslog.h>
78 #include <sys/sysctl.h>
79 #include <kern/locks.h>
80 #include <sys/kauth.h>
81 #include <libkern/OSAtomic.h>
84 #include <net/route.h>
85 #include <net/if_ipsec.h>
87 #include <netinet/in.h>
88 #include <netinet/in_systm.h>
89 #include <netinet/ip.h>
90 #include <netinet/ip_var.h>
91 #include <netinet/in_var.h>
92 #include <netinet/udp.h>
93 #include <netinet/udp_var.h>
94 #include <netinet/ip_ecn.h>
96 #include <netinet6/ip6_ecn.h>
98 #include <netinet/tcp.h>
99 #include <netinet/udp.h>
101 #include <netinet/ip6.h>
103 #include <netinet6/ip6_var.h>
105 #include <netinet/in_pcb.h>
107 #include <netinet/icmp6.h>
110 #include <netinet6/ipsec.h>
112 #include <netinet6/ipsec6.h>
114 #include <netinet6/ah.h>
116 #include <netinet6/ah6.h>
119 #include <netinet6/esp.h>
121 #include <netinet6/esp6.h>
124 #include <netinet6/ipcomp.h>
126 #include <netinet6/ipcomp6.h>
128 #include <netkey/key.h>
129 #include <netkey/keydb.h>
130 #include <netkey/key_debug.h>
132 #include <net/net_osdep.h>
140 #include <sys/kdebug.h>
141 #define DBG_LAYER_BEG NETDBG_CODE(DBG_NETIPSEC, 1)
142 #define DBG_LAYER_END NETDBG_CODE(DBG_NETIPSEC, 3)
143 #define DBG_FNC_GETPOL_SOCK NETDBG_CODE(DBG_NETIPSEC, (1 << 8))
144 #define DBG_FNC_GETPOL_ADDR NETDBG_CODE(DBG_NETIPSEC, (2 << 8))
145 #define DBG_FNC_IPSEC_OUT NETDBG_CODE(DBG_NETIPSEC, (3 << 8))
147 extern lck_mtx_t
*sadb_mutex
;
149 struct ipsecstat ipsecstat
;
150 int ip4_ah_cleartos
= 1;
151 int ip4_ah_offsetmask
= 0; /* maybe IP_DF? */
152 int ip4_ipsec_dfbit
= 0; /* DF bit on encap. 0: clear 1: set 2: copy */
153 int ip4_esp_trans_deflev
= IPSEC_LEVEL_USE
;
154 int ip4_esp_net_deflev
= IPSEC_LEVEL_USE
;
155 int ip4_ah_trans_deflev
= IPSEC_LEVEL_USE
;
156 int ip4_ah_net_deflev
= IPSEC_LEVEL_USE
;
157 struct secpolicy ip4_def_policy
;
158 int ip4_ipsec_ecn
= ECN_COMPATIBILITY
; /* ECN ignore(-1)/compatibility(0)/normal(1) */
159 int ip4_esp_randpad
= -1;
160 int esp_udp_encap_port
= 0;
161 static int sysctl_def_policy SYSCTL_HANDLER_ARGS
;
162 extern int natt_keepalive_interval
;
163 extern u_int32_t natt_now
;
167 SYSCTL_DECL(_net_inet_ipsec
);
169 SYSCTL_DECL(_net_inet6_ipsec6
);
172 SYSCTL_STRUCT(_net_inet_ipsec
, IPSECCTL_STATS
,
173 stats
, CTLFLAG_RD
| CTLFLAG_LOCKED
, &ipsecstat
, ipsecstat
, "");
174 SYSCTL_PROC(_net_inet_ipsec
, IPSECCTL_DEF_POLICY
, def_policy
, CTLTYPE_INT
|CTLFLAG_RW
| CTLFLAG_LOCKED
,
175 &ip4_def_policy
.policy
, 0, &sysctl_def_policy
, "I", "");
176 SYSCTL_INT(_net_inet_ipsec
, IPSECCTL_DEF_ESP_TRANSLEV
, esp_trans_deflev
,
177 CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip4_esp_trans_deflev
, 0, "");
178 SYSCTL_INT(_net_inet_ipsec
, IPSECCTL_DEF_ESP_NETLEV
, esp_net_deflev
,
179 CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip4_esp_net_deflev
, 0, "");
180 SYSCTL_INT(_net_inet_ipsec
, IPSECCTL_DEF_AH_TRANSLEV
, ah_trans_deflev
,
181 CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip4_ah_trans_deflev
, 0, "");
182 SYSCTL_INT(_net_inet_ipsec
, IPSECCTL_DEF_AH_NETLEV
, ah_net_deflev
,
183 CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip4_ah_net_deflev
, 0, "");
184 SYSCTL_INT(_net_inet_ipsec
, IPSECCTL_AH_CLEARTOS
,
185 ah_cleartos
, CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip4_ah_cleartos
, 0, "");
186 SYSCTL_INT(_net_inet_ipsec
, IPSECCTL_AH_OFFSETMASK
,
187 ah_offsetmask
, CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip4_ah_offsetmask
, 0, "");
188 SYSCTL_INT(_net_inet_ipsec
, IPSECCTL_DFBIT
,
189 dfbit
, CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip4_ipsec_dfbit
, 0, "");
190 SYSCTL_INT(_net_inet_ipsec
, IPSECCTL_ECN
,
191 ecn
, CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip4_ipsec_ecn
, 0, "");
192 SYSCTL_INT(_net_inet_ipsec
, IPSECCTL_DEBUG
,
193 debug
, CTLFLAG_RW
| CTLFLAG_LOCKED
, &ipsec_debug
, 0, "");
194 SYSCTL_INT(_net_inet_ipsec
, IPSECCTL_ESP_RANDPAD
,
195 esp_randpad
, CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip4_esp_randpad
, 0, "");
197 /* for performance, we bypass ipsec until a security policy is set */
198 int ipsec_bypass
= 1;
199 SYSCTL_INT(_net_inet_ipsec
, OID_AUTO
, bypass
, CTLFLAG_RD
| CTLFLAG_LOCKED
, &ipsec_bypass
,0, "");
202 * NAT Traversal requires a UDP port for encapsulation,
203 * esp_udp_encap_port controls which port is used. Racoon
204 * must set this port to the port racoon is using locally
207 SYSCTL_INT(_net_inet_ipsec
, OID_AUTO
, esp_port
,
208 CTLFLAG_RW
| CTLFLAG_LOCKED
, &esp_udp_encap_port
, 0, "");
211 struct ipsecstat ipsec6stat
;
212 int ip6_esp_trans_deflev
= IPSEC_LEVEL_USE
;
213 int ip6_esp_net_deflev
= IPSEC_LEVEL_USE
;
214 int ip6_ah_trans_deflev
= IPSEC_LEVEL_USE
;
215 int ip6_ah_net_deflev
= IPSEC_LEVEL_USE
;
216 struct secpolicy ip6_def_policy
;
217 int ip6_ipsec_ecn
= ECN_COMPATIBILITY
; /* ECN ignore(-1)/compatibility(0)/normal(1) */
218 int ip6_esp_randpad
= -1;
220 /* net.inet6.ipsec6 */
221 SYSCTL_STRUCT(_net_inet6_ipsec6
, IPSECCTL_STATS
,
222 stats
, CTLFLAG_RD
| CTLFLAG_LOCKED
, &ipsec6stat
, ipsecstat
, "");
223 SYSCTL_INT(_net_inet6_ipsec6
, IPSECCTL_DEF_POLICY
,
224 def_policy
, CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip6_def_policy
.policy
, 0, "");
225 SYSCTL_INT(_net_inet6_ipsec6
, IPSECCTL_DEF_ESP_TRANSLEV
, esp_trans_deflev
,
226 CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip6_esp_trans_deflev
, 0, "");
227 SYSCTL_INT(_net_inet6_ipsec6
, IPSECCTL_DEF_ESP_NETLEV
, esp_net_deflev
,
228 CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip6_esp_net_deflev
, 0, "");
229 SYSCTL_INT(_net_inet6_ipsec6
, IPSECCTL_DEF_AH_TRANSLEV
, ah_trans_deflev
,
230 CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip6_ah_trans_deflev
, 0, "");
231 SYSCTL_INT(_net_inet6_ipsec6
, IPSECCTL_DEF_AH_NETLEV
, ah_net_deflev
,
232 CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip6_ah_net_deflev
, 0, "");
233 SYSCTL_INT(_net_inet6_ipsec6
, IPSECCTL_ECN
,
234 ecn
, CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip6_ipsec_ecn
, 0, "");
235 SYSCTL_INT(_net_inet6_ipsec6
, IPSECCTL_DEBUG
,
236 debug
, CTLFLAG_RW
| CTLFLAG_LOCKED
, &ipsec_debug
, 0, "");
237 SYSCTL_INT(_net_inet6_ipsec6
, IPSECCTL_ESP_RANDPAD
,
238 esp_randpad
, CTLFLAG_RW
| CTLFLAG_LOCKED
, &ip6_esp_randpad
, 0, "");
241 static int ipsec_setspidx_interface(struct secpolicyindex
*, u_int
, struct mbuf
*,
243 static int ipsec_setspidx_mbuf(struct secpolicyindex
*, u_int
, u_int
,
245 static int ipsec4_setspidx_inpcb(struct mbuf
*, struct inpcb
*pcb
);
247 static int ipsec6_setspidx_in6pcb(struct mbuf
*, struct in6pcb
*pcb
);
249 static int ipsec_setspidx(struct mbuf
*, struct secpolicyindex
*, int, int);
250 static void ipsec4_get_ulp(struct mbuf
*m
, struct secpolicyindex
*, int);
251 static int ipsec4_setspidx_ipaddr(struct mbuf
*, struct secpolicyindex
*);
253 static void ipsec6_get_ulp(struct mbuf
*m
, struct secpolicyindex
*, int);
254 static int ipsec6_setspidx_ipaddr(struct mbuf
*, struct secpolicyindex
*);
256 static struct inpcbpolicy
*ipsec_newpcbpolicy(void);
257 static void ipsec_delpcbpolicy(struct inpcbpolicy
*);
258 static struct secpolicy
*ipsec_deepcopy_policy(struct secpolicy
*src
);
259 static int ipsec_set_policy(struct secpolicy
**pcb_sp
,
260 int optname
, caddr_t request
, size_t len
, int priv
);
261 static void vshiftl(unsigned char *, int, int);
262 static int ipsec_in_reject(struct secpolicy
*, struct mbuf
*);
264 static int ipsec64_encapsulate(struct mbuf
*, struct secasvar
*);
265 static int ipsec6_update_routecache_and_output(struct ipsec_output_state
*state
, struct secasvar
*sav
);
266 static int ipsec46_encapsulate(struct ipsec_output_state
*state
, struct secasvar
*sav
);
268 static struct ipsec_tag
*ipsec_addaux(struct mbuf
*);
269 static struct ipsec_tag
*ipsec_findaux(struct mbuf
*);
270 static void ipsec_optaux(struct mbuf
*, struct ipsec_tag
*);
271 int ipsec_send_natt_keepalive(struct secasvar
*sav
);
272 bool ipsec_fill_offload_frame(ifnet_t ifp
, struct secasvar
*sav
, struct ifnet_keepalive_offload_frame
*frame
, size_t frame_data_offset
);
275 sysctl_def_policy SYSCTL_HANDLER_ARGS
277 int old_policy
= ip4_def_policy
.policy
;
278 int error
= sysctl_handle_int(oidp
, oidp
->oid_arg1
, oidp
->oid_arg2
, req
);
280 #pragma unused(arg1, arg2)
282 if (ip4_def_policy
.policy
!= IPSEC_POLICY_NONE
&&
283 ip4_def_policy
.policy
!= IPSEC_POLICY_DISCARD
) {
284 ip4_def_policy
.policy
= old_policy
;
288 /* Turn off the bypass if the default security policy changes */
289 if (ipsec_bypass
!= 0 && ip4_def_policy
.policy
!= IPSEC_POLICY_NONE
)
296 * For OUTBOUND packet having a socket. Searching SPD for packet,
297 * and return a pointer to SP.
298 * OUT: NULL: no apropreate SP found, the following value is set to error.
300 * EACCES : discard packet.
301 * ENOENT : ipsec_acquire() in progress, maybe.
302 * others : error occurred.
303 * others: a pointer to SP
305 * NOTE: IPv6 mapped adddress concern is implemented here.
308 ipsec4_getpolicybysock(struct mbuf
*m
,
313 struct inpcbpolicy
*pcbsp
= NULL
;
314 struct secpolicy
*currsp
= NULL
; /* policy on socket */
315 struct secpolicy
*kernsp
= NULL
; /* policy on kernel */
317 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
319 if (m
== NULL
|| so
== NULL
|| error
== NULL
)
320 panic("ipsec4_getpolicybysock: NULL pointer was passed.\n");
322 if (so
->so_pcb
== NULL
) {
323 printf("ipsec4_getpolicybysock: so->so_pcb == NULL\n");
324 return ipsec4_getpolicybyaddr(m
, dir
, 0, error
);
327 switch (SOCK_DOM(so
)) {
329 pcbsp
= sotoinpcb(so
)->inp_sp
;
333 pcbsp
= sotoin6pcb(so
)->in6p_sp
;
339 /* Socket has not specified an IPSEC policy */
340 return ipsec4_getpolicybyaddr(m
, dir
, 0, error
);
343 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_START
, 0,0,0,0,0);
345 switch (SOCK_DOM(so
)) {
347 /* set spidx in pcb */
348 *error
= ipsec4_setspidx_inpcb(m
, sotoinpcb(so
));
352 /* set spidx in pcb */
353 *error
= ipsec6_setspidx_in6pcb(m
, sotoin6pcb(so
));
357 panic("ipsec4_getpolicybysock: unsupported address family\n");
360 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_END
, 1,*error
,0,0,0);
366 panic("ipsec4_getpolicybysock: pcbsp is NULL.\n");
369 case IPSEC_DIR_INBOUND
:
370 currsp
= pcbsp
->sp_in
;
372 case IPSEC_DIR_OUTBOUND
:
373 currsp
= pcbsp
->sp_out
;
376 panic("ipsec4_getpolicybysock: illegal direction.\n");
381 panic("ipsec4_getpolicybysock: currsp is NULL.\n");
383 /* when privilieged socket */
385 switch (currsp
->policy
) {
386 case IPSEC_POLICY_BYPASS
:
387 lck_mtx_lock(sadb_mutex
);
389 lck_mtx_unlock(sadb_mutex
);
391 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_END
, 2,*error
,0,0,0);
394 case IPSEC_POLICY_ENTRUST
:
395 /* look for a policy in SPD */
396 kernsp
= key_allocsp(&currsp
->spidx
, dir
);
399 if (kernsp
!= NULL
) {
400 KEYDEBUG(KEYDEBUG_IPSEC_STAMP
,
401 printf("DP ipsec4_getpolicybysock called "
402 "to allocate SP:0x%llx\n",
403 (uint64_t)VM_KERNEL_ADDRPERM(kernsp
)));
405 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_END
, 3,*error
,0,0,0);
410 lck_mtx_lock(sadb_mutex
);
411 if (ip4_def_policy
.policy
!= IPSEC_POLICY_DISCARD
412 && ip4_def_policy
.policy
!= IPSEC_POLICY_NONE
) {
414 "fixed system default policy: %d->%d\n",
415 ip4_def_policy
.policy
, IPSEC_POLICY_NONE
));
416 ip4_def_policy
.policy
= IPSEC_POLICY_NONE
;
418 ip4_def_policy
.refcnt
++;
419 lck_mtx_unlock(sadb_mutex
);
421 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_END
, 4,*error
,0,0,0);
422 return &ip4_def_policy
;
424 case IPSEC_POLICY_IPSEC
:
425 lck_mtx_lock(sadb_mutex
);
427 lck_mtx_unlock(sadb_mutex
);
429 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_END
, 5,*error
,0,0,0);
433 ipseclog((LOG_ERR
, "ipsec4_getpolicybysock: "
434 "Invalid policy for PCB %d\n", currsp
->policy
));
436 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_END
, 6,*error
,0,0,0);
442 /* when non-privilieged socket */
443 /* look for a policy in SPD */
444 kernsp
= key_allocsp(&currsp
->spidx
, dir
);
447 if (kernsp
!= NULL
) {
448 KEYDEBUG(KEYDEBUG_IPSEC_STAMP
,
449 printf("DP ipsec4_getpolicybysock called "
450 "to allocate SP:0x%llx\n",
451 (uint64_t)VM_KERNEL_ADDRPERM(kernsp
)));
453 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_END
, 7,*error
,0,0,0);
458 switch (currsp
->policy
) {
459 case IPSEC_POLICY_BYPASS
:
460 ipseclog((LOG_ERR
, "ipsec4_getpolicybysock: "
461 "Illegal policy for non-priviliged defined %d\n",
464 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_END
, 8,*error
,0,0,0);
467 case IPSEC_POLICY_ENTRUST
:
468 lck_mtx_lock(sadb_mutex
);
469 if (ip4_def_policy
.policy
!= IPSEC_POLICY_DISCARD
470 && ip4_def_policy
.policy
!= IPSEC_POLICY_NONE
) {
472 "fixed system default policy: %d->%d\n",
473 ip4_def_policy
.policy
, IPSEC_POLICY_NONE
));
474 ip4_def_policy
.policy
= IPSEC_POLICY_NONE
;
476 ip4_def_policy
.refcnt
++;
477 lck_mtx_unlock(sadb_mutex
);
479 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_END
, 9,*error
,0,0,0);
480 return &ip4_def_policy
;
482 case IPSEC_POLICY_IPSEC
:
483 lck_mtx_lock(sadb_mutex
);
485 lck_mtx_unlock(sadb_mutex
);
487 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_END
, 10,*error
,0,0,0);
491 ipseclog((LOG_ERR
, "ipsec4_getpolicybysock: "
492 "Invalid policy for PCB %d\n", currsp
->policy
));
494 KERNEL_DEBUG(DBG_FNC_GETPOL_SOCK
| DBG_FUNC_END
, 11,*error
,0,0,0);
501 * For FORWADING packet or OUTBOUND without a socket. Searching SPD for packet,
502 * and return a pointer to SP.
503 * OUT: positive: a pointer to the entry for security policy leaf matched.
504 * NULL: no apropreate SP found, the following value is set to error.
506 * EACCES : discard packet.
507 * ENOENT : ipsec_acquire() in progress, maybe.
508 * others : error occurred.
511 ipsec4_getpolicybyaddr(struct mbuf
*m
,
516 struct secpolicy
*sp
= NULL
;
518 if (ipsec_bypass
!= 0)
521 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
524 if (m
== NULL
|| error
== NULL
)
525 panic("ipsec4_getpolicybyaddr: NULL pointer was passed.\n");
527 struct secpolicyindex spidx
;
529 KERNEL_DEBUG(DBG_FNC_GETPOL_ADDR
| DBG_FUNC_START
, 0,0,0,0,0);
530 bzero(&spidx
, sizeof(spidx
));
532 /* make a index to look for a policy */
533 *error
= ipsec_setspidx_mbuf(&spidx
, dir
, AF_INET
, m
,
534 (flag
& IP_FORWARDING
) ? 0 : 1);
537 KERNEL_DEBUG(DBG_FNC_GETPOL_ADDR
| DBG_FUNC_END
, 1,*error
,0,0,0);
541 sp
= key_allocsp(&spidx
, dir
);
546 KEYDEBUG(KEYDEBUG_IPSEC_STAMP
,
547 printf("DP ipsec4_getpolicybyaddr called "
548 "to allocate SP:0x%llx\n",
549 (uint64_t)VM_KERNEL_ADDRPERM(sp
)));
551 KERNEL_DEBUG(DBG_FNC_GETPOL_ADDR
| DBG_FUNC_END
, 2,*error
,0,0,0);
556 lck_mtx_lock(sadb_mutex
);
557 if (ip4_def_policy
.policy
!= IPSEC_POLICY_DISCARD
558 && ip4_def_policy
.policy
!= IPSEC_POLICY_NONE
) {
559 ipseclog((LOG_INFO
, "fixed system default policy:%d->%d\n",
560 ip4_def_policy
.policy
,
562 ip4_def_policy
.policy
= IPSEC_POLICY_NONE
;
564 ip4_def_policy
.refcnt
++;
565 lck_mtx_unlock(sadb_mutex
);
567 KERNEL_DEBUG(DBG_FNC_GETPOL_ADDR
| DBG_FUNC_END
, 3,*error
,0,0,0);
568 return &ip4_def_policy
;
571 /* Match with bound interface rather than src addr.
572 * Unlike getpolicybyaddr, do not set the default policy.
573 * Return 0 if should continue processing, or -1 if packet
577 ipsec4_getpolicybyinterface(struct mbuf
*m
,
580 struct ip_out_args
*ipoa
,
581 struct secpolicy
**sp
)
583 struct secpolicyindex spidx
;
586 if (ipsec_bypass
!= 0)
590 if (m
== NULL
|| ipoa
== NULL
|| sp
== NULL
)
591 panic("ipsec4_getpolicybyinterface: NULL pointer was passed.\n");
593 if (ipoa
->ipoa_boundif
== IFSCOPE_NONE
)
596 KERNEL_DEBUG(DBG_FNC_GETPOL_ADDR
| DBG_FUNC_START
, 0,0,0,0,0);
597 bzero(&spidx
, sizeof(spidx
));
599 /* make a index to look for a policy */
600 error
= ipsec_setspidx_interface(&spidx
, dir
, m
, (*flags
& IP_FORWARDING
) ? 0 : 1,
601 ipoa
->ipoa_boundif
, 4);
604 KERNEL_DEBUG(DBG_FNC_GETPOL_ADDR
| DBG_FUNC_END
, 1,error
,0,0,0);
608 *sp
= key_allocsp(&spidx
, dir
);
610 /* Return SP, whether NULL or not */
611 if (*sp
!= NULL
&& (*sp
)->policy
== IPSEC_POLICY_IPSEC
) {
612 if ((*sp
)->ipsec_if
== NULL
) {
613 /* Invalid to capture on an interface without redirect */
614 key_freesp(*sp
, KEY_SADB_UNLOCKED
);
617 } else if ((*sp
)->disabled
) {
618 /* Disabled policies go in the clear */
619 key_freesp(*sp
, KEY_SADB_UNLOCKED
);
621 *flags
|= IP_NOIPSEC
; /* Avoid later IPSec check */
623 /* If policy is enabled, redirect to ipsec interface */
624 ipoa
->ipoa_boundif
= (*sp
)->ipsec_if
->if_index
;
628 KERNEL_DEBUG(DBG_FNC_GETPOL_ADDR
| DBG_FUNC_END
, 2,error
,0,0,0);
636 * For OUTBOUND packet having a socket. Searching SPD for packet,
637 * and return a pointer to SP.
638 * OUT: NULL: no apropreate SP found, the following value is set to error.
640 * EACCES : discard packet.
641 * ENOENT : ipsec_acquire() in progress, maybe.
642 * others : error occurred.
643 * others: a pointer to SP
646 ipsec6_getpolicybysock(struct mbuf
*m
,
651 struct inpcbpolicy
*pcbsp
= NULL
;
652 struct secpolicy
*currsp
= NULL
; /* policy on socket */
653 struct secpolicy
*kernsp
= NULL
; /* policy on kernel */
655 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
658 if (m
== NULL
|| so
== NULL
|| error
== NULL
)
659 panic("ipsec6_getpolicybysock: NULL pointer was passed.\n");
662 if (SOCK_DOM(so
) != PF_INET6
)
663 panic("ipsec6_getpolicybysock: socket domain != inet6\n");
666 pcbsp
= sotoin6pcb(so
)->in6p_sp
;
669 return ipsec6_getpolicybyaddr(m
, dir
, 0, error
);
672 /* set spidx in pcb */
673 ipsec6_setspidx_in6pcb(m
, sotoin6pcb(so
));
677 panic("ipsec6_getpolicybysock: pcbsp is NULL.\n");
680 case IPSEC_DIR_INBOUND
:
681 currsp
= pcbsp
->sp_in
;
683 case IPSEC_DIR_OUTBOUND
:
684 currsp
= pcbsp
->sp_out
;
687 panic("ipsec6_getpolicybysock: illegal direction.\n");
692 panic("ipsec6_getpolicybysock: currsp is NULL.\n");
694 /* when privilieged socket */
696 switch (currsp
->policy
) {
697 case IPSEC_POLICY_BYPASS
:
698 lck_mtx_lock(sadb_mutex
);
700 lck_mtx_unlock(sadb_mutex
);
704 case IPSEC_POLICY_ENTRUST
:
705 /* look for a policy in SPD */
706 kernsp
= key_allocsp(&currsp
->spidx
, dir
);
709 if (kernsp
!= NULL
) {
710 KEYDEBUG(KEYDEBUG_IPSEC_STAMP
,
711 printf("DP ipsec6_getpolicybysock called "
712 "to allocate SP:0x%llx\n",
713 (uint64_t)VM_KERNEL_ADDRPERM(kernsp
)));
719 lck_mtx_lock(sadb_mutex
);
720 if (ip6_def_policy
.policy
!= IPSEC_POLICY_DISCARD
721 && ip6_def_policy
.policy
!= IPSEC_POLICY_NONE
) {
723 "fixed system default policy: %d->%d\n",
724 ip6_def_policy
.policy
, IPSEC_POLICY_NONE
));
725 ip6_def_policy
.policy
= IPSEC_POLICY_NONE
;
727 ip6_def_policy
.refcnt
++;
728 lck_mtx_unlock(sadb_mutex
);
730 return &ip6_def_policy
;
732 case IPSEC_POLICY_IPSEC
:
733 lck_mtx_lock(sadb_mutex
);
735 lck_mtx_unlock(sadb_mutex
);
740 ipseclog((LOG_ERR
, "ipsec6_getpolicybysock: "
741 "Invalid policy for PCB %d\n", currsp
->policy
));
748 /* when non-privilieged socket */
749 /* look for a policy in SPD */
750 kernsp
= key_allocsp(&currsp
->spidx
, dir
);
753 if (kernsp
!= NULL
) {
754 KEYDEBUG(KEYDEBUG_IPSEC_STAMP
,
755 printf("DP ipsec6_getpolicybysock called "
756 "to allocate SP:0x%llx\n",
757 (uint64_t)VM_KERNEL_ADDRPERM(kernsp
)));
763 switch (currsp
->policy
) {
764 case IPSEC_POLICY_BYPASS
:
765 ipseclog((LOG_ERR
, "ipsec6_getpolicybysock: "
766 "Illegal policy for non-priviliged defined %d\n",
771 case IPSEC_POLICY_ENTRUST
:
772 lck_mtx_lock(sadb_mutex
);
773 if (ip6_def_policy
.policy
!= IPSEC_POLICY_DISCARD
774 && ip6_def_policy
.policy
!= IPSEC_POLICY_NONE
) {
776 "fixed system default policy: %d->%d\n",
777 ip6_def_policy
.policy
, IPSEC_POLICY_NONE
));
778 ip6_def_policy
.policy
= IPSEC_POLICY_NONE
;
780 ip6_def_policy
.refcnt
++;
781 lck_mtx_unlock(sadb_mutex
);
783 return &ip6_def_policy
;
785 case IPSEC_POLICY_IPSEC
:
786 lck_mtx_lock(sadb_mutex
);
788 lck_mtx_unlock(sadb_mutex
);
794 "ipsec6_policybysock: Invalid policy for PCB %d\n",
803 * For FORWADING packet or OUTBOUND without a socket. Searching SPD for packet,
804 * and return a pointer to SP.
805 * `flag' means that packet is to be forwarded whether or not.
807 * OUT: positive: a pointer to the entry for security policy leaf matched.
808 * NULL: no apropreate SP found, the following value is set to error.
810 * EACCES : discard packet.
811 * ENOENT : ipsec_acquire() in progress, maybe.
812 * others : error occurred.
814 #ifndef IP_FORWARDING
815 #define IP_FORWARDING 1
819 ipsec6_getpolicybyaddr(struct mbuf
*m
,
824 struct secpolicy
*sp
= NULL
;
826 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
829 if (m
== NULL
|| error
== NULL
)
830 panic("ipsec6_getpolicybyaddr: NULL pointer was passed.\n");
833 struct secpolicyindex spidx
;
835 bzero(&spidx
, sizeof(spidx
));
837 /* make a index to look for a policy */
838 *error
= ipsec_setspidx_mbuf(&spidx
, dir
, AF_INET6
, m
,
839 (flag
& IP_FORWARDING
) ? 0 : 1);
844 sp
= key_allocsp(&spidx
, dir
);
849 KEYDEBUG(KEYDEBUG_IPSEC_STAMP
,
850 printf("DP ipsec6_getpolicybyaddr called "
851 "to allocate SP:0x%llx\n",
852 (uint64_t)VM_KERNEL_ADDRPERM(sp
)));
858 lck_mtx_lock(sadb_mutex
);
859 if (ip6_def_policy
.policy
!= IPSEC_POLICY_DISCARD
860 && ip6_def_policy
.policy
!= IPSEC_POLICY_NONE
) {
861 ipseclog((LOG_INFO
, "fixed system default policy: %d->%d\n",
862 ip6_def_policy
.policy
, IPSEC_POLICY_NONE
));
863 ip6_def_policy
.policy
= IPSEC_POLICY_NONE
;
865 ip6_def_policy
.refcnt
++;
866 lck_mtx_unlock(sadb_mutex
);
868 return &ip6_def_policy
;
871 /* Match with bound interface rather than src addr.
872 * Unlike getpolicybyaddr, do not set the default policy.
873 * Return 0 if should continue processing, or -1 if packet
877 ipsec6_getpolicybyinterface(struct mbuf
*m
,
880 struct ip6_out_args
*ip6oap
,
882 struct secpolicy
**sp
)
884 struct secpolicyindex spidx
;
887 if (ipsec_bypass
!= 0)
891 if (m
== NULL
|| sp
== NULL
|| noipsec
== NULL
|| ip6oap
== NULL
)
892 panic("ipsec6_getpolicybyinterface: NULL pointer was passed.\n");
896 if (ip6oap
->ip6oa_boundif
== IFSCOPE_NONE
)
899 KERNEL_DEBUG(DBG_FNC_GETPOL_ADDR
| DBG_FUNC_START
, 0,0,0,0,0);
900 bzero(&spidx
, sizeof(spidx
));
902 /* make a index to look for a policy */
903 error
= ipsec_setspidx_interface(&spidx
, dir
, m
, (flag
& IP_FORWARDING
) ? 0 : 1,
904 ip6oap
->ip6oa_boundif
, 6);
907 KERNEL_DEBUG(DBG_FNC_GETPOL_ADDR
| DBG_FUNC_END
, 1,error
,0,0,0);
911 *sp
= key_allocsp(&spidx
, dir
);
913 /* Return SP, whether NULL or not */
914 if (*sp
!= NULL
&& (*sp
)->policy
== IPSEC_POLICY_IPSEC
) {
915 if ((*sp
)->ipsec_if
== NULL
) {
916 /* Invalid to capture on an interface without redirect */
917 key_freesp(*sp
, KEY_SADB_UNLOCKED
);
920 } else if ((*sp
)->disabled
) {
921 /* Disabled policies go in the clear */
922 key_freesp(*sp
, KEY_SADB_UNLOCKED
);
924 *noipsec
= 1; /* Avoid later IPSec check */
926 /* If policy is enabled, redirect to ipsec interface */
927 ip6oap
->ip6oa_boundif
= (*sp
)->ipsec_if
->if_index
;
931 KERNEL_DEBUG(DBG_FNC_GETPOL_ADDR
| DBG_FUNC_END
, 2,*error
,0,0,0);
938 * set IP address into spidx from mbuf.
939 * When Forwarding packet and ICMP echo reply, this function is used.
941 * IN: get the followings from mbuf.
942 * protocol family, src, dst, next protocol
945 * other: failure, and set errno.
949 struct secpolicyindex
*spidx
,
951 __unused u_int family
,
958 if (spidx
== NULL
|| m
== NULL
)
959 panic("ipsec_setspidx_mbuf: NULL pointer was passed.\n");
961 bzero(spidx
, sizeof(*spidx
));
963 error
= ipsec_setspidx(m
, spidx
, needport
, 0);
972 bzero(spidx
, sizeof(*spidx
));
977 ipsec_setspidx_interface(
978 struct secpolicyindex
*spidx
,
988 if (spidx
== NULL
|| m
== NULL
)
989 panic("ipsec_setspidx_interface: NULL pointer was passed.\n");
991 bzero(spidx
, sizeof(*spidx
));
993 error
= ipsec_setspidx(m
, spidx
, needport
, ip_version
);
999 ifnet_head_lock_shared();
1000 spidx
->internal_if
= ifindex2ifnet
[ifindex
];
1003 spidx
->internal_if
= NULL
;
1013 ipsec4_setspidx_inpcb(m
, pcb
)
1017 struct secpolicyindex
*spidx
;
1020 if (ipsec_bypass
!= 0)
1025 panic("ipsec4_setspidx_inpcb: no PCB found.\n");
1026 if (pcb
->inp_sp
== NULL
)
1027 panic("ipsec4_setspidx_inpcb: no inp_sp found.\n");
1028 if (pcb
->inp_sp
->sp_out
== NULL
|| pcb
->inp_sp
->sp_in
== NULL
)
1029 panic("ipsec4_setspidx_inpcb: no sp_in/out found.\n");
1031 bzero(&pcb
->inp_sp
->sp_in
->spidx
, sizeof(*spidx
));
1032 bzero(&pcb
->inp_sp
->sp_out
->spidx
, sizeof(*spidx
));
1034 spidx
= &pcb
->inp_sp
->sp_in
->spidx
;
1035 error
= ipsec_setspidx(m
, spidx
, 1, 0);
1038 spidx
->dir
= IPSEC_DIR_INBOUND
;
1040 spidx
= &pcb
->inp_sp
->sp_out
->spidx
;
1041 error
= ipsec_setspidx(m
, spidx
, 1, 0);
1044 spidx
->dir
= IPSEC_DIR_OUTBOUND
;
1049 bzero(&pcb
->inp_sp
->sp_in
->spidx
, sizeof(*spidx
));
1050 bzero(&pcb
->inp_sp
->sp_out
->spidx
, sizeof(*spidx
));
1056 ipsec6_setspidx_in6pcb(m
, pcb
)
1060 struct secpolicyindex
*spidx
;
1065 panic("ipsec6_setspidx_in6pcb: no PCB found.\n");
1066 if (pcb
->in6p_sp
== NULL
)
1067 panic("ipsec6_setspidx_in6pcb: no in6p_sp found.\n");
1068 if (pcb
->in6p_sp
->sp_out
== NULL
|| pcb
->in6p_sp
->sp_in
== NULL
)
1069 panic("ipsec6_setspidx_in6pcb: no sp_in/out found.\n");
1071 bzero(&pcb
->in6p_sp
->sp_in
->spidx
, sizeof(*spidx
));
1072 bzero(&pcb
->in6p_sp
->sp_out
->spidx
, sizeof(*spidx
));
1074 spidx
= &pcb
->in6p_sp
->sp_in
->spidx
;
1075 error
= ipsec_setspidx(m
, spidx
, 1, 0);
1078 spidx
->dir
= IPSEC_DIR_INBOUND
;
1080 spidx
= &pcb
->in6p_sp
->sp_out
->spidx
;
1081 error
= ipsec_setspidx(m
, spidx
, 1, 0);
1084 spidx
->dir
= IPSEC_DIR_OUTBOUND
;
1089 bzero(&pcb
->in6p_sp
->sp_in
->spidx
, sizeof(*spidx
));
1090 bzero(&pcb
->in6p_sp
->sp_out
->spidx
, sizeof(*spidx
));
1096 * configure security policy index (src/dst/proto/sport/dport)
1097 * by looking at the content of mbuf.
1098 * the caller is responsible for error recovery (like clearing up spidx).
1101 ipsec_setspidx(struct mbuf
*m
,
1102 struct secpolicyindex
*spidx
,
1104 int force_ip_version
)
1106 struct ip
*ip
= NULL
;
1114 panic("ipsec_setspidx: m == 0 passed.\n");
1117 * validate m->m_pkthdr.len. we see incorrect length if we
1118 * mistakenly call this function with inconsistent mbuf chain
1119 * (like 4.4BSD tcp/udp processing). XXX should we panic here?
1122 for (n
= m
; n
; n
= n
->m_next
)
1124 if (m
->m_pkthdr
.len
!= len
) {
1125 KEYDEBUG(KEYDEBUG_IPSEC_DUMP
,
1126 printf("ipsec_setspidx: "
1127 "total of m_len(%d) != pkthdr.len(%d), "
1129 len
, m
->m_pkthdr
.len
));
1133 if (m
->m_pkthdr
.len
< sizeof(struct ip
)) {
1134 KEYDEBUG(KEYDEBUG_IPSEC_DUMP
,
1135 printf("ipsec_setspidx: "
1136 "pkthdr.len(%d) < sizeof(struct ip), ignored.\n",
1141 if (m
->m_len
>= sizeof(*ip
))
1142 ip
= mtod(m
, struct ip
*);
1144 m_copydata(m
, 0, sizeof(ipbuf
), (caddr_t
)&ipbuf
);
1148 if (force_ip_version
) {
1149 v
= force_ip_version
;
1152 v
= _IP_VHL_V(ip
->ip_vhl
);
1159 error
= ipsec4_setspidx_ipaddr(m
, spidx
);
1162 ipsec4_get_ulp(m
, spidx
, needport
);
1166 if (m
->m_pkthdr
.len
< sizeof(struct ip6_hdr
)) {
1167 KEYDEBUG(KEYDEBUG_IPSEC_DUMP
,
1168 printf("ipsec_setspidx: "
1169 "pkthdr.len(%d) < sizeof(struct ip6_hdr), "
1170 "ignored.\n", m
->m_pkthdr
.len
));
1173 error
= ipsec6_setspidx_ipaddr(m
, spidx
);
1176 ipsec6_get_ulp(m
, spidx
, needport
);
1180 KEYDEBUG(KEYDEBUG_IPSEC_DUMP
,
1181 printf("ipsec_setspidx: "
1182 "unknown IP version %u, ignored.\n", v
));
1188 ipsec4_get_ulp(m
, spidx
, needport
)
1190 struct secpolicyindex
*spidx
;
1194 struct ip6_ext ip6e
;
1202 panic("ipsec4_get_ulp: NULL pointer was passed.\n");
1203 if (m
->m_pkthdr
.len
< sizeof(ip
))
1204 panic("ipsec4_get_ulp: too short\n");
1207 spidx
->ul_proto
= IPSEC_ULPROTO_ANY
;
1208 ((struct sockaddr_in
*)&spidx
->src
)->sin_port
= IPSEC_PORT_ANY
;
1209 ((struct sockaddr_in
*)&spidx
->dst
)->sin_port
= IPSEC_PORT_ANY
;
1211 m_copydata(m
, 0, sizeof(ip
), (caddr_t
)&ip
);
1212 /* ip_input() flips it into host endian XXX need more checking */
1213 if (ip
.ip_off
& (IP_MF
| IP_OFFMASK
))
1218 off
= _IP_VHL_HL(ip
->ip_vhl
) << 2;
1220 off
= ip
.ip_hl
<< 2;
1222 while (off
< m
->m_pkthdr
.len
) {
1225 spidx
->ul_proto
= nxt
;
1228 if (off
+ sizeof(struct tcphdr
) > m
->m_pkthdr
.len
)
1230 m_copydata(m
, off
, sizeof(th
), (caddr_t
)&th
);
1231 ((struct sockaddr_in
*)&spidx
->src
)->sin_port
=
1233 ((struct sockaddr_in
*)&spidx
->dst
)->sin_port
=
1237 spidx
->ul_proto
= nxt
;
1240 if (off
+ sizeof(struct udphdr
) > m
->m_pkthdr
.len
)
1242 m_copydata(m
, off
, sizeof(uh
), (caddr_t
)&uh
);
1243 ((struct sockaddr_in
*)&spidx
->src
)->sin_port
=
1245 ((struct sockaddr_in
*)&spidx
->dst
)->sin_port
=
1249 if (off
+ sizeof(ip6e
) > m
->m_pkthdr
.len
)
1251 m_copydata(m
, off
, sizeof(ip6e
), (caddr_t
)&ip6e
);
1252 off
+= (ip6e
.ip6e_len
+ 2) << 2;
1253 nxt
= ip6e
.ip6e_nxt
;
1257 /* XXX intermediate headers??? */
1258 spidx
->ul_proto
= nxt
;
1264 /* assumes that m is sane */
1266 ipsec4_setspidx_ipaddr(m
, spidx
)
1268 struct secpolicyindex
*spidx
;
1270 struct ip
*ip
= NULL
;
1272 struct sockaddr_in
*sin
;
1274 if (m
->m_len
>= sizeof(*ip
))
1275 ip
= mtod(m
, struct ip
*);
1277 m_copydata(m
, 0, sizeof(ipbuf
), (caddr_t
)&ipbuf
);
1281 sin
= (struct sockaddr_in
*)&spidx
->src
;
1282 bzero(sin
, sizeof(*sin
));
1283 sin
->sin_family
= AF_INET
;
1284 sin
->sin_len
= sizeof(struct sockaddr_in
);
1285 bcopy(&ip
->ip_src
, &sin
->sin_addr
, sizeof(ip
->ip_src
));
1286 spidx
->prefs
= sizeof(struct in_addr
) << 3;
1288 sin
= (struct sockaddr_in
*)&spidx
->dst
;
1289 bzero(sin
, sizeof(*sin
));
1290 sin
->sin_family
= AF_INET
;
1291 sin
->sin_len
= sizeof(struct sockaddr_in
);
1292 bcopy(&ip
->ip_dst
, &sin
->sin_addr
, sizeof(ip
->ip_dst
));
1293 spidx
->prefd
= sizeof(struct in_addr
) << 3;
1300 ipsec6_get_ulp(struct mbuf
*m
,
1301 struct secpolicyindex
*spidx
,
1310 panic("ipsec6_get_ulp: NULL pointer was passed.\n");
1312 KEYDEBUG(KEYDEBUG_IPSEC_DUMP
,
1313 printf("ipsec6_get_ulp:\n"); kdebug_mbuf(m
));
1316 spidx
->ul_proto
= IPSEC_ULPROTO_ANY
;
1317 ((struct sockaddr_in6
*)&spidx
->src
)->sin6_port
= IPSEC_PORT_ANY
;
1318 ((struct sockaddr_in6
*)&spidx
->dst
)->sin6_port
= IPSEC_PORT_ANY
;
1321 off
= ip6_lasthdr(m
, 0, IPPROTO_IPV6
, &nxt
);
1322 if (off
< 0 || m
->m_pkthdr
.len
< off
)
1327 spidx
->ul_proto
= nxt
;
1330 if (off
+ sizeof(struct tcphdr
) > m
->m_pkthdr
.len
)
1332 m_copydata(m
, off
, sizeof(th
), (caddr_t
)&th
);
1333 ((struct sockaddr_in6
*)&spidx
->src
)->sin6_port
= th
.th_sport
;
1334 ((struct sockaddr_in6
*)&spidx
->dst
)->sin6_port
= th
.th_dport
;
1337 spidx
->ul_proto
= nxt
;
1340 if (off
+ sizeof(struct udphdr
) > m
->m_pkthdr
.len
)
1342 m_copydata(m
, off
, sizeof(uh
), (caddr_t
)&uh
);
1343 ((struct sockaddr_in6
*)&spidx
->src
)->sin6_port
= uh
.uh_sport
;
1344 ((struct sockaddr_in6
*)&spidx
->dst
)->sin6_port
= uh
.uh_dport
;
1346 case IPPROTO_ICMPV6
:
1348 /* XXX intermediate headers??? */
1349 spidx
->ul_proto
= nxt
;
1354 /* assumes that m is sane */
1356 ipsec6_setspidx_ipaddr(struct mbuf
*m
,
1357 struct secpolicyindex
*spidx
)
1359 struct ip6_hdr
*ip6
= NULL
;
1360 struct ip6_hdr ip6buf
;
1361 struct sockaddr_in6
*sin6
;
1363 if (m
->m_len
>= sizeof(*ip6
))
1364 ip6
= mtod(m
, struct ip6_hdr
*);
1366 m_copydata(m
, 0, sizeof(ip6buf
), (caddr_t
)&ip6buf
);
1370 sin6
= (struct sockaddr_in6
*)&spidx
->src
;
1371 bzero(sin6
, sizeof(*sin6
));
1372 sin6
->sin6_family
= AF_INET6
;
1373 sin6
->sin6_len
= sizeof(struct sockaddr_in6
);
1374 bcopy(&ip6
->ip6_src
, &sin6
->sin6_addr
, sizeof(ip6
->ip6_src
));
1375 if (IN6_IS_SCOPE_LINKLOCAL(&ip6
->ip6_src
)) {
1376 sin6
->sin6_addr
.s6_addr16
[1] = 0;
1377 sin6
->sin6_scope_id
= ntohs(ip6
->ip6_src
.s6_addr16
[1]);
1379 spidx
->prefs
= sizeof(struct in6_addr
) << 3;
1381 sin6
= (struct sockaddr_in6
*)&spidx
->dst
;
1382 bzero(sin6
, sizeof(*sin6
));
1383 sin6
->sin6_family
= AF_INET6
;
1384 sin6
->sin6_len
= sizeof(struct sockaddr_in6
);
1385 bcopy(&ip6
->ip6_dst
, &sin6
->sin6_addr
, sizeof(ip6
->ip6_dst
));
1386 if (IN6_IS_SCOPE_LINKLOCAL(&ip6
->ip6_dst
)) {
1387 sin6
->sin6_addr
.s6_addr16
[1] = 0;
1388 sin6
->sin6_scope_id
= ntohs(ip6
->ip6_dst
.s6_addr16
[1]);
1390 spidx
->prefd
= sizeof(struct in6_addr
) << 3;
1396 static struct inpcbpolicy
*
1397 ipsec_newpcbpolicy()
1399 struct inpcbpolicy
*p
;
1401 p
= (struct inpcbpolicy
*)_MALLOC(sizeof(*p
), M_SECA
, M_WAITOK
);
1406 ipsec_delpcbpolicy(struct inpcbpolicy
*p
)
1411 /* initialize policy in PCB */
1413 ipsec_init_policy(struct socket
*so
,
1414 struct inpcbpolicy
**pcb_sp
)
1416 struct inpcbpolicy
*new;
1419 if (so
== NULL
|| pcb_sp
== NULL
)
1420 panic("ipsec_init_policy: NULL pointer was passed.\n");
1422 new = ipsec_newpcbpolicy();
1424 ipseclog((LOG_DEBUG
, "ipsec_init_policy: No more memory.\n"));
1427 bzero(new, sizeof(*new));
1430 if (kauth_cred_issuser(so
->so_cred
))
1432 if (so
->so_cred
!= 0 && !suser(so
->so_cred
->pc_ucred
, NULL
))
1438 if ((new->sp_in
= key_newsp()) == NULL
) {
1439 ipsec_delpcbpolicy(new);
1442 new->sp_in
->state
= IPSEC_SPSTATE_ALIVE
;
1443 new->sp_in
->policy
= IPSEC_POLICY_ENTRUST
;
1445 if ((new->sp_out
= key_newsp()) == NULL
) {
1446 key_freesp(new->sp_in
, KEY_SADB_UNLOCKED
);
1447 ipsec_delpcbpolicy(new);
1450 new->sp_out
->state
= IPSEC_SPSTATE_ALIVE
;
1451 new->sp_out
->policy
= IPSEC_POLICY_ENTRUST
;
1458 /* copy old ipsec policy into new */
1460 ipsec_copy_policy(struct inpcbpolicy
*old
,
1461 struct inpcbpolicy
*new)
1463 struct secpolicy
*sp
;
1465 if (ipsec_bypass
!= 0)
1468 sp
= ipsec_deepcopy_policy(old
->sp_in
);
1470 key_freesp(new->sp_in
, KEY_SADB_UNLOCKED
);
1475 sp
= ipsec_deepcopy_policy(old
->sp_out
);
1477 key_freesp(new->sp_out
, KEY_SADB_UNLOCKED
);
1482 new->priv
= old
->priv
;
1487 /* deep-copy a policy in PCB */
1488 static struct secpolicy
*
1489 ipsec_deepcopy_policy(struct secpolicy
*src
)
1491 struct ipsecrequest
*newchain
= NULL
;
1492 struct ipsecrequest
*p
;
1493 struct ipsecrequest
**q
;
1494 struct ipsecrequest
*r
;
1495 struct secpolicy
*dst
;
1504 * deep-copy IPsec request chain. This is required since struct
1505 * ipsecrequest is not reference counted.
1508 for (p
= src
->req
; p
; p
= p
->next
) {
1509 *q
= (struct ipsecrequest
*)_MALLOC(sizeof(struct ipsecrequest
),
1510 M_SECA
, M_WAITOK
| M_ZERO
);
1515 (*q
)->saidx
.proto
= p
->saidx
.proto
;
1516 (*q
)->saidx
.mode
= p
->saidx
.mode
;
1517 (*q
)->level
= p
->level
;
1518 (*q
)->saidx
.reqid
= p
->saidx
.reqid
;
1520 bcopy(&p
->saidx
.src
, &(*q
)->saidx
.src
, sizeof((*q
)->saidx
.src
));
1521 bcopy(&p
->saidx
.dst
, &(*q
)->saidx
.dst
, sizeof((*q
)->saidx
.dst
));
1528 dst
->req
= newchain
;
1529 dst
->state
= src
->state
;
1530 dst
->policy
= src
->policy
;
1531 /* do not touch the refcnt fields */
1536 for (p
= newchain
; p
; p
= r
) {
1541 key_freesp(dst
, KEY_SADB_UNLOCKED
);
1545 /* set policy and ipsec request if present. */
1547 ipsec_set_policy(struct secpolicy
**pcb_sp
,
1548 __unused
int optname
,
1553 struct sadb_x_policy
*xpl
;
1554 struct secpolicy
*newsp
= NULL
;
1558 if (pcb_sp
== NULL
|| *pcb_sp
== NULL
|| request
== NULL
)
1560 if (len
< sizeof(*xpl
))
1562 xpl
= (struct sadb_x_policy
*)(void *)request
;
1564 KEYDEBUG(KEYDEBUG_IPSEC_DUMP
,
1565 printf("ipsec_set_policy: passed policy\n");
1566 kdebug_sadb_x_policy((struct sadb_ext
*)xpl
));
1568 /* check policy type */
1569 /* ipsec_set_policy() accepts IPSEC, ENTRUST and BYPASS. */
1570 if (xpl
->sadb_x_policy_type
== IPSEC_POLICY_DISCARD
1571 || xpl
->sadb_x_policy_type
== IPSEC_POLICY_NONE
)
1574 /* check privileged socket */
1575 if (priv
== 0 && xpl
->sadb_x_policy_type
== IPSEC_POLICY_BYPASS
)
1578 /* allocation new SP entry */
1579 if ((newsp
= key_msg2sp(xpl
, len
, &error
)) == NULL
)
1582 newsp
->state
= IPSEC_SPSTATE_ALIVE
;
1584 /* clear old SP and set new SP */
1585 key_freesp(*pcb_sp
, KEY_SADB_UNLOCKED
);
1587 KEYDEBUG(KEYDEBUG_IPSEC_DUMP
,
1588 printf("ipsec_set_policy: new policy\n");
1589 kdebug_secpolicy(newsp
));
1595 ipsec4_set_policy(struct inpcb
*inp
,
1601 struct sadb_x_policy
*xpl
;
1602 struct secpolicy
**pcb_sp
;
1604 struct sadb_x_policy xpl_aligned_buf
;
1605 u_int8_t
*xpl_unaligned
;
1608 if (inp
== NULL
|| request
== NULL
)
1610 if (len
< sizeof(*xpl
))
1612 xpl
= (struct sadb_x_policy
*)(void *)request
;
1614 /* This is a new mbuf allocated by soopt_getm() */
1615 if (IPSEC_IS_P2ALIGNED(xpl
)) {
1616 xpl_unaligned
= NULL
;
1618 xpl_unaligned
= (__typeof__(xpl_unaligned
))xpl
;
1619 memcpy(&xpl_aligned_buf
, xpl
, sizeof(xpl_aligned_buf
));
1620 xpl
= (__typeof__(xpl
))&xpl_aligned_buf
;
1623 if (inp
->inp_sp
== NULL
) {
1624 error
= ipsec_init_policy(inp
->inp_socket
, &inp
->inp_sp
);
1629 /* select direction */
1630 switch (xpl
->sadb_x_policy_dir
) {
1631 case IPSEC_DIR_INBOUND
:
1632 pcb_sp
= &inp
->inp_sp
->sp_in
;
1634 case IPSEC_DIR_OUTBOUND
:
1635 pcb_sp
= &inp
->inp_sp
->sp_out
;
1638 ipseclog((LOG_ERR
, "ipsec4_set_policy: invalid direction=%u\n",
1639 xpl
->sadb_x_policy_dir
));
1643 /* turn bypass off */
1644 if (ipsec_bypass
!= 0)
1647 return ipsec_set_policy(pcb_sp
, optname
, request
, len
, priv
);
1650 /* delete policy in PCB */
1652 ipsec4_delete_pcbpolicy(struct inpcb
*inp
)
1657 panic("ipsec4_delete_pcbpolicy: NULL pointer was passed.\n");
1659 if (inp
->inp_sp
== NULL
)
1662 if (inp
->inp_sp
->sp_in
!= NULL
) {
1663 key_freesp(inp
->inp_sp
->sp_in
, KEY_SADB_UNLOCKED
);
1664 inp
->inp_sp
->sp_in
= NULL
;
1667 if (inp
->inp_sp
->sp_out
!= NULL
) {
1668 key_freesp(inp
->inp_sp
->sp_out
, KEY_SADB_UNLOCKED
);
1669 inp
->inp_sp
->sp_out
= NULL
;
1672 ipsec_delpcbpolicy(inp
->inp_sp
);
1680 ipsec6_set_policy(struct in6pcb
*in6p
,
1686 struct sadb_x_policy
*xpl
;
1687 struct secpolicy
**pcb_sp
;
1689 struct sadb_x_policy xpl_aligned_buf
;
1690 u_int8_t
*xpl_unaligned
;
1693 if (in6p
== NULL
|| request
== NULL
)
1695 if (len
< sizeof(*xpl
))
1697 xpl
= (struct sadb_x_policy
*)(void *)request
;
1699 /* This is a new mbuf allocated by soopt_getm() */
1700 if (IPSEC_IS_P2ALIGNED(xpl
)) {
1701 xpl_unaligned
= NULL
;
1703 xpl_unaligned
= (__typeof__(xpl_unaligned
))xpl
;
1704 memcpy(&xpl_aligned_buf
, xpl
, sizeof(xpl_aligned_buf
));
1705 xpl
= (__typeof__(xpl
))&xpl_aligned_buf
;
1708 if (in6p
->in6p_sp
== NULL
) {
1709 error
= ipsec_init_policy(in6p
->inp_socket
, &in6p
->in6p_sp
);
1714 /* select direction */
1715 switch (xpl
->sadb_x_policy_dir
) {
1716 case IPSEC_DIR_INBOUND
:
1717 pcb_sp
= &in6p
->in6p_sp
->sp_in
;
1719 case IPSEC_DIR_OUTBOUND
:
1720 pcb_sp
= &in6p
->in6p_sp
->sp_out
;
1723 ipseclog((LOG_ERR
, "ipsec6_set_policy: invalid direction=%u\n",
1724 xpl
->sadb_x_policy_dir
));
1728 return ipsec_set_policy(pcb_sp
, optname
, request
, len
, priv
);
1732 ipsec6_delete_pcbpolicy(struct in6pcb
*in6p
)
1737 panic("ipsec6_delete_pcbpolicy: NULL pointer was passed.\n");
1739 if (in6p
->in6p_sp
== NULL
)
1742 if (in6p
->in6p_sp
->sp_in
!= NULL
) {
1743 key_freesp(in6p
->in6p_sp
->sp_in
, KEY_SADB_UNLOCKED
);
1744 in6p
->in6p_sp
->sp_in
= NULL
;
1747 if (in6p
->in6p_sp
->sp_out
!= NULL
) {
1748 key_freesp(in6p
->in6p_sp
->sp_out
, KEY_SADB_UNLOCKED
);
1749 in6p
->in6p_sp
->sp_out
= NULL
;
1752 ipsec_delpcbpolicy(in6p
->in6p_sp
);
1753 in6p
->in6p_sp
= NULL
;
1760 * return current level.
1761 * Either IPSEC_LEVEL_USE or IPSEC_LEVEL_REQUIRE are always returned.
1764 ipsec_get_reqlevel(isr
)
1765 struct ipsecrequest
*isr
;
1768 u_int esp_trans_deflev
= 0, esp_net_deflev
= 0, ah_trans_deflev
= 0, ah_net_deflev
= 0;
1771 if (isr
== NULL
|| isr
->sp
== NULL
)
1772 panic("ipsec_get_reqlevel: NULL pointer is passed.\n");
1773 if (((struct sockaddr
*)&isr
->sp
->spidx
.src
)->sa_family
1774 != ((struct sockaddr
*)&isr
->sp
->spidx
.dst
)->sa_family
)
1775 panic("ipsec_get_reqlevel: family mismatched.\n");
1777 /* XXX note that we have ipseclog() expanded here - code sync issue */
1778 #define IPSEC_CHECK_DEFAULT(lev) \
1779 (((lev) != IPSEC_LEVEL_USE && (lev) != IPSEC_LEVEL_REQUIRE \
1780 && (lev) != IPSEC_LEVEL_UNIQUE) \
1782 ? log(LOG_INFO, "fixed system default level " #lev ":%d->%d\n",\
1783 (lev), IPSEC_LEVEL_REQUIRE) \
1785 (lev) = IPSEC_LEVEL_REQUIRE, \
1789 /* set default level */
1790 switch (((struct sockaddr
*)&isr
->sp
->spidx
.src
)->sa_family
) {
1793 esp_trans_deflev
= IPSEC_CHECK_DEFAULT(ip4_esp_trans_deflev
);
1794 esp_net_deflev
= IPSEC_CHECK_DEFAULT(ip4_esp_net_deflev
);
1795 ah_trans_deflev
= IPSEC_CHECK_DEFAULT(ip4_ah_trans_deflev
);
1796 ah_net_deflev
= IPSEC_CHECK_DEFAULT(ip4_ah_net_deflev
);
1801 esp_trans_deflev
= IPSEC_CHECK_DEFAULT(ip6_esp_trans_deflev
);
1802 esp_net_deflev
= IPSEC_CHECK_DEFAULT(ip6_esp_net_deflev
);
1803 ah_trans_deflev
= IPSEC_CHECK_DEFAULT(ip6_ah_trans_deflev
);
1804 ah_net_deflev
= IPSEC_CHECK_DEFAULT(ip6_ah_net_deflev
);
1808 panic("key_get_reqlevel: Unknown family. %d\n",
1809 ((struct sockaddr
*)&isr
->sp
->spidx
.src
)->sa_family
);
1812 #undef IPSEC_CHECK_DEFAULT
1815 switch (isr
->level
) {
1816 case IPSEC_LEVEL_DEFAULT
:
1817 switch (isr
->saidx
.proto
) {
1819 if (isr
->saidx
.mode
== IPSEC_MODE_TUNNEL
)
1820 level
= esp_net_deflev
;
1822 level
= esp_trans_deflev
;
1825 if (isr
->saidx
.mode
== IPSEC_MODE_TUNNEL
)
1826 level
= ah_net_deflev
;
1828 level
= ah_trans_deflev
;
1830 case IPPROTO_IPCOMP
:
1832 * we don't really care, as IPcomp document says that
1833 * we shouldn't compress small packets
1835 level
= IPSEC_LEVEL_USE
;
1838 panic("ipsec_get_reqlevel: "
1839 "Illegal protocol defined %u\n",
1844 case IPSEC_LEVEL_USE
:
1845 case IPSEC_LEVEL_REQUIRE
:
1848 case IPSEC_LEVEL_UNIQUE
:
1849 level
= IPSEC_LEVEL_REQUIRE
;
1853 panic("ipsec_get_reqlevel: Illegal IPsec level %u\n",
1861 * Check AH/ESP integrity.
1867 ipsec_in_reject(sp
, m
)
1868 struct secpolicy
*sp
;
1871 struct ipsecrequest
*isr
;
1873 int need_auth
, need_conf
, need_icv
;
1875 KEYDEBUG(KEYDEBUG_IPSEC_DATA
,
1876 printf("ipsec_in_reject: using SP\n");
1877 kdebug_secpolicy(sp
));
1880 switch (sp
->policy
) {
1881 case IPSEC_POLICY_DISCARD
:
1882 case IPSEC_POLICY_GENERATE
:
1884 case IPSEC_POLICY_BYPASS
:
1885 case IPSEC_POLICY_NONE
:
1888 case IPSEC_POLICY_IPSEC
:
1891 case IPSEC_POLICY_ENTRUST
:
1893 panic("ipsec_hdrsiz: Invalid policy found. %d\n", sp
->policy
);
1900 /* XXX should compare policy against ipsec header history */
1902 for (isr
= sp
->req
; isr
!= NULL
; isr
= isr
->next
) {
1904 /* get current level */
1905 level
= ipsec_get_reqlevel(isr
);
1907 switch (isr
->saidx
.proto
) {
1909 if (level
== IPSEC_LEVEL_REQUIRE
) {
1913 /* this won't work with multiple input threads - isr->sav would change
1914 * with every packet and is not necessarily related to the current packet
1915 * being processed. If ESP processing is required - the esp code should
1916 * make sure that the integrity check is present and correct. I don't see
1917 * why it would be necessary to check for the presence of the integrity
1918 * check value here. I think this is just wrong.
1919 * isr->sav has been removed.
1920 * %%%%%% this needs to be re-worked at some point but I think the code below can
1921 * be ignored for now.
1923 if (isr
->sav
!= NULL
1924 && isr
->sav
->flags
== SADB_X_EXT_NONE
1925 && isr
->sav
->alg_auth
!= SADB_AALG_NONE
)
1931 if (level
== IPSEC_LEVEL_REQUIRE
) {
1936 case IPPROTO_IPCOMP
:
1938 * we don't really care, as IPcomp document says that
1939 * we shouldn't compress small packets, IPComp policy
1940 * should always be treated as being in "use" level.
1946 KEYDEBUG(KEYDEBUG_IPSEC_DUMP
,
1947 printf("ipsec_in_reject: auth:%d conf:%d icv:%d m_flags:%x\n",
1948 need_auth
, need_conf
, need_icv
, m
->m_flags
));
1950 if ((need_conf
&& !(m
->m_flags
& M_DECRYPTED
))
1951 || (!need_auth
&& need_icv
&& !(m
->m_flags
& M_AUTHIPDGM
))
1952 || (need_auth
&& !(m
->m_flags
& M_AUTHIPHDR
)))
1959 * Check AH/ESP integrity.
1960 * This function is called from tcp_input(), udp_input(),
1961 * and {ah,esp}4_input for tunnel mode
1964 ipsec4_in_reject_so(m
, so
)
1968 struct secpolicy
*sp
= NULL
;
1972 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
1975 return 0; /* XXX should be panic ? */
1977 /* get SP for this packet.
1978 * When we are called from ip_forward(), we call
1979 * ipsec4_getpolicybyaddr() with IP_FORWARDING flag.
1982 sp
= ipsec4_getpolicybyaddr(m
, IPSEC_DIR_INBOUND
, IP_FORWARDING
, &error
);
1984 sp
= ipsec4_getpolicybyaddr(m
, IPSEC_DIR_INBOUND
, 0, &error
);
1987 return 0; /* XXX should be panic ?
1988 * -> No, there may be error. */
1990 result
= ipsec_in_reject(sp
, m
);
1991 KEYDEBUG(KEYDEBUG_IPSEC_STAMP
,
1992 printf("DP ipsec4_in_reject_so call free SP:0x%llx\n",
1993 (uint64_t)VM_KERNEL_ADDRPERM(sp
)));
1994 key_freesp(sp
, KEY_SADB_UNLOCKED
);
2000 ipsec4_in_reject(m
, inp
)
2005 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
2007 return ipsec4_in_reject_so(m
, NULL
);
2008 if (inp
->inp_socket
)
2009 return ipsec4_in_reject_so(m
, inp
->inp_socket
);
2011 panic("ipsec4_in_reject: invalid inpcb/socket");
2019 * Check AH/ESP integrity.
2020 * This function is called from tcp6_input(), udp6_input(),
2021 * and {ah,esp}6_input for tunnel mode
2024 ipsec6_in_reject_so(m
, so
)
2028 struct secpolicy
*sp
= NULL
;
2032 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
2035 return 0; /* XXX should be panic ? */
2037 /* get SP for this packet.
2038 * When we are called from ip_forward(), we call
2039 * ipsec6_getpolicybyaddr() with IP_FORWARDING flag.
2042 sp
= ipsec6_getpolicybyaddr(m
, IPSEC_DIR_INBOUND
, IP_FORWARDING
, &error
);
2044 sp
= ipsec6_getpolicybyaddr(m
, IPSEC_DIR_INBOUND
, 0, &error
);
2047 return 0; /* XXX should be panic ? */
2049 result
= ipsec_in_reject(sp
, m
);
2050 KEYDEBUG(KEYDEBUG_IPSEC_STAMP
,
2051 printf("DP ipsec6_in_reject_so call free SP:0x%llx\n",
2052 (uint64_t)VM_KERNEL_ADDRPERM(sp
)));
2053 key_freesp(sp
, KEY_SADB_UNLOCKED
);
2059 ipsec6_in_reject(m
, in6p
)
2061 struct in6pcb
*in6p
;
2064 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
2066 return ipsec6_in_reject_so(m
, NULL
);
2067 if (in6p
->in6p_socket
)
2068 return ipsec6_in_reject_so(m
, in6p
->in6p_socket
);
2070 panic("ipsec6_in_reject: invalid in6p/socket");
2078 * compute the byte size to be occupied by IPsec header.
2079 * in case it is tunneled, it includes the size of outer IP header.
2080 * NOTE: SP passed is free in this function.
2084 struct secpolicy
*sp
;
2086 struct ipsecrequest
*isr
;
2089 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
2090 KEYDEBUG(KEYDEBUG_IPSEC_DATA
,
2091 printf("ipsec_hdrsiz: using SP\n");
2092 kdebug_secpolicy(sp
));
2095 switch (sp
->policy
) {
2096 case IPSEC_POLICY_DISCARD
:
2097 case IPSEC_POLICY_GENERATE
:
2098 case IPSEC_POLICY_BYPASS
:
2099 case IPSEC_POLICY_NONE
:
2102 case IPSEC_POLICY_IPSEC
:
2105 case IPSEC_POLICY_ENTRUST
:
2107 panic("ipsec_hdrsiz: Invalid policy found. %d\n", sp
->policy
);
2112 for (isr
= sp
->req
; isr
!= NULL
; isr
= isr
->next
) {
2116 switch (isr
->saidx
.proto
) {
2119 clen
= esp_hdrsiz(isr
);
2125 clen
= ah_hdrsiz(isr
);
2127 case IPPROTO_IPCOMP
:
2128 clen
= sizeof(struct ipcomp
);
2132 if (isr
->saidx
.mode
== IPSEC_MODE_TUNNEL
) {
2133 switch (((struct sockaddr
*)&isr
->saidx
.dst
)->sa_family
) {
2135 clen
+= sizeof(struct ip
);
2139 clen
+= sizeof(struct ip6_hdr
);
2143 ipseclog((LOG_ERR
, "ipsec_hdrsiz: "
2144 "unknown AF %d in IPsec tunnel SA\n",
2145 ((struct sockaddr
*)&isr
->saidx
.dst
)->sa_family
));
2155 /* This function is called from ip_forward() and ipsec4_hdrsize_tcp(). */
2157 ipsec4_hdrsiz(m
, dir
, inp
)
2162 struct secpolicy
*sp
= NULL
;
2166 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
2169 return 0; /* XXX should be panic ? */
2170 if (inp
!= NULL
&& inp
->inp_socket
== NULL
)
2171 panic("ipsec4_hdrsize: why is socket NULL but there is PCB.");
2173 /* get SP for this packet.
2174 * When we are called from ip_forward(), we call
2175 * ipsec4_getpolicybyaddr() with IP_FORWARDING flag.
2178 sp
= ipsec4_getpolicybyaddr(m
, dir
, IP_FORWARDING
, &error
);
2180 sp
= ipsec4_getpolicybyaddr(m
, dir
, 0, &error
);
2183 return 0; /* XXX should be panic ? */
2185 size
= ipsec_hdrsiz(sp
);
2186 KEYDEBUG(KEYDEBUG_IPSEC_STAMP
,
2187 printf("DP ipsec4_hdrsiz call free SP:0x%llx\n",
2188 (uint64_t)VM_KERNEL_ADDRPERM(sp
)));
2189 KEYDEBUG(KEYDEBUG_IPSEC_DATA
,
2190 printf("ipsec4_hdrsiz: size:%lu.\n", (u_int32_t
)size
));
2191 key_freesp(sp
, KEY_SADB_UNLOCKED
);
2197 /* This function is called from ipsec6_hdrsize_tcp(),
2198 * and maybe from ip6_forward.()
2201 ipsec6_hdrsiz(m
, dir
, in6p
)
2204 struct in6pcb
*in6p
;
2206 struct secpolicy
*sp
= NULL
;
2210 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
2213 return 0; /* XXX shoud be panic ? */
2214 if (in6p
!= NULL
&& in6p
->in6p_socket
== NULL
)
2215 panic("ipsec6_hdrsize: why is socket NULL but there is PCB.");
2217 /* get SP for this packet */
2218 /* XXX Is it right to call with IP_FORWARDING. */
2220 sp
= ipsec6_getpolicybyaddr(m
, dir
, IP_FORWARDING
, &error
);
2222 sp
= ipsec6_getpolicybyaddr(m
, dir
, 0, &error
);
2226 size
= ipsec_hdrsiz(sp
);
2227 KEYDEBUG(KEYDEBUG_IPSEC_STAMP
,
2228 printf("DP ipsec6_hdrsiz call free SP:0x%llx\n",
2229 (uint64_t)VM_KERNEL_ADDRPERM(sp
)));
2230 KEYDEBUG(KEYDEBUG_IPSEC_DATA
,
2231 printf("ipsec6_hdrsiz: size:%lu.\n", (u_int32_t
)size
));
2232 key_freesp(sp
, KEY_SADB_UNLOCKED
);
2240 * encapsulate for ipsec tunnel.
2241 * ip->ip_src must be fixed later on.
2244 ipsec4_encapsulate(m
, sav
)
2246 struct secasvar
*sav
;
2253 /* can't tunnel between different AFs */
2254 if (((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
2255 != ((struct sockaddr
*)&sav
->sah
->saidx
.dst
)->sa_family
2256 || ((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
!= AF_INET
) {
2261 /* XXX if the dst is myself, perform nothing. */
2262 if (key_ismyaddr((struct sockaddr
*)&sav
->sah
->saidx
.dst
)) {
2268 if (m
->m_len
< sizeof(*ip
))
2269 panic("ipsec4_encapsulate: assumption failed (first mbuf length)");
2271 ip
= mtod(m
, struct ip
*);
2273 hlen
= _IP_VHL_HL(ip
->ip_vhl
) << 2;
2275 hlen
= ip
->ip_hl
<< 2;
2278 if (m
->m_len
!= hlen
)
2279 panic("ipsec4_encapsulate: assumption failed (first mbuf length)");
2281 /* generate header checksum */
2284 ip
->ip_sum
= in_cksum(m
, hlen
);
2286 ip
->ip_sum
= in_cksum(m
, hlen
);
2289 plen
= m
->m_pkthdr
.len
;
2292 * grow the mbuf to accomodate the new IPv4 header.
2293 * NOTE: IPv4 options will never be copied.
2295 if (M_LEADINGSPACE(m
->m_next
) < hlen
) {
2297 MGET(n
, M_DONTWAIT
, MT_DATA
);
2303 n
->m_next
= m
->m_next
;
2305 m
->m_pkthdr
.len
+= hlen
;
2306 oip
= mtod(n
, struct ip
*);
2308 m
->m_next
->m_len
+= hlen
;
2309 m
->m_next
->m_data
-= hlen
;
2310 m
->m_pkthdr
.len
+= hlen
;
2311 oip
= mtod(m
->m_next
, struct ip
*);
2313 ip
= mtod(m
, struct ip
*);
2314 ovbcopy((caddr_t
)ip
, (caddr_t
)oip
, hlen
);
2315 m
->m_len
= sizeof(struct ip
);
2316 m
->m_pkthdr
.len
-= (hlen
- sizeof(struct ip
));
2318 /* construct new IPv4 header. see RFC 2401 5.1.2.1 */
2319 /* ECN consideration. */
2320 ip_ecn_ingress(ip4_ipsec_ecn
, &ip
->ip_tos
, &oip
->ip_tos
);
2322 ip
->ip_vhl
= IP_MAKE_VHL(IPVERSION
, sizeof(struct ip
) >> 2);
2324 ip
->ip_hl
= sizeof(struct ip
) >> 2;
2326 ip
->ip_off
&= htons(~IP_OFFMASK
);
2327 ip
->ip_off
&= htons(~IP_MF
);
2328 switch (ip4_ipsec_dfbit
) {
2329 case 0: /* clear DF bit */
2330 ip
->ip_off
&= htons(~IP_DF
);
2332 case 1: /* set DF bit */
2333 ip
->ip_off
|= htons(IP_DF
);
2335 default: /* copy DF bit */
2338 ip
->ip_p
= IPPROTO_IPIP
;
2339 if (plen
+ sizeof(struct ip
) < IP_MAXPACKET
)
2340 ip
->ip_len
= htons(plen
+ sizeof(struct ip
));
2342 ipseclog((LOG_ERR
, "IPv4 ipsec: size exceeds limit: "
2343 "leave ip_len as is (invalid packet)\n"));
2345 ip
->ip_id
= ip_randomid();
2346 bcopy(&((struct sockaddr_in
*)&sav
->sah
->saidx
.src
)->sin_addr
,
2347 &ip
->ip_src
, sizeof(ip
->ip_src
));
2348 bcopy(&((struct sockaddr_in
*)&sav
->sah
->saidx
.dst
)->sin_addr
,
2349 &ip
->ip_dst
, sizeof(ip
->ip_dst
));
2350 ip
->ip_ttl
= IPDEFTTL
;
2352 /* XXX Should ip_src be updated later ? */
2358 * encapsulate for ipsec tunnel.
2359 * ip->ip_src must be fixed later on.
2362 ipsec4_encapsulate_utun_esp_keepalive(m_ptr
, sav
)
2363 struct mbuf
**m_ptr
;
2364 struct secasvar
*sav
;
2368 struct mbuf
*m
= *m_ptr
;
2370 /* can't tunnel between different AFs */
2371 if (((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
2372 != ((struct sockaddr
*)&sav
->sah
->saidx
.dst
)->sa_family
2373 || ((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
!= AF_INET
) {
2379 plen
= m
->m_pkthdr
.len
;
2382 * grow the mbuf to accomodate the new IPv4 header.
2383 * NOTE: IPv4 options will never be copied.
2387 MGETHDR(n
, M_DONTWAIT
, MT_HEADER
); /* MAC-OK */
2393 if (m
->m_flags
& M_PKTHDR
) {
2394 M_COPY_PKTHDR(n
, m
);
2395 m
->m_flags
&= ~M_PKTHDR
;
2397 MH_ALIGN(n
, sizeof(*ip
));
2398 n
->m_len
= sizeof(*ip
);
2400 n
->m_pkthdr
.len
= (plen
+ n
->m_len
);
2404 plen
= m
->m_pkthdr
.len
;
2406 ip
= mtod(m
, __typeof__(ip
));
2408 /* construct new IPv4 header. see RFC 2401 5.1.2.1 */
2409 // ip_ecn_ingress(ip4_ipsec_ecn, &ip->ip_tos, &oip->ip_tos);
2411 ip
->ip_vhl
= IP_MAKE_VHL(IPVERSION
, sizeof(*ip
) >> 2);
2413 ip
->ip_hl
= sizeof(*ip
) >> 2;
2415 ip
->ip_off
&= htons(~IP_OFFMASK
);
2416 ip
->ip_off
&= htons(~IP_MF
);
2417 switch (ip4_ipsec_dfbit
) {
2418 case 0: /* clear DF bit */
2419 ip
->ip_off
&= htons(~IP_DF
);
2421 case 1: /* set DF bit */
2422 ip
->ip_off
|= htons(IP_DF
);
2424 default: /* copy DF bit */
2427 ip
->ip_p
= IPPROTO_IPIP
;
2428 if (plen
< IP_MAXPACKET
)
2429 ip
->ip_len
= htons(plen
);
2431 ipseclog((LOG_ERR
, "IPv4 ipsec: size exceeds limit: "
2432 "leave ip_len as is (invalid packet)\n"));
2434 ip
->ip_id
= ip_randomid();
2435 bcopy(&((struct sockaddr_in
*)&sav
->sah
->saidx
.src
)->sin_addr
,
2436 &ip
->ip_src
, sizeof(ip
->ip_src
));
2437 bcopy(&((struct sockaddr_in
*)&sav
->sah
->saidx
.dst
)->sin_addr
,
2438 &ip
->ip_dst
, sizeof(ip
->ip_dst
));
2439 ip
->ip_ttl
= IPDEFTTL
;
2441 /* XXX Should ip_src be updated later ? */
2449 ipsec6_encapsulate(m
, sav
)
2451 struct secasvar
*sav
;
2453 struct ip6_hdr
*oip6
;
2454 struct ip6_hdr
*ip6
;
2457 /* can't tunnel between different AFs */
2458 if (((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
2459 != ((struct sockaddr
*)&sav
->sah
->saidx
.dst
)->sa_family
2460 || ((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
!= AF_INET6
) {
2465 /* XXX if the dst is myself, perform nothing. */
2466 if (key_ismyaddr((struct sockaddr
*)&sav
->sah
->saidx
.dst
)) {
2472 plen
= m
->m_pkthdr
.len
;
2475 * grow the mbuf to accomodate the new IPv6 header.
2477 if (m
->m_len
!= sizeof(struct ip6_hdr
))
2478 panic("ipsec6_encapsulate: assumption failed (first mbuf length)");
2479 if (M_LEADINGSPACE(m
->m_next
) < sizeof(struct ip6_hdr
)) {
2481 MGET(n
, M_DONTWAIT
, MT_DATA
);
2486 n
->m_len
= sizeof(struct ip6_hdr
);
2487 n
->m_next
= m
->m_next
;
2489 m
->m_pkthdr
.len
+= sizeof(struct ip6_hdr
);
2490 oip6
= mtod(n
, struct ip6_hdr
*);
2492 m
->m_next
->m_len
+= sizeof(struct ip6_hdr
);
2493 m
->m_next
->m_data
-= sizeof(struct ip6_hdr
);
2494 m
->m_pkthdr
.len
+= sizeof(struct ip6_hdr
);
2495 oip6
= mtod(m
->m_next
, struct ip6_hdr
*);
2497 ip6
= mtod(m
, struct ip6_hdr
*);
2498 ovbcopy((caddr_t
)ip6
, (caddr_t
)oip6
, sizeof(struct ip6_hdr
));
2500 /* Fake link-local scope-class addresses */
2501 if (IN6_IS_SCOPE_LINKLOCAL(&oip6
->ip6_src
))
2502 oip6
->ip6_src
.s6_addr16
[1] = 0;
2503 if (IN6_IS_SCOPE_LINKLOCAL(&oip6
->ip6_dst
))
2504 oip6
->ip6_dst
.s6_addr16
[1] = 0;
2506 /* construct new IPv6 header. see RFC 2401 5.1.2.2 */
2507 /* ECN consideration. */
2508 ip6_ecn_ingress(ip6_ipsec_ecn
, &ip6
->ip6_flow
, &oip6
->ip6_flow
);
2509 if (plen
< IPV6_MAXPACKET
- sizeof(struct ip6_hdr
))
2510 ip6
->ip6_plen
= htons(plen
);
2512 /* ip6->ip6_plen will be updated in ip6_output() */
2514 ip6
->ip6_nxt
= IPPROTO_IPV6
;
2515 bcopy(&((struct sockaddr_in6
*)&sav
->sah
->saidx
.src
)->sin6_addr
,
2516 &ip6
->ip6_src
, sizeof(ip6
->ip6_src
));
2517 bcopy(&((struct sockaddr_in6
*)&sav
->sah
->saidx
.dst
)->sin6_addr
,
2518 &ip6
->ip6_dst
, sizeof(ip6
->ip6_dst
));
2519 ip6
->ip6_hlim
= IPV6_DEFHLIM
;
2521 /* XXX Should ip6_src be updated later ? */
2527 ipsec64_encapsulate(m
, sav
)
2529 struct secasvar
*sav
;
2531 struct ip6_hdr
*ip6
, *ip6i
;
2536 /* tunneling over IPv4 */
2537 if (((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
2538 != ((struct sockaddr
*)&sav
->sah
->saidx
.dst
)->sa_family
2539 || ((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
!= AF_INET
) {
2544 /* XXX if the dst is myself, perform nothing. */
2545 if (key_ismyaddr((struct sockaddr
*)&sav
->sah
->saidx
.dst
)) {
2551 plen
= m
->m_pkthdr
.len
;
2552 ip6
= mtod(m
, struct ip6_hdr
*);
2553 hlim
= ip6
->ip6_hlim
;
2555 * grow the mbuf to accomodate the new IPv4 header.
2557 if (m
->m_len
!= sizeof(struct ip6_hdr
))
2558 panic("ipsec6_encapsulate: assumption failed (first mbuf length)");
2559 if (M_LEADINGSPACE(m
->m_next
) < sizeof(struct ip6_hdr
)) {
2561 MGET(n
, M_DONTWAIT
, MT_DATA
);
2566 n
->m_len
= sizeof(struct ip6_hdr
);
2567 n
->m_next
= m
->m_next
;
2569 m
->m_pkthdr
.len
+= sizeof(struct ip
);
2570 ip6i
= mtod(n
, struct ip6_hdr
*);
2572 m
->m_next
->m_len
+= sizeof(struct ip6_hdr
);
2573 m
->m_next
->m_data
-= sizeof(struct ip6_hdr
);
2574 m
->m_pkthdr
.len
+= sizeof(struct ip
);
2575 ip6i
= mtod(m
->m_next
, struct ip6_hdr
*);
2578 bcopy(ip6
, ip6i
, sizeof(struct ip6_hdr
));
2579 ip
= mtod(m
, struct ip
*);
2580 m
->m_len
= sizeof(struct ip
);
2582 * Fill in some of the IPv4 fields - we don't need all of them
2583 * because the rest will be filled in by ip_output
2585 ip
->ip_v
= IPVERSION
;
2586 ip
->ip_hl
= sizeof(struct ip
) >> 2;
2592 ip
->ip_p
= IPPROTO_IPV6
;
2594 /* construct new IPv4 header. see RFC 2401 5.1.2.1 */
2595 /* ECN consideration. */
2596 ip64_ecn_ingress(ip4_ipsec_ecn
, &ip
->ip_tos
, &ip6
->ip6_flow
);
2598 if (plen
+ sizeof(struct ip
) < IP_MAXPACKET
)
2599 ip
->ip_len
= htons(plen
+ sizeof(struct ip
));
2601 ip
->ip_len
= htons(plen
);
2602 ipseclog((LOG_ERR
, "IPv4 ipsec: size exceeds limit: "
2603 "leave ip_len as is (invalid packet)\n"));
2605 bcopy(&((struct sockaddr_in
*)&sav
->sah
->saidx
.src
)->sin_addr
,
2606 &ip
->ip_src
, sizeof(ip
->ip_src
));
2607 bcopy(&((struct sockaddr_in
*)&sav
->sah
->saidx
.dst
)->sin_addr
,
2608 &ip
->ip_dst
, sizeof(ip
->ip_dst
));
2614 ipsec6_encapsulate_utun_esp_keepalive(m_ptr
, sav
)
2615 struct mbuf
**m_ptr
;
2616 struct secasvar
*sav
;
2618 struct ip6_hdr
*ip6
;
2620 struct mbuf
*m
= *m_ptr
;
2622 /* can't tunnel between different AFs */
2623 if (((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
2624 != ((struct sockaddr
*)&sav
->sah
->saidx
.dst
)->sa_family
2625 || ((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
!= AF_INET6
) {
2631 plen
= m
->m_pkthdr
.len
;
2634 * grow the mbuf to accomodate the new IPv6 header.
2638 MGETHDR(n
, M_DONTWAIT
, MT_HEADER
); /* MAC-OK */
2644 if (m
->m_flags
& M_PKTHDR
) {
2645 M_COPY_PKTHDR(n
, m
);
2646 m
->m_flags
&= ~M_PKTHDR
;
2648 MH_ALIGN(n
, sizeof(*ip6
));
2649 n
->m_len
= sizeof(*ip6
);
2651 n
->m_pkthdr
.len
= (plen
+ n
->m_len
);
2655 plen
= m
->m_pkthdr
.len
;
2657 ip6
= mtod(m
, __typeof__(ip6
));
2659 /* construct new IPv6 header. see RFC 2401 5.1.2.2 */
2660 if (plen
< IPV6_MAXPACKET
)
2661 ip6
->ip6_plen
= htons(plen
);
2663 /* ip6->ip6_plen will be updated in ip6_output() */
2665 ip6
->ip6_nxt
= IPPROTO_IPV6
;
2666 bcopy(&((struct sockaddr_in6
*)&sav
->sah
->saidx
.src
)->sin6_addr
,
2667 &ip6
->ip6_src
, sizeof(ip6
->ip6_src
));
2668 bcopy(&((struct sockaddr_in6
*)&sav
->sah
->saidx
.dst
)->sin6_addr
,
2669 &ip6
->ip6_dst
, sizeof(ip6
->ip6_dst
));
2670 ip6
->ip6_hlim
= IPV6_DEFHLIM
;
2672 /* XXX Should ip6_src be updated later ? */
2678 ipsec6_update_routecache_and_output(state
, sav
)
2679 struct ipsec_output_state
*state
;
2680 struct secasvar
*sav
;
2682 struct sockaddr_in6
* dst6
;
2684 struct ip6_hdr
*ip6
;
2688 struct ip6_out_args ip6oa
;
2689 struct route_in6 ro6_new
;
2690 struct flowadv
*adv
= NULL
;
2695 ip6
= mtod(state
->m
, struct ip6_hdr
*);
2697 // grab sadb_mutex, before updating sah's route cache
2698 lck_mtx_lock(sadb_mutex
);
2699 ro6
= &sav
->sah
->sa_route
;
2700 dst6
= (struct sockaddr_in6
*)(void *)&ro6
->ro_dst
;
2702 RT_LOCK(ro6
->ro_rt
);
2704 if (ROUTE_UNUSABLE(ro6
) ||
2705 !IN6_ARE_ADDR_EQUAL(&dst6
->sin6_addr
, &ip6
->ip6_dst
)) {
2706 if (ro6
->ro_rt
!= NULL
)
2707 RT_UNLOCK(ro6
->ro_rt
);
2710 if (ro6
->ro_rt
== 0) {
2711 bzero(dst6
, sizeof(*dst6
));
2712 dst6
->sin6_family
= AF_INET6
;
2713 dst6
->sin6_len
= sizeof(*dst6
);
2714 dst6
->sin6_addr
= ip6
->ip6_dst
;
2717 RT_LOCK(ro6
->ro_rt
);
2720 if (ro6
->ro_rt
== 0) {
2721 ip6stat
.ip6s_noroute
++;
2722 IPSEC_STAT_INCREMENT(ipsec6stat
.out_noroute
);
2723 error
= EHOSTUNREACH
;
2724 // release sadb_mutex, after updating sah's route cache
2725 lck_mtx_unlock(sadb_mutex
);
2730 * adjust state->dst if tunnel endpoint is offlink
2732 * XXX: caching rt_gateway value in the state is
2733 * not really good, since it may point elsewhere
2734 * when the gateway gets modified to a larger
2735 * sockaddr via rt_setgate(). This is currently
2736 * addressed by SA_SIZE roundup in that routine.
2738 if (ro6
->ro_rt
->rt_flags
& RTF_GATEWAY
)
2739 dst6
= (struct sockaddr_in6
*)(void *)ro6
->ro_rt
->rt_gateway
;
2740 RT_UNLOCK(ro6
->ro_rt
);
2741 ROUTE_RELEASE(&state
->ro
);
2742 route_copyout(&state
->ro
, ro6
, sizeof(state
->ro
));
2743 state
->dst
= (struct sockaddr
*)dst6
;
2744 state
->tunneled
= 6;
2745 // release sadb_mutex, after updating sah's route cache
2746 lck_mtx_unlock(sadb_mutex
);
2748 state
->m
= ipsec6_splithdr(state
->m
);
2750 IPSEC_STAT_INCREMENT(ipsec6stat
.out_nomem
);
2755 ip6
= mtod(state
->m
, struct ip6_hdr
*);
2756 switch (sav
->sah
->saidx
.proto
) {
2759 error
= esp6_output(state
->m
, &ip6
->ip6_nxt
, state
->m
->m_next
, sav
);
2766 error
= ah6_output(state
->m
, &ip6
->ip6_nxt
, state
->m
->m_next
, sav
);
2768 case IPPROTO_IPCOMP
:
2769 /* XXX code should be here */
2772 ipseclog((LOG_ERR
, "%s: unknown ipsec protocol %d\n", __FUNCTION__
, sav
->sah
->saidx
.proto
));
2774 IPSEC_STAT_INCREMENT(ipsec6stat
.out_inval
);
2779 // If error, packet already freed by above output routines
2784 plen
= state
->m
->m_pkthdr
.len
- sizeof(struct ip6_hdr
);
2785 if (plen
> IPV6_MAXPACKET
) {
2786 ipseclog((LOG_ERR
, "%s: IPsec with IPv6 jumbogram is not supported\n", __FUNCTION__
));
2787 IPSEC_STAT_INCREMENT(ipsec6stat
.out_inval
);
2788 error
= EINVAL
;/*XXX*/
2791 ip6
= mtod(state
->m
, struct ip6_hdr
*);
2792 ip6
->ip6_plen
= htons(plen
);
2794 ipsec_set_pkthdr_for_interface(sav
->sah
->ipsec_if
, state
->m
, AF_INET6
);
2796 /* Increment statistics */
2797 ifnet_stat_increment_out(sav
->sah
->ipsec_if
, 1, mbuf_pkthdr_len(state
->m
), 0);
2799 /* Send to ip6_output */
2800 bzero(&ro6_new
, sizeof(ro6_new
));
2801 bzero(&ip6oa
, sizeof(ip6oa
));
2802 ip6oa
.ip6oa_flowadv
.code
= 0;
2803 ip6oa
.ip6oa_flags
= IPOAF_SELECT_SRCIF
| IPOAF_BOUND_SRCADDR
;
2804 if (state
->outgoing_if
) {
2805 ip6oa
.ip6oa_boundif
= state
->outgoing_if
;
2806 ip6oa
.ip6oa_flags
|= IPOAF_BOUND_IF
;
2809 adv
= &ip6oa
.ip6oa_flowadv
;
2810 (void) ip6_output(state
->m
, NULL
, &ro6_new
, IPV6_OUTARGS
, NULL
, NULL
, &ip6oa
);
2812 if (adv
->code
== FADV_FLOW_CONTROLLED
|| adv
->code
== FADV_SUSPENDED
) {
2814 ifnet_disable_output(sav
->sah
->ipsec_if
);
2822 ipsec46_encapsulate(state
, sav
)
2823 struct secasvar
*sav
;
2824 struct ipsec_output_state
*state
;
2827 struct ip6_hdr
*ip6
;
2838 /* can't tunnel between different AFs */
2839 if (((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
2840 != ((struct sockaddr
*)&sav
->sah
->saidx
.dst
)->sa_family
2841 || ((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
!= AF_INET6
) {
2846 /* XXX if the dst is myself, perform nothing. */
2847 if (key_ismyaddr((struct sockaddr
*)&sav
->sah
->saidx
.dst
)) {
2853 if (m
->m_len
< sizeof(*ip
)) {
2854 panic("ipsec46_encapsulate: assumption failed (first mbuf length)");
2858 ip
= mtod(m
, struct ip
*);
2860 hlen
= _IP_VHL_HL(ip
->ip_vhl
) << 2;
2862 hlen
= ip
->ip_hl
<< 2;
2865 if (m
->m_len
!= hlen
) {
2866 panic("ipsec46_encapsulate: assumption failed (first mbuf length)");
2870 /* generate header checksum */
2873 ip
->ip_sum
= in_cksum(m
, hlen
);
2875 ip
->ip_sum
= in_cksum(m
, hlen
);
2878 plen
= m
->m_pkthdr
.len
; // save original IPv4 packet len, this will be ipv6 payload len
2881 * First move the IPv4 header to the second mbuf in the chain
2883 if (M_LEADINGSPACE(m
->m_next
) < hlen
) {
2885 MGET(n
, M_DONTWAIT
, MT_DATA
);
2891 n
->m_next
= m
->m_next
;
2893 m
->m_pkthdr
.len
+= sizeof(struct ip6_hdr
);
2894 oip
= mtod(n
, struct ip
*);
2896 m
->m_next
->m_len
+= hlen
;
2897 m
->m_next
->m_data
-= hlen
;
2898 m
->m_pkthdr
.len
+= sizeof(struct ip6_hdr
);
2899 oip
= mtod(m
->m_next
, struct ip
*);
2901 ip
= mtod(m
, struct ip
*);
2902 ovbcopy((caddr_t
)ip
, (caddr_t
)oip
, hlen
);
2905 * Grow the first mbuf to accomodate the new IPv6 header.
2907 if (M_LEADINGSPACE(m
) < sizeof(struct ip6_hdr
) - hlen
) {
2909 MGETHDR(n
, M_DONTWAIT
, MT_HEADER
);
2914 M_COPY_PKTHDR(n
, m
);
2915 MH_ALIGN(n
, sizeof(struct ip6_hdr
));
2916 n
->m_len
= sizeof(struct ip6_hdr
);
2917 n
->m_next
= m
->m_next
;
2923 m
->m_len
+= (sizeof(struct ip6_hdr
) - hlen
);
2924 m
->m_data
-= (sizeof(struct ip6_hdr
) - hlen
);
2926 ip6
= mtod(m
, struct ip6_hdr
*);
2928 ip6
->ip6_vfc
&= ~IPV6_VERSION_MASK
;
2929 ip6
->ip6_vfc
|= IPV6_VERSION
;
2931 /* construct new IPv6 header. see RFC 2401 5.1.2.2 */
2932 /* ECN consideration. */
2933 ip46_ecn_ingress(ip6_ipsec_ecn
, &ip6
->ip6_flow
, &ip
->ip_tos
);
2934 if (plen
< IPV6_MAXPACKET
- sizeof(struct ip6_hdr
))
2935 ip6
->ip6_plen
= htons(plen
);
2937 /* ip6->ip6_plen will be updated in ip6_output() */
2940 ip6
->ip6_nxt
= IPPROTO_IPV4
;
2941 ip6
->ip6_hlim
= IPV6_DEFHLIM
;
2943 bcopy(&((struct sockaddr_in6
*)&sav
->sah
->saidx
.src
)->sin6_addr
,
2944 &ip6
->ip6_src
, sizeof(ip6
->ip6_src
));
2945 bcopy(&((struct sockaddr_in6
*)&sav
->sah
->saidx
.dst
)->sin6_addr
,
2946 &ip6
->ip6_dst
, sizeof(ip6
->ip6_dst
));
2954 * Check the variable replay window.
2955 * ipsec_chkreplay() performs replay check before ICV verification.
2956 * ipsec_updatereplay() updates replay bitmap. This must be called after
2957 * ICV verification (it also performs replay check, which is usually done
2959 * 0 (zero) is returned if packet disallowed, 1 if packet permitted.
2961 * based on RFC 2401.
2964 ipsec_chkreplay(seq
, sav
)
2966 struct secasvar
*sav
;
2968 const struct secreplay
*replay
;
2971 u_int32_t wsizeb
; /* constant: bits of window size */
2972 int frlast
; /* constant: last frame */
2977 panic("ipsec_chkreplay: NULL pointer was passed.\n");
2979 lck_mtx_lock(sadb_mutex
);
2980 replay
= sav
->replay
;
2982 if (replay
->wsize
== 0) {
2983 lck_mtx_unlock(sadb_mutex
);
2984 return 1; /* no need to check replay. */
2988 frlast
= replay
->wsize
- 1;
2989 wsizeb
= replay
->wsize
<< 3;
2991 /* sequence number of 0 is invalid */
2993 lck_mtx_unlock(sadb_mutex
);
2997 /* first time is always okay */
2998 if (replay
->count
== 0) {
2999 lck_mtx_unlock(sadb_mutex
);
3003 if (seq
> replay
->lastseq
) {
3004 /* larger sequences are okay */
3005 lck_mtx_unlock(sadb_mutex
);
3008 /* seq is equal or less than lastseq. */
3009 diff
= replay
->lastseq
- seq
;
3011 /* over range to check, i.e. too old or wrapped */
3012 if (diff
>= wsizeb
) {
3013 lck_mtx_unlock(sadb_mutex
);
3017 fr
= frlast
- diff
/ 8;
3019 /* this packet already seen ? */
3020 if ((replay
->bitmap
)[fr
] & (1 << (diff
% 8))) {
3021 lck_mtx_unlock(sadb_mutex
);
3025 /* out of order but good */
3026 lck_mtx_unlock(sadb_mutex
);
3032 * check replay counter whether to update or not.
3037 ipsec_updatereplay(seq
, sav
)
3039 struct secasvar
*sav
;
3041 struct secreplay
*replay
;
3044 u_int32_t wsizeb
; /* constant: bits of window size */
3045 int frlast
; /* constant: last frame */
3049 panic("ipsec_chkreplay: NULL pointer was passed.\n");
3051 lck_mtx_lock(sadb_mutex
);
3052 replay
= sav
->replay
;
3054 if (replay
->wsize
== 0)
3055 goto ok
; /* no need to check replay. */
3058 frlast
= replay
->wsize
- 1;
3059 wsizeb
= replay
->wsize
<< 3;
3061 /* sequence number of 0 is invalid */
3066 if (replay
->count
== 0) {
3067 replay
->lastseq
= seq
;
3068 bzero(replay
->bitmap
, replay
->wsize
);
3069 (replay
->bitmap
)[frlast
] = 1;
3073 if (seq
> replay
->lastseq
) {
3074 /* seq is larger than lastseq. */
3075 diff
= seq
- replay
->lastseq
;
3077 /* new larger sequence number */
3078 if (diff
< wsizeb
) {
3080 /* set bit for this packet */
3081 vshiftl((unsigned char *) replay
->bitmap
, diff
, replay
->wsize
);
3082 (replay
->bitmap
)[frlast
] |= 1;
3084 /* this packet has a "way larger" */
3085 bzero(replay
->bitmap
, replay
->wsize
);
3086 (replay
->bitmap
)[frlast
] = 1;
3088 replay
->lastseq
= seq
;
3090 /* larger is good */
3092 /* seq is equal or less than lastseq. */
3093 diff
= replay
->lastseq
- seq
;
3095 /* over range to check, i.e. too old or wrapped */
3096 if (diff
>= wsizeb
) {
3097 lck_mtx_unlock(sadb_mutex
);
3101 fr
= frlast
- diff
/ 8;
3103 /* this packet already seen ? */
3104 if ((replay
->bitmap
)[fr
] & (1 << (diff
% 8))) {
3105 lck_mtx_unlock(sadb_mutex
);
3110 (replay
->bitmap
)[fr
] |= (1 << (diff
% 8));
3112 /* out of order but good */
3116 if (replay
->count
== ~0) {
3118 /* set overflow flag */
3121 /* don't increment, no more packets accepted */
3122 if ((sav
->flags
& SADB_X_EXT_CYCSEQ
) == 0) {
3123 lck_mtx_unlock(sadb_mutex
);
3127 ipseclog((LOG_WARNING
, "replay counter made %d cycle. %s\n",
3128 replay
->overflow
, ipsec_logsastr(sav
)));
3133 lck_mtx_unlock(sadb_mutex
);
3138 * shift variable length buffer to left.
3139 * IN: bitmap: pointer to the buffer
3140 * nbit: the number of to shift.
3141 * wsize: buffer size (bytes).
3144 vshiftl(bitmap
, nbit
, wsize
)
3145 unsigned char *bitmap
;
3151 for (j
= 0; j
< nbit
; j
+= 8) {
3152 s
= (nbit
- j
< 8) ? (nbit
- j
): 8;
3154 for (i
= 1; i
< wsize
; i
++) {
3155 over
= (bitmap
[i
] >> (8 - s
));
3157 bitmap
[i
-1] |= over
;
3165 ipsec4_logpacketstr(ip
, spi
)
3169 static char buf
[256] __attribute__((aligned(4)));
3173 s
= (u_int8_t
*)(&ip
->ip_src
);
3174 d
= (u_int8_t
*)(&ip
->ip_dst
);
3177 snprintf(buf
, sizeof(buf
), "packet(SPI=%u ", (u_int32_t
)ntohl(spi
));
3180 snprintf(p
, sizeof(buf
) - (p
- buf
), "src=%u.%u.%u.%u",
3181 s
[0], s
[1], s
[2], s
[3]);
3184 snprintf(p
, sizeof(buf
) - (p
- buf
), " dst=%u.%u.%u.%u",
3185 d
[0], d
[1], d
[2], d
[3]);
3188 snprintf(p
, sizeof(buf
) - (p
- buf
), ")");
3195 ipsec6_logpacketstr(ip6
, spi
)
3196 struct ip6_hdr
*ip6
;
3199 static char buf
[256] __attribute__((aligned(4)));
3203 snprintf(buf
, sizeof(buf
), "packet(SPI=%u ", (u_int32_t
)ntohl(spi
));
3206 snprintf(p
, sizeof(buf
) - (p
- buf
), "src=%s",
3207 ip6_sprintf(&ip6
->ip6_src
));
3210 snprintf(p
, sizeof(buf
) - (p
- buf
), " dst=%s",
3211 ip6_sprintf(&ip6
->ip6_dst
));
3214 snprintf(p
, sizeof(buf
) - (p
- buf
), ")");
3222 struct secasvar
*sav
;
3224 static char buf
[256] __attribute__((aligned(4)));
3226 struct secasindex
*saidx
= &sav
->sah
->saidx
;
3228 /* validity check */
3229 if (((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
3230 != ((struct sockaddr
*)&sav
->sah
->saidx
.dst
)->sa_family
)
3231 panic("ipsec_logsastr: family mismatched.\n");
3234 snprintf(buf
, sizeof(buf
), "SA(SPI=%u ", (u_int32_t
)ntohl(sav
->spi
));
3237 if (((struct sockaddr
*)&saidx
->src
)->sa_family
== AF_INET
) {
3239 s
= (u_int8_t
*)&((struct sockaddr_in
*)&saidx
->src
)->sin_addr
;
3240 d
= (u_int8_t
*)&((struct sockaddr_in
*)&saidx
->dst
)->sin_addr
;
3241 snprintf(p
, sizeof(buf
) - (p
- buf
),
3242 "src=%d.%d.%d.%d dst=%d.%d.%d.%d",
3243 s
[0], s
[1], s
[2], s
[3], d
[0], d
[1], d
[2], d
[3]);
3246 else if (((struct sockaddr
*)&saidx
->src
)->sa_family
== AF_INET6
) {
3247 snprintf(p
, sizeof(buf
) - (p
- buf
),
3249 ip6_sprintf(&((struct sockaddr_in6
*)&saidx
->src
)->sin6_addr
));
3252 snprintf(p
, sizeof(buf
) - (p
- buf
),
3254 ip6_sprintf(&((struct sockaddr_in6
*)&saidx
->dst
)->sin6_addr
));
3259 snprintf(p
, sizeof(buf
) - (p
- buf
), ")");
3275 p
= mtod(m
, u_char
*);
3276 for (i
= 0; i
< m
->m_len
; i
++) {
3277 printf("%02x ", p
[i
]);
3279 if (totlen
% 16 == 0)
3284 if (totlen
% 16 != 0)
3291 * IPsec output logic for IPv4.
3294 ipsec4_output_internal(struct ipsec_output_state
*state
, struct secasvar
*sav
)
3296 struct ip
*ip
= NULL
;
3298 struct sockaddr_in
*dst4
;
3301 /* validity check */
3302 if (sav
== NULL
|| sav
->sah
== NULL
) {
3308 * If there is no valid SA, we give up to process any
3309 * more. In such a case, the SA's status is changed
3310 * from DYING to DEAD after allocating. If a packet
3311 * send to the receiver by dead SA, the receiver can
3312 * not decode a packet because SA has been dead.
3314 if (sav
->state
!= SADB_SASTATE_MATURE
3315 && sav
->state
!= SADB_SASTATE_DYING
) {
3316 IPSEC_STAT_INCREMENT(ipsecstat
.out_nosa
);
3321 state
->outgoing_if
= sav
->sah
->outgoing_if
;
3324 * There may be the case that SA status will be changed when
3325 * we are refering to one. So calling splsoftnet().
3328 if (sav
->sah
->saidx
.mode
== IPSEC_MODE_TUNNEL
) {
3330 * build IPsec tunnel.
3332 state
->m
= ipsec4_splithdr(state
->m
);
3338 if (((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
== AF_INET6
) {
3339 error
= ipsec46_encapsulate(state
, sav
);
3341 // packet already freed by encapsulation error handling
3346 error
= ipsec6_update_routecache_and_output(state
, sav
);
3349 } else if (((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
== AF_INET
) {
3350 error
= ipsec4_encapsulate(state
->m
, sav
);
3355 ip
= mtod(state
->m
, struct ip
*);
3357 // grab sadb_mutex, before updating sah's route cache
3358 lck_mtx_lock(sadb_mutex
);
3359 ro4
= &sav
->sah
->sa_route
;
3360 dst4
= (struct sockaddr_in
*)(void *)&ro4
->ro_dst
;
3361 if (ro4
->ro_rt
!= NULL
) {
3362 RT_LOCK(ro4
->ro_rt
);
3364 if (ROUTE_UNUSABLE(ro4
) ||
3365 dst4
->sin_addr
.s_addr
!= ip
->ip_dst
.s_addr
) {
3366 if (ro4
->ro_rt
!= NULL
)
3367 RT_UNLOCK(ro4
->ro_rt
);
3370 if (ro4
->ro_rt
== 0) {
3371 dst4
->sin_family
= AF_INET
;
3372 dst4
->sin_len
= sizeof(*dst4
);
3373 dst4
->sin_addr
= ip
->ip_dst
;
3375 if (ro4
->ro_rt
== 0) {
3376 OSAddAtomic(1, &ipstat
.ips_noroute
);
3377 error
= EHOSTUNREACH
;
3378 // release sadb_mutex, after updating sah's route cache
3379 lck_mtx_unlock(sadb_mutex
);
3382 RT_LOCK(ro4
->ro_rt
);
3386 * adjust state->dst if tunnel endpoint is offlink
3388 * XXX: caching rt_gateway value in the state is
3389 * not really good, since it may point elsewhere
3390 * when the gateway gets modified to a larger
3391 * sockaddr via rt_setgate(). This is currently
3392 * addressed by SA_SIZE roundup in that routine.
3394 if (ro4
->ro_rt
->rt_flags
& RTF_GATEWAY
)
3395 dst4
= (struct sockaddr_in
*)(void *)ro4
->ro_rt
->rt_gateway
;
3396 RT_UNLOCK(ro4
->ro_rt
);
3397 ROUTE_RELEASE(&state
->ro
);
3398 route_copyout(&state
->ro
, ro4
, sizeof(state
->ro
));
3399 state
->dst
= (struct sockaddr
*)dst4
;
3400 state
->tunneled
= 4;
3401 // release sadb_mutex, after updating sah's route cache
3402 lck_mtx_unlock(sadb_mutex
);
3404 ipseclog((LOG_ERR
, "%s: family mismatched between inner and outer spi=%u\n",
3405 __FUNCTION__
, (u_int32_t
)ntohl(sav
->spi
)));
3406 error
= EAFNOSUPPORT
;
3411 state
->m
= ipsec4_splithdr(state
->m
);
3416 switch (sav
->sah
->saidx
.proto
) {
3419 if ((error
= esp4_output(state
->m
, sav
)) != 0) {
3431 if ((error
= ah4_output(state
->m
, sav
)) != 0) {
3436 case IPPROTO_IPCOMP
:
3437 if ((error
= ipcomp4_output(state
->m
, sav
)) != 0) {
3444 "ipsec4_output: unknown ipsec protocol %d\n",
3445 sav
->sah
->saidx
.proto
));
3452 if (state
->m
== 0) {
3464 ipsec4_interface_output(struct ipsec_output_state
*state
, ifnet_t interface
)
3467 struct secasvar
*sav
= NULL
;
3469 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
3472 panic("state == NULL in ipsec4_output");
3474 panic("state->m == NULL in ipsec4_output");
3476 panic("state->dst == NULL in ipsec4_output");
3478 sav
= key_alloc_outbound_sav_for_interface(interface
, AF_INET
);
3483 if ((error
= ipsec4_output_internal(state
, sav
)) != 0) {
3487 KERNEL_DEBUG(DBG_FNC_IPSEC_OUT
| DBG_FUNC_END
, 0,0,0,0,0);
3489 key_freesav(sav
, KEY_SADB_UNLOCKED
);
3494 key_freesav(sav
, KEY_SADB_UNLOCKED
);
3497 KERNEL_DEBUG(DBG_FNC_IPSEC_OUT
| DBG_FUNC_END
, error
,0,0,0,0);
3502 ipsec4_output(struct ipsec_output_state
*state
, struct secpolicy
*sp
, __unused
int flags
)
3504 struct ip
*ip
= NULL
;
3505 struct ipsecrequest
*isr
= NULL
;
3506 struct secasindex saidx
;
3507 struct secasvar
*sav
= NULL
;
3509 struct sockaddr_in
*sin
;
3511 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
3514 panic("state == NULL in ipsec4_output");
3516 panic("state->m == NULL in ipsec4_output");
3518 panic("state->dst == NULL in ipsec4_output");
3520 KERNEL_DEBUG(DBG_FNC_IPSEC_OUT
| DBG_FUNC_START
, 0,0,0,0,0);
3522 KEYDEBUG(KEYDEBUG_IPSEC_DATA
,
3523 printf("ipsec4_output: applied SP\n");
3524 kdebug_secpolicy(sp
));
3526 for (isr
= sp
->req
; isr
!= NULL
; isr
= isr
->next
) {
3527 /* make SA index for search proper SA */
3528 ip
= mtod(state
->m
, struct ip
*);
3529 bcopy(&isr
->saidx
, &saidx
, sizeof(saidx
));
3530 saidx
.mode
= isr
->saidx
.mode
;
3531 saidx
.reqid
= isr
->saidx
.reqid
;
3532 sin
= (struct sockaddr_in
*)&saidx
.src
;
3533 if (sin
->sin_len
== 0) {
3534 sin
->sin_len
= sizeof(*sin
);
3535 sin
->sin_family
= AF_INET
;
3536 sin
->sin_port
= IPSEC_PORT_ANY
;
3537 bcopy(&ip
->ip_src
, &sin
->sin_addr
,
3538 sizeof(sin
->sin_addr
));
3540 sin
= (struct sockaddr_in
*)&saidx
.dst
;
3541 if (sin
->sin_len
== 0) {
3542 sin
->sin_len
= sizeof(*sin
);
3543 sin
->sin_family
= AF_INET
;
3544 sin
->sin_port
= IPSEC_PORT_ANY
;
3546 * Get port from packet if upper layer is UDP and nat traversal
3547 * is enabled and transport mode.
3550 if ((esp_udp_encap_port
& 0xFFFF) != 0 &&
3551 isr
->saidx
.mode
== IPSEC_MODE_TRANSPORT
) {
3553 if (ip
->ip_p
== IPPROTO_UDP
) {
3557 hlen
= IP_VHL_HL(ip
->ip_vhl
) << 2;
3559 hlen
= ip
->ip_hl
<< 2;
3561 if (state
->m
->m_len
< hlen
+ sizeof(struct udphdr
)) {
3562 state
->m
= m_pullup(state
->m
, hlen
+ sizeof(struct udphdr
));
3564 ipseclog((LOG_DEBUG
, "IPv4 output: can't pullup UDP header\n"));
3565 IPSEC_STAT_INCREMENT(ipsecstat
.in_inval
);
3568 ip
= mtod(state
->m
, struct ip
*);
3570 udp
= (struct udphdr
*)(void *)(((u_int8_t
*)ip
) + hlen
);
3571 sin
->sin_port
= udp
->uh_dport
;
3575 bcopy(&ip
->ip_dst
, &sin
->sin_addr
,
3576 sizeof(sin
->sin_addr
));
3579 if ((error
= key_checkrequest(isr
, &saidx
, &sav
)) != 0) {
3581 * IPsec processing is required, but no SA found.
3582 * I assume that key_acquire() had been called
3583 * to get/establish the SA. Here I discard
3584 * this packet because it is responsibility for
3585 * upper layer to retransmit the packet.
3587 IPSEC_STAT_INCREMENT(ipsecstat
.out_nosa
);
3591 /* validity check */
3593 switch (ipsec_get_reqlevel(isr
)) {
3594 case IPSEC_LEVEL_USE
:
3596 case IPSEC_LEVEL_REQUIRE
:
3597 /* must be not reached here. */
3598 panic("ipsec4_output: no SA found, but required.");
3602 if ((error
= ipsec4_output_internal(state
, sav
)) != 0) {
3607 KERNEL_DEBUG(DBG_FNC_IPSEC_OUT
| DBG_FUNC_END
, 0,0,0,0,0);
3609 key_freesav(sav
, KEY_SADB_UNLOCKED
);
3614 key_freesav(sav
, KEY_SADB_UNLOCKED
);
3617 KERNEL_DEBUG(DBG_FNC_IPSEC_OUT
| DBG_FUNC_END
, error
,0,0,0,0);
3625 * IPsec output logic for IPv6, transport mode.
3628 ipsec6_output_trans_internal(
3629 struct ipsec_output_state
*state
,
3630 struct secasvar
*sav
,
3634 struct ip6_hdr
*ip6
;
3638 /* validity check */
3639 if (sav
== NULL
|| sav
->sah
== NULL
) {
3645 * If there is no valid SA, we give up to process.
3646 * see same place at ipsec4_output().
3648 if (sav
->state
!= SADB_SASTATE_MATURE
3649 && sav
->state
!= SADB_SASTATE_DYING
) {
3650 IPSEC_STAT_INCREMENT(ipsec6stat
.out_nosa
);
3655 state
->outgoing_if
= sav
->sah
->outgoing_if
;
3657 switch (sav
->sah
->saidx
.proto
) {
3660 error
= esp6_output(state
->m
, nexthdrp
, mprev
->m_next
, sav
);
3667 error
= ah6_output(state
->m
, nexthdrp
, mprev
->m_next
, sav
);
3669 case IPPROTO_IPCOMP
:
3670 error
= ipcomp6_output(state
->m
, nexthdrp
, mprev
->m_next
, sav
);
3673 ipseclog((LOG_ERR
, "ipsec6_output_trans: "
3674 "unknown ipsec protocol %d\n", sav
->sah
->saidx
.proto
));
3676 IPSEC_STAT_INCREMENT(ipsec6stat
.out_inval
);
3684 plen
= state
->m
->m_pkthdr
.len
- sizeof(struct ip6_hdr
);
3685 if (plen
> IPV6_MAXPACKET
) {
3686 ipseclog((LOG_ERR
, "ipsec6_output_trans: "
3687 "IPsec with IPv6 jumbogram is not supported\n"));
3688 IPSEC_STAT_INCREMENT(ipsec6stat
.out_inval
);
3689 error
= EINVAL
; /*XXX*/
3692 ip6
= mtod(state
->m
, struct ip6_hdr
*);
3693 ip6
->ip6_plen
= htons(plen
);
3701 ipsec6_output_trans(
3702 struct ipsec_output_state
*state
,
3705 struct secpolicy
*sp
,
3709 struct ip6_hdr
*ip6
;
3710 struct ipsecrequest
*isr
= NULL
;
3711 struct secasindex saidx
;
3713 struct sockaddr_in6
*sin6
;
3714 struct secasvar
*sav
= NULL
;
3716 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
3719 panic("state == NULL in ipsec6_output_trans");
3721 panic("state->m == NULL in ipsec6_output_trans");
3723 panic("nexthdrp == NULL in ipsec6_output_trans");
3725 panic("mprev == NULL in ipsec6_output_trans");
3727 panic("sp == NULL in ipsec6_output_trans");
3729 panic("tun == NULL in ipsec6_output_trans");
3731 KEYDEBUG(KEYDEBUG_IPSEC_DATA
,
3732 printf("ipsec6_output_trans: applyed SP\n");
3733 kdebug_secpolicy(sp
));
3736 for (isr
= sp
->req
; isr
; isr
= isr
->next
) {
3737 if (isr
->saidx
.mode
== IPSEC_MODE_TUNNEL
) {
3738 /* the rest will be handled by ipsec6_output_tunnel() */
3742 /* make SA index for search proper SA */
3743 ip6
= mtod(state
->m
, struct ip6_hdr
*);
3744 bcopy(&isr
->saidx
, &saidx
, sizeof(saidx
));
3745 saidx
.mode
= isr
->saidx
.mode
;
3746 saidx
.reqid
= isr
->saidx
.reqid
;
3747 sin6
= (struct sockaddr_in6
*)&saidx
.src
;
3748 if (sin6
->sin6_len
== 0) {
3749 sin6
->sin6_len
= sizeof(*sin6
);
3750 sin6
->sin6_family
= AF_INET6
;
3751 sin6
->sin6_port
= IPSEC_PORT_ANY
;
3752 bcopy(&ip6
->ip6_src
, &sin6
->sin6_addr
,
3753 sizeof(ip6
->ip6_src
));
3754 if (IN6_IS_SCOPE_LINKLOCAL(&ip6
->ip6_src
)) {
3755 /* fix scope id for comparing SPD */
3756 sin6
->sin6_addr
.s6_addr16
[1] = 0;
3757 sin6
->sin6_scope_id
= ntohs(ip6
->ip6_src
.s6_addr16
[1]);
3760 sin6
= (struct sockaddr_in6
*)&saidx
.dst
;
3761 if (sin6
->sin6_len
== 0) {
3762 sin6
->sin6_len
= sizeof(*sin6
);
3763 sin6
->sin6_family
= AF_INET6
;
3764 sin6
->sin6_port
= IPSEC_PORT_ANY
;
3765 bcopy(&ip6
->ip6_dst
, &sin6
->sin6_addr
,
3766 sizeof(ip6
->ip6_dst
));
3767 if (IN6_IS_SCOPE_LINKLOCAL(&ip6
->ip6_dst
)) {
3768 /* fix scope id for comparing SPD */
3769 sin6
->sin6_addr
.s6_addr16
[1] = 0;
3770 sin6
->sin6_scope_id
= ntohs(ip6
->ip6_dst
.s6_addr16
[1]);
3774 if (key_checkrequest(isr
, &saidx
, &sav
) == ENOENT
) {
3776 * IPsec processing is required, but no SA found.
3777 * I assume that key_acquire() had been called
3778 * to get/establish the SA. Here I discard
3779 * this packet because it is responsibility for
3780 * upper layer to retransmit the packet.
3782 IPSEC_STAT_INCREMENT(ipsec6stat
.out_nosa
);
3786 * Notify the fact that the packet is discarded
3787 * to ourselves. I believe this is better than
3788 * just silently discarding. (jinmei@kame.net)
3789 * XXX: should we restrict the error to TCP packets?
3790 * XXX: should we directly notify sockets via
3793 icmp6_error(state
->m
, ICMP6_DST_UNREACH
,
3794 ICMP6_DST_UNREACH_ADMIN
, 0);
3795 state
->m
= NULL
; /* icmp6_error freed the mbuf */
3799 /* validity check */
3801 switch (ipsec_get_reqlevel(isr
)) {
3802 case IPSEC_LEVEL_USE
:
3804 case IPSEC_LEVEL_REQUIRE
:
3805 /* must be not reached here. */
3806 panic("ipsec6_output_trans: no SA found, but required.");
3810 if ((error
= ipsec6_output_trans_internal(state
, sav
, nexthdrp
, mprev
)) != 0) {
3815 /* if we have more to go, we need a tunnel mode processing */
3820 key_freesav(sav
, KEY_SADB_UNLOCKED
);
3825 key_freesav(sav
, KEY_SADB_UNLOCKED
);
3832 * IPsec output logic for IPv6, tunnel mode.
3835 ipsec6_output_tunnel_internal(struct ipsec_output_state
*state
, struct secasvar
*sav
, int *must_be_last
)
3837 struct ip6_hdr
*ip6
;
3840 struct sockaddr_in6
* dst6
;
3843 /* validity check */
3844 if (sav
== NULL
|| sav
->sah
== NULL
|| sav
->sah
->saidx
.mode
!= IPSEC_MODE_TUNNEL
) {
3850 * If there is no valid SA, we give up to process.
3851 * see same place at ipsec4_output().
3853 if (sav
->state
!= SADB_SASTATE_MATURE
3854 && sav
->state
!= SADB_SASTATE_DYING
) {
3855 IPSEC_STAT_INCREMENT(ipsec6stat
.out_nosa
);
3860 state
->outgoing_if
= sav
->sah
->outgoing_if
;
3862 if (sav
->sah
->saidx
.mode
== IPSEC_MODE_TUNNEL
) {
3864 * build IPsec tunnel.
3866 state
->m
= ipsec6_splithdr(state
->m
);
3868 IPSEC_STAT_INCREMENT(ipsec6stat
.out_nomem
);
3873 if (((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
== AF_INET6
) {
3874 error
= ipsec6_encapsulate(state
->m
, sav
);
3879 ip6
= mtod(state
->m
, struct ip6_hdr
*);
3880 } else if (((struct sockaddr
*)&sav
->sah
->saidx
.src
)->sa_family
== AF_INET
) {
3883 struct sockaddr_in
* dst4
;
3884 struct route
*ro4
= NULL
;
3885 struct route ro4_copy
;
3886 struct ip_out_args ipoa
= { IFSCOPE_NONE
, { 0 },
3887 IPOAF_SELECT_SRCIF
, 0 };
3892 state
->tunneled
= 4; /* must not process any further in ip6_output */
3893 error
= ipsec64_encapsulate(state
->m
, sav
);
3898 /* Now we have an IPv4 packet */
3899 ip
= mtod(state
->m
, struct ip
*);
3901 // grab sadb_mutex, to update sah's route cache and get a local copy of it
3902 lck_mtx_lock(sadb_mutex
);
3903 ro4
= &sav
->sah
->sa_route
;
3904 dst4
= (struct sockaddr_in
*)(void *)&ro4
->ro_dst
;
3906 RT_LOCK(ro4
->ro_rt
);
3908 if (ROUTE_UNUSABLE(ro4
) ||
3909 dst4
->sin_addr
.s_addr
!= ip
->ip_dst
.s_addr
) {
3910 if (ro4
->ro_rt
!= NULL
)
3911 RT_UNLOCK(ro4
->ro_rt
);
3914 if (ro4
->ro_rt
== NULL
) {
3915 dst4
->sin_family
= AF_INET
;
3916 dst4
->sin_len
= sizeof(*dst4
);
3917 dst4
->sin_addr
= ip
->ip_dst
;
3919 RT_UNLOCK(ro4
->ro_rt
);
3921 route_copyout(&ro4_copy
, ro4
, sizeof(ro4_copy
));
3922 // release sadb_mutex, after updating sah's route cache and getting a local copy
3923 lck_mtx_unlock(sadb_mutex
);
3924 state
->m
= ipsec4_splithdr(state
->m
);
3927 ROUTE_RELEASE(&ro4_copy
);
3930 switch (sav
->sah
->saidx
.proto
) {
3933 if ((error
= esp4_output(state
->m
, sav
)) != 0) {
3935 ROUTE_RELEASE(&ro4_copy
);
3944 ROUTE_RELEASE(&ro4_copy
);
3948 if ((error
= ah4_output(state
->m
, sav
)) != 0) {
3950 ROUTE_RELEASE(&ro4_copy
);
3954 case IPPROTO_IPCOMP
:
3955 if ((error
= ipcomp4_output(state
->m
, sav
)) != 0) {
3957 ROUTE_RELEASE(&ro4_copy
);
3963 "ipsec4_output: unknown ipsec protocol %d\n",
3964 sav
->sah
->saidx
.proto
));
3968 ROUTE_RELEASE(&ro4_copy
);
3972 if (state
->m
== 0) {
3974 ROUTE_RELEASE(&ro4_copy
);
3977 ipsec_set_pkthdr_for_interface(sav
->sah
->ipsec_if
, state
->m
, AF_INET
);
3978 ip
= mtod(state
->m
, struct ip
*);
3979 ip
->ip_len
= ntohs(ip
->ip_len
); /* flip len field before calling ip_output */
3980 error
= ip_output(state
->m
, NULL
, &ro4_copy
, IP_OUTARGS
, NULL
, &ipoa
);
3982 // grab sadb_mutex, to synchronize the sah's route cache with the local copy
3983 lck_mtx_lock(sadb_mutex
);
3984 route_copyin(&ro4_copy
, ro4
, sizeof(ro4_copy
));
3985 lck_mtx_unlock(sadb_mutex
);
3990 ipseclog((LOG_ERR
, "ipsec6_output_tunnel: "
3991 "unsupported inner family, spi=%u\n",
3992 (u_int32_t
)ntohl(sav
->spi
)));
3993 IPSEC_STAT_INCREMENT(ipsec6stat
.out_inval
);
3994 error
= EAFNOSUPPORT
;
3998 // grab sadb_mutex, before updating sah's route cache
3999 lck_mtx_lock(sadb_mutex
);
4000 ro6
= &sav
->sah
->sa_route
;
4001 dst6
= (struct sockaddr_in6
*)(void *)&ro6
->ro_dst
;
4003 RT_LOCK(ro6
->ro_rt
);
4005 if (ROUTE_UNUSABLE(ro6
) ||
4006 !IN6_ARE_ADDR_EQUAL(&dst6
->sin6_addr
, &ip6
->ip6_dst
)) {
4007 if (ro6
->ro_rt
!= NULL
)
4008 RT_UNLOCK(ro6
->ro_rt
);
4011 if (ro6
->ro_rt
== 0) {
4012 bzero(dst6
, sizeof(*dst6
));
4013 dst6
->sin6_family
= AF_INET6
;
4014 dst6
->sin6_len
= sizeof(*dst6
);
4015 dst6
->sin6_addr
= ip6
->ip6_dst
;
4018 RT_LOCK(ro6
->ro_rt
);
4021 if (ro6
->ro_rt
== 0) {
4022 ip6stat
.ip6s_noroute
++;
4023 IPSEC_STAT_INCREMENT(ipsec6stat
.out_noroute
);
4024 error
= EHOSTUNREACH
;
4025 // release sadb_mutex, after updating sah's route cache
4026 lck_mtx_unlock(sadb_mutex
);
4031 * adjust state->dst if tunnel endpoint is offlink
4033 * XXX: caching rt_gateway value in the state is
4034 * not really good, since it may point elsewhere
4035 * when the gateway gets modified to a larger
4036 * sockaddr via rt_setgate(). This is currently
4037 * addressed by SA_SIZE roundup in that routine.
4039 if (ro6
->ro_rt
->rt_flags
& RTF_GATEWAY
)
4040 dst6
= (struct sockaddr_in6
*)(void *)ro6
->ro_rt
->rt_gateway
;
4041 RT_UNLOCK(ro6
->ro_rt
);
4042 ROUTE_RELEASE(&state
->ro
);
4043 route_copyout(&state
->ro
, ro6
, sizeof(state
->ro
));
4044 state
->dst
= (struct sockaddr
*)dst6
;
4045 state
->tunneled
= 6;
4046 // release sadb_mutex, after updating sah's route cache
4047 lck_mtx_unlock(sadb_mutex
);
4050 state
->m
= ipsec6_splithdr(state
->m
);
4052 IPSEC_STAT_INCREMENT(ipsec6stat
.out_nomem
);
4056 ip6
= mtod(state
->m
, struct ip6_hdr
*);
4057 switch (sav
->sah
->saidx
.proto
) {
4060 error
= esp6_output(state
->m
, &ip6
->ip6_nxt
, state
->m
->m_next
, sav
);
4067 error
= ah6_output(state
->m
, &ip6
->ip6_nxt
, state
->m
->m_next
, sav
);
4069 case IPPROTO_IPCOMP
:
4070 /* XXX code should be here */
4073 ipseclog((LOG_ERR
, "ipsec6_output_tunnel: "
4074 "unknown ipsec protocol %d\n", sav
->sah
->saidx
.proto
));
4076 IPSEC_STAT_INCREMENT(ipsec6stat
.out_inval
);
4084 plen
= state
->m
->m_pkthdr
.len
- sizeof(struct ip6_hdr
);
4085 if (plen
> IPV6_MAXPACKET
) {
4086 ipseclog((LOG_ERR
, "ipsec6_output_tunnel: "
4087 "IPsec with IPv6 jumbogram is not supported\n"));
4088 IPSEC_STAT_INCREMENT(ipsec6stat
.out_inval
);
4089 error
= EINVAL
; /*XXX*/
4092 ip6
= mtod(state
->m
, struct ip6_hdr
*);
4093 ip6
->ip6_plen
= htons(plen
);
4102 ipsec6_output_tunnel(
4103 struct ipsec_output_state
*state
,
4104 struct secpolicy
*sp
,
4107 struct ip6_hdr
*ip6
;
4108 struct ipsecrequest
*isr
= NULL
;
4109 struct secasindex saidx
;
4110 struct secasvar
*sav
= NULL
;
4113 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
4116 panic("state == NULL in ipsec6_output_tunnel");
4118 panic("state->m == NULL in ipsec6_output_tunnel");
4120 panic("sp == NULL in ipsec6_output_tunnel");
4122 KEYDEBUG(KEYDEBUG_IPSEC_DATA
,
4123 printf("ipsec6_output_tunnel: applyed SP\n");
4124 kdebug_secpolicy(sp
));
4127 * transport mode ipsec (before the 1st tunnel mode) is already
4128 * processed by ipsec6_output_trans().
4130 for (isr
= sp
->req
; isr
; isr
= isr
->next
) {
4131 if (isr
->saidx
.mode
== IPSEC_MODE_TUNNEL
)
4135 for (/* already initialized */; isr
; isr
= isr
->next
) {
4136 if (isr
->saidx
.mode
== IPSEC_MODE_TUNNEL
) {
4137 /* When tunnel mode, SA peers must be specified. */
4138 bcopy(&isr
->saidx
, &saidx
, sizeof(saidx
));
4140 /* make SA index to look for a proper SA */
4141 struct sockaddr_in6
*sin6
;
4143 bzero(&saidx
, sizeof(saidx
));
4144 saidx
.proto
= isr
->saidx
.proto
;
4145 saidx
.mode
= isr
->saidx
.mode
;
4146 saidx
.reqid
= isr
->saidx
.reqid
;
4148 ip6
= mtod(state
->m
, struct ip6_hdr
*);
4149 sin6
= (struct sockaddr_in6
*)&saidx
.src
;
4150 if (sin6
->sin6_len
== 0) {
4151 sin6
->sin6_len
= sizeof(*sin6
);
4152 sin6
->sin6_family
= AF_INET6
;
4153 sin6
->sin6_port
= IPSEC_PORT_ANY
;
4154 bcopy(&ip6
->ip6_src
, &sin6
->sin6_addr
,
4155 sizeof(ip6
->ip6_src
));
4156 if (IN6_IS_SCOPE_LINKLOCAL(&ip6
->ip6_src
)) {
4157 /* fix scope id for comparing SPD */
4158 sin6
->sin6_addr
.s6_addr16
[1] = 0;
4159 sin6
->sin6_scope_id
= ntohs(ip6
->ip6_src
.s6_addr16
[1]);
4162 sin6
= (struct sockaddr_in6
*)&saidx
.dst
;
4163 if (sin6
->sin6_len
== 0) {
4164 sin6
->sin6_len
= sizeof(*sin6
);
4165 sin6
->sin6_family
= AF_INET6
;
4166 sin6
->sin6_port
= IPSEC_PORT_ANY
;
4167 bcopy(&ip6
->ip6_dst
, &sin6
->sin6_addr
,
4168 sizeof(ip6
->ip6_dst
));
4169 if (IN6_IS_SCOPE_LINKLOCAL(&ip6
->ip6_dst
)) {
4170 /* fix scope id for comparing SPD */
4171 sin6
->sin6_addr
.s6_addr16
[1] = 0;
4172 sin6
->sin6_scope_id
= ntohs(ip6
->ip6_dst
.s6_addr16
[1]);
4177 if (key_checkrequest(isr
, &saidx
, &sav
) == ENOENT
) {
4179 * IPsec processing is required, but no SA found.
4180 * I assume that key_acquire() had been called
4181 * to get/establish the SA. Here I discard
4182 * this packet because it is responsibility for
4183 * upper layer to retransmit the packet.
4185 IPSEC_STAT_INCREMENT(ipsec6stat
.out_nosa
);
4190 /* validity check */
4192 switch (ipsec_get_reqlevel(isr
)) {
4193 case IPSEC_LEVEL_USE
:
4195 case IPSEC_LEVEL_REQUIRE
:
4196 /* must be not reached here. */
4197 panic("ipsec6_output_tunnel: no SA found, but required.");
4202 * If there is no valid SA, we give up to process.
4203 * see same place at ipsec4_output().
4205 if (sav
->state
!= SADB_SASTATE_MATURE
4206 && sav
->state
!= SADB_SASTATE_DYING
) {
4207 IPSEC_STAT_INCREMENT(ipsec6stat
.out_nosa
);
4212 int must_be_last
= 0;
4214 if ((error
= ipsec6_output_tunnel_internal(state
, sav
, &must_be_last
)) != 0) {
4218 if (must_be_last
&& isr
->next
) {
4219 ipseclog((LOG_ERR
, "ipsec6_output_tunnel: "
4220 "IPv4 must be outer layer, spi=%u\n",
4221 (u_int32_t
)ntohl(sav
->spi
)));
4228 key_freesav(sav
, KEY_SADB_UNLOCKED
);
4233 key_freesav(sav
, KEY_SADB_UNLOCKED
);
4241 ipsec6_interface_output(struct ipsec_output_state
*state
, ifnet_t interface
, u_char
*nexthdrp
, struct mbuf
*mprev
)
4244 struct secasvar
*sav
= NULL
;
4246 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
4249 panic("state == NULL in ipsec6_output");
4251 panic("state->m == NULL in ipsec6_output");
4253 panic("nexthdrp == NULL in ipsec6_output");
4255 panic("mprev == NULL in ipsec6_output");
4257 sav
= key_alloc_outbound_sav_for_interface(interface
, AF_INET6
);
4262 if (sav
->sah
&& sav
->sah
->saidx
.mode
== IPSEC_MODE_TUNNEL
) {
4263 if ((error
= ipsec6_output_tunnel_internal(state
, sav
, NULL
)) != 0) {
4268 if ((error
= ipsec6_output_trans_internal(state
, sav
, nexthdrp
, mprev
)) != 0) {
4274 key_freesav(sav
, KEY_SADB_UNLOCKED
);
4279 key_freesav(sav
, KEY_SADB_UNLOCKED
);
4288 * Chop IP header and option off from the payload.
4298 if (m
->m_len
< sizeof(struct ip
))
4299 panic("ipsec4_splithdr: first mbuf too short, m_len %d, pkt_len %d, m_flag %x", m
->m_len
, m
->m_pkthdr
.len
, m
->m_flags
);
4300 ip
= mtod(m
, struct ip
*);
4302 hlen
= _IP_VHL_HL(ip
->ip_vhl
) << 2;
4304 hlen
= ip
->ip_hl
<< 2;
4306 if (m
->m_len
> hlen
) {
4307 MGETHDR(mh
, M_DONTWAIT
, MT_HEADER
); /* MAC-OK */
4312 M_COPY_PKTHDR(mh
, m
);
4314 m
->m_flags
&= ~M_PKTHDR
;
4315 m_mchtype(m
, MT_DATA
);
4321 bcopy((caddr_t
)ip
, mtod(m
, caddr_t
), hlen
);
4322 } else if (m
->m_len
< hlen
) {
4323 m
= m_pullup(m
, hlen
);
4337 struct ip6_hdr
*ip6
;
4340 if (m
->m_len
< sizeof(struct ip6_hdr
))
4341 panic("ipsec6_splithdr: first mbuf too short");
4342 ip6
= mtod(m
, struct ip6_hdr
*);
4343 hlen
= sizeof(struct ip6_hdr
);
4344 if (m
->m_len
> hlen
) {
4345 MGETHDR(mh
, M_DONTWAIT
, MT_HEADER
); /* MAC-OK */
4350 M_COPY_PKTHDR(mh
, m
);
4352 m
->m_flags
&= ~M_PKTHDR
;
4353 m_mchtype(m
, MT_DATA
);
4359 bcopy((caddr_t
)ip6
, mtod(m
, caddr_t
), hlen
);
4360 } else if (m
->m_len
< hlen
) {
4361 m
= m_pullup(m
, hlen
);
4369 /* validate inbound IPsec tunnel packet. */
4371 ipsec4_tunnel_validate(m
, off
, nxt0
, sav
, ifamily
)
4372 struct mbuf
*m
; /* no pullup permitted, m->m_len >= ip */
4375 struct secasvar
*sav
;
4376 sa_family_t
*ifamily
;
4378 u_int8_t nxt
= nxt0
& 0xff;
4379 struct sockaddr_in
*sin
;
4380 struct sockaddr_in osrc
, odst
, i4src
, i4dst
;
4381 struct sockaddr_in6 i6src
, i6dst
;
4383 struct secpolicy
*sp
;
4386 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
4389 if (m
->m_len
< sizeof(struct ip
))
4390 panic("too short mbuf on ipsec4_tunnel_validate");
4392 if (nxt
!= IPPROTO_IPV4
&& nxt
!= IPPROTO_IPV6
)
4394 if (m
->m_pkthdr
.len
< off
+ sizeof(struct ip
))
4396 /* do not decapsulate if the SA is for transport mode only */
4397 if (sav
->sah
->saidx
.mode
== IPSEC_MODE_TRANSPORT
)
4400 oip
= mtod(m
, struct ip
*);
4402 hlen
= _IP_VHL_HL(oip
->ip_vhl
) << 2;
4404 hlen
= oip
->ip_hl
<< 2;
4406 if (hlen
!= sizeof(struct ip
))
4409 sin
= (struct sockaddr_in
*)&sav
->sah
->saidx
.dst
;
4410 if (sin
->sin_family
!= AF_INET
)
4412 if (bcmp(&oip
->ip_dst
, &sin
->sin_addr
, sizeof(oip
->ip_dst
)) != 0)
4415 if (sav
->utun_in_fn
||
4416 sav
->sah
->ipsec_if
!= NULL
) {
4417 // the ipsec/utun interface SAs don't have a policies.
4418 if (nxt
== IPPROTO_IPV4
) {
4420 } else if (nxt
== IPPROTO_IPV6
) {
4421 *ifamily
= AF_INET6
;
4429 bzero(&osrc
, sizeof(osrc
));
4430 bzero(&odst
, sizeof(odst
));
4431 osrc
.sin_family
= odst
.sin_family
= AF_INET
;
4432 osrc
.sin_len
= odst
.sin_len
= sizeof(struct sockaddr_in
);
4433 osrc
.sin_addr
= oip
->ip_src
;
4434 odst
.sin_addr
= oip
->ip_dst
;
4436 * RFC2401 5.2.1 (b): (assume that we are using tunnel mode)
4437 * - if the inner destination is multicast address, there can be
4438 * multiple permissible inner source address. implementation
4439 * may want to skip verification of inner source address against
4441 * - if the inner protocol is ICMP, the packet may be an error report
4442 * from routers on the other side of the VPN cloud (R in the
4443 * following diagram). in this case, we cannot verify inner source
4444 * address against SPD selector.
4445 * me -- gw === gw -- R -- you
4447 * we consider the first bullet to be users responsibility on SPD entry
4448 * configuration (if you need to encrypt multicast traffic, set
4449 * the source range of SPD selector to 0.0.0.0/0, or have explicit
4450 * address ranges for possible senders).
4451 * the second bullet is not taken care of (yet).
4453 * therefore, we do not do anything special about inner source.
4455 if (nxt
== IPPROTO_IPV4
) {
4456 bzero(&i4src
, sizeof(struct sockaddr_in
));
4457 bzero(&i4dst
, sizeof(struct sockaddr_in
));
4458 i4src
.sin_family
= i4dst
.sin_family
= *ifamily
= AF_INET
;
4459 i4src
.sin_len
= i4dst
.sin_len
= sizeof(struct sockaddr_in
);
4460 m_copydata(m
, off
+ offsetof(struct ip
, ip_src
), sizeof(i4src
.sin_addr
),
4461 (caddr_t
)&i4src
.sin_addr
);
4462 m_copydata(m
, off
+ offsetof(struct ip
, ip_dst
), sizeof(i4dst
.sin_addr
),
4463 (caddr_t
)&i4dst
.sin_addr
);
4464 sp
= key_gettunnel((struct sockaddr
*)&osrc
, (struct sockaddr
*)&odst
,
4465 (struct sockaddr
*)&i4src
, (struct sockaddr
*)&i4dst
);
4466 } else if (nxt
== IPPROTO_IPV6
) {
4467 bzero(&i6src
, sizeof(struct sockaddr_in6
));
4468 bzero(&i6dst
, sizeof(struct sockaddr_in6
));
4469 i6src
.sin6_family
= i6dst
.sin6_family
= *ifamily
= AF_INET6
;
4470 i6src
.sin6_len
= i6dst
.sin6_len
= sizeof(struct sockaddr_in6
);
4471 m_copydata(m
, off
+ offsetof(struct ip6_hdr
, ip6_src
), sizeof(i6src
.sin6_addr
),
4472 (caddr_t
)&i6src
.sin6_addr
);
4473 m_copydata(m
, off
+ offsetof(struct ip6_hdr
, ip6_dst
), sizeof(i6dst
.sin6_addr
),
4474 (caddr_t
)&i6dst
.sin6_addr
);
4475 sp
= key_gettunnel((struct sockaddr
*)&osrc
, (struct sockaddr
*)&odst
,
4476 (struct sockaddr
*)&i6src
, (struct sockaddr
*)&i6dst
);
4478 return 0; /* unsupported family */
4483 key_freesp(sp
, KEY_SADB_UNLOCKED
);
4489 /* validate inbound IPsec tunnel packet. */
4491 ipsec6_tunnel_validate(m
, off
, nxt0
, sav
, ifamily
)
4492 struct mbuf
*m
; /* no pullup permitted, m->m_len >= ip */
4495 struct secasvar
*sav
;
4496 sa_family_t
*ifamily
;
4498 u_int8_t nxt
= nxt0
& 0xff;
4499 struct sockaddr_in6
*sin6
;
4500 struct sockaddr_in i4src
, i4dst
;
4501 struct sockaddr_in6 osrc
, odst
, i6src
, i6dst
;
4502 struct secpolicy
*sp
;
4503 struct ip6_hdr
*oip6
;
4505 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
4508 if (m
->m_len
< sizeof(struct ip6_hdr
))
4509 panic("too short mbuf on ipsec6_tunnel_validate");
4511 if (nxt
!= IPPROTO_IPV4
&& nxt
!= IPPROTO_IPV6
)
4514 if (m
->m_pkthdr
.len
< off
+ sizeof(struct ip6_hdr
))
4516 /* do not decapsulate if the SA is for transport mode only */
4517 if (sav
->sah
->saidx
.mode
== IPSEC_MODE_TRANSPORT
)
4520 oip6
= mtod(m
, struct ip6_hdr
*);
4521 /* AF_INET should be supported, but at this moment we don't. */
4522 sin6
= (struct sockaddr_in6
*)&sav
->sah
->saidx
.dst
;
4523 if (sin6
->sin6_family
!= AF_INET6
)
4525 if (!IN6_ARE_ADDR_EQUAL(&oip6
->ip6_dst
, &sin6
->sin6_addr
))
4528 if (sav
->utun_in_fn
||
4529 sav
->sah
->ipsec_if
!= NULL
) {
4530 // the ipsec/utun interface SAs don't have a policies.
4531 if (nxt
== IPPROTO_IPV4
) {
4533 } else if (nxt
== IPPROTO_IPV6
) {
4534 *ifamily
= AF_INET6
;
4542 bzero(&osrc
, sizeof(osrc
));
4543 bzero(&odst
, sizeof(odst
));
4544 osrc
.sin6_family
= odst
.sin6_family
= AF_INET6
;
4545 osrc
.sin6_len
= odst
.sin6_len
= sizeof(struct sockaddr_in6
);
4546 osrc
.sin6_addr
= oip6
->ip6_src
;
4547 odst
.sin6_addr
= oip6
->ip6_dst
;
4550 * regarding to inner source address validation, see a long comment
4551 * in ipsec4_tunnel_validate.
4554 if (nxt
== IPPROTO_IPV4
) {
4555 bzero(&i4src
, sizeof(struct sockaddr_in
));
4556 bzero(&i4dst
, sizeof(struct sockaddr_in
));
4557 i4src
.sin_family
= i4dst
.sin_family
= *ifamily
= AF_INET
;
4558 i4src
.sin_len
= i4dst
.sin_len
= sizeof(struct sockaddr_in
);
4559 m_copydata(m
, off
+ offsetof(struct ip
, ip_src
), sizeof(i4src
.sin_addr
),
4560 (caddr_t
)&i4src
.sin_addr
);
4561 m_copydata(m
, off
+ offsetof(struct ip
, ip_dst
), sizeof(i4dst
.sin_addr
),
4562 (caddr_t
)&i4dst
.sin_addr
);
4563 sp
= key_gettunnel((struct sockaddr
*)&osrc
, (struct sockaddr
*)&odst
,
4564 (struct sockaddr
*)&i4src
, (struct sockaddr
*)&i4dst
);
4565 } else if (nxt
== IPPROTO_IPV6
) {
4566 bzero(&i6src
, sizeof(struct sockaddr_in6
));
4567 bzero(&i6dst
, sizeof(struct sockaddr_in6
));
4568 i6src
.sin6_family
= i6dst
.sin6_family
= *ifamily
= AF_INET6
;
4569 i6src
.sin6_len
= i6dst
.sin6_len
= sizeof(struct sockaddr_in6
);
4570 m_copydata(m
, off
+ offsetof(struct ip6_hdr
, ip6_src
), sizeof(i6src
.sin6_addr
),
4571 (caddr_t
)&i6src
.sin6_addr
);
4572 m_copydata(m
, off
+ offsetof(struct ip6_hdr
, ip6_dst
), sizeof(i6dst
.sin6_addr
),
4573 (caddr_t
)&i6dst
.sin6_addr
);
4574 sp
= key_gettunnel((struct sockaddr
*)&osrc
, (struct sockaddr
*)&odst
,
4575 (struct sockaddr
*)&i6src
, (struct sockaddr
*)&i6dst
);
4577 return 0; /* unsupported family */
4579 * when there is no suitable inbound policy for the packet of the ipsec
4580 * tunnel mode, the kernel never decapsulate the tunneled packet
4581 * as the ipsec tunnel mode even when the system wide policy is "none".
4582 * then the kernel leaves the generic tunnel module to process this
4583 * packet. if there is no rule of the generic tunnel, the packet
4584 * is rejected and the statistics will be counted up.
4588 key_freesp(sp
, KEY_SADB_UNLOCKED
);
4595 * Make a mbuf chain for encryption.
4596 * If the original mbuf chain contains a mbuf with a cluster,
4597 * allocate a new cluster and copy the data to the new cluster.
4598 * XXX: this hack is inefficient, but is necessary to handle cases
4599 * of TCP retransmission...
4605 struct mbuf
*n
, **mpp
, *mnew
;
4607 for (n
= m
, mpp
= &m
; n
; n
= n
->m_next
) {
4608 if (n
->m_flags
& M_EXT
) {
4610 * Make a copy only if there are more than one references
4612 * XXX: is this approach effective?
4615 n
->m_ext
.ext_free
||
4616 m_mclhasreference(n
)
4622 if (n
->m_flags
& M_PKTHDR
) {
4623 MGETHDR(mnew
, M_DONTWAIT
, MT_HEADER
); /* MAC-OK */
4626 M_COPY_PKTHDR(mnew
, n
);
4629 MGET(mnew
, M_DONTWAIT
, MT_DATA
);
4637 * Copy data. If we don't have enough space to
4638 * store the whole data, allocate a cluster
4639 * or additional mbufs.
4640 * XXX: we don't use m_copyback(), since the
4641 * function does not use clusters and thus is
4650 if (remain
<= (mm
->m_flags
& M_PKTHDR
? MHLEN
: MLEN
))
4652 else { /* allocate a cluster */
4653 MCLGET(mm
, M_DONTWAIT
);
4654 if (!(mm
->m_flags
& M_EXT
)) {
4658 len
= remain
< MCLBYTES
?
4662 bcopy(n
->m_data
+ copied
, mm
->m_data
,
4669 if (remain
<= 0) /* completed? */
4672 /* need another mbuf */
4673 MGETHDR(mn
, M_DONTWAIT
, MT_HEADER
); /* XXXMAC: tags copied next time in loop? */
4676 mn
->m_pkthdr
.rcvif
= NULL
;
4682 mm
->m_next
= m_free(n
);
4701 * Tags are allocated as mbufs for now, since our minimum size is MLEN, we
4702 * should make use of up to that much space.
4704 #define IPSEC_TAG_HEADER \
4707 struct socket
*socket
;
4708 u_int32_t history_count
;
4709 struct ipsec_history history
[];
4712 #define IPSEC_TAG_SIZE (MLEN - sizeof(struct m_tag))
4713 #define IPSEC_TAG_HDR_SIZE (offsetof(struct ipsec_tag, history[0]))
4714 #define IPSEC_HISTORY_MAX ((IPSEC_TAG_SIZE - IPSEC_TAG_HDR_SIZE) / \
4715 sizeof(struct ipsec_history))
4717 static struct ipsec_tag
*
4723 /* Check if the tag already exists */
4724 tag
= m_tag_locate(m
, KERNEL_MODULE_TAG_ID
, KERNEL_TAG_TYPE_IPSEC
, NULL
);
4727 struct ipsec_tag
*itag
;
4729 /* Allocate a tag */
4730 tag
= m_tag_create(KERNEL_MODULE_TAG_ID
, KERNEL_TAG_TYPE_IPSEC
,
4731 IPSEC_TAG_SIZE
, M_DONTWAIT
, m
);
4734 itag
= (struct ipsec_tag
*)(tag
+ 1);
4736 itag
->history_count
= 0;
4738 m_tag_prepend(m
, tag
);
4742 return tag
? (struct ipsec_tag
*)(tag
+ 1) : NULL
;
4745 static struct ipsec_tag
*
4751 tag
= m_tag_locate(m
, KERNEL_MODULE_TAG_ID
, KERNEL_TAG_TYPE_IPSEC
, NULL
);
4753 return tag
? (struct ipsec_tag
*)(tag
+ 1) : NULL
;
4762 tag
= m_tag_locate(m
, KERNEL_MODULE_TAG_ID
, KERNEL_TAG_TYPE_IPSEC
, NULL
);
4765 m_tag_delete(m
, tag
);
4769 /* if the aux buffer is unnecessary, nuke it. */
4773 struct ipsec_tag
*itag
)
4775 if (itag
&& itag
->socket
== NULL
&& itag
->history_count
== 0) {
4776 m_tag_delete(m
, ((struct m_tag
*)itag
) - 1);
4781 ipsec_setsocket(struct mbuf
*m
, struct socket
*so
)
4783 struct ipsec_tag
*tag
;
4785 /* if so == NULL, don't insist on getting the aux mbuf */
4787 tag
= ipsec_addaux(m
);
4791 tag
= ipsec_findaux(m
);
4794 ipsec_optaux(m
, tag
);
4800 ipsec_getsocket(struct mbuf
*m
)
4802 struct ipsec_tag
*itag
;
4804 itag
= ipsec_findaux(m
);
4806 return itag
->socket
;
4817 struct ipsec_tag
*itag
;
4818 struct ipsec_history
*p
;
4819 itag
= ipsec_addaux(m
);
4822 if (itag
->history_count
== IPSEC_HISTORY_MAX
)
4823 return ENOSPC
; /* XXX */
4825 p
= &itag
->history
[itag
->history_count
];
4826 itag
->history_count
++;
4828 bzero(p
, sizeof(*p
));
4829 p
->ih_proto
= proto
;
4835 struct ipsec_history
*
4840 struct ipsec_tag
*itag
;
4842 itag
= ipsec_findaux(m
);
4845 if (itag
->history_count
== 0)
4848 *lenp
= (int)(itag
->history_count
* sizeof(struct ipsec_history
));
4849 return itag
->history
;
4856 struct ipsec_tag
*itag
;
4858 itag
= ipsec_findaux(m
);
4860 itag
->history_count
= 0;
4862 ipsec_optaux(m
, itag
);
4865 __private_extern__
int
4866 ipsec_send_natt_keepalive(
4867 struct secasvar
*sav
)
4872 struct ip_out_args ipoa
=
4873 { IFSCOPE_NONE
, { 0 }, IPOAF_SELECT_SRCIF
, 0 };
4875 int keepalive_interval
= natt_keepalive_interval
;
4877 lck_mtx_assert(sadb_mutex
, LCK_MTX_ASSERT_NOTOWNED
);
4879 if ((esp_udp_encap_port
& 0xFFFF) == 0 || sav
->remote_ike_port
== 0) return FALSE
;
4881 if (sav
->natt_interval
!= 0) {
4882 keepalive_interval
= (int)sav
->natt_interval
;
4885 // natt timestamp may have changed... reverify
4886 if ((natt_now
- sav
->natt_last_activity
) < keepalive_interval
) return FALSE
;
4888 if (sav
->flags
& SADB_X_EXT_ESP_KEEPALIVE
) return FALSE
; // don't send these from the kernel
4890 m
= m_gethdr(M_NOWAIT
, MT_DATA
);
4891 if (m
== NULL
) return FALSE
;
4893 ip
= (__typeof__(ip
))m_mtod(m
);
4895 // this sends one type of NATT keepalives (Type 1, ESP keepalives, aren't sent by kernel)
4896 if ((sav
->flags
& SADB_X_EXT_ESP_KEEPALIVE
) == 0) {
4900 * Type 2: a UDP packet complete with IP header.
4901 * We must do this because UDP output requires
4902 * an inpcb which we don't have. UDP packet
4903 * contains one byte payload. The byte is set
4906 uh
= (__typeof__(uh
))(void *)((char *)m_mtod(m
) + sizeof(*ip
));
4907 m
->m_len
= sizeof(struct udpiphdr
) + 1;
4908 bzero(m_mtod(m
), m
->m_len
);
4909 m
->m_pkthdr
.len
= m
->m_len
;
4911 ip
->ip_len
= m
->m_len
;
4912 ip
->ip_ttl
= ip_defttl
;
4913 ip
->ip_p
= IPPROTO_UDP
;
4914 if (sav
->sah
->dir
!= IPSEC_DIR_INBOUND
) {
4915 ip
->ip_src
= ((struct sockaddr_in
*)&sav
->sah
->saidx
.src
)->sin_addr
;
4916 ip
->ip_dst
= ((struct sockaddr_in
*)&sav
->sah
->saidx
.dst
)->sin_addr
;
4918 ip
->ip_src
= ((struct sockaddr_in
*)&sav
->sah
->saidx
.dst
)->sin_addr
;
4919 ip
->ip_dst
= ((struct sockaddr_in
*)&sav
->sah
->saidx
.src
)->sin_addr
;
4921 uh
->uh_sport
= htons((u_short
)esp_udp_encap_port
);
4922 uh
->uh_dport
= htons(sav
->remote_ike_port
);
4923 uh
->uh_ulen
= htons(1 + sizeof(*uh
));
4925 *(u_int8_t
*)((char*)m_mtod(m
) + sizeof(*ip
) + sizeof(*uh
)) = 0xFF;
4928 // grab sadb_mutex, to get a local copy of sah's route cache
4929 lck_mtx_lock(sadb_mutex
);
4930 if (ROUTE_UNUSABLE(&sav
->sah
->sa_route
) ||
4931 rt_key(sav
->sah
->sa_route
.ro_rt
)->sa_family
!= AF_INET
)
4932 ROUTE_RELEASE(&sav
->sah
->sa_route
);
4934 route_copyout(&ro
, &sav
->sah
->sa_route
, sizeof(ro
));
4935 lck_mtx_unlock(sadb_mutex
);
4937 necp_mark_packet_as_keepalive(m
, TRUE
);
4939 error
= ip_output(m
, NULL
, &ro
, IP_OUTARGS
| IP_NOIPSEC
, NULL
, &ipoa
);
4941 // grab sadb_mutex, to synchronize the sah's route cache with the local copy
4942 lck_mtx_lock(sadb_mutex
);
4943 route_copyin(&ro
, &sav
->sah
->sa_route
, sizeof(ro
));
4944 lck_mtx_unlock(sadb_mutex
);
4946 sav
->natt_last_activity
= natt_now
;
4952 __private_extern__
bool
4953 ipsec_fill_offload_frame(ifnet_t ifp
,
4954 struct secasvar
*sav
,
4955 struct ifnet_keepalive_offload_frame
*frame
,
4956 size_t frame_data_offset
)
4958 u_int8_t
*data
= NULL
;
4959 struct ip
*ip
= NULL
;
4960 struct udphdr
*uh
= NULL
;
4962 if (sav
== NULL
|| sav
->sah
== NULL
|| frame
== NULL
||
4963 (ifp
!= NULL
&& ifp
->if_index
!= sav
->sah
->outgoing_if
) ||
4964 sav
->sah
->saidx
.dst
.ss_family
!= AF_INET
||
4965 !(sav
->flags
& SADB_X_EXT_NATT
) ||
4966 !(sav
->flags
& SADB_X_EXT_NATT_KEEPALIVE
) ||
4967 !(sav
->flags
& SADB_X_EXT_NATT_KEEPALIVE_OFFLOAD
) ||
4968 sav
->flags
& SADB_X_EXT_ESP_KEEPALIVE
||
4969 (esp_udp_encap_port
& 0xFFFF) == 0 ||
4970 sav
->remote_ike_port
== 0 ||
4971 (natt_keepalive_interval
== 0 && sav
->natt_interval
== 0 && sav
->natt_offload_interval
== 0)) {
4972 /* SA is not eligible for keepalive offload on this interface */
4976 if (frame_data_offset
+ sizeof(struct udpiphdr
) + 1 >
4977 IFNET_KEEPALIVE_OFFLOAD_FRAME_DATA_SIZE
) {
4978 /* Not enough room in this data frame */
4983 ip
= (__typeof__(ip
))(void *)(data
+ frame_data_offset
);
4984 uh
= (__typeof__(uh
))(void *)(data
+ frame_data_offset
+ sizeof(*ip
));
4986 frame
->length
= frame_data_offset
+ sizeof(struct udpiphdr
) + 1;
4987 frame
->type
= IFNET_KEEPALIVE_OFFLOAD_FRAME_IPSEC
;
4988 frame
->ether_type
= IFNET_KEEPALIVE_OFFLOAD_FRAME_ETHERTYPE_IPV4
;
4990 bzero(data
, IFNET_KEEPALIVE_OFFLOAD_FRAME_DATA_SIZE
);
4992 ip
->ip_v
= IPVERSION
;
4993 ip
->ip_hl
= sizeof(struct ip
) >> 2;
4994 ip
->ip_off
&= htons(~IP_OFFMASK
);
4995 ip
->ip_off
&= htons(~IP_MF
);
4996 switch (ip4_ipsec_dfbit
) {
4997 case 0: /* clear DF bit */
4998 ip
->ip_off
&= htons(~IP_DF
);
5000 case 1: /* set DF bit */
5001 ip
->ip_off
|= htons(IP_DF
);
5003 default: /* copy DF bit */
5006 ip
->ip_len
= htons(sizeof(struct udpiphdr
) + 1);
5007 ip
->ip_id
= ip_randomid();
5008 ip
->ip_ttl
= ip_defttl
;
5009 ip
->ip_p
= IPPROTO_UDP
;
5011 if (sav
->sah
->dir
!= IPSEC_DIR_INBOUND
) {
5012 ip
->ip_src
= ((struct sockaddr_in
*)&sav
->sah
->saidx
.src
)->sin_addr
;
5013 ip
->ip_dst
= ((struct sockaddr_in
*)&sav
->sah
->saidx
.dst
)->sin_addr
;
5015 ip
->ip_src
= ((struct sockaddr_in
*)&sav
->sah
->saidx
.dst
)->sin_addr
;
5016 ip
->ip_dst
= ((struct sockaddr_in
*)&sav
->sah
->saidx
.src
)->sin_addr
;
5018 ip
->ip_sum
= in_cksum_hdr_opt(ip
);
5019 uh
->uh_sport
= htons((u_short
)esp_udp_encap_port
);
5020 uh
->uh_dport
= htons(sav
->remote_ike_port
);
5021 uh
->uh_ulen
= htons(1 + sizeof(*uh
));
5023 *(u_int8_t
*)(data
+ frame_data_offset
+ sizeof(*ip
) + sizeof(*uh
)) = 0xFF;
5025 if (sav
->natt_offload_interval
!= 0) {
5026 frame
->interval
= sav
->natt_offload_interval
;
5027 } else if (sav
->natt_interval
!= 0) {
5028 frame
->interval
= sav
->natt_interval
;
5030 frame
->interval
= natt_keepalive_interval
;