Tc u32 — how to match L2 protocols in recent kernels

linux-kernellinux-networkingtctraffic-shapingvlan

I have a nice shaper, with hashed filtering, built at a linux bridge. In short, br0 connects external and internal physical interfaces, VLAN tagged packets are bridged "transparently" (I mean, no VLAN interfaces are there).

Now, different kernels do it differently. I can be wrong with exact kernel verions ranges, please forgive me. Thanks.

2.6.26

So, in debian, 2.6.26 and up (up to 2.6.32, I believe) — this works:

tc filter add dev internal protocol 802.1q parent 1:0 prio 100 \
    u32 ht 1:64 match ip dst 192.168.1.100 flowid 1:200

Here, "kernel" matches two bytes in "protocol" field with 0x8100, but counts the beginning of ip packet as a "zero position" (sorry for my English, if I'm a bit unclear).

2.6.32

Again, in debian (I've not built vanilla kernel), 2.6.32-5 — this works:

tc filter add dev internal protocol 802.1q parent 1:0 prio 100 \
    u32 ht 1:64 match ip dst 192.168.1.100 at 20 flowid 1:200

Here, "kernel" matches the same for protocol, but counts offset from the beginning of this protocol's header — I have to add 4 bytes to offset (20, not 16 for dst address). It's ok, seems more logical, as for me.

3.2.11, the latest stable now

This works — as if there is no 802.1q tag at all:

tc filter add dev internal protocol ip parent 1:0 prio 100 \
    u32 ht 1:64 match ip dst 192.168.1.100 flowid 1:200

The problem is that I couldn't find a way to match 802.1q tag so far.

Matching 802.1q tag at past

I could do this before as follows:

tc filter add dev internal protocol 802.1q parent 1:0 prio 100 \
    u32 match u16 0x0ed8 0x0fff at -4 flowid 1:300

Now I'm unable to match 802.1q tag with at 0, at -2, at -4, at -6 or like that. The main issue that I have zero hits count — this filter is not being checked at all, "wrong protocol", in other words.

Please, anyone, help me 🙂

Thanks!

Best Answer

VLAN tag is stripped from skb in recent kernels. Try something like this to do a meta match in skb:

tc filter add dev internal protocol all parent 1:0 prio 100 basic match 'meta(vlan mask 0xfff eq 0x0ed8)' flowid 1:300