1 /* $NetBSD: if_vlan.c,v 1.107 2017/11/16 03:07:18 ozaki-r Exp $ */ 2 3 /*- 4 * Copyright (c) 2000, 2001 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by Andrew Doran, and by Jason R. Thorpe of Zembu Labs, Inc. 9 * 10 * Redistribution and use in source and binary forms, with or without 11 * modification, are permitted provided that the following conditions 12 * are met: 13 * 1. Redistributions of source code must retain the above copyright 14 * notice, this list of conditions and the following disclaimer. 15 * 2. Redistributions in binary form must reproduce the above copyright 16 * notice, this list of conditions and the following disclaimer in the 17 * documentation and/or other materials provided with the distribution. 18 * 19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 22 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 29 * POSSIBILITY OF SUCH DAMAGE. 30 */ 31 32 /* 33 * Copyright 1998 Massachusetts Institute of Technology 34 * 35 * Permission to use, copy, modify, and distribute this software and 36 * its documentation for any purpose and without fee is hereby 37 * granted, provided that both the above copyright notice and this 38 * permission notice appear in all copies, that both the above 39 * copyright notice and this permission notice appear in all 40 * supporting documentation, and that the name of M.I.T. not be used 41 * in advertising or publicity pertaining to distribution of the 42 * software without specific, written prior permission. M.I.T. makes 43 * no representations about the suitability of this software for any 44 * purpose. It is provided "as is" without express or implied 45 * warranty. 46 * 47 * THIS SOFTWARE IS PROVIDED BY M.I.T. ``AS IS''. M.I.T. DISCLAIMS 48 * ALL EXPRESS OR IMPLIED WARRANTIES WITH REGARD TO THIS SOFTWARE, 49 * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 50 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT 51 * SHALL M.I.T. BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 52 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 53 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF 54 * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 55 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 56 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT 57 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 58 * SUCH DAMAGE. 59 * 60 * from FreeBSD: if_vlan.c,v 1.16 2000/03/26 15:21:40 charnier Exp 61 * via OpenBSD: if_vlan.c,v 1.4 2000/05/15 19:15:00 chris Exp 62 */ 63 64 /* 65 * if_vlan.c - pseudo-device driver for IEEE 802.1Q virtual LANs. Might be 66 * extended some day to also handle IEEE 802.1P priority tagging. This is 67 * sort of sneaky in the implementation, since we need to pretend to be 68 * enough of an Ethernet implementation to make ARP work. The way we do 69 * this is by telling everyone that we are an Ethernet interface, and then 70 * catch the packets that ether_output() left on our output queue when it 71 * calls if_start(), rewrite them for use by the real outgoing interface, 72 * and ask it to send them. 73 * 74 * TODO: 75 * 76 * - Need some way to notify vlan interfaces when the parent 77 * interface changes MTU. 78 */ 79 80 #include <sys/cdefs.h> 81 __KERNEL_RCSID(0, "$NetBSD: if_vlan.c,v 1.107 2017/11/16 03:07:18 ozaki-r Exp $"); 82 83 #ifdef _KERNEL_OPT 84 #include "opt_inet.h" 85 #endif 86 87 #include <sys/param.h> 88 #include <sys/systm.h> 89 #include <sys/kernel.h> 90 #include <sys/mbuf.h> 91 #include <sys/queue.h> 92 #include <sys/socket.h> 93 #include <sys/sockio.h> 94 #include <sys/systm.h> 95 #include <sys/proc.h> 96 #include <sys/kauth.h> 97 #include <sys/mutex.h> 98 #include <sys/kmem.h> 99 #include <sys/cpu.h> 100 #include <sys/pserialize.h> 101 #include <sys/psref.h> 102 #include <sys/pslist.h> 103 #include <sys/atomic.h> 104 #include <sys/device.h> 105 #include <sys/module.h> 106 107 #include <net/bpf.h> 108 #include <net/if.h> 109 #include <net/if_dl.h> 110 #include <net/if_types.h> 111 #include <net/if_ether.h> 112 #include <net/if_vlanvar.h> 113 114 #ifdef INET 115 #include <netinet/in.h> 116 #include <netinet/if_inarp.h> 117 #endif 118 #ifdef INET6 119 #include <netinet6/in6_ifattach.h> 120 #include <netinet6/in6_var.h> 121 #endif 122 123 #include "ioconf.h" 124 125 struct vlan_mc_entry { 126 LIST_ENTRY(vlan_mc_entry) mc_entries; 127 /* 128 * A key to identify this entry. The mc_addr below can't be 129 * used since multiple sockaddr may mapped into the same 130 * ether_multi (e.g., AF_UNSPEC). 131 */ 132 union { 133 struct ether_multi *mcu_enm; 134 } mc_u; 135 struct sockaddr_storage mc_addr; 136 }; 137 138 #define mc_enm mc_u.mcu_enm 139 140 141 struct ifvlan_linkmib { 142 struct ifvlan *ifvm_ifvlan; 143 const struct vlan_multisw *ifvm_msw; 144 int ifvm_encaplen; /* encapsulation length */ 145 int ifvm_mtufudge; /* MTU fudged by this much */ 146 int ifvm_mintu; /* min transmission unit */ 147 uint16_t ifvm_proto; /* encapsulation ethertype */ 148 uint16_t ifvm_tag; /* tag to apply on packets */ 149 struct ifnet *ifvm_p; /* parent interface of this vlan */ 150 151 struct psref_target ifvm_psref; 152 }; 153 154 struct ifvlan { 155 union { 156 struct ethercom ifvu_ec; 157 } ifv_u; 158 struct ifvlan_linkmib *ifv_mib; /* 159 * reader must use vlan_getref_linkmib() 160 * instead of direct dereference 161 */ 162 kmutex_t ifv_lock; /* writer lock for ifv_mib */ 163 164 LIST_HEAD(__vlan_mchead, vlan_mc_entry) ifv_mc_listhead; 165 LIST_ENTRY(ifvlan) ifv_list; 166 struct pslist_entry ifv_hash; 167 int ifv_flags; 168 }; 169 170 #define IFVF_PROMISC 0x01 /* promiscuous mode enabled */ 171 172 #define ifv_ec ifv_u.ifvu_ec 173 174 #define ifv_if ifv_ec.ec_if 175 176 #define ifv_msw ifv_mib.ifvm_msw 177 #define ifv_encaplen ifv_mib.ifvm_encaplen 178 #define ifv_mtufudge ifv_mib.ifvm_mtufudge 179 #define ifv_mintu ifv_mib.ifvm_mintu 180 #define ifv_tag ifv_mib.ifvm_tag 181 182 struct vlan_multisw { 183 int (*vmsw_addmulti)(struct ifvlan *, struct ifreq *); 184 int (*vmsw_delmulti)(struct ifvlan *, struct ifreq *); 185 void (*vmsw_purgemulti)(struct ifvlan *); 186 }; 187 188 static int vlan_ether_addmulti(struct ifvlan *, struct ifreq *); 189 static int vlan_ether_delmulti(struct ifvlan *, struct ifreq *); 190 static void vlan_ether_purgemulti(struct ifvlan *); 191 192 const struct vlan_multisw vlan_ether_multisw = { 193 vlan_ether_addmulti, 194 vlan_ether_delmulti, 195 vlan_ether_purgemulti, 196 }; 197 198 static int vlan_clone_create(struct if_clone *, int); 199 static int vlan_clone_destroy(struct ifnet *); 200 static int vlan_config(struct ifvlan *, struct ifnet *, 201 uint16_t); 202 static int vlan_ioctl(struct ifnet *, u_long, void *); 203 static void vlan_start(struct ifnet *); 204 static int vlan_transmit(struct ifnet *, struct mbuf *); 205 static void vlan_unconfig(struct ifnet *); 206 static int vlan_unconfig_locked(struct ifvlan *, 207 struct ifvlan_linkmib *); 208 static void vlan_hash_init(void); 209 static int vlan_hash_fini(void); 210 static struct ifvlan_linkmib* vlan_getref_linkmib(struct ifvlan *, 211 struct psref *); 212 static void vlan_putref_linkmib(struct ifvlan_linkmib *, 213 struct psref *); 214 static void vlan_linkmib_update(struct ifvlan *, 215 struct ifvlan_linkmib *); 216 static struct ifvlan_linkmib* vlan_lookup_tag_psref(struct ifnet *, 217 uint16_t, struct psref *); 218 static int tag_hash_func(uint16_t, u_long); 219 220 LIST_HEAD(vlan_ifvlist, ifvlan); 221 static struct { 222 kmutex_t lock; 223 struct vlan_ifvlist list; 224 } ifv_list __cacheline_aligned; 225 226 227 #if !defined(VLAN_TAG_HASH_SIZE) 228 #define VLAN_TAG_HASH_SIZE 32 229 #endif 230 static struct { 231 kmutex_t lock; 232 struct pslist_head *lists; 233 u_long mask; 234 } ifv_hash __cacheline_aligned = { 235 .lists = NULL, 236 .mask = 0, 237 }; 238 239 pserialize_t vlan_psz __read_mostly; 240 static struct psref_class *ifvm_psref_class __read_mostly; 241 242 struct if_clone vlan_cloner = 243 IF_CLONE_INITIALIZER("vlan", vlan_clone_create, vlan_clone_destroy); 244 245 /* Used to pad ethernet frames with < ETHER_MIN_LEN bytes */ 246 static char vlan_zero_pad_buff[ETHER_MIN_LEN]; 247 248 void 249 vlanattach(int n) 250 { 251 252 /* 253 * Nothing to do here, initialization is handled by the 254 * module initialization code in vlaninit() below). 255 */ 256 } 257 258 static void 259 vlaninit(void) 260 { 261 mutex_init(&ifv_list.lock, MUTEX_DEFAULT, IPL_NONE); 262 LIST_INIT(&ifv_list.list); 263 264 mutex_init(&ifv_hash.lock, MUTEX_DEFAULT, IPL_NONE); 265 vlan_psz = pserialize_create(); 266 ifvm_psref_class = psref_class_create("vlanlinkmib", IPL_SOFTNET); 267 if_clone_attach(&vlan_cloner); 268 269 vlan_hash_init(); 270 } 271 272 static int 273 vlandetach(void) 274 { 275 int error = 0; 276 277 mutex_enter(&ifv_list.lock); 278 if (!LIST_EMPTY(&ifv_list.list)) { 279 mutex_exit(&ifv_list.lock); 280 return EBUSY; 281 } 282 mutex_exit(&ifv_list.lock); 283 284 error = vlan_hash_fini(); 285 if (error != 0) 286 return error; 287 288 if_clone_detach(&vlan_cloner); 289 psref_class_destroy(ifvm_psref_class); 290 pserialize_destroy(vlan_psz); 291 mutex_destroy(&ifv_hash.lock); 292 mutex_destroy(&ifv_list.lock); 293 294 return 0; 295 } 296 297 static void 298 vlan_reset_linkname(struct ifnet *ifp) 299 { 300 301 /* 302 * We start out with a "802.1Q VLAN" type and zero-length 303 * addresses. When we attach to a parent interface, we 304 * inherit its type, address length, address, and data link 305 * type. 306 */ 307 308 ifp->if_type = IFT_L2VLAN; 309 ifp->if_addrlen = 0; 310 ifp->if_dlt = DLT_NULL; 311 if_alloc_sadl(ifp); 312 } 313 314 static int 315 vlan_clone_create(struct if_clone *ifc, int unit) 316 { 317 struct ifvlan *ifv; 318 struct ifnet *ifp; 319 struct ifvlan_linkmib *mib; 320 int rv; 321 322 ifv = malloc(sizeof(struct ifvlan), M_DEVBUF, M_WAITOK|M_ZERO); 323 mib = kmem_zalloc(sizeof(struct ifvlan_linkmib), KM_SLEEP); 324 ifp = &ifv->ifv_if; 325 LIST_INIT(&ifv->ifv_mc_listhead); 326 327 mib->ifvm_ifvlan = ifv; 328 mib->ifvm_p = NULL; 329 psref_target_init(&mib->ifvm_psref, ifvm_psref_class); 330 331 mutex_init(&ifv->ifv_lock, MUTEX_DEFAULT, IPL_NONE); 332 ifv->ifv_mib = mib; 333 334 mutex_enter(&ifv_list.lock); 335 LIST_INSERT_HEAD(&ifv_list.list, ifv, ifv_list); 336 mutex_exit(&ifv_list.lock); 337 338 if_initname(ifp, ifc->ifc_name, unit); 339 ifp->if_softc = ifv; 340 ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST; 341 ifp->if_extflags = IFEF_MPSAFE | IFEF_NO_LINK_STATE_CHANGE; 342 ifp->if_start = vlan_start; 343 ifp->if_transmit = vlan_transmit; 344 ifp->if_ioctl = vlan_ioctl; 345 IFQ_SET_READY(&ifp->if_snd); 346 347 rv = if_initialize(ifp); 348 if (rv != 0) { 349 aprint_error("%s: if_initialize failed(%d)\n", ifp->if_xname, 350 rv); 351 goto fail; 352 } 353 354 vlan_reset_linkname(ifp); 355 if_register(ifp); 356 return 0; 357 358 fail: 359 mutex_enter(&ifv_list.lock); 360 LIST_REMOVE(ifv, ifv_list); 361 mutex_exit(&ifv_list.lock); 362 363 mutex_destroy(&ifv->ifv_lock); 364 psref_target_destroy(&ifv->ifv_mib->ifvm_psref, ifvm_psref_class); 365 kmem_free(ifv->ifv_mib, sizeof(struct ifvlan_linkmib)); 366 free(ifv, M_DEVBUF); 367 368 return rv; 369 } 370 371 static int 372 vlan_clone_destroy(struct ifnet *ifp) 373 { 374 struct ifvlan *ifv = ifp->if_softc; 375 376 mutex_enter(&ifv_list.lock); 377 LIST_REMOVE(ifv, ifv_list); 378 mutex_exit(&ifv_list.lock); 379 380 vlan_unconfig(ifp); 381 if_detach(ifp); 382 383 psref_target_destroy(&ifv->ifv_mib->ifvm_psref, ifvm_psref_class); 384 kmem_free(ifv->ifv_mib, sizeof(struct ifvlan_linkmib)); 385 mutex_destroy(&ifv->ifv_lock); 386 free(ifv, M_DEVBUF); 387 388 return (0); 389 } 390 391 /* 392 * Configure a VLAN interface. 393 */ 394 static int 395 vlan_config(struct ifvlan *ifv, struct ifnet *p, uint16_t tag) 396 { 397 struct ifnet *ifp = &ifv->ifv_if; 398 struct ifvlan_linkmib *nmib = NULL; 399 struct ifvlan_linkmib *omib = NULL; 400 struct ifvlan_linkmib *checkmib = NULL; 401 struct psref_target *nmib_psref = NULL; 402 int error = 0; 403 int idx; 404 bool omib_cleanup = false; 405 struct psref psref; 406 407 nmib = kmem_alloc(sizeof(*nmib), KM_SLEEP); 408 409 mutex_enter(&ifv->ifv_lock); 410 omib = ifv->ifv_mib; 411 412 if (omib->ifvm_p != NULL) { 413 error = EBUSY; 414 goto done; 415 } 416 417 /* Duplicate check */ 418 checkmib = vlan_lookup_tag_psref(p, tag, &psref); 419 if (checkmib != NULL) { 420 vlan_putref_linkmib(checkmib, &psref); 421 error = EEXIST; 422 goto done; 423 } 424 425 *nmib = *omib; 426 nmib_psref = &nmib->ifvm_psref; 427 428 psref_target_init(nmib_psref, ifvm_psref_class); 429 430 switch (p->if_type) { 431 case IFT_ETHER: 432 { 433 struct ethercom *ec = (void *) p; 434 nmib->ifvm_msw = &vlan_ether_multisw; 435 nmib->ifvm_encaplen = ETHER_VLAN_ENCAP_LEN; 436 nmib->ifvm_mintu = ETHERMIN; 437 438 if (ec->ec_nvlans++ == 0) { 439 if ((error = ether_enable_vlan_mtu(p)) >= 0) { 440 if (error) { 441 ec->ec_nvlans--; 442 goto done; 443 } 444 nmib->ifvm_mtufudge = 0; 445 } else { 446 /* 447 * Fudge the MTU by the encapsulation size. This 448 * makes us incompatible with strictly compliant 449 * 802.1Q implementations, but allows us to use 450 * the feature with other NetBSD 451 * implementations, which might still be useful. 452 */ 453 nmib->ifvm_mtufudge = nmib->ifvm_encaplen; 454 } 455 error = 0; 456 } 457 458 /* 459 * If the parent interface can do hardware-assisted 460 * VLAN encapsulation, then propagate its hardware- 461 * assisted checksumming flags and tcp segmentation 462 * offload. 463 */ 464 if (ec->ec_capabilities & ETHERCAP_VLAN_HWTAGGING) { 465 ec->ec_capenable |= ETHERCAP_VLAN_HWTAGGING; 466 ifp->if_capabilities = p->if_capabilities & 467 (IFCAP_TSOv4 | IFCAP_TSOv6 | 468 IFCAP_CSUM_IPv4_Tx|IFCAP_CSUM_IPv4_Rx| 469 IFCAP_CSUM_TCPv4_Tx|IFCAP_CSUM_TCPv4_Rx| 470 IFCAP_CSUM_UDPv4_Tx|IFCAP_CSUM_UDPv4_Rx| 471 IFCAP_CSUM_TCPv6_Tx|IFCAP_CSUM_TCPv6_Rx| 472 IFCAP_CSUM_UDPv6_Tx|IFCAP_CSUM_UDPv6_Rx); 473 } 474 /* 475 * We inherit the parent's Ethernet address. 476 */ 477 ether_ifattach(ifp, CLLADDR(p->if_sadl)); 478 ifp->if_hdrlen = sizeof(struct ether_vlan_header); /* XXX? */ 479 break; 480 } 481 482 default: 483 error = EPROTONOSUPPORT; 484 goto done; 485 } 486 487 nmib->ifvm_p = p; 488 nmib->ifvm_tag = tag; 489 ifv->ifv_if.if_mtu = p->if_mtu - nmib->ifvm_mtufudge; 490 ifv->ifv_if.if_flags = p->if_flags & 491 (IFF_UP | IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST); 492 493 /* 494 * Inherit the if_type from the parent. This allows us 495 * to participate in bridges of that type. 496 */ 497 ifv->ifv_if.if_type = p->if_type; 498 499 PSLIST_ENTRY_INIT(ifv, ifv_hash); 500 idx = tag_hash_func(tag, ifv_hash.mask); 501 502 mutex_enter(&ifv_hash.lock); 503 PSLIST_WRITER_INSERT_HEAD(&ifv_hash.lists[idx], ifv, ifv_hash); 504 mutex_exit(&ifv_hash.lock); 505 506 vlan_linkmib_update(ifv, nmib); 507 nmib = NULL; 508 nmib_psref = NULL; 509 omib_cleanup = true; 510 511 done: 512 mutex_exit(&ifv->ifv_lock); 513 514 if (nmib_psref) 515 psref_target_destroy(nmib_psref, ifvm_psref_class); 516 517 if (nmib) 518 kmem_free(nmib, sizeof(*nmib)); 519 520 if (omib_cleanup) 521 kmem_free(omib, sizeof(*omib)); 522 523 return error; 524 } 525 526 /* 527 * Unconfigure a VLAN interface. 528 */ 529 static void 530 vlan_unconfig(struct ifnet *ifp) 531 { 532 struct ifvlan *ifv = ifp->if_softc; 533 struct ifvlan_linkmib *nmib = NULL; 534 int error; 535 536 nmib = kmem_alloc(sizeof(*nmib), KM_SLEEP); 537 538 mutex_enter(&ifv->ifv_lock); 539 error = vlan_unconfig_locked(ifv, nmib); 540 mutex_exit(&ifv->ifv_lock); 541 542 if (error) 543 kmem_free(nmib, sizeof(*nmib)); 544 } 545 static int 546 vlan_unconfig_locked(struct ifvlan *ifv, struct ifvlan_linkmib *nmib) 547 { 548 struct ifnet *p; 549 struct ifnet *ifp = &ifv->ifv_if; 550 struct psref_target *nmib_psref = NULL; 551 struct ifvlan_linkmib *omib; 552 int error = 0; 553 554 KASSERT(mutex_owned(&ifv->ifv_lock)); 555 556 omib = ifv->ifv_mib; 557 p = omib->ifvm_p; 558 559 if (p == NULL) { 560 error = -1; 561 goto done; 562 } 563 564 *nmib = *omib; 565 nmib_psref = &nmib->ifvm_psref; 566 psref_target_init(nmib_psref, ifvm_psref_class); 567 568 /* 569 * Since the interface is being unconfigured, we need to empty the 570 * list of multicast groups that we may have joined while we were 571 * alive and remove them from the parent's list also. 572 */ 573 (*nmib->ifvm_msw->vmsw_purgemulti)(ifv); 574 575 /* Disconnect from parent. */ 576 switch (p->if_type) { 577 case IFT_ETHER: 578 { 579 struct ethercom *ec = (void *)p; 580 if (--ec->ec_nvlans == 0) 581 (void)ether_disable_vlan_mtu(p); 582 583 ether_ifdetach(ifp); 584 /* Restore vlan_ioctl overwritten by ether_ifdetach */ 585 ifp->if_ioctl = vlan_ioctl; 586 vlan_reset_linkname(ifp); 587 break; 588 } 589 590 #ifdef DIAGNOSTIC 591 default: 592 panic("vlan_unconfig: impossible"); 593 #endif 594 } 595 596 nmib->ifvm_p = NULL; 597 ifv->ifv_if.if_mtu = 0; 598 ifv->ifv_flags = 0; 599 600 mutex_enter(&ifv_hash.lock); 601 PSLIST_WRITER_REMOVE(ifv, ifv_hash); 602 pserialize_perform(vlan_psz); 603 mutex_exit(&ifv_hash.lock); 604 PSLIST_ENTRY_DESTROY(ifv, ifv_hash); 605 606 vlan_linkmib_update(ifv, nmib); 607 608 mutex_exit(&ifv->ifv_lock); 609 610 nmib_psref = NULL; 611 kmem_free(omib, sizeof(*omib)); 612 613 #ifdef INET6 614 /* To delete v6 link local addresses */ 615 if (in6_present) 616 in6_ifdetach(ifp); 617 #endif 618 619 if ((ifp->if_flags & IFF_PROMISC) != 0) 620 ifpromisc(ifp, 0); 621 if_down(ifp); 622 ifp->if_flags &= ~(IFF_UP|IFF_RUNNING); 623 ifp->if_capabilities = 0; 624 mutex_enter(&ifv->ifv_lock); 625 done: 626 627 if (nmib_psref) 628 psref_target_destroy(nmib_psref, ifvm_psref_class); 629 630 return error; 631 } 632 633 static void 634 vlan_hash_init(void) 635 { 636 637 ifv_hash.lists = hashinit(VLAN_TAG_HASH_SIZE, HASH_PSLIST, true, 638 &ifv_hash.mask); 639 } 640 641 static int 642 vlan_hash_fini(void) 643 { 644 int i; 645 646 mutex_enter(&ifv_hash.lock); 647 648 for (i = 0; i < ifv_hash.mask + 1; i++) { 649 if (PSLIST_WRITER_FIRST(&ifv_hash.lists[i], struct ifvlan, 650 ifv_hash) != NULL) { 651 mutex_exit(&ifv_hash.lock); 652 return EBUSY; 653 } 654 } 655 656 for (i = 0; i < ifv_hash.mask + 1; i++) 657 PSLIST_DESTROY(&ifv_hash.lists[i]); 658 659 mutex_exit(&ifv_hash.lock); 660 661 hashdone(ifv_hash.lists, HASH_PSLIST, ifv_hash.mask); 662 663 ifv_hash.lists = NULL; 664 ifv_hash.mask = 0; 665 666 return 0; 667 } 668 669 static int 670 tag_hash_func(uint16_t tag, u_long mask) 671 { 672 uint32_t hash; 673 674 hash = (tag >> 8) ^ tag; 675 hash = (hash >> 2) ^ hash; 676 677 return hash & mask; 678 } 679 680 static struct ifvlan_linkmib * 681 vlan_getref_linkmib(struct ifvlan *sc, struct psref *psref) 682 { 683 struct ifvlan_linkmib *mib; 684 int s; 685 686 s = pserialize_read_enter(); 687 mib = sc->ifv_mib; 688 if (mib == NULL) { 689 pserialize_read_exit(s); 690 return NULL; 691 } 692 membar_datadep_consumer(); 693 psref_acquire(psref, &mib->ifvm_psref, ifvm_psref_class); 694 pserialize_read_exit(s); 695 696 return mib; 697 } 698 699 static void 700 vlan_putref_linkmib(struct ifvlan_linkmib *mib, struct psref *psref) 701 { 702 if (mib == NULL) 703 return; 704 psref_release(psref, &mib->ifvm_psref, ifvm_psref_class); 705 } 706 707 static struct ifvlan_linkmib * 708 vlan_lookup_tag_psref(struct ifnet *ifp, uint16_t tag, struct psref *psref) 709 { 710 int idx; 711 int s; 712 struct ifvlan *sc; 713 714 idx = tag_hash_func(tag, ifv_hash.mask); 715 716 s = pserialize_read_enter(); 717 PSLIST_READER_FOREACH(sc, &ifv_hash.lists[idx], struct ifvlan, 718 ifv_hash) { 719 struct ifvlan_linkmib *mib = sc->ifv_mib; 720 if (mib == NULL) 721 continue; 722 if (mib->ifvm_tag != tag) 723 continue; 724 if (mib->ifvm_p != ifp) 725 continue; 726 727 psref_acquire(psref, &mib->ifvm_psref, ifvm_psref_class); 728 pserialize_read_exit(s); 729 return mib; 730 } 731 pserialize_read_exit(s); 732 return NULL; 733 } 734 735 static void 736 vlan_linkmib_update(struct ifvlan *ifv, struct ifvlan_linkmib *nmib) 737 { 738 struct ifvlan_linkmib *omib = ifv->ifv_mib; 739 740 KASSERT(mutex_owned(&ifv->ifv_lock)); 741 742 membar_producer(); 743 ifv->ifv_mib = nmib; 744 745 pserialize_perform(vlan_psz); 746 psref_target_destroy(&omib->ifvm_psref, ifvm_psref_class); 747 } 748 749 /* 750 * Called when a parent interface is detaching; destroy any VLAN 751 * configuration for the parent interface. 752 */ 753 void 754 vlan_ifdetach(struct ifnet *p) 755 { 756 struct ifvlan *ifv; 757 struct ifvlan_linkmib *mib, **nmibs; 758 struct psref psref; 759 int error; 760 int bound; 761 int i, cnt = 0; 762 763 bound = curlwp_bind(); 764 mutex_enter(&ifv_list.lock); 765 LIST_FOREACH(ifv, &ifv_list.list, ifv_list) { 766 mib = vlan_getref_linkmib(ifv, &psref); 767 if (mib == NULL) 768 continue; 769 770 if (mib->ifvm_p == p) 771 cnt++; 772 773 vlan_putref_linkmib(mib, &psref); 774 } 775 mutex_exit(&ifv_list.lock); 776 777 /* 778 * The value of "cnt" does not increase while ifv_list.lock 779 * and ifv->ifv_lock are released here, because the parent 780 * interface is detaching. 781 */ 782 nmibs = kmem_alloc(sizeof(*nmibs) * cnt, KM_SLEEP); 783 for (i=0; i < cnt; i++) { 784 nmibs[i] = kmem_alloc(sizeof(*nmibs[i]), KM_SLEEP); 785 } 786 787 mutex_enter(&ifv_list.lock); 788 789 i = 0; 790 LIST_FOREACH(ifv, &ifv_list.list, ifv_list) { 791 mutex_enter(&ifv->ifv_lock); 792 if (ifv->ifv_mib->ifvm_p == p) { 793 KASSERTMSG(i < cnt, "no memory for unconfig, parent=%s", 794 p->if_xname); 795 error = vlan_unconfig_locked(ifv, nmibs[i]); 796 if (!error) { 797 nmibs[i] = NULL; 798 i++; 799 } 800 801 } 802 mutex_exit(&ifv->ifv_lock); 803 } 804 805 mutex_exit(&ifv_list.lock); 806 curlwp_bindx(bound); 807 808 for (i=0; i < cnt; i++) { 809 if (nmibs[i]) 810 kmem_free(nmibs[i], sizeof(*nmibs[i])); 811 } 812 813 kmem_free(nmibs, sizeof(*nmibs) * cnt); 814 815 return; 816 } 817 818 static int 819 vlan_set_promisc(struct ifnet *ifp) 820 { 821 struct ifvlan *ifv = ifp->if_softc; 822 struct ifvlan_linkmib *mib; 823 struct psref psref; 824 int error = 0; 825 int bound; 826 827 bound = curlwp_bind(); 828 mib = vlan_getref_linkmib(ifv, &psref); 829 if (mib == NULL) { 830 curlwp_bindx(bound); 831 return EBUSY; 832 } 833 834 if ((ifp->if_flags & IFF_PROMISC) != 0) { 835 if ((ifv->ifv_flags & IFVF_PROMISC) == 0) { 836 error = ifpromisc(mib->ifvm_p, 1); 837 if (error == 0) 838 ifv->ifv_flags |= IFVF_PROMISC; 839 } 840 } else { 841 if ((ifv->ifv_flags & IFVF_PROMISC) != 0) { 842 error = ifpromisc(mib->ifvm_p, 0); 843 if (error == 0) 844 ifv->ifv_flags &= ~IFVF_PROMISC; 845 } 846 } 847 vlan_putref_linkmib(mib, &psref); 848 curlwp_bindx(bound); 849 850 return (error); 851 } 852 853 static int 854 vlan_ioctl(struct ifnet *ifp, u_long cmd, void *data) 855 { 856 struct lwp *l = curlwp; /* XXX */ 857 struct ifvlan *ifv = ifp->if_softc; 858 struct ifaddr *ifa = (struct ifaddr *) data; 859 struct ifreq *ifr = (struct ifreq *) data; 860 struct ifnet *pr; 861 struct ifcapreq *ifcr; 862 struct vlanreq vlr; 863 struct ifvlan_linkmib *mib; 864 struct psref psref; 865 int error = 0; 866 int bound; 867 868 switch (cmd) { 869 case SIOCSIFMTU: 870 bound = curlwp_bind(); 871 mib = vlan_getref_linkmib(ifv, &psref); 872 if (mib == NULL) { 873 curlwp_bindx(bound); 874 error = EBUSY; 875 break; 876 } 877 878 if (mib->ifvm_p == NULL) { 879 vlan_putref_linkmib(mib, &psref); 880 curlwp_bindx(bound); 881 error = EINVAL; 882 } else if ( 883 ifr->ifr_mtu > (mib->ifvm_p->if_mtu - mib->ifvm_mtufudge) || 884 ifr->ifr_mtu < (mib->ifvm_mintu - mib->ifvm_mtufudge)) { 885 vlan_putref_linkmib(mib, &psref); 886 curlwp_bindx(bound); 887 error = EINVAL; 888 } else { 889 vlan_putref_linkmib(mib, &psref); 890 curlwp_bindx(bound); 891 892 error = ifioctl_common(ifp, cmd, data); 893 if (error == ENETRESET) 894 error = 0; 895 } 896 897 break; 898 899 case SIOCSETVLAN: 900 if ((error = kauth_authorize_network(l->l_cred, 901 KAUTH_NETWORK_INTERFACE, 902 KAUTH_REQ_NETWORK_INTERFACE_SETPRIV, ifp, (void *)cmd, 903 NULL)) != 0) 904 break; 905 if ((error = copyin(ifr->ifr_data, &vlr, sizeof(vlr))) != 0) 906 break; 907 908 if (vlr.vlr_parent[0] == '\0') { 909 bound = curlwp_bind(); 910 mib = vlan_getref_linkmib(ifv, &psref); 911 if (mib == NULL) { 912 curlwp_bindx(bound); 913 error = EBUSY; 914 break; 915 } 916 917 if (mib->ifvm_p != NULL && 918 (ifp->if_flags & IFF_PROMISC) != 0) 919 error = ifpromisc(mib->ifvm_p, 0); 920 921 vlan_putref_linkmib(mib, &psref); 922 curlwp_bindx(bound); 923 924 vlan_unconfig(ifp); 925 break; 926 } 927 if (vlr.vlr_tag != EVL_VLANOFTAG(vlr.vlr_tag)) { 928 error = EINVAL; /* check for valid tag */ 929 break; 930 } 931 if ((pr = ifunit(vlr.vlr_parent)) == 0) { 932 error = ENOENT; 933 break; 934 } 935 error = vlan_config(ifv, pr, vlr.vlr_tag); 936 if (error != 0) { 937 break; 938 } 939 ifp->if_flags |= IFF_RUNNING; 940 941 /* Update promiscuous mode, if necessary. */ 942 vlan_set_promisc(ifp); 943 break; 944 945 case SIOCGETVLAN: 946 memset(&vlr, 0, sizeof(vlr)); 947 bound = curlwp_bind(); 948 mib = vlan_getref_linkmib(ifv, &psref); 949 if (mib == NULL) { 950 curlwp_bindx(bound); 951 error = EBUSY; 952 break; 953 } 954 if (mib->ifvm_p != NULL) { 955 snprintf(vlr.vlr_parent, sizeof(vlr.vlr_parent), "%s", 956 mib->ifvm_p->if_xname); 957 vlr.vlr_tag = mib->ifvm_tag; 958 } 959 vlan_putref_linkmib(mib, &psref); 960 curlwp_bindx(bound); 961 error = copyout(&vlr, ifr->ifr_data, sizeof(vlr)); 962 break; 963 964 case SIOCSIFFLAGS: 965 if ((error = ifioctl_common(ifp, cmd, data)) != 0) 966 break; 967 /* 968 * For promiscuous mode, we enable promiscuous mode on 969 * the parent if we need promiscuous on the VLAN interface. 970 */ 971 bound = curlwp_bind(); 972 mib = vlan_getref_linkmib(ifv, &psref); 973 if (mib == NULL) { 974 curlwp_bindx(bound); 975 error = EBUSY; 976 break; 977 } 978 979 if (mib->ifvm_p != NULL) 980 error = vlan_set_promisc(ifp); 981 vlan_putref_linkmib(mib, &psref); 982 curlwp_bindx(bound); 983 break; 984 985 case SIOCADDMULTI: 986 mutex_enter(&ifv->ifv_lock); 987 mib = ifv->ifv_mib; 988 if (mib == NULL) { 989 error = EBUSY; 990 mutex_exit(&ifv->ifv_lock); 991 break; 992 } 993 994 error = (mib->ifvm_p != NULL) ? 995 (*mib->ifvm_msw->vmsw_addmulti)(ifv, ifr) : EINVAL; 996 mib = NULL; 997 mutex_exit(&ifv->ifv_lock); 998 break; 999 1000 case SIOCDELMULTI: 1001 mutex_enter(&ifv->ifv_lock); 1002 mib = ifv->ifv_mib; 1003 if (mib == NULL) { 1004 error = EBUSY; 1005 mutex_exit(&ifv->ifv_lock); 1006 break; 1007 } 1008 error = (mib->ifvm_p != NULL) ? 1009 (*mib->ifvm_msw->vmsw_delmulti)(ifv, ifr) : EINVAL; 1010 mib = NULL; 1011 mutex_exit(&ifv->ifv_lock); 1012 break; 1013 1014 case SIOCSIFCAP: 1015 ifcr = data; 1016 /* make sure caps are enabled on parent */ 1017 bound = curlwp_bind(); 1018 mib = vlan_getref_linkmib(ifv, &psref); 1019 if (mib == NULL) { 1020 curlwp_bindx(bound); 1021 error = EBUSY; 1022 break; 1023 } 1024 1025 if (mib->ifvm_p == NULL) { 1026 vlan_putref_linkmib(mib, &psref); 1027 curlwp_bindx(bound); 1028 error = EINVAL; 1029 break; 1030 } 1031 if ((mib->ifvm_p->if_capenable & ifcr->ifcr_capenable) != 1032 ifcr->ifcr_capenable) { 1033 vlan_putref_linkmib(mib, &psref); 1034 curlwp_bindx(bound); 1035 error = EINVAL; 1036 break; 1037 } 1038 1039 vlan_putref_linkmib(mib, &psref); 1040 curlwp_bindx(bound); 1041 1042 if ((error = ifioctl_common(ifp, cmd, data)) == ENETRESET) 1043 error = 0; 1044 break; 1045 case SIOCINITIFADDR: 1046 bound = curlwp_bind(); 1047 mib = vlan_getref_linkmib(ifv, &psref); 1048 if (mib == NULL) { 1049 curlwp_bindx(bound); 1050 error = EBUSY; 1051 break; 1052 } 1053 1054 if (mib->ifvm_p == NULL) { 1055 error = EINVAL; 1056 vlan_putref_linkmib(mib, &psref); 1057 curlwp_bindx(bound); 1058 break; 1059 } 1060 vlan_putref_linkmib(mib, &psref); 1061 curlwp_bindx(bound); 1062 1063 ifp->if_flags |= IFF_UP; 1064 #ifdef INET 1065 if (ifa->ifa_addr->sa_family == AF_INET) 1066 arp_ifinit(ifp, ifa); 1067 #endif 1068 break; 1069 1070 default: 1071 error = ether_ioctl(ifp, cmd, data); 1072 } 1073 1074 return (error); 1075 } 1076 1077 static int 1078 vlan_ether_addmulti(struct ifvlan *ifv, struct ifreq *ifr) 1079 { 1080 const struct sockaddr *sa = ifreq_getaddr(SIOCADDMULTI, ifr); 1081 struct vlan_mc_entry *mc; 1082 uint8_t addrlo[ETHER_ADDR_LEN], addrhi[ETHER_ADDR_LEN]; 1083 struct ifvlan_linkmib *mib; 1084 int error; 1085 1086 KASSERT(mutex_owned(&ifv->ifv_lock)); 1087 1088 if (sa->sa_len > sizeof(struct sockaddr_storage)) 1089 return (EINVAL); 1090 1091 error = ether_addmulti(sa, &ifv->ifv_ec); 1092 if (error != ENETRESET) 1093 return (error); 1094 1095 /* 1096 * This is new multicast address. We have to tell parent 1097 * about it. Also, remember this multicast address so that 1098 * we can delete them on unconfigure. 1099 */ 1100 mc = malloc(sizeof(struct vlan_mc_entry), M_DEVBUF, M_NOWAIT); 1101 if (mc == NULL) { 1102 error = ENOMEM; 1103 goto alloc_failed; 1104 } 1105 1106 /* 1107 * As ether_addmulti() returns ENETRESET, following two 1108 * statement shouldn't fail. 1109 */ 1110 (void)ether_multiaddr(sa, addrlo, addrhi); 1111 ETHER_LOOKUP_MULTI(addrlo, addrhi, &ifv->ifv_ec, mc->mc_enm); 1112 memcpy(&mc->mc_addr, sa, sa->sa_len); 1113 LIST_INSERT_HEAD(&ifv->ifv_mc_listhead, mc, mc_entries); 1114 1115 mib = ifv->ifv_mib; 1116 error = if_mcast_op(mib->ifvm_p, SIOCADDMULTI, sa); 1117 1118 if (error != 0) 1119 goto ioctl_failed; 1120 return (error); 1121 1122 ioctl_failed: 1123 LIST_REMOVE(mc, mc_entries); 1124 free(mc, M_DEVBUF); 1125 alloc_failed: 1126 (void)ether_delmulti(sa, &ifv->ifv_ec); 1127 return (error); 1128 } 1129 1130 static int 1131 vlan_ether_delmulti(struct ifvlan *ifv, struct ifreq *ifr) 1132 { 1133 const struct sockaddr *sa = ifreq_getaddr(SIOCDELMULTI, ifr); 1134 struct ether_multi *enm; 1135 struct vlan_mc_entry *mc; 1136 struct ifvlan_linkmib *mib; 1137 uint8_t addrlo[ETHER_ADDR_LEN], addrhi[ETHER_ADDR_LEN]; 1138 int error; 1139 1140 KASSERT(mutex_owned(&ifv->ifv_lock)); 1141 1142 /* 1143 * Find a key to lookup vlan_mc_entry. We have to do this 1144 * before calling ether_delmulti for obvious reason. 1145 */ 1146 if ((error = ether_multiaddr(sa, addrlo, addrhi)) != 0) 1147 return (error); 1148 ETHER_LOOKUP_MULTI(addrlo, addrhi, &ifv->ifv_ec, enm); 1149 1150 error = ether_delmulti(sa, &ifv->ifv_ec); 1151 if (error != ENETRESET) 1152 return (error); 1153 1154 /* We no longer use this multicast address. Tell parent so. */ 1155 mib = ifv->ifv_mib; 1156 error = if_mcast_op(mib->ifvm_p, SIOCDELMULTI, sa); 1157 1158 if (error == 0) { 1159 /* And forget about this address. */ 1160 for (mc = LIST_FIRST(&ifv->ifv_mc_listhead); mc != NULL; 1161 mc = LIST_NEXT(mc, mc_entries)) { 1162 if (mc->mc_enm == enm) { 1163 LIST_REMOVE(mc, mc_entries); 1164 free(mc, M_DEVBUF); 1165 break; 1166 } 1167 } 1168 KASSERT(mc != NULL); 1169 } else 1170 (void)ether_addmulti(sa, &ifv->ifv_ec); 1171 return (error); 1172 } 1173 1174 /* 1175 * Delete any multicast address we have asked to add from parent 1176 * interface. Called when the vlan is being unconfigured. 1177 */ 1178 static void 1179 vlan_ether_purgemulti(struct ifvlan *ifv) 1180 { 1181 struct vlan_mc_entry *mc; 1182 struct ifvlan_linkmib *mib; 1183 1184 KASSERT(mutex_owned(&ifv->ifv_lock)); 1185 mib = ifv->ifv_mib; 1186 if (mib == NULL) { 1187 return; 1188 } 1189 1190 while ((mc = LIST_FIRST(&ifv->ifv_mc_listhead)) != NULL) { 1191 (void)if_mcast_op(mib->ifvm_p, SIOCDELMULTI, 1192 (const struct sockaddr *)&mc->mc_addr); 1193 LIST_REMOVE(mc, mc_entries); 1194 free(mc, M_DEVBUF); 1195 } 1196 } 1197 1198 static void 1199 vlan_start(struct ifnet *ifp) 1200 { 1201 struct ifvlan *ifv = ifp->if_softc; 1202 struct ifnet *p; 1203 struct ethercom *ec; 1204 struct mbuf *m; 1205 struct ifvlan_linkmib *mib; 1206 struct psref psref; 1207 int error; 1208 1209 mib = vlan_getref_linkmib(ifv, &psref); 1210 if (mib == NULL) 1211 return; 1212 p = mib->ifvm_p; 1213 ec = (void *)mib->ifvm_p; 1214 1215 ifp->if_flags |= IFF_OACTIVE; 1216 1217 for (;;) { 1218 IFQ_DEQUEUE(&ifp->if_snd, m); 1219 if (m == NULL) 1220 break; 1221 1222 #ifdef ALTQ 1223 /* 1224 * KERNEL_LOCK is required for ALTQ even if NET_MPSAFE is defined. 1225 */ 1226 KERNEL_LOCK(1, NULL); 1227 /* 1228 * If ALTQ is enabled on the parent interface, do 1229 * classification; the queueing discipline might 1230 * not require classification, but might require 1231 * the address family/header pointer in the pktattr. 1232 */ 1233 if (ALTQ_IS_ENABLED(&p->if_snd)) { 1234 switch (p->if_type) { 1235 case IFT_ETHER: 1236 altq_etherclassify(&p->if_snd, m); 1237 break; 1238 #ifdef DIAGNOSTIC 1239 default: 1240 panic("vlan_start: impossible (altq)"); 1241 #endif 1242 } 1243 } 1244 KERNEL_UNLOCK_ONE(NULL); 1245 #endif /* ALTQ */ 1246 1247 bpf_mtap(ifp, m); 1248 /* 1249 * If the parent can insert the tag itself, just mark 1250 * the tag in the mbuf header. 1251 */ 1252 if (ec->ec_capabilities & ETHERCAP_VLAN_HWTAGGING) { 1253 vlan_set_tag(m, mib->ifvm_tag); 1254 } else { 1255 /* 1256 * insert the tag ourselves 1257 */ 1258 M_PREPEND(m, mib->ifvm_encaplen, M_DONTWAIT); 1259 if (m == NULL) { 1260 printf("%s: unable to prepend encap header", 1261 p->if_xname); 1262 ifp->if_oerrors++; 1263 continue; 1264 } 1265 1266 switch (p->if_type) { 1267 case IFT_ETHER: 1268 { 1269 struct ether_vlan_header *evl; 1270 1271 if (m->m_len < sizeof(struct ether_vlan_header)) 1272 m = m_pullup(m, 1273 sizeof(struct ether_vlan_header)); 1274 if (m == NULL) { 1275 printf("%s: unable to pullup encap " 1276 "header", p->if_xname); 1277 ifp->if_oerrors++; 1278 continue; 1279 } 1280 1281 /* 1282 * Transform the Ethernet header into an 1283 * Ethernet header with 802.1Q encapsulation. 1284 */ 1285 memmove(mtod(m, void *), 1286 mtod(m, char *) + mib->ifvm_encaplen, 1287 sizeof(struct ether_header)); 1288 evl = mtod(m, struct ether_vlan_header *); 1289 evl->evl_proto = evl->evl_encap_proto; 1290 evl->evl_encap_proto = htons(ETHERTYPE_VLAN); 1291 evl->evl_tag = htons(mib->ifvm_tag); 1292 1293 /* 1294 * To cater for VLAN-aware layer 2 ethernet 1295 * switches which may need to strip the tag 1296 * before forwarding the packet, make sure 1297 * the packet+tag is at least 68 bytes long. 1298 * This is necessary because our parent will 1299 * only pad to 64 bytes (ETHER_MIN_LEN) and 1300 * some switches will not pad by themselves 1301 * after deleting a tag. 1302 */ 1303 if (m->m_pkthdr.len < 1304 (ETHER_MIN_LEN - ETHER_CRC_LEN + 1305 ETHER_VLAN_ENCAP_LEN)) { 1306 m_copyback(m, m->m_pkthdr.len, 1307 (ETHER_MIN_LEN - ETHER_CRC_LEN + 1308 ETHER_VLAN_ENCAP_LEN) - 1309 m->m_pkthdr.len, 1310 vlan_zero_pad_buff); 1311 } 1312 break; 1313 } 1314 1315 #ifdef DIAGNOSTIC 1316 default: 1317 panic("vlan_start: impossible"); 1318 #endif 1319 } 1320 } 1321 1322 if ((p->if_flags & IFF_RUNNING) == 0) { 1323 m_freem(m); 1324 continue; 1325 } 1326 1327 error = if_transmit_lock(p, m); 1328 if (error) { 1329 /* mbuf is already freed */ 1330 ifp->if_oerrors++; 1331 continue; 1332 } 1333 ifp->if_opackets++; 1334 } 1335 1336 ifp->if_flags &= ~IFF_OACTIVE; 1337 1338 /* Remove reference to mib before release */ 1339 p = NULL; 1340 ec = NULL; 1341 1342 vlan_putref_linkmib(mib, &psref); 1343 } 1344 1345 static int 1346 vlan_transmit(struct ifnet *ifp, struct mbuf *m) 1347 { 1348 struct ifvlan *ifv = ifp->if_softc; 1349 struct ifnet *p; 1350 struct ethercom *ec; 1351 struct ifvlan_linkmib *mib; 1352 struct psref psref; 1353 int error; 1354 size_t pktlen = m->m_pkthdr.len; 1355 bool mcast = (m->m_flags & M_MCAST) != 0; 1356 1357 mib = vlan_getref_linkmib(ifv, &psref); 1358 if (mib == NULL) { 1359 m_freem(m); 1360 return ENETDOWN; 1361 } 1362 1363 p = mib->ifvm_p; 1364 ec = (void *)mib->ifvm_p; 1365 1366 bpf_mtap(ifp, m); 1367 /* 1368 * If the parent can insert the tag itself, just mark 1369 * the tag in the mbuf header. 1370 */ 1371 if (ec->ec_capabilities & ETHERCAP_VLAN_HWTAGGING) { 1372 vlan_set_tag(m, mib->ifvm_tag); 1373 } else { 1374 /* 1375 * insert the tag ourselves 1376 */ 1377 M_PREPEND(m, mib->ifvm_encaplen, M_DONTWAIT); 1378 if (m == NULL) { 1379 printf("%s: unable to prepend encap header", 1380 p->if_xname); 1381 ifp->if_oerrors++; 1382 error = ENOBUFS; 1383 goto out; 1384 } 1385 1386 switch (p->if_type) { 1387 case IFT_ETHER: 1388 { 1389 struct ether_vlan_header *evl; 1390 1391 if (m->m_len < sizeof(struct ether_vlan_header)) 1392 m = m_pullup(m, 1393 sizeof(struct ether_vlan_header)); 1394 if (m == NULL) { 1395 printf("%s: unable to pullup encap " 1396 "header", p->if_xname); 1397 ifp->if_oerrors++; 1398 error = ENOBUFS; 1399 goto out; 1400 } 1401 1402 /* 1403 * Transform the Ethernet header into an 1404 * Ethernet header with 802.1Q encapsulation. 1405 */ 1406 memmove(mtod(m, void *), 1407 mtod(m, char *) + mib->ifvm_encaplen, 1408 sizeof(struct ether_header)); 1409 evl = mtod(m, struct ether_vlan_header *); 1410 evl->evl_proto = evl->evl_encap_proto; 1411 evl->evl_encap_proto = htons(ETHERTYPE_VLAN); 1412 evl->evl_tag = htons(mib->ifvm_tag); 1413 1414 /* 1415 * To cater for VLAN-aware layer 2 ethernet 1416 * switches which may need to strip the tag 1417 * before forwarding the packet, make sure 1418 * the packet+tag is at least 68 bytes long. 1419 * This is necessary because our parent will 1420 * only pad to 64 bytes (ETHER_MIN_LEN) and 1421 * some switches will not pad by themselves 1422 * after deleting a tag. 1423 */ 1424 if (m->m_pkthdr.len < 1425 (ETHER_MIN_LEN - ETHER_CRC_LEN + 1426 ETHER_VLAN_ENCAP_LEN)) { 1427 m_copyback(m, m->m_pkthdr.len, 1428 (ETHER_MIN_LEN - ETHER_CRC_LEN + 1429 ETHER_VLAN_ENCAP_LEN) - 1430 m->m_pkthdr.len, 1431 vlan_zero_pad_buff); 1432 } 1433 break; 1434 } 1435 1436 #ifdef DIAGNOSTIC 1437 default: 1438 panic("vlan_transmit: impossible"); 1439 #endif 1440 } 1441 } 1442 1443 if ((p->if_flags & IFF_RUNNING) == 0) { 1444 m_freem(m); 1445 error = ENETDOWN; 1446 goto out; 1447 } 1448 1449 error = if_transmit_lock(p, m); 1450 if (error) { 1451 /* mbuf is already freed */ 1452 ifp->if_oerrors++; 1453 } else { 1454 1455 ifp->if_opackets++; 1456 ifp->if_obytes += pktlen; 1457 if (mcast) 1458 ifp->if_omcasts++; 1459 } 1460 1461 out: 1462 /* Remove reference to mib before release */ 1463 p = NULL; 1464 ec = NULL; 1465 1466 vlan_putref_linkmib(mib, &psref); 1467 return error; 1468 } 1469 1470 /* 1471 * Given an Ethernet frame, find a valid vlan interface corresponding to the 1472 * given source interface and tag, then run the real packet through the 1473 * parent's input routine. 1474 */ 1475 void 1476 vlan_input(struct ifnet *ifp, struct mbuf *m) 1477 { 1478 struct ifvlan *ifv; 1479 u_int tag; 1480 struct ifvlan_linkmib *mib; 1481 struct psref psref; 1482 bool have_vtag; 1483 1484 have_vtag = vlan_has_tag(m); 1485 if (have_vtag) { 1486 tag = EVL_VLANOFTAG(vlan_get_tag(m)); 1487 m->m_flags &= ~M_VLANTAG; 1488 } else { 1489 switch (ifp->if_type) { 1490 case IFT_ETHER: 1491 { 1492 struct ether_vlan_header *evl; 1493 1494 if (m->m_len < sizeof(struct ether_vlan_header) && 1495 (m = m_pullup(m, 1496 sizeof(struct ether_vlan_header))) == NULL) { 1497 printf("%s: no memory for VLAN header, " 1498 "dropping packet.\n", ifp->if_xname); 1499 return; 1500 } 1501 evl = mtod(m, struct ether_vlan_header *); 1502 KASSERT(ntohs(evl->evl_encap_proto) == ETHERTYPE_VLAN); 1503 1504 tag = EVL_VLANOFTAG(ntohs(evl->evl_tag)); 1505 1506 /* 1507 * Restore the original ethertype. We'll remove 1508 * the encapsulation after we've found the vlan 1509 * interface corresponding to the tag. 1510 */ 1511 evl->evl_encap_proto = evl->evl_proto; 1512 break; 1513 } 1514 1515 default: 1516 tag = (u_int) -1; /* XXX GCC */ 1517 #ifdef DIAGNOSTIC 1518 panic("vlan_input: impossible"); 1519 #endif 1520 } 1521 } 1522 1523 mib = vlan_lookup_tag_psref(ifp, tag, &psref); 1524 if (mib == NULL) { 1525 m_freem(m); 1526 ifp->if_noproto++; 1527 return; 1528 } 1529 1530 ifv = mib->ifvm_ifvlan; 1531 if ((ifv->ifv_if.if_flags & (IFF_UP|IFF_RUNNING)) != 1532 (IFF_UP|IFF_RUNNING)) { 1533 m_freem(m); 1534 ifp->if_noproto++; 1535 goto out; 1536 } 1537 1538 /* 1539 * Now, remove the encapsulation header. The original 1540 * header has already been fixed up above. 1541 */ 1542 if (!have_vtag) { 1543 memmove(mtod(m, char *) + mib->ifvm_encaplen, 1544 mtod(m, void *), sizeof(struct ether_header)); 1545 m_adj(m, mib->ifvm_encaplen); 1546 } 1547 1548 m_set_rcvif(m, &ifv->ifv_if); 1549 ifv->ifv_if.if_ipackets++; 1550 1551 m->m_flags &= ~M_PROMISC; 1552 if_input(&ifv->ifv_if, m); 1553 out: 1554 vlan_putref_linkmib(mib, &psref); 1555 } 1556 1557 /* 1558 * Module infrastructure 1559 */ 1560 #include "if_module.h" 1561 1562 IF_MODULE(MODULE_CLASS_DRIVER, vlan, "") 1563