/* * Copyright (c) 2011-2015 Samsung Electronics Co., Ltd All Rights Reserved * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ /** * @file serialization.h * @author Tomasz Swierczek (t.swierczek@samsung.com) * @version 1.0 * @brief Interfaces and templates used for data serialization. */ #ifndef CCHECKER_SERIALIZATION_H #define CCHECKER_SERIALIZATION_H #include #include #include #include #include #include namespace CCHECKER { // Abstract data stream buffer class IStream { public: virtual void Read(size_t num, void *bytes) = 0; virtual void Write(size_t num, const void *bytes) = 0; virtual ~IStream() {} }; // Serializable interface class ISerializable { public: /* ISerializable(){}; * ISerializable(IStream&){}; */ virtual void Serialize(IStream &) const = 0; virtual ~ISerializable() {} }; struct Serialization { // serialization // normal functions // ISerializable objects static void Serialize(IStream &stream, const ISerializable &object) { object.Serialize(stream); } static void Serialize(IStream &stream, const ISerializable *const object) { object->Serialize(stream); } // char static void Serialize(IStream &stream, const char value) { stream.Write(sizeof(value), &value); } static void Serialize(IStream &stream, const char *const value) { stream.Write(sizeof(*value), value); } // unsigned char static void Serialize(IStream &stream, const unsigned char value) { stream.Write(sizeof(value), &value); } static void Serialize(IStream &stream, const unsigned char *const value) { stream.Write(sizeof(*value), value); } // unsigned int32 static void Serialize(IStream &stream, const uint32_t value) { stream.Write(sizeof(value), &value); } static void Serialize(IStream &stream, const uint32_t *const value) { stream.Write(sizeof(*value), value); } // int32 static void Serialize(IStream &stream, const int32_t value) { stream.Write(sizeof(value), &value); } static void Serialize(IStream &stream, const int32_t *const value) { stream.Write(sizeof(*value), value); } // unsigned int64 static void Serialize(IStream &stream, const uint64_t value) { stream.Write(sizeof(value), &value); } static void Serialize(IStream &stream, const uint64_t *const value) { stream.Write(sizeof(*value), value); } // int64 static void Serialize(IStream &stream, const int64_t value) { stream.Write(sizeof(value), &value); } static void Serialize(IStream &stream, const int64_t *const value) { stream.Write(sizeof(*value), value); } // bool static void Serialize(IStream &stream, const bool value) { stream.Write(sizeof(value), &value); } static void Serialize(IStream &stream, const bool *const value) { stream.Write(sizeof(*value), value); } // std::string template static void Serialize(IStream &stream, const std::basic_string &str) { int length = str.size(); stream.Write(sizeof(length), &length); stream.Write(length * sizeof(T), str.data()); } template static void Serialize(IStream &stream, const std::basic_string *const str) { int length = str->size(); stream.Write(sizeof(length), &length); stream.Write(length * sizeof(T), str->data()); } // STL templates // std::list template static void Serialize(IStream &stream, const std::list &list) { int length = list.size(); stream.Write(sizeof(length), &length); for (typename std::list::const_iterator list_iter = list.begin(); list_iter != list.end(); list_iter++) { Serialize(stream, *list_iter); } } template static void Serialize(IStream &stream, const std::list *const list) { Serialize(stream, *list); } // RawBuffer template static void Serialize(IStream &stream, const std::vector &vec) { int length = vec.size(); stream.Write(sizeof(length), &length); stream.Write(length, vec.data()); } template static void Serialize(IStream &stream, const std::vector *const vec) { Serialize(stream, *vec); } // std::vector template static void Serialize(IStream &stream, const std::vector &vec) { int length = vec.size(); stream.Write(sizeof(length), &length); for (const auto &i : vec) { Serialize(stream, i); } } template static void Serialize(IStream &stream, const std::vector *const vec) { Serialize(stream, *vec); } // std::pair template static void Serialize(IStream &stream, const std::pair &p) { Serialize(stream, p.first); Serialize(stream, p.second); } template static void Serialize(IStream &stream, const std::pair *const p) { Serialize(stream, *p); } // std::map template static void Serialize(IStream &stream, const std::map &map) { int length = map.size(); stream.Write(sizeof(length), &length); typename std::map::const_iterator it; for (it = map.begin(); it != map.end(); ++it) { Serialize(stream, (*it).first); Serialize(stream, (*it).second); } } template static void Serialize(IStream &stream, const std::map *const map) { Serialize(stream, *map); } // std::unique_ptr template static void Serialize(IStream &stream, const std::unique_ptr &p) { Serialize(stream, *p); } }; // struct Serialization struct Deserialization { // deserialization // normal functions // ISerializable objects // T instead of ISerializable is needed to call proper constructor template static void Deserialize(IStream &stream, T &object) { object = T(stream); } template static void Deserialize(IStream &stream, T *&object) { object = new T(stream); } // char static void Deserialize(IStream &stream, char &value) { stream.Read(sizeof(value), &value); } static void Deserialize(IStream &stream, char *&value) { value = new char; stream.Read(sizeof(*value), value); } // unsigned char static void Deserialize(IStream &stream, unsigned char &value) { stream.Read(sizeof(value), &value); } static void Deserialize(IStream &stream, unsigned char *&value) { value = new unsigned char; stream.Read(sizeof(*value), value); } // unsigned int32 static void Deserialize(IStream &stream, uint32_t &value) { stream.Read(sizeof(value), &value); } static void Deserialize(IStream &stream, uint32_t *&value) { value = new uint32_t; stream.Read(sizeof(*value), value); } // int32 static void Deserialize(IStream &stream, int32_t &value) { stream.Read(sizeof(value), &value); } static void Deserialize(IStream &stream, int32_t *&value) { value = new int32_t; stream.Read(sizeof(*value), value); } // unsigned int64 static void Deserialize(IStream &stream, uint64_t &value) { stream.Read(sizeof(value), &value); } static void Deserialize(IStream &stream, uint64_t *&value) { value = new uint64_t; stream.Read(sizeof(*value), value); } // int64 static void Deserialize(IStream &stream, int64_t &value) { stream.Read(sizeof(value), &value); } static void Deserialize(IStream &stream, int64_t *&value) { value = new int64_t; stream.Read(sizeof(*value), value); } // bool static void Deserialize(IStream &stream, bool &value) { stream.Read(sizeof(value), &value); } static void Deserialize(IStream &stream, bool *&value) { value = new bool; stream.Read(sizeof(*value), value); } template static void Deserialize(IStream &stream, std::basic_string &str) { int length; stream.Read(sizeof(length), &length); std::vector buf(length); stream.Read(length * sizeof(T), buf.data()); str = std::basic_string(buf.data(), buf.data() + length); } template static void Deserialize(IStream &stream, std::basic_string *&str) { int length; stream.Read(sizeof(length), &length); std::vector buf(length); stream.Read(length * sizeof(T), buf.data()); str = new std::basic_string(buf.data(), buf.data() + length); } // STL templates // std::list template static void Deserialize(IStream &stream, std::list &list) { int length; stream.Read(sizeof(length), &length); for (int i = 0; i < length; ++i) { T obj; Deserialize(stream, obj); list.push_back(std::move(obj)); } } template static void Deserialize(IStream &stream, std::list *&list) { list = new std::list; Deserialize(stream, *list); } // RawBuffer template static void Deserialize(IStream &stream, std::vector &vec) { int length; stream.Read(sizeof(length), &length); vec.resize(length); stream.Read(length, vec.data()); } template static void Deserialize(IStream &stream, std::vector *&vec) { vec = new std::vector; Deserialize(stream, *vec); } // std::vector template static void Deserialize(IStream &stream, std::vector &vec) { int length; stream.Read(sizeof(length), &length); for (int i = 0; i < length; ++i) { T obj; Deserialize(stream, obj); vec.push_back(std::move(obj)); } } template static void Deserialize(IStream &stream, std::vector *&vec) { vec = new std::vector; Deserialize(stream, *vec); } // std::pair template static void Deserialize(IStream &stream, std::pair &p) { Deserialize(stream, p.first); Deserialize(stream, p.second); } template static void Deserialize(IStream &stream, std::pair *&p) { p = new std::pair; Deserialize(stream, *p); } // std::map template static void Deserialize(IStream &stream, std::map &map) { int length; stream.Read(sizeof(length), &length); for (int i = 0; i < length; ++i) { K key; T obj; Deserialize(stream, key); Deserialize(stream, obj); map[key] = std::move(obj); } } template static void Deserialize(IStream &stream, std::map *&map) { map = new std::map; Deserialize(stream, *map); } }; // struct Deserialization // generic serialization template struct Serializer; template struct Serializer : public Serializer { static void Serialize(IStream &stream, const First &f, const Args &... args) { Serialization::Serialize(stream, f); Serializer::Serialize(stream, args...); } }; // end of recursion template <> struct Serializer<> { static void Serialize(IStream &) { return; } }; // generic deserialization template struct Deserializer; template struct Deserializer : public Deserializer { static void Deserialize(IStream &stream, First &f, Args &... args) { Deserialization::Deserialize(stream, f); Deserializer::Deserialize(stream, args...); } }; // end of recursion template <> struct Deserializer<> { static void Deserialize(IStream &) { return; } }; } // CCHECKER #endif // CCHECKER_SERIALIZATION_H