netdev.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: "Julius R. Volz" <juliusv@google.com>
To: lvs-devel@vger.kernel.org, netdev@vger.kernel.org
Cc: horms@verge.net.au, davem@davemloft.net, vbusam@google.com,
	"Julius R. Volz" <juliusv@google.com>
Subject: [PATCH 18/26] IPVS: Add functions for getting/creating IPv6 connections.
Date: Wed, 11 Jun 2008 19:12:01 +0200	[thread overview]
Message-ID: <1213204329-10973-19-git-send-email-juliusv@google.com> (raw)
In-Reply-To: <1213204329-10973-1-git-send-email-juliusv@google.com>

Add functions for getting/creating IPv6 connections and connection
templates where these diverge significantly from the IPv4 versions.

Signed-off-by: Julius R. Volz <juliusv@google.com>

 2 files changed, 211 insertions(+), 0 deletions(-)

diff --git a/include/net/ip_vs.h b/include/net/ip_vs.h
index d04d5c6..6a58dff 100644
--- a/include/net/ip_vs.h
+++ b/include/net/ip_vs.h
@@ -816,6 +816,19 @@ extern struct ip_vs_conn *ip_vs_ct_in_get
 extern struct ip_vs_conn *ip_vs_conn_out_get
 (int protocol, __be32 s_addr, __be16 s_port, __be32 d_addr, __be16 d_port);
 
+#ifdef CONFIG_IP_VS_IPV6
+extern struct ip_vs_conn *
+ip_vs_conn_in_get_v6(int protocol, const struct in6_addr *s_addr, __be16 s_port,
+		     const struct in6_addr *d_addr, __be16 d_port);
+extern struct ip_vs_conn *
+ip_vs_ct_in_get_v6(int protocol, const struct in6_addr *s_addr, __be16 s_port,
+		   const struct in6_addr *d_addr, __be16 d_port);
+extern struct ip_vs_conn *
+ip_vs_conn_out_get_v6(int protocol, const struct in6_addr *s_addr,
+		      __be16 s_port, const struct in6_addr *d_addr,
+		      __be16 d_port);
+#endif
+
 /* put back the conn without restarting its timer */
 static inline void __ip_vs_conn_put(struct ip_vs_conn *cp)
 {
@@ -828,6 +841,15 @@ extern struct ip_vs_conn *
 ip_vs_conn_new(int proto, __be32 caddr, __be16 cport, __be32 vaddr, __be16 vport,
 	       __be32 daddr, __be16 dport, unsigned flags,
 	       struct ip_vs_dest *dest);
+
+#ifdef CONFIG_IP_VS_IPV6
+extern struct ip_vs_conn *
+ip_vs_conn_new_v6(int proto, const struct in6_addr *caddr, __be16 cport,
+		  const struct in6_addr *vaddr, __be16 vport,
+		  const struct in6_addr *daddr, __be16 dport, unsigned flags,
+		  struct ip_vs_dest *dest);
+#endif
+
 extern void ip_vs_conn_expire_now(struct ip_vs_conn *cp);
 
 extern const char * ip_vs_state_name(__u16 proto, int state);
diff --git a/net/netfilter/ipvs/ip_vs_conn.c b/net/netfilter/ipvs/ip_vs_conn.c
index 4ee5dac..30e1ad2 100644
--- a/net/netfilter/ipvs/ip_vs_conn.c
+++ b/net/netfilter/ipvs/ip_vs_conn.c
@@ -236,6 +236,36 @@ static inline struct ip_vs_conn *__ip_vs_conn_in_get
 	return NULL;
 }
 
+#ifdef CONFIG_IP_VS_IPV6
+static inline struct ip_vs_conn *__ip_vs_conn_in_get_v6
+(int protocol, const struct in6_addr *s_addr, __be16 s_port, const struct in6_addr *d_addr, __be16 d_port)
+{
+	unsigned hash;
+	struct ip_vs_conn *cp;
+
+	hash = ip_vs_conn_hashkey_v6(protocol, s_addr, s_port);
+
+	ct_read_lock(hash);
+
+	list_for_each_entry(cp, &ip_vs_conn_tab[hash], c_list) {
+		if (cp->af == AF_INET6 &&
+		    ipv6_addr_equal(s_addr, &cp->caddr.v6) && s_port==cp->cport &&
+		    ipv6_addr_equal(d_addr, &cp->vaddr.v6) && d_port==cp->vport &&
+		    ((!s_port) ^ (!(cp->flags & IP_VS_CONN_F_NO_CPORT))) &&
+		    protocol==cp->protocol) {
+			/* HIT */
+			atomic_inc(&cp->refcnt);
+			ct_read_unlock(hash);
+			return cp;
+		}
+	}
+
+	ct_read_unlock(hash);
+
+	return NULL;
+}
+#endif
+
 struct ip_vs_conn *ip_vs_conn_in_get
 (int protocol, __be32 s_addr, __be16 s_port, __be32 d_addr, __be16 d_port)
 {
@@ -254,6 +284,26 @@ struct ip_vs_conn *ip_vs_conn_in_get
 	return cp;
 }
 
+#ifdef CONFIG_IP_VS_IPV6
+struct ip_vs_conn *ip_vs_conn_in_get_v6
+(int protocol, const struct in6_addr *s_addr, __be16 s_port, const struct in6_addr *d_addr, __be16 d_port)
+{
+	struct ip_vs_conn *cp;
+
+	cp = __ip_vs_conn_in_get_v6(protocol, s_addr, s_port, d_addr, d_port);
+	if (!cp && atomic_read(&ip_vs_conn_no_cport_cnt))
+		cp = __ip_vs_conn_in_get_v6(protocol, s_addr, 0, d_addr, d_port);
+
+	IP_VS_DBG(9, "lookup/in %s " NIP6_FMT ":%d->" NIP6_FMT ":%d %s\n",
+		  ip_vs_proto_name(protocol),
+		  NIP6(*s_addr), ntohs(s_port),
+		  NIP6(*d_addr), ntohs(d_port),
+		  cp?"hit":"not hit");
+
+	return cp;
+}
+#endif
+
 /* Get reference to connection template */
 struct ip_vs_conn *ip_vs_ct_in_get
 (int protocol, __be32 s_addr, __be16 s_port, __be32 d_addr, __be16 d_port)
@@ -290,6 +340,44 @@ struct ip_vs_conn *ip_vs_ct_in_get
 	return cp;
 }
 
+#ifdef CONFIG_IP_VS_IPV6
+/* Get reference to connection template */
+struct ip_vs_conn *ip_vs_ct_in_get_v6
+(int protocol, const struct in6_addr *s_addr, __be16 s_port, const struct in6_addr *d_addr, __be16 d_port)
+{
+	unsigned hash;
+	struct ip_vs_conn *cp;
+
+	hash = ip_vs_conn_hashkey_v6(protocol, s_addr, s_port);
+
+	ct_read_lock(hash);
+
+	list_for_each_entry(cp, &ip_vs_conn_tab[hash], c_list) {
+		if (cp->af == AF_INET6 &&
+		    ipv6_addr_equal(s_addr, &cp->caddr.v6) && s_port==cp->cport &&
+		    ipv6_addr_equal(d_addr, &cp->vaddr.v6) && d_port==cp->vport &&
+		    cp->flags & IP_VS_CONN_F_TEMPLATE &&
+		    protocol==cp->protocol) {
+			/* HIT */
+			atomic_inc(&cp->refcnt);
+			goto out;
+		}
+	}
+	cp = NULL;
+
+  out:
+	ct_read_unlock(hash);
+
+	IP_VS_DBG(9, "template lookup/in %s " NIP6_FMT ":%d->" NIP6_FMT ":%d %s\n",
+		  ip_vs_proto_name(protocol),
+		  NIP6(*s_addr), ntohs(s_port),
+		  NIP6(*d_addr), ntohs(d_port),
+		  cp?"hit":"not hit");
+
+	return cp;
+}
+#endif
+
 /*
  *  Gets ip_vs_conn associated with supplied parameters in the ip_vs_conn_tab.
  *  Called for pkts coming from inside-to-OUTside.
@@ -332,6 +420,44 @@ struct ip_vs_conn *ip_vs_conn_out_get
 	return ret;
 }
 
+#ifdef CONFIG_IP_VS_IPV6
+struct ip_vs_conn *ip_vs_conn_out_get_v6
+(int protocol, const struct in6_addr *s_addr, __be16 s_port, const struct in6_addr *d_addr, __be16 d_port)
+{
+	unsigned hash;
+	struct ip_vs_conn *cp, *ret=NULL;
+
+	/*
+	 *	Check for "full" addressed entries
+	 */
+	hash = ip_vs_conn_hashkey_v6(protocol, d_addr, d_port);
+
+	ct_read_lock(hash);
+
+	list_for_each_entry(cp, &ip_vs_conn_tab[hash], c_list) {
+		if (cp->af == AF_INET6 &&
+		    ipv6_addr_equal(d_addr, &cp->caddr.v6) && d_port==cp->cport &&
+		    ipv6_addr_equal(s_addr, &cp->daddr.v6) && s_port==cp->dport &&
+		    protocol == cp->protocol) {
+			/* HIT */
+			atomic_inc(&cp->refcnt);
+			ret = cp;
+			break;
+		}
+	}
+
+	ct_read_unlock(hash);
+
+	IP_VS_DBG(9, "lookup/out %s " NIP6_FMT ":%d->" NIP6_FMT ":%d %s\n",
+		  ip_vs_proto_name(protocol),
+		  NIP6(*s_addr), ntohs(s_port),
+		  NIP6(*d_addr), ntohs(d_port),
+		  ret?"hit":"not hit");
+
+	return ret;
+}
+#endif
+
 
 /*
  *      Put back the conn and restart its timer with its timeout
@@ -766,6 +892,69 @@ ip_vs_conn_new(int proto, __be32 caddr, __be16 cport, __be32 vaddr, __be16 vport
 	return cp;
 }
 
+#ifdef CONFIG_IP_VS_IPV6
+struct ip_vs_conn *
+ip_vs_conn_new_v6(int proto, const struct in6_addr *caddr, __be16 cport,
+	          const struct in6_addr *vaddr, __be16 vport,
+	          const struct in6_addr *daddr, __be16 dport, unsigned flags,
+	          struct ip_vs_dest *dest)
+{
+	struct ip_vs_conn *cp;
+	struct ip_vs_protocol *pp = ip_vs_proto_get(proto);
+
+	cp = kmem_cache_zalloc(ip_vs_conn_cachep, GFP_ATOMIC);
+	if (cp == NULL) {
+		IP_VS_ERR_RL("ip_vs_conn_new_v6: no memory available.\n");
+		return NULL;
+	}
+
+	INIT_LIST_HEAD(&cp->c_list);
+	setup_timer(&cp->timer, ip_vs_conn_expire, (unsigned long)cp);
+	cp->af		   = AF_INET6;
+	cp->protocol	   = proto;
+	cp->caddr.v6	   = *caddr;
+	cp->cport	   = cport;
+	cp->vaddr.v6	   = *vaddr;
+	cp->vport	   = vport;
+	cp->daddr.v6	   = *daddr;
+	cp->dport          = dport;
+	cp->flags	   = flags;
+	spin_lock_init(&cp->lock);
+
+	/*
+	 * Set the entry is referenced by the current thread before hashing
+	 * it in the table, so that other thread run ip_vs_random_dropentry
+	 * but cannot drop this entry.
+	 */
+	atomic_set(&cp->refcnt, 1);
+
+	atomic_set(&cp->n_control, 0);
+	atomic_set(&cp->in_pkts, 0);
+
+	atomic_inc(&ip_vs_conn_count);
+	if (flags & IP_VS_CONN_F_NO_CPORT)
+		atomic_inc(&ip_vs_conn_no_cport_cnt);
+
+	/* Bind the connection with a destination server */
+	ip_vs_bind_dest(cp, dest);
+
+	/* Set its state and timeout */
+	cp->state = 0;
+	cp->timeout = 3*HZ;
+
+	/* Bind its packet transmitter */
+	ip_vs_bind_xmit_v6(cp);
+
+	if (unlikely(pp && atomic_read(&pp->appcnt)))
+		ip_vs_bind_app(cp, pp);
+
+	/* Hash it in the ip_vs_conn_tab finally */
+	ip_vs_conn_hash(cp);
+
+	return cp;
+}
+#endif
+
 
 /*
  *	/proc/net/ip_vs_conn entries
-- 
1.5.3.6


  parent reply	other threads:[~2008-06-11 17:12 UTC|newest]

Thread overview: 76+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2008-06-11 17:11 [PATCH 00/26] IPVS: Add first IPv6 support to IPVS Julius R. Volz
2008-06-11 17:11 ` [PATCH 01/26] IPVS: Add CONFIG_IP_VS_IPV6 option for IPv6 support Julius R. Volz
2008-06-11 17:11 ` [PATCH 02/26] IPVS: Change IPVS data structures to support IPv6 addresses Julius R. Volz
2008-06-11 17:12   ` Patrick McHardy
     [not found]     ` <f4845fc0806111041u2a9a197fseefe300ffbbda3c3@mail.gmail.com>
     [not found]       ` <485010E9.6000506@trash.net>
2008-06-11 18:08         ` Julius Volz
2008-06-12  1:54   ` Brian Haley
2008-06-12  9:47     ` Julius Volz
2008-06-11 17:11 ` [PATCH 03/26] IPVS: Use new address family fields in IPVS structs Julius R. Volz
2008-06-11 17:11 ` [PATCH 04/26] IPVS: Add address family specific debugging macros Julius R. Volz
2008-06-11 17:11 ` [PATCH 05/26] IPVS: Use new " Julius R. Volz
2008-06-11 17:14   ` Patrick McHardy
2008-06-11 17:11 ` [PATCH 06/26] IPVS: Add IPv6-specific function pointers to struct ip_vs_protocol Julius R. Volz
2008-06-11 17:11 ` [PATCH 07/26] IPVS: Add IPv6 handler functions to AH protocol handler Julius R. Volz
2008-06-11 17:11 ` [PATCH 08/26] IPVS: Add IPv6 handler functions to ESP " Julius R. Volz
2008-06-11 17:11 ` [PATCH 09/26] IPVS: Add IPv6 handler functions to TCP " Julius R. Volz
2008-06-11 17:11 ` [PATCH 10/26] IPVS: Add IPv6 handler functions to UDP " Julius R. Volz
2008-06-11 17:18   ` Patrick McHardy
2008-06-11 17:11 ` [PATCH 11/26] IPVS: Add supports_ipv6 flag to schedulers Julius R. Volz
2008-06-11 17:11 ` [PATCH 12/26] IPVS: Extend proto handler debug functions to handle IPv6 Julius R. Volz
2008-06-11 17:17   ` Patrick McHardy
2008-06-11 17:11 ` [PATCH 13/26] IPVS: Turn off FTP application helper for IPv6 Julius R. Volz
2008-06-11 17:11 ` [PATCH 14/26] IPVS: Extend xmit routing cache to support IPv6 Julius R. Volz
2008-06-11 17:11 ` [PATCH 15/26] IPVS: Modify IP_VS_XMIT() " Julius R. Volz
2008-06-11 17:11 ` [PATCH 16/26] IPVS: Add IPv6 xmit forwarding functions Julius R. Volz
2008-06-12  1:55   ` Brian Haley
2008-06-11 17:12 ` [PATCH 17/26] IPVS: Add connection hashing function for IPv6 entries Julius R. Volz
2008-06-11 17:12 ` Julius R. Volz [this message]
2008-06-12  1:55   ` [PATCH 18/26] IPVS: Add functions for getting/creating IPv6 connections Brian Haley
2008-06-11 17:12 ` [PATCH 19/26] IPVS: Add scheduling functions for " Julius R. Volz
2008-06-11 17:12 ` [PATCH 20/26] IPVS: Add IPv6 Netfilter hooks and add/modify support functions Julius R. Volz
2008-06-12  1:55   ` Brian Haley
2008-06-11 17:12 ` [PATCH 21/26] IPVS: Make proc/net files output IPv6 entries correctly Julius R. Volz
2008-06-11 17:12 ` [PATCH 22/26] IPVS: Add function to find out if IPv6 address is local Julius R. Volz
2008-06-11 17:12 ` [PATCH 23/26] IPVS: Add hash functions for IPv6 services and real servers Julius R. Volz
2008-06-11 17:12 ` [PATCH 24/26] IPVS: Add IPv6 support to userspace interface Julius R. Volz
2008-06-12  1:55   ` Brian Haley
2008-06-12  9:46     ` Julius Volz
2008-06-11 17:12 ` [PATCH 25/26] IPVS: Add support for IPv6 entry output in procfs files Julius R. Volz
2008-06-11 17:12 ` [PATCH 26/26] IPVS: Add some blame/credits for IPv6 version Julius R. Volz
2008-06-11 17:23 ` [PATCH 00/26] IPVS: Add first IPv6 support to IPVS Patrick McHardy
2008-06-11 18:23   ` Julius Volz
2008-06-11 18:42     ` Patrick McHardy
2008-06-11 19:05       ` Julius Volz
2008-06-11 19:10         ` Patrick McHardy
2008-06-11 19:29           ` Julius Volz
2008-06-11 19:31             ` Patrick McHardy
2008-06-11 19:53               ` Julius Volz
2008-06-11 20:14                 ` Julius Volz
2008-06-11 20:55                   ` Vince Busam
2008-06-11 21:30                     ` Ben Greear
2008-06-11 22:26                       ` Vince Busam
2008-06-12  1:45                         ` Simon Horman
2008-06-12 13:31                           ` Julius Volz
2008-06-12 13:38                             ` Patrick McHardy
2008-06-12 15:34                               ` Julius Volz
2008-06-12 15:41                                 ` Julius Volz
2008-06-12 15:46                                 ` Patrick McHardy
2008-06-12 19:33                                   ` Julius Volz
2008-06-13  6:26                                     ` Simon Horman
2008-06-13 14:17                                       ` Julius Volz
2008-06-13 15:14                                         ` Patrick McHardy
2008-06-16  0:14                                           ` Julius Volz
2008-06-16 11:47                                             ` Patrick McHardy
2008-06-16 12:13                                               ` Julius Volz
2008-06-16 23:19                                               ` Julius Volz
2008-06-17 11:52                                                 ` Patrick McHardy
2008-06-17 17:18                                                   ` Julius Volz
2008-06-17 20:08                                                     ` Patrick McHardy
2008-06-17 22:47                                                       ` Julius Volz
2008-06-18  8:57                                                         ` Patrick McHardy
2008-06-18 14:17                                                           ` Julius Volz
2008-06-18 14:19                                                             ` Patrick McHardy
2008-06-18 14:27                                                               ` Julius Volz
2008-06-18 14:30                                                                 ` Patrick McHardy
2008-06-18 14:36                                                                   ` Julius Volz
2008-06-30 12:01                                               ` Julius Volz

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=1213204329-10973-19-git-send-email-juliusv@google.com \
    --to=juliusv@google.com \
    --cc=davem@davemloft.net \
    --cc=horms@verge.net.au \
    --cc=lvs-devel@vger.kernel.org \
    --cc=netdev@vger.kernel.org \
    --cc=vbusam@google.com \
    /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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).