#pragma once #include "remote.hpp" #include namespace saw { namespace rmt { struct Loopback {}; } template<> class remote { private: struct key_t { std::array data; bool operator<(const std::array& rhs) const { for(uint64_t i = 0u; i < 3; ++i){ if(data[i] != rhs.data[i]){ return data[i] < rhs.data[i]; } } return false; } }; std::map>> registered_data_servers_; public: /** * Resolves an address for the remote */ error_or>> parse_address(data id){ return heap>(id); } /** * Connect to a remote */ template conveyor> connect(const remote_address& addr); /** * Start listening */ template rpc_server listen(const remote_address& addr, typename rpc_server::InterfaceT iface){ return {addr, std::move(iface)}; } /** * Start data server */ template error_or>> data_listen(const remote_address& addr){ auto find = registered_data_servers_.find(addr.get_address_id()); if(find == registered_data_servers_.end()){ return make_error("Server already bound to this address"); } return {addr,*this}; } /** * Connect to a data server */ template conveyor> data_connect(const remote_address& addr){ auto class_id = srv.get_class_id(); key_t key; key.data = {addr.get_address_id(), class_id.first, class_id.second}; auto find = registered_data_servers_.find(key); if(find == registered_data_servers_.end()){ return make_error("Server not found"); } } /** * Internal function */ error_or register_data_server(const remote_address& addr, i_data_server& srv){ auto class_id = srv.get_class_id(); key_t key; key.data = {addr.get_address_id(), class_id.first, class_id.second}; auto insert = registered_data_servers_.emplace(std::make_pair(key, {srv})); if(insert.second){ return make_error("Server already bound to this address"); } return make_void(); } }; }