mengxh3000 发表于 2014-08-12 10:05

调用函数 dev_queue_xmit 问题

本帖最后由 mengxh3000 于 2014-08-12 10:17 编辑

在网桥的 NF_BR_POST_ROUTING 里面 把普通的ETH_P_IP包添加vlan id 变成ETH_P_8021Q的包,调用 dev_queue_xmit 返回0,但是对方并没有收到包。(本机没有配置vlan的虚拟网卡,就是用eth0发送)不知道问题出在哪里 ,代码如下:


static unsigned int brTestHookLocalPostRouting(unsigned int hooknum,
                                        struct sk_buff **skb,
                                        const struct net_device *in,
                                        const struct net_device *out,
                                        int (*okfn)(struct sk_buff *))
{
        int ret = 0;
        struct vlan_ethhdr *veth;
        struct sk_buff *pskb = *skb;

        if (pskb == NULL)
                return NF_DROP;

        //printk("PostRouting ---- \n");

        if (pskb->protocol == __constant_htons(ETH_P_8021Q))
        {
                return NF_ACCEPT;
        }
       
        hexDump(pskb->mac.raw, 60);
        printk("PostRouting ---- PostRouting\n");

             // 本机的mac地址,若是从本机发出的包就打上vlan id 为100的tag
        // 00 e9 24 13 12 49
        unsigned char* p = pskb->mac.raw;
        if (p ==0x00 && p ==0xe9 &&
                p ==0x24 && p ==0x13 &&
                p == 0x12 && p == 0x49)
        {
                printk("PostRouting ---- put tag\n");

                skb_push(pskb, ETH_HLEN);
                struct vlan_ethhdr *veth1;
                if (skb_headroom(pskb) < VLAN_HLEN)
                {
                        struct sk_buff *sk_tmp = pskb;
                        pskb = skb_realloc_headroom(sk_tmp, VLAN_HLEN);
                        kfree_skb(sk_tmp);
                        if (!pskb)
                        {
                                printk("PostRouting ---- vlan: failed to realloc headroom\n");
                                return NF_DROP;
                        }

                        //hexDump(pskb->mac.raw, 60);
                        //printk("PostRouting ---- skb_realloc_headroom \n");
                }
                else
                {
                        pskb = skb_unshare(pskb, GFP_ATOMIC);
                        if (!pskb)
                        {
                                printk("PostRouting ---- vlan: failed to unshare skbuff\n");
                                return NF_DROP;
                        }

                        //hexDump(pskb->mac.raw, 60);
                        //printk("PostRouting ---- skb_unshare \n");
                }

                veth1 = (struct vlan_ethhdr *)skb_push(pskb, VLAN_HLEN);

                //hexDump(pskb->mac.raw, 60);
                //printk("PostRouting ---- skb_push \n");

                /* Move the mac addresses to the beginning of the new header. */
                memmove(pskb->data, pskb->data + VLAN_HLEN, 2 * VLAN_ETH_ALEN);

                //hexDump(pskb->mac.raw, 60);
                //printk("PostRouting ---- memmove \n");

                veth1->h_vlan_proto = __constant_htons(ETH_P_8021Q);
                veth1->h_vlan_TCI = htons(100);

                pskb->protocol = __constant_htons(ETH_P_8021Q);
                pskb->mac.raw -= VLAN_HLEN;
                pskb->nh.raw -= VLAN_HLEN;

                pskb->ip_summed = CHECKSUM_HW;

                hexDump(pskb->mac.raw, 60);

                //pskb = __vlan_put_tag(pskb, 10);
                printk("PostRouting ---- __vlan_put_tag \n");
                if (!pskb)
                {
                        printk("PostRouting ---- __vlan_put_tag failed \n");
                        //stats->tx_dropped++;
                        return NF_DROP;
                }

                printk("PostRouting----- pskb->dev->name = %s\n", pskb->dev->name);
                int rr = dev_queue_xmit(pskb);
                printk("PostRouting ---- dev_queue_xmit = %d\n", rr);
                return NF_STOLEN;
        }
        else
        {
                return NF_ACCEPT;
        }

        return NF_ACCEPT;
}

humjb_1983 发表于 2014-08-12 13:46

对端做vlan相关配置了么?

mengxh3000 发表于 2014-08-12 14:11

这台机器放在trunk链路上,通过本机的包都正常转发走了,就是本机发出的包打上vlan id

Tinnal 发表于 2014-08-12 15:23

楼主很执着的去改变标准的东西。你要非这么做,就你这个情况。可以在trunk链路上接个网络分析议(可以由电脑去左代替),看看发出来的包有什么不对,再有针对的去处理。

mengxh3000 发表于 2014-08-12 16:05

因为这个放到trunk链路上因为有很多vlan,我用vconfig添加虚拟网卡,发现丢包严重,所以才想用这种方法。

liwei_swjtu 发表于 2014-08-14 16:07

抓包看看吧,发出去的报文格式内容对一下是否正确,然后再检查一下对端的配置是否正确,如果正确,看一下丢包计数之类的,先确认报文到哪里了,因为什么原因被丢弃了,一步一步有针对性的来就好了。

freeos 发表于 2014-08-14 20:35

1:在Postrouting并没有MAC头部,你这样处理,跳过ARP协议处理部分,肯定会不通。因为MAC头不对
2:你跳过了分片处理部分,超过MTU的包会出问题

还是用常规vconfig好,丢包严重与vconfig创建的虚拟接口没有关系,肯定是其它原因。
页: [1]
查看完整版本: 调用函数 dev_queue_xmit 问题