Quick question.. when you mail out such patches, I presume they go into the
CVS, so if I download the latest snapshot (a day or two later) it will be
included there??

/Christopher Thorjussen

----- Original Message -----
From: "Harald Welte" <[EMAIL PROTECTED]>
To: "David Miller" <[EMAIL PROTECTED]>
Cc: "Netfilter Development Mailinglist" <[EMAIL PROTECTED]>
Sent: Thursday, March 14, 2002 4:12 PM
Subject: [PATCH] netfilter: support DNAT for LOCAL_OUT


> Hi DaveM!
>
> This patch adds support for destination nat on connections initiated by
> local processes.  This is needed in a couple of setups but not supported
> by our current codebase.
>
> Hoever, as it is a little bit expensive to hook the nat table into yet
another
> netfilter hook, we've made it a kernel config option.
>
> Please apply,
>
> diff -Nru --exclude .depend --exclude *.o --exclude *.ver --exclude
.*.flags --exclude *.orig --exclude *.rej --exclude *~
linux-2.4.19-pre3-plain/include/linux/netfilter_ipv4/ip_nat.h
linux-2.4.19-pre3-davem/include/linux/netfilter_ipv4/ip_nat.h
> --- linux-2.4.19-pre3-plain/include/linux/netfilter_ipv4/ip_nat.h Thu Apr
26 00:00:28 2001
> +++ linux-2.4.19-pre3-davem/include/linux/netfilter_ipv4/ip_nat.h Thu Mar
14 17:16:37 2002
> @@ -11,8 +11,13 @@
>   IP_NAT_MANIP_DST
>  };
>
> +#ifndef CONFIG_IP_NF_NAT_LOCAL
>  /* SRC manip occurs only on POST_ROUTING */
>  #define HOOK2MANIP(hooknum) ((hooknum) != NF_IP_POST_ROUTING)
> +#else
> +/* SRC manip occurs POST_ROUTING or LOCAL_IN */
> +#define HOOK2MANIP(hooknum) ((hooknum) != NF_IP_POST_ROUTING && (hooknum)
!= NF_IP_LOCAL_IN)
> +#endif
>
>  /* 2.3.19 (I hope) will define this in linux/netfilter_ipv4.h. */
>  #ifndef SO_ORIGINAL_DST
> diff -Nru --exclude .depend --exclude *.o --exclude *.ver --exclude
.*.flags --exclude *.orig --exclude *.rej --exclude *~
linux-2.4.19-pre3-plain/net/ipv4/netfilter/Config.in
linux-2.4.19-pre3-davem/net/ipv4/netfilter/Config.in
> --- linux-2.4.19-pre3-plain/net/ipv4/netfilter/Config.in Mon Feb 25
20:38:14 2002
> +++ linux-2.4.19-pre3-davem/net/ipv4/netfilter/Config.in Thu Mar 14
17:16:37 2002
> @@ -47,6 +47,7 @@
>        define_bool CONFIG_IP_NF_NAT_NEEDED y
>        dep_tristate '    MASQUERADE target support'
CONFIG_IP_NF_TARGET_MASQUERADE $CONFIG_IP_NF_NAT
>        dep_tristate '    REDIRECT target support'
CONFIG_IP_NF_TARGET_REDIRECT $CONFIG_IP_NF_NAT
> +      bool '    NAT of local connections' CONFIG_IP_NF_NAT_LOCAL
>        if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then
>          dep_tristate '    Basic SNMP-ALG support (EXPERIMENTAL)'
CONFIG_IP_NF_NAT_SNMP_BASIC $CONFIG_IP_NF_NAT
>        fi
> diff -Nru --exclude .depend --exclude *.o --exclude *.ver --exclude
.*.flags --exclude *.orig --exclude *.rej --exclude *~
linux-2.4.19-pre3-plain/net/ipv4/netfilter/ip_nat_core.c
linux-2.4.19-pre3-davem/net/ipv4/netfilter/ip_nat_core.c
> --- linux-2.4.19-pre3-plain/net/ipv4/netfilter/ip_nat_core.c Fri Dec 21
18:42:05 2001
> +++ linux-2.4.19-pre3-davem/net/ipv4/netfilter/ip_nat_core.c Thu Mar 14
17:16:37 2002
> @@ -314,6 +314,7 @@
>   * do_extra_mangle last time. */
>   *other_ipp = saved_ip;
>
> +#ifdef CONFIG_IP_NF_NAT_LOCAL
>   if (hooknum == NF_IP_LOCAL_OUT
>       && *var_ipp != orig_dstip
>       && !do_extra_mangle(*var_ipp, other_ipp)) {
> @@ -324,6 +325,7 @@
>   * anyway. */
>   continue;
>   }
> +#endif
>
>   /* Count how many others map onto this. */
>   score = count_maps(tuple->src.ip, tuple->dst.ip,
> @@ -367,11 +369,13 @@
>   else {
>   /* Only do extra mangle when required (breaks
>                             socket binding) */
> +#ifdef CONFIG_IP_NF_NAT_LOCAL
>   if (tuple->dst.ip != mr->range[0].min_ip
>       && hooknum == NF_IP_LOCAL_OUT
>       && !do_extra_mangle(mr->range[0].min_ip,
>   &tuple->src.ip))
>   return NULL;
> +#endif
>   tuple->dst.ip = mr->range[0].min_ip;
>   }
>   }
> @@ -494,7 +498,10 @@
>  static unsigned int opposite_hook[NF_IP_NUMHOOKS]
>  = { [NF_IP_PRE_ROUTING] = NF_IP_POST_ROUTING,
>      [NF_IP_POST_ROUTING] = NF_IP_PRE_ROUTING,
> -    [NF_IP_LOCAL_OUT] = NF_IP_POST_ROUTING
> +#ifdef CONFIG_IP_NF_NAT_LOCAL
> +    [NF_IP_LOCAL_OUT] = NF_IP_LOCAL_IN,
> +    [NF_IP_LOCAL_IN] = NF_IP_LOCAL_OUT,
> +#endif
>  };
>
>  unsigned int
> diff -Nru --exclude .depend --exclude *.o --exclude *.ver --exclude
.*.flags --exclude *.orig --exclude *.rej --exclude *~
linux-2.4.19-pre3-plain/net/ipv4/netfilter/ip_nat_rule.c
linux-2.4.19-pre3-davem/net/ipv4/netfilter/ip_nat_rule.c
> --- linux-2.4.19-pre3-plain/net/ipv4/netfilter/ip_nat_rule.c Mon Feb 25
20:38:14 2002
> +++ linux-2.4.19-pre3-davem/net/ipv4/netfilter/ip_nat_rule.c Thu Mar 14
17:16:37 2002
> @@ -140,8 +140,12 @@
>   struct ip_conntrack *ct;
>   enum ip_conntrack_info ctinfo;
>
> +#ifdef CONFIG_IP_NF_NAT_LOCAL
>   IP_NF_ASSERT(hooknum == NF_IP_PRE_ROUTING
>        || hooknum == NF_IP_LOCAL_OUT);
> +#else
> + IP_NF_ASSERT(hooknum == NF_IP_PRE_ROUTING);
> +#endif
>
>   ct = ip_conntrack_get(*pskb, &ctinfo);
>
> @@ -210,7 +214,7 @@
>
>   /* Only allow these for NAT. */
>   if (strcmp(tablename, "nat") != 0) {
> - DEBUGP("SNAT: wrong table %s\n", tablename);
> + DEBUGP("DNAT: wrong table %s\n", tablename);
>   return 0;
>   }
>
> @@ -218,6 +222,14 @@
>   DEBUGP("DNAT: hook mask 0x%x bad\n", hook_mask);
>   return 0;
>   }
> +
> +#ifndef CONFIG_IP_NF_NAT_LOCAL
> + if (hook_mask & (1 << NF_IP_LOCAL_OUT)) {
> + DEBUGP("DNAT: CONFIG_IP_NF_NAT_LOCAL not enabled\n");
> + return 0;
> + }
> +#endif
> +
>   return 1;
>  }
>
> diff -Nru --exclude .depend --exclude *.o --exclude *.ver --exclude
.*.flags --exclude *.orig --exclude *.rej --exclude *~
linux-2.4.19-pre3-plain/net/ipv4/netfilter/ip_nat_standalone.c
linux-2.4.19-pre3-davem/net/ipv4/netfilter/ip_nat_standalone.c
> --- linux-2.4.19-pre3-plain/net/ipv4/netfilter/ip_nat_standalone.c Mon Feb
25 20:38:14 2002
> +++ linux-2.4.19-pre3-davem/net/ipv4/netfilter/ip_nat_standalone.c Thu Mar
14 17:16:37 2002
> @@ -41,7 +41,8 @@
>  #define HOOKNAME(hooknum) ((hooknum) == NF_IP_POST_ROUTING ?
"POST_ROUTING"  \
>      : ((hooknum) == NF_IP_PRE_ROUTING ? "PRE_ROUTING" \
>         : ((hooknum) == NF_IP_LOCAL_OUT ? "LOCAL_OUT"  \
> - : "*ERROR*")))
> +          : ((hooknum) == NF_IP_LOCAL_IN ? "LOCAL_IN"  \
> +     : "*ERROR*")))
>
>  static unsigned int
>  ip_nat_fn(unsigned int hooknum,
> @@ -94,6 +95,12 @@
>   }
>   /* Fall thru... (Only ICMPs can be IP_CT_IS_REPLY) */
>   case IP_CT_NEW:
> +#ifdef CONFIG_IP_NF_NAT_LOCAL
> + /* LOCAL_IN hook doesn't have a chain and thus doesn't care
> + * about new packets -HW */
> + if (hooknum == NF_IP_LOCAL_IN)
> + return NF_ACCEPT;
> +#endif
>   info = &ct->nat.info;
>
>   WRITE_LOCK(&ip_nat_lock);
> @@ -204,6 +211,11 @@
>  static struct nf_hook_ops ip_nat_local_out_ops
>  = { { NULL, NULL }, ip_nat_local_fn, PF_INET, NF_IP_LOCAL_OUT,
NF_IP_PRI_NAT_DST };
>
> +#ifdef CONFIG_IP_NF_NAT_LOCAL
> +static struct nf_hook_ops ip_nat_local_in_ops
> += { { NULL, NULL }, ip_nat_fn, PF_INET, NF_IP_LOCAL_IN,
NF_IP_PRI_NAT_SRC };
> +#endif
> +
>  /* Protocol registration. */
>  int ip_nat_protocol_register(struct ip_nat_protocol *proto)
>  {
> @@ -272,6 +284,13 @@
>   printk("ip_nat_init: can't register local out hook.\n");
>   goto cleanup_outops;
>   }
> +#ifdef CONFIG_IP_NF_NAT_LOCAL
> + ret = nf_register_hook(&ip_nat_local_in_ops);
> + if (ret < 0) {
> + printk("ip_nat_init: can't register local in hook.\n");
> + goto cleanup_localoutops;
> + }
> +#endif
>   if (ip_conntrack_module)
>   __MOD_INC_USE_COUNT(ip_conntrack_module);
>   return ret;
> @@ -279,6 +298,10 @@
>   cleanup:
>   if (ip_conntrack_module)
>   __MOD_DEC_USE_COUNT(ip_conntrack_module);
> +#ifdef CONFIG_IP_NF_NAT_LOCAL
> + nf_unregister_hook(&ip_nat_local_in_ops);
> + cleanup_localoutops:
> +#endif
>   nf_unregister_hook(&ip_nat_local_out_ops);
>   cleanup_outops:
>   nf_unregister_hook(&ip_nat_out_ops);
> --
> Live long and prosper
> - Harald Welte / [EMAIL PROTECTED]
http://www.gnumonks.org/
>
============================================================================
> GCS/E/IT d- s-: a-- C+++ UL++++$ P+++ L++++$ E--- W- N++ o? K- w--- O- M+
> V-- PS++ PE-- Y++ PGP++ t+ 5-- !X !R tv-- b+++ !DI !D G+ e* h--- r++ y+(*)
>
>



Reply via email to