MessagePack for C++
fusion.hpp
Go to the documentation of this file.
1//
2// MessagePack for C++ static resolution routine
3//
4// Copyright (C) 2015-2016 KONDO Takatoshi
5//
6// Distributed under the Boost Software License, Version 1.0.
7// (See accompanying file LICENSE_1_0.txt or copy at
8// http://www.boost.org/LICENSE_1_0.txt)
9//
10#ifndef MSGPACK_V1_TYPE_BOOST_FUSION_HPP
11#define MSGPACK_V1_TYPE_BOOST_FUSION_HPP
12
16#include "msgpack/meta.hpp"
17
19
20#if !defined (MSGPACK_USE_CPP03)
22#endif // #if !defined (MSGPACK_USE_CPP03)
23
24#if defined(__GNUC__)
25#pragma GCC diagnostic push
26#pragma GCC diagnostic ignored "-Wconversion"
27#endif // defined(__GNUC__)
28
29#include <boost/fusion/support/is_sequence.hpp>
30#include <boost/fusion/sequence/intrinsic/size.hpp>
31#include <boost/fusion/algorithm/iteration/for_each.hpp>
32#include <boost/fusion/sequence/intrinsic/at.hpp>
33#include <boost/fusion/include/mpl.hpp>
34
35
36#if defined(__GNUC__)
37#pragma GCC diagnostic pop
38#endif // defined(__GNUC__)
39
40
41#include <boost/mpl/size.hpp>
42
43namespace msgpack {
44
48
49namespace adaptor {
50
51namespace detail {
52
53template <typename T>
55 static bool const value = false;
56};
57
58template <typename T, typename U>
59struct is_std_pair<std::pair<T, U> > {
60 static bool const value = true;
61};
62
63#if !defined(MSGPACK_USE_CPP03)
64
65template <typename T>
67 static bool const value = false;
68};
69
70template <typename... Args>
71struct is_std_tuple<std::tuple<Args...>> {
72 static bool const value = true;
73};
74
75#endif // !defined(MSGPACK_USE_CPP03)
76
77template <typename T>
79 static bool const value =
80 boost::fusion::traits::is_sequence<T>::value
81 &&
83#if !defined (MSGPACK_USE_CPP03)
84 &&
86#endif // !defined (MSGPACK_USE_CPP03)
87 ;
88};
89
90} // namespace detail
91
92#if !defined (MSGPACK_USE_CPP03)
93
94template <typename T>
95struct as<
96 T,
97 typename msgpack::enable_if<
98 detail::is_seq_no_pair_no_tuple<T>::value &&
99 boost::mpl::fold<
100 T,
101 boost::mpl::bool_<true>,
102 boost::mpl::if_ <
103 boost::mpl::or_<
104 boost::mpl::_1,
105 msgpack::has_as<boost::mpl::_2>
106 >,
107 boost::mpl::bool_<true>,
108 boost::mpl::bool_<false>
109 >
110 >::type::value
111 >::type
112> {
113 T operator()(msgpack::object const& o) const {
114 if (o.type != msgpack::type::ARRAY) { throw msgpack::type_error(); }
115 if (o.via.array.size != checked_get_container_size(boost::mpl::size<T>::value)) {
116 throw msgpack::type_error();
117 }
118 using tuple_t = decltype(to_tuple(std::declval<T>(), gen_seq<boost::mpl::size<T>::value>()));
119 return to_t(
120 o.as<tuple_t>(),
121 msgpack::gen_seq<boost::mpl::size<T>::value>());
122 }
123 template<std::size_t... Is, typename U>
124 static std::tuple<
125 typename std::remove_reference<
126 typename boost::fusion::result_of::at_c<T, static_cast<int>(Is)>::type
127 >::type...>
128 to_tuple(U const& u, seq<Is...>) {
129 return std::make_tuple(boost::fusion::at_c<Is>(u)...);
130 }
131 template<std::size_t... Is, typename U>
132 static T to_t(U const& u, seq<Is...>) {
133 return T(std::get<Is>(u)...);
134 }
135};
136
137#endif // !defined (MSGPACK_USE_CPP03)
138
139template <typename T>
140struct convert<T, typename msgpack::enable_if<detail::is_seq_no_pair_no_tuple<T>::value>::type > {
141 msgpack::object const& operator()(msgpack::object const& o, T& v) const {
142 if (o.type != msgpack::type::ARRAY) { throw msgpack::type_error(); }
144 throw msgpack::type_error();
145 }
146 uint32_t index = 0;
147 boost::fusion::for_each(v, convert_imp(o, index));
148 return o;
149 }
150private:
151 struct convert_imp {
152 convert_imp(msgpack::object const& obj, uint32_t& index):obj_(obj), index_(index) {}
153 template <typename U>
154 void operator()(U& v) const {
155 msgpack::adaptor::convert<U>()(obj_.via.array.ptr[index_++], v);
156 }
157 private:
158 msgpack::object const& obj_;
159 uint32_t& index_;
160 };
161};
162
163template <typename T>
164struct pack<T, typename msgpack::enable_if<detail::is_seq_no_pair_no_tuple<T>::value>::type > {
165 template <typename Stream>
168 o.pack_array(size);
169 boost::fusion::for_each(v, pack_imp<Stream>(o));
170 return o;
171 }
172private:
173 template <typename Stream>
174 struct pack_imp {
175 pack_imp(msgpack::packer<Stream>& stream):stream_(stream) {}
176 template <typename U>
177 void operator()(U const& v) const {
178 stream_.pack(v);
179 }
180 private:
182 };
183};
184
185template <typename T>
186struct object_with_zone<T, typename msgpack::enable_if<detail::is_seq_no_pair_no_tuple<T>::value>::type > {
187 void operator()(msgpack::object::with_zone& o, const T& v) const {
191 o.via.array.size = size;
192 uint32_t count = 0;
193 boost::fusion::for_each(v, with_zone_imp(o, count));
194 }
195private:
196 struct with_zone_imp {
197 with_zone_imp(msgpack::object::with_zone const& obj, uint32_t& count):obj_(obj), count_(count) {}
198 template <typename U>
199 void operator()(U const& v) const {
200 obj_.via.array.ptr[count_++] = msgpack::object(v, obj_.zone);
201 }
202 msgpack::object::with_zone const& obj_;
203 uint32_t& count_;
204 };
205};
206
207} // namespace adaptor
208
210} // MSGPACK_API_VERSION_NAMESPACE(v1)
212
213} // namespace msgpack
214
215#endif // MSGPACK_V1_TYPE_BOOST_FUSION_HPP
The class template that supports continuous packing.
Definition: pack.hpp:33
packer< Stream > & pack_array(uint32_t n)
Packing array header and size.
Definition: pack.hpp:1195
Definition: object_fwd.hpp:231
void * allocate_align(size_t size, size_t align=MSGPACK_ZONE_ALIGN)
Definition: cpp03_zone.hpp:255
tuple make_tuple()
Definition: cpp03_msgpack_tuple.hpp:10408
std::size_t size(T const &t)
Definition: size_equal_only.hpp:24
@ ARRAY
Definition: object_fwd_decl.hpp:40
Definition: adaptor_base.hpp:15
uint32_t checked_get_container_size(T size)
Definition: check_container_size.hpp:55
Definition: object_fwd_decl.hpp:61
msgpack::object const & operator()(msgpack::object const &o, T &v) const
Definition: fusion.hpp:141
Definition: adaptor_base.hpp:27
msgpack::object const & operator()(msgpack::object const &o, T &v) const
Definition: object.hpp:646
static bool const value
Definition: fusion.hpp:79
Definition: fusion.hpp:54
static bool const value
Definition: fusion.hpp:55
static bool const value
Definition: fusion.hpp:67
void operator()(msgpack::object::with_zone &o, const T &v) const
Definition: fusion.hpp:187
Definition: adaptor_base.hpp:43
void operator()(msgpack::object::with_zone &o, T const &v) const
Definition: object.hpp:662
msgpack::packer< Stream > & operator()(msgpack::packer< Stream > &o, const T &v) const
Definition: fusion.hpp:166
Definition: adaptor_base.hpp:32
msgpack::packer< Stream > & operator()(msgpack::packer< Stream > &o, T const &v) const
Definition: object.hpp:655
Definition: meta.hpp:40
Definition: object.hpp:35
msgpack::zone & zone
Definition: object.hpp:37
uint32_t size
Definition: object_fwd.hpp:23
msgpack::object * ptr
Definition: object_fwd.hpp:24
Object class that corresponding to MessagePack format object.
Definition: object_fwd.hpp:75
std::enable_if< msgpack::has_as< T >::value, T >::type as() const
Get value as T.
Definition: object.hpp:1126
union_type via
Definition: object_fwd.hpp:93
msgpack::type::object_type type
Definition: object_fwd.hpp:92
msgpack::object_array array
Definition: object_fwd.hpp:85
#define MSGPACK_ZONE_ALIGNOF(type)
Definition: cpp03_zone_decl.hpp:30
#define MSGPACK_API_VERSION_NAMESPACE(ns)
Definition: versioning.hpp:66