我正在开发一些网络驱动程序,我正在尝试根据ip :: tos值将数据包分配到不同的队列。出于测试目的,我正在运行:
ping -Q 1 10.0.0.2
将ip :: tos值设置为1.我遇到的问题是在我运行ping命令的系统上 - 传出skb有skb-> priority == 0,但我认为它应该是1。
我认为设置“-Q 1”会将skb->优先级设置为1,但事实并非如此。
任何人都知道为什么?
答案 0 :(得分:4)
首先,skb->优先级和IP TOS字段之间没有直接映射。它在linux内核中完成:
sk->sk_priority = rt_tos2priority(val)
...
static inline char rt_tos2priority(u8 tos)
{
return ip_tos2prio[IPTOS_TOS(tos)>>1];
}
(ip_tos2prio表可以在ipv4 / route.c中找到)。
在我看来,你必须将“TOS”字节设置为至少32以获得除0以外的任何其他任何内容的skb->优先级。
ping -Q 1将整个TOS字节设置为1.请注意,不推荐使用TOS而使用DSCP。 2个低位用于ECN,而高6位用于DSCP值(“优先级”)。
所以你可能必须从4开始,才能获得DSCP优先级1,但是根据上表,从32开始获得skb->优先级设置,如ping -Q 32 10.0.0.2
但是,我不确定在所有情况下都会设置skb->优先级。如果ping
工具使用原始套接字处理数据包,则可能会绕过设置skb->优先级。
然而,如果例如一个,则设置本地生成的分组的skb->优先级。
int tos = 32;
setsockopt(sock_fd, IPPROTO_IP, IP_TOS,
&tos, sizeof(tos));
所以你可能需要在发送数据包之前做一个小样本程序来完成上述工作。
答案 1 :(得分:1)
上面的答案是对的,让我们在这里完成
INSERT INTO symbols (test_chars) VALUES ('''')
其中IPTOS_TOS是一个宏,其ANDs“tos”值为0x1E
因此,如果您将TOS设为0xFF,则上述return语句将减少为
static inline char rt_tos2priority(u8 tos)
{
return ip_tos2prio[IPTOS_TOS(tos)>>1];
}
进一步计算,(0x1E& 0xFF)等于0x1E, 和(0x1E>> 1)给出0x0F,十进制为15。 我们可以说上面的return语句等于
return ip_tos2prio[(0x1E & 0xFF)>>1];
现在“ip_tos2prio”是一个预定义的数组,就像这个
return ip_tos2prio[15];
其中每个不同的值具有含义,0-> BESTEFFORT,2-> BULK,4->交互式大块,6->交互。
返回return语句,返回 ip_tos2prio 数组中的第15个元素,即4。