Go to the documentation of this file.00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
00025 
00026 
00027 
00028 
00029 
00030 
00031 
00032 
00033 
00034 
00035 
00036 
00037 
00038 
00039 #ifndef ORO_PARTDATASOURCE_HPP_
00040 #define ORO_PARTDATASOURCE_HPP_
00041 
00042 #include "DataSource.hpp"
00043 #include "../types/carray.hpp"
00044 
00045 namespace RTT
00046 {
00047     namespace internal
00048     {
00057         template<typename T>
00058         class PartDataSource
00059         : public AssignableDataSource<T>
00060         {
00061             
00062             typename AssignableDataSource<T>::reference_t mref;
00063             
00064             base::DataSourceBase::shared_ptr mparent;
00065         public:
00066             ~PartDataSource() {}
00067 
00068             typedef boost::intrusive_ptr<PartDataSource<T> > shared_ptr;
00069 
00076             PartDataSource( typename AssignableDataSource<T>::reference_t ref,
00077                             base::DataSourceBase::shared_ptr parent )
00078                 : mref(ref), mparent(parent)
00079             {
00080             }
00081 
00082             typename DataSource<T>::result_t get() const
00083             {
00084                 return mref;
00085             }
00086 
00087             typename DataSource<T>::result_t value() const
00088             {
00089                 return mref;
00090             }
00091 
00092             void set( typename AssignableDataSource<T>::param_t t )
00093             {
00094                 mref = t;
00095                 updated();
00096             }
00097 
00098             typename AssignableDataSource<T>::reference_t set()
00099             {
00100                 return mref;
00101             }
00102 
00103             typename AssignableDataSource<T>::const_reference_t rvalue() const
00104             {
00105                 return mref;
00106             }
00107 
00108             void updated() {
00109                 mparent->updated();
00110             }
00111 
00112             virtual PartDataSource<T>* clone() const {
00113                 return new PartDataSource<T>(mref, mparent);
00114             }
00115 
00116             virtual PartDataSource<T>* copy( std::map<const base::DataSourceBase*, base::DataSourceBase*>& replace ) const {
00117                 
00118                 if ( replace[this] != 0 ) {
00119                     assert ( dynamic_cast<PartDataSource<T>*>( replace[this] ) == static_cast<PartDataSource<T>*>( replace[this] ) );
00120                     return static_cast<PartDataSource<T>*>( replace[this] );
00121                 }
00122                 
00123                 assert( mparent->getRawPointer() != 0 && "Can't copy part of rvalue datasource.");
00124                 if ( mparent->getRawPointer() == 0 )
00125                     throw std::runtime_error("PartDataSource.hpp: Can't copy part of rvalue datasource.");
00126                 base::DataSourceBase::shared_ptr mparent_copy =  mparent->copy(replace);
00127                 
00128                 int offset = reinterpret_cast<unsigned char*>( &mref ) - reinterpret_cast<unsigned char*>(mparent->getRawPointer());
00129                 
00130                 typename AssignableDataSource<T>::value_t* mref_copy = reinterpret_cast<typename AssignableDataSource<T>::value_t*>( reinterpret_cast<unsigned char*>(mparent_copy->getRawPointer()) + offset );
00131                 replace[this] = new PartDataSource<T>( *mref_copy, mparent_copy );
00132                 
00133                 return static_cast<PartDataSource<T>*>(replace[this]);
00134 
00135             }
00136         };
00137 
00141         template<typename T>
00142         class PartDataSource< types::carray<T> >
00143         : public AssignableDataSource< types::carray<T> >
00144         {
00145             
00146             types::carray<T> mref;
00147             
00148             base::DataSourceBase::shared_ptr mparent;
00149         public:
00150             ~PartDataSource() {}
00151 
00152             typedef boost::intrusive_ptr<PartDataSource<T> > shared_ptr;
00153 
00160             PartDataSource( types::carray<T> ref,
00161                             base::DataSourceBase::shared_ptr parent )
00162                 : mref(ref), mparent(parent)
00163             {
00164             }
00165 
00166             types::carray<T> get() const
00167             {
00168                 return mref;
00169             }
00170 
00171             types::carray<T> value() const
00172             {
00173                 return mref;
00174             }
00175 
00176             void set( typename AssignableDataSource< types::carray<T> >::param_t t )
00177             {
00178                 mref = t;
00179                 updated();
00180             }
00181 
00182             types::carray<T>& set()
00183             {
00184                 return mref;
00185             }
00186 
00187             types::carray<T> const& rvalue() const
00188             {
00189                 return mref;
00190             }
00191 
00192             void updated() {
00193                 mparent->updated();
00194             }
00195 
00196             virtual PartDataSource* clone() const {
00197                 return new PartDataSource(mref, mparent);
00198             }
00199 
00200             virtual PartDataSource* copy( std::map<const base::DataSourceBase*, base::DataSourceBase*>& replace ) const {
00201                 
00202                 if ( replace[this] != 0 ) {
00203                     assert ( dynamic_cast<PartDataSource*>( replace[this] ) == static_cast<PartDataSource*>( replace[this] ) );
00204                     return static_cast<PartDataSource*>( replace[this] );
00205                 }
00206                 
00207                 assert( mparent->getRawPointer() != 0 && "Can't copy part of rvalue datasource.");
00208                 if ( mparent->getRawPointer() == 0 )
00209                     throw std::runtime_error("PartDataSource.hpp: Can't copy part of rvalue datasource.");
00210                 base::DataSourceBase::shared_ptr mparent_copy =  mparent->copy(replace);
00211                 
00212                 int offset = reinterpret_cast<unsigned char*>( mref.address() ) - reinterpret_cast<unsigned char*>(mparent->getRawPointer());
00213                 
00214                 types::carray<T> mref_copy;
00215                 mref_copy.init(reinterpret_cast<T*>( reinterpret_cast<unsigned char*>(mparent_copy->getRawPointer()) + offset ), mref.count() );
00216                 replace[this] = new PartDataSource(mref_copy, mparent_copy);
00217                 
00218                 return static_cast<PartDataSource*>(replace[this]);
00219 
00220             }
00221         };
00222     }
00223 }
00224 
00225 
00226 #endif