linux netlink多播组问题
经过了三天的苦战,终于把netlink广播组的问题给解决了,现写一下心得,方便以后查找,同时也帮助需要解决此问题的同道中人…… 问题现象: 设定netlink广播组后,应用层向内核发送数据,内核可以收到,但是内核通过netlink_broadcast向应用层发送时,返回-3,表示没有socket在监听。 应用层关键代码大致如下:int nl_init(int
经过了三天的苦战,终于把netlink广播组的问题给解决了,现写一下心得,方便以后查找,同时也帮助需要解决此问题的同道中人……
问题现象:
设定netlink广播组后,应用层向内核发送数据,内核可以收到,但是内核通过netlink_broadcast向应用层发送时,返回-3,表示没有socket在监听。
应用层关键代码大致如下:
int nl_init(int mod_id)
{
int sock_fd = 0;
struct sockaddr_nl src_addr; sock_fd = socket(PF_NETLINK,SOCK_RAW,NETLINK_TEST/*24*/);
memset(&src_addr,0,sizeof(src_addr));
src_addr.nl_family = AF_NETLINK;
src_addr.nl_pid = getpid();
src_addr.nl_groups = mod_id;
bind(sock_fd,(struct sockaddr *)&src_addr,sizeof(src_addr));
return sock_fd;
}
用红色字体标注的地方时关键代码,这个nl_groups字段很有意思,它表示多播组的掩码(注意,是掩码,不是多播组的组号);就这个字段我查了无数的资料,大多都是设置成0或者1,而且也没有说为什么,有的甚至就直接说“不清楚这个字段,一般设置成0,通过pid来通讯”。没办法,网上没有自能自己搞定了,我只能慢慢试了(中间死机无数次),最终,在内核的af_netlink.c中让我看到了一个netlink_group_mask函数,我觉得有希望了,但是还不清楚这个函数用在什么地方(或者是用在那一端,或者两端都用),我只好再次一点一点的试验,最终终于解决了多播组掩码的问题,最终代码如下:
static int netlink_group_mask(int group)
{
return group ? 1 << (group - 1) : 0;
}
int nl_init(int mod_id)
{
int sock_fd = 0;
struct sockaddr_nl src_addr;
sock_fd = socket(PF_NETLINK,SOCK_RAW,NETLINK_TEST/*24*/);
memset(&src_addr,0,sizeof(src_addr));
src_addr.nl_family = AF_NETLINK;
src_addr.nl_pid = getpid();
src_addr.nl_groups = netlink_group_mask(mod_id);
bind(sock_fd,(struct sockaddr *)&src_addr,sizeof(src_addr));
return sock_fd;
}
内核发送代码:
netlink_broadcast(hsk, skb, 0, mod_id, GFP_ATOMIC)
更多推荐
所有评论(0)