4 // Fraunhofer Institute for Open Communication Systems (FOKUS)
6 // The contents of this file are subject to the Fraunhofer FOKUS Public License
7 // Version 1.0 (the "License"); you may not use this file except in compliance
8 // with the License. You may obtain a copy of the License at
9 // http://senf.berlios.de/license.html
11 // The Fraunhofer FOKUS Public License Version 1.0 is based on,
12 // but modifies the Mozilla Public License Version 1.1.
13 // See the full license text for the amendments.
15 // Software distributed under the License is distributed on an "AS IS" basis,
16 // WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
17 // for the specific language governing rights and limitations under the License.
19 // The Original Code is Fraunhofer FOKUS code.
21 // The Initial Developer of the Original Code is Fraunhofer-Gesellschaft e.V.
22 // (registered association), Hansastraße 27 c, 80686 Munich, Germany.
23 // All Rights Reserved.
26 // Thorsten Horstmann <tho@berlios.de>
29 \brief GenericTLV non-inline template implementation */
31 //#include "GenericTLV.ih"
34 #include <boost/io/ios_state.hpp>
35 #include <senf/Utils/hexdump.hh>
36 #include <senf/Utils/TypeInfo.hh>
37 #include <senf/Utils/Format.hh>
40 //-/////////////////////////////////////////////////////////////////////////////////////////////////
42 //-/////////////////////////////////////////////////////////////////////////////////////////////////
43 // senf::GenericTLVParserBase<Base>
46 template <class Parser>
47 prefix_ Parser senf::GenericTLVParserBase<Base>::init()
49 PacketParserBase::size_type oldSize (bytes() );
50 PacketParserBase::size_type newParserSize ( senf::init_bytes<Parser>::value );
51 this->resize( oldSize, newParserSize);
52 std::fill(this->i(), boost::next(this->i(), newParserSize), 0u);
53 Parser concreteParser = Parser(this->i(), this->state() );
54 concreteParser.init();
55 // concreteParser.length() = newParserSize - senf::init_bytes<Base>::value;
56 return concreteParser;
60 prefix_ void senf::GenericTLVParserBase<Base>::dump(std::ostream & os)
63 if (Base::Registry::instance().isRegistered( *this)) {
64 Base::Registry::instance().dump( *this, os);
66 boost::io::ios_all_saver ias(os);
67 os << " GenericTLVParser<" << prettyName(typeid(Base)) << ">\n"
68 << " type: " << format::dumpint(this->type()) << "\n"
69 << " length: " << format::dumpint(this->length()) << "\n"
71 hexdump(value().begin(), value().end(), os);
76 prefix_ senf::PacketInterpreterBase::range senf::GenericTLVParserBase<Base>::value()
79 PacketData::iterator begin ( boost::next(this->i(), senf::bytes( self())) );
80 return PacketInterpreterBase::range(begin, boost::next( begin, this->length()) );
84 template <class ForwardReadableRange>
85 prefix_ void senf::GenericTLVParserBase<Base>::value_(ForwardReadableRange const &range)
87 //typename boost::range_difference<ForwardReadableRange>::type rangeSize ( boost::size(range));
88 unsigned rangeSize ( boost::size(range));
89 if ( rangeSize != this->length() )
90 Base::resize( bytes(), rangeSize + senf::bytes(self()) );
91 std::copy( boost::begin(range), boost::end(range), boost::next(
92 this->i(), senf::bytes( self())) );
93 this->length_() = rangeSize;
97 //-/////////////////////////////////////////////////////////////////////////////////////////////////
98 // senf::GenericTLVParserRegistry<BaseParser,Keytype>
100 template <class BaseParser, class Keytype>
101 template <typename Parser>
102 prefix_ void senf::GenericTLVParserRegistry<BaseParser,Keytype>::registerParser()
104 Keytype key (Parser::typeId+0);
105 SENF_ASSERT_EXPRESSION(
106 map_.insert( key, new detail::GenericTLVParserRegistry_Entry<BaseParser, Parser>()).second,
107 "Duplicate TLV registration");
110 // Wow ... this is stupid .. Boost 1.33 ptr_map API is broken ...
112 #if BOOST_VERSION < 103400
113 #define PTRMAP_GET_CONTENTS(v) (v)
115 #define PTRMAP_GET_CONTENTS(v) (*(v).second)
118 template <class BaseParser, class Keytype>
119 prefix_ void senf::GenericTLVParserRegistry<BaseParser,Keytype>::dump(
120 GenericTLVParser const & parser, std::ostream & os)
123 typename Map::const_iterator i (map_.find( parser.type()));
125 PTRMAP_GET_CONTENTS(*i).dump(parser, os);
128 template <class BaseParser, class Keytype>
129 prefix_ void senf::GenericTLVParserRegistry<BaseParser,Keytype>::dump(
130 GenericTLVParser const & parser, Keytype const & key, std::ostream & os)
133 typename Map::const_iterator i (map_.find( key));
135 PTRMAP_GET_CONTENTS(*i).dump(parser, os);
138 template <class BaseParser, class Keytype>
139 prefix_ senf::PacketParserBase::size_type senf::GenericTLVParserRegistry<BaseParser,Keytype>::bytes(
140 GenericTLVParser const & parser)
143 typename Map::const_iterator i (map_.find( parser.type()));
145 return PTRMAP_GET_CONTENTS(*i).bytes(parser);
147 throw TLVParserNotRegisteredException();
150 template <class BaseParser, class Keytype>
151 prefix_ senf::PacketParserBase::size_type senf::GenericTLVParserRegistry<BaseParser,Keytype>::bytes(
152 GenericTLVParser const & parser, Keytype const & key)
155 typename Map::const_iterator i (map_.find( key));
157 return PTRMAP_GET_CONTENTS(*i).bytes(parser);
159 throw TLVParserNotRegisteredException();
162 #undef PTRMAP_GET_CONTENTS
164 //-/////////////////////////////////////////////////////////////////////////////////////////////////
171 // comment-column: 40
172 // c-file-style: "senf"
173 // indent-tabs-mode: nil
174 // ispell-local-dictionary: "american"
175 // compile-command: "scons -u test"