All of lore.kernel.org
 help / color / mirror / Atom feed
From: ebiederm-aS9lmoZGLiVWk0Htik3J/w@public.gmane.org (Eric W. Biederman)
To: Nicolas Dichtel
	<nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
Cc: netdev-u79uwXL29TY76Z2rM5mHXA@public.gmane.org,
	containers-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA@public.gmane.org,
	linux-kernel-u79uwXL29TY76Z2rM5mHXA@public.gmane.org,
	luto-kltTT9wpgjJwATOyAt5JVQ@public.gmane.org,
	stephen-OTpzqLSitTUnbdJkjeBofR2eb7JE58TQ@public.gmane.org,
	cwang-xCSkyg8dI+0RB7SZvlqPiA@public.gmane.org,
	linux-api-u79uwXL29TY76Z2rM5mHXA@public.gmane.org,
	akpm-de/tnXTf+JLsfHDXvbKv3WD2FQJk+8+b@public.gmane.org,
	davem-fT/PcQaiUtIeIZ0/mPfg9Q@public.gmane.org
Subject: Re: [PATCH net-next v4 1/4] netns: add genl cmd to add and get peer netns ids
Date: Thu, 30 Oct 2014 11:35:31 -0700	[thread overview]
Message-ID: <874mulh0cs.fsf@x220.int.ebiederm.org> (raw)
In-Reply-To: <1414682728-4532-2-git-send-email-nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org> (Nicolas Dichtel's message of "Thu, 30 Oct 2014 16:25:25 +0100")

Nicolas Dichtel <nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org> writes:

> With this patch, a user can define an id for a peer netns by providing a FD or a
> PID. These ids are local to netns (ie valid only into one netns).

Scratches head.  Do you actually find value in using the pid instead of
a file descriptor?

Doing things by pid was an early attempt to make things work, and has
been a bit clutsy.  If you don't find value in it I would recommend just
supporting getting/setting the network namespace by file descriptor.

Eric

> This will be useful for netlink messages when a x-netns interface is dumped.
>
> Signed-off-by: Nicolas Dichtel <nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
> ---
>  MAINTAINERS                 |   1 +
>  include/net/net_namespace.h |   5 ++
>  include/uapi/linux/Kbuild   |   1 +
>  include/uapi/linux/netns.h  |  38 +++++++++
>  net/core/net_namespace.c    | 195 ++++++++++++++++++++++++++++++++++++++++++++
>  net/netlink/genetlink.c     |   4 +
>  6 files changed, 244 insertions(+)
>  create mode 100644 include/uapi/linux/netns.h
>
> diff --git a/MAINTAINERS b/MAINTAINERS
> index 43898b1a8a2d..de7e6fcbd5c2 100644
> --- a/MAINTAINERS
> +++ b/MAINTAINERS
> @@ -6382,6 +6382,7 @@ F:	include/linux/netdevice.h
>  F:	include/uapi/linux/in.h
>  F:	include/uapi/linux/net.h
>  F:	include/uapi/linux/netdevice.h
> +F:	include/uapi/linux/netns.h
>  F:	tools/net/
>  F:	tools/testing/selftests/net/
>  F:	lib/random32.c
> diff --git a/include/net/net_namespace.h b/include/net/net_namespace.h
> index e0d64667a4b3..0f1367a71b81 100644
> --- a/include/net/net_namespace.h
> +++ b/include/net/net_namespace.h
> @@ -59,6 +59,7 @@ struct net {
>  	struct list_head	exit_list;	/* Use only net_mutex */
>  
>  	struct user_namespace   *user_ns;	/* Owning user namespace */
> +	struct idr		netns_ids;
>  
>  	unsigned int		proc_inum;
>  
> @@ -289,6 +290,10 @@ static inline struct net *read_pnet(struct net * const *pnet)
>  #define __net_initconst	__initconst
>  #endif
>  
> +int peernet2id(struct net *net, struct net *peer);
> +struct net *get_net_ns_by_id(struct net *net, int id);
> +int netns_genl_register(void);
> +
>  struct pernet_operations {
>  	struct list_head list;
>  	int (*init)(struct net *net);
> diff --git a/include/uapi/linux/Kbuild b/include/uapi/linux/Kbuild
> index 6cad97485bad..d7f49c69585a 100644
> --- a/include/uapi/linux/Kbuild
> +++ b/include/uapi/linux/Kbuild
> @@ -277,6 +277,7 @@ header-y += netfilter_decnet.h
>  header-y += netfilter_ipv4.h
>  header-y += netfilter_ipv6.h
>  header-y += netlink.h
> +header-y += netns.h
>  header-y += netrom.h
>  header-y += nfc.h
>  header-y += nfs.h
> diff --git a/include/uapi/linux/netns.h b/include/uapi/linux/netns.h
> new file mode 100644
> index 000000000000..2edf129377de
> --- /dev/null
> +++ b/include/uapi/linux/netns.h
> @@ -0,0 +1,38 @@
> +/* Copyright (c) 2014 6WIND S.A.
> + * Author: Nicolas Dichtel <nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
> + *
> + * This program is free software; you can redistribute it and/or modify it
> + * under the terms and conditions of the GNU General Public License,
> + * version 2, as published by the Free Software Foundation.
> + */
> +#ifndef _UAPI_LINUX_NETNS_H_
> +#define _UAPI_LINUX_NETNS_H_
> +
> +/* Generic netlink messages */
> +
> +#define NETNS_GENL_NAME			"netns"
> +#define NETNS_GENL_VERSION		0x1
> +
> +/* Commands */
> +enum {
> +	NETNS_CMD_UNSPEC,
> +	NETNS_CMD_NEWID,
> +	NETNS_CMD_GETID,
> +	__NETNS_CMD_MAX,
> +};
> +
> +#define NETNS_CMD_MAX		(__NETNS_CMD_MAX - 1)
> +
> +/* Attributes */
> +enum {
> +	NETNSA_NONE,
> +#define NETNSA_NSINDEX_UNKNOWN	-1
> +	NETNSA_NSID,
> +	NETNSA_PID,
> +	NETNSA_FD,
> +	__NETNSA_MAX,
> +};
> +
> +#define NETNSA_MAX		(__NETNSA_MAX - 1)
> +
> +#endif /* _UAPI_LINUX_NETNS_H_ */
> diff --git a/net/core/net_namespace.c b/net/core/net_namespace.c
> index 7f155175bba8..4a5680ed42fb 100644
> --- a/net/core/net_namespace.c
> +++ b/net/core/net_namespace.c
> @@ -15,6 +15,8 @@
>  #include <linux/file.h>
>  #include <linux/export.h>
>  #include <linux/user_namespace.h>
> +#include <linux/netns.h>
> +#include <net/genetlink.h>
>  #include <net/net_namespace.h>
>  #include <net/netns/generic.h>
>  
> @@ -144,6 +146,50 @@ static void ops_free_list(const struct pernet_operations *ops,
>  	}
>  }
>  
> +/* This function is used by idr_for_each(). If net is equal to peer, the
> + * function returns the id so that idr_for_each() stops. Because we cannot
> + * returns the id 0 (idr_for_each() will not stop), we return the magic value
> + * -1 for it.
> + */
> +static int net_eq_idr(int id, void *net, void *peer)
> +{
> +	if (net_eq(net, peer))
> +		return id ? : -1;
> +	return 0;
> +}
> +
> +/* returns NETNSA_NSINDEX_UNKNOWN if not found */
> +int peernet2id(struct net *net, struct net *peer)
> +{
> +	int id = idr_for_each(&net->netns_ids, net_eq_idr, peer);
> +
> +	ASSERT_RTNL();
> +
> +	/* Magic value for id 0. */
> +	if (id == -1)
> +		return 0;
> +	if (id == 0)
> +		return NETNSA_NSINDEX_UNKNOWN;
> +
> +	return id;
> +}
> +
> +struct net *get_net_ns_by_id(struct net *net, int id)
> +{
> +	struct net *peer;
> +
> +	if (id < 0)
> +		return NULL;
> +
> +	rcu_read_lock();
> +	peer = idr_find(&net->netns_ids, id);
> +	if (peer)
> +		get_net(peer);
> +	rcu_read_unlock();
> +
> +	return peer;
> +}
> +
>  /*
>   * setup_net runs the initializers for the network namespace object.
>   */
> @@ -158,6 +204,7 @@ static __net_init int setup_net(struct net *net, struct user_namespace *user_ns)
>  	atomic_set(&net->passive, 1);
>  	net->dev_base_seq = 1;
>  	net->user_ns = user_ns;
> +	idr_init(&net->netns_ids);
>  
>  #ifdef NETNS_REFCNT_DEBUG
>  	atomic_set(&net->use_count, 0);
> @@ -288,6 +335,14 @@ static void cleanup_net(struct work_struct *work)
>  	list_for_each_entry(net, &net_kill_list, cleanup_list) {
>  		list_del_rcu(&net->list);
>  		list_add_tail(&net->exit_list, &net_exit_list);
> +		for_each_net(tmp) {
> +			int id = peernet2id(tmp, net);
> +
> +			if (id >= 0)
> +				idr_remove(&tmp->netns_ids, id);
> +		}
> +		idr_destroy(&net->netns_ids);
> +
>  	}
>  	rtnl_unlock();
>  
> @@ -399,6 +454,146 @@ static struct pernet_operations __net_initdata net_ns_ops = {
>  	.exit = net_ns_net_exit,
>  };
>  
> +static struct genl_family netns_genl_family = {
> +	.id		= GENL_ID_GENERATE,
> +	.name		= NETNS_GENL_NAME,
> +	.version	= NETNS_GENL_VERSION,
> +	.hdrsize	= 0,
> +	.maxattr	= NETNSA_MAX,
> +	.netnsok	= true,
> +};
> +
> +static struct nla_policy netns_nl_policy[NETNSA_MAX + 1] = {
> +	[NETNSA_NONE]		= { .type = NLA_UNSPEC },
> +	[NETNSA_NSID]		= { .type = NLA_S32 },
> +	[NETNSA_PID]		= { .type = NLA_U32 },
> +	[NETNSA_FD]		= { .type = NLA_U32 },
> +};
> +
> +static int netns_nl_cmd_newid(struct sk_buff *skb, struct genl_info *info)
> +{
> +	struct net *net = genl_info_net(info);
> +	struct net *peer;
> +	int nsid, err;
> +
> +	if (!info->attrs[NETNSA_NSID])
> +		return -EINVAL;
> +	nsid = nla_get_s32(info->attrs[NETNSA_NSID]);
> +	if (nsid < 0)
> +		return -EINVAL;
> +
> +	if (info->attrs[NETNSA_PID])
> +		peer = get_net_ns_by_pid(nla_get_u32(info->attrs[NETNSA_PID]));
> +	else if (info->attrs[NETNSA_FD])
> +		peer = get_net_ns_by_fd(nla_get_u32(info->attrs[NETNSA_FD]));
> +	else
> +		return -EINVAL;
> +	if (IS_ERR(peer))
> +		return PTR_ERR(peer);
> +
> +	rtnl_lock();
> +	if (peernet2id(net, peer) >= 0) {
> +		err = -EEXIST;
> +		goto out;
> +	}
> +
> +	err = idr_alloc(&net->netns_ids, peer, nsid, nsid + 1, GFP_KERNEL);
> +	if (err >= 0)
> +		err = 0;
> +out:
> +	rtnl_unlock();
> +	put_net(peer);
> +	return err;
> +}
> +
> +static int netns_nl_get_size(void)
> +{
> +	return nla_total_size(sizeof(s32)) /* NETNSA_NSID */
> +	       ;
> +}
> +
> +static int netns_nl_fill(struct sk_buff *skb, u32 portid, u32 seq, int flags,
> +			 int cmd, struct net *net, struct net *peer)
> +{
> +	void *hdr;
> +	int id;
> +
> +	hdr = genlmsg_put(skb, portid, seq, &netns_genl_family, flags, cmd);
> +	if (!hdr)
> +		return -EMSGSIZE;
> +
> +	rtnl_lock();
> +	id = peernet2id(net, peer);
> +	rtnl_unlock();
> +	if (nla_put_s32(skb, NETNSA_NSID, id))
> +		goto nla_put_failure;
> +
> +	return genlmsg_end(skb, hdr);
> +
> +nla_put_failure:
> +	genlmsg_cancel(skb, hdr);
> +	return -EMSGSIZE;
> +}
> +
> +static int netns_nl_cmd_getid(struct sk_buff *skb, struct genl_info *info)
> +{
> +	struct net *net = genl_info_net(info);
> +	struct sk_buff *msg;
> +	int err = -ENOBUFS;
> +	struct net *peer;
> +
> +	if (info->attrs[NETNSA_PID])
> +		peer = get_net_ns_by_pid(nla_get_u32(info->attrs[NETNSA_PID]));
> +	else if (info->attrs[NETNSA_FD])
> +		peer = get_net_ns_by_fd(nla_get_u32(info->attrs[NETNSA_FD]));
> +	else
> +		return -EINVAL;
> +
> +	if (IS_ERR(peer))
> +		return PTR_ERR(peer);
> +
> +	msg = genlmsg_new(netns_nl_get_size(), GFP_KERNEL);
> +	if (!msg) {
> +		err = -ENOMEM;
> +		goto out;
> +	}
> +
> +	err = netns_nl_fill(msg, info->snd_portid, info->snd_seq,
> +			    NLM_F_ACK, NETNS_CMD_GETID, net, peer);
> +	if (err < 0)
> +		goto err_out;
> +
> +	err = genlmsg_unicast(net, msg, info->snd_portid);
> +	goto out;
> +
> +err_out:
> +	nlmsg_free(msg);
> +out:
> +	put_net(peer);
> +	return err;
> +}
> +
> +static struct genl_ops netns_genl_ops[] = {
> +	{
> +		.cmd = NETNS_CMD_NEWID,
> +		.policy = netns_nl_policy,
> +		.doit = netns_nl_cmd_newid,
> +		.flags = GENL_ADMIN_PERM,
> +	},
> +	{
> +		.cmd = NETNS_CMD_GETID,
> +		.policy = netns_nl_policy,
> +		.doit = netns_nl_cmd_getid,
> +		.flags = GENL_ADMIN_PERM,
> +	},
> +};
> +
> +int netns_genl_register(void)
> +{
> +	return genl_register_family_with_ops(&netns_genl_family,
> +					     netns_genl_ops);
> +}
> +
>  static int __init net_ns_init(void)
>  {
>  	struct net_generic *ng;
> diff --git a/net/netlink/genetlink.c b/net/netlink/genetlink.c
> index 76393f2f4b22..c6f39e40c9f3 100644
> --- a/net/netlink/genetlink.c
> +++ b/net/netlink/genetlink.c
> @@ -1029,6 +1029,10 @@ static int __init genl_init(void)
>  	if (err)
>  		goto problem;
>  
> +	err = netns_genl_register();
> +	if (err < 0)
> +		goto problem;
> +
>  	return 0;
>  
>  problem:

WARNING: multiple messages have this Message-ID (diff)
From: ebiederm@xmission.com (Eric W. Biederman)
To: Nicolas Dichtel <nicolas.dichtel@6wind.com>
Cc: netdev@vger.kernel.org, containers@lists.linux-foundation.org,
	linux-kernel@vger.kernel.org, linux-api@vger.kernel.org,
	davem@davemloft.net, stephen@networkplumber.org,
	akpm@linux-foundation.org, luto@amacapital.net,
	cwang@twopensource.com
Subject: Re: [PATCH net-next v4 1/4] netns: add genl cmd to add and get peer netns ids
Date: Thu, 30 Oct 2014 11:35:31 -0700	[thread overview]
Message-ID: <874mulh0cs.fsf@x220.int.ebiederm.org> (raw)
In-Reply-To: <1414682728-4532-2-git-send-email-nicolas.dichtel@6wind.com> (Nicolas Dichtel's message of "Thu, 30 Oct 2014 16:25:25 +0100")

Nicolas Dichtel <nicolas.dichtel@6wind.com> writes:

> With this patch, a user can define an id for a peer netns by providing a FD or a
> PID. These ids are local to netns (ie valid only into one netns).

Scratches head.  Do you actually find value in using the pid instead of
a file descriptor?

Doing things by pid was an early attempt to make things work, and has
been a bit clutsy.  If you don't find value in it I would recommend just
supporting getting/setting the network namespace by file descriptor.

Eric

> This will be useful for netlink messages when a x-netns interface is dumped.
>
> Signed-off-by: Nicolas Dichtel <nicolas.dichtel@6wind.com>
> ---
>  MAINTAINERS                 |   1 +
>  include/net/net_namespace.h |   5 ++
>  include/uapi/linux/Kbuild   |   1 +
>  include/uapi/linux/netns.h  |  38 +++++++++
>  net/core/net_namespace.c    | 195 ++++++++++++++++++++++++++++++++++++++++++++
>  net/netlink/genetlink.c     |   4 +
>  6 files changed, 244 insertions(+)
>  create mode 100644 include/uapi/linux/netns.h
>
> diff --git a/MAINTAINERS b/MAINTAINERS
> index 43898b1a8a2d..de7e6fcbd5c2 100644
> --- a/MAINTAINERS
> +++ b/MAINTAINERS
> @@ -6382,6 +6382,7 @@ F:	include/linux/netdevice.h
>  F:	include/uapi/linux/in.h
>  F:	include/uapi/linux/net.h
>  F:	include/uapi/linux/netdevice.h
> +F:	include/uapi/linux/netns.h
>  F:	tools/net/
>  F:	tools/testing/selftests/net/
>  F:	lib/random32.c
> diff --git a/include/net/net_namespace.h b/include/net/net_namespace.h
> index e0d64667a4b3..0f1367a71b81 100644
> --- a/include/net/net_namespace.h
> +++ b/include/net/net_namespace.h
> @@ -59,6 +59,7 @@ struct net {
>  	struct list_head	exit_list;	/* Use only net_mutex */
>  
>  	struct user_namespace   *user_ns;	/* Owning user namespace */
> +	struct idr		netns_ids;
>  
>  	unsigned int		proc_inum;
>  
> @@ -289,6 +290,10 @@ static inline struct net *read_pnet(struct net * const *pnet)
>  #define __net_initconst	__initconst
>  #endif
>  
> +int peernet2id(struct net *net, struct net *peer);
> +struct net *get_net_ns_by_id(struct net *net, int id);
> +int netns_genl_register(void);
> +
>  struct pernet_operations {
>  	struct list_head list;
>  	int (*init)(struct net *net);
> diff --git a/include/uapi/linux/Kbuild b/include/uapi/linux/Kbuild
> index 6cad97485bad..d7f49c69585a 100644
> --- a/include/uapi/linux/Kbuild
> +++ b/include/uapi/linux/Kbuild
> @@ -277,6 +277,7 @@ header-y += netfilter_decnet.h
>  header-y += netfilter_ipv4.h
>  header-y += netfilter_ipv6.h
>  header-y += netlink.h
> +header-y += netns.h
>  header-y += netrom.h
>  header-y += nfc.h
>  header-y += nfs.h
> diff --git a/include/uapi/linux/netns.h b/include/uapi/linux/netns.h
> new file mode 100644
> index 000000000000..2edf129377de
> --- /dev/null
> +++ b/include/uapi/linux/netns.h
> @@ -0,0 +1,38 @@
> +/* Copyright (c) 2014 6WIND S.A.
> + * Author: Nicolas Dichtel <nicolas.dichtel@6wind.com>
> + *
> + * This program is free software; you can redistribute it and/or modify it
> + * under the terms and conditions of the GNU General Public License,
> + * version 2, as published by the Free Software Foundation.
> + */
> +#ifndef _UAPI_LINUX_NETNS_H_
> +#define _UAPI_LINUX_NETNS_H_
> +
> +/* Generic netlink messages */
> +
> +#define NETNS_GENL_NAME			"netns"
> +#define NETNS_GENL_VERSION		0x1
> +
> +/* Commands */
> +enum {
> +	NETNS_CMD_UNSPEC,
> +	NETNS_CMD_NEWID,
> +	NETNS_CMD_GETID,
> +	__NETNS_CMD_MAX,
> +};
> +
> +#define NETNS_CMD_MAX		(__NETNS_CMD_MAX - 1)
> +
> +/* Attributes */
> +enum {
> +	NETNSA_NONE,
> +#define NETNSA_NSINDEX_UNKNOWN	-1
> +	NETNSA_NSID,
> +	NETNSA_PID,
> +	NETNSA_FD,
> +	__NETNSA_MAX,
> +};
> +
> +#define NETNSA_MAX		(__NETNSA_MAX - 1)
> +
> +#endif /* _UAPI_LINUX_NETNS_H_ */
> diff --git a/net/core/net_namespace.c b/net/core/net_namespace.c
> index 7f155175bba8..4a5680ed42fb 100644
> --- a/net/core/net_namespace.c
> +++ b/net/core/net_namespace.c
> @@ -15,6 +15,8 @@
>  #include <linux/file.h>
>  #include <linux/export.h>
>  #include <linux/user_namespace.h>
> +#include <linux/netns.h>
> +#include <net/genetlink.h>
>  #include <net/net_namespace.h>
>  #include <net/netns/generic.h>
>  
> @@ -144,6 +146,50 @@ static void ops_free_list(const struct pernet_operations *ops,
>  	}
>  }
>  
> +/* This function is used by idr_for_each(). If net is equal to peer, the
> + * function returns the id so that idr_for_each() stops. Because we cannot
> + * returns the id 0 (idr_for_each() will not stop), we return the magic value
> + * -1 for it.
> + */
> +static int net_eq_idr(int id, void *net, void *peer)
> +{
> +	if (net_eq(net, peer))
> +		return id ? : -1;
> +	return 0;
> +}
> +
> +/* returns NETNSA_NSINDEX_UNKNOWN if not found */
> +int peernet2id(struct net *net, struct net *peer)
> +{
> +	int id = idr_for_each(&net->netns_ids, net_eq_idr, peer);
> +
> +	ASSERT_RTNL();
> +
> +	/* Magic value for id 0. */
> +	if (id == -1)
> +		return 0;
> +	if (id == 0)
> +		return NETNSA_NSINDEX_UNKNOWN;
> +
> +	return id;
> +}
> +
> +struct net *get_net_ns_by_id(struct net *net, int id)
> +{
> +	struct net *peer;
> +
> +	if (id < 0)
> +		return NULL;
> +
> +	rcu_read_lock();
> +	peer = idr_find(&net->netns_ids, id);
> +	if (peer)
> +		get_net(peer);
> +	rcu_read_unlock();
> +
> +	return peer;
> +}
> +
>  /*
>   * setup_net runs the initializers for the network namespace object.
>   */
> @@ -158,6 +204,7 @@ static __net_init int setup_net(struct net *net, struct user_namespace *user_ns)
>  	atomic_set(&net->passive, 1);
>  	net->dev_base_seq = 1;
>  	net->user_ns = user_ns;
> +	idr_init(&net->netns_ids);
>  
>  #ifdef NETNS_REFCNT_DEBUG
>  	atomic_set(&net->use_count, 0);
> @@ -288,6 +335,14 @@ static void cleanup_net(struct work_struct *work)
>  	list_for_each_entry(net, &net_kill_list, cleanup_list) {
>  		list_del_rcu(&net->list);
>  		list_add_tail(&net->exit_list, &net_exit_list);
> +		for_each_net(tmp) {
> +			int id = peernet2id(tmp, net);
> +
> +			if (id >= 0)
> +				idr_remove(&tmp->netns_ids, id);
> +		}
> +		idr_destroy(&net->netns_ids);
> +
>  	}
>  	rtnl_unlock();
>  
> @@ -399,6 +454,146 @@ static struct pernet_operations __net_initdata net_ns_ops = {
>  	.exit = net_ns_net_exit,
>  };
>  
> +static struct genl_family netns_genl_family = {
> +	.id		= GENL_ID_GENERATE,
> +	.name		= NETNS_GENL_NAME,
> +	.version	= NETNS_GENL_VERSION,
> +	.hdrsize	= 0,
> +	.maxattr	= NETNSA_MAX,
> +	.netnsok	= true,
> +};
> +
> +static struct nla_policy netns_nl_policy[NETNSA_MAX + 1] = {
> +	[NETNSA_NONE]		= { .type = NLA_UNSPEC },
> +	[NETNSA_NSID]		= { .type = NLA_S32 },
> +	[NETNSA_PID]		= { .type = NLA_U32 },
> +	[NETNSA_FD]		= { .type = NLA_U32 },
> +};
> +
> +static int netns_nl_cmd_newid(struct sk_buff *skb, struct genl_info *info)
> +{
> +	struct net *net = genl_info_net(info);
> +	struct net *peer;
> +	int nsid, err;
> +
> +	if (!info->attrs[NETNSA_NSID])
> +		return -EINVAL;
> +	nsid = nla_get_s32(info->attrs[NETNSA_NSID]);
> +	if (nsid < 0)
> +		return -EINVAL;
> +
> +	if (info->attrs[NETNSA_PID])
> +		peer = get_net_ns_by_pid(nla_get_u32(info->attrs[NETNSA_PID]));
> +	else if (info->attrs[NETNSA_FD])
> +		peer = get_net_ns_by_fd(nla_get_u32(info->attrs[NETNSA_FD]));
> +	else
> +		return -EINVAL;
> +	if (IS_ERR(peer))
> +		return PTR_ERR(peer);
> +
> +	rtnl_lock();
> +	if (peernet2id(net, peer) >= 0) {
> +		err = -EEXIST;
> +		goto out;
> +	}
> +
> +	err = idr_alloc(&net->netns_ids, peer, nsid, nsid + 1, GFP_KERNEL);
> +	if (err >= 0)
> +		err = 0;
> +out:
> +	rtnl_unlock();
> +	put_net(peer);
> +	return err;
> +}
> +
> +static int netns_nl_get_size(void)
> +{
> +	return nla_total_size(sizeof(s32)) /* NETNSA_NSID */
> +	       ;
> +}
> +
> +static int netns_nl_fill(struct sk_buff *skb, u32 portid, u32 seq, int flags,
> +			 int cmd, struct net *net, struct net *peer)
> +{
> +	void *hdr;
> +	int id;
> +
> +	hdr = genlmsg_put(skb, portid, seq, &netns_genl_family, flags, cmd);
> +	if (!hdr)
> +		return -EMSGSIZE;
> +
> +	rtnl_lock();
> +	id = peernet2id(net, peer);
> +	rtnl_unlock();
> +	if (nla_put_s32(skb, NETNSA_NSID, id))
> +		goto nla_put_failure;
> +
> +	return genlmsg_end(skb, hdr);
> +
> +nla_put_failure:
> +	genlmsg_cancel(skb, hdr);
> +	return -EMSGSIZE;
> +}
> +
> +static int netns_nl_cmd_getid(struct sk_buff *skb, struct genl_info *info)
> +{
> +	struct net *net = genl_info_net(info);
> +	struct sk_buff *msg;
> +	int err = -ENOBUFS;
> +	struct net *peer;
> +
> +	if (info->attrs[NETNSA_PID])
> +		peer = get_net_ns_by_pid(nla_get_u32(info->attrs[NETNSA_PID]));
> +	else if (info->attrs[NETNSA_FD])
> +		peer = get_net_ns_by_fd(nla_get_u32(info->attrs[NETNSA_FD]));
> +	else
> +		return -EINVAL;
> +
> +	if (IS_ERR(peer))
> +		return PTR_ERR(peer);
> +
> +	msg = genlmsg_new(netns_nl_get_size(), GFP_KERNEL);
> +	if (!msg) {
> +		err = -ENOMEM;
> +		goto out;
> +	}
> +
> +	err = netns_nl_fill(msg, info->snd_portid, info->snd_seq,
> +			    NLM_F_ACK, NETNS_CMD_GETID, net, peer);
> +	if (err < 0)
> +		goto err_out;
> +
> +	err = genlmsg_unicast(net, msg, info->snd_portid);
> +	goto out;
> +
> +err_out:
> +	nlmsg_free(msg);
> +out:
> +	put_net(peer);
> +	return err;
> +}
> +
> +static struct genl_ops netns_genl_ops[] = {
> +	{
> +		.cmd = NETNS_CMD_NEWID,
> +		.policy = netns_nl_policy,
> +		.doit = netns_nl_cmd_newid,
> +		.flags = GENL_ADMIN_PERM,
> +	},
> +	{
> +		.cmd = NETNS_CMD_GETID,
> +		.policy = netns_nl_policy,
> +		.doit = netns_nl_cmd_getid,
> +		.flags = GENL_ADMIN_PERM,
> +	},
> +};
> +
> +int netns_genl_register(void)
> +{
> +	return genl_register_family_with_ops(&netns_genl_family,
> +					     netns_genl_ops);
> +}
> +
>  static int __init net_ns_init(void)
>  {
>  	struct net_generic *ng;
> diff --git a/net/netlink/genetlink.c b/net/netlink/genetlink.c
> index 76393f2f4b22..c6f39e40c9f3 100644
> --- a/net/netlink/genetlink.c
> +++ b/net/netlink/genetlink.c
> @@ -1029,6 +1029,10 @@ static int __init genl_init(void)
>  	if (err)
>  		goto problem;
>  
> +	err = netns_genl_register();
> +	if (err < 0)
> +		goto problem;
> +
>  	return 0;
>  
>  problem:

  parent reply	other threads:[~2014-10-30 18:35 UTC|newest]

Thread overview: 149+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2014-09-23 13:20 [RFC PATCH net-next v2 0/5] netns: allow to identify peer netns Nicolas Dichtel
2014-09-23 13:20 ` [RFC PATCH net-next v2 1/5] netns: allocate netns ids Nicolas Dichtel
2014-09-23 13:20 ` [RFC PATCH net-next v2 2/5] netns: add genl cmd to get the id of a netns Nicolas Dichtel
2014-09-23 13:20 ` [RFC PATCH net-next v2 3/5] rtnl: add link netns id to interface messages Nicolas Dichtel
2014-09-23 13:20 ` [RFC PATCH net-next v2 4/5] iptunnels: advertise link netns via netlink Nicolas Dichtel
     [not found] ` <1411478430-4989-1-git-send-email-nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-09-23 13:20   ` [RFC PATCH net-next v2 1/5] netns: allocate netns ids Nicolas Dichtel
2014-09-23 13:20   ` [RFC PATCH net-next v2 2/5] netns: add genl cmd to get the id of a netns Nicolas Dichtel
2014-09-23 13:20   ` [RFC PATCH net-next v2 3/5] rtnl: add link netns id to interface messages Nicolas Dichtel
2014-09-23 13:20   ` [RFC PATCH net-next v2 4/5] iptunnels: advertise link netns via netlink Nicolas Dichtel
2014-09-23 13:20   ` [RFC PATCH net-next v2 5/5] rtnl: allow to create device with IFLA_LINK_NETNSID set Nicolas Dichtel
2014-09-23 13:20     ` Nicolas Dichtel
2014-09-23 19:22   ` [RFC PATCH net-next v2 0/5] netns: allow to identify peer netns Cong Wang
2014-09-23 19:22     ` Cong Wang
     [not found]     ` <CAHA+R7NnBJ=T3sukzzp-OD2am1nd318XbrXCX84LfSL=nu9ojw-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-09-24  9:23       ` Nicolas Dichtel
2014-09-24  9:23         ` Nicolas Dichtel
     [not found]         ` <54228D87.3070309-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-09-24 16:01           ` Cong Wang
2014-09-24 16:01             ` Cong Wang
     [not found]             ` <CAHA+R7NfJYzCsZx0E9YVXKVCQbCm_thPSi+80tix8Z9nVA82Ug-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-09-24 16:15               ` Cong Wang
2014-09-24 16:15                 ` Cong Wang
     [not found]                 ` <CAHA+R7MVL=WpepRy8iz6iT6Kkq1RHG+b9TxJothP94ixyAj-3Q-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-09-24 16:31                   ` Nicolas Dichtel
2014-09-24 16:31                     ` Nicolas Dichtel
     [not found]                     ` <5422F1F7.8010308-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-09-24 16:48                       ` Cong Wang
2014-09-24 16:48                         ` Cong Wang
     [not found]                         ` <CAHA+R7MM04ew=J8sHfSQERwoCAgEDfrGgtgRORqs3ePgtjVYWg-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-09-25  8:53                           ` Nicolas Dichtel
2014-09-25  8:53                             ` Nicolas Dichtel
     [not found]                             ` <5423D808.7050800-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-09-26  1:58                               ` Cong Wang
2014-09-26  1:58                                 ` Cong Wang
     [not found]                                 ` <CAHA+R7OdOUMShX6Nphdfh8+fGiXyO+sGNHy0ch_XYh5dpURcmQ-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-09-26 13:38                                   ` Nicolas Dichtel
2014-09-26 13:38                                     ` Nicolas Dichtel
2014-09-24 16:27               ` Nicolas Dichtel
2014-09-24 16:27                 ` Nicolas Dichtel
     [not found]                 ` <5422F0F4.6000709-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-09-24 16:45                   ` Cong Wang
2014-09-24 16:45                     ` Cong Wang
     [not found]                     ` <CAHA+R7Ot2kLHb+ne5AW3bFNc87qkFOiEHEyDh9sFrsHqXgrY3g-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-09-25  8:53                       ` Nicolas Dichtel
2014-09-25  8:53                         ` Nicolas Dichtel
     [not found]                         ` <5423D80B.9060500-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-09-26  2:09                           ` Cong Wang
2014-09-26  2:09                             ` Cong Wang
2014-09-26 13:40                             ` Nicolas Dichtel
2014-09-26 13:40                               ` Nicolas Dichtel
     [not found]                               ` <54256CCB.4000709-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-09-26 19:15                                 ` David Ahern
2014-09-26 19:15                                   ` David Ahern
     [not found]                                   ` <5425BB3E.10700-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>
2014-09-26 19:34                                     ` Eric W. Biederman
2014-09-26 19:34                                       ` Eric W. Biederman
2014-09-26 19:34                                       ` Eric W. Biederman
     [not found]                                       ` <87mw9myy4n.fsf-JOvCrm2gF+uungPnsOpG7nhyD016LWXt@public.gmane.org>
2014-09-26 19:44                                         ` David Ahern
2014-09-26 19:44                                           ` David Ahern
     [not found]                                           ` <5425C22F.7050301-Re5JQEeQqe8AvxtiuMwx3w@public.gmane.org>
2014-09-26 20:45                                             ` Eric W. Biederman
2014-09-26 20:45                                             ` Eric W. Biederman
2014-09-26 20:45                                               ` Eric W. Biederman
2014-09-26 20:45                                               ` Eric W. Biederman
     [not found]                                               ` <87tx3uun4q.fsf-JOvCrm2gF+uungPnsOpG7nhyD016LWXt@public.gmane.org>
2014-09-26 20:56                                                 ` David Ahern
2014-09-26 20:56                                                   ` David Ahern
2014-09-26 19:34                                     ` Eric W. Biederman
2014-09-24 16:01           ` Cong Wang
2014-09-23 19:22   ` Cong Wang
2014-09-23 19:26   ` Andy Lutomirski
2014-09-23 19:26     ` Andy Lutomirski
     [not found]     ` <CALCETrWnZtWstBviDxcHpLpjHF3R+sgS48RYf2pbKBYeExZVOQ-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-09-24  9:31       ` Nicolas Dichtel
2014-09-24  9:31         ` Nicolas Dichtel
     [not found]         ` <54228F8B.2030804-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-09-24 17:05           ` Andy Lutomirski
2014-09-24 17:05             ` Andy Lutomirski
     [not found]             ` <CALCETrXMkV_1XR2mXOoO_2_vpB=6cPbWAAOhPFhPbDa_1P+zxw-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-09-25  7:54               ` Nicolas Dichtel
2014-09-25  7:54                 ` Nicolas Dichtel
2014-09-25  7:54               ` Nicolas Dichtel
2014-09-24 17:05           ` Andy Lutomirski
2014-09-26 18:10   ` Eric W. Biederman
2014-09-26 18:10     ` Eric W. Biederman
     [not found]     ` <87ppei45ig.fsf-JOvCrm2gF+uungPnsOpG7nhyD016LWXt@public.gmane.org>
2014-09-26 18:26       ` Andy Lutomirski
2014-09-26 18:26         ` Andy Lutomirski
     [not found]         ` <CALCETrX5e0cp4QFCv1eAqR1hjoROU9Rh=cRos9U35DaR-py3Eg-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-09-26 18:57           ` Eric W. Biederman
2014-09-26 18:57             ` Eric W. Biederman
     [not found]             ` <87y4t61a6v.fsf-JOvCrm2gF+uungPnsOpG7nhyD016LWXt@public.gmane.org>
2014-09-29 12:06               ` Nicolas Dichtel
2014-09-29 12:06             ` Nicolas Dichtel
     [not found]               ` <54294B4E.70501-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-09-29 18:43                 ` Eric W. Biederman
2014-09-29 18:43                   ` Eric W. Biederman
     [not found]                   ` <87y4t2gtd0.fsf-JOvCrm2gF+uungPnsOpG7nhyD016LWXt@public.gmane.org>
2014-10-02 13:46                     ` Nicolas Dichtel
2014-10-02 13:46                       ` Nicolas Dichtel
     [not found]                       ` <542D5726.8070308-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-10-02 13:48                         ` [RFC PATCH net-next v3 0/4] " Nicolas Dichtel
2014-10-02 13:48                           ` Nicolas Dichtel
     [not found]                           ` <1412257690-31253-1-git-send-email-nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-10-02 13:48                             ` [RFC PATCH net-next v3 1/4] netns: add genl cmd to add and get peer netns ids Nicolas Dichtel
2014-10-02 13:48                             ` Nicolas Dichtel
2014-10-02 13:48                               ` Nicolas Dichtel
     [not found]                               ` <1412257690-31253-2-git-send-email-nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-10-02 19:33                                 ` Eric W. Biederman
2014-10-02 19:33                                   ` Eric W. Biederman
     [not found]                                   ` <87tx3mmflp.fsf-JOvCrm2gF+uungPnsOpG7nhyD016LWXt@public.gmane.org>
2014-10-03 12:22                                     ` Nicolas Dichtel
2014-10-03 12:22                                     ` Nicolas Dichtel
2014-10-03 12:22                                       ` Nicolas Dichtel
2014-10-02 13:48                             ` [RFC PATCH net-next v3 2/4] rtnl: add link netns id to interface messages Nicolas Dichtel
2014-10-02 13:48                               ` Nicolas Dichtel
2014-10-02 13:48                             ` [RFC PATCH net-next v3 3/4] iptunnels: advertise link netns via netlink Nicolas Dichtel
2014-10-02 13:48                               ` Nicolas Dichtel
2014-10-02 13:48                             ` [RFC PATCH net-next v3 4/4] rtnl: allow to create device with IFLA_LINK_NETNSID set Nicolas Dichtel
2014-10-02 13:48                               ` Nicolas Dichtel
2014-10-30 15:25                             ` [PATCH net-next v4 0/4] netns: allow to identify peer netns Nicolas Dichtel
2014-10-30 15:25                               ` Nicolas Dichtel
2014-10-30 15:25                               ` [PATCH net-next v4 1/4] netns: add genl cmd to add and get peer netns ids Nicolas Dichtel
     [not found]                                 ` <1414682728-4532-2-git-send-email-nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-10-30 18:35                                   ` Eric W. Biederman [this message]
2014-10-30 18:35                                     ` Eric W. Biederman
     [not found]                                     ` <874mulh0cs.fsf-JOvCrm2gF+uungPnsOpG7nhyD016LWXt@public.gmane.org>
2014-10-31  9:41                                       ` Nicolas Dichtel
2014-10-31  9:41                                         ` Nicolas Dichtel
2014-10-31  9:41                                       ` Nicolas Dichtel
     [not found]                               ` <1414682728-4532-1-git-send-email-nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-10-30 15:25                                 ` Nicolas Dichtel
2014-10-30 15:25                                 ` [PATCH net-next v4 2/4] rtnl: add link netns id to interface messages Nicolas Dichtel
2014-10-30 15:25                                   ` Nicolas Dichtel
2014-10-30 15:25                                 ` [PATCH net-next v4 3/4] iptunnels: advertise link netns via netlink Nicolas Dichtel
2014-10-30 15:25                                   ` Nicolas Dichtel
2014-10-30 15:25                                 ` [PATCH net-next v4 4/4] rtnl: allow to create device with IFLA_LINK_NETNSID set Nicolas Dichtel
2014-10-30 15:25                                   ` Nicolas Dichtel
2014-10-30 18:41                                 ` [PATCH net-next v4 0/4] netns: allow to identify peer netns Eric W. Biederman
2014-10-30 18:41                                   ` Eric W. Biederman
     [not found]                                   ` <871tpph03k.fsf-JOvCrm2gF+uungPnsOpG7nhyD016LWXt@public.gmane.org>
2014-10-31  9:48                                     ` Nicolas Dichtel
2014-10-31  9:48                                     ` Nicolas Dichtel
2014-10-31  9:48                                       ` Nicolas Dichtel
     [not found]                                       ` <54535B00.5090708-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-10-31 19:14                                         ` Eric W. Biederman
2014-10-31 19:14                                           ` Eric W. Biederman
     [not found]                                           ` <87wq7g831b.fsf-JOvCrm2gF+uungPnsOpG7nhyD016LWXt@public.gmane.org>
2014-11-05 14:23                                             ` Nicolas Dichtel
2014-11-05 14:23                                               ` Nicolas Dichtel
     [not found]                                               ` <545A32C4.7070108-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2014-12-04 16:21                                                 ` Nicolas Dichtel
2014-12-04 16:21                                                   ` Nicolas Dichtel
2015-01-15 14:11                                             ` [PATCH net-next v5 " Nicolas Dichtel
2015-01-15 14:11                                           ` Nicolas Dichtel
     [not found]                                             ` <1421331078-21622-1-git-send-email-nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org>
2015-01-15 14:11                                               ` [PATCH net-next v5 1/4] netns: add rtnl cmd to add and get peer netns ids Nicolas Dichtel
2015-01-15 14:11                                               ` [PATCH net-next v5 2/4] rtnl: add link netns id to interface messages Nicolas Dichtel
2015-01-15 14:11                                               ` [PATCH net-next v5 3/4] tunnels: advertise link netns via netlink Nicolas Dichtel
2015-01-15 14:11                                               ` [PATCH net-next v5 4/4] rtnl: allow to create device with IFLA_LINK_NETNSID set Nicolas Dichtel
2015-01-19 19:16                                               ` [PATCH net-next v5 0/4] netns: allow to identify peer netns David Miller
2015-01-19 19:16                                                 ` David Miller
2015-01-19 19:16                                               ` David Miller
2015-01-15 14:11                                             ` [PATCH net-next v5 1/4] netns: add rtnl cmd to add and get peer netns ids Nicolas Dichtel
2015-01-15 14:11                                             ` [PATCH net-next v5 2/4] rtnl: add link netns id to interface messages Nicolas Dichtel
2015-01-15 14:11                                             ` [PATCH net-next v5 3/4] tunnels: advertise link netns via netlink Nicolas Dichtel
2015-01-15 14:11                                             ` [PATCH net-next v5 4/4] rtnl: allow to create device with IFLA_LINK_NETNSID set Nicolas Dichtel
2014-11-01 21:08                                     ` [PATCH net-next v4 0/4] netns: allow to identify peer netns David Miller
2014-11-01 21:08                                     ` David Miller
2014-11-01 21:08                                       ` David Miller
2014-11-24 13:45                                     ` Nicolas Dichtel
2014-11-24 13:45                                       ` Nicolas Dichtel
2014-10-30 15:25                             ` Nicolas Dichtel
2014-10-02 19:20                         ` [RFC PATCH net-next v2 0/5] " Eric W. Biederman
2014-10-02 19:20                           ` Eric W. Biederman
     [not found]                           ` <8761g2nurx.fsf-JOvCrm2gF+uungPnsOpG7nhyD016LWXt@public.gmane.org>
2014-10-02 19:31                             ` Andy Lutomirski
2014-10-02 19:31                               ` Andy Lutomirski
     [not found]                               ` <CALCETrWxqzUF1x+TmW5G4kuHPP+sUtiRaT6dpZ0mQTJ217QB5w-JsoAwUIsXosN+BqQ9rBEUg@public.gmane.org>
2014-10-02 19:45                                 ` Eric W. Biederman
2014-10-02 19:45                                   ` Eric W. Biederman
     [not found]                                   ` <877g0il0gd.fsf-JOvCrm2gF+uungPnsOpG7nhyD016LWXt@public.gmane.org>
2014-10-02 19:48                                     ` Andy Lutomirski
2014-10-02 19:48                                       ` Andy Lutomirski
2014-10-03 12:22                             ` Nicolas Dichtel
2014-10-03 12:22                               ` Nicolas Dichtel
2014-10-03 12:22                             ` Nicolas Dichtel

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=874mulh0cs.fsf@x220.int.ebiederm.org \
    --to=ebiederm-as9lmozglivwk0htik3j/w@public.gmane.org \
    --cc=akpm-de/tnXTf+JLsfHDXvbKv3WD2FQJk+8+b@public.gmane.org \
    --cc=containers-cunTk1MwBs9QetFLy7KEm3xJsTq8ys+cHZ5vskTnxNA@public.gmane.org \
    --cc=cwang-xCSkyg8dI+0RB7SZvlqPiA@public.gmane.org \
    --cc=davem-fT/PcQaiUtIeIZ0/mPfg9Q@public.gmane.org \
    --cc=linux-api-u79uwXL29TY76Z2rM5mHXA@public.gmane.org \
    --cc=linux-kernel-u79uwXL29TY76Z2rM5mHXA@public.gmane.org \
    --cc=luto-kltTT9wpgjJwATOyAt5JVQ@public.gmane.org \
    --cc=netdev-u79uwXL29TY76Z2rM5mHXA@public.gmane.org \
    --cc=nicolas.dichtel-pdR9zngts4EAvxtiuMwx3w@public.gmane.org \
    --cc=stephen-OTpzqLSitTUnbdJkjeBofR2eb7JE58TQ@public.gmane.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.