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_LOCAL_METHOD_HPP
00040 #define ORO_LOCAL_METHOD_HPP
00041 
00042 #include <boost/function.hpp>
00043 #include <boost/shared_ptr.hpp>
00044 #include <boost/make_shared.hpp>
00045 #include <string>
00046 #include "Invoker.hpp"
00047 #include "../base/OperationCallerBase.hpp"
00048 #include "../base/OperationBase.hpp"
00049 #include "BindStorage.hpp"
00050 #include "../SendStatus.hpp"
00051 #include "../SendHandle.hpp"
00052 #include "../ExecutionEngine.hpp"
00053 #include "OperationCallerBinder.hpp"
00054 #include <boost/fusion/include/vector_tie.hpp>
00055 #include "../os/oro_allocator.hpp"
00056 
00057 #include <iostream>
00058 
00059 #include <boost/fusion/sequence/io.hpp>
00060 
00061 namespace RTT
00062 {
00063     namespace internal
00064     {
00076         template<class FunctionT>
00077         class LocalOperationCallerImpl
00078             : public base::OperationCallerBase<FunctionT>,
00079               public internal::CollectBase<FunctionT>,
00080               protected BindStorage<FunctionT>
00081         {
00082         public:
00083             LocalOperationCallerImpl() {}
00084             typedef FunctionT Signature;
00085             typedef typename boost::function_traits<Signature>::result_type result_type;
00086             typedef typename boost::function_traits<Signature>::result_type result_reference;
00087             typedef boost::function_traits<Signature> traits;
00088 
00089             typedef boost::shared_ptr<LocalOperationCallerImpl> shared_ptr;
00090 
00091             virtual bool ready() const {
00092                 return true;
00093             }
00094 
00095             virtual bool isError() const {
00096               return this->retv.isError();
00097             }
00098 
00099             void executeAndDispose() {
00100                 if (!this->retv.isExecuted()) {
00101                     this->exec(); 
00102                     
00103                     if(this->retv.isError())
00104                         this->reportError();
00105                     bool result = false;
00106                     if ( this->caller){
00107                         result = this->caller->process(this);
00108                     }
00109                     if (!result)
00110                         dispose();
00111                 } else {
00112                     
00113                     
00114                     
00115                     
00116                     
00117                     dispose();
00118                 }
00119                 return;
00120             }
00121 
00126             void dispose() {
00127                 
00128                 
00129                 self.reset();
00130             }
00131 
00132             
00133             ExecutionEngine* getMessageProcessor() const { return this->myengine; }
00134 
00135             SendHandle<Signature> do_send(shared_ptr cl) {
00136                 assert(this->myengine); 
00137                 
00138                 if ( this->myengine->process( cl.get() ) ) {
00139                     cl->self = cl;
00140                     return SendHandle<Signature>( cl );
00141                 } else {
00142                     
00143                     
00144                     
00145                     return SendHandle<Signature>();
00146                 }
00147             }
00148             
00149             SendHandle<Signature> send_impl() {
00150                 return do_send( this->cloneRT() );
00151             }
00152 
00153             template<class T1>
00154             SendHandle<Signature> send_impl( T1 a1 ) {
00155                 
00156                 shared_ptr cl = this->cloneRT();
00157                 cl->store( a1 );
00158                 return do_send(cl);
00159             }
00160 
00161             template<class T1, class T2>
00162             SendHandle<Signature> send_impl( T1 a1, T2 a2 ) {
00163                 
00164                 shared_ptr cl = this->cloneRT();
00165                 cl->store( a1,a2 );
00166                 return do_send(cl);
00167             }
00168 
00169             template<class T1, class T2, class T3>
00170             SendHandle<Signature> send_impl( T1 a1, T2 a2, T3 a3 ) {
00171                 
00172                 shared_ptr cl = this->cloneRT();
00173                 cl->store( a1,a2,a3 );
00174                 return do_send(cl);
00175             }
00176 
00177             template<class T1, class T2, class T3, class T4>
00178             SendHandle<Signature> send_impl( T1 a1, T2 a2, T3 a3, T4 a4 ) {
00179                 
00180                 shared_ptr cl = this->cloneRT();
00181                 cl->store( a1,a2,a3,a4 );
00182                 return do_send(cl);
00183             }
00184 
00185             template<class T1, class T2, class T3, class T4, class T5>
00186             SendHandle<Signature> send_impl( T1 a1, T2 a2, T3 a3, T4 a4, T5 a5 ) {
00187                 
00188                 shared_ptr cl = this->cloneRT();
00189                 cl->store( a1,a2,a3,a4,a5 );
00190                 return do_send(cl);
00191             }
00192 
00193             template<class T1, class T2, class T3, class T4, class T5, class T6>
00194             SendHandle<Signature> send_impl( T1 a1, T2 a2, T3 a3, T4 a4, T5 a5, T6 a6 ) {
00195                 
00196                 shared_ptr cl = this->cloneRT();
00197                 cl->store( a1,a2,a3,a4,a5,a6 );
00198                 return do_send(cl);
00199             }
00200 
00201             template<class T1, class T2, class T3, class T4, class T5, class T6, class T7>
00202             SendHandle<Signature> send_impl( T1 a1, T2 a2, T3 a3, T4 a4, T5 a5, T6 a6, T7 a7 ) {
00203                 
00204                 shared_ptr cl = this->cloneRT();
00205                 cl->store( a1,a2,a3,a4,a5,a6,a7 );
00206                 return do_send(cl);
00207             }
00208 
00209 
00210             SendStatus collectIfDone_impl() {
00211                 if ( this->retv.isExecuted()) {
00212                     this->retv.checkError();
00213                     return SendSuccess;
00214                 } else
00215                     return SendNotReady;
00216             }
00217 
00218             
00219             
00220             template<class T1>
00221             SendStatus collectIfDone_impl( T1& a1 ) {
00222                 if ( this->retv.isExecuted()) {
00223                     this->retv.checkError();
00224                     bf::vector_tie(a1) = bf::filter_if< is_arg_return<boost::remove_reference<mpl::_> > >(this->vStore);
00225                     return SendSuccess;
00226                 } else
00227                     return SendNotReady;
00228             }
00229 
00230             template<class T1, class T2>
00231             SendStatus collectIfDone_impl( T1& a1, T2& a2 ) {
00232                 if ( this->retv.isExecuted()) {
00233                     this->retv.checkError();
00234                     bf::vector_tie(a1,a2) = bf::filter_if< is_arg_return<boost::remove_reference<mpl::_> > >(this->vStore);
00235                     return SendSuccess;
00236                 }
00237                 return SendNotReady;
00238             }
00239 
00240             template<class T1, class T2, class T3>
00241             SendStatus collectIfDone_impl( T1& a1, T2& a2, T3& a3 ) {
00242                 if ( this->retv.isExecuted()) {
00243                     this->retv.checkError();
00244                     bf::vector_tie(a1,a2,a3) = bf::filter_if< is_arg_return<boost::remove_reference<mpl::_> > >(this->vStore);
00245                     return SendSuccess;
00246                 } else
00247                     return SendNotReady;
00248             }
00249 
00250             template<class T1, class T2, class T3, class T4>
00251             SendStatus collectIfDone_impl( T1& a1, T2& a2, T3& a3, T4& a4 ) {
00252                 if ( this->retv.isExecuted()) {
00253                     this->retv.checkError();
00254                     bf::vector_tie(a1,a2,a3,a4) = bf::filter_if< is_arg_return<boost::remove_reference<mpl::_> > >(this->vStore);
00255                     return SendSuccess;
00256                 } else
00257                     return SendNotReady;
00258             }
00259 
00260             template<class T1, class T2, class T3, class T4, class T5>
00261             SendStatus collectIfDone_impl( T1& a1, T2& a2, T3& a3, T4& a4, T5& a5 ) {
00262                 if ( this->retv.isExecuted()) {
00263                     this->retv.checkError();
00264                     bf::vector_tie(a1,a2,a3,a4,a5) = bf::filter_if< is_arg_return<boost::remove_reference<mpl::_> > >(this->vStore);
00265                     return SendSuccess;
00266                 } else
00267                     return SendNotReady;
00268             }
00269 
00270             template<class T1, class T2, class T3, class T4, class T5, class T6>
00271             SendStatus collectIfDone_impl( T1& a1, T2& a2, T3& a3, T4& a4, T5& a5, T6& a6 ) {
00272                 if ( this->retv.isExecuted()) {
00273                     this->retv.checkError();
00274                     bf::vector_tie(a1,a2,a3,a4,a5,a6) = bf::filter_if< is_arg_return<boost::remove_reference<mpl::_> > >(this->vStore);
00275                     return SendSuccess;
00276                 } else
00277                     return SendNotReady;
00278             }
00279 
00280             template<class T1, class T2, class T3, class T4, class T5, class T6, class T7>
00281             SendStatus collectIfDone_impl( T1& a1, T2& a2, T3& a3, T4& a4, T5& a5, T6& a6, T7& a7 ) {
00282                 if ( this->retv.isExecuted()) {
00283                     this->retv.checkError();
00284                     bf::vector_tie(a1,a2,a3,a4,a5,a6,a7) = bf::filter_if< is_arg_return<boost::remove_reference<mpl::_> > >(this->vStore);
00285                     return SendSuccess;
00286                 } else
00287                     return SendNotReady;
00288             }
00289 
00290             SendStatus collect_impl() {
00291                 this->caller->waitForMessages( boost::bind(&Store::RStoreType::isExecuted,boost::ref(this->retv)) );
00292                 return this->collectIfDone_impl();
00293             }
00294             template<class T1>
00295             SendStatus collect_impl( T1& a1 ) {
00296                 this->caller->waitForMessages( boost::bind(&Store::RStoreType::isExecuted,boost::ref(this->retv)) );
00297                 return this->collectIfDone_impl(a1);
00298             }
00299 
00300             template<class T1, class T2>
00301             SendStatus collect_impl( T1& a1, T2& a2 ) {
00302                 this->caller->waitForMessages( boost::bind(&Store::RStoreType::isExecuted,boost::ref(this->retv)) );
00303                 return this->collectIfDone_impl(a1,a2);
00304             }
00305 
00306             template<class T1, class T2, class T3>
00307             SendStatus collect_impl( T1& a1, T2& a2, T3& a3 ) {
00308                 this->caller->waitForMessages( boost::bind(&Store::RStoreType::isExecuted,boost::ref(this->retv)) );
00309                 return this->collectIfDone_impl(a1,a2,a3);
00310             }
00311 
00312             template<class T1, class T2, class T3, class T4>
00313             SendStatus collect_impl( T1& a1, T2& a2, T3& a3, T4& a4) {
00314                 this->caller->waitForMessages( boost::bind(&Store::RStoreType::isExecuted,boost::ref(this->retv)) );
00315                 return this->collectIfDone_impl(a1,a2,a3,a4);
00316             }
00317 
00318             template<class T1, class T2, class T3, class T4, class T5>
00319             SendStatus collect_impl( T1& a1, T2& a2, T3& a3, T4& a4, T5& a5) {
00320                 this->caller->waitForMessages( boost::bind(&Store::RStoreType::isExecuted,boost::ref(this->retv)) );
00321                 return this->collectIfDone_impl(a1,a2,a3,a4, a5);
00322             }
00323 
00324             template<class T1, class T2, class T3, class T4, class T5, class T6>
00325             SendStatus collect_impl( T1& a1, T2& a2, T3& a3, T4& a4, T5& a5, T6& a6) {
00326                 this->caller->waitForMessages( boost::bind(&Store::RStoreType::isExecuted,boost::ref(this->retv)) );
00327                 return this->collectIfDone_impl(a1,a2,a3,a4,a5,a6);
00328             }
00329 
00330             template<class T1, class T2, class T3, class T4, class T5, class T6, class T7>
00331             SendStatus collect_impl( T1& a1, T2& a2, T3& a3, T4& a4, T5& a5, T6& a6, T7& a7) {
00332                 this->caller->waitForMessages( boost::bind(&Store::RStoreType::isExecuted,boost::ref(this->retv)) );
00333                 return this->collectIfDone_impl(a1,a2,a3,a4,a5,a6,a7);
00334             }
00335 
00339             result_type call_impl()
00340             {
00341 
00342                 if ( this->isSend() ) {
00343                     SendHandle<Signature> h = send_impl();
00344                     if ( h.collect() == SendSuccess )
00345                         return h.ret();
00346                     else
00347                         throw SendFailure;
00348                 } else {
00349 #ifdef ORO_SIGNALLING_OPERATIONS
00350                     if (this->msig) this->msig->emit();
00351 #endif
00352                     if ( this->mmeth )
00353                         return this->mmeth(); 
00354                     else
00355                         return NA<result_type>::na();
00356                 }
00357             }
00358 
00359 
00363             template<class T1>
00364             result_type call_impl(T1 a1)
00365             {
00366                 SendHandle<Signature> h;
00367                 if ( this->isSend() ) {
00368                     h = send_impl<T1>(a1);
00369                     
00370                     
00371                     if ( h.collect() == SendSuccess )
00372                         return h.ret(a1);
00373                     else
00374                         throw SendFailure;
00375                 } else{
00376 #ifdef ORO_SIGNALLING_OPERATIONS
00377                     if (this->msig) this->msig->emit(a1);
00378 #endif
00379                     if ( this->mmeth )
00380                         return this->mmeth(a1);
00381                     else
00382                         return NA<result_type>::na();
00383                 }
00384                 return NA<result_type>::na();
00385             }
00386 
00387             template<class T1, class T2>
00388             result_type call_impl(T1 a1, T2 a2)
00389             {
00390                 SendHandle<Signature> h;
00391                 if ( this->isSend() ) {
00392                     h = send_impl<T1,T2>(a1,a2);
00393                     if ( h.collect() == SendSuccess )
00394                         return h.ret(a1,a2);
00395                     else
00396                         throw SendFailure;
00397                 } else {
00398 #ifdef ORO_SIGNALLING_OPERATIONS
00399                     if (this->msig) this->msig->emit(a1,a2);
00400 #endif
00401                     if ( this->mmeth )
00402                         return this->mmeth(a1,a2);
00403                     else
00404                         return NA<result_type>::na();
00405                 }
00406                 return NA<result_type>::na();
00407             }
00408 
00409             template<class T1, class T2, class T3>
00410             result_type call_impl(T1 a1, T2 a2, T3 a3)
00411             {
00412                 SendHandle<Signature> h;
00413                 if ( this->isSend() ) {
00414                     h = send_impl<T1,T2,T3>(a1,a2,a3);
00415                     if ( h.collect() == SendSuccess )
00416                         return h.ret(a1,a2,a3);
00417                     else
00418                         throw SendFailure;
00419                 } else {
00420 #ifdef ORO_SIGNALLING_OPERATIONS
00421                     if (this->msig) this->msig->emit(a1,a2,a3);
00422 #endif
00423                     if ( this->mmeth )
00424                         return this->mmeth(a1,a2,a3);
00425                     else
00426                         return NA<result_type>::na();
00427                 }
00428                 return NA<result_type>::na();
00429             }
00430 
00431             template<class T1, class T2, class T3, class T4>
00432             result_type call_impl(T1 a1, T2 a2, T3 a3, T4 a4)
00433             {
00434                 SendHandle<Signature> h;
00435                 if ( this->isSend() ) {
00436                     h = send_impl<T1,T2,T3,T4>(a1,a2,a3,a4);
00437                     if ( h.collect() == SendSuccess )
00438                         return h.ret(a1,a2,a3,a4);
00439                     else
00440                         throw SendFailure;
00441                 } else {
00442 #ifdef ORO_SIGNALLING_OPERATIONS
00443                     if (this->msig) this->msig->emit(a1,a2,a3,a4);
00444 #endif
00445                     if ( this->mmeth )
00446                         return this->mmeth(a1,a2,a3,a4);
00447                     else
00448                         return NA<result_type>::na();
00449                 }
00450                 return NA<result_type>::na();
00451             }
00452 
00453             template<class T1, class T2, class T3, class T4, class T5>
00454             result_type call_impl(T1 a1, T2 a2, T3 a3, T4 a4, T5 a5)
00455             {
00456                 SendHandle<Signature> h;
00457                 if (this->isSend()) {
00458                     h = send_impl<T1,T2,T3,T4,T5>(a1,a2,a3,a4,a5);
00459                     if ( h.collect() == SendSuccess )
00460                         return h.ret(a1,a2,a3,a4,a5);
00461                     else
00462                         throw SendFailure;
00463                 } else {
00464 #ifdef ORO_SIGNALLING_OPERATIONS
00465                     if (this->msig) this->msig->emit(a1,a2,a3,a4,a5);
00466 #endif
00467                     if ( this->mmeth )
00468                         return this->mmeth(a1,a2,a3,a4,a5);
00469                     else
00470                         return NA<result_type>::na();
00471                 }
00472                 return NA<result_type>::na();
00473             }
00474 
00475             template<class T1, class T2, class T3, class T4, class T5, class T6>
00476             result_type call_impl(T1 a1, T2 a2, T3 a3, T4 a4, T5 a5, T6 a6)
00477             {
00478                 SendHandle<Signature> h;
00479                 if (this->isSend()) {
00480                     h = send_impl<T1,T2,T3,T4,T5,T6>(a1,a2,a3,a4,a5,a6);
00481                     if ( h.collect() == SendSuccess )
00482                         return h.ret(a1,a2,a3,a4,a5,a6);
00483                     else
00484                         throw SendFailure;
00485                 } else {
00486 #ifdef ORO_SIGNALLING_OPERATIONS
00487                     if (this->msig) this->msig->emit(a1,a2,a3,a4,a5,a6);
00488 #endif
00489                     if ( this->mmeth )
00490                         return this->mmeth(a1,a2,a3,a4,a5,a6);
00491                     else
00492                         return NA<result_type>::na();
00493                 }
00494                 return NA<result_type>::na();
00495             }
00496 
00497             template<class T1, class T2, class T3, class T4, class T5, class T6, class T7>
00498             result_type call_impl(T1 a1, T2 a2, T3 a3, T4 a4, T5 a5, T6 a6, T7 a7)
00499             {
00500                 SendHandle<Signature> h;
00501                 if (this->isSend()) {
00502                     h = send_impl<T1,T2,T3,T4,T5,T6,T7>(a1,a2,a3,a4,a5,a6,a7);
00503                     if ( h.collect() == SendSuccess )
00504                         return h.ret(a1,a2,a3,a4,a5,a6,a7);
00505                     else
00506                         throw SendFailure;
00507                 } else {
00508 #ifdef ORO_SIGNALLING_OPERATIONS
00509                     if (this->msig) this->msig->emit(a1,a2,a3,a4,a5,a6,a7);
00510 #endif
00511                     if ( this->mmeth )
00512                         return this->mmeth(a1,a2,a3,a4,a5,a6,a7);
00513                     else
00514                         return NA<result_type>::na();
00515                 }
00516                 return NA<result_type>::na();
00517             }
00518 
00519             result_type ret_impl()
00520             {
00521                 this->retv.checkError();
00522                 return this->retv.result(); 
00523             }
00524 
00530             template<class T1>
00531             result_type ret_impl(T1 a1)
00532             {
00533                 this->retv.checkError();
00534                 typedef mpl::and_<boost::is_reference<mpl::_>, mpl::not_<boost::is_const<boost::remove_reference<mpl::_> > > > pred;
00535                 bf::vector<T1> vArgs( boost::ref(a1) );
00536                 if ( this->retv.isExecuted())
00537                     as_vector(bf::filter_if< pred >(vArgs)) = bf::filter_if< is_out_arg<boost::remove_reference<mpl::_> > >(this->vStore);
00538                 return this->retv.result(); 
00539             }
00540 
00541             template<class T1,class T2>
00542             result_type ret_impl(T1 a1, T2 a2)
00543             {
00544                 this->retv.checkError();
00545                 typedef mpl::and_<boost::is_reference<mpl::_>, mpl::not_<boost::is_const<boost::remove_reference<mpl::_> > > > pred;
00546                 bf::vector<T1,T2> vArgs( boost::ref(a1), boost::ref(a2) );
00547                 if ( this->retv.isExecuted())
00548                     as_vector(bf::filter_if< pred >(vArgs)) = bf::filter_if< is_out_arg< boost::remove_reference<mpl::_> > >(this->vStore);
00549                 return this->retv.result(); 
00550             }
00551 
00552             template<class T1,class T2, class T3>
00553             result_type ret_impl(T1 a1, T2 a2, T3 a3)
00554             {
00555                 this->retv.checkError();
00556                 typedef mpl::and_<boost::is_reference<mpl::_>, mpl::not_<boost::is_const<boost::remove_reference<mpl::_> > > > pred;
00557                 bf::vector<T1,T2,T3> vArgs( boost::ref(a1), boost::ref(a2), boost::ref(a3) );
00558                 if ( this->retv.isExecuted())
00559                     as_vector(bf::filter_if< pred >(vArgs)) = bf::filter_if< is_out_arg<boost::remove_reference<mpl::_> > >(this->vStore);
00560                 return this->retv.result(); 
00561             }
00562 
00563             template<class T1,class T2, class T3, class T4>
00564             result_type ret_impl(T1 a1, T2 a2, T3 a3, T4 a4)
00565             {
00566                 this->retv.checkError();
00567                 typedef mpl::and_<boost::is_reference<mpl::_>, mpl::not_<boost::is_const<boost::remove_reference<mpl::_> > > > pred;
00568                 bf::vector<T1,T2,T3,T4> vArgs( boost::ref(a1), boost::ref(a2), boost::ref(a3), boost::ref(a4) );
00569                 if ( this->retv.isExecuted())
00570                     as_vector(bf::filter_if< pred >(vArgs)) = bf::filter_if< is_out_arg<boost::remove_reference<mpl::_> > >(this->vStore);
00571                 return this->retv.result(); 
00572             }
00573 
00574             template<class T1,class T2, class T3, class T4, class T5>
00575             result_type ret_impl(T1 a1, T2 a2, T3 a3, T4 a4, T5 a5)
00576             {
00577                 this->retv.checkError();
00578                 typedef mpl::and_<boost::is_reference<mpl::_>, mpl::not_<boost::is_const<boost::remove_reference<mpl::_> > > > pred;
00579                 bf::vector<T1,T2,T3,T4,T5> vArgs( boost::ref(a1), boost::ref(a2), boost::ref(a3), boost::ref(a4), boost::ref(a5) );
00580                 if ( this->retv.isExecuted())
00581                     as_vector(bf::filter_if< pred >(vArgs)) = bf::filter_if< is_out_arg<boost::remove_reference<mpl::_> > >(this->vStore);
00582                 return this->retv.result(); 
00583             }
00584 
00585             template<class T1,class T2, class T3, class T4, class T5, class T6>
00586             result_type ret_impl(T1 a1, T2 a2, T3 a3, T4 a4, T5 a5, T6 a6)
00587             {
00588                 this->retv.checkError();
00589                 typedef mpl::and_<boost::is_reference<mpl::_>, mpl::not_<boost::is_const<boost::remove_reference<mpl::_> > > > pred;
00590                 bf::vector<T1,T2,T3,T4,T5,T6> vArgs( boost::ref(a1), boost::ref(a2), boost::ref(a3), boost::ref(a4), boost::ref(a5), boost::ref(a6) );
00591                 if ( this->retv.isExecuted())
00592                     as_vector(bf::filter_if< pred >(vArgs)) = bf::filter_if< is_out_arg<boost::remove_reference<mpl::_> > >(this->vStore);
00593                 return this->retv.result(); 
00594             }
00595 
00596             template<class T1,class T2, class T3, class T4, class T5, class T6, class T7>
00597             result_type ret_impl(T1 a1, T2 a2, T3 a3, T4 a4, T5 a5, T6 a6, T7 a7)
00598             {
00599                 this->retv.checkError();
00600                 typedef mpl::and_<boost::is_reference<mpl::_>, mpl::not_<boost::is_const<boost::remove_reference<mpl::_> > > > pred;
00601                 bf::vector<T1,T2,T3,T4,T5,T6,T7> vArgs( boost::ref(a1), boost::ref(a2), boost::ref(a3), boost::ref(a4), boost::ref(a5), boost::ref(a6), boost::ref(a7) );
00602                 if ( this->retv.isExecuted())
00603                     as_vector(bf::filter_if< pred >(vArgs)) = bf::filter_if< is_out_arg<boost::remove_reference<mpl::_> > >(this->vStore);
00604                 return this->retv.result(); 
00605             }
00606 
00607             virtual shared_ptr cloneRT() const = 0;
00608         protected:
00609             typedef BindStorage<FunctionT> Store;
00615             typename base::OperationCallerBase<FunctionT>::shared_ptr self;
00616         };
00617 
00627         template<class FunctionT>
00628         struct LocalOperationCaller
00629             : public Invoker<FunctionT,LocalOperationCallerImpl<FunctionT> >
00630         {
00631             typedef FunctionT Signature;
00632             typedef typename boost::function_traits<Signature>::result_type result_type;
00633             typedef boost::function_traits<Signature> traits;
00634 
00635             typedef boost::shared_ptr<LocalOperationCaller> shared_ptr;
00636 
00642             LocalOperationCaller()
00643             {}
00644 
00655             template<class M, class ObjectType>
00656             LocalOperationCaller(M meth, ObjectType object, ExecutionEngine* ee, ExecutionEngine* caller, ExecutionThread et = ClientThread, ExecutionEngine* oe = NULL )
00657             {
00658                 this->setExecutor( ee );
00659                 this->setCaller( caller );
00660                 this->setOwner(oe);
00661                 this->setThread( et, ee );
00662                 this->mmeth = OperationCallerBinder<Signature>()(meth, object);
00663             }
00664 
00670             template<class M>
00671             LocalOperationCaller(M meth, ExecutionEngine* ee, ExecutionEngine* caller, ExecutionThread et = ClientThread, ExecutionEngine* oe = NULL )
00672             {
00673                 this->setExecutor( ee );
00674                 this->setCaller( caller );
00675                 this->setOwner(oe);
00676                 this->setThread( et, ee );
00677                 this->mmeth = meth;
00678             }
00679 
00680             boost::function<Signature> getOperationCallerFunction() const
00681             {
00682                 return this->mmeth;
00683             }
00684 
00685 #ifdef ORO_SIGNALLING_OPERATIONS
00686             void setSignal(typename Signal<Signature>::shared_ptr sig) {
00687                 this->msig = sig;
00688             }
00689 #endif
00690             base::OperationCallerBase<Signature>* cloneI(ExecutionEngine* caller) const
00691             {
00692                 LocalOperationCaller<Signature>* ret = new LocalOperationCaller<Signature>(*this);
00693                 ret->setCaller( caller );
00694 #ifdef ORO_SIGNALLING_OPERATIONS
00695                 ret->setSignal( this->msig );
00696 #endif
00697                 return ret;
00698             }
00699 
00700             typename LocalOperationCallerImpl<Signature>::shared_ptr cloneRT() const
00701             {
00702                 
00703                 
00704                 return boost::allocate_shared<LocalOperationCaller<Signature> >(os::rt_allocator<LocalOperationCaller<Signature> >(), *this);
00705             }
00706         };
00707     }
00708 }
00709 
00710 #endif