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>