Subject: kern/14002: Premature TCP/UDP NAT time out when ICMP is returned
To: None <gnats-bugs@gnats.netbsd.org>
From: None <eramore@era-t.ericsson.se>
List: netbsd-bugs
Date: 09/18/2001 23:41:04
>Number:         14002
>Category:       kern
>Synopsis:       Premature TCP/UDP NAT time out when ICMP is returned
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    kern-bug-people
>State:          open
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Tue Sep 18 14:43:00 PDT 2001
>Closed-Date:
>Last-Modified:
>Originator:     Michael Eriksson
>Release:        NetBSD 1.5.2 and -current
>Organization:
Ericsson Radio Systems AB
>Environment:
System: NetBSD bolle 1.5.1 NetBSD 1.5.1 (BOLLE) #0: Thu Jul 26 00:37:29 CEST 2001 mer@burken:/usr/src/sys/arch/i386/compile/BOLLE i386


>Description:

There is a bug in the IP NAT functionality of ip-filter. If there a
temporary network problem, and an ICMP messages like Time Exceeded is
sent back for a TCP or UDP packet, the TCP/UDP translation in the NAT
table will timeout after three seconds (rather than the normal five
days). This means e.g. that a NAT'ed TCP connection which gets a
single ICMP error packet will likely get dropped and lost.

This bug is fixed in ip-filter 3.4.18. Until that or a later version
is imported, the small patch below will make IP NAT a lot more robust
against network problems.

>How-To-Repeat:

Run ssh and create a temporary routing loop, which will send an ICMP
message for one of your TCP packets. Watch your ssh session die with a
TCP reset when the network is OK again, as the NAT will have created a
new (bogus) port mapping after the original one timed out after three
seconds.

>Fix:

Index: ip_nat.c
===================================================================
RCS file: /cvsroot/syssrc/sys/netinet/ip_nat.c,v
retrieving revision 1.34.2.3
diff -u -u -r1.34.2.3 ip_nat.c
--- ip_nat.c	2001/04/14 20:57:01	1.34.2.3
+++ ip_nat.c	2001/09/18 21:06:43
@@ -1645,7 +1645,8 @@
 			}
 		}
 	}
-	nat->nat_age = fr_defnaticmpage;
+	if (oip->ip_p == IPPROTO_ICMP)
+		nat->nat_age = fr_defnaticmpage;
 	return nat;
 }
 

>Release-Note:
>Audit-Trail:
>Unformatted: