include/trace-tools/wifi/frame/filter/intersector.hxx

00001 /*
00002  * trace-tools - A library and a set of tools to manipulate wireless traces.
00003  * Copyright (C) 2007  Universite Pierre et Marie Curie - Paris 6
00004  *
00005  * This program is free software; you can redistribute it and/or modify
00006  * it under the terms of the GNU General Public License as published by
00007  * the Free Software Foundation; either version 2 of the License, or
00008  * (at your option) any later version.
00009  *
00010  * This program is distributed in the hope that it will be useful,
00011  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00012  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00013  * GNU General Public License for more details.
00014  *
00015  * You should have received a copy of the GNU General Public License
00016  * along with this program; if not, write to the Free Software
00017  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
00018  * MA  02110-1301  USA
00019  *
00020  * Author: Thomas Claveirole <thomas.claveirole@lip6.fr>
00021  */
00022 #ifndef WIFI_FRAME_FILTER_INTERSECTOR_HXX_
00023 # define WIFI_FRAME_FILTER_INTERSECTOR_HXX_
00024 
00025 # include "intersector.hh"
00026 
00027 namespace wifi
00028 {
00029   namespace frame
00030   {
00031     namespace filter
00032     {
00033 
00034       namespace internals
00035       {
00036 
00037         template <class I1, class I2, class B1, class B2>
00038         intersector_iterator<I1, I2, B1, B2>::
00039         intersector_iterator(iterable_type& i, bool end):
00040           tool::iterator_base<exact_type> (i, end)
00041         {
00042         }
00043 
00044         template <class I1, class I2, class B1, class B2>
00045         void
00046         intersector_iterator<I1, I2, B1, B2>::increment()
00047         {
00048           arrivals1_type&       arrivals1 = this->i_->arrivals1_;
00049           arrivals2_type&       arrivals2 = this->i_->arrivals2_;
00050           I1&                   next1 = this->i_->next1_;
00051           I2&                   next2 = this->i_->next2_;
00052           const I1&             last1 = this->i_->last1_;
00053           const I2&             last2 = this->i_->last2_;
00054 
00055           while (next1 != last1 or next2 != last2)
00056             if ((next1 != last1 and check<false>(next1, arrivals1, arrivals2))
00057                 or
00058                 (next2 != last2 and check<true>(next2, arrivals2, arrivals1)))
00059               return;
00060           arrivals1.clear();
00061           arrivals2.clear();
00062           this->v_ = boost::none_t ();
00063         }
00064 
00065         template <class I1, class I2, class B1, class B2>
00066         template <bool SwapResult, class ArrType, class RHSArrType>
00067         bool
00068         intersector_iterator<I1, I2, B1, B2>::
00069         check(I1&               frm,
00070               ArrType&          frm_arrivals,
00071               RHSArrType&       rhs_arrivals)
00072         {
00073           typename RHSArrType::iterator i = rhs_arrivals.find(*frm);
00074 
00075           if (i == rhs_arrivals.end())
00076             {
00077               frm_arrivals.insert(*frm);
00078               ++frm;
00079               return false;
00080             }
00081 
00082           this->v_ = SwapResult ?
00083             std::make_pair(*i, *frm):
00084             std::make_pair(*frm, *i);
00085 
00086           // Cleanup the set of arrivals (i.e. remove frames previous
00087           // to this one).  We should do it systematically, but that
00088           // operation takes time.  So we ignore it by default.  We
00089           // only do it if the set of arrivals is too big (i.e. there
00090           // is a risk of saturating memory, or the search time may
00091           // become non-negligible).
00092           {
00093             enum { arrivals_max_size = 0 }; // 1000000 };
00094 
00095             if (rhs_arrivals.size() > arrivals_max_size)
00096               cleanup_arrivals(i, rhs_arrivals);
00097           }
00098 
00099           rhs_arrivals.erase(i);
00100           ++frm;
00101           return true;
00102         }
00103 
00104         template <class I1, class I2, class B1, class B2>
00105         template <class ArrType>
00106         void
00107         intersector_iterator<I1, I2, B1, B2>::
00108         cleanup_arrivals(const typename ArrType::iterator&      frame,
00109                          ArrType&                               arrivals)
00110         {
00111           const tool::microseconds      m = frame->microseconds();
00112           typename ArrType::iterator    i = arrivals.begin();
00113 
00114           while (i != arrivals.end())
00115             {
00116               if (i->microseconds() < m)
00117                 arrivals.erase(i++);
00118               else
00119                 ++i;
00120             }
00121         }
00122 
00123       } // End of namespace internals.
00124 
00125 
00126       template <class I1, class I2, class B>
00127       intersector<I1, I2, B>::intersector(const I1& first1, const I1& last1,
00128                                           const I2& first2, const I2& last2):
00129         arrivals1_ (),
00130         arrivals2_ (),
00131         next1_ (first1),
00132         last1_ (last1),
00133         next2_ (first2),
00134         last2_ (last2)
00135       {
00136       }
00137 
00138     } // End of namespace wifi::frame::filter.
00139 
00140   } // End of namespace wifi::frame.
00141 
00142 } // End of namespace wifi.
00143 
00144 #endif // ! WIFI_FRAME_FILTER_INTERSECTOR_HXX_

Generated on Wed Sep 12 16:02:47 2007 for trace-tools by  doxygen 1.5.3