aboutsummaryrefslogtreecommitdiffstats
path: root/net/8021q/vlan.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@g5.osdl.org>2006-03-21 12:31:48 -0500
committerLinus Torvalds <torvalds@g5.osdl.org>2006-03-21 12:31:48 -0500
commit3d1f337b3e7378923c89f37afb573a918ef40be5 (patch)
tree386798378567a10d1c7b24f599cb50f70298694c /net/8021q/vlan.c
parent2bf2154c6bb5599e3ec3f73c34861a0b12aa839e (diff)
parent5e35941d990123f155b02d5663e51a24f816b6f3 (diff)
Merge master.kernel.org:/pub/scm/linux/kernel/git/davem/net-2.6
* master.kernel.org:/pub/scm/linux/kernel/git/davem/net-2.6: (235 commits) [NETFILTER]: Add H.323 conntrack/NAT helper [TG3]: Don't mark tg3_test_registers() as returning const. [IPV6]: Cleanups for net/ipv6/addrconf.c (kzalloc, early exit) v2 [IPV6]: Nearly complete kzalloc cleanup for net/ipv6 [IPV6]: Cleanup of net/ipv6/reassambly.c [BRIDGE]: Remove duplicate const from is_link_local() argument type. [DECNET]: net/decnet/dn_route.c: fix inconsequent NULL checking [TG3]: make drivers/net/tg3.c:tg3_request_irq() static [BRIDGE]: use LLC to send STP [LLC]: llc_mac_hdr_init const arguments [BRIDGE]: allow show/store of group multicast address [BRIDGE]: use llc for receiving STP packets [BRIDGE]: stp timer to jiffies cleanup [BRIDGE]: forwarding remove unneeded preempt and bh diasables [BRIDGE]: netfilter inline cleanup [BRIDGE]: netfilter VLAN macro cleanup [BRIDGE]: netfilter dont use __constant_htons [BRIDGE]: netfilter whitespace [BRIDGE]: optimize frame pass up [BRIDGE]: use kzalloc ...
Diffstat (limited to 'net/8021q/vlan.c')
-rw-r--r--net/8021q/vlan.c43
1 files changed, 27 insertions, 16 deletions
diff --git a/net/8021q/vlan.c b/net/8021q/vlan.c
index fa76220708ce..3948949a609a 100644
--- a/net/8021q/vlan.c
+++ b/net/8021q/vlan.c
@@ -69,7 +69,7 @@ static struct packet_type vlan_packet_type = {
69 69
70/* Bits of netdev state that are propagated from real device to virtual */ 70/* Bits of netdev state that are propagated from real device to virtual */
71#define VLAN_LINK_STATE_MASK \ 71#define VLAN_LINK_STATE_MASK \
72 ((1<<__LINK_STATE_PRESENT)|(1<<__LINK_STATE_NOCARRIER)) 72 ((1<<__LINK_STATE_PRESENT)|(1<<__LINK_STATE_NOCARRIER)|(1<<__LINK_STATE_DORMANT))
73 73
74/* End of global variables definitions. */ 74/* End of global variables definitions. */
75 75
@@ -344,6 +344,26 @@ static void vlan_setup(struct net_device *new_dev)
344 new_dev->do_ioctl = vlan_dev_ioctl; 344 new_dev->do_ioctl = vlan_dev_ioctl;
345} 345}
346 346
347static void vlan_transfer_operstate(const struct net_device *dev, struct net_device *vlandev)
348{
349 /* Have to respect userspace enforced dormant state
350 * of real device, also must allow supplicant running
351 * on VLAN device
352 */
353 if (dev->operstate == IF_OPER_DORMANT)
354 netif_dormant_on(vlandev);
355 else
356 netif_dormant_off(vlandev);
357
358 if (netif_carrier_ok(dev)) {
359 if (!netif_carrier_ok(vlandev))
360 netif_carrier_on(vlandev);
361 } else {
362 if (netif_carrier_ok(vlandev))
363 netif_carrier_off(vlandev);
364 }
365}
366
347/* Attach a VLAN device to a mac address (ie Ethernet Card). 367/* Attach a VLAN device to a mac address (ie Ethernet Card).
348 * Returns the device that was created, or NULL if there was 368 * Returns the device that was created, or NULL if there was
349 * an error of some kind. 369 * an error of some kind.
@@ -450,7 +470,7 @@ static struct net_device *register_vlan_device(const char *eth_IF_name,
450 new_dev->flags = real_dev->flags; 470 new_dev->flags = real_dev->flags;
451 new_dev->flags &= ~IFF_UP; 471 new_dev->flags &= ~IFF_UP;
452 472
453 new_dev->state = real_dev->state & VLAN_LINK_STATE_MASK; 473 new_dev->state = real_dev->state & ~(1<<__LINK_STATE_START);
454 474
455 /* need 4 bytes for extra VLAN header info, 475 /* need 4 bytes for extra VLAN header info,
456 * hope the underlying device can handle it. 476 * hope the underlying device can handle it.
@@ -498,6 +518,10 @@ static struct net_device *register_vlan_device(const char *eth_IF_name,
498 if (register_netdevice(new_dev)) 518 if (register_netdevice(new_dev))
499 goto out_free_newdev; 519 goto out_free_newdev;
500 520
521 new_dev->iflink = real_dev->ifindex;
522 vlan_transfer_operstate(real_dev, new_dev);
523 linkwatch_fire_event(new_dev); /* _MUST_ call rfc2863_policy() */
524
501 /* So, got the sucker initialized, now lets place 525 /* So, got the sucker initialized, now lets place
502 * it into our local structure. 526 * it into our local structure.
503 */ 527 */
@@ -573,25 +597,12 @@ static int vlan_device_event(struct notifier_block *unused, unsigned long event,
573 switch (event) { 597 switch (event) {
574 case NETDEV_CHANGE: 598 case NETDEV_CHANGE:
575 /* Propagate real device state to vlan devices */ 599 /* Propagate real device state to vlan devices */
576 flgs = dev->state & VLAN_LINK_STATE_MASK;
577 for (i = 0; i < VLAN_GROUP_ARRAY_LEN; i++) { 600 for (i = 0; i < VLAN_GROUP_ARRAY_LEN; i++) {
578 vlandev = grp->vlan_devices[i]; 601 vlandev = grp->vlan_devices[i];
579 if (!vlandev) 602 if (!vlandev)
580 continue; 603 continue;
581 604
582 if (netif_carrier_ok(dev)) { 605 vlan_transfer_operstate(dev, vlandev);
583 if (!netif_carrier_ok(vlandev))
584 netif_carrier_on(vlandev);
585 } else {
586 if (netif_carrier_ok(vlandev))
587 netif_carrier_off(vlandev);
588 }
589
590 if ((vlandev->state & VLAN_LINK_STATE_MASK) != flgs) {
591 vlandev->state = (vlandev->state &~ VLAN_LINK_STATE_MASK)
592 | flgs;
593 netdev_state_change(vlandev);
594 }
595 } 606 }
596 break; 607 break;
597 608