Commit 5a61e5da authored by Dominik Charousset's avatar Dominik Charousset

Move to_string and from_string to a single header

parent 0a440521
...@@ -25,7 +25,6 @@ set (LIBCAF_CORE_SRCS ...@@ -25,7 +25,6 @@ set (LIBCAF_CORE_SRCS
src/actor_ostream.cpp src/actor_ostream.cpp
src/actor_proxy.cpp src/actor_proxy.cpp
src/actor_registry.cpp src/actor_registry.cpp
src/atom.cpp
src/attachable.cpp src/attachable.cpp
src/behavior.cpp src/behavior.cpp
src/behavior_stack.cpp src/behavior_stack.cpp
......
...@@ -36,11 +36,6 @@ enum class atom_value : uint64_t { ...@@ -36,11 +36,6 @@ enum class atom_value : uint64_t {
}; };
/**
* Returns `what` as a string representation.
*/
std::string to_string(const atom_value& what);
/** /**
* Creates an atom from given string literal. * Creates an atom from given string literal.
*/ */
......
...@@ -20,41 +20,6 @@ ...@@ -20,41 +20,6 @@
#ifndef CAF_FROM_STRING_HPP #ifndef CAF_FROM_STRING_HPP
#define CAF_FROM_STRING_HPP #define CAF_FROM_STRING_HPP
#include <string> #include "caf/string_serialization.hpp"
#include <typeinfo>
#include <exception>
#include "caf/uniform_type_info.hpp"
namespace caf {
/**
* Converts a string created by `to_string` to its original value.
*/
uniform_value from_string_impl(const std::string& what);
/**
* Convenience function that tries to deserializes a value from
* `what` and converts the result to `T`.
*/
template <class T>
optional<T> from_string(const std::string& what) {
auto uti = uniform_typeid<T>();
auto uv = from_string_impl(what);
if (!uv || (*uv->ti) != typeid(T)) {
// try again using the type name
std::string tmp = uti->name();
tmp += " ( ";
tmp += what;
tmp += " )";
uv = from_string_impl(tmp);
}
if (uv && (*uv->ti) == typeid(T)) {
return T{std::move(*reinterpret_cast<T*>(uv->val))};
}
return none;
}
} // namespace caf
#endif // CAF_FROM_STRING_HPP #endif // CAF_FROM_STRING_HPP
...@@ -159,11 +159,6 @@ class node_id : detail::comparable<node_id>, ...@@ -159,11 +159,6 @@ class node_id : detail::comparable<node_id>,
}; };
/**
* @relates node_id
*/
std::string to_string(const node_id& what);
} // namespace caf } // namespace caf
#endif // CAF_PROCESS_INFORMATION_HPP #endif // CAF_PROCESS_INFORMATION_HPP
...@@ -17,26 +17,80 @@ ...@@ -17,26 +17,80 @@
* http://www.boost.org/LICENSE_1_0.txt. * * http://www.boost.org/LICENSE_1_0.txt. *
******************************************************************************/ ******************************************************************************/
#include "caf/atom.hpp" #ifndef CAF_STRING_SERIALIZATION_HPP
#define CAF_STRING_SERIALIZATION_HPP
#include <string>
#include "caf/fwd.hpp"
#include "caf/optional.hpp"
#include "caf/uniform_type_info.hpp"
namespace std {
class exception;
}
namespace caf { namespace caf {
std::string to_string(const atom_value& what) { std::string to_string(const message& what);
auto x = static_cast<uint64_t>(what);
std::string result; std::string to_string(const group& what);
result.reserve(11);
// don't read characters before we found the leading 0xF std::string to_string(const channel& what);
// first four bits set?
bool read_chars = ((x & 0xF000000000000000) >> 60) == 0xF; std::string to_string(const message_id& what);
uint64_t mask = 0x0FC0000000000000;
for (int bitshift = 54; bitshift >= 0; bitshift -= 6, mask >>= 6) { std::string to_string(const actor_addr& what);
if (read_chars) {
result += detail::decoding_table[(x & mask) >> bitshift]; std::string to_string(const actor& what);
} else if (((x & mask) >> bitshift) == 0xF) {
read_chars = true; /**
} * @relates node_id
*/
//std::string to_string(const node_id::host_id_type& node_id);
/**
* @relates node_id
*/
std::string to_string(const node_id& what);
/**
* Returns `what` as a string representation.
*/
std::string to_string(const atom_value& what);
/**
* Converts `e` to a string including the demangled type of `e` and `e.what()`.
*/
std::string to_verbose_string(const std::exception& e);
/**
* Converts a string created by `to_string` to its original value.
*/
uniform_value from_string_impl(const std::string& what);
/**
* Convenience function that tries to deserializes a value from
* `what` and converts the result to `T`.
*/
template <class T>
optional<T> from_string(const std::string& what) {
auto uti = uniform_typeid<T>();
auto uv = from_string_impl(what);
if (!uv || (*uv->ti) != typeid(T)) {
// try again using the type name
std::string tmp = uti->name();
tmp += " ( ";
tmp += what;
tmp += " )";
uv = from_string_impl(tmp);
} }
return result; if (uv && (*uv->ti) == typeid(T)) {
return T{std::move(*reinterpret_cast<T*>(uv->val))};
}
return none;
} }
} // namespace caf } // namespace caf
#endif // CAF_STRING_SERIALIZATION_HPP
...@@ -20,76 +20,6 @@ ...@@ -20,76 +20,6 @@
#ifndef CAF_TO_STRING_HPP #ifndef CAF_TO_STRING_HPP
#define CAF_TO_STRING_HPP #define CAF_TO_STRING_HPP
#include <type_traits> #include "caf/string_serialization.hpp"
#include "caf/intrusive_ptr.hpp"
#include "caf/atom.hpp" // included for to_string(atom_value)
#include "caf/actor.hpp"
#include "caf/group.hpp"
#include "caf/channel.hpp"
#include "caf/node_id.hpp"
#include "caf/message.hpp"
#include "caf/anything.hpp"
#include "caf/actor_addr.hpp"
#include "caf/abstract_group.hpp"
#include "caf/uniform_type_info.hpp"
namespace std {
class exception;
}
namespace caf {
namespace detail {
std::string to_string_impl(const void* what, const uniform_type_info* utype);
template <class T>
inline std::string to_string_impl(const T& what) {
return to_string_impl(&what, uniform_typeid<T>());
}
} // namespace detail
std::string to_string(const actor_addr& what);
inline std::string to_string(const actor& what) {
return to_string(what.address());
}
inline std::string to_string(const message& what) {
return detail::to_string_impl(what);
}
inline std::string to_string(const group& what) {
return detail::to_string_impl(what);
}
inline std::string to_string(const channel& what) {
return detail::to_string_impl(what);
}
inline std::string to_string(const message_id& what) {
return detail::to_string_impl(what);
}
// implemented in node_id.cpp
std::string to_string(const node_id& what);
// implemented in node_id.cpp
std::string to_string(const node_id& what);
template <class T, class U, class... Us>
std::string to_string(const T& a1, const U& a2, const Us&... as) {
return to_string(a1) + ", " + to_string(a2, as...);
}
/**
* Converts `e` to a string including the demangled type of `e` and `e.what()`.
*/
std::string to_verbose_string(const std::exception& e);
} // namespace caf
#endif // CAF_TO_STRING_HPP #endif // CAF_TO_STRING_HPP
...@@ -123,17 +123,6 @@ node_id::node_id(uint32_t a, const host_id_type& b) : m_data(new data{a, b}) { ...@@ -123,17 +123,6 @@ node_id::node_id(uint32_t a, const host_id_type& b) : m_data(new data{a, b}) {
// nop // nop
} }
std::string to_string(const node_id::host_id_type& node_id) {
std::ostringstream oss;
oss << std::hex;
oss.fill('0');
for (size_t i = 0; i < node_id::host_id_size; ++i) {
oss.width(2);
oss << static_cast<uint32_t>(node_id[i]);
}
return oss.str();
}
int node_id::compare(const invalid_node_id_t&) const { int node_id::compare(const invalid_node_id_t&) const {
return m_data ? 1 : 0; // invalid instances are always smaller return m_data ? 1 : 0; // invalid instances are always smaller
} }
...@@ -162,12 +151,6 @@ int node_id::compare(const node_id& other) const { ...@@ -162,12 +151,6 @@ int node_id::compare(const node_id& other) const {
return tmp; return tmp;
} }
std::string to_string(const node_id& what) {
std::ostringstream oss;
oss << to_string(what.host_id()) << ":" << what.process_id();
return oss.str();
}
node_id::data::data(uint32_t procid, host_id_type hid) node_id::data::data(uint32_t procid, host_id_type hid)
: process_id(procid), host_id(hid) { : process_id(procid), host_id(hid) {
// nop // nop
......
...@@ -26,7 +26,12 @@ ...@@ -26,7 +26,12 @@
#include "caf/string_algorithms.hpp" #include "caf/string_algorithms.hpp"
#include "caf/atom.hpp" #include "caf/atom.hpp"
#include "caf/actor.hpp"
#include "caf/channel.hpp"
#include "caf/message.hpp"
#include "caf/node_id.hpp"
#include "caf/to_string.hpp" #include "caf/to_string.hpp"
#include "caf/actor_addr.hpp"
#include "caf/serializer.hpp" #include "caf/serializer.hpp"
#include "caf/from_string.hpp" #include "caf/from_string.hpp"
#include "caf/deserializer.hpp" #include "caf/deserializer.hpp"
...@@ -144,7 +149,7 @@ class string_serializer : public serializer, public dummy_backend { ...@@ -144,7 +149,7 @@ class string_serializer : public serializer, public dummy_backend {
if (!isbuiltin(tname)) if (!isbuiltin(tname))
out << tname; out << tname;
else if (tname.compare(0, 3, "@<>") == 0) { else if (tname.compare(0, 3, "@<>") == 0) {
std::vector<std::string> subtypes; std::vector<string> subtypes;
split(subtypes, tname, is_any_of("+"), token_compress_on); split(subtypes, tname, is_any_of("+"), token_compress_on);
} }
m_obj_just_opened = true; m_obj_just_opened = true;
...@@ -412,7 +417,7 @@ class string_deserializer : public deserializer, public dummy_backend { ...@@ -412,7 +417,7 @@ class string_deserializer : public deserializer, public dummy_backend {
} }
char c = *m_pos++; char c = *m_pos++;
if (!isxdigit(c)) { if (!isxdigit(c)) {
std::string errmsg = "unexpected character: '"; string errmsg = "unexpected character: '";
errmsg += c; errmsg += c;
errmsg += "', expected [0-9a-f]"; errmsg += "', expected [0-9a-f]";
throw_malformed(errmsg); throw_malformed(errmsg);
...@@ -510,9 +515,30 @@ string to_string_impl(const void* what, const uniform_type_info* utype) { ...@@ -510,9 +515,30 @@ string to_string_impl(const void* what, const uniform_type_info* utype) {
return osstr.str(); return osstr.str();
} }
template <class T>
inline string to_string_impl(const T& what) {
return to_string_impl(&what, uniform_typeid<T>());
}
} // namespace detail } // namespace detail
std::string to_string(const actor_addr& what) { string to_string(const message& what) {
return detail::to_string_impl(what);
}
string to_string(const group& what) {
return detail::to_string_impl(what);
}
string to_string(const channel& what) {
return detail::to_string_impl(what);
}
string to_string(const message_id& what) {
return detail::to_string_impl(what);
}
string to_string(const actor_addr& what) {
if (what == invalid_actor_addr) { if (what == invalid_actor_addr) {
return "0@00000000000000000000:0"; return "0@00000000000000000000:0";
} }
...@@ -521,6 +547,45 @@ std::string to_string(const actor_addr& what) { ...@@ -521,6 +547,45 @@ std::string to_string(const actor_addr& what) {
return oss.str(); return oss.str();
} }
string to_string(const actor& what) {
return to_string(what.address());
}
string to_string(const atom_value& what) {
auto x = static_cast<uint64_t>(what);
string result;
result.reserve(11);
// don't read characters before we found the leading 0xF
// first four bits set?
bool read_chars = ((x & 0xF000000000000000) >> 60) == 0xF;
uint64_t mask = 0x0FC0000000000000;
for (int bitshift = 54; bitshift >= 0; bitshift -= 6, mask >>= 6) {
if (read_chars) {
result += detail::decoding_table[(x & mask) >> bitshift];
} else if (((x & mask) >> bitshift) == 0xF) {
read_chars = true;
}
}
return result;
}
string to_string(const node_id::host_id_type& node_id) {
std::ostringstream oss;
oss << std::hex;
oss.fill('0');
for (size_t i = 0; i < node_id::host_id_size; ++i) {
oss.width(2);
oss << static_cast<uint32_t>(node_id[i]);
}
return oss.str();
}
string to_string(const node_id& what) {
std::ostringstream oss;
oss << to_string(what.host_id()) << ":" << what.process_id();
return oss.str();
}
string to_verbose_string(const std::exception& e) { string to_verbose_string(const std::exception& e) {
std::ostringstream oss; std::ostringstream oss;
oss << detail::demangle(typeid(e)) << ": " << e.what(); oss << detail::demangle(typeid(e)) << ": " << e.what();
......
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