]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - sys/net/if_ipsec.c
usb: Fix two typos in source code comments
[FreeBSD/FreeBSD.git] / sys / net / if_ipsec.c
1 /*-
2  * Copyright (c) 2016-2018 Yandex LLC
3  * Copyright (c) 2016-2018 Andrey V. Elsukov <ae@FreeBSD.org>
4  * All rights reserved.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions
8  * are met:
9  *
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
20  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
21  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
25  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26  */
27
28 #include <sys/cdefs.h>
29 #include "opt_inet.h"
30 #include "opt_inet6.h"
31 #include "opt_ipsec.h"
32
33 #include <sys/param.h>
34 #include <sys/systm.h>
35 #include <sys/kernel.h>
36 #include <sys/fnv_hash.h>
37 #include <sys/jail.h>
38 #include <sys/lock.h>
39 #include <sys/malloc.h>
40 #include <sys/mbuf.h>
41 #include <sys/module.h>
42 #include <sys/socket.h>
43 #include <sys/sockio.h>
44 #include <sys/sx.h>
45 #include <sys/errno.h>
46 #include <sys/sysctl.h>
47 #include <sys/priv.h>
48 #include <sys/proc.h>
49 #include <sys/conf.h>
50
51 #include <net/if.h>
52 #include <net/if_var.h>
53 #include <net/if_clone.h>
54 #include <net/if_types.h>
55 #include <net/bpf.h>
56 #include <net/route.h>
57 #include <net/vnet.h>
58
59 #include <netinet/in.h>
60 #include <netinet/in_var.h>
61 #include <netinet/ip.h>
62 #include <netinet/ip_encap.h>
63
64 #include <netinet/ip6.h>
65 #include <netinet6/in6_var.h>
66 #include <netinet6/scope6_var.h>
67
68 #include <netipsec/ipsec.h>
69 #ifdef INET6
70 #include <netipsec/ipsec6.h>
71 #endif
72
73 #include <net/if_ipsec.h>
74 #include <netipsec/key.h>
75
76 #include <security/mac/mac_framework.h>
77
78 static MALLOC_DEFINE(M_IPSEC, "ipsec", "IPsec Virtual Tunnel Interface");
79 static const char ipsecname[] = "ipsec";
80
81 #if defined(INET) && defined(INET6)
82 #define IPSEC_SPCOUNT           4
83 #else
84 #define IPSEC_SPCOUNT           2
85 #endif
86
87 struct ipsec_softc {
88         struct ifnet            *ifp;
89         struct secpolicy        *sp[IPSEC_SPCOUNT];
90         uint32_t                reqid;
91         u_int                   family;
92         u_int                   fibnum;
93
94         CK_LIST_ENTRY(ipsec_softc) idhash;
95         CK_LIST_ENTRY(ipsec_softc) srchash;
96 };
97
98 #define IPSEC_RLOCK_TRACKER     struct epoch_tracker ipsec_et
99 #define IPSEC_RLOCK()   epoch_enter_preempt(net_epoch_preempt, &ipsec_et)
100 #define IPSEC_RUNLOCK() epoch_exit_preempt(net_epoch_preempt, &ipsec_et)
101 #define IPSEC_WAIT()    epoch_wait_preempt(net_epoch_preempt)
102
103 #ifndef IPSEC_HASH_SIZE
104 #define IPSEC_HASH_SIZE (1 << 5)
105 #endif
106
107 CK_LIST_HEAD(ipsec_iflist, ipsec_softc);
108 VNET_DEFINE_STATIC(struct ipsec_iflist *, ipsec_idhtbl) = NULL;
109 #define V_ipsec_idhtbl          VNET(ipsec_idhtbl)
110
111 #ifdef INET
112 VNET_DEFINE_STATIC(struct ipsec_iflist *, ipsec4_srchtbl) = NULL;
113 #define V_ipsec4_srchtbl        VNET(ipsec4_srchtbl)
114 static const struct srcaddrtab *ipsec4_srctab = NULL;
115 #endif
116
117 #ifdef INET6
118 VNET_DEFINE_STATIC(struct ipsec_iflist *, ipsec6_srchtbl) = NULL;
119 #define V_ipsec6_srchtbl        VNET(ipsec6_srchtbl)
120 static const struct srcaddrtab *ipsec6_srctab = NULL;
121 #endif
122
123 static struct ipsec_iflist *
124 ipsec_idhash(uint32_t id)
125 {
126
127         return (&V_ipsec_idhtbl[fnv_32_buf(&id, sizeof(id),
128             FNV1_32_INIT) & (IPSEC_HASH_SIZE - 1)]);
129 }
130
131 static struct ipsec_iflist *
132 ipsec_srchash(const struct sockaddr *sa)
133 {
134         uint32_t hval;
135
136         switch (sa->sa_family) {
137 #ifdef INET
138         case AF_INET:
139                 hval = fnv_32_buf(
140                     &((const struct sockaddr_in *)sa)->sin_addr.s_addr,
141                     sizeof(in_addr_t), FNV1_32_INIT);
142                 return (&V_ipsec4_srchtbl[hval & (IPSEC_HASH_SIZE - 1)]);
143 #endif
144 #ifdef INET6
145         case AF_INET6:
146                 hval = fnv_32_buf(
147                     &((const struct sockaddr_in6 *)sa)->sin6_addr,
148                     sizeof(struct in6_addr), FNV1_32_INIT);
149                 return (&V_ipsec6_srchtbl[hval & (IPSEC_HASH_SIZE - 1)]);
150 #endif
151         }
152         return (NULL);
153 }
154
155 /*
156  * ipsec_ioctl_sx protects from concurrent ioctls.
157  */
158 static struct sx ipsec_ioctl_sx;
159 SX_SYSINIT(ipsec_ioctl_sx, &ipsec_ioctl_sx, "ipsec_ioctl");
160
161 static int      ipsec_init_reqid(struct ipsec_softc *);
162 static int      ipsec_set_tunnel(struct ipsec_softc *, struct sockaddr *,
163     struct sockaddr *, uint32_t);
164 static void     ipsec_delete_tunnel(struct ipsec_softc *);
165
166 static int      ipsec_set_addresses(struct ifnet *, struct sockaddr *,
167     struct sockaddr *);
168 static int      ipsec_set_reqid(struct ipsec_softc *, uint32_t);
169 static void     ipsec_set_running(struct ipsec_softc *);
170
171 #ifdef VIMAGE
172 static void     ipsec_reassign(struct ifnet *, struct vnet *, char *);
173 #endif
174 static void     ipsec_srcaddr(void *, const struct sockaddr *, int);
175 static int      ipsec_ioctl(struct ifnet *, u_long, caddr_t);
176 static int      ipsec_transmit(struct ifnet *, struct mbuf *);
177 static int      ipsec_output(struct ifnet *, struct mbuf *,
178     const struct sockaddr *, struct route *);
179 static void     ipsec_qflush(struct ifnet *);
180 static int      ipsec_clone_create(struct if_clone *, int, caddr_t);
181 static void     ipsec_clone_destroy(struct ifnet *);
182
183 VNET_DEFINE_STATIC(struct if_clone *, ipsec_cloner);
184 #define V_ipsec_cloner          VNET(ipsec_cloner)
185
186 static int
187 ipsec_clone_create(struct if_clone *ifc, int unit, caddr_t params)
188 {
189         struct ipsec_softc *sc;
190         struct ifnet *ifp;
191
192         sc = malloc(sizeof(*sc), M_IPSEC, M_WAITOK | M_ZERO);
193         sc->fibnum = curthread->td_proc->p_fibnum;
194         sc->ifp = ifp = if_alloc(IFT_TUNNEL);
195         ifp->if_softc = sc;
196         if_initname(ifp, ipsecname, unit);
197
198         ifp->if_addrlen = 0;
199         ifp->if_mtu = IPSEC_MTU;
200         ifp->if_flags  = IFF_POINTOPOINT | IFF_MULTICAST;
201         ifp->if_ioctl  = ipsec_ioctl;
202         ifp->if_transmit  = ipsec_transmit;
203         ifp->if_qflush  = ipsec_qflush;
204         ifp->if_output = ipsec_output;
205 #ifdef VIMAGE
206         ifp->if_reassign = ipsec_reassign;
207 #endif
208         if_attach(ifp);
209         bpfattach(ifp, DLT_NULL, sizeof(uint32_t));
210
211         return (0);
212 }
213
214 #ifdef VIMAGE
215 static void
216 ipsec_reassign(struct ifnet *ifp, struct vnet *new_vnet __unused,
217     char *unused __unused)
218 {
219         struct ipsec_softc *sc;
220
221         sx_xlock(&ipsec_ioctl_sx);
222         sc = ifp->if_softc;
223         if (sc != NULL)
224                 ipsec_delete_tunnel(sc);
225         sx_xunlock(&ipsec_ioctl_sx);
226 }
227 #endif /* VIMAGE */
228
229 static void
230 ipsec_clone_destroy(struct ifnet *ifp)
231 {
232         struct ipsec_softc *sc;
233
234         sx_xlock(&ipsec_ioctl_sx);
235         sc = ifp->if_softc;
236         ipsec_delete_tunnel(sc);
237         /*
238          * Delete softc from idhash on interface destroy, since
239          * ipsec_delete_tunnel() keeps reqid unchanged.
240          */
241         if (sc->reqid != 0)
242                 CK_LIST_REMOVE(sc, idhash);
243         bpfdetach(ifp);
244         if_detach(ifp);
245         ifp->if_softc = NULL;
246         sx_xunlock(&ipsec_ioctl_sx);
247
248         IPSEC_WAIT();
249         if_free(ifp);
250         free(sc, M_IPSEC);
251 }
252
253 static struct ipsec_iflist *
254 ipsec_hashinit(void)
255 {
256         struct ipsec_iflist *hash;
257         int i;
258
259         hash = malloc(sizeof(struct ipsec_iflist) * IPSEC_HASH_SIZE,
260             M_IPSEC, M_WAITOK);
261         for (i = 0; i < IPSEC_HASH_SIZE; i++)
262                 CK_LIST_INIT(&hash[i]);
263
264         return (hash);
265 }
266
267 static void
268 vnet_ipsec_init(const void *unused __unused)
269 {
270
271         V_ipsec_idhtbl = ipsec_hashinit();
272 #ifdef INET
273         V_ipsec4_srchtbl = ipsec_hashinit();
274         if (IS_DEFAULT_VNET(curvnet))
275                 ipsec4_srctab = ip_encap_register_srcaddr(ipsec_srcaddr,
276                     NULL, M_WAITOK);
277 #endif
278 #ifdef INET6
279         V_ipsec6_srchtbl = ipsec_hashinit();
280         if (IS_DEFAULT_VNET(curvnet))
281                 ipsec6_srctab = ip6_encap_register_srcaddr(ipsec_srcaddr,
282                     NULL, M_WAITOK);
283 #endif
284         V_ipsec_cloner = if_clone_simple(ipsecname, ipsec_clone_create,
285             ipsec_clone_destroy, 0);
286 }
287 VNET_SYSINIT(vnet_ipsec_init, SI_SUB_PROTO_IFATTACHDOMAIN, SI_ORDER_ANY,
288     vnet_ipsec_init, NULL);
289
290 static void
291 vnet_ipsec_uninit(const void *unused __unused)
292 {
293
294         if_clone_detach(V_ipsec_cloner);
295         free(V_ipsec_idhtbl, M_IPSEC);
296         /*
297          * Use V_ipsec_idhtbl pointer as indicator that VNET is going to be
298          * destroyed, it is used by ipsec_srcaddr() callback.
299          */
300         V_ipsec_idhtbl = NULL;
301         IPSEC_WAIT();
302
303 #ifdef INET
304         if (IS_DEFAULT_VNET(curvnet))
305                 ip_encap_unregister_srcaddr(ipsec4_srctab);
306         free(V_ipsec4_srchtbl, M_IPSEC);
307 #endif
308 #ifdef INET6
309         if (IS_DEFAULT_VNET(curvnet))
310                 ip6_encap_unregister_srcaddr(ipsec6_srctab);
311         free(V_ipsec6_srchtbl, M_IPSEC);
312 #endif
313 }
314 VNET_SYSUNINIT(vnet_ipsec_uninit, SI_SUB_PROTO_IFATTACHDOMAIN, SI_ORDER_ANY,
315     vnet_ipsec_uninit, NULL);
316
317 static struct secpolicy *
318 ipsec_getpolicy(struct ipsec_softc *sc, int dir, sa_family_t af)
319 {
320
321         switch (af) {
322 #ifdef INET
323         case AF_INET:
324                 return (sc->sp[(dir == IPSEC_DIR_INBOUND ? 0: 1)]);
325 #endif
326 #ifdef INET6
327         case AF_INET6:
328                 return (sc->sp[(dir == IPSEC_DIR_INBOUND ? 0: 1)
329 #ifdef INET
330                         + 2
331 #endif
332                 ]);
333 #endif
334         }
335         return (NULL);
336 }
337
338 static struct secasindex *
339 ipsec_getsaidx(struct ipsec_softc *sc, int dir, sa_family_t af)
340 {
341         struct secpolicy *sp;
342
343         sp = ipsec_getpolicy(sc, dir, af);
344         if (sp == NULL)
345                 return (NULL);
346         return (&sp->req[0]->saidx);
347 }
348
349 static int
350 ipsec_transmit(struct ifnet *ifp, struct mbuf *m)
351 {
352         IPSEC_RLOCK_TRACKER;
353         struct ipsec_softc *sc;
354         struct secpolicy *sp;
355         struct ip *ip;
356         uint32_t af;
357         int error;
358
359         IPSEC_RLOCK();
360 #ifdef MAC
361         error = mac_ifnet_check_transmit(ifp, m);
362         if (error) {
363                 m_freem(m);
364                 goto err;
365         }
366 #endif
367         error = ENETDOWN;
368         sc = ifp->if_softc;
369         if ((ifp->if_drv_flags & IFF_DRV_RUNNING) == 0 ||
370             (ifp->if_flags & IFF_MONITOR) != 0 ||
371             (ifp->if_flags & IFF_UP) == 0 || sc->family == 0) {
372                 m_freem(m);
373                 goto err;
374         }
375
376         /* Determine address family to correctly handle packet in BPF */
377         ip = mtod(m, struct ip *);
378         switch (ip->ip_v) {
379 #ifdef INET
380         case IPVERSION:
381                 af = AF_INET;
382                 break;
383 #endif
384 #ifdef INET6
385         case (IPV6_VERSION >> 4):
386                 af = AF_INET6;
387                 break;
388 #endif
389         default:
390                 error = EAFNOSUPPORT;
391                 m_freem(m);
392                 goto err;
393         }
394
395         /*
396          * Loop prevention.
397          * XXX: for now just check presence of IPSEC_OUT_DONE mbuf tag.
398          *      We can read full chain and compare destination address,
399          *      proto and mode from xform_history with values from softc.
400          */
401         if (m_tag_find(m, PACKET_TAG_IPSEC_OUT_DONE, NULL) != NULL) {
402                 m_freem(m);
403                 goto err;
404         }
405
406         sp = ipsec_getpolicy(sc, IPSEC_DIR_OUTBOUND, af);
407         key_addref(sp);
408         M_SETFIB(m, sc->fibnum);
409
410         BPF_MTAP2(ifp, &af, sizeof(af), m);
411         if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1);
412         if_inc_counter(ifp, IFCOUNTER_OBYTES, m->m_pkthdr.len);
413
414         switch (af) {
415 #ifdef INET
416         case AF_INET:
417                 error = ipsec4_process_packet(m, sp, NULL);
418                 break;
419 #endif
420 #ifdef INET6
421         case AF_INET6:
422                 error = ipsec6_process_packet(m, sp, NULL);
423                 break;
424 #endif
425         default:
426                 panic("%s: unknown address family\n", __func__);
427         }
428 err:
429         if (error != 0)
430                 if_inc_counter(ifp, IFCOUNTER_OERRORS, 1);
431         IPSEC_RUNLOCK();
432         return (error);
433 }
434
435 static void
436 ipsec_qflush(struct ifnet *ifp __unused)
437 {
438
439 }
440
441 static int
442 ipsec_output(struct ifnet *ifp, struct mbuf *m, const struct sockaddr *dst,
443         struct route *ro)
444 {
445
446         return (ifp->if_transmit(ifp, m));
447 }
448
449 int
450 ipsec_if_input(struct mbuf *m, struct secasvar *sav, uint32_t af)
451 {
452         IPSEC_RLOCK_TRACKER;
453         struct secasindex *saidx;
454         struct ipsec_softc *sc;
455         struct ifnet *ifp;
456
457         if (sav->state != SADB_SASTATE_MATURE &&
458             sav->state != SADB_SASTATE_DYING) {
459                 m_freem(m);
460                 return (ENETDOWN);
461         }
462
463         if (sav->sah->saidx.mode != IPSEC_MODE_TUNNEL ||
464             sav->sah->saidx.proto != IPPROTO_ESP)
465                 return (0);
466
467         IPSEC_RLOCK();
468         CK_LIST_FOREACH(sc, ipsec_idhash(sav->sah->saidx.reqid), idhash) {
469                 if (sc->family == 0)
470                         continue;
471                 saidx = ipsec_getsaidx(sc, IPSEC_DIR_INBOUND,
472                     sav->sah->saidx.src.sa.sa_family);
473                 /* SA's reqid should match reqid in SP */
474                 if (saidx == NULL ||
475                     sav->sah->saidx.reqid != saidx->reqid)
476                         continue;
477                 /* SAH's addresses should match tunnel endpoints. */
478                 if (key_sockaddrcmp(&sav->sah->saidx.dst.sa,
479                     &saidx->dst.sa, 0) != 0)
480                         continue;
481                 if (key_sockaddrcmp(&sav->sah->saidx.src.sa,
482                     &saidx->src.sa, 0) == 0)
483                         break;
484         }
485         if (sc == NULL) {
486                 IPSEC_RUNLOCK();
487                 /* Tunnel was not found. Nothing to do. */
488                 return (0);
489         }
490         ifp = sc->ifp;
491         if ((ifp->if_drv_flags & IFF_DRV_RUNNING) == 0 ||
492             (ifp->if_flags & IFF_UP) == 0) {
493                 IPSEC_RUNLOCK();
494                 m_freem(m);
495                 return (ENETDOWN);
496         }
497         /*
498          * We found matching and working tunnel.
499          * Set its ifnet as receiving interface.
500          */
501         m->m_pkthdr.rcvif = ifp;
502
503         m_clrprotoflags(m);
504         M_SETFIB(m, ifp->if_fib);
505         BPF_MTAP2(ifp, &af, sizeof(af), m);
506         if_inc_counter(ifp, IFCOUNTER_IPACKETS, 1);
507         if_inc_counter(ifp, IFCOUNTER_IBYTES, m->m_pkthdr.len);
508         if ((ifp->if_flags & IFF_MONITOR) != 0) {
509                 IPSEC_RUNLOCK();
510                 m_freem(m);
511                 return (ENETDOWN);
512         }
513         IPSEC_RUNLOCK();
514         return (0);
515 }
516
517 static int
518 ipsec_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
519 {
520         struct ifreq *ifr = (struct ifreq*)data;
521         struct sockaddr *dst, *src;
522         struct ipsec_softc *sc;
523         struct secasindex *saidx;
524 #ifdef INET
525         struct sockaddr_in *sin = NULL;
526 #endif
527 #ifdef INET6
528         struct sockaddr_in6 *sin6 = NULL;
529 #endif
530         uint32_t reqid;
531         int error;
532
533         switch (cmd) {
534         case SIOCSIFADDR:
535                 ifp->if_flags |= IFF_UP;
536         case SIOCADDMULTI:
537         case SIOCDELMULTI:
538         case SIOCGIFMTU:
539         case SIOCSIFFLAGS:
540                 return (0);
541         case SIOCSIFMTU:
542                 if (ifr->ifr_mtu < IPSEC_MTU_MIN ||
543                     ifr->ifr_mtu > IPSEC_MTU_MAX)
544                         return (EINVAL);
545                 else
546                         ifp->if_mtu = ifr->ifr_mtu;
547                 return (0);
548         }
549         sx_xlock(&ipsec_ioctl_sx);
550         sc = ifp->if_softc;
551         /* Check that softc is still here */
552         if (sc == NULL) {
553                 error = ENXIO;
554                 goto bad;
555         }
556         error = 0;
557         switch (cmd) {
558         case SIOCSIFPHYADDR:
559 #ifdef INET6
560         case SIOCSIFPHYADDR_IN6:
561 #endif
562                 error = EINVAL;
563                 switch (cmd) {
564 #ifdef INET
565                 case SIOCSIFPHYADDR:
566                         src = (struct sockaddr *)
567                                 &(((struct in_aliasreq *)data)->ifra_addr);
568                         dst = (struct sockaddr *)
569                                 &(((struct in_aliasreq *)data)->ifra_dstaddr);
570                         break;
571 #endif
572 #ifdef INET6
573                 case SIOCSIFPHYADDR_IN6:
574                         src = (struct sockaddr *)
575                                 &(((struct in6_aliasreq *)data)->ifra_addr);
576                         dst = (struct sockaddr *)
577                                 &(((struct in6_aliasreq *)data)->ifra_dstaddr);
578                         break;
579 #endif
580                 default:
581                         goto bad;
582                 }
583                 /* sa_family must be equal */
584                 if (src->sa_family != dst->sa_family ||
585                     src->sa_len != dst->sa_len)
586                         goto bad;
587
588                 /* validate sa_len */
589                 switch (src->sa_family) {
590 #ifdef INET
591                 case AF_INET:
592                         if (src->sa_len != sizeof(struct sockaddr_in))
593                                 goto bad;
594                         break;
595 #endif
596 #ifdef INET6
597                 case AF_INET6:
598                         if (src->sa_len != sizeof(struct sockaddr_in6))
599                                 goto bad;
600                         break;
601 #endif
602                 default:
603                         error = EAFNOSUPPORT;
604                         goto bad;
605                 }
606                 /* check sa_family looks sane for the cmd */
607                 error = EAFNOSUPPORT;
608                 switch (cmd) {
609 #ifdef INET
610                 case SIOCSIFPHYADDR:
611                         if (src->sa_family == AF_INET)
612                                 break;
613                         goto bad;
614 #endif
615 #ifdef INET6
616                 case SIOCSIFPHYADDR_IN6:
617                         if (src->sa_family == AF_INET6)
618                                 break;
619                         goto bad;
620 #endif
621                 }
622                 error = EADDRNOTAVAIL;
623                 switch (src->sa_family) {
624 #ifdef INET
625                 case AF_INET:
626                         if (satosin(src)->sin_addr.s_addr == INADDR_ANY ||
627                             satosin(dst)->sin_addr.s_addr == INADDR_ANY)
628                                 goto bad;
629                         break;
630 #endif
631 #ifdef INET6
632                 case AF_INET6:
633                         if (IN6_IS_ADDR_UNSPECIFIED(
634                             &satosin6(src)->sin6_addr) ||
635                             IN6_IS_ADDR_UNSPECIFIED(
636                             &satosin6(dst)->sin6_addr))
637                                 goto bad;
638                         /*
639                          * Check validity of the scope zone ID of the
640                          * addresses, and convert it into the kernel
641                          * internal form if necessary.
642                          */
643                         error = sa6_embedscope(satosin6(src), 0);
644                         if (error != 0)
645                                 goto bad;
646                         error = sa6_embedscope(satosin6(dst), 0);
647                         if (error != 0)
648                                 goto bad;
649 #endif
650                 };
651                 error = ipsec_set_addresses(ifp, src, dst);
652                 break;
653         case SIOCDIFPHYADDR:
654                 ipsec_delete_tunnel(sc);
655                 break;
656         case SIOCGIFPSRCADDR:
657         case SIOCGIFPDSTADDR:
658 #ifdef INET6
659         case SIOCGIFPSRCADDR_IN6:
660         case SIOCGIFPDSTADDR_IN6:
661 #endif
662                 if (sc->family == 0) {
663                         error = EADDRNOTAVAIL;
664                         break;
665                 }
666                 saidx = ipsec_getsaidx(sc, IPSEC_DIR_OUTBOUND, sc->family);
667                 if (saidx == NULL) {
668                         error = ENXIO;
669                         break;
670                 }
671                 switch (cmd) {
672 #ifdef INET
673                 case SIOCGIFPSRCADDR:
674                 case SIOCGIFPDSTADDR:
675                         if (saidx->src.sa.sa_family != AF_INET) {
676                                 error = EADDRNOTAVAIL;
677                                 break;
678                         }
679                         sin = (struct sockaddr_in *)&ifr->ifr_addr;
680                         memset(sin, 0, sizeof(*sin));
681                         sin->sin_family = AF_INET;
682                         sin->sin_len = sizeof(*sin);
683                         break;
684 #endif
685 #ifdef INET6
686                 case SIOCGIFPSRCADDR_IN6:
687                 case SIOCGIFPDSTADDR_IN6:
688                         if (saidx->src.sa.sa_family != AF_INET6) {
689                                 error = EADDRNOTAVAIL;
690                                 break;
691                         }
692                         sin6 = (struct sockaddr_in6 *)
693                                 &(((struct in6_ifreq *)data)->ifr_addr);
694                         memset(sin6, 0, sizeof(*sin6));
695                         sin6->sin6_family = AF_INET6;
696                         sin6->sin6_len = sizeof(*sin6);
697                         break;
698 #endif
699                 default:
700                         error = EAFNOSUPPORT;
701                 }
702                 if (error == 0) {
703                         switch (cmd) {
704 #ifdef INET
705                         case SIOCGIFPSRCADDR:
706                                 sin->sin_addr = saidx->src.sin.sin_addr;
707                                 break;
708                         case SIOCGIFPDSTADDR:
709                                 sin->sin_addr = saidx->dst.sin.sin_addr;
710                                 break;
711 #endif
712 #ifdef INET6
713                         case SIOCGIFPSRCADDR_IN6:
714                                 sin6->sin6_addr = saidx->src.sin6.sin6_addr;
715                                 break;
716                         case SIOCGIFPDSTADDR_IN6:
717                                 sin6->sin6_addr = saidx->dst.sin6.sin6_addr;
718                                 break;
719 #endif
720                         }
721                 }
722                 if (error != 0)
723                         break;
724                 switch (cmd) {
725 #ifdef INET
726                 case SIOCGIFPSRCADDR:
727                 case SIOCGIFPDSTADDR:
728                         error = prison_if(curthread->td_ucred,
729                             (struct sockaddr *)sin);
730                         if (error != 0)
731                                 memset(sin, 0, sizeof(*sin));
732                         break;
733 #endif
734 #ifdef INET6
735                 case SIOCGIFPSRCADDR_IN6:
736                 case SIOCGIFPDSTADDR_IN6:
737                         error = prison_if(curthread->td_ucred,
738                             (struct sockaddr *)sin6);
739                         if (error == 0)
740                                 error = sa6_recoverscope(sin6);
741                         if (error != 0)
742                                 memset(sin6, 0, sizeof(*sin6));
743 #endif
744                 }
745                 break;
746         case SIOCGTUNFIB:
747                 ifr->ifr_fib = sc->fibnum;
748                 break;
749         case SIOCSTUNFIB:
750                 if ((error = priv_check(curthread, PRIV_NET_SETIFFIB)) != 0)
751                         break;
752                 if (ifr->ifr_fib >= rt_numfibs)
753                         error = EINVAL;
754                 else
755                         sc->fibnum = ifr->ifr_fib;
756                 break;
757         case IPSECGREQID:
758                 reqid = sc->reqid;
759                 error = copyout(&reqid, ifr_data_get_ptr(ifr), sizeof(reqid));
760                 break;
761         case IPSECSREQID:
762                 if ((error = priv_check(curthread, PRIV_NET_SETIFCAP)) != 0)
763                         break;
764                 error = copyin(ifr_data_get_ptr(ifr), &reqid, sizeof(reqid));
765                 if (error != 0)
766                         break;
767                 error = ipsec_set_reqid(sc, reqid);
768                 break;
769         default:
770                 error = EINVAL;
771                 break;
772         }
773 bad:
774         sx_xunlock(&ipsec_ioctl_sx);
775         return (error);
776 }
777
778 /*
779  * Check that ingress address belongs to local host.
780  */
781 static void
782 ipsec_set_running(struct ipsec_softc *sc)
783 {
784         struct secasindex *saidx;
785         int localip;
786
787         saidx = ipsec_getsaidx(sc, IPSEC_DIR_OUTBOUND, sc->family);
788         if (saidx == NULL)
789                 return;
790         localip = 0;
791         switch (sc->family) {
792 #ifdef INET
793         case AF_INET:
794                 localip = in_localip(saidx->src.sin.sin_addr);
795                 break;
796 #endif
797 #ifdef INET6
798         case AF_INET6:
799                 localip = in6_localip(&saidx->src.sin6.sin6_addr);
800                 break;
801 #endif
802         }
803         if (localip != 0)
804                 sc->ifp->if_drv_flags |= IFF_DRV_RUNNING;
805         else
806                 sc->ifp->if_drv_flags &= ~IFF_DRV_RUNNING;
807 }
808
809 /*
810  * ifaddr_event handler.
811  * Clear IFF_DRV_RUNNING flag when ingress address disappears to prevent
812  * source address spoofing.
813  */
814 static void
815 ipsec_srcaddr(void *arg __unused, const struct sockaddr *sa,
816     int event __unused)
817 {
818         struct ipsec_softc *sc;
819         struct secasindex *saidx;
820         struct ipsec_iflist *iflist;
821
822         /* Check that VNET is ready */
823         if (V_ipsec_idhtbl == NULL)
824                 return;
825
826         NET_EPOCH_ASSERT();
827         iflist = ipsec_srchash(sa);
828         if (iflist == NULL)
829                 return;
830         CK_LIST_FOREACH(sc, iflist, srchash) {
831                 if (sc->family == 0)
832                         continue;
833                 saidx = ipsec_getsaidx(sc, IPSEC_DIR_OUTBOUND, sa->sa_family);
834                 if (saidx == NULL ||
835                     key_sockaddrcmp(&saidx->src.sa, sa, 0) != 0)
836                         continue;
837                 ipsec_set_running(sc);
838         }
839 }
840
841 /*
842  * Allocate new private security policies for tunneling interface.
843  * Each tunneling interface has following security policies for
844  * both AF:
845  *   0.0.0.0/0[any] 0.0.0.0/0[any] -P in \
846  *      ipsec esp/tunnel/RemoteIP-LocalIP/unique:reqid
847  *   0.0.0.0/0[any] 0.0.0.0/0[any] -P out \
848  *      ipsec esp/tunnel/LocalIP-RemoteIP/unique:reqid
849  */
850 static int
851 ipsec_newpolicies(struct ipsec_softc *sc, struct secpolicy *sp[IPSEC_SPCOUNT],
852     const struct sockaddr *src, const struct sockaddr *dst, uint32_t reqid)
853 {
854         struct ipsecrequest *isr;
855         int i;
856
857         memset(sp, 0, sizeof(struct secpolicy *) * IPSEC_SPCOUNT);
858         for (i = 0; i < IPSEC_SPCOUNT; i++) {
859                 if ((sp[i] = key_newsp()) == NULL)
860                         goto fail;
861                 if ((isr = ipsec_newisr()) == NULL)
862                         goto fail;
863
864                 sp[i]->policy = IPSEC_POLICY_IPSEC;
865                 sp[i]->state = IPSEC_SPSTATE_DEAD;
866                 sp[i]->req[sp[i]->tcount++] = isr;
867                 sp[i]->created = time_second;
868                 /* Use priority field to store if_index */
869                 sp[i]->priority = sc->ifp->if_index;
870                 isr->level = IPSEC_LEVEL_UNIQUE;
871                 isr->saidx.proto = IPPROTO_ESP;
872                 isr->saidx.mode = IPSEC_MODE_TUNNEL;
873                 isr->saidx.reqid = reqid;
874                 if (i % 2 == 0) {
875                         sp[i]->spidx.dir = IPSEC_DIR_INBOUND;
876                         bcopy(src, &isr->saidx.dst, src->sa_len);
877                         bcopy(dst, &isr->saidx.src, dst->sa_len);
878                 } else {
879                         sp[i]->spidx.dir = IPSEC_DIR_OUTBOUND;
880                         bcopy(src, &isr->saidx.src, src->sa_len);
881                         bcopy(dst, &isr->saidx.dst, dst->sa_len);
882                 }
883                 sp[i]->spidx.ul_proto = IPSEC_ULPROTO_ANY;
884 #ifdef INET
885                 if (i < 2) {
886                         sp[i]->spidx.src.sa.sa_family =
887                             sp[i]->spidx.dst.sa.sa_family = AF_INET;
888                         sp[i]->spidx.src.sa.sa_len =
889                             sp[i]->spidx.dst.sa.sa_len =
890                             sizeof(struct sockaddr_in);
891                         continue;
892                 }
893 #endif
894 #ifdef INET6
895                 sp[i]->spidx.src.sa.sa_family =
896                     sp[i]->spidx.dst.sa.sa_family = AF_INET6;
897                 sp[i]->spidx.src.sa.sa_len =
898                     sp[i]->spidx.dst.sa.sa_len = sizeof(struct sockaddr_in6);
899 #endif
900         }
901         return (0);
902 fail:
903         for (i = 0; i < IPSEC_SPCOUNT; i++)
904                 key_freesp(&sp[i]);
905         return (ENOMEM);
906 }
907
908 static int
909 ipsec_check_reqid(uint32_t reqid)
910 {
911         struct ipsec_softc *sc;
912
913         sx_assert(&ipsec_ioctl_sx, SA_XLOCKED);
914         CK_LIST_FOREACH(sc, ipsec_idhash(reqid), idhash) {
915                 if (sc->reqid == reqid)
916                         return (EEXIST);
917         }
918         return (0);
919 }
920
921 /*
922  * We use key_newreqid() to automatically obtain unique reqid.
923  * Then we check that given id is unique, i.e. it is not used by
924  * another if_ipsec(4) interface. This macro limits the number of
925  * tries to get unique id.
926  */
927 #define IPSEC_REQID_TRYCNT      64
928 static int
929 ipsec_init_reqid(struct ipsec_softc *sc)
930 {
931         uint32_t reqid;
932         int trycount;
933
934         sx_assert(&ipsec_ioctl_sx, SA_XLOCKED);
935         if (sc->reqid != 0) /* already initialized */
936                 return (0);
937
938         trycount = IPSEC_REQID_TRYCNT;
939         while (--trycount > 0) {
940                 reqid = key_newreqid();
941                 if (ipsec_check_reqid(reqid) == 0)
942                         break;
943         }
944         if (trycount == 0)
945                 return (EEXIST);
946         sc->reqid = reqid;
947         CK_LIST_INSERT_HEAD(ipsec_idhash(reqid), sc, idhash);
948         return (0);
949 }
950
951 /*
952  * Set or update reqid for given tunneling interface.
953  * When specified reqid is zero, generate new one.
954  * We are protected by ioctl_sx lock from concurrent id generation.
955  * Also softc would not disappear while we hold ioctl_sx lock.
956  */
957 static int
958 ipsec_set_reqid(struct ipsec_softc *sc, uint32_t reqid)
959 {
960         struct secasindex *saidx;
961
962         sx_assert(&ipsec_ioctl_sx, SA_XLOCKED);
963
964         if (sc->reqid == reqid && reqid != 0)
965                 return (0);
966
967         if (reqid != 0) {
968                 /* Check that specified reqid doesn't exist */
969                 if (ipsec_check_reqid(reqid) != 0)
970                         return (EEXIST);
971                 if (sc->reqid != 0) {
972                         CK_LIST_REMOVE(sc, idhash);
973                         IPSEC_WAIT();
974                 }
975                 sc->reqid = reqid;
976                 CK_LIST_INSERT_HEAD(ipsec_idhash(reqid), sc, idhash);
977         } else {
978                 /* Generate new reqid */
979                 if (ipsec_init_reqid(sc) != 0)
980                         return (EEXIST);
981         }
982
983         /* Tunnel isn't fully configured, just return. */
984         if (sc->family == 0)
985                 return (0);
986
987         saidx = ipsec_getsaidx(sc, IPSEC_DIR_OUTBOUND, sc->family);
988         KASSERT(saidx != NULL,
989             ("saidx is NULL, but family is %d", sc->family));
990         return (ipsec_set_tunnel(sc, &saidx->src.sa, &saidx->dst.sa,
991             sc->reqid));
992 }
993
994 /*
995  * Set tunnel endpoints addresses.
996  */
997 static int
998 ipsec_set_addresses(struct ifnet *ifp, struct sockaddr *src,
999     struct sockaddr *dst)
1000 {
1001         struct ipsec_softc *sc;
1002         struct secasindex *saidx;
1003
1004         sx_assert(&ipsec_ioctl_sx, SA_XLOCKED);
1005
1006         sc = ifp->if_softc;
1007         if (sc->family != 0) {
1008                 saidx = ipsec_getsaidx(sc, IPSEC_DIR_OUTBOUND,
1009                     src->sa_family);
1010                 if (saidx != NULL && saidx->reqid == sc->reqid &&
1011                     key_sockaddrcmp(&saidx->src.sa, src, 0) == 0 &&
1012                     key_sockaddrcmp(&saidx->dst.sa, dst, 0) == 0)
1013                         return (0); /* Nothing has been changed. */
1014         }
1015         /* If reqid is not set, generate new one. */
1016         if (ipsec_init_reqid(sc) != 0)
1017                 return (EEXIST);
1018         return (ipsec_set_tunnel(sc, src, dst, sc->reqid));
1019 }
1020
1021 static int
1022 ipsec_set_tunnel(struct ipsec_softc *sc, struct sockaddr *src,
1023     struct sockaddr *dst, uint32_t reqid)
1024 {
1025         struct ipsec_iflist *iflist;
1026         struct secpolicy *sp[IPSEC_SPCOUNT];
1027         int i;
1028
1029         sx_assert(&ipsec_ioctl_sx, SA_XLOCKED);
1030
1031         /* Allocate SP with new addresses. */
1032         iflist = ipsec_srchash(src);
1033         if (iflist == NULL) {
1034                 sc->ifp->if_drv_flags &= ~IFF_DRV_RUNNING;
1035                 return (EAFNOSUPPORT);
1036         }
1037         if (ipsec_newpolicies(sc, sp, src, dst, reqid) == 0) {
1038                 /* Add new policies to SPDB */
1039                 if (key_register_ifnet(sp, IPSEC_SPCOUNT) != 0) {
1040                         for (i = 0; i < IPSEC_SPCOUNT; i++)
1041                                 key_freesp(&sp[i]);
1042                         return (EAGAIN);
1043                 }
1044                 if (sc->family != 0)
1045                         ipsec_delete_tunnel(sc);
1046                 for (i = 0; i < IPSEC_SPCOUNT; i++)
1047                         sc->sp[i] = sp[i];
1048                 sc->family = src->sa_family;
1049                 CK_LIST_INSERT_HEAD(iflist, sc, srchash);
1050         } else {
1051                 sc->ifp->if_drv_flags &= ~IFF_DRV_RUNNING;
1052                 return (ENOMEM);
1053         }
1054         ipsec_set_running(sc);
1055         return (0);
1056 }
1057
1058 static void
1059 ipsec_delete_tunnel(struct ipsec_softc *sc)
1060 {
1061         int i;
1062
1063         sx_assert(&ipsec_ioctl_sx, SA_XLOCKED);
1064
1065         sc->ifp->if_drv_flags &= ~IFF_DRV_RUNNING;
1066         if (sc->family != 0) {
1067                 CK_LIST_REMOVE(sc, srchash);
1068                 sc->family = 0;
1069                 /*
1070                  * Make sure that ipsec_if_input() will not do access
1071                  * to softc's policies.
1072                  */
1073                 IPSEC_WAIT();
1074
1075                 key_unregister_ifnet(sc->sp, IPSEC_SPCOUNT);
1076                 for (i = 0; i < IPSEC_SPCOUNT; i++)
1077                         key_freesp(&sc->sp[i]);
1078         }
1079 }