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