Commit 8ef32d55 authored by ufownl's avatar ufownl

Fix the issue of empty non-POD classes serialization

parent 602dda7d
......@@ -266,7 +266,8 @@ private:
template <class T, class AccessPolicy,
class SerializePolicy = default_serialize_policy,
bool IsEnum = std::is_enum<T>::value,
bool IsEmptyType = std::is_class<T>::value&& std::is_empty<T>::value>
bool IsEmptyType = std::is_class<T>::value
&& std::is_empty<T>::value>
class member_tinfo : public abstract_uniform_type_info<T> {
public:
using super = abstract_uniform_type_info<T>;
......@@ -296,7 +297,6 @@ public:
}
private:
void ds(void* p, deserializer* d, std::true_type) const {
spol_(apol_(p), d);
}
......@@ -309,7 +309,6 @@ private:
AccessPolicy apol_;
SerializePolicy spol_;
};
template <class T, class A, class S>
......@@ -339,6 +338,38 @@ public:
}
};
template <class T>
struct empty_non_pod_type_wrapper {
// nop
};
template <class T, class A, class S>
class member_tinfo<empty_non_pod_type_wrapper<T>, A, S, false, true>
: public abstract_uniform_type_info<T> {
public:
using super = abstract_uniform_type_info<T>;
member_tinfo(const A&, const S&) : super("--member--") {
// nop
}
member_tinfo(const A&) : super("--member--") {
// nop
}
member_tinfo() : super("--member--") {
// nop
}
void serialize(const void*, serializer*) const override {
// nop
}
void deserialize(void*, deserializer*) const override {
// nop
}
};
template <class T, class AccessPolicy, class SerializePolicy>
class member_tinfo<T, AccessPolicy, SerializePolicy, true, false>
: public abstract_uniform_type_info<T> {
......@@ -503,7 +534,14 @@ public:
}
default_uniform_type_info(std::string tname) : super(std::move(tname)) {
using result_type = member_tinfo<T, fake_access_policy<T>>;
using result_type =
member_tinfo<
typename std::conditional<
std::is_polymorphic<T>::value,
empty_non_pod_type_wrapper<T>, T
>::type,
fake_access_policy<T>
>;
members_.push_back(uniform_type_info_ptr(new result_type));
}
......
......@@ -111,6 +111,15 @@ struct test_array {
int value2[2][4];
};
struct test_empty_non_pod {
virtual void foo() {
// nop
}
bool operator==(const test_empty_non_pod&) const {
return false;
}
};
struct fixture {
int32_t i32 = -345;
test_enum te = test_enum::b;
......@@ -129,6 +138,7 @@ struct fixture {
announce<test_enum>("test_enum");
announce(typeid(raw_struct), uniform_type_info_ptr{new raw_struct_type_info});
announce<test_array>("test_array", &test_array::value, &test_array::value2);
announce<test_empty_non_pod>("test_empty_non_pod");
rs.str.assign(string(str.rbegin(), str.rend()));
msg = make_message(i32, te, str, rs);
}
......@@ -286,6 +296,13 @@ CAF_TEST(test_array_serialization) {
}
}
CAF_TEST(test_empty_non_pod_serialization) {
test_empty_non_pod x;
auto buf = binary_util::serialize(x);
binary_util::deserialize(buf, &x);
CAF_CHECK(true);
}
CAF_TEST(test_single_message) {
auto buf = binary_util::serialize(msg);
message x;
......
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