123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282 |
- <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
- <!--Converted with LaTeX2HTML 2002-2 (1.70)
- original version by: Nikos Drakos, CBLU, University of Leeds
- * revised and updated by: Marcus Hennecke, Ross Moore, Herb Swan
- * with significant contributions from:
- Jens Lippmann, Marek Rouchal, Martin Wilck and others -->
- <HTML>
- <HEAD>
- <TITLE>4 Multiple Independent Flows</TITLE>
- <META NAME="description" CONTENT="4 Multiple Independent Flows">
- <META NAME="keywords" CONTENT="flowreplay">
- <META NAME="resource-type" CONTENT="document">
- <META NAME="distribution" CONTENT="global">
- <META HTTP-EQUIV="Content-Type" CONTENT="text/html; charset=iso-8859-1">
- <META NAME="Generator" CONTENT="LaTeX2HTML v2002-2">
- <META HTTP-EQUIV="Content-Style-Type" CONTENT="text/css">
- <LINK REL="STYLESHEET" HREF="flowreplay.css">
- <LINK REL="next" HREF="node5.html">
- <LINK REL="previous" HREF="node3.html">
- <LINK REL="up" HREF="flowreplay.html">
- <LINK REL="next" HREF="node5.html">
- </HEAD>
- <BODY >
- <DIV CLASS="navigation"><!--Navigation Panel-->
- <A NAME="tex2html72"
- HREF="node5.html">
- <IMG WIDTH="37" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="next" SRC="next.png"></A>
- <A NAME="tex2html70"
- HREF="flowreplay.html">
- <IMG WIDTH="26" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="up" SRC="up.png"></A>
- <A NAME="tex2html64"
- HREF="node3.html">
- <IMG WIDTH="63" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="previous" SRC="prev.png"></A>
- <BR>
- <B> Next:</B> <A NAME="tex2html73"
- HREF="node5.html">5 pcap vs flow</A>
- <B> Up:</B> <A NAME="tex2html71"
- HREF="flowreplay.html">Flowreplay Design Notes</A>
- <B> Previous:</B> <A NAME="tex2html65"
- HREF="node3.html">3 Design Thoughts</A>
- <BR>
- <BR></DIV>
- <!--End of Navigation Panel-->
- <!--Table of Child-Links-->
- <A NAME="CHILD_LINKS"><STRONG>Subsections</STRONG></A>
- <UL CLASS="ChildLinks">
- <LI><A NAME="tex2html74"
- HREF="node4.html#SECTION00041000000000000000"><SPAN CLASS="arabic">4</SPAN>.<SPAN CLASS="arabic">1</SPAN> <SPAN ID="hue158">IP Fragments and TCP Streams</SPAN></A>
- <LI><A NAME="tex2html75"
- HREF="node4.html#SECTION00042000000000000000"><SPAN CLASS="arabic">4</SPAN>.<SPAN CLASS="arabic">2</SPAN> <SPAN ID="hue194">Blocking</SPAN></A>
- </UL>
- <!--End of Table of Child-Links-->
- <HR>
- <H1><A NAME="SECTION00040000000000000000">
- <SPAN CLASS="arabic">4</SPAN> <SPAN ID="hue142">Multiple Independent Flows</SPAN></A>
- </H1>
- <P>
- <SPAN ID="hue144">The biggest asynchronous problem, that pcap files
- are serial, has to be solved in a scaleable manner. Not much can be
- assumed about the network traffic contained in a pcap savefile other
- then Murphy's Law will be in effect. This means we'll have to deal
- with:</SPAN>
- <P>
- <UL>
- <LI><SPAN ID="hue147">Thousands of small simultaneous flows (captured
- on a busy network)</SPAN>
- </LI>
- <LI><SPAN ID="hue380">Flows which ``hang'' mid-stream (an exploit
- against a server causes it to crash)</SPAN>
- </LI>
- <LI><SPAN ID="hue151">Flows which contain large quantities of data (FTP
- transfers of ISO's for example)</SPAN>
- </LI>
- </UL>
- <SPAN ID="hue154">How we implement parallel processing of the pcap
- savefile will dramatically effect how well we can scale. A few considerations:</SPAN>
- <P>
- <UL>
- <LI>Most Unix systems limit the maximum number of open file descriptors
- a single process can have. Generally speaking this shouldn't be a
- problem except for highly parallel pcap's.
- </LI>
- <LI>While RAM isn't limitless, we can use mmap() to get around this.
- </LI>
- <LI>Many Unix systems have enhanced solutions to poll() which will improve
- flow management.
- </LI>
- </UL>
- <P>
- <H2><A NAME="SECTION00041000000000000000">
- <SPAN CLASS="arabic">4</SPAN>.<SPAN CLASS="arabic">1</SPAN> <SPAN ID="hue158">IP Fragments and TCP Streams</SPAN></A>
- </H2>
- <P>
- <SPAN ID="hue160">There are five major complications with flowreplay:</SPAN>
- <P>
- <OL>
- <LI><SPAN ID="hue163">The IP datagrams may be fragmented- we won't be
- able to use the standard 5-tuple (src/dst IP, src/dst port, protocol)
- to lookup which flow a packet belongs to.</SPAN>
- </LI>
- <LI><SPAN ID="hue165">IP fragments may arrive out of order which will
- complicate ordering of data to be sent.</SPAN>
- </LI>
- <LI><SPAN ID="hue167">The TCP segments may arrive out of order which will
- complicate ordering of data to be sent.</SPAN>
- </LI>
- <LI><SPAN ID="hue169">Packets may be missing in the pcap file because
- they were dropped during capture.</SPAN>
- </LI>
- <LI><SPAN ID="hue171">There are tools like fragrouter which intentionally
- create non-deterministic situations.</SPAN>
- </LI>
- </OL>
- <SPAN ID="hue174">First off, I've decided, that I'm not going to worry
- about fragrouter or it's cousins. I'll handle non-deterministic situations
- one and only one way, so that the way flowreplay handles the traffic
- will be deterministic. Perhaps, I'll make it easy for others to write
- a plug-in which will change it, but that's not something I'm going
- to concern myself with now.</SPAN>
- <P>
- <SPAN ID="hue176">Missing packets in the pcap file will probably make
- that flow unplayable. There are proabably certain situation where
- we can make an educated guess, but this is far too complex to worry
- about for the first stable release.</SPAN>
- <P>
- <SPAN ID="hue178">That still leaves creating a basic TCP/IP stack
- in user space. The good news it that there is already a library which
- does this called libnids. As of version 1.17, libnids can process
- packets from a pcap savefile (it's not documented in the man page,
- but the code is there).</SPAN>
- <P>
- <SPAN ID="hue180">A potential problem with libnids though is that
- it has to maintain it's own state/cache system. This not only means
- additional overhead, but jumping around in the pcap file as I'm planning
- on doing to handle multiple simultaneous flows is likely to really
- confuse libnids' state engine. Also, libnids is licensed under the
- GPL, but I want flowreplay released under a BSD-like license; I need
- to research if the two are compatible in this way.</SPAN>
- <P>
- <SPAN ID="hue182">Possible solutions:</SPAN>
- <P>
- <UL>
- <LI><SPAN ID="hue185">Developing a custom wedge between the capture file
- and libnids which will cause each packet to only be processed a single
- time.</SPAN>
- </LI>
- <LI><SPAN ID="hue187">Use libnids to process the pcap file into a new
- flow-based format, effectively putting the TCP/IP stack into a dedicated
- utility.</SPAN>
- </LI>
- <LI><SPAN ID="hue189">Develop a custom user-space TCP/IP stack, perhaps
- based on a BSD TCP/IP stack, much like libnids is based on Linux 2.0.37.</SPAN>
- </LI>
- <LI><SPAN ID="hue191">Screw it and say that IP fragmentation and out of
- order IP packets/TCP segments are not supported. Not sure if this
- will meet the needs of potential users.</SPAN>
- </LI>
- </UL>
- <P>
- <H2><A NAME="SECTION00042000000000000000">
- <SPAN CLASS="arabic">4</SPAN>.<SPAN CLASS="arabic">2</SPAN> <SPAN ID="hue194">Blocking</SPAN></A>
- </H2>
- <P>
- <SPAN ID="hue196">As earlier stated, one of the main goals of this
- project is to keep things single threaded to make coding plugins easier.
- One caveat of that is that any function which blocks will cause serious
- problems.</SPAN>
- <P>
- <SPAN ID="hue198">There are three major cases where blocking is likely
- to occur:</SPAN>
- <P>
- <OL>
- <LI><SPAN ID="hue201">Opening a socket</SPAN>
- </LI>
- <LI><SPAN ID="hue203">Reading from a socket</SPAN>
- </LI>
- <LI><SPAN ID="hue205">Writing to a socket</SPAN>
- </LI>
- </OL>
- <SPAN ID="hue208">Reading from sockets in a non-blocking manner is
- easy to solve for using poll() or select(). Writing to a socket, or
- merely opening a TCP socket via connect() however requires a different
- method:</SPAN>
- <P>
- <BLOCKQUOTE>
- <SPAN ID="hue211">It is possible to do non-blocking IO on sockets
- by setting the O_NONBLOCK flag on a socket file descriptor using
- fcntl(2). Then all operations that would block will (usually) return
- with EAGAIN (operation should be retried later); connect(2) will return
- EINPROGRESS error. The user can then wait for various events via poll(2)
- or select(2).</SPAN><A NAME="tex2html7"
- HREF="#foot383"><SUP><SPAN CLASS="arabic">7</SPAN></SUP></A>
- </BLOCKQUOTE>
- <SPAN ID="hue216">If connect() returns EINPROGRESS, then we'll just
- have to do something like this:</SPAN>
- <P>
- <DL COMPACT>
- <DT>
- <DD><SPAN ID="hue219">int e, len=sizeof(e);</SPAN>
- <P>
- <SPAN ID="hue221">if (getsockopt(conn->s, SOL_SOCKET, SO_ERROR, &e, &len) < 0) { </SPAN>
- <P>
- <SPAN ID="hue384"> /* not yet */</SPAN>
- <P>
- <SPAN ID="hue385"> if(errno != EINPROGRESS){ /* yuck. kill it. */ </SPAN>
- <P>
- <SPAN ID="hue386"> log_fn(LOG_DEBUG,"in-progress connect failed. Removing."); </SPAN>
- <P>
- <SPAN ID="hue232"> return -1; </SPAN>
- <P>
- <SPAN ID="hue234"> } else { </SPAN>
- <P>
- <SPAN ID="hue387"> return 0; /* no change, see if next time is better */ </SPAN>
- <P>
- <SPAN ID="hue239"> } </SPAN>
- <P>
- <SPAN ID="hue241">} </SPAN>
- <P>
- <SPAN ID="hue388">/* the connect has finished. */ </SPAN>
- </DD>
- </DL><BLOCKQUOTE>
- <SPAN ID="hue248">Note: It may not be totally right, but it works
- ok. (that chunk of code gets called after poll returns the socket
- as writable. if poll returns it as readable, then it's probably because
- of eof, connect fails. You must poll for both.</SPAN>
- </BLOCKQUOTE>
- <P>
- <BR><HR><H4>Footnotes</H4>
- <DL>
- <DT><A NAME="foot383">... </A><A
- HREF="node4.html#tex2html7"><SUP><SPAN CLASS="arabic">7</SPAN></SUP></A></DT>
- <DD><SPAN ID="hue213">socket(7)</SPAN>
- </DD>
- </DL>
- <DIV CLASS="navigation"><HR>
- <!--Navigation Panel-->
- <A NAME="tex2html72"
- HREF="node5.html">
- <IMG WIDTH="37" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="next" SRC="next.png"></A>
- <A NAME="tex2html70"
- HREF="flowreplay.html">
- <IMG WIDTH="26" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="up" SRC="up.png"></A>
- <A NAME="tex2html64"
- HREF="node3.html">
- <IMG WIDTH="63" HEIGHT="24" ALIGN="BOTTOM" BORDER="0" ALT="previous" SRC="prev.png"></A>
- <BR>
- <B> Next:</B> <A NAME="tex2html73"
- HREF="node5.html">5 pcap vs flow</A>
- <B> Up:</B> <A NAME="tex2html71"
- HREF="flowreplay.html">Flowreplay Design Notes</A>
- <B> Previous:</B> <A NAME="tex2html65"
- HREF="node3.html">3 Design Thoughts</A></DIV>
- <!--End of Navigation Panel-->
- <ADDRESS>
- Aaron Turner
- 2006-08-07
- </ADDRESS>
- </BODY>
- </HTML>
|