Browse Source

netfilter: combine IPv4 and IPv6 nf_nat_redirect code in one module

This resolves linking problems with CONFIG_IPV6=n:

net/built-in.o: In function `redirect_tg6':
xt_REDIRECT.c:(.text+0x6d021): undefined reference to `nf_nat_redirect_ipv6'

Reported-by: Andreas Ruprecht <rupran@einserver.de>
Reported-by: Or Gerlitz <ogerlitz@mellanox.com>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>
Pablo Neira Ayuso 10 years ago
parent
commit
b59eaf9e28

+ 0 - 9
include/net/netfilter/ipv4/nf_nat_redirect.h

@@ -1,9 +0,0 @@
-#ifndef _NF_NAT_REDIRECT_IPV4_H_
-#define _NF_NAT_REDIRECT_IPV4_H_
-
-unsigned int
-nf_nat_redirect_ipv4(struct sk_buff *skb,
-		     const struct nf_nat_ipv4_multi_range_compat *mr,
-		     unsigned int hooknum);
-
-#endif /* _NF_NAT_REDIRECT_IPV4_H_ */

+ 0 - 8
include/net/netfilter/ipv6/nf_nat_redirect.h

@@ -1,8 +0,0 @@
-#ifndef _NF_NAT_REDIRECT_IPV6_H_
-#define _NF_NAT_REDIRECT_IPV6_H_
-
-unsigned int
-nf_nat_redirect_ipv6(struct sk_buff *skb, const struct nf_nat_range *range,
-		     unsigned int hooknum);
-
-#endif /* _NF_NAT_REDIRECT_IPV6_H_ */

+ 12 - 0
include/net/netfilter/nf_nat_redirect.h

@@ -0,0 +1,12 @@
+#ifndef _NF_NAT_REDIRECT_H_
+#define _NF_NAT_REDIRECT_H_
+
+unsigned int
+nf_nat_redirect_ipv4(struct sk_buff *skb,
+		     const struct nf_nat_ipv4_multi_range_compat *mr,
+		     unsigned int hooknum);
+unsigned int
+nf_nat_redirect_ipv6(struct sk_buff *skb, const struct nf_nat_range *range,
+		     unsigned int hooknum);
+
+#endif /* _NF_NAT_REDIRECT_H_ */

+ 1 - 7
net/ipv4/netfilter/Kconfig

@@ -104,12 +104,6 @@ config NF_NAT_MASQUERADE_IPV4
 	  This is the kernel functionality to provide NAT in the masquerade
 	  This is the kernel functionality to provide NAT in the masquerade
 	  flavour (automatic source address selection).
 	  flavour (automatic source address selection).
 
 
-config NF_NAT_REDIRECT_IPV4
-	tristate "IPv4 redirect support"
-	help
-	  This is the kernel functionality to provide NAT in the redirect
-	  flavour (redirect packets to local machine).
-
 config NFT_MASQ_IPV4
 config NFT_MASQ_IPV4
 	tristate "IPv4 masquerading support for nf_tables"
 	tristate "IPv4 masquerading support for nf_tables"
 	depends on NF_TABLES_IPV4
 	depends on NF_TABLES_IPV4
@@ -123,7 +117,7 @@ config NFT_REDIR_IPV4
 	tristate "IPv4 redirect support for nf_tables"
 	tristate "IPv4 redirect support for nf_tables"
 	depends on NF_TABLES_IPV4
 	depends on NF_TABLES_IPV4
 	depends on NFT_REDIR
 	depends on NFT_REDIR
-	select NF_NAT_REDIRECT_IPV4
+	select NF_NAT_REDIRECT
 	help
 	help
 	  This is the expression that provides IPv4 redirect support for
 	  This is the expression that provides IPv4 redirect support for
 	  nf_tables.
 	  nf_tables.

+ 0 - 1
net/ipv4/netfilter/Makefile

@@ -31,7 +31,6 @@ obj-$(CONFIG_NF_NAT_H323) += nf_nat_h323.o
 obj-$(CONFIG_NF_NAT_PPTP) += nf_nat_pptp.o
 obj-$(CONFIG_NF_NAT_PPTP) += nf_nat_pptp.o
 obj-$(CONFIG_NF_NAT_SNMP_BASIC) += nf_nat_snmp_basic.o
 obj-$(CONFIG_NF_NAT_SNMP_BASIC) += nf_nat_snmp_basic.o
 obj-$(CONFIG_NF_NAT_MASQUERADE_IPV4) += nf_nat_masquerade_ipv4.o
 obj-$(CONFIG_NF_NAT_MASQUERADE_IPV4) += nf_nat_masquerade_ipv4.o
-obj-$(CONFIG_NF_NAT_REDIRECT_IPV4) += nf_nat_redirect_ipv4.o
 
 
 # NAT protocols (nf_nat)
 # NAT protocols (nf_nat)
 obj-$(CONFIG_NF_NAT_PROTO_GRE) += nf_nat_proto_gre.o
 obj-$(CONFIG_NF_NAT_PROTO_GRE) += nf_nat_proto_gre.o

+ 1 - 1
net/ipv4/netfilter/nft_redir_ipv4.c

@@ -14,7 +14,7 @@
 #include <linux/netfilter/nf_tables.h>
 #include <linux/netfilter/nf_tables.h>
 #include <net/netfilter/nf_tables.h>
 #include <net/netfilter/nf_tables.h>
 #include <net/netfilter/nf_nat.h>
 #include <net/netfilter/nf_nat.h>
-#include <net/netfilter/ipv4/nf_nat_redirect.h>
+#include <net/netfilter/nf_nat_redirect.h>
 #include <net/netfilter/nft_redir.h>
 #include <net/netfilter/nft_redir.h>
 
 
 static void nft_redir_ipv4_eval(const struct nft_expr *expr,
 static void nft_redir_ipv4_eval(const struct nft_expr *expr,

+ 1 - 7
net/ipv6/netfilter/Kconfig

@@ -82,12 +82,6 @@ config NF_NAT_MASQUERADE_IPV6
 	  This is the kernel functionality to provide NAT in the masquerade
 	  This is the kernel functionality to provide NAT in the masquerade
 	  flavour (automatic source address selection) for IPv6.
 	  flavour (automatic source address selection) for IPv6.
 
 
-config NF_NAT_REDIRECT_IPV6
-	tristate "IPv6 redirect support"
-	help
-	  This is the kernel functionality to provide NAT in the redirect
-	  flavour (redirect packet to local machine) for IPv6.
-
 config NFT_MASQ_IPV6
 config NFT_MASQ_IPV6
 	tristate "IPv6 masquerade support for nf_tables"
 	tristate "IPv6 masquerade support for nf_tables"
 	depends on NF_TABLES_IPV6
 	depends on NF_TABLES_IPV6
@@ -101,7 +95,7 @@ config NFT_REDIR_IPV6
 	tristate "IPv6 redirect support for nf_tables"
 	tristate "IPv6 redirect support for nf_tables"
 	depends on NF_TABLES_IPV6
 	depends on NF_TABLES_IPV6
 	depends on NFT_REDIR
 	depends on NFT_REDIR
-	select NF_NAT_REDIRECT_IPV6
+	select NF_NAT_REDIRECT
 	help
 	help
 	  This is the expression that provides IPv4 redirect support for
 	  This is the expression that provides IPv4 redirect support for
 	  nf_tables.
 	  nf_tables.

+ 0 - 1
net/ipv6/netfilter/Makefile

@@ -19,7 +19,6 @@ obj-$(CONFIG_NF_CONNTRACK_IPV6) += nf_conntrack_ipv6.o
 nf_nat_ipv6-y		:= nf_nat_l3proto_ipv6.o nf_nat_proto_icmpv6.o
 nf_nat_ipv6-y		:= nf_nat_l3proto_ipv6.o nf_nat_proto_icmpv6.o
 obj-$(CONFIG_NF_NAT_IPV6) += nf_nat_ipv6.o
 obj-$(CONFIG_NF_NAT_IPV6) += nf_nat_ipv6.o
 obj-$(CONFIG_NF_NAT_MASQUERADE_IPV6) += nf_nat_masquerade_ipv6.o
 obj-$(CONFIG_NF_NAT_MASQUERADE_IPV6) += nf_nat_masquerade_ipv6.o
-obj-$(CONFIG_NF_NAT_REDIRECT_IPV6) += nf_nat_redirect_ipv6.o
 
 
 # defrag
 # defrag
 nf_defrag_ipv6-y := nf_defrag_ipv6_hooks.o nf_conntrack_reasm.o
 nf_defrag_ipv6-y := nf_defrag_ipv6_hooks.o nf_conntrack_reasm.o

+ 0 - 75
net/ipv6/netfilter/nf_nat_redirect_ipv6.c

@@ -1,75 +0,0 @@
-/*
- * (C) 1999-2001 Paul `Rusty' Russell
- * (C) 2002-2006 Netfilter Core Team <coreteam@netfilter.org>
- * Copyright (c) 2011 Patrick McHardy <kaber@trash.net>
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation.
- *
- * Based on Rusty Russell's IPv4 REDIRECT target. Development of IPv6
- * NAT funded by Astaro.
- */
-
-#include <linux/if.h>
-#include <linux/inetdevice.h>
-#include <linux/ip.h>
-#include <linux/kernel.h>
-#include <linux/module.h>
-#include <linux/netdevice.h>
-#include <linux/netfilter.h>
-#include <linux/types.h>
-#include <linux/netfilter_ipv6.h>
-#include <linux/netfilter/x_tables.h>
-#include <net/addrconf.h>
-#include <net/checksum.h>
-#include <net/protocol.h>
-#include <net/netfilter/nf_nat.h>
-#include <net/netfilter/ipv6/nf_nat_redirect.h>
-
-static const struct in6_addr loopback_addr = IN6ADDR_LOOPBACK_INIT;
-
-unsigned int
-nf_nat_redirect_ipv6(struct sk_buff *skb, const struct nf_nat_range *range,
-		     unsigned int hooknum)
-{
-	struct nf_nat_range newrange;
-	struct in6_addr newdst;
-	enum ip_conntrack_info ctinfo;
-	struct nf_conn *ct;
-
-	ct = nf_ct_get(skb, &ctinfo);
-	if (hooknum == NF_INET_LOCAL_OUT) {
-		newdst = loopback_addr;
-	} else {
-		struct inet6_dev *idev;
-		struct inet6_ifaddr *ifa;
-		bool addr = false;
-
-		rcu_read_lock();
-		idev = __in6_dev_get(skb->dev);
-		if (idev != NULL) {
-			list_for_each_entry(ifa, &idev->addr_list, if_list) {
-				newdst = ifa->addr;
-				addr = true;
-				break;
-			}
-		}
-		rcu_read_unlock();
-
-		if (!addr)
-			return NF_DROP;
-	}
-
-	newrange.flags		= range->flags | NF_NAT_RANGE_MAP_IPS;
-	newrange.min_addr.in6	= newdst;
-	newrange.max_addr.in6	= newdst;
-	newrange.min_proto	= range->min_proto;
-	newrange.max_proto	= range->max_proto;
-
-	return nf_nat_setup_info(ct, &newrange, NF_NAT_MANIP_DST);
-}
-EXPORT_SYMBOL_GPL(nf_nat_redirect_ipv6);
-
-MODULE_LICENSE("GPL");
-MODULE_AUTHOR("Patrick McHardy <kaber@trash.net>");

+ 1 - 1
net/ipv6/netfilter/nft_redir_ipv6.c

@@ -15,7 +15,7 @@
 #include <net/netfilter/nf_tables.h>
 #include <net/netfilter/nf_tables.h>
 #include <net/netfilter/nf_nat.h>
 #include <net/netfilter/nf_nat.h>
 #include <net/netfilter/nft_redir.h>
 #include <net/netfilter/nft_redir.h>
-#include <net/netfilter/ipv6/nf_nat_redirect.h>
+#include <net/netfilter/nf_nat_redirect.h>
 
 
 static void nft_redir_ipv6_eval(const struct nft_expr *expr,
 static void nft_redir_ipv6_eval(const struct nft_expr *expr,
 				struct nft_data data[NFT_REG_MAX + 1],
 				struct nft_data data[NFT_REG_MAX + 1],

+ 8 - 2
net/netfilter/Kconfig

@@ -411,6 +411,13 @@ config NF_NAT_TFTP
 	depends on NF_CONNTRACK && NF_NAT
 	depends on NF_CONNTRACK && NF_NAT
 	default NF_NAT && NF_CONNTRACK_TFTP
 	default NF_NAT && NF_CONNTRACK_TFTP
 
 
+config NF_NAT_REDIRECT
+        tristate "IPv4/IPv6 redirect support"
+	depends on NF_NAT
+        help
+          This is the kernel functionality to redirect packets to local
+          machine through NAT.
+
 config NETFILTER_SYNPROXY
 config NETFILTER_SYNPROXY
 	tristate
 	tristate
 
 
@@ -844,8 +851,7 @@ config NETFILTER_XT_TARGET_RATEEST
 config NETFILTER_XT_TARGET_REDIRECT
 config NETFILTER_XT_TARGET_REDIRECT
 	tristate "REDIRECT target support"
 	tristate "REDIRECT target support"
 	depends on NF_NAT
 	depends on NF_NAT
-	select NF_NAT_REDIRECT_IPV4 if NF_NAT_IPV4
-	select NF_NAT_REDIRECT_IPV6 if NF_NAT_IPV6
+	select NF_NAT_REDIRECT
 	---help---
 	---help---
 	REDIRECT is a special case of NAT: all incoming connections are
 	REDIRECT is a special case of NAT: all incoming connections are
 	mapped onto the incoming interface's address, causing the packets to
 	mapped onto the incoming interface's address, causing the packets to

+ 1 - 0
net/netfilter/Makefile

@@ -51,6 +51,7 @@ nf_nat-y	:= nf_nat_core.o nf_nat_proto_unknown.o nf_nat_proto_common.o \
 obj-$(CONFIG_NF_LOG_COMMON) += nf_log_common.o
 obj-$(CONFIG_NF_LOG_COMMON) += nf_log_common.o
 
 
 obj-$(CONFIG_NF_NAT) += nf_nat.o
 obj-$(CONFIG_NF_NAT) += nf_nat.o
+obj-$(CONFIG_NF_NAT_REDIRECT) += nf_nat_redirect.o
 
 
 # NAT protocols (nf_nat)
 # NAT protocols (nf_nat)
 obj-$(CONFIG_NF_NAT_PROTO_DCCP) += nf_nat_proto_dccp.o
 obj-$(CONFIG_NF_NAT_PROTO_DCCP) += nf_nat_proto_dccp.o

+ 46 - 1
net/ipv4/netfilter/nf_nat_redirect_ipv4.c → net/netfilter/nf_nat_redirect.c

@@ -20,12 +20,13 @@
 #include <linux/netfilter.h>
 #include <linux/netfilter.h>
 #include <linux/types.h>
 #include <linux/types.h>
 #include <linux/netfilter_ipv4.h>
 #include <linux/netfilter_ipv4.h>
+#include <linux/netfilter_ipv6.h>
 #include <linux/netfilter/x_tables.h>
 #include <linux/netfilter/x_tables.h>
 #include <net/addrconf.h>
 #include <net/addrconf.h>
 #include <net/checksum.h>
 #include <net/checksum.h>
 #include <net/protocol.h>
 #include <net/protocol.h>
 #include <net/netfilter/nf_nat.h>
 #include <net/netfilter/nf_nat.h>
-#include <net/netfilter/ipv4/nf_nat_redirect.h>
+#include <net/netfilter/nf_nat_redirect.h>
 
 
 unsigned int
 unsigned int
 nf_nat_redirect_ipv4(struct sk_buff *skb,
 nf_nat_redirect_ipv4(struct sk_buff *skb,
@@ -78,5 +79,49 @@ nf_nat_redirect_ipv4(struct sk_buff *skb,
 }
 }
 EXPORT_SYMBOL_GPL(nf_nat_redirect_ipv4);
 EXPORT_SYMBOL_GPL(nf_nat_redirect_ipv4);
 
 
+static const struct in6_addr loopback_addr = IN6ADDR_LOOPBACK_INIT;
+
+unsigned int
+nf_nat_redirect_ipv6(struct sk_buff *skb, const struct nf_nat_range *range,
+		     unsigned int hooknum)
+{
+	struct nf_nat_range newrange;
+	struct in6_addr newdst;
+	enum ip_conntrack_info ctinfo;
+	struct nf_conn *ct;
+
+	ct = nf_ct_get(skb, &ctinfo);
+	if (hooknum == NF_INET_LOCAL_OUT) {
+		newdst = loopback_addr;
+	} else {
+		struct inet6_dev *idev;
+		struct inet6_ifaddr *ifa;
+		bool addr = false;
+
+		rcu_read_lock();
+		idev = __in6_dev_get(skb->dev);
+		if (idev != NULL) {
+			list_for_each_entry(ifa, &idev->addr_list, if_list) {
+				newdst = ifa->addr;
+				addr = true;
+				break;
+			}
+		}
+		rcu_read_unlock();
+
+		if (!addr)
+			return NF_DROP;
+	}
+
+	newrange.flags		= range->flags | NF_NAT_RANGE_MAP_IPS;
+	newrange.min_addr.in6	= newdst;
+	newrange.max_addr.in6	= newdst;
+	newrange.min_proto	= range->min_proto;
+	newrange.max_proto	= range->max_proto;
+
+	return nf_nat_setup_info(ct, &newrange, NF_NAT_MANIP_DST);
+}
+EXPORT_SYMBOL_GPL(nf_nat_redirect_ipv6);
+
 MODULE_LICENSE("GPL");
 MODULE_LICENSE("GPL");
 MODULE_AUTHOR("Patrick McHardy <kaber@trash.net>");
 MODULE_AUTHOR("Patrick McHardy <kaber@trash.net>");

+ 1 - 2
net/netfilter/xt_REDIRECT.c

@@ -26,8 +26,7 @@
 #include <net/checksum.h>
 #include <net/checksum.h>
 #include <net/protocol.h>
 #include <net/protocol.h>
 #include <net/netfilter/nf_nat.h>
 #include <net/netfilter/nf_nat.h>
-#include <net/netfilter/ipv4/nf_nat_redirect.h>
-#include <net/netfilter/ipv6/nf_nat_redirect.h>
+#include <net/netfilter/nf_nat_redirect.h>
 
 
 static unsigned int
 static unsigned int
 redirect_tg6(struct sk_buff *skb, const struct xt_action_param *par)
 redirect_tg6(struct sk_buff *skb, const struct xt_action_param *par)