Linux VRF 移植遇到的无法绑定VRF interface发送单播数据包问题

起因

系统内核版本3.10.104, 然而VRF的multicast支持在4.4版本才开始,而且版本之间很多问题也不一样,后续导致了一些问题。

理解错误?

在我的理解中,如果要绑定VRF interface,在发送数据包的时候需要提供ifindex, 也就是真实的接口的ifindex,而不是VRF接口的ifindex.

VRF 作者的pdf
VRF 作者在论坛中回复

问题

之前的移植,发送广播的时候没什么问题,发送IPv6单播的时候就出现问题了。无法绑定vlan interface,或者VRF interface 发送。 之前的两个链接明确回复说是VRF可以接收所有路由到这个路由表的数据,但是发送需要通过真实的设备发送。所以绑定VRF 接口无法发送,我觉得可以理解,但是IPv4竟然工作,而且绑定到vlan接口仍然不能发送这个就让我觉得哪里出错了。

解决方案

后来我在rt6_check_dev里面找到了可以判断数据来自哪个接口,根据这个来判断,给这个路由查抄返回1,也可以让其工作,在接收的地方放过也接收这个数据报文就可以了。 【拙劣的自检】
还有一种方式,是4.9内核才实现的,4.4内核到现在也没有同步,不知道为什么内核没有测试出这个问题。就是在数据包要走vrf lookup查找之前,判断数据报文的目的地址是不是广播,LINK_LOCAL,组播之类的,也就是rt6_need_strict判断。

···
struct dst_entry *ip6_route_output_flags(struct net *net, const struct sock *sk,
struct flowi6 *fl6, int flags)
{
bool any_src;

    if (rt6_need_strict(&fl6->daddr)) {
           struct dst_entry *dst;

           dst = l3mdev_link_scope_lookup(net, fl6);
           if (dst)
                   return dst;
    }

···

总结

对于VRF的整体实现,虽然通过匹配代码方式,马马虎虎的让其工作了,但是由于对这个VRF的整体实现原理,和协议栈的理解不透彻还是存在一些问题的,如果你让我看代码找出问题我估计除非我对这两者再熟悉深入一层,否则还不如对着BUG解决问题。

学而时习之,不亦说乎。

你可能感兴趣的:(Linux,KnowHow)