include/wipal/wifi/frame/filter/uniquely_identifiable.hxx

00001 /*
00002  * WiPal - 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_UNIQUELY_IDENTIFIABLE_HXX_
00023 # define WIFI_FRAME_FILTER_UNIQUELY_IDENTIFIABLE_HXX_
00024 
00025 # include <wipal/wifi/frame/dissector/dissector.hh>
00026 # include <wipal/wifi/frame/unique_id/unique_id.hh>
00027 # include <wipal/wifi/frame/filter/non_noisy_prism.hh>
00028 
00029 namespace wifi
00030 {
00031   namespace frame
00032   {
00033     namespace filter
00034     {
00035 
00036       namespace internals
00037       {
00038 
00039         template <class U, class I, class H, class B1, class B2>
00040         uniquely_identifiable_iterator<U, I, H, B1, B2>::
00041         uniquely_identifiable_iterator(const iterable_type&     uif,
00042                                        bool                     end):
00043           super_type (),
00044           iterable_ (&uif),
00045           next_ (end ? uif.end_ : uif.begin_)
00046         {
00047           if (not end)
00048             increment();
00049         }
00050 
00051         template <class U, class I, class H, class B1, class B2>
00052         bool
00053         uniquely_identifiable_iterator<U, I, H, B1, B2>::
00054 	equal(const uniquely_identifiable_iterator& rhs) const
00055         {
00056           if (not rhs.value())
00057             return not this->value();
00058           return next_ == rhs.next_;
00059         }
00060 
00061         template <class U, class I, class H, class B1, class B2>
00062         void
00063         uniquely_identifiable_iterator<U, I, H, B1, B2>::increment()
00064         {
00065           using tool::endian::need_swap;
00066 
00067           boost::optional<U>    id;
00068 
00069           while (next_ != iterable_->end_ and not id)
00070             {
00071               const pcapxx::pkthdr*     p = next_->pcap_header().get();
00072               const H*                  h =
00073                 reinterpret_cast<const H*> (next_->bytes().get());
00074 
00075               mactime_.tick(h, p->caplen,
00076                             need_swap(iterable_->phy_end_, p->swapped));
00077               id = make_unique_id<U, H>(*next_, *iterable_->mapping_);
00078               ++next_;
00079             }
00080           if (id)
00081             this->value() = value_type (mactime_.microseconds(), id.get());
00082           else
00083             this->value() = boost::none_t ();
00084         }
00085 
00086       } // End of namespace wifi::frame::filter::internals.
00087 
00088       template <class U, class I, class H, class B>
00089       uniquely_identifiable<U, I, H, B>::
00090       uniquely_identifiable(const I&                    begin,
00091                             const I&                    end,
00092                             addr_mapping&               mapping,
00093                             tool::endian::endianness    phy_end):
00094         begin_ (begin),
00095         end_ (end),
00096         mapping_ (&mapping),
00097         phy_end_ (phy_end)
00098       {
00099       }
00100 
00101       template <class U, class HT, class I, class F>
00102       void
00103       for_each_uniquely_identifiable(const I&                   first,
00104                                      const I&                   last,
00105                                      addr_mapping&              mapping,
00106                                      F&                         func,
00107                                      bool                       filter_prism,
00108                                      tool::endian::endianness   phy_end)
00109       {
00110         if (filter_prism)
00111           {
00112             typedef non_noisy_prism<I>                          filter_type;
00113             typedef typename filter_type::iterator              iterator;
00114             typedef uniquely_identifiable<U, iterator, HT>      unique_type;
00115 
00116             filter_type f (first, last);
00117             unique_type u (f.begin(), f.end(), mapping, phy_end);
00118 
00119             u.for_each(func);
00120           }
00121         else
00122           {
00123             typedef uniquely_identifiable<U, I, HT>             unique_type;
00124 
00125             unique_type u (first, last, mapping, phy_end);
00126 
00127             u.for_each(func);
00128           }
00129       }
00130 
00131       // FIXME: Avoid code duplication with the above. :-( :-(
00132       template <class U, class HT, class I, class F>
00133       void
00134       for_each_uniquely_identifiable(const I&                   first,
00135                                      const I&                   last,
00136                                      addr_mapping&              mapping,
00137                                      const F&                   func,
00138                                      bool                       filter_prism,
00139                                      tool::endian::endianness   phy_end)
00140       {
00141         if (filter_prism)
00142           {
00143             typedef non_noisy_prism<I>                          filter_type;
00144             typedef typename filter_type::iterator              iterator;
00145             typedef uniquely_identifiable<U, iterator, HT>      unique_type;
00146 
00147             filter_type f (first, last);
00148             unique_type u (f.begin(), f.end(), mapping, phy_end);
00149 
00150             u.for_each(func);
00151           }
00152         else
00153           {
00154             typedef uniquely_identifiable<U, I, HT>             unique_type;
00155 
00156             unique_type u (first, last, mapping, phy_end);
00157 
00158             u.for_each(func);
00159           }
00160       }
00161 
00162     } // End of namespace wifi::frame::filter.
00163 
00164   } // End of namespace wifi::frame.
00165 
00166 } // End of namespace wifi.
00167 
00168 #endif // ! WIFI_FRAME_FILTER_UNIQUELY_IDENTIFIABLE_HXX_

Generated on Wed Jan 16 16:15:14 2008 for wipal by  doxygen 1.5.4