Skip site navigation (1)Skip section navigation (2)
Date:      Tue, 24 Aug 2010 13:53:21 GMT
From:      Jens Kassel <jens.kassel@servicefactory.com>
To:        freebsd-gnats-submit@FreeBSD.org
Subject:   kern/149937: kernel panic in ipfilter IP fragments with TCP paylaod in reverse order 
Message-ID:  <201008241353.o7ODrLDH084078@www.freebsd.org>
Resent-Message-ID: <201008241400.o7OE03vu010952@freefall.freebsd.org>

next in thread | raw e-mail | index | archive | help

>Number:         149937
>Category:       kern
>Synopsis:       kernel panic in ipfilter IP fragments with TCP paylaod in reverse order
>Confidential:   no
>Severity:       critical
>Priority:       high
>Responsible:    freebsd-bugs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Tue Aug 24 14:00:02 UTC 2010
>Closed-Date:
>Last-Modified:
>Originator:     Jens Kassel
>Release:        FreeBSD 7.2
>Organization:
Servicefactory AB
>Environment:
FreeBSD h167.servicefactory.com 7.2-RELEASE FreeBSD 7.2-RELEASE #0: Fri May  1 08:49:13 UTC 2009     root@walker.cse.buffalo.edu:/usr/obj/usr/src/sys/GENERIC  i386
>Description:
Kernel panic in ipfilter when trying to NAT IP fragments with TCP payload sent in "wrong" order. The following line in ip_nat.c will crash on NULL pointer.



 if (nat->nat_p == IPPROTO_TCP)
                nat->nat_seqnext[0] = ntohl(tcp->th_seq);


tcp is not set.


This is not fixed in FreeBSD 8.1
>How-To-Repeat:
Set up ipnat:
List of active MAP/Redirect filters:
map bge2 10.10.0.0/24 -> 0.0.0.0/32 proxy port ftp ftp/tcp
map bge2 10.10.0.0/24 -> 0.0.0.0/32 portmap tcp/udp 1025:65500
map bge2 10.10.0.0/24 -> 0.0.0.0/32
map lo3 10.10.0.0/24 -> 127.0.0.3/32 portmap tcp/udp 9000:65500
map lo0 10.10.0.0/24 -> 127.0.0.1/32 portmap udp 9000:65500
map-block lo0 10.10.0.0/24 -> 127.0.0.1/32 ports 10 tcp
rdr lo0 0.0.0.0/0 port 80 -> 127.0.0.1 port 65501 tcp
rdr lo0 0.0.0.0/0 port 443 -> 127.0.0.1 port 65502 tcp
rdr lo3 0.0.0.0/0 port 8080 -> 127.0.0.3 port 65504 tcp
rdr lo1 0.0.0.0/0 port 8080 -> 127.0.0.2 port 65503 tcp
map lo1 10.10.0.0/24 -> 127.0.0.2/32 portmap tcp/udp 9000:65500

List of active sessions:



Send correct fragmented IP packet with proto TCP and offset larger than 0 (not first fragment). Source 10.10.0.x. Destination some externel host.
>Fix:
The following patch will discard these fragments if sent in reverse order (solving the problem).


--- ip_nat.c.org        2010-08-24 13:43:56.000000000 +0200
+++ ip_nat.c    2010-08-24 14:41:33.000000000 +0200
@@ -3770,6 +3770,17 @@
                if ((nflags & IPN_TCPUDP))
                        tcp = fin->fin_dp;
        }
+       else
+        {
+                /* Discard TCP unknown fragments out of order
+                */
+                if ((IPPROTO_TCP == fin->fin_p) &&  !fr_nat_knownfrag(fin))
+                {
+                       nat_stats.ns_badnat++;
+                        return -1;
+                }
+        }
+

        ipa = fin->fin_saddr;

@@ -4065,6 +4076,17 @@
                        dport = tcp->th_dport;
                }
        }
+       else
+        {
+                /* Discard TCP unknown fragments out of order
+                */
+                if ((IPPROTO_TCP == fin->fin_p) &&  !fr_nat_knownfrag(fin))
+                {
+                       nat_stats.ns_badnat++;
+                        return -1;
+                }
+        }
+

        in = fin->fin_dst;


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



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201008241353.o7ODrLDH084078>