netlink是否使用'广播'传递消息?

时间:2015-06-18 03:06:10

标签: netlink

我正在关注this question and answer上的netlink示例。

但是,我没有在源代码中看到某种connection identifier。说:

内核

my_nl_sock = netlink_kernel_create(&init_net, NETLINK_USERSOCK, 0,
                 my_nl_rcv_msg, NULL, THIS_MODULE);

用户空间

nls = nl_socket_alloc();
ret = nl_connect(nls, NETLINK_USERSOCK);
ret = nl_send_simple(nls, MY_MSG_TYPE, 0, msg, sizeof(msg));

其中NETLINK_USERSOCKMY_MSG_TYPE似乎不是connection identifier

在这种情况下,netlink如何知道哪些数据来自哪个用户空间应用程序或内核模块以及数据应该去哪个用户空间应用程序或内核模块?

在我的猜测中,netlink从用户空间应用程序或内核模块接收数据并进行广播。每个netlink连接的应用程序或模块都会检查消息类型,如果数据是指定给我'

我认为对吗?

1 个答案:

答案 0 :(得分:0)

首先,我建议您阅读一些文档,例如http://www.linuxfoundation.org/collaborate/workgroups/networking/generic_netlink_howto

要进行沟通,您必须在支持的操作中注册一个家庭。可以使用以下功能完成

int genl_register_family( struct genl_family *family)   
int genl_register_ops( struct genl_family * family, struct genl_ops *ops)

家庭定义的一个例子:

/* 
 *  Attributes (variables): the index in this enum is used as a reference for the type,
 *  userspace application has to indicate the corresponding type
 */
enum {
    CTRL_ATT_R_UNSPEC = 0,
    CTRL_ATT_CNT_SESSIONS,
    __CTRL_ATT_R_MAX
};

#define CTRL_ATT_R_MAX ( __CTRL_ATT_R_MAX - 1 )

#define CTRL_FAMILY "your-family"
#define CTRL_PROTO_VERSION 1

/* Family definition */
static struct genl_family ctrl_bin_gnl_family = {
    .id = GENL_ID_GENERATE,         // genetlink should generate an id
    .hdrsize = 0,
    .name = CTRL_FAMILY,            // the name of this family, used by userspace application
    .version = CTRL_PROTO_VERSION,  // version number  
    .maxattr = CTRL_ATT_R_MAX,      // max number of attr 
};

操作定义的示例:

struct genl_ops ctrl_info = {
    .cmd = CTRL_CMD_INFO,
    .flags = 0,
    .policy = 0,      // you can use policy if you need 
    .doit = 0,        // set this callback if this op does some interval stuff 
    .dumpit = __info, // set this callback if this op dump data
};

之后,您可以在您的用户空间应用程序中使用您的家人和操作进行通信。建立联系:

struct nl_sock * _nl = nl_socket_alloc();

int ret = genl_connect(nl);
// test if fail

int gid = genl_ctrl_resolve( nl, CTRL_FAMILY );
// test if fail

发送信息操作

struct nl_msg * msg = msg_alloc( 
    CTRL_CMD_INFO,
    NLM_F_DUMP 
);

int ret = nl_send_auto(_nl, msg );
// test if fail
// wait for the ack
// read a reply