1 /*- 2 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. 3 * Copyright (c) 2010-2011 Juniper Networks, Inc. 4 * All rights reserved. 5 * 6 * Portions of this software were developed by Robert N. M. Watson under 7 * contract to Juniper Networks, Inc. 8 * 9 * Redistribution and use in source and binary forms, with or without 10 * modification, are permitted provided that the following conditions 11 * are met: 12 * 1. Redistributions of source code must retain the above copyright 13 * notice, this list of conditions and the following disclaimer. 14 * 2. Redistributions in binary form must reproduce the above copyright 15 * notice, this list of conditions and the following disclaimer in the 16 * documentation and/or other materials provided with the distribution. 17 * 3. Neither the name of the project nor the names of its contributors 18 * may be used to endorse or promote products derived from this software 19 * without specific prior written permission. 20 * 21 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND 22 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 24 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE 25 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 26 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 27 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 28 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 29 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 30 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 31 * SUCH DAMAGE. 32 * 33 * $KAME: udp6_usrreq.c,v 1.27 2001/05/21 05:45:10 jinmei Exp $ 34 * $KAME: udp6_output.c,v 1.31 2001/05/21 16:39:15 jinmei Exp $ 35 */ 36 37 /*- 38 * Copyright (c) 1982, 1986, 1988, 1990, 1993, 1995 39 * The Regents of the University of California. 40 * All rights reserved. 41 * 42 * Redistribution and use in source and binary forms, with or without 43 * modification, are permitted provided that the following conditions 44 * are met: 45 * 1. Redistributions of source code must retain the above copyright 46 * notice, this list of conditions and the following disclaimer. 47 * 2. Redistributions in binary form must reproduce the above copyright 48 * notice, this list of conditions and the following disclaimer in the 49 * documentation and/or other materials provided with the distribution. 50 * 4. Neither the name of the University nor the names of its contributors 51 * may be used to endorse or promote products derived from this software 52 * without specific prior written permission. 53 * 54 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 55 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 56 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 57 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 58 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 59 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 60 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 61 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 62 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 63 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 64 * SUCH DAMAGE. 65 * 66 * @(#)udp_usrreq.c 8.6 (Berkeley) 5/23/95 67 */ 68 69 #include <sys/cdefs.h> 70 __FBSDID("$FreeBSD$"); 71 72 #include "opt_inet.h" 73 #include "opt_inet6.h" 74 #include "opt_ipfw.h" 75 #include "opt_ipsec.h" 76 #include "opt_kdtrace.h" 77 78 #include <sys/param.h> 79 #include <sys/jail.h> 80 #include <sys/kernel.h> 81 #include <sys/lock.h> 82 #include <sys/mbuf.h> 83 #include <sys/priv.h> 84 #include <sys/proc.h> 85 #include <sys/protosw.h> 86 #include <sys/sdt.h> 87 #include <sys/signalvar.h> 88 #include <sys/socket.h> 89 #include <sys/socketvar.h> 90 #include <sys/sx.h> 91 #include <sys/sysctl.h> 92 #include <sys/syslog.h> 93 #include <sys/systm.h> 94 95 #include <net/if.h> 96 #include <net/if_var.h> 97 #include <net/if_types.h> 98 #include <net/route.h> 99 100 #include <netinet/in.h> 101 #include <netinet/in_kdtrace.h> 102 #include <netinet/in_pcb.h> 103 #include <netinet/in_systm.h> 104 #include <netinet/in_var.h> 105 #include <netinet/ip.h> 106 #include <netinet/ip_icmp.h> 107 #include <netinet/ip6.h> 108 #include <netinet/icmp_var.h> 109 #include <netinet/icmp6.h> 110 #include <netinet/ip_var.h> 111 #include <netinet/udp.h> 112 #include <netinet/udp_var.h> 113 114 #include <netinet6/ip6protosw.h> 115 #include <netinet6/ip6_var.h> 116 #include <netinet6/in6_pcb.h> 117 #include <netinet6/udp6_var.h> 118 #include <netinet6/scope6_var.h> 119 120 #ifdef IPSEC 121 #include <netipsec/ipsec.h> 122 #include <netipsec/ipsec6.h> 123 #endif /* IPSEC */ 124 125 #include <security/mac/mac_framework.h> 126 127 /* 128 * UDP protocol implementation. 129 * Per RFC 768, August, 1980. 130 */ 131 132 extern struct protosw inetsw[]; 133 static void udp6_detach(struct socket *so); 134 135 static void 136 udp6_append(struct inpcb *inp, struct mbuf *n, int off, 137 struct sockaddr_in6 *fromsa) 138 { 139 struct socket *so; 140 struct mbuf *opts; 141 142 INP_LOCK_ASSERT(inp); 143 144 #ifdef IPSEC 145 /* Check AH/ESP integrity. */ 146 if (ipsec6_in_reject(n, inp)) { 147 m_freem(n); 148 IPSEC6STAT_INC(ips_in_polvio); 149 return; 150 } 151 #endif /* IPSEC */ 152 #ifdef MAC 153 if (mac_inpcb_check_deliver(inp, n) != 0) { 154 m_freem(n); 155 return; 156 } 157 #endif 158 opts = NULL; 159 if (inp->inp_flags & INP_CONTROLOPTS || 160 inp->inp_socket->so_options & SO_TIMESTAMP) 161 ip6_savecontrol(inp, n, &opts); 162 m_adj(n, off + sizeof(struct udphdr)); 163 164 so = inp->inp_socket; 165 SOCKBUF_LOCK(&so->so_rcv); 166 if (sbappendaddr_locked(&so->so_rcv, (struct sockaddr *)fromsa, n, 167 opts) == 0) { 168 SOCKBUF_UNLOCK(&so->so_rcv); 169 m_freem(n); 170 if (opts) 171 m_freem(opts); 172 UDPSTAT_INC(udps_fullsock); 173 } else 174 sorwakeup_locked(so); 175 } 176 177 int 178 udp6_input(struct mbuf **mp, int *offp, int proto) 179 { 180 struct mbuf *m = *mp; 181 struct ifnet *ifp; 182 struct ip6_hdr *ip6; 183 struct udphdr *uh; 184 struct inpcb *inp; 185 struct udpcb *up; 186 int off = *offp; 187 int plen, ulen; 188 struct sockaddr_in6 fromsa; 189 struct m_tag *fwd_tag; 190 uint16_t uh_sum; 191 192 ifp = m->m_pkthdr.rcvif; 193 ip6 = mtod(m, struct ip6_hdr *); 194 195 if (faithprefix_p != NULL && (*faithprefix_p)(&ip6->ip6_dst)) { 196 /* XXX send icmp6 host/port unreach? */ 197 m_freem(m); 198 return (IPPROTO_DONE); 199 } 200 201 #ifndef PULLDOWN_TEST 202 IP6_EXTHDR_CHECK(m, off, sizeof(struct udphdr), IPPROTO_DONE); 203 ip6 = mtod(m, struct ip6_hdr *); 204 uh = (struct udphdr *)((caddr_t)ip6 + off); 205 #else 206 IP6_EXTHDR_GET(uh, struct udphdr *, m, off, sizeof(*uh)); 207 if (!uh) 208 return (IPPROTO_DONE); 209 #endif 210 211 UDPSTAT_INC(udps_ipackets); 212 213 /* 214 * Destination port of 0 is illegal, based on RFC768. 215 */ 216 if (uh->uh_dport == 0) 217 goto badunlocked; 218 219 plen = ntohs(ip6->ip6_plen) - off + sizeof(*ip6); 220 ulen = ntohs((u_short)uh->uh_ulen); 221 222 if (plen != ulen) { 223 UDPSTAT_INC(udps_badlen); 224 goto badunlocked; 225 } 226 227 /* 228 * Checksum extended UDP header and data. 229 */ 230 if (uh->uh_sum == 0) { 231 UDPSTAT_INC(udps_nosum); 232 goto badunlocked; 233 } 234 235 if (m->m_pkthdr.csum_flags & CSUM_DATA_VALID_IPV6) { 236 if (m->m_pkthdr.csum_flags & CSUM_PSEUDO_HDR) 237 uh_sum = m->m_pkthdr.csum_data; 238 else 239 uh_sum = in6_cksum_pseudo(ip6, ulen, 240 IPPROTO_UDP, m->m_pkthdr.csum_data); 241 uh_sum ^= 0xffff; 242 } else 243 uh_sum = in6_cksum(m, IPPROTO_UDP, off, ulen); 244 245 if (uh_sum != 0) { 246 UDPSTAT_INC(udps_badsum); 247 goto badunlocked; 248 } 249 250 /* 251 * Construct sockaddr format source address. 252 */ 253 init_sin6(&fromsa, m); 254 fromsa.sin6_port = uh->uh_sport; 255 256 if (IN6_IS_ADDR_MULTICAST(&ip6->ip6_dst)) { 257 struct inpcb *last; 258 struct ip6_moptions *imo; 259 260 INP_INFO_RLOCK(&V_udbinfo); 261 /* 262 * In the event that laddr should be set to the link-local 263 * address (this happens in RIPng), the multicast address 264 * specified in the received packet will not match laddr. To 265 * handle this situation, matching is relaxed if the 266 * receiving interface is the same as one specified in the 267 * socket and if the destination multicast address matches 268 * one of the multicast groups specified in the socket. 269 */ 270 271 /* 272 * KAME note: traditionally we dropped udpiphdr from mbuf 273 * here. We need udphdr for IPsec processing so we do that 274 * later. 275 */ 276 last = NULL; 277 LIST_FOREACH(inp, &V_udb, inp_list) { 278 if ((inp->inp_vflag & INP_IPV6) == 0) 279 continue; 280 if (inp->inp_lport != uh->uh_dport) 281 continue; 282 if (inp->inp_fport != 0 && 283 inp->inp_fport != uh->uh_sport) 284 continue; 285 if (!IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_laddr)) { 286 if (!IN6_ARE_ADDR_EQUAL(&inp->in6p_laddr, 287 &ip6->ip6_dst)) 288 continue; 289 } 290 if (!IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_faddr)) { 291 if (!IN6_ARE_ADDR_EQUAL(&inp->in6p_faddr, 292 &ip6->ip6_src) || 293 inp->inp_fport != uh->uh_sport) 294 continue; 295 } 296 297 /* 298 * XXXRW: Because we weren't holding either the inpcb 299 * or the hash lock when we checked for a match 300 * before, we should probably recheck now that the 301 * inpcb lock is (supposed to be) held. 302 */ 303 304 /* 305 * Handle socket delivery policy for any-source 306 * and source-specific multicast. [RFC3678] 307 */ 308 imo = inp->in6p_moptions; 309 if (imo && IN6_IS_ADDR_MULTICAST(&ip6->ip6_dst)) { 310 struct sockaddr_in6 mcaddr; 311 int blocked; 312 313 INP_RLOCK(inp); 314 315 bzero(&mcaddr, sizeof(struct sockaddr_in6)); 316 mcaddr.sin6_len = sizeof(struct sockaddr_in6); 317 mcaddr.sin6_family = AF_INET6; 318 mcaddr.sin6_addr = ip6->ip6_dst; 319 320 blocked = im6o_mc_filter(imo, ifp, 321 (struct sockaddr *)&mcaddr, 322 (struct sockaddr *)&fromsa); 323 if (blocked != MCAST_PASS) { 324 if (blocked == MCAST_NOTGMEMBER) 325 IP6STAT_INC(ip6s_notmember); 326 if (blocked == MCAST_NOTSMEMBER || 327 blocked == MCAST_MUTED) 328 UDPSTAT_INC(udps_filtermcast); 329 INP_RUNLOCK(inp); /* XXX */ 330 continue; 331 } 332 333 INP_RUNLOCK(inp); 334 } 335 if (last != NULL) { 336 struct mbuf *n; 337 338 if ((n = m_copy(m, 0, M_COPYALL)) != NULL) { 339 INP_RLOCK(last); 340 up = intoudpcb(last); 341 if (up->u_tun_func == NULL) { 342 udp6_append(last, n, off, &fromsa); 343 } else { 344 /* 345 * Engage the tunneling 346 * protocol we will have to 347 * leave the info_lock up, 348 * since we are hunting 349 * through multiple UDP's. 350 * 351 */ 352 (*up->u_tun_func)(n, off, last); 353 } 354 INP_RUNLOCK(last); 355 } 356 } 357 last = inp; 358 /* 359 * Don't look for additional matches if this one does 360 * not have either the SO_REUSEPORT or SO_REUSEADDR 361 * socket options set. This heuristic avoids 362 * searching through all pcbs in the common case of a 363 * non-shared port. It assumes that an application 364 * will never clear these options after setting them. 365 */ 366 if ((last->inp_socket->so_options & 367 (SO_REUSEPORT|SO_REUSEADDR)) == 0) 368 break; 369 } 370 371 if (last == NULL) { 372 /* 373 * No matching pcb found; discard datagram. (No need 374 * to send an ICMP Port Unreachable for a broadcast 375 * or multicast datgram.) 376 */ 377 UDPSTAT_INC(udps_noport); 378 UDPSTAT_INC(udps_noportmcast); 379 goto badheadlocked; 380 } 381 INP_RLOCK(last); 382 INP_INFO_RUNLOCK(&V_udbinfo); 383 up = intoudpcb(last); 384 UDP_PROBE(receive, NULL, last, ip6, last, uh); 385 if (up->u_tun_func == NULL) { 386 udp6_append(last, m, off, &fromsa); 387 } else { 388 /* 389 * Engage the tunneling protocol. 390 */ 391 (*up->u_tun_func)(m, off, last); 392 } 393 INP_RUNLOCK(last); 394 return (IPPROTO_DONE); 395 } 396 /* 397 * Locate pcb for datagram. 398 */ 399 400 /* 401 * Grab info from PACKET_TAG_IPFORWARD tag prepended to the chain. 402 */ 403 if ((m->m_flags & M_IP6_NEXTHOP) && 404 (fwd_tag = m_tag_find(m, PACKET_TAG_IPFORWARD, NULL)) != NULL) { 405 struct sockaddr_in6 *next_hop6; 406 407 next_hop6 = (struct sockaddr_in6 *)(fwd_tag + 1); 408 409 /* 410 * Transparently forwarded. Pretend to be the destination. 411 * Already got one like this? 412 */ 413 inp = in6_pcblookup_mbuf(&V_udbinfo, 414 &ip6->ip6_src, uh->uh_sport, &ip6->ip6_dst, uh->uh_dport, 415 INPLOOKUP_RLOCKPCB, m->m_pkthdr.rcvif, m); 416 if (!inp) { 417 /* 418 * It's new. Try to find the ambushing socket. 419 * Because we've rewritten the destination address, 420 * any hardware-generated hash is ignored. 421 */ 422 inp = in6_pcblookup(&V_udbinfo, &ip6->ip6_src, 423 uh->uh_sport, &next_hop6->sin6_addr, 424 next_hop6->sin6_port ? htons(next_hop6->sin6_port) : 425 uh->uh_dport, INPLOOKUP_WILDCARD | 426 INPLOOKUP_RLOCKPCB, m->m_pkthdr.rcvif); 427 } 428 /* Remove the tag from the packet. We don't need it anymore. */ 429 m_tag_delete(m, fwd_tag); 430 m->m_flags &= ~M_IP6_NEXTHOP; 431 } else 432 inp = in6_pcblookup_mbuf(&V_udbinfo, &ip6->ip6_src, 433 uh->uh_sport, &ip6->ip6_dst, uh->uh_dport, 434 INPLOOKUP_WILDCARD | INPLOOKUP_RLOCKPCB, 435 m->m_pkthdr.rcvif, m); 436 if (inp == NULL) { 437 if (udp_log_in_vain) { 438 char ip6bufs[INET6_ADDRSTRLEN]; 439 char ip6bufd[INET6_ADDRSTRLEN]; 440 441 log(LOG_INFO, 442 "Connection attempt to UDP [%s]:%d from [%s]:%d\n", 443 ip6_sprintf(ip6bufd, &ip6->ip6_dst), 444 ntohs(uh->uh_dport), 445 ip6_sprintf(ip6bufs, &ip6->ip6_src), 446 ntohs(uh->uh_sport)); 447 } 448 UDPSTAT_INC(udps_noport); 449 if (m->m_flags & M_MCAST) { 450 printf("UDP6: M_MCAST is set in a unicast packet.\n"); 451 UDPSTAT_INC(udps_noportmcast); 452 goto badunlocked; 453 } 454 if (V_udp_blackhole) 455 goto badunlocked; 456 if (badport_bandlim(BANDLIM_ICMP6_UNREACH) < 0) 457 goto badunlocked; 458 icmp6_error(m, ICMP6_DST_UNREACH, ICMP6_DST_UNREACH_NOPORT, 0); 459 return (IPPROTO_DONE); 460 } 461 INP_RLOCK_ASSERT(inp); 462 up = intoudpcb(inp); 463 UDP_PROBE(receive, NULL, inp, ip6, inp, uh); 464 if (up->u_tun_func == NULL) { 465 udp6_append(inp, m, off, &fromsa); 466 } else { 467 /* 468 * Engage the tunneling protocol. 469 */ 470 471 (*up->u_tun_func)(m, off, inp); 472 } 473 INP_RUNLOCK(inp); 474 return (IPPROTO_DONE); 475 476 badheadlocked: 477 INP_INFO_RUNLOCK(&V_udbinfo); 478 badunlocked: 479 if (m) 480 m_freem(m); 481 return (IPPROTO_DONE); 482 } 483 484 void 485 udp6_ctlinput(int cmd, struct sockaddr *sa, void *d) 486 { 487 struct udphdr uh; 488 struct ip6_hdr *ip6; 489 struct mbuf *m; 490 int off = 0; 491 struct ip6ctlparam *ip6cp = NULL; 492 const struct sockaddr_in6 *sa6_src = NULL; 493 void *cmdarg; 494 struct inpcb *(*notify)(struct inpcb *, int) = udp_notify; 495 struct udp_portonly { 496 u_int16_t uh_sport; 497 u_int16_t uh_dport; 498 } *uhp; 499 500 if (sa->sa_family != AF_INET6 || 501 sa->sa_len != sizeof(struct sockaddr_in6)) 502 return; 503 504 if ((unsigned)cmd >= PRC_NCMDS) 505 return; 506 if (PRC_IS_REDIRECT(cmd)) 507 notify = in6_rtchange, d = NULL; 508 else if (cmd == PRC_HOSTDEAD) 509 d = NULL; 510 else if (inet6ctlerrmap[cmd] == 0) 511 return; 512 513 /* if the parameter is from icmp6, decode it. */ 514 if (d != NULL) { 515 ip6cp = (struct ip6ctlparam *)d; 516 m = ip6cp->ip6c_m; 517 ip6 = ip6cp->ip6c_ip6; 518 off = ip6cp->ip6c_off; 519 cmdarg = ip6cp->ip6c_cmdarg; 520 sa6_src = ip6cp->ip6c_src; 521 } else { 522 m = NULL; 523 ip6 = NULL; 524 cmdarg = NULL; 525 sa6_src = &sa6_any; 526 } 527 528 if (ip6) { 529 /* 530 * XXX: We assume that when IPV6 is non NULL, 531 * M and OFF are valid. 532 */ 533 534 /* Check if we can safely examine src and dst ports. */ 535 if (m->m_pkthdr.len < off + sizeof(*uhp)) 536 return; 537 538 bzero(&uh, sizeof(uh)); 539 m_copydata(m, off, sizeof(*uhp), (caddr_t)&uh); 540 541 (void) in6_pcbnotify(&V_udbinfo, sa, uh.uh_dport, 542 (struct sockaddr *)ip6cp->ip6c_src, uh.uh_sport, cmd, 543 cmdarg, notify); 544 } else 545 (void) in6_pcbnotify(&V_udbinfo, sa, 0, 546 (const struct sockaddr *)sa6_src, 0, cmd, cmdarg, notify); 547 } 548 549 static int 550 udp6_getcred(SYSCTL_HANDLER_ARGS) 551 { 552 struct xucred xuc; 553 struct sockaddr_in6 addrs[2]; 554 struct inpcb *inp; 555 int error; 556 557 error = priv_check(req->td, PRIV_NETINET_GETCRED); 558 if (error) 559 return (error); 560 561 if (req->newlen != sizeof(addrs)) 562 return (EINVAL); 563 if (req->oldlen != sizeof(struct xucred)) 564 return (EINVAL); 565 error = SYSCTL_IN(req, addrs, sizeof(addrs)); 566 if (error) 567 return (error); 568 if ((error = sa6_embedscope(&addrs[0], V_ip6_use_defzone)) != 0 || 569 (error = sa6_embedscope(&addrs[1], V_ip6_use_defzone)) != 0) { 570 return (error); 571 } 572 inp = in6_pcblookup(&V_udbinfo, &addrs[1].sin6_addr, 573 addrs[1].sin6_port, &addrs[0].sin6_addr, addrs[0].sin6_port, 574 INPLOOKUP_WILDCARD | INPLOOKUP_RLOCKPCB, NULL); 575 if (inp != NULL) { 576 INP_RLOCK_ASSERT(inp); 577 if (inp->inp_socket == NULL) 578 error = ENOENT; 579 if (error == 0) 580 error = cr_canseesocket(req->td->td_ucred, 581 inp->inp_socket); 582 if (error == 0) 583 cru2x(inp->inp_cred, &xuc); 584 INP_RUNLOCK(inp); 585 } else 586 error = ENOENT; 587 if (error == 0) 588 error = SYSCTL_OUT(req, &xuc, sizeof(struct xucred)); 589 return (error); 590 } 591 592 SYSCTL_PROC(_net_inet6_udp6, OID_AUTO, getcred, CTLTYPE_OPAQUE|CTLFLAG_RW, 0, 593 0, udp6_getcred, "S,xucred", "Get the xucred of a UDP6 connection"); 594 595 static int 596 udp6_output(struct inpcb *inp, struct mbuf *m, struct sockaddr *addr6, 597 struct mbuf *control, struct thread *td) 598 { 599 u_int32_t ulen = m->m_pkthdr.len; 600 u_int32_t plen = sizeof(struct udphdr) + ulen; 601 struct ip6_hdr *ip6; 602 struct udphdr *udp6; 603 struct in6_addr *laddr, *faddr, in6a; 604 struct sockaddr_in6 *sin6 = NULL; 605 struct ifnet *oifp = NULL; 606 int scope_ambiguous = 0; 607 u_short fport; 608 int error = 0; 609 struct ip6_pktopts *optp, opt; 610 int af = AF_INET6, hlen = sizeof(struct ip6_hdr); 611 int flags; 612 struct sockaddr_in6 tmp; 613 614 INP_WLOCK_ASSERT(inp); 615 INP_HASH_WLOCK_ASSERT(inp->inp_pcbinfo); 616 617 if (addr6) { 618 /* addr6 has been validated in udp6_send(). */ 619 sin6 = (struct sockaddr_in6 *)addr6; 620 621 /* protect *sin6 from overwrites */ 622 tmp = *sin6; 623 sin6 = &tmp; 624 625 /* 626 * Application should provide a proper zone ID or the use of 627 * default zone IDs should be enabled. Unfortunately, some 628 * applications do not behave as it should, so we need a 629 * workaround. Even if an appropriate ID is not determined, 630 * we'll see if we can determine the outgoing interface. If we 631 * can, determine the zone ID based on the interface below. 632 */ 633 if (sin6->sin6_scope_id == 0 && !V_ip6_use_defzone) 634 scope_ambiguous = 1; 635 if ((error = sa6_embedscope(sin6, V_ip6_use_defzone)) != 0) 636 return (error); 637 } 638 639 if (control) { 640 if ((error = ip6_setpktopts(control, &opt, 641 inp->in6p_outputopts, td->td_ucred, IPPROTO_UDP)) != 0) 642 goto release; 643 optp = &opt; 644 } else 645 optp = inp->in6p_outputopts; 646 647 if (sin6) { 648 faddr = &sin6->sin6_addr; 649 650 /* 651 * Since we saw no essential reason for calling in_pcbconnect, 652 * we get rid of such kind of logic, and call in6_selectsrc 653 * and in6_pcbsetport in order to fill in the local address 654 * and the local port. 655 */ 656 if (sin6->sin6_port == 0) { 657 error = EADDRNOTAVAIL; 658 goto release; 659 } 660 661 if (!IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_faddr)) { 662 /* how about ::ffff:0.0.0.0 case? */ 663 error = EISCONN; 664 goto release; 665 } 666 667 fport = sin6->sin6_port; /* allow 0 port */ 668 669 if (IN6_IS_ADDR_V4MAPPED(faddr)) { 670 if ((inp->inp_flags & IN6P_IPV6_V6ONLY)) { 671 /* 672 * I believe we should explicitly discard the 673 * packet when mapped addresses are disabled, 674 * rather than send the packet as an IPv6 one. 675 * If we chose the latter approach, the packet 676 * might be sent out on the wire based on the 677 * default route, the situation which we'd 678 * probably want to avoid. 679 * (20010421 jinmei@kame.net) 680 */ 681 error = EINVAL; 682 goto release; 683 } 684 if (!IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_laddr) && 685 !IN6_IS_ADDR_V4MAPPED(&inp->in6p_laddr)) { 686 /* 687 * when remote addr is an IPv4-mapped address, 688 * local addr should not be an IPv6 address, 689 * since you cannot determine how to map IPv6 690 * source address to IPv4. 691 */ 692 error = EINVAL; 693 goto release; 694 } 695 696 af = AF_INET; 697 } 698 699 if (!IN6_IS_ADDR_V4MAPPED(faddr)) { 700 error = in6_selectsrc(sin6, optp, inp, NULL, 701 td->td_ucred, &oifp, &in6a); 702 if (error) 703 goto release; 704 if (oifp && scope_ambiguous && 705 (error = in6_setscope(&sin6->sin6_addr, 706 oifp, NULL))) { 707 goto release; 708 } 709 laddr = &in6a; 710 } else 711 laddr = &inp->in6p_laddr; /* XXX */ 712 if (laddr == NULL) { 713 if (error == 0) 714 error = EADDRNOTAVAIL; 715 goto release; 716 } 717 if (inp->inp_lport == 0 && 718 (error = in6_pcbsetport(laddr, inp, td->td_ucred)) != 0) { 719 /* Undo an address bind that may have occurred. */ 720 inp->in6p_laddr = in6addr_any; 721 goto release; 722 } 723 } else { 724 if (IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_faddr)) { 725 error = ENOTCONN; 726 goto release; 727 } 728 if (IN6_IS_ADDR_V4MAPPED(&inp->in6p_faddr)) { 729 if ((inp->inp_flags & IN6P_IPV6_V6ONLY)) { 730 /* 731 * XXX: this case would happen when the 732 * application sets the V6ONLY flag after 733 * connecting the foreign address. 734 * Such applications should be fixed, 735 * so we bark here. 736 */ 737 log(LOG_INFO, "udp6_output: IPV6_V6ONLY " 738 "option was set for a connected socket\n"); 739 error = EINVAL; 740 goto release; 741 } else 742 af = AF_INET; 743 } 744 laddr = &inp->in6p_laddr; 745 faddr = &inp->in6p_faddr; 746 fport = inp->inp_fport; 747 } 748 749 if (af == AF_INET) 750 hlen = sizeof(struct ip); 751 752 /* 753 * Calculate data length and get a mbuf 754 * for UDP and IP6 headers. 755 */ 756 M_PREPEND(m, hlen + sizeof(struct udphdr), M_NOWAIT); 757 if (m == 0) { 758 error = ENOBUFS; 759 goto release; 760 } 761 762 /* 763 * Stuff checksum and output datagram. 764 */ 765 udp6 = (struct udphdr *)(mtod(m, caddr_t) + hlen); 766 udp6->uh_sport = inp->inp_lport; /* lport is always set in the PCB */ 767 udp6->uh_dport = fport; 768 if (plen <= 0xffff) 769 udp6->uh_ulen = htons((u_short)plen); 770 else 771 udp6->uh_ulen = 0; 772 udp6->uh_sum = 0; 773 774 switch (af) { 775 case AF_INET6: 776 ip6 = mtod(m, struct ip6_hdr *); 777 ip6->ip6_flow = inp->inp_flow & IPV6_FLOWINFO_MASK; 778 ip6->ip6_vfc &= ~IPV6_VERSION_MASK; 779 ip6->ip6_vfc |= IPV6_VERSION; 780 ip6->ip6_plen = htons((u_short)plen); 781 ip6->ip6_nxt = IPPROTO_UDP; 782 ip6->ip6_hlim = in6_selecthlim(inp, NULL); 783 ip6->ip6_src = *laddr; 784 ip6->ip6_dst = *faddr; 785 786 udp6->uh_sum = in6_cksum_pseudo(ip6, plen, IPPROTO_UDP, 0); 787 m->m_pkthdr.csum_flags = CSUM_UDP_IPV6; 788 m->m_pkthdr.csum_data = offsetof(struct udphdr, uh_sum); 789 790 flags = 0; 791 792 UDP_PROBE(send, NULL, inp, ip6, inp, udp6); 793 UDPSTAT_INC(udps_opackets); 794 error = ip6_output(m, optp, NULL, flags, inp->in6p_moptions, 795 NULL, inp); 796 break; 797 case AF_INET: 798 error = EAFNOSUPPORT; 799 goto release; 800 } 801 goto releaseopt; 802 803 release: 804 m_freem(m); 805 806 releaseopt: 807 if (control) { 808 ip6_clearpktopts(&opt, -1); 809 m_freem(control); 810 } 811 return (error); 812 } 813 814 static void 815 udp6_abort(struct socket *so) 816 { 817 struct inpcb *inp; 818 819 inp = sotoinpcb(so); 820 KASSERT(inp != NULL, ("udp6_abort: inp == NULL")); 821 822 #ifdef INET 823 if (inp->inp_vflag & INP_IPV4) { 824 struct pr_usrreqs *pru; 825 826 pru = inetsw[ip_protox[IPPROTO_UDP]].pr_usrreqs; 827 (*pru->pru_abort)(so); 828 return; 829 } 830 #endif 831 832 INP_WLOCK(inp); 833 if (!IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_faddr)) { 834 INP_HASH_WLOCK(&V_udbinfo); 835 in6_pcbdisconnect(inp); 836 inp->in6p_laddr = in6addr_any; 837 INP_HASH_WUNLOCK(&V_udbinfo); 838 soisdisconnected(so); 839 } 840 INP_WUNLOCK(inp); 841 } 842 843 static int 844 udp6_attach(struct socket *so, int proto, struct thread *td) 845 { 846 struct inpcb *inp; 847 int error; 848 849 inp = sotoinpcb(so); 850 KASSERT(inp == NULL, ("udp6_attach: inp != NULL")); 851 852 if (so->so_snd.sb_hiwat == 0 || so->so_rcv.sb_hiwat == 0) { 853 error = soreserve(so, udp_sendspace, udp_recvspace); 854 if (error) 855 return (error); 856 } 857 INP_INFO_WLOCK(&V_udbinfo); 858 error = in_pcballoc(so, &V_udbinfo); 859 if (error) { 860 INP_INFO_WUNLOCK(&V_udbinfo); 861 return (error); 862 } 863 inp = (struct inpcb *)so->so_pcb; 864 inp->inp_vflag |= INP_IPV6; 865 if ((inp->inp_flags & IN6P_IPV6_V6ONLY) == 0) 866 inp->inp_vflag |= INP_IPV4; 867 inp->in6p_hops = -1; /* use kernel default */ 868 inp->in6p_cksum = -1; /* just to be sure */ 869 /* 870 * XXX: ugly!! 871 * IPv4 TTL initialization is necessary for an IPv6 socket as well, 872 * because the socket may be bound to an IPv6 wildcard address, 873 * which may match an IPv4-mapped IPv6 address. 874 */ 875 inp->inp_ip_ttl = V_ip_defttl; 876 877 error = udp_newudpcb(inp); 878 if (error) { 879 in_pcbdetach(inp); 880 in_pcbfree(inp); 881 INP_INFO_WUNLOCK(&V_udbinfo); 882 return (error); 883 } 884 INP_WUNLOCK(inp); 885 INP_INFO_WUNLOCK(&V_udbinfo); 886 return (0); 887 } 888 889 static int 890 udp6_bind(struct socket *so, struct sockaddr *nam, struct thread *td) 891 { 892 struct inpcb *inp; 893 int error; 894 895 inp = sotoinpcb(so); 896 KASSERT(inp != NULL, ("udp6_bind: inp == NULL")); 897 898 INP_WLOCK(inp); 899 INP_HASH_WLOCK(&V_udbinfo); 900 inp->inp_vflag &= ~INP_IPV4; 901 inp->inp_vflag |= INP_IPV6; 902 if ((inp->inp_flags & IN6P_IPV6_V6ONLY) == 0) { 903 struct sockaddr_in6 *sin6_p; 904 905 sin6_p = (struct sockaddr_in6 *)nam; 906 907 if (IN6_IS_ADDR_UNSPECIFIED(&sin6_p->sin6_addr)) 908 inp->inp_vflag |= INP_IPV4; 909 #ifdef INET 910 else if (IN6_IS_ADDR_V4MAPPED(&sin6_p->sin6_addr)) { 911 struct sockaddr_in sin; 912 913 in6_sin6_2_sin(&sin, sin6_p); 914 inp->inp_vflag |= INP_IPV4; 915 inp->inp_vflag &= ~INP_IPV6; 916 error = in_pcbbind(inp, (struct sockaddr *)&sin, 917 td->td_ucred); 918 goto out; 919 } 920 #endif 921 } 922 923 error = in6_pcbbind(inp, nam, td->td_ucred); 924 #ifdef INET 925 out: 926 #endif 927 INP_HASH_WUNLOCK(&V_udbinfo); 928 INP_WUNLOCK(inp); 929 return (error); 930 } 931 932 static void 933 udp6_close(struct socket *so) 934 { 935 struct inpcb *inp; 936 937 inp = sotoinpcb(so); 938 KASSERT(inp != NULL, ("udp6_close: inp == NULL")); 939 940 #ifdef INET 941 if (inp->inp_vflag & INP_IPV4) { 942 struct pr_usrreqs *pru; 943 944 pru = inetsw[ip_protox[IPPROTO_UDP]].pr_usrreqs; 945 (*pru->pru_disconnect)(so); 946 return; 947 } 948 #endif 949 INP_WLOCK(inp); 950 if (!IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_faddr)) { 951 INP_HASH_WLOCK(&V_udbinfo); 952 in6_pcbdisconnect(inp); 953 inp->in6p_laddr = in6addr_any; 954 INP_HASH_WUNLOCK(&V_udbinfo); 955 soisdisconnected(so); 956 } 957 INP_WUNLOCK(inp); 958 } 959 960 static int 961 udp6_connect(struct socket *so, struct sockaddr *nam, struct thread *td) 962 { 963 struct inpcb *inp; 964 struct sockaddr_in6 *sin6; 965 int error; 966 967 inp = sotoinpcb(so); 968 sin6 = (struct sockaddr_in6 *)nam; 969 KASSERT(inp != NULL, ("udp6_connect: inp == NULL")); 970 971 /* 972 * XXXRW: Need to clarify locking of v4/v6 flags. 973 */ 974 INP_WLOCK(inp); 975 #ifdef INET 976 if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) { 977 struct sockaddr_in sin; 978 979 if ((inp->inp_flags & IN6P_IPV6_V6ONLY) != 0) { 980 error = EINVAL; 981 goto out; 982 } 983 if (inp->inp_faddr.s_addr != INADDR_ANY) { 984 error = EISCONN; 985 goto out; 986 } 987 in6_sin6_2_sin(&sin, sin6); 988 inp->inp_vflag |= INP_IPV4; 989 inp->inp_vflag &= ~INP_IPV6; 990 error = prison_remote_ip4(td->td_ucred, &sin.sin_addr); 991 if (error != 0) 992 goto out; 993 INP_HASH_WLOCK(&V_udbinfo); 994 error = in_pcbconnect(inp, (struct sockaddr *)&sin, 995 td->td_ucred); 996 INP_HASH_WUNLOCK(&V_udbinfo); 997 if (error == 0) 998 soisconnected(so); 999 goto out; 1000 } 1001 #endif 1002 if (!IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_faddr)) { 1003 error = EISCONN; 1004 goto out; 1005 } 1006 inp->inp_vflag &= ~INP_IPV4; 1007 inp->inp_vflag |= INP_IPV6; 1008 error = prison_remote_ip6(td->td_ucred, &sin6->sin6_addr); 1009 if (error != 0) 1010 goto out; 1011 INP_HASH_WLOCK(&V_udbinfo); 1012 error = in6_pcbconnect(inp, nam, td->td_ucred); 1013 INP_HASH_WUNLOCK(&V_udbinfo); 1014 if (error == 0) 1015 soisconnected(so); 1016 out: 1017 INP_WUNLOCK(inp); 1018 return (error); 1019 } 1020 1021 static void 1022 udp6_detach(struct socket *so) 1023 { 1024 struct inpcb *inp; 1025 struct udpcb *up; 1026 1027 inp = sotoinpcb(so); 1028 KASSERT(inp != NULL, ("udp6_detach: inp == NULL")); 1029 1030 INP_INFO_WLOCK(&V_udbinfo); 1031 INP_WLOCK(inp); 1032 up = intoudpcb(inp); 1033 KASSERT(up != NULL, ("%s: up == NULL", __func__)); 1034 in_pcbdetach(inp); 1035 in_pcbfree(inp); 1036 INP_INFO_WUNLOCK(&V_udbinfo); 1037 udp_discardcb(up); 1038 } 1039 1040 static int 1041 udp6_disconnect(struct socket *so) 1042 { 1043 struct inpcb *inp; 1044 int error; 1045 1046 inp = sotoinpcb(so); 1047 KASSERT(inp != NULL, ("udp6_disconnect: inp == NULL")); 1048 1049 #ifdef INET 1050 if (inp->inp_vflag & INP_IPV4) { 1051 struct pr_usrreqs *pru; 1052 1053 pru = inetsw[ip_protox[IPPROTO_UDP]].pr_usrreqs; 1054 (void)(*pru->pru_disconnect)(so); 1055 return (0); 1056 } 1057 #endif 1058 1059 INP_WLOCK(inp); 1060 1061 if (IN6_IS_ADDR_UNSPECIFIED(&inp->in6p_faddr)) { 1062 error = ENOTCONN; 1063 goto out; 1064 } 1065 1066 INP_HASH_WLOCK(&V_udbinfo); 1067 in6_pcbdisconnect(inp); 1068 inp->in6p_laddr = in6addr_any; 1069 INP_HASH_WUNLOCK(&V_udbinfo); 1070 SOCK_LOCK(so); 1071 so->so_state &= ~SS_ISCONNECTED; /* XXX */ 1072 SOCK_UNLOCK(so); 1073 out: 1074 INP_WUNLOCK(inp); 1075 return (0); 1076 } 1077 1078 static int 1079 udp6_send(struct socket *so, int flags, struct mbuf *m, 1080 struct sockaddr *addr, struct mbuf *control, struct thread *td) 1081 { 1082 struct inpcb *inp; 1083 int error = 0; 1084 1085 inp = sotoinpcb(so); 1086 KASSERT(inp != NULL, ("udp6_send: inp == NULL")); 1087 1088 INP_WLOCK(inp); 1089 if (addr) { 1090 if (addr->sa_len != sizeof(struct sockaddr_in6)) { 1091 error = EINVAL; 1092 goto bad; 1093 } 1094 if (addr->sa_family != AF_INET6) { 1095 error = EAFNOSUPPORT; 1096 goto bad; 1097 } 1098 } 1099 1100 #ifdef INET 1101 if ((inp->inp_flags & IN6P_IPV6_V6ONLY) == 0) { 1102 int hasv4addr; 1103 struct sockaddr_in6 *sin6 = 0; 1104 1105 if (addr == 0) 1106 hasv4addr = (inp->inp_vflag & INP_IPV4); 1107 else { 1108 sin6 = (struct sockaddr_in6 *)addr; 1109 hasv4addr = IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr) 1110 ? 1 : 0; 1111 } 1112 if (hasv4addr) { 1113 struct pr_usrreqs *pru; 1114 1115 /* 1116 * XXXRW: We release UDP-layer locks before calling 1117 * udp_send() in order to avoid recursion. However, 1118 * this does mean there is a short window where inp's 1119 * fields are unstable. Could this lead to a 1120 * potential race in which the factors causing us to 1121 * select the UDPv4 output routine are invalidated? 1122 */ 1123 INP_WUNLOCK(inp); 1124 if (sin6) 1125 in6_sin6_2_sin_in_sock(addr); 1126 pru = inetsw[ip_protox[IPPROTO_UDP]].pr_usrreqs; 1127 /* addr will just be freed in sendit(). */ 1128 return ((*pru->pru_send)(so, flags, m, addr, control, 1129 td)); 1130 } 1131 } 1132 #endif 1133 #ifdef MAC 1134 mac_inpcb_create_mbuf(inp, m); 1135 #endif 1136 INP_HASH_WLOCK(&V_udbinfo); 1137 error = udp6_output(inp, m, addr, control, td); 1138 INP_HASH_WUNLOCK(&V_udbinfo); 1139 #ifdef INET 1140 #endif 1141 INP_WUNLOCK(inp); 1142 return (error); 1143 1144 bad: 1145 INP_WUNLOCK(inp); 1146 m_freem(m); 1147 return (error); 1148 } 1149 1150 struct pr_usrreqs udp6_usrreqs = { 1151 .pru_abort = udp6_abort, 1152 .pru_attach = udp6_attach, 1153 .pru_bind = udp6_bind, 1154 .pru_connect = udp6_connect, 1155 .pru_control = in6_control, 1156 .pru_detach = udp6_detach, 1157 .pru_disconnect = udp6_disconnect, 1158 .pru_peeraddr = in6_mapped_peeraddr, 1159 .pru_send = udp6_send, 1160 .pru_shutdown = udp_shutdown, 1161 .pru_sockaddr = in6_mapped_sockaddr, 1162 .pru_soreceive = soreceive_dgram, 1163 .pru_sosend = sosend_dgram, 1164 .pru_sosetlabel = in_pcbsosetlabel, 1165 .pru_close = udp6_close 1166 }; 1167