1/*- 2 * Copyright (c) 1982, 1986, 1988, 1993 3 * The Regents of the University of California. All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 4. Neither the name of the University nor the names of its contributors 14 * may be used to endorse or promote products derived from this software 15 * without specific prior written permission. 16 * 17 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 20 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 27 * SUCH DAMAGE. 28 */ 29 30#include <sys/cdefs.h>
|
86#endif 87#define V_ip6_ipsec6_filtertunnel VNET(ip6_ipsec6_filtertunnel) 88 89SYSCTL_DECL(_net_inet6_ipsec6); 90SYSCTL_VNET_INT(_net_inet6_ipsec6, OID_AUTO, 91 filtertunnel, CTLFLAG_RW, &VNET_NAME(ip6_ipsec6_filtertunnel), 0, 92 "If set filter packets from an IPsec tunnel."); 93#endif /* IPSEC */ 94#endif /* INET6 */ 95 96/* 97 * Check if we have to jump over firewall processing for this packet. 98 * Called from ip_input(). 99 * 1 = jump over firewall, 0 = packet goes through firewall. 100 */ 101int 102ip6_ipsec_filtertunnel(struct mbuf *m) 103{ 104#if defined(IPSEC) 105 106 /* 107 * Bypass packet filtering for packets from a tunnel. 108 */ 109 if (!V_ip6_ipsec6_filtertunnel && 110 m_tag_find(m, PACKET_TAG_IPSEC_IN_DONE, NULL) != NULL) 111 return 1; 112#endif 113 return 0; 114} 115 116/* 117 * Check if this packet has an active SA and needs to be dropped instead 118 * of forwarded. 119 * Called from ip_input(). 120 * 1 = drop packet, 0 = forward packet. 121 */ 122int 123ip6_ipsec_fwd(struct mbuf *m) 124{ 125#ifdef IPSEC 126 struct m_tag *mtag; 127 struct tdb_ident *tdbi; 128 struct secpolicy *sp; 129 int s, error; 130 mtag = m_tag_find(m, PACKET_TAG_IPSEC_IN_DONE, NULL); 131 s = splnet(); 132 if (mtag != NULL) { 133 tdbi = (struct tdb_ident *)(mtag + 1); 134 sp = ipsec_getpolicy(tdbi, IPSEC_DIR_INBOUND); 135 } else { 136 sp = ipsec_getpolicybyaddr(m, IPSEC_DIR_INBOUND, 137 IP_FORWARDING, &error); 138 } 139 if (sp == NULL) { /* NB: can happen if error */ 140 splx(s); 141 /*XXX error stat???*/ 142 DPRINTF(("ip_input: no SP for forwarding\n")); /*XXX*/ 143 return 1; 144 } 145 146 /* 147 * Check security policy against packet attributes. 148 */ 149 error = ipsec_in_reject(sp, m); 150 KEY_FREESP(&sp); 151 splx(s); 152 if (error) { 153 V_ip6stat.ip6s_cantforward++; 154 return 1; 155 } 156#endif /* IPSEC */ 157 return 0; 158} 159 160/* 161 * Check if protocol type doesn't have a further header and do IPSEC 162 * decryption or reject right now. Protocols with further headers get 163 * their IPSEC treatment within the protocol specific processing. 164 * Called from ip_input(). 165 * 1 = drop packet, 0 = continue processing packet. 166 */ 167int 168ip6_ipsec_input(struct mbuf *m, int nxt) 169{ 170#ifdef IPSEC 171 struct m_tag *mtag; 172 struct tdb_ident *tdbi; 173 struct secpolicy *sp; 174 int s, error; 175 /* 176 * enforce IPsec policy checking if we are seeing last header. 177 * note that we do not visit this with protocols with pcb layer 178 * code - like udp/tcp/raw ip. 179 */ 180 if ((inet6sw[ip6_protox[nxt]].pr_flags & PR_LASTHDR) != 0 && 181 ipsec6_in_reject(m, NULL)) { 182 183 /* 184 * Check if the packet has already had IPsec processing 185 * done. If so, then just pass it along. This tag gets 186 * set during AH, ESP, etc. input handling, before the 187 * packet is returned to the ip input queue for delivery. 188 */ 189 mtag = m_tag_find(m, PACKET_TAG_IPSEC_IN_DONE, NULL); 190 s = splnet(); 191 if (mtag != NULL) { 192 tdbi = (struct tdb_ident *)(mtag + 1); 193 sp = ipsec_getpolicy(tdbi, IPSEC_DIR_INBOUND); 194 } else { 195 sp = ipsec_getpolicybyaddr(m, IPSEC_DIR_INBOUND, 196 IP_FORWARDING, &error); 197 } 198 if (sp != NULL) { 199 /* 200 * Check security policy against packet attributes. 201 */ 202 error = ipsec_in_reject(sp, m); 203 KEY_FREESP(&sp); 204 } else { 205 /* XXX error stat??? */ 206 error = EINVAL; 207 DPRINTF(("ip_input: no SP, packet discarded\n"));/*XXX*/ 208 return 1; 209 } 210 splx(s); 211 if (error) 212 return 1; 213 } 214#endif /* IPSEC */ 215 return 0; 216} 217 218/* 219 * Called from ip6_output(). 220 * 1 = drop packet, 0 = continue processing packet, 221 * -1 = packet was reinjected and stop processing packet 222 */ 223 224int 225ip6_ipsec_output(struct mbuf **m, struct inpcb *inp, int *flags, int *error, 226 struct ifnet **ifp, struct secpolicy **sp) 227{ 228#ifdef IPSEC 229 struct tdb_ident *tdbi; 230 struct m_tag *mtag; 231 /* XXX int s; */ 232 if (sp == NULL) 233 return 1; 234 mtag = m_tag_find(*m, PACKET_TAG_IPSEC_PENDING_TDB, NULL); 235 if (mtag != NULL) { 236 tdbi = (struct tdb_ident *)(mtag + 1); 237 *sp = ipsec_getpolicy(tdbi, IPSEC_DIR_OUTBOUND); 238 if (*sp == NULL) 239 *error = -EINVAL; /* force silent drop */ 240 m_tag_delete(*m, mtag); 241 } else { 242 *sp = ipsec4_checkpolicy(*m, IPSEC_DIR_OUTBOUND, *flags, 243 error, inp); 244 } 245 246 /* 247 * There are four return cases: 248 * sp != NULL apply IPsec policy 249 * sp == NULL, error == 0 no IPsec handling needed 250 * sp == NULL, error == -EINVAL discard packet w/o error 251 * sp == NULL, error != 0 discard packet, report error 252 */ 253 if (*sp != NULL) { 254 /* Loop detection, check if ipsec processing already done */ 255 KASSERT((*sp)->req != NULL, ("ip_output: no ipsec request")); 256 for (mtag = m_tag_first(*m); mtag != NULL; 257 mtag = m_tag_next(*m, mtag)) { 258 if (mtag->m_tag_cookie != MTAG_ABI_COMPAT) 259 continue; 260 if (mtag->m_tag_id != PACKET_TAG_IPSEC_OUT_DONE && 261 mtag->m_tag_id != PACKET_TAG_IPSEC_OUT_CRYPTO_NEEDED) 262 continue; 263 /* 264 * Check if policy has an SA associated with it. 265 * This can happen when an SP has yet to acquire 266 * an SA; e.g. on first reference. If it occurs, 267 * then we let ipsec4_process_packet do its thing. 268 */ 269 if ((*sp)->req->sav == NULL) 270 break; 271 tdbi = (struct tdb_ident *)(mtag + 1); 272 if (tdbi->spi == (*sp)->req->sav->spi && 273 tdbi->proto == (*sp)->req->sav->sah->saidx.proto && 274 bcmp(&tdbi->dst, &(*sp)->req->sav->sah->saidx.dst, 275 sizeof (union sockaddr_union)) == 0) { 276 /* 277 * No IPsec processing is needed, free 278 * reference to SP. 279 * 280 * NB: null pointer to avoid free at 281 * done: below. 282 */ 283 KEY_FREESP(sp), *sp = NULL; 284 /* XXX splx(s); */ 285 goto done; 286 } 287 } 288 289 /* 290 * Do delayed checksums now because we send before 291 * this is done in the normal processing path. 292 */ 293 if ((*m)->m_pkthdr.csum_flags & CSUM_DELAY_DATA) { 294 in_delayed_cksum(*m); 295 (*m)->m_pkthdr.csum_flags &= ~CSUM_DELAY_DATA; 296 } 297 298 /* 299 * Preserve KAME behaviour: ENOENT can be returned 300 * when an SA acquire is in progress. Don't propagate 301 * this to user-level; it confuses applications. 302 * 303 * XXX this will go away when the SADB is redone. 304 */ 305 if (*error == ENOENT) 306 *error = 0; 307 goto do_ipsec; 308 } else { /* sp == NULL */ 309 if (*error != 0) { 310 /* 311 * Hack: -EINVAL is used to signal that a packet 312 * should be silently discarded. This is typically 313 * because we asked key management for an SA and 314 * it was delayed (e.g. kicked up to IKE). 315 */ 316 if (*error == -EINVAL) 317 *error = 0; 318 goto bad; 319 } else { 320 /* No IPsec processing for this packet. */ 321 } 322 } 323done: 324 return 0; 325do_ipsec: 326 return -1; 327bad: 328 return 1; 329#endif /* IPSEC */ 330 return 0; 331} 332 333#if 0 334/* 335 * Compute the MTU for a forwarded packet that gets IPSEC encapsulated. 336 * Called from ip_forward(). 337 * Returns MTU suggestion for ICMP needfrag reply. 338 */ 339int 340ip6_ipsec_mtu(struct mbuf *m) 341{ 342 int mtu = 0; 343 /* 344 * If the packet is routed over IPsec tunnel, tell the 345 * originator the tunnel MTU. 346 * tunnel MTU = if MTU - sizeof(IP) - ESP/AH hdrsiz 347 * XXX quickhack!!! 348 */ 349#ifdef IPSEC 350 struct secpolicy *sp = NULL; 351 int ipsecerror; 352 int ipsechdr; 353 struct route *ro; 354 sp = ipsec_getpolicybyaddr(m, 355 IPSEC_DIR_OUTBOUND, 356 IP_FORWARDING, 357 &ipsecerror); 358 if (sp != NULL) { 359 /* count IPsec header size */ 360 ipsechdr = ipsec_hdrsiz(m, IPSEC_DIR_OUTBOUND, NULL); 361 362 /* 363 * find the correct route for outer IPv4 364 * header, compute tunnel MTU. 365 */ 366 if (sp->req != NULL && 367 sp->req->sav != NULL && 368 sp->req->sav->sah != NULL) { 369 ro = &sp->req->sav->sah->route_cache.sa_route; 370 if (ro->ro_rt && ro->ro_rt->rt_ifp) { 371 mtu = 372 ro->ro_rt->rt_rmx.rmx_mtu ? 373 ro->ro_rt->rt_rmx.rmx_mtu : 374 ro->ro_rt->rt_ifp->if_mtu; 375 mtu -= ipsechdr; 376 } 377 } 378 KEY_FREESP(&sp); 379 } 380#endif /* IPSEC */ 381 /* XXX else case missing. */ 382 return mtu; 383} 384#endif
|