我有一个网络模块,如果它的目的地不是本地或直接连接的网络,它会封装一个数据包。为此,我有一个函数可以检测此数据包是否为本地数据包。此功能适用于 IPv4 数据包,我应该复制它以对 IPv6 执行相同的操作。IPv4的函数代码是:
bool is_v4addr_local(struct iphdr *iph, const struct net_device *output_dev)
{
struct flowi fl;
struct rtable *rt;
struct net_device *dev;
if(output_dev == NULL) {
printk(KERN_DEBUG "output_dev is NULL!");
return 0;
}
memset(&fl, 0, sizeof(fl));
fl.u.ip4.daddr = iph->daddr;
fl.flowi_tos = RTO_ONLINK; //locally connected
rt = ip_route_output_key(dev_net(output_dev), &fl.u.ip4);
if (IS_ERR(rt))
return 0;
dev = rt->dst.dev;
ip_rt_put(rt);
if (!dev)
return 0;
// If we got anything, it's local
return 1;
}
为了适应它,我认为我应该使用函数 fib6_rule_lookup 但我知道如何引入函数的最后一个参数(在某些示例中,他们只放置了 ip6_pol_route_lookup 但它不起作用)。
你能帮我调整这个功能吗?是我第一次在内核空间编程。
谢谢
bool is_v6addr_local(struct ipv6hdr *iph, const struct net_device *output_dev)
{
struct rt6_info *rt;
struct net_device *dev;
struct dst_entry *dst;
struct flowi6 fl6;
if(output_dev == NULL) {
printk(KERN_DEBUG "output_dev is NULL!");
return 0;
}
memset(&fl6, 0, sizeof(fl6));
fl6.flowi6_tos = RTO_ONLINK;
fl6.daddr = iph->daddr;
dst = fib6_rule_lookup(dev_net(output_dev), &fl6, 0, ip6_pol_route_lookup);
if (dst->error != 0)
return 0;
rt = (struct rt6_info *) dst;
dev = rt->dst.dev;
if (!dev)
return 0;
// If we got anything, it's local*/
return 1;
}