• Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 657
  • Last Modified:

Does IMQ with qdisc support the TOS field?

Hi all,

Can anyone tell me please why the below doesn't work? With the below
iptables rule i'd expect all traffic coming in on BR1 interface to get
it's TOS field updated and then with the default 3 band PRIO qdisc
applied to the IMQ root.. all traffic now marked as
Maximize-Throughput would get placed into the 3rd PRIO band. When i
run the below, all traffic ends up in band 2 which is just the default?

Am i doing anything wrong? Is this even possible ?

tc qdisc del dev imq0 root
tc qdisc add dev imq0 root handle 1: prio
tc qdisc add dev imq0 parent 1:1 handle 10: bfifo
tc qdisc add dev imq0 parent 1:2 handle 20: bfifo
tc qdisc add dev imq0 parent 1:3 handle 30: bfifo

iptables -t mangle -F
iptables -t mangle -A PREROUTING -i br1 -p ALL -j TOS --set-tos
Maximize-Throughput
iptables -t mangle -A PREROUTING -i br1 -j IMQ --todev 0

iptables -t mangle -L -v -n
tc qdisc show dev imq0


tc -s qdisc show dev imq0

qdisc prio 1: bands 3 priomap  1 2 2 2 1 2 0 0 1 1 1 1 1 1 1 1
 Sent 4800 bytes 80 pkts (dropped 0, overlimits 0)
qdisc bfifo 10: parent 1:1 limit 45000b
 Sent 0 bytes 0 pkts (dropped 0, overlimits 0)
qdisc bfifo 20: parent 1:2 limit 45000b
 Sent 4800 bytes 80 pkts (dropped 0, overlimits 0)
qdisc bfifo 30: parent 1:3 limit 45000b
 Sent 0 bytes 0 pkts (dropped 0, overlimits 0)

Many thanks!
flo
0
fourlightson
Asked:
fourlightson
  • 5
  • 4
1 Solution
 
NopiusCommented:
Hi again.

> all traffic now marked as Maximize-Throughput would get placed into the 3rd PRIO band. When i run the below, all traffic ends up in band 2 which is just the default?

Max throughput is mapped to band 2 by default, that's correct:
http://www.opalsoft.net/qos/DS-23.htm
http://www.opalsoft.net/qos/ds-lb-232-1.gif

In your case priomap is '1 2 2 2 1 2 0 0 1 1 1 1 1 1 1 1'  (priomap is 0-based while your queue numbers are 1-based, so add 1 to map priomap to queue number) in max-throughput is 0x08, and this bit corresponds to it: 1 2 2 2 1 2 0 0 1 1 1 1 1 1 1 1, so it is queued to the 2nd queue.
You may either use tc filter (as I said in previous post) or change priomap (while creating priomap), like this:
tc qdisc add dev imq0 root handle 1:0 prio priomap 1 2 2 2 1 2 0 0 1 1 1 1 2 1 1 1


0
 
fourlightsonAuthor Commented:
ok many thanks for replying again.

The reason why i thought that my qdisc rules should make the traffic go into band 3 or in other words queue "qdisc bfifo 30: parent 1:3 limit 45000b"  is based on what i read at http://linux.die.net/man/8/tc-prio 

Like you said, the priomap is 0 based so with Maximize Throughput being band 2 bulk traffic, according to the man page, it should have went into the bfifo queue 3 in the prio qdisc.

But instead it's going into the bfifo queue 2 in the prio qdisc.

So to confirm, i'm using iptables -t mangle -A PREROUTING -i br1 -p ALL -j TOS --set-tos
Maximize-Throughput
to mark all traffic as Maximize Throughput which should be bulk traffic and allocated to the 0-based band 2 which should be qdisc prio queue 3 because it's 1-based. But instead it's going into queue 2.

Am i making some silly mistake here ? I based on the above, i still think my traffic is going into the wrong queue.

thanks again for helping.

0
 
NopiusCommented:
> he priomap is 0 based so with Maximize Throughput being band 2 bulk traffic, according to the man page, it should have went into the bfifo queue 3 in the prio qdisc.

This manpage is not 100% correct. The table is manpage corresponds to another (non default) priomap, while the further example is about default priomap, that's confusing.

"The last column shows the result of the default priomap. On the commandline, the default priomap looks like this:
1, 2, 2, 2, 1, 2, 0, 0 , 1, 1, 1, 1, 1, 1, 1, 1
This means that priority 4, for example, gets mapped to band number 1. "

But their table is for priomap 1 1 1 1 0 0 0 0 2 2 2 2 1 1 2 1
'1 2 2 2 1 2 0 0 1 1 1 1 1 1 1 1
If you want do direct all traffic to band 3, you have 3 choices:

- either change your priomap, so that Maximize-Throughput (0x8) will go to band 3:
tc qdisc add dev imq0 root handle 1:0 prio priomap 1 2 2 2 1 2 0 0 1 1 1 1 2 1 1 1

- or change iptables, so that your traffic would be marked with TOS, that goes to band 3 by default:
iptables -t mangle -A PREROUTING -i br1 -p ALL -j TOS --set-tos 0x1a

- or change qdisc filter, so that your 'max-throughput' would go to queue 2 regardless of priomap:
tc filter add dev imq0 parent 1:0 protocol ip prio 10 u32 match ip tos 0x08 0xff  flowid  1:3

All three approaches should work. Linux is networking very flexible.
And don't believe man page, or even experts on EE, test everything! I do such tests before posting here :-)
0
Cloud Class® Course: Microsoft Windows 7 Basic

This introductory course to Windows 7 environment will teach you about working with the Windows operating system. You will learn about basic functions including start menu; the desktop; managing files, folders, and libraries.

 
fourlightsonAuthor Commented:
hi many thanks, that helps a lot.

There is one thing that i don't understand.

In your example you say:

But their table is for priomap 1 1 1 1 0 0 0 0 2 2 2 2 1 1 2 1

I just assumed that when reading the table on http://linux.die.net/man/8/tc-prio that in the same way i read the table from top->down that i'd read the priomap left->right. But based on your example above i should be reading the priomap right->left. Is that correct? or is it just the way you typed it in?

I don't know why but, from that man page again due to 'Maximize Throughput' being 5th down in the table i'd have just changed the 5th priomap value in from the left to be 2.. but you changed the 4th value from the right to be 2?

So i'd have changed it to look like below.

so that Maximize-Throughput (0x8) will go to band 3:
tc qdisc add dev imq0 root handle 1:0 prio priomap 1 2 2 2 2 2 0 0 1 1 1 1 2 1 1 1

I understand what you mean with my priomap and the man page priomap, i see how in my logic 'Maximize Throughput' is 5th down so 5th in from left which in my priomap is 1 which equals band 2 hence why the traffic was going into the wrong band form what i expected. But i don't understand how to came to the new values in you first example to fix it ' either change your priomap, so that Maximize-Throughput (0x8) will go to band 3:'

maybe i'm just missing something really obvious and stupid here ?

thanks again

0
 
NopiusCommented:
> based on your example above i should be reading the priomap right->left. Is that correct?
Yes.
bit are numbered from right to left

> i'd have just changed the 5th priomap value in from the left to be 2.. but you changed the 4th value from the right to be 2?

Max throuthput is coded as 0x8, that is '1000' in binary, that means you should change 4th bit from right hand.
0
 
fourlightsonAuthor Commented:
ok thanks.

I'm close to giving up because the more i try to figure out prio qdisc the less i understand from the doc's online.

I've just create a custom prio qdisc with the below priomap and for some reason all traffic with tos 0x10 is going into band 3. Can you explain that ?

qdisc prio 1: root bands 3 priomap  1 0 0 0 0 0 2 0 0 0 0 0 0 0 0 0

Based on what you've said before and the man pages, that makes no sense. what so ever.

thanks once more.
0
 
NopiusCommented:
First, my appologies, priomap doesnt' correspond to TOS field directly:

"The kernel assigns each packet a TC_PRIO priority, based on TOS flags or socket options passed by the application".

The same notes are in 'tc' manual:
"Type of Service
              Some qdiscs have built in rules for classifying packets based on
              the TOS field.

       skb->priority
              Userspace  programs can encode a class-id in the skb->priority
              field using the SO_PRIORITY option
"
How exactly kernel assigns a packet TC_PRIO, only kernel knows. SO you can't be sure that TOS 0x8 will always be mapped to the same TC_PRIO bit.
BTW. In my case with 'qdisc prio 1: root bands 3 priomap  1 0 0 0 0 0 2 0 0 0 0 0 0 0 0 0' everything goes to band 2, not 3 and only first '1' matches all traffic, everything else is ignored.

Next, I found a problem very similar to your's (theys say it's a kernel bug):
https://lists.linux-foundation.org/pipermail/bugme-new/2007-August/016676.html
Probably that's not a bug, just changed mapping rules to TC_PRIO inside the kernel.

Also I found an interesting mail arvchive of kernel developers, they discuss priomap there:
http://www.mail-archive.com/netdev@vger.kernel.org/msg05770.html
After reading it (the entire thread) you should understand why you should _never_ rely on priomap :-)

So from all possible choices with 'prio' qdisc only one left:
-  change qdisc filter, so that your 'max-throughput' would go to queue 2 regardless of priomap:
this works, test it.
say If you have:
tc qdisc del dev imq0 root
tc qdisc add dev imq0 root handle 1: prio
tc qdisc add dev imq0 parent 1:1 handle 10: bfifo
tc qdisc add dev imq0 parent 1:2 handle 20: bfifo
tc qdisc add dev imq0 parent 1:3 handle 30: bfifo
iptables -t mangle -F
iptables -t mangle -A PREROUTING -i imq0 -p ICMP -j TOS --set-tos 0x8
iptables -t mangle -A PREROUTING -i imq0 -p TCP -j TOS --set-tos 0x10

and want to map 0x8 TOS (max throughput) to band 3 and map 0x10 (mimimize delay) to band 1
these tc filters are mandatory:
tc filter add dev imq0 parent 1:0 prio 1 protocol ip u32 match ip tos 0x8 0xff flowid 1:3
tc filter add dev imq0 parent 1:0 prio 2 protocol ip u32 match ip tos 0x10 0xff flowid 1:1

here 'prio 1' and 'prio 2' is the number of filter rule inside 'dev imq1', so they may be checked in an order, the first match hit classifies a packet. Deciphering 'tc filter' is left to you.
Here is how it works:
qdisc prio 1: bands 3 priomap  2 2 2 2 0 0 0 0 0 2 2 2 2 2 2 2
 Sent 850 bytes 12 pkt (dropped 0, overlimits 0 requeues 0)
 rate 0bit 0pps backlog 0b 0p requeues 0
qdisc bfifo 11: parent 1:1 limit 1500000b
 Sent 206 bytes 3 pkt (dropped 0, overlimits 0 requeues 0)
 rate 0bit 0pps backlog 0b 0p requeues 0
qdisc bfifo 12: parent 1:2 limit 1500000b
 Sent 0 bytes 0 pkt (dropped 0, overlimits 0 requeues 0)
 rate 0bit 0pps backlog 0b 0p requeues 0
qdisc bfifo 13: parent 1:3 limit 1500000b
 Sent 644 bytes 9 pkt (dropped 0, overlimits 0 requeues 0)
 rate 0bit 0pps backlog 0b 0p requeues 0
0
 
fourlightsonAuthor Commented:
excellent, much appreciated. Some interesting reading on those links.

I'll add the filters and be done with it. It's not a big deal adding the filters and i know that solution works. I was just trying to get the prio qdisc working as i understood it should work from the various man pages and postings. But i guess they are old and various things have changed over time. Shame, it would have been quite a nice elegant solution.

thanks again for the help.
0
 
NopiusCommented:
Thank you for points.

Really 'priomap' is not so elegant solution.
TOS field is a bitset, so what to do with a packet, that has BOTH bits set 'max-throughput' and 'min-delay'? This is only one example. What if we have 3 or 4 or 5 bits set? How to classify such packets with multiple TOS fields? There is no obvious way to decide what is a packet priority 'by default' for such cases.
I guess user-defined filters is the only way to make the configuration manageable and clear for understanding.
0
Question has a verified solution.

Are you are experiencing a similar issue? Get a personalized answer when you ask a related question.

Have a better answer? Share it in a comment.

Join & Write a Comment

Featured Post

Free Tool: Subnet Calculator

The subnet calculator helps you design networks by taking an IP address and network mask and returning information such as network, broadcast address, and host range.

One of a set of tools we're offering as a way of saying thank you for being a part of the community.

  • 5
  • 4
Tackle projects and never again get stuck behind a technical roadblock.
Join Now