diff mbox

vlan: allow VLAN ID 0 to be used

Message ID 4AE5CAC6.4000604@gmail.com
State Changes Requested, archived
Delegated to: David Miller
Headers show

Commit Message

Eric Dumazet Oct. 26, 2009, 4:13 p.m. UTC
Eric Dumazet a écrit :
> VLAN id 0 is not usable on current kernel because we use 16 bits in skb to
>  store vlan_tci, and vlan_tci = 0 means there is no VLAN tagging.
> 
> 
> We could use high order bit (0x8000) to tell if vlan tagging is set or not.
> 

Here is the patch I cooked that permitted VLAN 0 to be used with tg3
(and other HW accelerated vlan nics I suppose)

[PATCH] vlan: allow VLAN ID 0 to be used

We currently use a 16 bit field (vlan_tci) to store VLAN ID on a skb.

0 value is used a special value, meaning VLAN ID not set.
This forbids use of VLAN ID 0

As VLAN ID is 12 bits, we can use high order bit as a flag, and
allow VLAN ID 0

Reported-by: Gertjan Hofman <gertjan_hofman@yahoo.com>
Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com>
---
--
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Comments

David Miller Oct. 27, 2009, 12:32 a.m. UTC | #1
From: Eric Dumazet <eric.dumazet@gmail.com>
Date: Mon, 26 Oct 2009 17:13:58 +0100

> [PATCH] vlan: allow VLAN ID 0 to be used
> 
> We currently use a 16 bit field (vlan_tci) to store VLAN ID on a skb.
> 
> 0 value is used a special value, meaning VLAN ID not set.
> This forbids use of VLAN ID 0
> 
> As VLAN ID is 12 bits, we can use high order bit as a flag, and
> allow VLAN ID 0
> 
> Reported-by: Gertjan Hofman <gertjan_hofman@yahoo.com>
> Signed-off-by: Eric Dumazet <eric.dumazet@gmail.com>

This is going to need some more work.

IXGBE is already using the higher bits of ->vlan_tci internally,
your change breaks that.

QLGE explicitly initializes skb->vlan_tci to zero, you'll need to make
sure that's OK.

There is an explicit "if (skb->vlan_tci" (ie. zero vs. non-zero) test
in net/core/dev.c:netif_receive_skb()

net/core/skbuff.c:__copy_skb_header() does a straight copy, you'll
need to make sure that's still OK.

net/packet/af_packet.c:tpacket_rcv() and packet_recvmsg() report the
skb->vlan_tci value to userspace, that's broken now as userspace
doesn't expect that new bit to be there.
--
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Benny Amorsen Oct. 27, 2009, 9:52 a.m. UTC | #2
Eric Dumazet <eric.dumazet@gmail.com> writes:

> Here is the patch I cooked that permitted VLAN 0 to be used with tg3
> (and other HW accelerated vlan nics I suppose)
>
> [PATCH] vlan: allow VLAN ID 0 to be used
>
> We currently use a 16 bit field (vlan_tci) to store VLAN ID on a skb.
>
> 0 value is used a special value, meaning VLAN ID not set.
> This forbids use of VLAN ID 0

Are you sure you actually want to do this?

VLAN 0 IS special. Frames received on VLAN 0 should be treated just as
if they had no VLAN tag at all, except that they have an 802.1p value.

Sending frames with VLAN 0 should have something to do with whether
the sender wants to use 802.1p, which doesn't really have much to do
with VLAN's at all...

It would be nice if the unsuspecting user was at least warned that their
use of VLAN 0 is non-standard and may cause surprising results like
leakage into the "native" VLAN. That could be done in /sbin/ip or
/sbin/vconfig, of course.


/Benny

--
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Eric Dumazet Oct. 27, 2009, 10:02 a.m. UTC | #3
Benny Amorsen a écrit :
> Eric Dumazet <eric.dumazet@gmail.com> writes:
> 
>> Here is the patch I cooked that permitted VLAN 0 to be used with tg3
>> (and other HW accelerated vlan nics I suppose)
>>
>> [PATCH] vlan: allow VLAN ID 0 to be used
>>
>> We currently use a 16 bit field (vlan_tci) to store VLAN ID on a skb.
>>
>> 0 value is used a special value, meaning VLAN ID not set.
>> This forbids use of VLAN ID 0
> 
> Are you sure you actually want to do this?
> 
> VLAN 0 IS special. Frames received on VLAN 0 should be treated just as
> if they had no VLAN tag at all, except that they have an 802.1p value.
> 
> Sending frames with VLAN 0 should have something to do with whether
> the sender wants to use 802.1p, which doesn't really have much to do
> with VLAN's at all...
> 
> It would be nice if the unsuspecting user was at least warned that their
> use of VLAN 0 is non-standard and may cause surprising results like
> leakage into the "native" VLAN. That could be done in /sbin/ip or
> /sbin/vconfig, of course.
> 

Quotting http://en.wikipedia.org/wiki/IEEE_802.1Q

VLAN Identifier (VID): a 12-bit field specifying the VLAN to which the frame belongs.
 A value of 0 means that the frame doesn't belong to any VLAN; in this case the 802.1Q
 tag specifies only a priority and is referred to as a priority tag.
A value of hex FFF is reserved for implementation use.
All other values may be used as VLAN identifiers, allowing up to 4094 VLANs


So we expect to generate a 802.1Q frame, even with a VID=0 field.
Before patch, device sends a non 802.1Q frame, which is not what was wanted by user.
(Maybe he wants to check its device/network is able to transport 1522 bytes frames, who knows...)

To use non tagged frames, user selects eth0 device, and to send tagged frames, he selects eth0.0


Now, maybe eth0 and eth0.0 should share same IP addresses, because incoming frame
with ID=0 tag should be received by eth0 device, but I am not sure standard requires this.

--
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Patrick McHardy Oct. 28, 2009, 4:13 p.m. UTC | #4
Eric Dumazet wrote:
> Benny Amorsen a écrit :
>> Eric Dumazet <eric.dumazet@gmail.com> writes:
>>
>>> Here is the patch I cooked that permitted VLAN 0 to be used with tg3
>>> (and other HW accelerated vlan nics I suppose)
>>>
>>> [PATCH] vlan: allow VLAN ID 0 to be used
>>>
>>> We currently use a 16 bit field (vlan_tci) to store VLAN ID on a skb.
>>>
>>> 0 value is used a special value, meaning VLAN ID not set.
>>> This forbids use of VLAN ID 0
>> Are you sure you actually want to do this?
>>
>> VLAN 0 IS special. Frames received on VLAN 0 should be treated just as
>> if they had no VLAN tag at all, except that they have an 802.1p value.
>>
>> Sending frames with VLAN 0 should have something to do with whether
>> the sender wants to use 802.1p, which doesn't really have much to do
>> with VLAN's at all...
>>
>> It would be nice if the unsuspecting user was at least warned that their
>> use of VLAN 0 is non-standard and may cause surprising results like
>> leakage into the "native" VLAN. That could be done in /sbin/ip or
>> /sbin/vconfig, of course.
>>
> 
> Quotting http://en.wikipedia.org/wiki/IEEE_802.1Q
> 
> VLAN Identifier (VID): a 12-bit field specifying the VLAN to which the frame belongs.
>  A value of 0 means that the frame doesn't belong to any VLAN; in this case the 802.1Q
>  tag specifies only a priority and is referred to as a priority tag.
> A value of hex FFF is reserved for implementation use.
> All other values may be used as VLAN identifiers, allowing up to 4094 VLANs
> 
> 
> So we expect to generate a 802.1Q frame, even with a VID=0 field.
> Before patch, device sends a non 802.1Q frame, which is not what was wanted by user.
> (Maybe he wants to check its device/network is able to transport 1522 bytes frames, who knows...)
> 
> To use non tagged frames, user selects eth0 device, and to send tagged frames, he selects eth0.0

I agree. Quoting IEEE802.1Q:

0 The null VLAN ID. Indicates that the tag header contains only priority
  information; no VLAN identifier is present in the frame. ...

which implies that its valid to use 0 as tag in the header.

> Now, maybe eth0 and eth0.0 should share same IP addresses, because incoming frame
> with ID=0 tag should be received by eth0 device, but I am not sure standard requires this.

I don't think the standard makes any demands regarding this.

The current behaviour seems better to me since its symetrical
to the output path, where the VLAN device is necessary to be
able to specify a priority mapping.


--
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
diff mbox

Patch

diff --git a/include/linux/if_vlan.h b/include/linux/if_vlan.h
index 7ff9af1..7dfcdb5 100644
--- a/include/linux/if_vlan.h
+++ b/include/linux/if_vlan.h
@@ -105,8 +105,9 @@  static inline void vlan_group_set_device(struct vlan_group *vg,
 	array[vlan_id % VLAN_GROUP_ARRAY_PART_LEN] = dev;
 }
 
-#define vlan_tx_tag_present(__skb)	((__skb)->vlan_tci)
-#define vlan_tx_tag_get(__skb)		((__skb)->vlan_tci)
+#define VLAN_TAG_PRESENT		0x8000
+#define vlan_tx_tag_present(__skb)	((__skb)->vlan_tci & VLAN_TAG_PRESENT)
+#define vlan_tx_tag_get(__skb)		((__skb)->vlan_tci & 0x7fff)
 
 #if defined(CONFIG_VLAN_8021Q) || defined(CONFIG_VLAN_8021Q_MODULE)
 extern struct net_device *vlan_dev_real_dev(const struct net_device *dev);
@@ -231,7 +232,7 @@  static inline struct sk_buff *__vlan_put_tag(struct sk_buff *skb, u16 vlan_tci)
 static inline struct sk_buff *__vlan_hwaccel_put_tag(struct sk_buff *skb,
 						     u16 vlan_tci)
 {
-	skb->vlan_tci = vlan_tci;
+	skb->vlan_tci = VLAN_TAG_PRESENT | vlan_tci;
 	return skb;
 }
 
@@ -284,7 +285,7 @@  static inline int __vlan_hwaccel_get_tag(const struct sk_buff *skb,
 					 u16 *vlan_tci)
 {
 	if (vlan_tx_tag_present(skb)) {
-		*vlan_tci = skb->vlan_tci;
+		*vlan_tci = vlan_tx_tag_get(skb);
 		return 0;
 	} else {
 		*vlan_tci = 0;