1 // Copyright (c) 2007-2015 Hartmut Kaiser 2 // 3 // Distributed under the Boost Software License, Version 1.0. (See accompanying 4 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) 5 6 #if !defined(HPX_LCOS_ASYNC_COLOCATED_FEB_01_2014_0105PM) 7 #define HPX_LCOS_ASYNC_COLOCATED_FEB_01_2014_0105PM 8 9 #include <hpx/config.hpp> 10 #include <hpx/lcos/async_continue_fwd.hpp> 11 #include <hpx/lcos/async_fwd.hpp> 12 #include <hpx/lcos/detail/async_colocated_fwd.hpp> 13 #include <hpx/lcos/future.hpp> 14 #include <hpx/runtime/actions/action_support.hpp> 15 #include <hpx/runtime/agas/primary_namespace.hpp> 16 #include <hpx/runtime/agas/server/primary_namespace.hpp> 17 #include <hpx/runtime/naming/name.hpp> 18 #include <hpx/traits/extract_action.hpp> 19 #include <hpx/traits/is_continuation.hpp> 20 #include <hpx/traits/promise_local_result.hpp> 21 #include <hpx/util/bind.hpp> 22 #include <hpx/util/bind_action.hpp> 23 #include <hpx/util/functional/colocated_helpers.hpp> 24 #include <hpx/util/unique_function.hpp> 25 26 #include <type_traits> 27 #include <utility> 28 29 namespace hpx { namespace detail 30 { 31 template <typename Tuple> 32 struct async_colocated_bound_tuple; 33 34 template <typename ...Ts> 35 struct async_colocated_bound_tuple<util::tuple<Ts...> > 36 { 37 typedef 38 util::tuple< 39 hpx::util::detail::bound< 40 hpx::util::functional::extract_locality 41 , hpx::util::detail::placeholder<2ul> 42 , hpx::id_type 43 > 44 , Ts... 45 > 46 type; 47 }; 48 }} 49 50 #define HPX_REGISTER_ASYNC_COLOCATED_DECLARATION(Action, Name) \ 51 HPX_UTIL_REGISTER_UNIQUE_FUNCTION_DECLARATION( \ 52 void (hpx::naming::id_type, hpx::naming::id_type) \ 53 , (hpx::util::functional::detail::async_continuation_impl< \ 54 hpx::util::detail::bound_action< \ 55 Action \ 56 , hpx::detail::async_colocated_bound_tuple< \ 57 Action ::arguments_type \ 58 >::type \ 59 >, \ 60 hpx::util::unused_type \ 61 >) \ 62 , Name \ 63 ); \ 64 /**/ 65 66 #define HPX_REGISTER_ASYNC_COLOCATED(Action, Name) \ 67 HPX_UTIL_REGISTER_UNIQUE_FUNCTION( \ 68 void (hpx::naming::id_type, hpx::naming::id_type) \ 69 , (hpx::util::functional::detail::async_continuation_impl< \ 70 hpx::util::detail::bound_action< \ 71 Action \ 72 , hpx::detail::async_colocated_bound_tuple< \ 73 Action ::arguments_type \ 74 >::type \ 75 >, \ 76 hpx::util::unused_type \ 77 >) \ 78 , Name \ 79 ); \ 80 /**/ 81 82 namespace hpx { namespace detail 83 { 84 /////////////////////////////////////////////////////////////////////////// 85 template <typename Action, typename ...Ts> 86 lcos::future< 87 typename traits::promise_local_result< 88 typename hpx::traits::extract_action<Action>::remote_result_type 89 >::type> async_colocated(naming::id_type const & gid,Ts &&...vs)90 async_colocated(naming::id_type const& gid, Ts&&... vs) 91 { 92 // Attach the requested action as a continuation to a resolve_async 93 // call on the locality responsible for the target gid. 94 naming::id_type service_target( 95 agas::primary_namespace::get_service_instance(gid.get_gid()) 96 , naming::id_type::unmanaged); 97 98 typedef 99 typename hpx::traits::extract_action<Action>::remote_result_type 100 remote_result_type; 101 typedef agas::server::primary_namespace::colocate_action action_type; 102 103 using util::placeholders::_2; 104 return detail::async_continue_r<action_type, remote_result_type>( 105 util::functional::async_continuation( 106 util::bind<Action>( 107 util::bind(util::functional::extract_locality(), _2, gid) 108 , std::forward<Ts>(vs)...) 109 ), service_target, gid.get_gid()); 110 } 111 112 template < 113 typename Component, typename Signature, typename Derived, 114 typename ...Ts> 115 lcos::future< 116 typename traits::promise_local_result< 117 typename hpx::traits::extract_action<Derived>::remote_result_type 118 >::type> async_colocated(hpx::actions::basic_action<Component,Signature,Derived>,naming::id_type const & gid,Ts &&...vs)119 async_colocated( 120 hpx::actions::basic_action<Component, Signature, Derived> /*act*/ 121 , naming::id_type const& gid, Ts&&... vs) 122 { 123 return async_colocated<Derived>(gid, std::forward<Ts>(vs)...); 124 } 125 126 /////////////////////////////////////////////////////////////////////////// 127 template <typename Action, typename Continuation, typename ...Ts> 128 typename std::enable_if< 129 traits::is_continuation<Continuation>::value, 130 lcos::future< 131 typename traits::promise_local_result< 132 typename hpx::traits::extract_action<Action>::remote_result_type 133 >::type 134 > 135 >::type async_colocated(Continuation && cont,naming::id_type const & gid,Ts &&...vs)136 async_colocated(Continuation && cont, 137 naming::id_type const& gid, Ts&&... vs) 138 { 139 // Attach the requested action as a continuation to a resolve_async 140 // call on the locality responsible for the target gid. 141 naming::id_type service_target( 142 agas::primary_namespace::get_service_instance(gid.get_gid()) 143 , naming::id_type::unmanaged); 144 145 typedef 146 typename hpx::traits::extract_action<Action>::remote_result_type 147 remote_result_type; 148 typedef agas::server::primary_namespace::colocate_action action_type; 149 150 using util::placeholders::_2; 151 return detail::async_continue_r<action_type, remote_result_type>( 152 util::functional::async_continuation( 153 util::bind<Action>( 154 util::bind(util::functional::extract_locality(), _2, gid) 155 , std::forward<Ts>(vs)...) 156 , std::forward<Continuation>(cont)) 157 , service_target, gid.get_gid()); 158 } 159 160 template < 161 typename Continuation, 162 typename Component, typename Signature, typename Derived, 163 typename ...Ts> 164 typename std::enable_if< 165 traits::is_continuation<Continuation>::value, 166 lcos::future< 167 typename traits::promise_local_result< 168 typename hpx::traits::extract_action<Derived>::remote_result_type 169 >::type 170 > 171 >::type async_colocated(Continuation && cont,hpx::actions::basic_action<Component,Signature,Derived>,naming::id_type const & gid,Ts &&...vs)172 async_colocated( 173 Continuation && cont 174 , hpx::actions::basic_action<Component, Signature, Derived> /*act*/ 175 , naming::id_type const& gid, Ts&&... vs) 176 { 177 return async_colocated<Derived>(std::forward<Continuation>(cont), gid, 178 std::forward<Ts>(vs)...); 179 } 180 }} 181 182 #endif 183