Orocos Real-Time Toolkit  2.9.0
type_discovery.hpp
Go to the documentation of this file.
1 /***************************************************************************
2  tag: The SourceWorks Tue Sep 7 00:55:18 CEST 2010 type_discovery.hpp
3 
4  type_discovery.hpp - description
5  -------------------
6  begin : Tue September 07 2010
7  copyright : (C) 2010 The SourceWorks
8  email : peter@thesourceworks.com
9 
10  ***************************************************************************
11  * This library is free software; you can redistribute it and/or *
12  * modify it under the terms of the GNU General Public *
13  * License as published by the Free Software Foundation; *
14  * version 2 of the License. *
15  * *
16  * As a special exception, you may use this file as part of a free *
17  * software library without restriction. Specifically, if other files *
18  * instantiate templates or use macros or inline functions from this *
19  * file, or you compile this file and link it with other files to *
20  * produce an executable, this file does not by itself cause the *
21  * resulting executable to be covered by the GNU General Public *
22  * License. This exception does not however invalidate any other *
23  * reasons why the executable file might be covered by the GNU General *
24  * Public License. *
25  * *
26  * This library is distributed in the hope that it will be useful, *
27  * but WITHOUT ANY WARRANTY; without even the implied warranty of *
28  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
29  * Lesser General Public License for more details. *
30  * *
31  * You should have received a copy of the GNU General Public *
32  * License along with this library; if not, write to the Free Software *
33  * Foundation, Inc., 59 Temple Place, *
34  * Suite 330, Boston, MA 02111-1307 USA *
35  * *
36  ***************************************************************************/
37 
38 
39 #ifndef TYPE_DISCOVERY_HPP_
40 #define TYPE_DISCOVERY_HPP_
41 
42 // (C) Copyright 2002 Robert Ramey - http://www.rrsd.com .
43 // (C) Copyright 2009 Peter Soetens - http://www.thesourceworks.com .
44 // Use, modification and distribution is subject to the Boost Software
45 // License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
46 // http://www.boost.org/LICENSE_1_0.txt)
47 
48 // See http://www.boost.org for updates, documentation, and revision history.
49 
50 
64 #include <cassert>
65 #include <boost/version.hpp>
66 #include <boost/serialization/serialization.hpp>
67 #include <boost/serialization/is_bitwise_serializable.hpp>
68 #include <boost/serialization/vector.hpp>
69 #include <boost/serialization/string.hpp>
70 #include <boost/serialization/array.hpp>
71 #include <boost/archive/detail/iserializer.hpp>
72 #include <boost/archive/detail/oserializer.hpp>
73 #include <boost/archive/archive_exception.hpp>
74 #include <boost/config.hpp>
75 #include <boost/mpl/bool.hpp>
76 #include <boost/array.hpp>
77 
78 #include <vector>
79 #include <string>
80 #include "../base/DataSourceBase.hpp"
81 #include "../internal/PartDataSource.hpp"
82 #include "../internal/DataSources.hpp"
83 #include "../internal/Reference.hpp"
84 #include "carray.hpp"
85 
86 namespace RTT
87 {
88  namespace types
89  {
95  {
96  public:
101 
102  typedef std::vector<base::DataSourceBase::shared_ptr> Parts;
103  typedef std::vector<std::string> PartNames;
107  Parts mparts;
108 
112  PartNames mnames;
113 
117  std::string membername;
118 
124 
125  typedef char Elem;
129  typedef boost::mpl::bool_<true> is_loading;
133  typedef boost::mpl::bool_<false> is_saving;
134 
140  mparent(parent), mref(0)
141  {
142  }
143 
149  mparent(), mref(0)
150  {
151  }
152 
153  base::DataSourceBase::shared_ptr getMember(const std::string name) {
154  PartNames::iterator it = find( mnames.begin(), mnames.end(), name);
155  if ( it != mnames.end() && mparts.size() == mnames.size() )
156  return mparts.at( it - mnames.begin() );
158  }
159 
166  template<class T>
167  void discover( T& t) {
168 #if BOOST_VERSION >= 104100
169  boost::archive::detail::load_non_pointer_type<type_discovery>::load_only::invoke(*this,t);
170 #else
171  boost::archive::detail::load_non_pointer_type<type_discovery,T>::load_only::invoke(*this,t);
172 #endif
173  }
174 
180  template<class T>
181  base::DataSourceBase::shared_ptr discoverMember( T& t, const std::string name) {
182  membername = name;
183  discover( t );
184  if ( ! mparts.empty() )
185  return mparts[0];
187  }
188 
193  template<class T>
194  bool referenceMember(internal::Reference* ref, T& t, const std::string name) {
195  assert(ref);
196  membername = name;
197  mref = ref;
198  discover( t );
199  if (mref == 0) // we found it
200  return true;
201  return false;
202  }
203 
208  unsigned int get_library_version() { return 0; }
209 
215  void reset_object_address(const void * new_address, const void * old_address) {}
216 
221 
227  template<class T>
228  const boost::archive::detail::basic_pointer_iserializer *
229  register_type(T * = NULL) {return 0;}
230 
236  void load_object(void *x, const boost::archive::detail::basic_oserializer & bos)
237  {
238  assert(false);
239  }
240 
246  template<class T>
248  {
249  return load_a_type(t, boost::mpl::bool_<boost::serialization::implementation_level<T>::value == boost::serialization::primitive_type>());
250  }
251 
257  template<class T>
259  {
260  return this->operator>>(t);
261  }
262 
268  template<class T>
269  type_discovery &load_a_type(T &t, boost::mpl::true_)
270  {
271  // stores the part
272  if (mparent) {
273  mparts.push_back(new internal::PartDataSource<T> (t, mparent));
274  }
275  return *this;
276  }
277 
283  template<class T>
284  type_discovery &load_a_type(T &t, boost::mpl::false_)
285  {
286  mparts.push_back(new internal::PartDataSource<T> (t, mparent));
287  return *this;
288  }
289 
295  template<class T>
296 #if BOOST_VERSION >= 106100
297  type_discovery &load_a_type(const boost::serialization::array_wrapper<T> &t, boost::mpl::false_)
298 #else
299  type_discovery &load_a_type(const boost::serialization::array<T> &t, boost::mpl::false_)
300 #endif
301  {
302  mparts.push_back(new internal::PartDataSource< carray<T> > ( carray<T>(t), mparent) );
303  return *this;
304  }
305 
311  template<class T, std::size_t N>
312  type_discovery &load_a_type(boost::array<T,N> &t, boost::mpl::false_)
313  {
314  mparts.push_back(new internal::PartDataSource< carray<T> > ( carray<T>(t), mparent) );
315  return *this;
316  }
317 
324  template<class T>
325  type_discovery &load_a_type(const T* &, boost::mpl::false_)
326  {
327  //pointers can not be serialized.
328  //BOOST_STATIC_ASSERT( boost::mpl::false_ );
329  return *this;
330  }
331 
334  template<class T>
335  type_discovery &load_a_type(const boost::serialization::nvp<T> & t, boost::mpl::false_)
336  {
337  // check for single-member extraction first:
338  if ( !membername.empty() ) {
339  // Only serialize if the name matches:
340  if ( t.name() == membername ) {
341  if ( !mref ) {
342  *this & t.value();
343  } else {
344  mref->setReference( (void*) & t.value() );
345  mref = 0; // signals' we're done.
346  }
347  }
348  } else {
349  // Full extraction of all parts:
350  // store name of member
351  mnames.push_back( t.name() );
352 
353  // serialize the data as usual
354  if (mparent)
355  *this & t.value();
356  }
357 
358  return *this;
359  }
360  };
361  }
362 }
363 
364 #endif /* TYPE_DISCOVERY_HPP_ */
A DataSource which is used to manipulate a reference to a part of a data source.
type_discovery & load_a_type(const T *&, boost::mpl::false_)
We do not support pointer types.
void load_object(void *x, const boost::archive::detail::basic_oserializer &bos)
Note: not in LoadArchive concept but required when we use archive::load !
internal::Reference * mref
If non-empty, use this reference to the member with name membername.
boost::mpl::bool_< true > is_loading
Saving Archive Concept::is_loading.
virtual void setReference(void *ref)=0
Sets the reference to a given pointer.
type_discovery()
Constructor which only introspects the part names.
Wraps a C array such that we can return a C array from a DataSource.
Definition: carray.hpp:70
base::DataSourceBase::shared_ptr getMember(const std::string name)
type_discovery & load_a_type(boost::array< T, N > &t, boost::mpl::false_)
Specialisation that converts a boost::array into a RTT types carray.
type_discovery & operator>>(T &t)
Saving Archive Concept::operator<<.
base::DataSourceBase::shared_ptr discoverMember(T &t, const std::string name)
This function discovers a single part of a serializable struct and returns an assignable datasource t...
PartNames mnames
The names of the parts of the parent struct.
type_discovery & operator&(T &t)
Saving Archive Concept::operator&.
type_discovery & load_a_type(const boost::serialization::array< T > &t, boost::mpl::false_)
Specialisation that converts a boost serialization array into a RTT types carray. ...
void delete_created_pointers()
Loading Archive Concept::delete_created_pointers()
void reset_object_address(const void *new_address, const void *old_address)
Loading Archive Concept::reset_object_address(v,u)
base::DataSourceBase::shared_ptr mparent
The parent struct we&#39;re deserializing.
std::vector< std::string > PartNames
std::vector< base::DataSourceBase::shared_ptr > Parts
const boost::archive::detail::basic_pointer_iserializer * register_type(T *=NULL)
Loading Archive Concept::register_type<T>() and ::register_type(u)
Parts mparts
The parts of the parent struct.
type_discovery & load_a_type(T &t, boost::mpl::false_)
Specialisation for writing out composite types (objects).
unsigned int get_library_version()
Loading Archive Concept::get_library_version()
type_discovery & load_a_type(T &t, boost::mpl::true_)
Specialisation for writing out primitive types.
This archive is capable of decomposing objects of serialization level 1 and 2 into part data sources...
Object that may receive a reference to some data by means of a pointer or data source.
Definition: Reference.hpp:15
boost::intrusive_ptr< DataSourceBase > shared_ptr
Use this type to store a pointer to a DataSourceBase.
Contains TaskContext, Activity, OperationCaller, Operation, Property, InputPort, OutputPort, Attribute.
Definition: Activity.cpp:52
type_discovery(base::DataSourceBase::shared_ptr parent)
Constructor which inspects part names and creates part data sources.
std::string membername
If non-empty, only discover the member with this name.
bool referenceMember(internal::Reference *ref, T &t, const std::string name)
This function discovers a single part of a serializable struct and sets a reference to that member of...
boost::mpl::bool_< false > is_saving
Saving Archive Concept::is_saving.
type_discovery & load_a_type(const boost::serialization::nvp< T > &t, boost::mpl::false_)
special treatment for name-value pairs.
void discover(T &t)
This function discovers all parts of a serializable struct and creates a DataSource object for each m...