72715e7ea4bdf5b5c25ccd9b41388ae9781f3e08
[senf.git] / Packets / PacketInterpreter.ct
1 // $Id$
2 //
3 // Copyright (C) 2007 
4 // Fraunhofer Institute for Open Communication Systems (FOKUS) 
5 // Competence Center NETwork research (NET), St. Augustin, GERMANY 
6 //     Stefan Bund <g0dil@berlios.de>
7 //
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.
12 //
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.
17 //
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.
22
23 /** \file
24     \brief PacketInterpreter non-inline template implementation  */
25
26 //#include "PacketInterpreter.ih"
27
28 // Custom includes
29 #include "Packet.hh"
30
31 #define prefix_
32 ///////////////////////////////ct.p////////////////////////////////////////
33
34 ///////////////////////////////////////////////////////////////////////////
35 // senf::PacketInterpreterBase
36
37 // Interpreter chain access
38
39 template <class Type>
40 prefix_ typename senf::PacketInterpreter<Type>::ptr
41 senf::PacketInterpreterBase::parseNextAs()
42 {
43     optional_range r (nextPacketRange());
44     if (!r)
45         throw InvalidPacketChainException();
46     
47     if (next())
48         impl().truncateInterpreters(next().get());
49
50     typename PacketInterpreter<Type>::ptr pi 
51         (PacketInterpreter<Type>::create(&impl(),r->begin(),r->end(),Append));
52     return pi;
53 }
54
55 ///////////////////////////////////////////////////////////////////////////
56 // senf::PacketInterpreter<PacketType>
57
58 // Create completely new packet
59
60 template <class PacketType>
61 prefix_ typename senf::PacketInterpreter<PacketType>::ptr
62 senf::PacketInterpreter<PacketType>::create(size_type size)
63 {
64     if (size < initSize())
65         throw TruncatedPacketException();
66     ptr pi (create(size,senf::noinit));
67     pi->init();
68     return pi;
69 }
70
71 template <class PacketType>
72 prefix_ typename senf::PacketInterpreter<PacketType>::ptr
73 senf::PacketInterpreter<PacketType>::create(size_type size, senf::NoInit_t)
74 {
75     detail::PacketImpl::Guard p (new detail::PacketImpl(size,0));
76     ptr pi (create(p.p,p.p->begin(),p.p->end(),Append));
77     return pi;
78 }
79
80 // Create packet as new packet after a given packet
81
82 template <class PacketType>
83 prefix_ typename senf::PacketInterpreter<PacketType>::ptr
84 senf::PacketInterpreter<PacketType>::createAfter(PacketInterpreterBase::ptr packet,
85                                                  size_type size)
86 {
87     if (size < initSize())
88         throw TruncatedPacketException();
89     ptr pi (createAfter(packet,size,senf::noinit));
90     std::fill(pi->data().begin(), pi->data().end(),0);
91     pi->init();
92     return pi;
93 }
94
95 template <class PacketType>
96 prefix_ typename senf::PacketInterpreter<PacketType>::ptr
97 senf::PacketInterpreter<PacketType>::createAfter(PacketInterpreterBase::ptr packet,
98                                                  size_type size, senf::NoInit_t)
99 {
100     optional_range r (packet->nextPacketRange());
101     if (!r)
102         throw InvalidPacketChainException();
103
104     if (packet->next())
105         packet->impl().truncateInterpreters(packet->next().get());
106
107     ptr pi (create(&packet->impl(),r->begin(),r->end(),Append));
108     pi->data().resize(size);
109     return pi;
110 }
111
112 template <class PacketType>
113 template <class ForwardReadableRange>
114 prefix_ typename senf::PacketInterpreter<PacketType>::ptr
115 senf::PacketInterpreter<PacketType>::createAfter(PacketInterpreterBase::ptr packet,
116                                                  ForwardReadableRange const & range)
117 {
118     optional_range r (packet->nextPacketRange());
119     if (!r)
120         throw InvalidPacketChainException();
121     
122     if (packet->next())
123         packet->impl().truncateInterpreters(packet->next().get());
124
125     ptr pi (create(&packet->impl(),r->begin(),r->end(),Append));
126     pi->data().resize(boost::size(range));
127     std::copy(boost::begin(range), boost::end(range), pi->data().begin());
128     return pi;
129 }
130
131 // Create packet as new packet (header) before a given packet
132
133 template <class PacketType>
134 prefix_ typename senf::PacketInterpreter<PacketType>::ptr
135 senf::PacketInterpreter<PacketType>::createBefore(PacketInterpreterBase::ptr packet)
136 {
137     ptr pi (createBefore(packet, senf::noinit));
138     pi->data().insert(pi->data().begin(),initHeadSize(),byte(0x00u));
139     pi->data().insert(pi->data().end(),initSize()-initHeadSize(),byte(0x00u));
140     pi->init();
141     return pi;
142 }
143
144 template <class PacketType>
145 prefix_ typename senf::PacketInterpreter<PacketType>::ptr
146 senf::PacketInterpreter<PacketType>::createBefore(PacketInterpreterBase::ptr packet, senf::NoInit_t)
147 {
148     if (packet->prev())
149         packet->impl().truncateInterpretersBackwards(packet->prev().get());
150     
151     return create(&packet->impl(),packet->data().begin(),packet->data().end(),Prepend);
152 }
153
154 ////////////////////////////////////////
155 // private members
156
157 // virtual interface
158
159 template <class PacketType>
160 prefix_ typename senf::PacketInterpreter<PacketType>::optional_range
161 senf::PacketInterpreter<PacketType>::v_nextPacketRange()
162 {
163     return type::nextPacketRange(ConcretePacket<PacketType>(ptr(this)));
164 }
165
166 template <class PacketType>
167 prefix_ senf::PacketInterpreterBase::ptr
168 senf::PacketInterpreter<PacketType>::v_appendClone(detail::PacketImpl * impl, iterator base,
169                                                    iterator new_base)
170 {
171     return create(impl,
172                   boost::next(new_base,std::distance(base,begin())),
173                   boost::next(new_base,std::distance(base,end())),
174                   Append);
175 }
176
177 template <class PacketType>
178 prefix_ senf::PacketInterpreterBase::ptr
179 senf::PacketInterpreter<PacketType>::v_appendClone(detail::PacketImpl * impl, range r)
180 {
181     return create(impl, r.begin(), r.end(), Append);
182 }
183
184 template <class PacketType>
185 prefix_ void senf::PacketInterpreter<PacketType>::v_finalize()
186 {
187     type::finalize(ConcretePacket<PacketType>(ptr(this)));
188 }
189
190 template <class PacketType>
191 prefix_ void senf::PacketInterpreter<PacketType>::v_dump(std::ostream & os)
192 {
193     type::dump(ConcretePacket<PacketType>(ptr(this)),os);
194 }
195
196 template <class PacketType>
197 prefix_ senf::TypeIdValue senf::PacketInterpreter<PacketType>::v_type()
198 {
199     return typeIdValue< ConcretePacket<PacketType> >();
200 }
201
202 template <class PacketType>
203 prefix_ typename senf::PacketInterpreter<PacketType>::factory_t
204 senf::PacketInterpreter<PacketType>::v_factory()
205 {
206     return factory();
207 }
208
209 template <class PacketType>
210 prefix_ typename senf::PacketInterpreter<PacketType>::factory_t
211 senf::PacketInterpreter<PacketType>::v_nextPacketType()
212 {
213     return type::nextPacketType(ConcretePacket<PacketType>(ptr(this)));
214 }
215
216
217 ///////////////////////////////////////////////////////////////////////////
218 // senf::PacketInterpreterBase::Factory
219
220 template <class ForwardReadableRange>
221 prefix_ senf::PacketInterpreterBase::ptr
222 senf::PacketInterpreterBase::Factory::create(ForwardReadableRange const & range)
223     const
224 {
225     ptr pi (create(boost::size(range),senf::noinit));
226     std::copy(boost::begin(range), boost::end(range), pi->data().begin());
227     return pi;
228 }
229
230 template <class ForwardReadableRange>
231 prefix_ senf::PacketInterpreterBase::ptr
232 senf::PacketInterpreterBase::Factory::createAfter(PacketInterpreterBase::ptr packet,
233                                                   ForwardReadableRange const & range)
234     const
235 {
236     ptr pi (createAfter(packet,boost::size(range),senf::noinit));
237     std::copy(boost::begin(range), boost::end(range), pi->data().begin());
238     return pi;
239 }
240
241 ///////////////////////////////////////////////////////////////////////////
242 // senf::PacketInterpreter<PacketType>::FactoryImpl
243
244 // Create completely new packet
245
246 template <class PacketType>
247 prefix_ typename senf::PacketInterpreterBase::ptr
248 senf::PacketInterpreter<PacketType>::FactoryImpl::create()
249     const
250 {
251     return senf::PacketInterpreter<PacketType>::create();
252 }
253
254 template <class PacketType>
255 prefix_ typename senf::PacketInterpreterBase::ptr
256 senf::PacketInterpreter<PacketType>::FactoryImpl::create(senf::NoInit_t)
257     const
258 {
259     return senf::PacketInterpreter<PacketType>::create(senf::noinit);
260 }
261
262 template <class PacketType>
263 prefix_ typename senf::PacketInterpreterBase::ptr
264 senf::PacketInterpreter<PacketType>::FactoryImpl::create(size_type size)
265     const
266 {
267     return senf::PacketInterpreter<PacketType>::create(size);
268 }
269
270 template <class PacketType>
271 prefix_ typename senf::PacketInterpreterBase::ptr
272 senf::PacketInterpreter<PacketType>::FactoryImpl::create(size_type size, senf::NoInit_t)
273     const
274 {
275     return senf::PacketInterpreter<PacketType>::create(size, senf::noinit);
276 }
277
278 // Create packet as new packet after a given packet
279
280 template <class PacketType>
281 prefix_ typename senf::PacketInterpreterBase::ptr
282 senf::PacketInterpreter<PacketType>::FactoryImpl::createAfter(PacketInterpreterBase::ptr packet)
283     const
284 {
285     return senf::PacketInterpreter<PacketType>::createAfter(packet);
286 }
287
288 template <class PacketType>
289 prefix_ typename senf::PacketInterpreterBase::ptr
290 senf::PacketInterpreter<PacketType>::FactoryImpl::createAfter(PacketInterpreterBase::ptr packet,
291                                                               senf::NoInit_t)
292     const
293 {
294     return senf::PacketInterpreter<PacketType>::createAfter(packet,senf::noinit);
295 }
296
297 template <class PacketType>
298 prefix_ typename senf::PacketInterpreterBase::ptr
299 senf::PacketInterpreter<PacketType>::FactoryImpl::createAfter(PacketInterpreterBase::ptr packet,
300                                                               size_type size)
301     const
302 {
303     return senf::PacketInterpreter<PacketType>::createAfter(packet,size);
304 }
305
306 template <class PacketType>
307 prefix_ typename senf::PacketInterpreterBase::ptr
308 senf::PacketInterpreter<PacketType>::FactoryImpl::createAfter(PacketInterpreterBase::ptr packet,
309                                                               size_type size, senf::NoInit_t)
310     const
311 {
312     return senf::PacketInterpreter<PacketType>::createAfter(packet,size,senf::noinit);
313 }
314
315 // Create packet as new packet (header) before a given packet
316
317 template <class PacketType>
318 prefix_ typename senf::PacketInterpreterBase::ptr
319 senf::PacketInterpreter<PacketType>::FactoryImpl::
320 createBefore(PacketInterpreterBase::ptr packet)
321     const
322 {
323     return senf::PacketInterpreter<PacketType>::createBefore(packet);
324 }
325
326 template <class PacketType>
327 prefix_ senf::PacketInterpreterBase::ptr
328 senf::PacketInterpreter<PacketType>::FactoryImpl::
329 createBefore(PacketInterpreterBase::ptr packet, senf::NoInit_t)
330     const
331 {
332     return senf::PacketInterpreter<PacketType>::createBefore(packet,senf::noinit);
333 }
334
335 // Parse next packet in chain
336
337 template <class PacketType>
338 prefix_ typename senf::PacketInterpreterBase::ptr
339 senf::PacketInterpreter<PacketType>::FactoryImpl::parseNext(PacketInterpreterBase::ptr packet)
340     const
341 {
342     optional_range r (packet->nextPacketRange());
343     if (!r)
344         throw InvalidPacketChainException();
345     
346     if (packet->next())
347         packet->impl().truncateInterpreters(packet->next().get());
348
349     return senf::PacketInterpreter<PacketType>::create(&packet->impl(),r->begin(),r->end(),Append);
350 }
351
352 template <class PacketType>
353 const typename senf::PacketInterpreter<PacketType>::FactoryImpl 
354     senf::PacketInterpreter<PacketType>::factory_;
355
356 ///////////////////////////////ct.e////////////////////////////////////////
357 #undef prefix_
358
359 \f
360 // Local Variables:
361 // mode: c++
362 // fill-column: 100
363 // c-file-style: "senf"
364 // indent-tabs-mode: nil
365 // ispell-local-dictionary: "american"
366 // compile-command: "scons -u test"
367 // comment-column: 40
368 // End: