Commit 8c71fa2f authored by Dominik Charousset's avatar Dominik Charousset

provide convenience function deserializer::read<T>

this member function automatically converts the read `primitive_variant`
to its native type T
parent 9d72da68
......@@ -98,6 +98,17 @@ class deserializer {
*/
virtual primitive_variant read_value(primitive_type ptype) = 0;
/**
* @brief Reads a value of type @p T from the data source of type @p ptype.
* @note @p T must be of a primitive type.
* @returns The read value of type @p T.
*/
template<typename T>
inline T read() {
auto val = read_value(detail::type_to_ptype<T>::ptype);
return std::move(get_ref<T>(val));
}
/**
* @brief Reads a tuple of primitive values from the data
* source of the types @p ptypes.
......
......@@ -212,8 +212,7 @@ class default_serialize_policy {
template<typename T>
void dimpl(T& storage, deserializer* d, primitive_impl) const {
primitive_variant val = d->read_value(type_to_ptype<T>::ptype);
storage = std::move(get<T>(val));
storage = d->read<T>();
}
template<typename T>
......
......@@ -126,7 +126,7 @@ class tree_type_info : public util::abstract_uniform_type_info<tree> {
void deserialize_node(tree_node& node, deserializer* source) const {
// value, ... children ...
auto value = get<std::uint32_t>(source->read_value(pt_uint32));
auto value = source->read<std::uint32_t>();
node.value = value;
auto num_children = source->begin_sequence();
for (size_t i = 0; i < num_children; ++i) {
......
......@@ -52,21 +52,21 @@ typedef const char* iterator;
inline void range_check(iterator begin, iterator end, size_t read_size) {
if ((begin + read_size) > end) {
CPPA_LOGF_ERROR("range_check failed");
throw out_of_range("binary_deserializer::read()");
throw out_of_range("binary_deserializer::read_range()");
}
}
template<typename T>
iterator read(iterator begin, iterator end, T& storage,
iterator read_range(iterator begin, iterator end, T& storage,
typename enable_if<is_integral<T>::value>::type* = 0) {
range_check(begin, end, sizeof(T));
memcpy(&storage, begin, sizeof(T));
return begin + sizeof(T);
}
iterator read(iterator begin, iterator end, string& storage) {
iterator read_range(iterator begin, iterator end, string& storage) {
uint32_t str_size;
begin = read(begin, end, str_size);
begin = read_range(begin, end, str_size);
range_check(begin, end, str_size);
storage.clear();
storage.reserve(str_size);
......@@ -78,11 +78,11 @@ iterator read(iterator begin, iterator end, string& storage) {
template<typename CharType, typename StringType>
iterator read_unicode_string(iterator begin, iterator end, StringType& str) {
uint32_t str_size;
begin = read(begin, end, str_size);
begin = read_range(begin, end, str_size);
str.reserve(str_size);
for (size_t i = 0; i < str_size; ++i) {
CharType c;
begin = read(begin, end, c);
begin = read_range(begin, end, c);
str += static_cast<typename StringType::value_type>(c);
}
return begin;
......@@ -90,7 +90,7 @@ iterator read_unicode_string(iterator begin, iterator end, StringType& str) {
// @returns the next iterator position
template<typename T>
iterator read(iterator begin, iterator end, T& value,
iterator read_range(iterator begin, iterator end, T& value,
typename enable_if<is_floating_point<T>::value>::type* = 0) {
// floating points are written as strings
string str;
......@@ -100,13 +100,13 @@ iterator read(iterator begin, iterator end, T& value,
return result;
}
iterator read(iterator begin, iterator end, u16string& storage) {
iterator read_range(iterator begin, iterator end, u16string& storage) {
// char16_t is guaranteed to has *at least* 16 bytes,
// but not to have *exactly* 16 bytes; thus use uint16_t
return read_unicode_string<uint16_t>(begin, end, storage);
}
iterator read(iterator begin, iterator end, u32string& storage) {
iterator read_range(iterator begin, iterator end, u32string& storage) {
// char32_t is guaranteed to has *at least* 32 bytes,
// but not to have *exactly* 32 bytes; thus use uint32_t
return read_unicode_string<uint32_t>(begin, end, storage);
......@@ -121,7 +121,7 @@ struct pt_reader {
template<typename T>
inline void operator()(T& value) {
begin = read(begin, end, value);
begin = read_range(begin, end, value);
}
};
......@@ -138,13 +138,13 @@ binary_deserializer::binary_deserializer(const char* bbegin, const char* bend,
string binary_deserializer::seek_object() {
string result;
pos = read(pos, end, result);
pos = read_range(pos, end, result);
return result;
}
string binary_deserializer::peek_object() {
string result;
read(pos, end, result);
read_range(pos, end, result);
return result;
}
......@@ -157,7 +157,7 @@ size_t binary_deserializer::begin_sequence() {
static_assert(sizeof(size_t) >= sizeof(uint32_t),
"sizeof(size_t) < sizeof(uint32_t)");
uint32_t result;
pos = read(pos, end, result);
pos = read_range(pos, end, result);
return static_cast<size_t>(result);
}
......
......@@ -73,11 +73,9 @@ void default_actor_addressing::write(serializer* sink, const actor_ptr& ptr) {
CPPA_LOG_ERROR("ptr is not a default_actor_proxy instance");
}
}
primitive_variant ptup[2];
ptup[0] = ptr->id();
ptup[1] = pinf->process_id();
sink->begin_object("@actor");
sink->write_tuple(2, ptup);
sink->write_value(ptr->id());
sink->write_value(pinf->process_id());
sink->write_raw(process_information::node_id_size,
pinf->node_id().data());
sink->end_object();
......@@ -94,23 +92,20 @@ actor_ptr default_actor_addressing::read(deserializer* source) {
return nullptr;
}
else if (cname == "@actor") {
primitive_variant ptup[2];
primitive_type ptypes[] = { pt_uint32, pt_uint32 };
process_information::node_id_type nid;
source->begin_object(cname);
source->read_tuple(2, ptypes, ptup);
auto aid = source->read<uint32_t>();
auto pid = source->read<uint32_t>();
source->read_raw(process_information::node_id_size, nid.data());
source->end_object();
// local actor?
auto pinf = process_information::get();
if ( pinf->process_id() == cppa::get<uint32_t>(ptup[1])
&& std::equal(pinf->node_id().begin(), pinf->node_id().end(), nid.begin())) {
auto id = cppa::get<uint32_t>(ptup[0]);
return detail::singleton_manager::get_actor_registry()->get(id);
if (pid == pinf->process_id() && nid == pinf->node_id()) {
return detail::singleton_manager::get_actor_registry()->get(aid);
}
else {
process_information tmp(cppa::get<uint32_t>(ptup[1]), nid);
return get_or_put(tmp, cppa::get<uint32_t>(ptup[0]));
process_information tmp(pid, nid);
return get_or_put(tmp, aid);
}
}
else throw runtime_error("expected type name \"@0\" or \"@actor\"; "
......@@ -144,7 +139,7 @@ void default_actor_addressing::put(const process_information& node,
if (i == submap.end()) {
submap.insert(make_pair(aid, proxy));
auto p = m_parent->get_peer(node);
CPPA_LOG_ERROR_IF(!p, "put a proxy for an unknown peer");
CPPA_LOG_WARNING_IF(!p, "put a proxy for an unknown peer");
if (p) {
p->enqueue({nullptr, nullptr}, make_any_tuple(atom("MONITOR"), process_information::get(), aid));
}
......
......@@ -279,8 +279,7 @@ class local_group_module : public group::module {
intrusive_ptr<group> deserialize(deserializer* source) {
// deserialize {identifier, process_id, node_id}
auto pv_identifier = source->read_value(pt_u8string);
auto& identifier = cppa::get<string>(pv_identifier);
auto identifier = source->read<string>();
// deserialize broker
actor_ptr broker;
m_actor_utype->deserialize(&broker, source);
......@@ -513,8 +512,7 @@ class remote_group_module : public group::module {
}
intrusive_ptr<group> deserialize(deserializer* source) {
auto pv_identifier = source->read_value(pt_u8string);
return get(cppa::get<string>(pv_identifier));
return get(source->read<string>());
}
void serialize(group* ptr, serializer* sink) {
......
......@@ -558,8 +558,9 @@ void abstract_middleman::stop_reader(const continuable_reader_ptr& ptr) {
void middleman_loop(middleman_impl* impl) {
middleman_event_handler* handler = &impl->m_handler;
CPPA_LOGF_TRACE("run middleman loop, node: "
<< to_string(*process_information::get()));
CPPA_LOGF_TRACE("run middleman loop");
CPPA_LOGF_INFO("middleman runs at "
<< to_string(*process_information::get()));
handler->init();
impl->continue_reader(make_counted<middleman_overseer>(impl->m_pipe_read, impl->m_queue));
handler->update();
......
......@@ -235,8 +235,8 @@ class group_ptr_tinfo : public util::abstract_uniform_type_info<group_ptr> {
}
else {
source->begin_object(name);
auto modname = source->read_value(pt_u8string);
ptrref = group::get_module(get<string>(modname))
auto modname = source->read<string>();
ptrref = group::get_module(modname)
->deserialize(source);
source->end_object();
}
......@@ -411,8 +411,8 @@ class msg_hdr_tinfo : public util::abstract_uniform_type_info<network::message_h
auto& msg = *reinterpret_cast<network::message_header*>(instance);
actor_ptr_tinfo::s_deserialize(msg.sender, source, actor_ptr_name);
actor_ptr_tinfo::s_deserialize(msg.receiver, source, actor_ptr_name);
auto msg_id = source->read_value(pt_uint64);
msg.id = message_id_t::from_integer_value(get<pt_uint64>(msg_id));
auto msg_id = source->read<std::uint64_t>();
msg.id = message_id_t::from_integer_value(msg_id);
source->end_object();
}
......@@ -453,7 +453,7 @@ class process_info_ptr_tinfo : public util::abstract_uniform_type_info<process_i
}
else {
source->begin_object(cname);
auto id = get<uint32_t>(source->read_value(pt_uint32));
auto id = source->read<uint32_t>();
process_information::node_id_type nid;
source->read_raw(nid.size(), nid.data());
source->end_object();
......@@ -478,9 +478,8 @@ class atom_value_tinfo : public util::abstract_uniform_type_info<atom_value> {
assert_type_name(source);
auto val = reinterpret_cast<atom_value*>(instance);
source->begin_object(name());
auto ptval = source->read_value(pt_uint64);
*val = static_cast<atom_value>(source->read<uint64_t>());
source->end_object();
*val = static_cast<atom_value>(get<uint64_t>(ptval));
}
};
......@@ -499,10 +498,10 @@ class duration_tinfo : public util::abstract_uniform_type_info<util::duration> {
assert_type_name(source);
source->begin_object(name());
auto val = reinterpret_cast<util::duration*>(instance);
auto unit_val = source->read_value(pt_uint32);
auto count_val = source->read_value(pt_uint32);
auto unit_val = source->read<uint32_t>();
auto count_val = source->read<uint32_t>();
source->end_object();
switch (get<uint32_t>(unit_val)) {
switch (unit_val) {
case 1:
val->unit = util::time_unit::seconds;
break;
......@@ -519,7 +518,7 @@ class duration_tinfo : public util::abstract_uniform_type_info<util::duration> {
val->unit = util::time_unit::none;
break;
}
val->count = get<uint32_t>(count_val);
val->count = count_val;
}
};
......@@ -555,9 +554,8 @@ class bool_tinfo : public util::abstract_uniform_type_info<bool> {
virtual void deserialize(void* instance, deserializer* source) const {
assert_type_name(source);
source->begin_object(name());
auto ptval = source->read_value(pt_uint8);
*reinterpret_cast<bool*>(instance) = source->read<uint8_t>() != 0;
source->end_object();
*reinterpret_cast<bool*>(instance) = (get<pt_uint8>(ptval) != 0);
}
};
......
......@@ -136,7 +136,7 @@ struct raw_struct_type_info : util::abstract_uniform_type_info<raw_struct> {
source->begin_object(name());
auto rs = reinterpret_cast<raw_struct*>(ptr);
rs->str.clear();
auto size = get<std::uint32_t>(source->read_value(pt_uint32));
auto size = source->read<std::uint32_t>();
rs->str.resize(size);
source->read_raw(size, &(rs->str[0]));
source->end_object();
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment