Module Name:    src
Committed By:   tsutsui
Date:           Sat Apr 18 11:19:09 UTC 2009

Modified Files:
        src/sys/dist/ipf/netinet: ip_nat.c

Log Message:
Pull a fix for ipnat from upstream as per info from darrenr@:
 2031730 4.1.31 Nat drops fragmented packets after the first
 
http://ipfilter.cvs.sourceforge.net/viewvc/ipfilter/ipfilter/ip_nat.c#rev1.2.2.48

Fixes problems on UDP NFS with ipnat as mentioned in PR kern/38773 and
PR kern/41074.  Tested on several slow NFS clients and an i386 server
running ipnat.

Should be pulled up to 5.0.


To generate a diff of this commit:
cvs rdiff -u -r1.38 -r1.39 src/sys/dist/ipf/netinet/ip_nat.c

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/dist/ipf/netinet/ip_nat.c
diff -u src/sys/dist/ipf/netinet/ip_nat.c:1.38 src/sys/dist/ipf/netinet/ip_nat.c:1.39
--- src/sys/dist/ipf/netinet/ip_nat.c:1.38	Sat Jul 26 19:44:28 2008
+++ src/sys/dist/ipf/netinet/ip_nat.c	Sat Apr 18 11:19:09 2009
@@ -1,4 +1,4 @@
-/*	$NetBSD: ip_nat.c,v 1.38 2008/07/26 19:44:28 darrenr Exp $	*/
+/*	$NetBSD: ip_nat.c,v 1.39 2009/04/18 11:19:09 tsutsui Exp $	*/
 
 /*
  * Copyright (C) 1995-2003 by Darren Reed.
@@ -118,10 +118,10 @@
 #if !defined(lint)
 #if defined(__NetBSD__)
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: ip_nat.c,v 1.38 2008/07/26 19:44:28 darrenr Exp $");
+__KERNEL_RCSID(0, "$NetBSD: ip_nat.c,v 1.39 2009/04/18 11:19:09 tsutsui Exp $");
 #else
 static const char sccsid[] = "@(#)ip_nat.c	1.11 6/5/96 (C) 1995 Darren Reed";
-static const char rcsid[] = "@(#)$Id: ip_nat.c,v 1.38 2008/07/26 19:44:28 darrenr Exp $";
+static const char rcsid[] = "@(#)$Id: ip_nat.c,v 1.39 2009/04/18 11:19:09 tsutsui Exp $";
 #endif
 #endif
 
@@ -3834,25 +3834,21 @@
 	else if ((nat = nat_outlookup(fin, nflags|NAT_SEARCH, (u_int)fin->fin_p,
 				      fin->fin_src, fin->fin_dst))) {
 		nflags = nat->nat_flags;
-	} else {
+	} else if (fin->fin_off == 0) {
 		u_32_t hv, msk, nmsk;
 
+		msk = 0xffffffff;
+		nmsk = nat_masks;
 		/*
 		 * If there is no current entry in the nat table for this IP#,
 		 * create one for it (if there is a matching rule).
 		 */
-		if ((fin->fin_off != 0) && (fin->fin_flx & FI_TCPUDP)) {
-			natfailed = -1;
-			goto nonatfrag;
-		}
-		msk = 0xffffffff;
-		nmsk = nat_masks;
 maskloop:
 		iph = ipa & htonl(msk);
 		hv = NAT_HASH_FN(iph, 0, ipf_natrules_sz);
 		for (np = nat_rules[hv]; np; np = npnext) {
 			npnext = np->in_mnext;
-			if ((np->in_ifps[1] && (np->in_ifps[1] != ifp)))
+			if (np->in_ifps[1] && (np->in_ifps[1] != ifp))
 				continue;
 			if (np->in_v != fin->fin_v)
 				continue;
@@ -3918,7 +3914,6 @@
 		}
 	}
 
-nonatfrag:
 	if (nat != NULL) {
 		rval = fr_natout(fin, nat, natadd, nflags);
 		if (rval == 1) {
@@ -4142,20 +4137,17 @@
 	if (((fin->fin_flx & FI_ICMPERR) != 0) &&
 	    (nat = nat_icmperror(fin, &nflags, NAT_INBOUND)))
 		/*EMPTY*/;
-	else if ((fin->fin_flx & FI_FRAG) && (nat = fr_nat_knownfrag(fin)))
+	else if ((fin->fin_flx & FI_FRAG) && 
+		 (nat = fr_nat_knownfrag(fin)))
 		natadd = 0;
 	else if ((nat = nat_inlookup(fin, nflags|NAT_SEARCH, (u_int)fin->fin_p,
 				     fin->fin_src, in))) {
 		nflags = nat->nat_flags;
-	} else {
+	} else if (fin->fin_off == 0) {
 		u_32_t hv, msk, rmsk;
 
-		if ((fin->fin_off != 0) && (fin->fin_flx & FI_TCPUDP)) {
-			natfailed = -1;
-			goto nonatfrag;
-		}
-		rmsk = rdr_masks;
 		msk = 0xffffffff;
+		rmsk = rdr_masks;
 		/*
 		 * If there is no current entry in the nat table for this IP#,
 		 * create one for it (if there is a matching rule).
@@ -4230,7 +4222,6 @@
 		}
 	}
 
-nonatfrag:
 	if (nat != NULL) {
 		rval = fr_natin(fin, nat, natadd, nflags);
 		if (rval == 1) {

Reply via email to