From patchwork Mon Nov 16 15:06:45 2015 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Andreas Schultz X-Patchwork-Id: 545055 X-Patchwork-Delegate: pablo@netfilter.org Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from lists.osmocom.org (tmp.osmocom.org [144.76.43.76]) by ozlabs.org (Postfix) with ESMTP id 5A74914144D for ; Tue, 17 Nov 2015 02:07:10 +1100 (AEDT) Received: from lists.osmocom.org (lists.osmocom.org [144.76.43.76]) by lists.osmocom.org (Postfix) with ESMTP id 236AF9BE5; Mon, 16 Nov 2015 15:07:09 +0000 (UTC) X-Original-To: openbsc@lists.osmocom.org Delivered-To: openbsc@lists.osmocom.org Received: from mail.tpip.net (mail.tpip.net [92.43.49.48]) by lists.osmocom.org (Postfix) with ESMTP id 6BE469BC3 for ; Mon, 16 Nov 2015 15:07:06 +0000 (UTC) Received: from office.tpip.net (office.tpip.net [92.43.51.2]) (using TLSv1 with cipher ADH-AES256-SHA (256/256 bits)) (No client certificate requested) by mail.tpip.net (Postfix) with ESMTPS id 0AF9C4F418; Mon, 16 Nov 2015 15:07:05 +0000 (UTC) Received: from localhost (localhost [127.0.0.1]) by office.tpip.net (Postfix) with ESMTP id 49B0AA2CAB; Mon, 16 Nov 2015 16:07:06 +0100 (CET) Received: from office.tpip.net ([127.0.0.1]) by localhost (office.tpip.net [127.0.0.1]) (amavisd-new, port 10032) with ESMTP id WIdANa7JjKF5; Mon, 16 Nov 2015 16:07:05 +0100 (CET) Received: from localhost (localhost [127.0.0.1]) by office.tpip.net (Postfix) with ESMTP id CE853A2CA8; Mon, 16 Nov 2015 16:07:05 +0100 (CET) X-Virus-Scanned: amavisd-new at tpip.net Received: from office.tpip.net ([127.0.0.1]) by localhost (office.tpip.net [127.0.0.1]) (amavisd-new, port 10026) with ESMTP id SIAFu3u5cHcU; Mon, 16 Nov 2015 16:07:05 +0100 (CET) Received: from alice.tpip.org (unknown [192.168.13.53]) by office.tpip.net (Postfix) with ESMTPSA id 70EADA2C9A; Mon, 16 Nov 2015 16:07:05 +0100 (CET) From: Andreas Schultz To: openbsc@lists.osmocom.org Subject: [PATCH 04/16] gtp: select netns based on NL attribute Date: Mon, 16 Nov 2015 16:06:45 +0100 Message-Id: <1447686417-3979-5-git-send-email-aschultz@tpip.net> X-Mailer: git-send-email 2.5.0 In-Reply-To: <1447686417-3979-1-git-send-email-aschultz@tpip.net> References: <1447686417-3979-1-git-send-email-aschultz@tpip.net> X-BeenThere: openbsc@lists.osmocom.org X-Mailman-Version: 2.1.20 Precedence: list List-Id: Development of the OpenBSC GSM base station controller List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Pablo Neira Ayuso Errors-To: openbsc-bounces@lists.osmocom.org Sender: "OpenBSC" This permits a split namespace setup where the GTP transport sockets are in one namespace the gtp tunnel interface is in another namespace. The target namespece is selected by the new GTPA_NET_NS_FD NL attributes. It fall back to the netns of the GTP-U sockets if the NL attr is not present. Signed-off-by: Andreas Schultz --- gtp.c | 41 +++++++++++++++++++++++++++++++++++++---- gtp_nl.h | 1 + 2 files changed, 38 insertions(+), 4 deletions(-) diff --git a/gtp.c b/gtp.c index 7c61e61..11f8fad 100644 --- a/gtp.c +++ b/gtp.c @@ -330,6 +330,8 @@ static int gtp_udp_encap_recv(struct sock *sk, struct sk_buff *skb) if (!gti) goto user; + netdev_dbg(gti->dev, "encap_recv %p\n", sk); + switch (udp_sk(sk)->encap_type) { case UDP_ENCAP_GTP0: netdev_dbg(gti->dev, "received GTP0 packet\n"); @@ -738,7 +740,7 @@ static int gtp_encap_enable(struct net_device *dev, struct gtp_instance *gti, static int gtp_newlink(struct net *src_net, struct net_device *dev, struct nlattr *tb[], struct nlattr *data[]) { - struct gtp_net *gn = net_generic(src_net, gtp_net_id); + struct gtp_net *gn; struct net_device *real_dev; struct gtp_instance *gti; int hashsize, err, fd0, fd1; @@ -778,6 +780,7 @@ static int gtp_newlink(struct net *src_net, struct net_device *dev, if (err < 0) goto err1; + gn = net_generic(dev_net(dev), gtp_net_id); list_add_rcu(>i->list, &gn->gtp_instance_list); netdev_dbg(dev, "registered new interface\n"); @@ -845,6 +848,19 @@ static struct rtnl_link_ops gtp_link_ops __read_mostly = { .fill_info = gtp_fill_info, }; +static struct net *gtp_genl_get_net(struct net *src_net, struct nlattr *tb[]) +{ + struct net *net; + /* Examine the link attributes and figure out which + * network namespace we are talking about. + */ + if (tb[GTPA_NET_NS_FD]) + net = get_net_ns_by_fd(nla_get_u32(tb[GTPA_NET_NS_FD])); + else + net = get_net(src_net); + return net; +} + static int gtp_hashtable_new(struct gtp_instance *gti, int hsize) { int i; @@ -893,6 +909,8 @@ static int gtp_encap_enable(struct net_device *dev, struct gtp_instance *gti, struct socket *sock0, *sock1u; struct sock *sk; + netdev_dbg(dev, "enable gtp on %d, %d\n", fd_gtp0, fd_gtp1); + sock0 = sockfd_lookup(fd_gtp0, &err); if (sock0 == NULL) { netdev_dbg(dev, "socket fd=%d not found (gtp0)\n", fd_gtp0); @@ -918,6 +936,8 @@ static int gtp_encap_enable(struct net_device *dev, struct gtp_instance *gti, goto err2; } + netdev_dbg(dev, "enable gtp on %p, %p\n", sock0, sock1u); + gti->sock0 = sock0; gti->sock1u = sock1u; @@ -1059,7 +1079,7 @@ static int ipv4_pdp_add(struct net_device *dev, struct genl_info *info) static int gtp_genl_tunnel_new(struct sk_buff *skb, struct genl_info *info) { - struct net *net = sock_net(skb->sk); + struct net *net; struct net_device *dev; if (!info->attrs[GTPA_VERSION] || @@ -1069,6 +1089,10 @@ static int gtp_genl_tunnel_new(struct sk_buff *skb, struct genl_info *info) !info->attrs[GTPA_TID]) return -EINVAL; + net = gtp_genl_get_net(sock_net(skb->sk), info->attrs); + if (net == NULL) + return -EINVAL; + /* Check if there's an existing gtpX device to configure */ dev = gtp_find_dev(net, nla_get_u32(info->attrs[GTPA_LINK])); if (dev == NULL) @@ -1079,7 +1103,7 @@ static int gtp_genl_tunnel_new(struct sk_buff *skb, struct genl_info *info) static int gtp_genl_tunnel_delete(struct sk_buff *skb, struct genl_info *info) { - struct net *net = sock_net(skb->sk); + struct net *net; struct gtp_instance *gti; struct net_device *dev; struct pdp_ctx *pctx; @@ -1107,6 +1131,10 @@ static int gtp_genl_tunnel_delete(struct sk_buff *skb, struct genl_info *info) if (gtp_version == GTP_V1 && tid > UINT_MAX) return -EINVAL; + net = gtp_genl_get_net(sock_net(skb->sk), info->attrs); + if (net == NULL) + return -EINVAL; + /* Check if there's an existing gtpX device to configure */ dev = gtp_find_dev(net, nla_get_u32(info->attrs[GTPA_LINK])); if (dev == NULL) @@ -1175,7 +1203,7 @@ nla_put_failure: static int gtp_genl_tunnel_get(struct sk_buff *skb, struct genl_info *info) { - struct net *net = sock_net(skb->sk); + struct net *net; struct net_device *dev; struct gtp_instance *gti; struct pdp_ctx *pctx = NULL; @@ -1196,6 +1224,10 @@ static int gtp_genl_tunnel_get(struct sk_buff *skb, struct genl_info *info) return -EINVAL; } + net = gtp_genl_get_net(sock_net(skb->sk), info->attrs); + if (net == NULL) + return -EINVAL; + /* Check if there's an existing gtpX device to configure */ dev = gtp_find_dev(net, nla_get_u32(info->attrs[GTPA_LINK])); if (dev == NULL) @@ -1304,6 +1336,7 @@ static struct nla_policy gtp_genl_policy[GTPA_MAX + 1] = { [GTPA_SGSN_ADDRESS] = { .type = NLA_NESTED, }, [GTPA_MS_ADDRESS] = { .type = NLA_NESTED, }, [GTPA_FLOW] = { .type = NLA_U16, }, + [GTPA_NET_NS_FD] = { .type = NLA_U32, }, }; static const struct genl_ops gtp_genl_ops[] = { diff --git a/gtp_nl.h b/gtp_nl.h index 7bdd2f5..c20666d 100644 --- a/gtp_nl.h +++ b/gtp_nl.h @@ -40,6 +40,7 @@ enum gtp_attrs { GTPA_SGSN_ADDRESS, GTPA_MS_ADDRESS, GTPA_FLOW, + GTPA_NET_NS_FD, __GTPA_MAX, }; #define GTPA_MAX (__GTPA_MAX + 1)