--- /dev/null
+// $Id$
+//
+// Copyright (C) 2008
+// Fraunhofer Institute for Open Communication Systems (FOKUS)
+// Competence Center NETwork research (NET), St. Augustin, GERMANY
+// Stefan Bund <g0dil@berlios.de>
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License as published by
+// the Free Software Foundation; either version 2 of the License, or
+// (at your option) any later version.
+//
+// This program is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the
+// Free Software Foundation, Inc.,
+// 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+
+/** \file
+ \brief AuxParser inline template implementation */
+
+//#include "AuxParser.ih"
+
+// Custom includes
+
+#define prefix_ inline
+///////////////////////////////cti.p///////////////////////////////////////
+
+///////////////////////////////////////////////////////////////////////////
+// senf::detail::PrefixAuxParserPolicy<P>
+
+template <class P>
+prefix_ typename senf::detail::PrefixAuxParserPolicy<P>::ParserType
+senf::detail::PrefixAuxParserPolicy<P>::aux(PacketParserBase::data_iterator i,
+ PacketParserBase::state_type s)
+ const
+{
+ return ParserType(i, s);
+}
+
+template <class P>
+prefix_ senf::PacketParserBase::data_iterator
+senf::detail::PrefixAuxParserPolicy<P>::adjust(PacketParserBase::data_iterator i,
+ PacketParserBase::state_type s)
+ const
+{
+ return i+ParserType::fixed_bytes;
+}
+
+///////////////////////////////////////////////////////////////////////////
+// senf::detail::FixedAuxParserPolicy<P>
+
+template <class P, unsigned Dist>
+prefix_ typename senf::detail::FixedAuxParserPolicy<P,Dist>::ParserType
+senf::detail::FixedAuxParserPolicy<P,Dist>::aux(PacketParserBase::data_iterator i,
+ PacketParserBase::state_type s)
+ const
+{
+ return ParserType(i-Dist, s);
+}
+
+template <class P, unsigned Dist>
+prefix_ senf::PacketParserBase::data_iterator
+senf::detail::FixedAuxParserPolicy<P,Dist>::adjust(PacketParserBase::data_iterator i,
+ PacketParserBase::state_type s)
+ const
+{
+ return i;
+}
+
+///////////////////////////////////////////////////////////////////////////
+// senf::detail::DynamicAuxParserPolicy<P>
+
+template <class P>
+prefix_ senf::detail::DynamicAuxParserPolicy<P>::DynamicAuxParserPolicy(ParserType p)
+ : p_ (p)
+{}
+
+template <class P>
+prefix_
+senf::detail::DynamicAuxParserPolicy<P>::DynamicAuxParserPolicy(WrapperPolicy const & other)
+ : p_ (* other.p_)
+{}
+
+template <class P>
+prefix_ typename senf::detail::DynamicAuxParserPolicy<P>::ParserType
+senf::detail::DynamicAuxParserPolicy<P>::aux(PacketParserBase::data_iterator i,
+ PacketParserBase::state_type s)
+ const
+{
+ return p_;
+}
+
+template <class P>
+prefix_ senf::PacketParserBase::data_iterator
+senf::detail::DynamicAuxParserPolicy<P>::adjust(PacketParserBase::data_iterator i,
+ PacketParserBase::state_type s)
+ const
+{
+ return i;
+}
+
+///////////////////////////////////////////////////////////////////////////
+// senf::detail::DynamicWrapperAuxParserPolicy<P>
+
+template <class P>
+prefix_ senf::detail::DynamicWrapperAuxParserPolicy<P>::
+DynamicWrapperAuxParserPolicy(ParserPolicy const & other)
+ : p_ (other.p_)
+{}
+
+template <class P>
+prefix_ typename senf::detail::DynamicWrapperAuxParserPolicy<P>::ParserType
+senf::detail::DynamicWrapperAuxParserPolicy<P>::aux(PacketParserBase::data_iterator i,
+ PacketParserBase::state_type s)
+ const
+{
+ return * p_;
+}
+
+template <class P>
+prefix_ senf::PacketParserBase::data_iterator
+senf::detail::DynamicWrapperAuxParserPolicy<P>::adjust(PacketParserBase::data_iterator i,
+ PacketParserBase::state_type s)
+ const
+{
+ return i;
+}
+
+///////////////////////////////cti.e///////////////////////////////////////
+#undef prefix_
+
+\f
+// Local Variables:
+// mode: c++
+// fill-column: 100
+// comment-column: 40
+// c-file-style: "senf"
+// indent-tabs-mode: nil
+// ispell-local-dictionary: "american"
+// compile-command: "scons -u test"
+// End:
--- /dev/null
+// $Id$
+//
+// Copyright (C) 2008
+// Fraunhofer Institute for Open Communication Systems (FOKUS)
+// Competence Center NETwork research (NET), St. Augustin, GERMANY
+// Stefan Bund <g0dil@berlios.de>
+//
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License as published by
+// the Free Software Foundation; either version 2 of the License, or
+// (at your option) any later version.
+//
+// This program is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the
+// Free Software Foundation, Inc.,
+// 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+
+/** \file
+ \brief AuxParser public header */
+
+#ifndef HH_AuxParser_
+#define HH_AuxParser_ 1
+
+#ifndef HH_Packets_
+#error "Don't include 'AuxParser.hh' directly, include 'Packets.hh'"
+#endif
+
+// Custom includes
+#include "PacketParser.hh"
+#include "SafeIterator.hh"
+
+//#include "AuxParser.mpp"
+///////////////////////////////hh.p////////////////////////////////////////
+
+namespace senf {
+namespace detail {
+
+ template <class P>
+ struct PrefixAuxParserPolicy
+ {
+ typedef PrefixAuxParserPolicy WrapperPolicy;
+ typedef P ParserType;
+
+ static PacketParserBase::size_type const aux_bytes = ParserType::fixed_bytes;
+
+ ParserType aux(PacketParserBase::data_iterator i, PacketParserBase::state_type s) const;
+ PacketParserBase::data_iterator adjust(PacketParserBase::data_iterator i, PacketParserBase::state_type s) const;
+ };
+
+ template <class P, unsigned Dist>
+ struct FixedAuxParserPolicy
+ {
+ typedef FixedAuxParserPolicy WrapperPolicy;
+ typedef P ParserType;
+
+ static PacketParserBase::size_type const aux_bytes = 0;
+
+ ParserType aux(PacketParserBase::data_iterator i, PacketParserBase::state_type s) const;
+ PacketParserBase::data_iterator adjust(PacketParserBase::data_iterator i, PacketParserBase::state_type s) const;
+ };
+
+ template <class P> struct DynamicWrapperAuxParserPolicy;
+
+ template <class P>
+ struct DynamicAuxParserPolicy
+ {
+ typedef DynamicWrapperAuxParserPolicy<P> WrapperPolicy;
+ typedef P ParserType;
+
+ static PacketParserBase::size_type const aux_bytes = 0;
+
+ DynamicAuxParserPolicy(ParserType p);
+ DynamicAuxParserPolicy(WrapperPolicy const & other);
+
+ ParserType aux(PacketParserBase::data_iterator i, PacketParserBase::state_type s) const;
+ PacketParserBase::data_iterator adjust(PacketParserBase::data_iterator i, PacketParserBase::state_type s) const;
+
+ ParserType p_;
+ };
+
+ template <class P>
+ struct DynamicWrapperAuxParserPolicy
+ {
+ typedef DynamicAuxParserPolicy<P> ParserPolicy;
+ typedef P ParserType;
+
+ static PacketParserBase::size_type const aux_bytes = 0;
+
+ DynamicWrapperAuxParserPolicy(ParserPolicy const & other);
+
+ ParserType aux(PacketParserBase::data_iterator i, PacketParserBase::state_type s) const;
+ PacketParserBase::data_iterator adjust(PacketParserBase::data_iterator i, PacketParserBase::state_type s) const;
+
+ SafePacketParserWrapper<ParserType> p_;
+ };
+}}
+
+///////////////////////////////hh.e////////////////////////////////////////
+#endif
+#if !defined(HH_Packets__decls_) && !defined(HH_AuxParser_i_)
+#define HH_AuxParser_i_
+//#include "AuxParser.cci"
+//#include "AuxParser.ct"
+#include "AuxParser.cti"
+#endif
+
+\f
+// Local Variables:
+// mode: c++
+// fill-column: 100
+// comment-column: 40
+// c-file-style: "senf"
+// indent-tabs-mode: nil
+// ispell-local-dictionary: "american"
+// compile-command: "scons -u test"
+// End:
return Parser(i,state());
}
+template <class Parser, class Arg>
+prefix_ Parser senf::PacketParserBase::parse(Arg const & arg, data_iterator i)
+ const
+{
+ return Parser(arg, i, state());
+}
+
template <class Parser>
prefix_ Parser senf::PacketParserBase::parse(size_type n)
const
return Parser(boost::next(i(),n),state());
}
+template <class Parser, class Arg>
+prefix_ Parser senf::PacketParserBase::parse(Arg const & arg, size_type n)
+ const
+{
+ return Parser(arg, boost::next(i(),n), state());
+}
+
///////////////////////////////////////////////////////////////////////////
// namespace members
beginning at \a i. Automatically passes \a state() to
the new parser. */
+ template <class Parser, class Arg> Parser parse(Arg const & arg, data_iterator i) const;
+ ///< Create sub-parser
+ /**< This is like parse(data_iterator), however it passes
+ the extra argument \a arg to the \a Parser
+ constructor. */
+
template <class Parser> Parser parse(size_type n) const; ///< Create sub-parser
/**< Creates a new instance of \a Parser to parse data
* beginning at i()<tt> + </tt>\a n. Automatically passes \a
state() to the new parser. */
+ template <class Parser, class Arg> Parser parse(Arg const & arg, size_type n) const;
+ ///< Create sub-parser
+ /**< This is like parse(size_type), however it passes the
+ extra argument \a arg to the \a Parser constructor. */
+
void defaultInit() const; ///< Default implementation
/**< This is just an empty default
implementation. Re-implement this member in your own
PacketParserBase::size_type bytes(Parser p);
namespace detail { template <class Parser> class ParserInitBytes; }
+ namespace detail { template <class Parser> class ParserIsFixed; }
/** \brief Return number of bytes to allocate to new object of given type
struct init_bytes : public detail::ParserInitBytes<Parser>
{};
+ template <class Parser>
+ struct is_fixed : public detail::ParserIsFixed<Parser>
+ {};
+
# ifndef DOXYGEN
template <class Parser>
typename boost::enable_if<
struct ParserInitBytes
: public ParserInitBytes_Choose<Parser,SENF_MPL_RV(ParserInitBytes_Choose_<Parser>(0))> {};
+ template <class Parser, unsigned _>
+ struct ParserIsFixed_Choose
+ : public boost::false_type {};
+
+ template <class Parser>
+ struct ParserIsFixed_Choose<Parser, 1>
+ : public boost::true_type {};
+
+ template <class Parser>
+ struct ParserIsFixed
+ : public ParserIsFixed_Choose<Parser,SENF_MPL_RV(ParserInitBytes_Choose_<Parser>(0))> {};
+
# endif
}}
#include "PacketParser.hh"
#include "SafeIterator.hh"
#include "ArrayParser.hh"
+#include "AuxParser.hh"
#include "ListParser.hh"
#include "ListBParser.hh"
#include "ListNParser.hh"
#include "SafeIterator.hh"
#include "ArrayParser.hh"
#include "IntParser.hh"
+#include "AuxParser.hh"
#include "ListParser.hh"
#include "ListBParser.hh"
#include "ListNParser.hh"
SENF_MPL_SLOT_DEF_ZERO(init_bytes); \
SENF_MPL_SLOT_DEF_ZERO(bit); \
SENF_MPL_SLOT_DEF_ZERO(bitfield_size); \
+ SENF_MPL_SLOT_DEF_ZERO(group); \
void init_chain(senf::mpl::rv<0>*) const {} \
size_type field_offset_(senf::mpl::rv<0>*) const { return 0; } \
public:
#
# define SENF_PARSER_FIELD_I(name, type, ofstype, rwtype, access) \
access: \
+ SENF_PARSER_FIELD_SETUP_I(name, type, ofstype, rwtype, access) \
+ BOOST_PP_CAT(SENF_PARSER_I_FIELD_VAL_, rwtype) (name, type, access) \
+ public:
+#
+# define SENF_PARSER_FIELD_SETUP_I(name, type, ofstype, rwtype, access) \
SENF_PARSER_I_BITFIELD_RESET() \
SENF_PARSER_I_FIELD_INTRO(name, type, access) \
BOOST_PP_CAT(SENF_PARSER_I_FIELD_INIT_, rwtype) (name, type, access) \
name, type, \
BOOST_PP_CAT(SENF_PARSER_I_SIZE_, ofstype) (name, type), \
BOOST_PP_CAT(SENF_PARSER_I_INITBYTES_, ofstype) (name, type), \
- access ) \
- BOOST_PP_CAT(SENF_PARSER_I_FIELD_VAL_, rwtype) (name, type, access) \
- public:
+ BOOST_PP_CAT(SENF_PARSER_I_ISVAR_, ofstype) (name, type), \
+ access )
#
# ////////////////////////////////////////
# // SENF_PARSER_I_FIELD_INTRO
# ////////////////////////////////////////
# // SENF_PARSER_I_ADVANCE_OFS_*
#
-# // Can't call 'name()' here if 'name' is an ro field ...
-# define SENF_PARSER_I_SIZE_var(name, type) senf::bytes(parse<type>(BOOST_PP_CAT(name,_offset)()))
+# define SENF_PARSER_I_SIZE_var(name, type) senf::bytes(BOOST_PP_CAT(name, _)())
# define SENF_PARSER_I_INITBYTES_var(name, type) senf::init_bytes<type>::value
#
# define SENF_PARSER_I_SIZE_fix(name, type) type::fixed_bytes
# define SENF_PARSER_I_INITBYTES_fix(name, type) void
#
-# define SENF_PARSER_I_ADVANCE_OFS_var(name, type, size, isize, access) \
+# define SENF_PARSER_I_ISVAR_fix(name, type) 0
+# define SENF_PARSER_I_ISVAR_var(name, type) (senf::is_fixed<type>::value?0:1)
+#
+# define SENF_PARSER_I_ADVANCE_OFS_var(name, type, size, isize, isvar, access) \
size_type BOOST_PP_CAT(name, _next_offset)() const { \
return BOOST_PP_CAT(name,_offset)() + size; \
} \
return BOOST_PP_CAT(name, _next_offset)(); \
} \
SENF_MPL_SLOT_SET(init_bytes, BOOST_PP_CAT(name,_next_init_bytes)); \
+ static size_type const BOOST_PP_CAT(name, _group) = SENF_MPL_SLOT_GET(group) + isvar; \
+ SENF_MPL_SLOT_SET(group, BOOST_PP_CAT(name, _group)); \
access:
#
-# define SENF_PARSER_I_ADVANCE_OFS_fix(name, type, size, isize, access) \
+# define SENF_PARSER_I_ADVANCE_OFS_fix(name, type, size, isize, isvar, access) \
static size_type const BOOST_PP_CAT(name, _next_offset) = \
BOOST_PP_CAT(name, _offset) + size; \
private: \
# // SENF_PARSER_I_FIELD_VAL_*
#
# define SENF_PARSER_I_FIELD_VAL_rw(name, type, access) \
- BOOST_PP_CAT(name, _t) name() const { \
+ private: \
+ BOOST_PP_CAT(name, _t) BOOST_PP_CAT(name, _)() const { \
return parse<type>( SENF_PARSER_OFFSET(name) ); \
+ } \
+ access: \
+ BOOST_PP_CAT(name, _t) name() const { \
+ return BOOST_PP_CAT(name,_)(); \
}
#
# define SENF_PARSER_I_FIELD_VAL_ro(name, type, access) \
SENF_PARSER_I_FIELD_INTRO(name, type, public) \
SENF_PARSER_I_FIELD_INIT_ro(name, type, public) \
BOOST_PP_CAT(SENF_PARSER_I_FIELD_OFS_, ofstype) (name, type, public) \
- BOOST_PP_CAT(SENF_PARSER_I_ADVANCE_OFS_, ofstype) (name, type, size, isize, public) \
+ BOOST_PP_CAT(SENF_PARSER_I_ADVANCE_OFS_, ofstype) (name, type, size, isize, 1, public) \
BOOST_PP_CAT(name, _t) name() const
#
# ///////////////////////////////////////////////////////////////////////////
BOOST_PP_CAT(SENF_PARSER_I_ADVANCE_OFS_, ofstype) ( \
name, type, \
BOOST_PP_CAT(name, _t)::fixed_bytes, BOOST_PP_CAT(name, _t)::fixed_bytes, \
+ 0, \
access) \
private: \
SENF_MPL_SLOT_SET(bitfield_size, BOOST_PP_CAT(name, _t)::fixed_bytes); \
SENF_PARSER_I_FIELD_INTRO(name, void, private) \
SENF_PARSER_I_FIELD_INIT_ro(name, void, private) \
BOOST_PP_CAT(SENF_PARSER_I_FIELD_OFS_, ofstype) (name, type, access) \
- BOOST_PP_CAT(SENF_PARSER_I_ADVANCE_OFS_, ofstype) (name, void, bytes, ibytes, private) \
+ BOOST_PP_CAT(SENF_PARSER_I_ADVANCE_OFS_, ofstype) (name, void, bytes, ibytes, 1, \
+ private) \
public:
#
# ///////////////////////////////////////////////////////////////////////////
SENF_PARSER_I_FIELD_INTRO(name, void, access) \
SENF_PARSER_I_FIELD_INIT_ro(name, void, access) \
BOOST_PP_CAT(SENF_PARSER_I_FIELD_OFS_, ofstype) (name, type, access) \
- BOOST_PP_CAT(SENF_PARSER_I_ADVANCE_OFS_, ofstype) (name, void, 0, 0,access) \
+ BOOST_PP_CAT(SENF_PARSER_I_ADVANCE_OFS_, ofstype) (name, void, 0, 0, 0, access) \
public:
#
# ///////////////////////////////////////////////////////////////////////////
# define SENF_PARSER_FIXED_OFFSET_var(name) BOOST_PP_CAT(name, _init_bytes)
#
# ///////////////////////////////////////////////////////////////////////////
-# // SENF_PARSER_FIXED_OFFSET_*
+# // SENF_PARSER_CURRENT_FIXED_OFFSET_*
#
# define SENF_PARSER_CURRENT_FIXED_OFFSET_fix() SENF_MPL_SLOT_GET(offset)
# define SENF_PARSER_CURRENT_FIXED_OFFSET_var() SENF_MPL_SLOT_GET(init_bytes)
public: \
void init() const { init(0); }
#
+# ///////////////////////////////////////////////////////////////////////////
+# // SENF_PARSER_REQUIRE_VAR
+#
+# define SENF_PARSER_REQUIRE_VAR(description) \
+ BOOST_PP_CAT(SENF_PARSER_REQUIRE_VAR_, SENF_PARSER_TYPE)(description)
+#
+# define SENF_PARSER_REQUIRE_VAR_var(description)
+#
+# define SENF_PARSER_REQUIRE_VAR_fix(description) \
+ typedef BOOST_PP_CAT( PARSER_ERROR__, \
+ BOOST_PP_CAT(description, _not_allowed_in_fixed_parser) ) \
+ BOOST_PP_CAT(errsym_, __LINE__);
+#
+# ///////////////////////////////////////////////////////////////////////////
+# // SENF_PARSER_COLLECTION_I
+#
+ namespace senf { namespace detail { namespace auxtag { struct none {}; } } }
+#
+# define SENF_PARSER_COLLECTION_I(access, name, aux, traits) \
+ private: \
+ BOOST_PP_CAT(SENF_PARSER_COLLECTION_AUXTYPE_, SENF_PARSER_TYPE)(name, aux) \
+ typedef BOOST_PP_CAT(SENF_PARSER_COLLECTION_AUX_I_, SENF_PARSER_TYPE)(name, aux) \
+ BOOST_PP_CAT(name,_aux_policy); \
+ typedef traits::parser< \
+ BOOST_PP_CAT(name,_aux_policy), \
+ senf::detail::auxtag::none \
+ >::type BOOST_PP_CAT(name, _collection_t); \
+ access: \
+ SENF_PARSER_FIELD_SETUP_I( name, \
+ BOOST_PP_CAT(name, _collection_t), \
+ SENF_PARSER_TYPE, \
+ rw, \
+ access ) \
+ BOOST_PP_CAT(SENF_PARSER_COLLECTION_VAL_, SENF_PARSER_TYPE)(name, aux, access) \
+ public:
+#
+# define SENF_PARSER_COLLECTION_AUXTYPE_var(name, aux) \
+ static bool const BOOST_PP_CAT(name, _aux_fixed) = \
+ (SENF_MPL_SLOT_GET(group) - BOOST_PP_CAT(aux, _group) == 0);
+#
+# define SENF_PARSER_COLLECTION_AUXTYPE_fix(name, aux)
+#
+ namespace senf { namespace detail {
+ template <class Parser> struct DynamicAuxParserPolicy;
+ template <class Parser, unsigned offset> struct FixedAuxParserPolicy;
+ template <class Parser, unsigned fixedOffset, bool fixedDelta>
+ struct ParserAuxPolicySelect
+ { typedef senf::detail::DynamicAuxParserPolicy<Parser> type; };
+ template <class Parser, unsigned fixedOffset>
+ struct ParserAuxPolicySelect<Parser, fixedOffset, true>
+ { typedef senf::detail::FixedAuxParserPolicy<Parser, fixedOffset> type; };
+ }};
+#
+# define SENF_PARSER_COLLECTION_AUX_I_var(name, aux) \
+ senf::detail::ParserAuxPolicySelect< BOOST_PP_CAT(aux, _t), \
+ SENF_PARSER_CURRENT_FIXED_OFFSET() \
+ - SENF_PARSER_FIXED_OFFSET(aux), \
+ BOOST_PP_CAT(name, _aux_fixed) >::type
+#
+# define SENF_PARSER_COLLECTION_AUX_I_fix(name, aux) \
+ senf::detail::FixedAuxParserPolicy< BOOST_PP_CAT(aux, _t), \
+ SENF_PARSER_CURRENT_FIXED_OFFSET() \
+ - SENF_PARSER_FIXED_OFFSET(aux) >
+#
+# define SENF_PARSER_COLLECTION_VAL_var(name,aux,access) \
+ private: \
+ template <class T> T BOOST_PP_CAT(name, _dispatch)(boost::true_type) const \
+ { return parse<T>( SENF_PARSER_OFFSET(name) ); } \
+ template <class T> T BOOST_PP_CAT(name, _dispatch)(boost::false_type) const \
+ { return parse<T>( BOOST_PP_CAT(name, _aux_policy)(aux()), SENF_PARSER_OFFSET(name) ); } \
+ BOOST_PP_CAT(name, _t) BOOST_PP_CAT(name, _)() const \
+ { return BOOST_PP_CAT(name, _dispatch) <BOOST_PP_CAT(name, _t)>( \
+ boost::integral_constant<bool, BOOST_PP_CAT(name, _aux_fixed)>()); } \
+ access: \
+ BOOST_PP_CAT(name, _t) name() const \
+ { return BOOST_PP_CAT(name, _)(); }
+#
+# define SENF_PARSER_COLLECTION_VAL_fix(name,aux,access) \
+ private: \
+ BOOST_PP_CAT(name, _t) BOOST_PP_CAT(name, _)() const \
+ { return parse<BOOST_PP_CAT(name, _t)>( SENF_PARSER_OFFSET(name) ); } \
+ access: \
+ BOOST_PP_CAT(name, _t) name() const \
+ { return BOOST_PP_CAT(name, _)(); }
+#
# ////////////////////////////////ih.e///////////////////////////////////////
# endif
#
prefix_ void senf::VectorParser<ElementParser,Sizer>::init()
const
{
- sizer_.init(i(),state());
+ aux(i(), state()) = 0;
iterator i (begin());
iterator const e (end());
for (; i!=e; ++i)
///////////////////////////////////////////////////////////////////////////
// senf::VectorParser<ElementParser,Sizer>
-template <class ElementParser, class Sizer>
-prefix_ senf::VectorParser<ElementParser,Sizer>::VectorParser(data_iterator i, state_type s)
- : PacketParserBase(i,s), sizer_()
+template <class ElementParser, class AuxPolicy>
+prefix_ senf::VectorParser<ElementParser,AuxPolicy>::VectorParser(data_iterator i, state_type s)
+ : PacketParserBase(i,s), AuxPolicy()
{}
-template <class ElementParser, class Sizer>
-prefix_ senf::VectorParser<ElementParser,Sizer>::VectorParser(Sizer sizer, data_iterator i,
- state_type s)
- : PacketParserBase(i,s), sizer_(sizer)
+template <class ElementParser, class AuxPolicy>
+prefix_ senf::VectorParser<ElementParser,AuxPolicy>::VectorParser(AuxPolicy policy,
+ data_iterator i, state_type s)
+ : PacketParserBase(i,s), AuxPolicy(policy)
{}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser<ElementParser,Sizer>::size_type
-senf::VectorParser<ElementParser,Sizer>::bytes()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser<ElementParser,AuxPolicy>::size_type
+senf::VectorParser<ElementParser,AuxPolicy>::bytes()
const
{
- return size()*ElementParser::fixed_bytes + sizer_.bytes(i(),state());
+ return size()*ElementParser::fixed_bytes + AuxPolicy::aux_bytes;
}
// Container interface
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser<ElementParser,Sizer>::size_type
-senf::VectorParser<ElementParser,Sizer>::size()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser<ElementParser,AuxPolicy>::size_type
+senf::VectorParser<ElementParser,AuxPolicy>::size()
const
{
- return sizer_.size(i(),state());
+ return aux(i(),state());
}
-template <class ElementParser, class Sizer>
-prefix_ bool senf::VectorParser<ElementParser,Sizer>::empty()
+template <class ElementParser, class AuxPolicy>
+prefix_ bool senf::VectorParser<ElementParser,AuxPolicy>::empty()
const
{
return size()==0;
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser<ElementParser,Sizer>::iterator
-senf::VectorParser<ElementParser,Sizer>::begin()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser<ElementParser,AuxPolicy>::iterator
+senf::VectorParser<ElementParser,AuxPolicy>::begin()
const
{
- return iterator(sizer_.begin(i(),state()),state());
+ return iterator(adjust(i(),state()),state());
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser<ElementParser,Sizer>::iterator
-senf::VectorParser<ElementParser,Sizer>::end()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser<ElementParser,AuxPolicy>::iterator
+senf::VectorParser<ElementParser,AuxPolicy>::end()
const
{
return boost::next(begin(),size());
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser<ElementParser,Sizer>::value_type
-senf::VectorParser<ElementParser,Sizer>::operator[](difference_type i)
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser<ElementParser,AuxPolicy>::value_type
+senf::VectorParser<ElementParser,AuxPolicy>::operator[](difference_type i)
const
{
return begin()[i];
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser<ElementParser,Sizer>::value_type
-senf::VectorParser<ElementParser,Sizer>::front()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser<ElementParser,AuxPolicy>::value_type
+senf::VectorParser<ElementParser,AuxPolicy>::front()
const
{
return begin()[0];
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser<ElementParser,Sizer>::value_type
-senf::VectorParser<ElementParser,Sizer>::back()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser<ElementParser,AuxPolicy>::value_type
+senf::VectorParser<ElementParser,AuxPolicy>::back()
const
{
return begin()[size()-1];
// Mutators
-template <class ElementParser, class Sizer>
+template <class ElementParser, class AuxPolicy>
template <class Value>
-prefix_ void senf::VectorParser<ElementParser,Sizer>::push_back(Value value, size_type n)
+prefix_ void senf::VectorParser<ElementParser,AuxPolicy>::push_back(Value value, size_type n)
const
{
container c (*this);
c.push_back(value,n);
}
-template <class ElementParser, class Sizer>
-prefix_ void senf::VectorParser<ElementParser,Sizer>::push_back_space(size_type n)
+template <class ElementParser, class AuxPolicy>
+prefix_ void senf::VectorParser<ElementParser,AuxPolicy>::push_back_space(size_type n)
const
{
container c (*this);
c.push_back_space(n);
}
-template <class ElementParser, class Sizer>
+template <class ElementParser, class AuxPolicy>
template <class Value>
-prefix_ void senf::VectorParser<ElementParser,Sizer>::push_front(Value value, size_type n)
+prefix_ void senf::VectorParser<ElementParser,AuxPolicy>::push_front(Value value, size_type n)
const
{
container c (*this);
c.push_front(value,n);
}
-template <class ElementParser, class Sizer>
-prefix_ void senf::VectorParser<ElementParser,Sizer>::push_front_space(size_type n)
+template <class ElementParser, class AuxPolicy>
+prefix_ void senf::VectorParser<ElementParser,AuxPolicy>::push_front_space(size_type n)
const
{
container c (*this);
c.push_front_space(n);
}
-template <class ElementParser, class Sizer>
-prefix_ void senf::VectorParser<ElementParser,Sizer>::resize(size_type n)
+template <class ElementParser, class AuxPolicy>
+prefix_ void senf::VectorParser<ElementParser,AuxPolicy>::resize(size_type n)
const
{
container c (*this);
c.resize(n);
}
-template <class ElementParser, class Sizer>
+template <class ElementParser, class AuxPolicy>
template <class Value>
-prefix_ void senf::VectorParser<ElementParser,Sizer>::resize(size_type n, Value value)
+prefix_ void senf::VectorParser<ElementParser,AuxPolicy>::resize(size_type n, Value value)
const
{
container c (*this);
}
///////////////////////////////////////////////////////////////////////////
-// senf::SimpleSizeParser<SizeParser,offset>
-
-template <class SizeParser, unsigned Distance>
-prefix_ typename senf::detail::VectorNParser_Sizer<SizeParser,Distance>::size_type
-senf::detail::VectorNParser_Sizer<SizeParser,Distance>::size(iterator i, state_type s)
- const
-{
- return SizeParser(boost::prior(i, Distance), s).value();
-}
-
-template <class SizeParser, unsigned Distance>
-prefix_ void senf::detail::VectorNParser_Sizer<SizeParser,Distance>::size(iterator i,
- state_type s,
- size_type v)
- const
-{
- SizeParser(boost::prior(i, Distance), s).value(v);
-}
-
-template <class SizeParser, unsigned Distance>
-prefix_ typename senf::detail::VectorNParser_Sizer<SizeParser,Distance>::iterator
-senf::detail::VectorNParser_Sizer<SizeParser,Distance>::begin(iterator i, state_type s)
- const
-{
- return i;
-}
-
-template <class SizeParser, unsigned Distance>
-prefix_ typename senf::detail::VectorNParser_Sizer<SizeParser,Distance>::size_type
-senf::detail::VectorNParser_Sizer<SizeParser,Distance>::bytes(iterator i, state_type s)
- const
-{
- return 0;
-}
-
-template <class SizeParser, unsigned Distance>
-prefix_ void senf::detail::VectorNParser_Sizer<SizeParser,Distance>::init(iterator i,
- state_type s)
- const
-{}
-
-///////////////////////////////////////////////////////////////////////////
// senf::VectorParser_wrapper<Parser,SizeParser,Container>
// structors and default members
// hm ... be careful here ! the data() member is called in an incompletely intitialized
// instance. However, data() only depends on state_ which is initialized before the call. YOU MUST
// NOT CHANGE THE ORDERING OF THE DATA MEMBERS
-template <class ElementParser, class Sizer>
-prefix_ senf::VectorParser_Container<ElementParser,Sizer>::
+template <class ElementParser, class AuxPolicy>
+prefix_ senf::VectorParser_Container<ElementParser,AuxPolicy>::
VectorParser_Container(parser_type const & vector)
- : sizer_ (vector.sizer_), state_ (vector.state()),
+ : AuxPolicy(vector), state_ (vector.state()),
i_ (std::distance(data().begin(),vector.i()))
{}
// accessors
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser_Container<ElementParser,Sizer>::size_type
-senf::VectorParser_Container<ElementParser,Sizer>::size()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser_Container<ElementParser,AuxPolicy>::size_type
+senf::VectorParser_Container<ElementParser,AuxPolicy>::size()
const
{
- return sizer_.size(i(),state());
+ return aux(i(),state());
}
-template <class ElementParser, class Sizer>
-prefix_ bool senf::VectorParser_Container<ElementParser,Sizer>::empty()
+template <class ElementParser, class AuxPolicy>
+prefix_ bool senf::VectorParser_Container<ElementParser,AuxPolicy>::empty()
const
{
return size() == 0;
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser_Container<ElementParser,Sizer>::iterator
-senf::VectorParser_Container<ElementParser,Sizer>::begin()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser_Container<ElementParser,AuxPolicy>::iterator
+senf::VectorParser_Container<ElementParser,AuxPolicy>::begin()
const
{
- return iterator(sizer_.begin(i(),state()),state());
+ return iterator(adjust(i(),state()),state());
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser_Container<ElementParser,Sizer>::iterator
-senf::VectorParser_Container<ElementParser,Sizer>::end()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser_Container<ElementParser,AuxPolicy>::iterator
+senf::VectorParser_Container<ElementParser,AuxPolicy>::end()
const
{
return boost::next(begin(),size());
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser_Container<ElementParser,Sizer>::value_type
-senf::VectorParser_Container<ElementParser,Sizer>::operator[](difference_type i)
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser_Container<ElementParser,AuxPolicy>::value_type
+senf::VectorParser_Container<ElementParser,AuxPolicy>::operator[](difference_type i)
const
{
return begin()[i];
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser_Container<ElementParser,Sizer>::value_type
-senf::VectorParser_Container<ElementParser,Sizer>::front()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser_Container<ElementParser,AuxPolicy>::value_type
+senf::VectorParser_Container<ElementParser,AuxPolicy>::front()
const
{
return begin()[0];
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser_Container<ElementParser,Sizer>::value_type
-senf::VectorParser_Container<ElementParser,Sizer>::back()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser_Container<ElementParser,AuxPolicy>::value_type
+senf::VectorParser_Container<ElementParser,AuxPolicy>::back()
const
{
return begin()[size()-1];
// Mutators
-template <class ElementParser, class Sizer>
+template <class ElementParser, class AuxPolicy>
template <class Value>
-prefix_ void senf::VectorParser_Container<ElementParser,Sizer>::insert(iterator pos,
+prefix_ void senf::VectorParser_Container<ElementParser,AuxPolicy>::insert(iterator pos,
Value const & t)
{
*shift(pos) << t;
}
-template <class ElementParser, class Sizer>
-prefix_ void senf::VectorParser_Container<ElementParser,Sizer>::erase(iterator pos, size_type n)
+template <class ElementParser, class AuxPolicy>
+prefix_ void senf::VectorParser_Container<ElementParser,AuxPolicy>::erase(iterator pos, size_type n)
{
data().erase(pos.raw(),boost::next(pos.raw(),n*ElementParser::fixed_bytes));
setSize(size()-n);
}
-template <class ElementParser, class Sizer>
-prefix_ void senf::VectorParser_Container<ElementParser,Sizer>::erase(iterator f, iterator l)
+template <class ElementParser, class AuxPolicy>
+prefix_ void senf::VectorParser_Container<ElementParser,AuxPolicy>::erase(iterator f, iterator l)
{
erase(f,std::distance(f,l));
}
-template <class ElementParser, class Sizer>
-prefix_ void senf::VectorParser_Container<ElementParser,Sizer>::clear()
+template <class ElementParser, class AuxPolicy>
+prefix_ void senf::VectorParser_Container<ElementParser,AuxPolicy>::clear()
{
erase(begin(),end());
}
-template <class ElementParser, class Sizer>
+template <class ElementParser, class AuxPolicy>
template <class Value>
-prefix_ void senf::VectorParser_Container<ElementParser,Sizer>::push_back(Value value,
+prefix_ void senf::VectorParser_Container<ElementParser,AuxPolicy>::push_back(Value value,
size_type n)
{
insert(end(),n,value);
}
-template <class ElementParser, class Sizer>
-prefix_ void senf::VectorParser_Container<ElementParser,Sizer>::push_back_space(size_type n)
+template <class ElementParser, class AuxPolicy>
+prefix_ void senf::VectorParser_Container<ElementParser,AuxPolicy>::push_back_space(size_type n)
{
shift(end(),n);
}
-template <class ElementParser, class Sizer>
+template <class ElementParser, class AuxPolicy>
template <class Value>
-prefix_ void senf::VectorParser_Container<ElementParser,Sizer>::push_front(Value value,
+prefix_ void senf::VectorParser_Container<ElementParser,AuxPolicy>::push_front(Value value,
size_type n)
{
insert(begin(),n,value);
}
-template <class ElementParser, class Sizer>
-prefix_ void senf::VectorParser_Container<ElementParser,Sizer>::push_front_space(size_type n)
+template <class ElementParser, class AuxPolicy>
+prefix_ void senf::VectorParser_Container<ElementParser,AuxPolicy>::push_front_space(size_type n)
{
shift(begin(),n);
}
// Parser interface
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser_Container<ElementParser,Sizer>::parser_type
-senf::VectorParser_Container<ElementParser,Sizer>::parser()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser_Container<ElementParser,AuxPolicy>::parser_type
+senf::VectorParser_Container<ElementParser,AuxPolicy>::parser()
const
{
return parser_type(i(),state());
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser_Container<ElementParser,Sizer>::data_iterator
-senf::VectorParser_Container<ElementParser,Sizer>::i()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser_Container<ElementParser,AuxPolicy>::data_iterator
+senf::VectorParser_Container<ElementParser,AuxPolicy>::i()
const
{
return boost::next(data().begin(),i_);
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser_Container<ElementParser,Sizer>::state_type
-senf::VectorParser_Container<ElementParser,Sizer>::state()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser_Container<ElementParser,AuxPolicy>::state_type
+senf::VectorParser_Container<ElementParser,AuxPolicy>::state()
const
{
return state_;
}
-template <class ElementParser, class Sizer>
+template <class ElementParser, class AuxPolicy>
prefix_ senf::PacketData &
-senf::VectorParser_Container<ElementParser,Sizer>::data()
+senf::VectorParser_Container<ElementParser,AuxPolicy>::data()
const
{
return *state_;
}
-template <class ElementParser, class Sizer>
-prefix_ typename senf::VectorParser_Container<ElementParser,Sizer>::size_type
-senf::VectorParser_Container<ElementParser,Sizer>::bytes()
+template <class ElementParser, class AuxPolicy>
+prefix_ typename senf::VectorParser_Container<ElementParser,AuxPolicy>::size_type
+senf::VectorParser_Container<ElementParser,AuxPolicy>::bytes()
const
{
- return size()*ElementParser::fixed_bytes + sizer_.bytes(i(),state());
+ return size()*ElementParser::fixed_bytes + AuxPolicy::aux_bytes;
}
// private members
-template <class ElementParser, class Sizer>
-prefix_ void senf::VectorParser_Container<ElementParser,Sizer>::setSize(size_type value)
+template <class ElementParser, class AuxPolicy>
+prefix_ void senf::VectorParser_Container<ElementParser,AuxPolicy>::setSize(size_type value)
{
- sizer_.size(i(),state(),value);
+ aux(i(),state()).value(value);
}
/////////////////////////////cti.e///////////////////////////////////////
#include <boost/type_traits.hpp>
#include "PacketParser.hh"
#include "ArrayParser.hh" // for ArrayParser_iterator
+#include "AuxParser.hh" // for the AuxPolicies
//#include "VectorParser.mpp"
-#include "VectorParser.ih"
///////////////////////////////hh.p////////////////////////////////////////
namespace senf {
\see ExampleVectorPolicy
\ingroup parsecollection
*/
- template <class ElementParser, class Sizer>
- struct VectorParser : public PacketParserBase
+ template <class ElementParser, class AuxPolicy>
+ struct VectorParser
+ : public PacketParserBase,
+ private AuxPolicy
{
VectorParser(data_iterator i, state_type s);
- VectorParser(Sizer sizer, data_iterator i, state_type s);
+ VectorParser(AuxPolicy policy, data_iterator i, state_type s);
///< Additional sizer specific constructor
/**< This constructor may be used, if the sizer needs
additional parameters. */
size_type bytes() const;
void init() const;
- static const size_type init_bytes = Sizer::init_bytes;
+ static const size_type init_bytes = AuxPolicy::aux_bytes;
///////////////////////////////////////////////////////////////////////////
// Container interface
typedef ElementParser value_type;
typedef detail::ArrayParser_iterator<value_type> iterator;
typedef iterator const_iterator;
- typedef VectorParser_Container<ElementParser,Sizer> container;
+ typedef VectorParser_Container<ElementParser,AuxPolicy> container;
size_type size() const;
bool empty() const;
template <class Value> void resize (size_type n, Value value) const;
private:
- Sizer sizer_;
- friend class VectorParser_Container<ElementParser,Sizer>;
- };
-
- /** \brief Vector with prefix sizing
-
- This is a 'template typedef'. It defines a vector with a <em>directly preceding</em> size
- field holding the number of vector elements. The size field is considered part of the
- vector.
- \code
- // Define MyVector as a vector of 16bit unsigned elements with a directly preceding
- // 8bit unsigned size field
- typedef senf::VectorNParser<senf::UInt16Parser, senf::UInt8Parser>::parser MyVector;
- \endcode
-
- \param ElementParser \e fixed-size parser for parsing the vector elements
- \param SizeParser parser for parsing the vector size (number of elements)
-
- \see VectorParser
- \ingroup parsecollection
- */
- template <class ElementParser, class SizeParser, unsigned Distance>
- struct VectorNParser
- {
- typedef VectorParser< ElementParser,
- detail::VectorNParser_Sizer<SizeParser, Distance> > parser;
+ friend class VectorParser_Container<ElementParser,AuxPolicy>;
};
/** \brief Define VectorNParser field
// The size field should be declared private (size is accessible via the vector)
SENF_PARSER_PRIVATE_FIELD ( vec_size_, senf::UInt16Parser );
// Define the vector, here it has 32bit unsigned integer elements
- SENF_PARSER_VEC_N ( vec, _vec_size, senf::UInt32Parser );
+ SENF_PARSER_VEC_N ( vec, vec_size_, senf::UInt32Parser );
\endcode
\param[in] name field name
# define SENF_PARSER_PRIVATE_VEC_N(name, size, elt_type) \
SENF_PARSER_VEC_N_I(SENF_PARSER_PRIVATE_FIELD, name, size, elt_type)
+# define SENF_PARSER_VECTOR(name, size, elt_type) \
+ SENF_PARSER_VECTOR_I(public, name, size, elt_type)
+
+# define SENF_PARSER_PRIVATE_VECTOR(name, size, elt_type) \
+ SENF_PARSER_VECTOR_I(private, name, size, elt_type)
+
+
+
/** \brief VectorParser container wrapper
This is the container wrapper used for vector parsers. The container wrapper will stay valid
\see VectorParser
*/
- template <class ElementParser, class Sizer>
+ template <class ElementParser, class AuxPolicy>
class VectorParser_Container
+ : private AuxPolicy
{
public:
///////////////////////////////////////////////////////////////////////////
// Types
- typedef VectorParser<ElementParser,Sizer> parser_type;
+ typedef VectorParser<ElementParser,AuxPolicy> parser_type;
typedef PacketParserBase::data_iterator data_iterator;
typedef PacketParserBase::size_type size_type;
typedef PacketParserBase::difference_type difference_type;
private:
void setSize(size_type value);
- Sizer sizer_;
state_type state_;
size_type i_;
};
namespace senf {
namespace detail {
- /** \brief Internal: Sizer implementing prefix sizing
-
- \internal
+# define SENF_PARSER_VEC_N_I(field, name, size, elt_type) \
+ typedef senf::VectorParser< \
+ elt_type, \
+ senf::detail::FixedAuxParserPolicy< BOOST_PP_CAT(size, _t), \
+ SENF_PARSER_CURRENT_FIXED_OFFSET() \
+ - SENF_PARSER_FIXED_OFFSET(size) > \
+ > BOOST_PP_CAT(name, _vec_t); \
+ field( name, BOOST_PP_CAT(name, _vec_t) )
- This is the sizer policy used by VectorNParser
- */
- template <class SizeParser, unsigned Distance>
- struct VectorNParser_Sizer
+ template <class ElementParser>
+ struct VectorParserTraits
{
- typedef PacketParserBase::size_type size_type;
- typedef PacketParserBase::data_iterator iterator;
- typedef PacketParserBase::state_type state_type;
-
- static const size_type init_bytes = 0;
-
- size_type size (iterator i, state_type s) const;
- void size (iterator i, state_type s, size_type v) const;
- iterator begin (iterator i, state_type s) const;
- size_type bytes (iterator i, state_type s) const;
- void init (iterator i, state_type s) const;
+ template <class AuxPolicy, class AuxTag>
+ struct parser {
+ typedef senf::VectorParser<ElementParser, AuxPolicy> type;
+ };
};
-# define SENF_PARSER_VEC_N_I(field, name, size, elt_type) \
- typedef senf::VectorNParser< elt_type, \
- BOOST_PP_CAT(size, _t), \
- SENF_PARSER_CURRENT_FIXED_OFFSET() \
- - SENF_PARSER_FIXED_OFFSET(size) \
- >::parser BOOST_PP_CAT(name, _vec_t); \
- field( name, BOOST_PP_CAT(name, _vec_t) )
-}}
+# define SENF_PARSER_VECTOR_I(access, name, size, elt_type) \
+ SENF_PARSER_REQUIRE_VAR(vector) \
+ SENF_PARSER_COLLECTION_I( access, \
+ name, \
+ size, \
+ senf::detail::VectorParserTraits<elt_type> )
+}}
+
///////////////////////////////ih.e////////////////////////////////////////
#endif
senf::PacketInterpreterBase::ptr p (senf::PacketInterpreter<VoidPacket>::create(data));
typedef senf::VectorParser<
senf::UInt16Parser,
- senf::detail::VectorNParser_Sizer<senf::UInt8Parser, 1u>
+ senf::detail::FixedAuxParserPolicy<senf::UInt8Parser, 1u>
> UInt16VectorParser;
{
senf::PacketInterpreterBase::ptr p (senf::PacketInterpreter<VoidPacket>::create(data));
typedef senf::VectorParser<
senf::UInt16Parser,
- senf::detail::VectorNParser_Sizer<senf::UInt8Parser, 1u>
+ senf::detail::FixedAuxParserPolicy<senf::UInt8Parser, 1u>
> UInt16VectorParser;
UInt16VectorParser v (boost::next(p->data().begin(),1), &p->data());
UInt16VectorParser::container w (v);
BOOST_CHECK_EQUAL( w.parser().size(), 0u );
}
+BOOST_AUTO_UNIT_TEST(dynamicPolicyVector)
+{
+ unsigned char data[] = { 0x03, // size
+ 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, // data
+ 0x20, 0x21, 0x22, 0x23, 0x24, 0x25 };
+ senf::PacketInterpreterBase::ptr p (senf::PacketInterpreter<VoidPacket>::create(data));
+
+ typedef senf::VectorParser<
+ senf::UInt16Parser,
+ senf::detail::DynamicAuxParserPolicy<senf::UInt8Parser>
+ > UInt16VectorParser;
+
+ UInt16VectorParser v (senf::UInt8Parser(p->data().begin(), &p->data()),
+ boost::next(p->data().begin(),1), &p->data());
+ UInt16VectorParser::container w (v);
+
+ BOOST_CHECK_EQUAL( v.size(), 3u );
+ BOOST_CHECK_EQUAL( w.size(), 3u );
+
+ BOOST_CHECK_EQUAL( v[0], 0x1011 );
+ BOOST_CHECK_EQUAL( v[2], 0x1415 );
+
+ BOOST_CHECK_EQUAL( w[0], 0x1011 );
+ BOOST_CHECK_EQUAL( w[2], 0x1415 );
+}
+
+namespace {
+
+ struct TestVectorParser
+ : public senf::PacketParserBase
+ {
+# include SENF_PARSER()
+
+ SENF_PARSER_PRIVATE_FIELD ( size1 , senf::UInt8Parser );
+ SENF_PARSER_PRIVATE_FIELD ( size2 , senf::UInt8Parser );
+ SENF_PARSER_FIELD ( dummy , senf::UInt32Parser );
+ SENF_PARSER_VECTOR ( vec1 , size1, senf::UInt16Parser );
+ SENF_PARSER_VECTOR ( vec2 , size2, senf::UInt16Parser );
+
+ SENF_PARSER_FINALIZE( TestVectorParser );
+ };
+
+}
+
+BOOST_AUTO_UNIT_TEST(vectorMacro)
+{
+ unsigned char data[] = { 0x03, // size1
+ 0x02, // size2
+ 0x01, 0x02, 0x03, 0x04, // dummy
+ 0x05, 0x06, // vec1[0]
+ 0x07, 0x08, // vec1[1]
+ 0x09, 0x0A, // vec1[2]
+ 0x0B, 0x0C, // vec2[0]
+ 0x0D, 0x0E }; // vec2[1]
+
+ senf::DataPacket p (senf::DataPacket::create(data));
+ TestVectorParser parser (p.data().begin(), &p.data());
+
+ BOOST_CHECK_EQUAL( parser.vec1().size(), 3u );
+ BOOST_CHECK_EQUAL( parser.vec2().size(), 2u );
+ BOOST_CHECK_EQUAL( parser.dummy(), 0x01020304u );
+ BOOST_CHECK_EQUAL( parser.vec1()[0], 0x0506u );
+ BOOST_CHECK_EQUAL( parser.vec1()[1], 0x0708u );
+ BOOST_CHECK_EQUAL( parser.vec1()[2], 0x090Au );
+ BOOST_CHECK_EQUAL( parser.vec2()[0], 0x0B0Cu );
+ BOOST_CHECK_EQUAL( parser.vec2()[1], 0x0D0Eu );
+}
+
///////////////////////////////cc.e////////////////////////////////////////
#undef prefix_