将多播地址添加到 tap 驱动程序时的事件

Event when a multicast address is added to the tap driver

我正在将用户space 网络驱动程序移植到较新的linux 版本。

想法是摆脱将内核的网络堆栈连接到驱动程序的自定义内核模块,并改用 TUN/TAP。

我现在面临的问题是 adding/removing 驱动程序应该在线上收听的多播地址。

我知道如何获取接口的当前多播地址列表

cat /proc/net/dev_mcast

但是当列表更改时我没有收到任何事件。

当驱动程序应该监听新的多播地址时,用户 space 调用:

struct ip_mreq group;
group.imr_multiaddr.s_addr = inet_addr("226.1.1.1");     // multicast address
group.imr_interface.s_addr = inet_addr("172.16.72.100"); // interface address

setsockopt(sd, IPPROTO_IP, IP_ADD_MEMBERSHIP, (char *) &group, sizeof(group));

这导致内核调用

struct net_device_op.ndo_set_rx_mode

然后驱动程序可以更新其(硬件)多播过滤器。

很遗憾,TAP 驱动程序中的回调为空。

是否有任何替代方法来检测多播接收中的变化(无需轮询)?

我尝试了 netlink 消息,但是 RTNLGRP_NEIGH 没有报告对多播地址的更改。

使用 inotify 监控 /proc/net/dev_mcast 也不起作用,因为虚拟文件系统不支持 inotify。

谢谢, 沃尔夫冈

Usespace 路由守护程序通常会监听 routing netlink socket and epoll 状态以对事件做出反应。我认为这应该会给你想要的行为。

如果您必须执行更高级的多播路由,您可能需要查看一个特殊的 Linux 内核挂钩,用于多播路由守护进程管理标记为 CONFIG_IP_MROUTE 的多播路由 table .

这篇文章很好地解释了这个机制: http://www.linuxjournal.com/article/6070

使用此挂钩的简单多播路由守护程序的示例是: http://troglobit.com/projects/smcroute/