How to create a "netlink" between the kernel and user space?

I want to use netlink for communication between an application and kernel space. My version of the Linux kernel is 2.6.28, and the following code is incorrect.

nf_sock=netlink_kernel_create(NL_PROTO,0,nl_user_skb,THIS_MODULE); 

Short error message:

 error: too few arguments to function 'netlink_kernel_create' 

In the <linux/netlink.h> the netlink_kernel_create() function is defined as

 extern struct sock *netlink_kernel_create(struct net *net,int unit,unsigned int groups,void (*input)(struct sk_buff *skb),struct mutex *cb_mutex,struct module *module) 

I do not understand what to use for the first argument, net . Can someone explain what I should use here?

+4
source share
4 answers

A struct net contains information about the namespace on the network, the set of network resources available to processes. Note that there may be several network namespaces (i.e., multiple instances of the network stack), but most drivers use the init_net namespace.

Your call should look something like this:

 nf_sock = netlink_kernel_create(&init_net, NETLINK_USERSOCK, 0, nl_rcv_func, NULL, THIS_MODULE); 

where nl_rcv_func is a function that takes struct sk_buff *skb as the only argument and processes the received netlink message.

+4
source

It seems that you are following a guide, for example this one , which (since 2005) could significantly outperform core development. It seems that the core API for creating netlink from the kernel has changed.

Either check the documentation / folder in the local kernel tree for some (hopefully more recent) documentation, or read the code itself. You can also trawl the Linux Kernel mailing list archives for any mention of changes that seem to have occurred.

Here is the actual implementation since 2.6.29, if you prefer to unravel it back (and haven't checked it in your own tree yet, of course).

+2
source

Yes, the net structure is valid for the network namespace, but do not always use init_net, you must register your own pernet_operations, for example:

 static struct pernet_operations fib_net_ops = { .init = fib_net_init, .exit = fib_net_exit, }; static int __net_init fib_net_init(struct net *net) { int error; #ifdef CONFIG_IP_ROUTE_CLASSID net->ipv4.fib_num_tclassid_users = 0; #endif error = ip_fib_net_init(net); if (error < 0) goto out; error = nl_fib_lookup_init(net); if (error < 0) goto out_nlfl; error = fib_proc_init(net); if (error < 0) goto out_proc; out: return error; out_proc: nl_fib_lookup_exit(net); out_nlfl: ip_fib_net_exit(net); goto out; } static int __net_init nl_fib_lookup_init(struct net *net) { struct sock *sk; struct netlink_kernel_cfg cfg = { .input = nl_fib_input, }; sk = netlink_kernel_create(net, NETLINK_FIB_LOOKUP, &cfg); if (sk == NULL) return -EAFNOSUPPORT; net->ipv4.fibnl = sk; return 0; } 

and finally:

 register_pernet_subsys(&fib_net_ops); 
+1
source

I suggest ioctl to communicate with the kernel / user. The ioctl interface is standard and there is little likelihood of an update between the kernels.

-3
source

All Articles