Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 19 Feb 2004 02:03:18 +0100
From:      Andre Oppermann <andre@freebsd.org>
To:        "Jacques A. Vidrine" <nectar@FreeBSD.org>, freebsd-net@freebsd.org, FreeBSD Security Officer Team <security-team@FreeBSD.org>
Subject:   Re: Fwd: [is this mbuf problem real?]
Message-ID:  <40340B56.A30FD511@freebsd.org>
References:  <20040218220230.GF47727@madman.celabo.org> <4034049A.906ACDB9@freebsd.org> <4034079B.8C29425C@freebsd.org>

next in thread | previous in thread | raw e-mail | index | archive | help
Andre Oppermann wrote:
> 
> Andre Oppermann wrote:
> >
> > "Jacques A. Vidrine" wrote:
> > >
> > > Does anyone have time to investigate?  I will try to get more
> > > information from iDEFENSE.
> >
> > Looking at the code there are indeed some problems.
> >
> >  - there seems to be no boundary on how many segments we keep in the
> >    tcp reassembly queue
> >  - there seems to be no timeout of overaged fragments (we can drop
> >    the segments after 1*msl because we don't have SACK and it has
> >    to be retransmitted anyway since not ACK'ed which happens after
> >    read from userland).  Possibly it can be dropped earlier after
> >    we've got x bytes or packets of more segments since it is un-
> >    likely to receive the missing packet this late except for really
> >    massive reordering
> >  - this attack can be made with small packets which consume an mbuf
> >    cluster anyway
> 
>  - it uses MALLOC() to allocate its queue entry wheras it probably
>    should use the zone allocator.  The max limit on the zone than
>    directly gives us a upper limit on the number of concatenated
>    segments (not mbufs)
>  - it uses LIST_FOREACH which is pretty inefficient.  NetBSD has
>    optimized this part quite a bit with a tail queue
> 
> > For IP packet reassembly we have global and local limits:
> >
> >  net.inet.ip.maxfragpackets: 800
> >  net.inet.ip.maxfragsperpacket: 16
> >
> > Something like this is needed for TCP as well to cope with this kind
> > of resource exhaustion attack.

We can simply use the free space in the socket receive buffer as per
connection limit.  Actually this is the correct thing to do plus time
out after 1*msl.  A global limit is probably not needed anymore since
with this we come to the same point as when applications stop reading
their sockets and the socket buffer fills up.  We won't use more space
in the reassembly queue than that.  This sounds like a plan.  I'll go
and implement this (limiter w/o optimizations) tomorrow and/or Friday.
While doing that I'll check if the right things happens if the protocol
drain queue of tcp gets called in a low memory situation.  We should
simply discard all data in the reassembly queues.  In 99 percent of the
cases not a significant loss because it gets retransmitted anyway.

> > I can fix this stuff but I won't be able to do that in emergency mode.
> > The first code can be ready after the weekend.  If someone else wants
> > to takle it earlier/faster tell me.

-- 
Andre [keeping replying to himself, FreeBSD lists seem to be broken]



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