4 // Fraunhofer Institute for Open Communication Systems (FOKUS)
5 // Competence Center NETwork research (NET), St. Augustin, GERMANY
6 // Stefan Bund <g0dil@berlios.de>
8 // This program is free software; you can redistribute it and/or modify
9 // it under the terms of the GNU General Public License as published by
10 // the Free Software Foundation; either version 2 of the License, or
11 // (at your option) any later version.
13 // This program is distributed in the hope that it will be useful,
14 // but WITHOUT ANY WARRANTY; without even the implied warranty of
15 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 // GNU General Public License for more details.
18 // You should have received a copy of the GNU General Public License
19 // along with this program; if not, write to the
20 // Free Software Foundation, Inc.,
21 // 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
24 \brief VectorParser public header */
26 #ifndef HH_SENF_Packets_VectorParser_
27 #define HH_SENF_Packets_VectorParser_ 1
30 #include <boost/iterator/iterator_facade.hpp>
31 #include <boost/utility.hpp>
32 #include <boost/range.hpp>
33 #include <boost/type_traits.hpp>
34 #include "PacketParser.hh"
35 #include "ArrayParser.hh" // for ArrayParser_iterator
36 #include "AuxParser.hh" // for the AuxPolicies
38 //#include "VectorParser.mpp"
39 ///////////////////////////////hh.p////////////////////////////////////////
43 template <class ElementParser, class AuxPolicy> class VectorParser_Container;
45 /** \brief Collection of fixed-size elements
47 A Vector is a collection of fixed-size elements of which the size of the collection can be
48 determined directly (that is without traversing the collection). This allows very efficient
49 random access to the elements of the collection.
51 A vector is a model of an STL random-access sequence. The parser only provides a reduced
52 interface, the container wrapper however completes this interface.
54 VectorParser makes use of a policy template argument, \a AuxPolicy, to customize the way the
55 containers size is obtained. You will normally not instantiate VectorParser directly, you
56 will use the \ref SENF_PARSER_VECTOR() helper macro.
58 Some basic vector access methods are defined as parser members. To access the complete list
59 API however you will need to instantiate a container wrapper for the vector. See \ref
60 packet_usage_fields_collection.
63 \ref How to access \ref packet_usage_fields_collection \n
64 SENF_PARSER_VECTOR() macro used to define vector fields \n
65 VectorParser_Container vector container wrapper API
67 \ingroup parsecollection
69 template <class ElementParser, class AuxPolicy>
71 : public PacketParserBase,
74 VectorParser(data_iterator i, state_type s);
75 VectorParser(AuxPolicy policy, data_iterator i, state_type s);
76 ///< Additional sizer specific constructor
77 /**< This constructor may be used, if the sizer needs
78 additional parameters. */
80 size_type bytes() const;
83 static const size_type init_bytes = AuxPolicy::aux_bytes;
85 ///////////////////////////////////////////////////////////////////////////
86 // Container interface
88 typedef ElementParser value_type;
89 typedef detail::ArrayParser_iterator<value_type> iterator;
90 typedef iterator const_iterator;
91 typedef VectorParser_Container<ElementParser,AuxPolicy> container;
93 size_type size() const;
96 iterator begin() const;
99 value_type operator[](difference_type i) const;
100 value_type front() const;
101 value_type back() const;
105 // The mutators provided here are those which don't take an iterator argument.
106 // If you need to pass an iterator it is much simpler and cleaner to use the
107 // 'container' wrapper
109 template <class Value> void push_back (Value const & value, size_type n=1) const;
110 value_type push_back_space (size_type n=1) const;
111 template <class Value> void push_front (Value const & value, size_type n=1) const;
112 value_type push_front_space (size_type n=1) const;
113 void resize (size_type n) const;
114 template <class Value> void resize (size_type n, Value value) const;
118 friend class VectorParser_Container<ElementParser,AuxPolicy>;
121 /** \brief VectorParser container wrapper
123 This is the container wrapper used for vector parsers. The container wrapper will stay valid
124 after changing the collection. However the container still depends on the packet and will be
125 invalidated if the Packet is deallocated or if the packet size is changed from without the
126 container wrapper (more precisely, it is invalided if the insertion/deletion happens before
127 the vector in the packet data).
129 The vector container wrapper provides a complete STL random-access sequence interface.
133 SomePacket::aVectorCollection_t::container c (p->aVectorCollection());
134 c.insert(c.begin(), ... );
139 template <class ElementParser, class AuxPolicy>
140 class VectorParser_Container
141 : private AuxPolicy::WrapperPolicy
144 ///////////////////////////////////////////////////////////////////////////
147 typedef VectorParser<ElementParser,AuxPolicy> parser_type;
148 typedef PacketParserBase::data_iterator data_iterator;
149 typedef PacketParserBase::size_type size_type;
150 typedef PacketParserBase::difference_type difference_type;
151 typedef ElementParser value_type;
152 typedef detail::ArrayParser_iterator<value_type> iterator;
153 typedef iterator const_iterator;
154 typedef PacketParserBase::state_type state_type;
156 ///////////////////////////////////////////////////////////////////////////
157 ///\name Structors and default members
160 // no default constructor
162 // default destructor
163 // conversion constructors
165 VectorParser_Container(parser_type const & vector);
168 ///////////////////////////////////////////////////////////////////////////
173 size_type size() const;
176 iterator begin() const;
177 iterator end() const;
179 value_type operator[](difference_type i) const;
180 value_type front() const;
181 value_type back() const;
187 iterator shift(iterator pos, size_type n=1);
188 template <class Value>
189 void insert(iterator pos, Value const & t);
190 template <class Value>
191 void insert(iterator pos, size_type n, Value const & t);
193 template <class ForwardIterator>
194 void insert(iterator pos, ForwardIterator f, ForwardIterator l,
195 typename boost::disable_if< boost::is_convertible<ForwardIterator,size_type> >::type * = 0);
197 template <class ForwardIterator>
198 void insert(iterator pos, ForwardIterator f, ForwardIterator l);
201 void erase(iterator pos, size_type n=1);
202 void erase(iterator f, iterator l);
205 template <class Value> void push_back (Value const & value, size_type n=1);
206 value_type push_back_space (size_type n=1);
207 template <class Value> void push_front (Value const & value, size_type n=1);
208 value_type push_front_space (size_type n=1);
209 void resize (size_type n);
210 template <class Value> void resize (size_type n, Value value);
214 ///\name Parser interface
217 parser_type parser() const;
218 data_iterator i() const;
219 state_type state() const;
220 PacketData & data() const;
222 size_type bytes() const;
230 void setSize(size_type value);
236 /** \brief Define VectorParser field
238 This macro is a special helper to define a senf::VectorParser type field, a vector of
239 elements of type \a elt_type (a parser) which size is given by the \a size field.
242 // The size field should be declared private (size is accessible via the vector)
243 SENF_PARSER_PRIVATE_FIELD ( vec_size_, senf::UInt16Parser );
244 // Define the vector, here it has 32bit unsigned integer elements
245 SENF_PARSER_VECTOR ( vec, vec_size_, senf::UInt32Parser );
248 \warning Realize, that the \a size field is controlled by the vector parser. This field
249 should therefore be declared either read-only or private and must be changed only via
252 Further additional tags are supported which modify the way, the \a size field is
255 <table class="senf fixedcolumn">
256 <tr><td>\c bytes(\a size)</td><td>\a size gives the size of the vector in bytes not the
257 number of contained elements</td></tr>
259 <tr><td>\c packetSize()</td><td>Use the size of the packet to get the vector size. The
260 vector will occupy all space up to the end of the packet.</td></tr>
262 <tr><td>\c transform(\a transform, \a size)</td><td>The \a transform is applied to the \a
263 size value, the value is not used directly</td>
266 The optional \a transform is a class with the following layout
271 typedef ... value_type;
272 static value_type get(other_type v);
273 static other_type set(value_type v);
275 \endcode \c other_type is the \a size ::\c value_type where as the \c value_type typedef is
276 the arbitrary return type of the transform.
278 The tags are applied to the \a size parameter:
280 SENF_PARSER_VECTOR ( vec, transform(MyTransform, vec_size_), senf::UInt32Parser );
281 SENF_PARSER_VECTOR ( vec, packetSize(), senf::UInt32Parser );
284 \param[in] name field name
285 \param[in] size name of field giving the vector size
286 \param[in] elt_type vector element type
289 How to use \ref packet_usage_fields_collection \n
290 senf::VectorParser the vector parser API for vector field access
291 senf::VectorParser_Container the vector parser container API for vector field access
294 \ingroup packetparsermacros
296 # define SENF_PARSER_VECTOR(name, size, elt_type) \
297 SENF_PARSER_VECTOR_I(public, name, size, elt_type)
299 /** \brief Define private VectorParser field
301 \see \ref SENF_PARSER_VECTOR()
304 \ingroup packetparsermacros
306 # define SENF_PARSER_PRIVATE_VECTOR(name, size, elt_type) \
307 SENF_PARSER_VECTOR_I(protected, name, size, elt_type)
310 ///////////////////////////////hh.e////////////////////////////////////////
312 #if !defined(HH_SENF_Packets_Packets__decls_) && !defined(HH_SENF_Packets_VectorParser_i_)
313 #define HH_SENF_Packets_VectorParser_i_
314 //#include "VectorParser.cci"
315 #include "VectorParser.ct"
316 #include "VectorParser.cti"
323 // c-file-style: "senf"
324 // indent-tabs-mode: nil
325 // ispell-local-dictionary: "american"
326 // compile-command: "scons -u test"
327 // comment-column: 40