MessagePack for C++
Loading...
Searching...
No Matches
object.hpp
Go to the documentation of this file.
1//
2// MessagePack for C++ static resolution routine
3//
4// Copyright (C) 2008-2014 FURUHASHI Sadayuki and 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_OBJECT_HPP
11#define MSGPACK_V1_OBJECT_HPP
12
15
16#include <cstring>
17#include <stdexcept>
18#include <typeinfo>
19#include <limits>
20#include <ostream>
21#include <typeinfo>
22#include <iomanip>
23
24namespace msgpack {
25
29
34
41
42
45public:
48
50
55 msgpack::object const& obj,
56#if defined(MSGPACK_USE_CPP03)
57 msgpack::unique_ptr<msgpack::zone> z
58#else // defined(MSGPACK_USE_CPP03)
59 msgpack::unique_ptr<msgpack::zone>&& z
60#endif // defined(MSGPACK_USE_CPP03)
61 ) :
62 m_obj(obj), m_zone(msgpack::move(z)) { }
63
64 void set(msgpack::object const& obj)
65 { m_obj = obj; }
66
68
71 const msgpack::object& get() const
72 { return m_obj; }
73
78 { return get(); }
79
84 { return &get(); }
85
87
90 msgpack::unique_ptr<msgpack::zone>& zone()
91 { return m_zone; }
92
94
97 const msgpack::unique_ptr<msgpack::zone>& zone() const
98 { return m_zone; }
99
100#if defined(MSGPACK_USE_CPP03)
101 struct object_handle_ref {
102 object_handle_ref(object_handle* oh):m_oh(oh) {}
103 object_handle* m_oh;
104 };
105
107 m_obj(other.m_obj),
108 m_zone(msgpack::move(other.m_zone)) {
109 }
110
111 object_handle(object_handle_ref ref):
112 m_obj(ref.m_oh->m_obj),
113 m_zone(msgpack::move(ref.m_oh->m_zone)) {
114 }
115
116 object_handle& operator=(object_handle& other) {
117 m_obj = other.m_obj;
118 m_zone = msgpack::move(other.m_zone);
119 return *this;
120 }
121
122 object_handle& operator=(object_handle_ref ref) {
123 m_obj = ref.m_oh->m_obj;
124 m_zone = msgpack::move(ref.m_oh->m_zone);
125 return *this;
126 }
127
128 operator object_handle_ref() {
129 return object_handle_ref(this);
130 }
131#endif // defined(MSGPACK_USE_CPP03)
132
133private:
134 msgpack::object m_obj;
135 msgpack::unique_ptr<msgpack::zone> m_zone;
136};
137
138namespace detail {
139
140template <std::size_t N>
141inline std::size_t add_ext_type_size(std::size_t size) {
142 return size + 1;
143}
144
145template <>
146inline std::size_t add_ext_type_size<4>(std::size_t size) {
147 return size == 0xffffffff ? size : size + 1;
148}
149
150} // namespace detail
152private:
153 enum next_ret {
154 cont,
155 finish,
156 abort
157 };
158 struct elem {
159 elem(msgpack::object const* p, std::size_t r)
160 : rest(r), is_map(false), is_key(false) {
161 as.obj_ptr = p;
162 }
163
164 elem(msgpack::object_kv const* p, std::size_t r)
165 : rest(r), is_map(true), is_key(true) {
166 as.kv_ptr = p;
167 }
168
169 msgpack::object const& get() const {
170 if (is_map) {
171 if (is_key) {
172 return as.kv_ptr->key;
173 }
174 else {
175 return as.kv_ptr->val;
176 }
177 }
178 else {
179 return *as.obj_ptr;
180 }
181 }
182
183 template <typename Visitor>
184 next_ret next(Visitor& v) {
185 if (rest == 0) {
186 if (is_map) {
187 if (!v.end_map()) return abort;
188 }
189 else {
190 if (!v.end_array()) return abort;
191 }
192 return finish;
193 }
194 else {
195 if (is_map) {
196 if (is_key) {
197 if (!v.end_map_key()) return abort;
198 if (!v.start_map_value()) return abort;
199 is_key = false;
200 }
201 else {
202 if (!v.end_map_value()) return abort;
203 --rest;
204 if (rest == 0) {
205 if (!v.end_map()) return abort;
206 return finish;
207 }
208 if (!v.start_map_key()) return abort;
209 ++as.kv_ptr;
210 is_key = true;
211 }
212 }
213 else {
214 if (!v.end_array_item()) return abort;
215 --rest;
216 if (rest == 0) {
217 if (!v.end_array()) return abort;
218 return finish;
219 }
220 if (!v.start_array_item()) return abort;
221 ++as.obj_ptr;
222 }
223 return cont;
224 }
225 }
226
227 union {
228 msgpack::object const* obj_ptr;
229 msgpack::object_kv const* kv_ptr;
230 } as;
231 std::size_t rest;
232 bool is_map;
233 bool is_key;
234 };
235public:
236 explicit object_parser(msgpack::object const& obj):m_current(&obj) {}
237 template <typename Visitor>
238 void parse(Visitor& v) {
239 while (true) {
240 bool start_collection = false;
241 switch(m_current->type) {
242 case msgpack::type::NIL:
243 if (!v.visit_nil()) return;
244 break;
245 case msgpack::type::BOOLEAN:
246 if (!v.visit_boolean(m_current->via.boolean)) return;
247 break;
248 case msgpack::type::POSITIVE_INTEGER:
249 if (!v.visit_positive_integer(m_current->via.u64)) return;
250 break;
251 case msgpack::type::NEGATIVE_INTEGER:
252 if (!v.visit_negative_integer(m_current->via.i64)) return;
253 break;
254 case msgpack::type::FLOAT32:
255 if (!v.visit_float32(static_cast<float>(m_current->via.f64))) return;
256 break;
257 case msgpack::type::FLOAT64:
258 if (!v.visit_float64(m_current->via.f64)) return;
259 break;
260 case msgpack::type::STR:
261 if (!v.visit_str(m_current->via.str.ptr, m_current->via.str.size)) return;
262 break;
263 case msgpack::type::BIN:
264 if (!v.visit_bin(m_current->via.bin.ptr, m_current->via.bin.size)) return;
265 break;
266 case msgpack::type::EXT:
267 msgpack::detail::check_container_size<sizeof(std::size_t)>(m_current->via.ext.size);
268 if (!v.visit_ext(m_current->via.ext.ptr, m_current->via.ext.size + 1)) return;
269 break;
270 case msgpack::type::ARRAY:
271 if (!v.start_array(m_current->via.array.size)) return;
272 m_ctx.push_back(elem(m_current->via.array.ptr, m_current->via.array.size));
273 start_collection = m_current->via.array.size != 0;
274 if (start_collection) {
275 if (!v.start_array_item()) return;
276 }
277 break;
278 case msgpack::type::MAP:
279 if (!v.start_map(m_current->via.map.size)) return;
280 m_ctx.push_back(elem(m_current->via.map.ptr, m_current->via.map.size));
281 start_collection = m_current->via.map.size != 0;
282 if (start_collection) {
283 if (!v.start_map_key()) return;
284 }
285 break;
286 default:
287 throw msgpack::type_error();
288 break;
289 }
290 if (m_ctx.empty()) return;
291 if (!start_collection) {
292 while (true) {
293 next_ret r = m_ctx.back().next(v);
294 if (r == finish) {
295 m_ctx.pop_back();
296 if (m_ctx.empty()) return;
297 }
298 else if (r == cont) {
299 break;
300 }
301 else {
302 // abort
303 return;
304 }
305 }
306 }
307 m_current = &m_ctx.back().get();
308 }
309 }
310private:
311 msgpack::object const* m_current;
312 std::vector<elem> m_ctx;
313};
314
315template <typename Stream>
318 :m_packer(pk) {}
319 bool visit_nil() {
320 m_packer.pack_nil();
321 return true;
322 }
323 bool visit_boolean(bool v) {
324 if (v) m_packer.pack_true();
325 else m_packer.pack_false();
326 return true;
327 }
328 bool visit_positive_integer(uint64_t v) {
329 m_packer.pack_uint64(v);
330 return true;
331 }
332 bool visit_negative_integer(int64_t v) {
333 m_packer.pack_int64(v);
334 return true;
335 }
336 bool visit_float32(float v) {
337 m_packer.pack_float(v);
338 return true;
339 }
340 bool visit_float64(double v) {
341 m_packer.pack_double(v);
342 return true;
343 }
344 bool visit_str(const char* v, uint32_t size) {
345 m_packer.pack_str(size);
346 m_packer.pack_str_body(v, size);
347 return true;
348 }
349 bool visit_bin(const char* v, uint32_t size) {
350 m_packer.pack_bin(size);
351 m_packer.pack_bin_body(v, size);
352 return true;
353 }
354 bool visit_ext(const char* v, uint32_t size) {
355 m_packer.pack_ext(size - 1, static_cast<int8_t>(*v));
356 m_packer.pack_ext_body(v + 1, size - 1);
357 return true;
358 }
359 bool start_array(uint32_t num_elements) {
360 m_packer.pack_array(num_elements);
361 return true;
362 }
364 return true;
365 }
367 return true;
368 }
369 bool end_array() {
370 return true;
371 }
372 bool start_map(uint32_t num_kv_pairs) {
373 m_packer.pack_map(num_kv_pairs);
374 return true;
375 }
377 return true;
378 }
379 bool end_map_key() {
380 return true;
381 }
383 return true;
384 }
386 return true;
387 }
388 bool end_map() {
389 return true;
390 }
391private:
392 msgpack::packer<Stream>& m_packer;
393};
394
395
397 explicit object_stringize_visitor(std::ostream& os)
398 :m_os(os) {}
399 bool visit_nil() {
400 m_os << "null";
401 return true;
402 }
403 bool visit_boolean(bool v) {
404 if (v) m_os << "true";
405 else m_os << "false";
406 return true;
407 }
408 bool visit_positive_integer(uint64_t v) {
409 m_os << v;
410 return true;
411 }
412 bool visit_negative_integer(int64_t v) {
413 m_os << v;
414 return true;
415 }
416 bool visit_float32(float v) {
417 m_os << v;
418 return true;
419 }
420 bool visit_float64(double v) {
421 m_os << v;
422 return true;
423 }
424 bool visit_str(const char* v, uint32_t size) {
425 m_os << '"';
426 for (uint32_t i = 0; i < size; ++i) {
427 char c = v[i];
428 switch (c) {
429 case '\\':
430 m_os << "\\\\";
431 break;
432 case '"':
433 m_os << "\\\"";
434 break;
435 case '/':
436 m_os << "\\/";
437 break;
438 case '\b':
439 m_os << "\\b";
440 break;
441 case '\f':
442 m_os << "\\f";
443 break;
444 case '\n':
445 m_os << "\\n";
446 break;
447 case '\r':
448 m_os << "\\r";
449 break;
450 case '\t':
451 m_os << "\\t";
452 break;
453 default: {
454 unsigned int code = static_cast<unsigned int>(c);
455 if (code < 0x20 || code == 0x7f) {
456 std::ios::fmtflags flags(m_os.flags());
457 m_os << "\\u" << std::hex << std::setw(4) << std::setfill('0') << (code & 0xff);
458 m_os.flags(flags);
459 }
460 else {
461 m_os << c;
462 }
463 } break;
464 }
465 }
466 m_os << '"';
467 return true;
468 }
469 bool visit_bin(const char* /*v*/, uint32_t size) {
470 m_os << "\"BIN(size:" << size << ")\"";
471 return true;
472 }
473 bool visit_ext(const char* v, uint32_t size) {
474 if (size == 0) {
475 m_os << "\"EXT(size:0)\"";
476 }
477 else {
478 m_os << "\"EXT(type:" << static_cast<int>(v[0]) << ",size:" << size - 1 << ")\"";
479 }
480 return true;
481 }
482 bool start_array(uint32_t num_elements) {
483 m_current_size.push_back(num_elements);
484 m_os << "[";
485 return true;
486 }
488 return true;
489 }
491 --m_current_size.back();
492 if (m_current_size.back() != 0) {
493 m_os << ",";
494 }
495 return true;
496 }
497 bool end_array() {
498 m_current_size.pop_back();
499 m_os << "]";
500 return true;
501 }
502 bool start_map(uint32_t num_kv_pairs) {
503 m_current_size.push_back(num_kv_pairs);
504 m_os << "{";
505 return true;
506 }
508 return true;
509 }
510 bool end_map_key() {
511 m_os << ":";
512 return true;
513 }
515 return true;
516 }
518 --m_current_size.back();
519 if (m_current_size.back() != 0) {
520 m_os << ",";
521 }
522 return true;
523 }
524 bool end_map() {
525 m_current_size.pop_back();
526 m_os << "}";
527 return true;
528 }
529private:
530 std::ostream& m_os;
531 std::vector<uint32_t> m_current_size;
532};
533
535 explicit aligned_zone_size_visitor(std::size_t& s)
536 :m_size(s) {}
537 bool visit_nil() {
538 return true;
539 }
540 bool visit_boolean(bool) {
541 return true;
542 }
543 bool visit_positive_integer(uint64_t) {
544 return true;
545 }
547 return true;
548 }
549 bool visit_float32(float) {
550 return true;
551 }
552 bool visit_float64(double) {
553 return true;
554 }
555 bool visit_str(const char*, uint32_t size) {
556 m_size += msgpack::aligned_size(size, MSGPACK_ZONE_ALIGNOF(char));
557 return true;
558 }
559 bool visit_bin(const char*, uint32_t size) {
560 m_size += msgpack::aligned_size(size, MSGPACK_ZONE_ALIGNOF(char));
561 return true;
562 }
563 bool visit_ext(const char*, uint32_t size) {
564 m_size += msgpack::aligned_size(size, MSGPACK_ZONE_ALIGNOF(char));
565 return true;
566 }
567 bool start_array(uint32_t num_elements) {
568 m_size += msgpack::aligned_size(
569 sizeof(msgpack::object) * num_elements,
571 return true;
572 }
574 return true;
575 }
577 return true;
578 }
579 bool end_array() {
580 return true;
581 }
582 bool start_map(uint32_t num_kv_pairs) {
583 m_size += msgpack::aligned_size(
584 sizeof(msgpack::object_kv) * num_kv_pairs,
586 return true;
587 }
589 return true;
590 }
591 bool end_map_key() {
592 return true;
593 }
595 return true;
596 }
598 return true;
599 }
600 bool end_map() {
601 return true;
602 }
603private:
604 std::size_t& m_size;
605};
606
607inline std::size_t aligned_zone_size(msgpack::object const& obj) {
608 std::size_t s = 0;
611 return s;
612}
613
615
623 std::size_t size = msgpack::aligned_zone_size(obj);
624 msgpack::unique_ptr<msgpack::zone> z(size == 0 ? MSGPACK_NULLPTR : new msgpack::zone(size));
625 msgpack::object newobj = z.get() ? msgpack::object(obj, *z) : obj;
626 return object_handle(newobj, msgpack::move(z));
627}
628
629template <typename T>
630inline object::implicit_type::operator T() { return obj.as<T>(); }
631
632namespace detail {
633template <typename Stream, typename T>
634struct packer_serializer {
636 v.msgpack_pack(o);
637 return o;
638 }
639};
640} // namespace detail
641
642// Adaptor functors' member functions definitions.
643template <typename T, typename Enabler>
644inline
645msgpack::object const&
647 v.msgpack_unpack(o.convert());
648 return o;
649}
650
651template <typename T, typename Enabler>
652template <typename Stream>
653inline
656 return msgpack::detail::packer_serializer<Stream, T>::pack(o, v);
657}
658
659template <typename T, typename Enabler>
660inline
661void
663 v.msgpack_object(static_cast<msgpack::object*>(&o), o.zone);
664}
665
666// Adaptor functor specialization to object
667namespace adaptor {
668
669template <>
672 v = o;
673 return o;
674 }
675};
676
677template <>
679 template <typename Stream>
685};
686
687template <>
690 object_with_zone_visitor vis(o);
692 }
693private:
694 struct object_with_zone_visitor {
695 explicit object_with_zone_visitor(msgpack::object::with_zone& owz)
696 :m_zone(owz.zone), m_ptr(&owz) {
697 m_objs.push_back(&owz);
698 }
699 bool visit_nil() {
700 m_ptr->type = msgpack::type::NIL;
701 return true;
702 }
703 bool visit_boolean(bool v) {
704 m_ptr->type = msgpack::type::BOOLEAN;
705 m_ptr->via.boolean = v;
706 return true;
707 }
708 bool visit_positive_integer(uint64_t v) {
710 m_ptr->via.u64 = v;
711 return true;
712 }
713 bool visit_negative_integer(int64_t v) {
715 m_ptr->via.i64 = v;
716 return true;
717 }
718 bool visit_float32(float v) {
719 m_ptr->type = msgpack::type::FLOAT32;
720 m_ptr->via.f64 = v;
721 return true;
722 }
723 bool visit_float64(double v) {
724 m_ptr->type = msgpack::type::FLOAT64;
725 m_ptr->via.f64 = v;
726 return true;
727 }
728 bool visit_str(const char* v, uint32_t size) {
729 m_ptr->type = msgpack::type::STR;
730 m_ptr->via.str.size = size;
731 char* ptr = static_cast<char*>(m_zone.allocate_align(size, MSGPACK_ZONE_ALIGNOF(char)));
732 m_ptr->via.str.ptr = ptr;
733 std::memcpy(ptr, v, size);
734 return true;
735 }
736 bool visit_bin(const char* v, uint32_t size) {
737 m_ptr->type = msgpack::type::BIN;
738 m_ptr->via.bin.size = size;
739 char* ptr = static_cast<char*>(m_zone.allocate_align(size, MSGPACK_ZONE_ALIGNOF(char)));
740 m_ptr->via.bin.ptr = ptr;
741 std::memcpy(ptr, v, size);
742 return true;
743 }
744 bool visit_ext(const char* v, uint32_t size) {
745 m_ptr->type = msgpack::type::EXT;
746
747 // v contains type but length(size) doesn't count the type byte.
748 // See https://github.com/msgpack/msgpack/blob/master/spec.md#ext-format-family
749 m_ptr->via.ext.size = size - 1;
750
751 char* ptr = static_cast<char*>(m_zone.allocate_align(size, MSGPACK_ZONE_ALIGNOF(char)));
752 m_ptr->via.ext.ptr = ptr;
753 std::memcpy(ptr, v, size);
754 return true;
755 }
756 bool start_array(uint32_t num_elements) {
757 m_ptr->type = msgpack::type::ARRAY;
758 m_ptr->via.array.ptr = static_cast<msgpack::object*>(
759 m_zone.allocate_align(
760 sizeof(msgpack::object) * num_elements, MSGPACK_ZONE_ALIGNOF(msgpack::object)));
761 m_ptr->via.array.size = num_elements;
762 m_objs.push_back(elem(m_ptr->via.array.ptr));
763 return true;
764 }
765 bool start_array_item() {
766 m_ptr = m_objs.back().get_item();
767 return true;
768 }
769 bool end_array_item() {
770 ++m_objs.back().as.obj;
771 return true;
772 }
773 bool end_array() {
774 m_objs.pop_back();
775 return true;
776 }
777 bool start_map(uint32_t num_kv_pairs) {
778 m_ptr->type = msgpack::type::MAP;
779 m_ptr->via.map.ptr = (msgpack::object_kv*)m_zone.allocate_align(
781 m_ptr->via.map.size = num_kv_pairs;
782 m_objs.push_back(elem(m_ptr->via.map.ptr));
783 return true;
784 }
785 bool start_map_key() {
786 m_ptr = m_objs.back().get_key();
787 return true;
788 }
789 bool end_map_key() {
790 return true;
791 }
792 bool start_map_value() {
793 m_ptr = m_objs.back().get_val();
794 return true;
795 }
796 bool end_map_value() {
797 ++m_objs.back().as.kv;
798 return true;
799 }
800 bool end_map() {
801 m_objs.pop_back();
802 return true;
803 }
804 private:
805 struct elem {
806 elem(msgpack::object* obj)
807 :is_obj(true) {
808 as.obj = obj;
809 }
810 elem(msgpack::object_kv* kv)
811 :is_obj(false) {
812 as.kv = kv;
813 }
814 msgpack::object* get_item() {
815 return as.obj;
816 }
817 msgpack::object* get_key() {
818 return &as.kv->key;
819 }
820 msgpack::object* get_val() {
821 return &as.kv->val;
822 }
823 union {
824 msgpack::object* obj;
826 } as;
827 bool is_obj;
828 };
829 std::vector<elem> m_objs;
830 msgpack::zone& m_zone;
831 msgpack::object* m_ptr;
832 };
833};
834
835// Adaptor functor specialization to object::with_zone
836
837template <>
838struct object_with_zone<msgpack::object::with_zone> {
841 msgpack::object::with_zone const& v) const {
842 o << static_cast<msgpack::object const&>(v);
843 }
844};
845
846
847} // namespace adaptor
848
849
850// obsolete
851template <typename Type>
852class define : public Type {
853public:
854 typedef Type msgpack_type;
858
859 template <typename Packer>
860 void msgpack_pack(Packer& o) const
861 {
862 msgpack::operator<<(o, static_cast<const msgpack_type&>(*this));
863 }
864
865 void msgpack_unpack(object const& o)
866 {
867 msgpack::operator>>(o, static_cast<msgpack_type&>(*this));
868 }
869};
870
871// deconvert operator
872
873template <typename Stream>
874template <typename T>
876{
877 msgpack::operator<<(*this, v);
878 return *this;
879}
880
882 object_equal_visitor(msgpack::object const& obj, bool& result)
883 :m_ptr(&obj), m_result(result) {}
884 bool visit_nil() {
885 if (m_ptr->type != msgpack::type::NIL) {
886 m_result = false;
887 return false;
888 }
889 return true;
890 }
891 bool visit_boolean(bool v) {
892 if (m_ptr->type != msgpack::type::BOOLEAN || m_ptr->via.boolean != v) {
893 m_result = false;
894 return false;
895 }
896 return true;
897 }
898 bool visit_positive_integer(uint64_t v) {
899 if (m_ptr->type != msgpack::type::POSITIVE_INTEGER || m_ptr->via.u64 != v) {
900 m_result = false;
901 return false;
902 }
903 return true;
904 }
905 bool visit_negative_integer(int64_t v) {
906 if (m_ptr->type != msgpack::type::NEGATIVE_INTEGER || m_ptr->via.i64 != v) {
907 m_result = false;
908 return false;
909 }
910 return true;
911 }
912 bool visit_float32(float v) {
913 if (m_ptr->type != msgpack::type::FLOAT32 || m_ptr->via.f64 != v) {
914 m_result = false;
915 return false;
916 }
917 return true;
918 }
919 bool visit_float64(double v) {
920 if (m_ptr->type != msgpack::type::FLOAT64 || m_ptr->via.f64 != v) {
921 m_result = false;
922 return false;
923 }
924 return true;
925 }
926 bool visit_str(const char* v, uint32_t size) {
927 if (m_ptr->type != msgpack::type::STR ||
928 m_ptr->via.str.size != size ||
929 std::memcmp(m_ptr->via.str.ptr, v, size) != 0) {
930 m_result = false;
931 return false;
932 }
933 return true;
934 }
935 bool visit_bin(const char* v, uint32_t size) {
936 if (m_ptr->type != msgpack::type::BIN ||
937 m_ptr->via.bin.size != size ||
938 std::memcmp(m_ptr->via.bin.ptr, v, size) != 0) {
939 m_result = false;
940 return false;
941 }
942 return true;
943 }
944 bool visit_ext(const char* v, uint32_t size) {
945 if (m_ptr->type != msgpack::type::EXT ||
946 m_ptr->via.ext.size != size - 1 ||
947 std::memcmp(m_ptr->via.ext.ptr, v, size) != 0) {
948 m_result = false;
949 return false;
950 }
951 return true;
952 }
953 bool start_array(uint32_t num_elements) {
954 if (m_ptr->type != msgpack::type::ARRAY ||
955 m_ptr->via.array.size != num_elements) {
956 m_result = false;
957 return false;
958 }
959 m_objs.push_back(elem(m_ptr->via.array.ptr));
960 return true;
961 }
963 m_ptr = m_objs.back().get_item();
964 return true;
965 }
967 ++m_objs.back().as.obj;
968 return true;
969 }
970 bool end_array() {
971 m_objs.pop_back();
972 return true;
973 }
974 bool start_map(uint32_t num_kv_pairs) {
975 if (m_ptr->type != msgpack::type::MAP ||
976 m_ptr->via.array.size != num_kv_pairs) {
977 m_result = false;
978 return false;
979 }
980 m_objs.push_back(elem(m_ptr->via.map.ptr));
981 return true;
982 }
984 m_ptr = m_objs.back().get_key();
985 return true;
986 }
987 bool end_map_key() {
988 return true;
989 }
991 m_ptr = m_objs.back().get_val();
992 return true;
993 }
995 ++m_objs.back().as.kv;
996 return true;
997 }
998 bool end_map() {
999 m_objs.pop_back();
1000 return true;
1001 }
1002private:
1003 struct elem {
1004 elem(msgpack::object const* obj)
1005 :is_obj(true) {
1006 as.obj = obj;
1007 }
1008 elem(msgpack::object_kv const* kv)
1009 :is_obj(false) {
1010 as.kv = kv;
1011 }
1012 msgpack::object const* get_item() {
1013 return as.obj;
1014 }
1015 msgpack::object const* get_key() {
1016 return &as.kv->key;
1017 }
1018 msgpack::object const* get_val() {
1019 return &as.kv->val;
1020 }
1021 union {
1022 msgpack::object const* obj;
1023 msgpack::object_kv const* kv;
1024 } as;
1025 bool is_obj;
1026 };
1027 std::vector<elem> m_objs;
1028 msgpack::object const* m_ptr;
1029 bool& m_result;
1030};
1031
1032inline bool operator==(const msgpack::object& x, const msgpack::object& y)
1033{
1034 if(x.type != y.type) { return false; }
1035 bool b = true;
1036 object_equal_visitor vis(y, b);
1038 return b;
1039}
1040
1041template <typename T>
1042inline bool operator==(const msgpack::object& x, const T& y)
1043try {
1044 return x == msgpack::object(y);
1045} catch (msgpack::type_error&) {
1046 return false;
1047}
1048
1049inline bool operator!=(const msgpack::object& x, const msgpack::object& y)
1050{ return !(x == y); }
1051
1052template <typename T>
1053inline bool operator==(const T& y, const msgpack::object& x)
1054{ return x == y; }
1055
1056template <typename T>
1057inline bool operator!=(const msgpack::object& x, const T& y)
1058{ return !(x == y); }
1059
1060template <typename T>
1061inline bool operator!=(const T& y, const msgpack::object& x)
1062{ return x != y; }
1063
1064
1066{
1067 return object::implicit_type(*this);
1068}
1069
1070template <typename T>
1071inline
1072typename msgpack::enable_if<
1073 !msgpack::is_array<T>::value && !msgpack::is_pointer<T>::value,
1074 T&
1075>::type
1077{
1078 msgpack::operator>>(*this, v);
1079 return v;
1080}
1081
1082template <typename T, std::size_t N>
1083inline T(&object::convert(T(&v)[N]) const)[N]
1084{
1085 msgpack::operator>>(*this, v);
1086 return v;
1087}
1088
1089#if !defined(MSGPACK_DISABLE_LEGACY_CONVERT)
1090template <typename T>
1091inline
1092typename msgpack::enable_if<
1093 msgpack::is_pointer<T>::value,
1094 T
1095>::type
1097{
1098 convert(*v);
1099 return v;
1100}
1101#endif // !defined(MSGPACK_DISABLE_LEGACY_CONVERT)
1102
1103template <typename T>
1104inline bool object::convert_if_not_nil(T& v) const
1105{
1106 if (is_nil()) {
1107 return false;
1108 }
1109 convert(v);
1110 return true;
1111}
1112
1113#if defined(MSGPACK_USE_CPP03)
1114
1115template <typename T>
1116inline T object::as() const
1117{
1118 T v;
1119 convert(v);
1120 return v;
1121}
1122
1123#else // defined(MSGPACK_USE_CPP03)
1124
1125template <typename T>
1126inline typename std::enable_if<msgpack::has_as<T>::value, T>::type object::as() const {
1127 return msgpack::adaptor::as<T>()(*this);
1128}
1129
1130template <typename T>
1131inline typename std::enable_if<!msgpack::has_as<T>::value, T>::type object::as() const {
1132 T v;
1133 convert(v);
1134 return v;
1135}
1136
1137#endif // defined(MSGPACK_USE_CPP03)
1138
1140{
1141 type = msgpack::type::NIL;
1142}
1143
1144template <typename T>
1145inline object::object(const T& v)
1146{
1147 *this << v;
1148}
1149
1150template <typename T>
1151inline object& object::operator=(const T& v)
1152{
1153 *this = object(v);
1154 return *this;
1155}
1156
1157template <typename T>
1158inline object::object(const T& v, msgpack::zone& z)
1159{
1160 with_zone oz(z);
1161 msgpack::operator<<(oz, v);
1162 type = oz.type;
1163 via = oz.via;
1164}
1165
1166template <typename T>
1167inline object::object(const T& v, msgpack::zone* z)
1168{
1169 with_zone oz(*z);
1170 msgpack::operator<<(oz, v);
1171 type = oz.type;
1172 via = oz.via;
1173}
1174
1175
1176// obsolete
1177template <typename T>
1178inline void convert(T& v, msgpack::object const& o)
1179{
1180 o.convert(v);
1181}
1182
1183// obsolete
1184template <typename Stream, typename T>
1185inline void pack(msgpack::packer<Stream>& o, const T& v)
1186{
1187 o.pack(v);
1188}
1189
1190// obsolete
1191template <typename Stream, typename T>
1193{
1194 pack(o, v);
1195}
1196
1197template <typename Stream>
1198inline msgpack::packer<Stream>& operator<< (msgpack::packer<Stream>& o, const msgpack::object& v)
1199{
1200 object_pack_visitor<Stream> vis(o);
1202 return o;
1203}
1204
1205template <typename Stream>
1207{
1208 return o << static_cast<msgpack::object>(v);
1209}
1210
1211inline std::ostream& operator<< (std::ostream& s, const msgpack::object& v)
1212{
1215 return s;
1216}
1217
1219} // MSGPACK_API_VERSION_NAMESPACE(v1)
1221
1222} // namespace msgpack
1223
1224#endif // MSGPACK_V1_OBJECT_HPP
Definition object.hpp:852
define()
Definition object.hpp:856
define(const msgpack_type &v)
Definition object.hpp:857
void msgpack_pack(Packer &o) const
Definition object.hpp:860
void msgpack_unpack(object const &o)
Definition object.hpp:865
define< Type > define_type
Definition object.hpp:855
Type msgpack_type
Definition object.hpp:854
The class holds object and zone.
Definition object.hpp:44
object_handle(msgpack::object const &obj, msgpack::unique_ptr< msgpack::zone > &&z)
Constructor that creates an object_handle holding object obj and zone z.
Definition object.hpp:54
const msgpack::object & operator*() const
Definition object.hpp:77
const msgpack::object * operator->() const
Definition object.hpp:83
const msgpack::unique_ptr< msgpack::zone > & zone() const
Get unique_ptr const reference of zone.
Definition object.hpp:97
void set(msgpack::object const &obj)
Definition object.hpp:64
const msgpack::object & get() const
Get object reference.
Definition object.hpp:71
object_handle()
Constructor that creates nil object and null zone.
Definition object.hpp:47
msgpack::unique_ptr< msgpack::zone > & zone()
Get unique_ptr reference of zone.
Definition object.hpp:90
Definition object.hpp:151
void parse(Visitor &v)
Definition object.hpp:238
object_parser(msgpack::object const &obj)
Definition object.hpp:236
The class template that supports continuous packing.
Definition pack.hpp:33
packer< Stream > & pack(const T &v)
Packing function template.
Definition object_fwd.hpp:231
Definition cpp03_zone.hpp:30
#define MSGPACK_USE_CPP03
Definition cpp_version.hpp:9
std::size_t size(T const &t)
Definition size_equal_only.hpp:24
@ EXT
Definition object_fwd_decl.hpp:42
@ FLOAT64
Definition object_fwd_decl.hpp:33
@ MAP
Definition object_fwd_decl.hpp:41
@ STR
Definition object_fwd_decl.hpp:38
@ ARRAY
Definition object_fwd_decl.hpp:40
@ BIN
Definition object_fwd_decl.hpp:39
@ POSITIVE_INTEGER
Definition object_fwd_decl.hpp:30
@ NEGATIVE_INTEGER
Definition object_fwd_decl.hpp:31
@ FLOAT32
Definition object_fwd_decl.hpp:32
Definition adaptor_base.hpp:15
void pack(msgpack::packer< Stream > &o, const T &v)
Definition object.hpp:1185
std::size_t aligned_size(std::size_t size, std::size_t align)
Definition cpp03_zone.hpp:353
void pack_copy(msgpack::packer< Stream > &o, T v)
Definition object.hpp:1192
object_handle clone(msgpack::object const &obj)
clone object
Definition object.hpp:622
std::size_t aligned_zone_size(msgpack::object const &obj)
Definition object.hpp:607
msgpack::enable_if<!is_array< T >::value, msgpack::packer< Stream > & >::type operator<<(msgpack::packer< Stream > &o, T const &v)
Definition adaptor_base.hpp:72
msgpack::enable_if<!is_array< T >::value, msgpack::objectconst & >::type operator>>(msgpack::object const &o, T &v)
Definition adaptor_base.hpp:57
void convert(T &v, msgpack::object const &o)
Definition object.hpp:1178
Definition object_fwd_decl.hpp:61
msgpack::object const & operator()(msgpack::object const &o, msgpack::object &v) const
Definition object.hpp:671
Definition adaptor_base.hpp:27
msgpack::object const & operator()(msgpack::object const &o, T &v) const
Definition object.hpp:646
void operator()(msgpack::object::with_zone &o, msgpack::object const &v) const
Definition object.hpp:689
void operator()(msgpack::object::with_zone &o, msgpack::object::with_zone const &v) const
Definition object.hpp:839
Definition adaptor_base.hpp:43
void operator()(msgpack::object::with_zone &o, T const &v) const
Definition object.hpp:662
Definition adaptor_base.hpp:38
msgpack::packer< Stream > & operator()(msgpack::packer< Stream > &o, msgpack::object const &v) const
Definition object.hpp:680
Definition adaptor_base.hpp:32
msgpack::packer< Stream > & operator()(msgpack::packer< Stream > &o, T const &v) const
Definition object.hpp:655
Definition object.hpp:534
bool visit_nil()
Definition object.hpp:537
bool start_map(uint32_t num_kv_pairs)
Definition object.hpp:582
bool end_map()
Definition object.hpp:600
bool visit_ext(const char *, uint32_t size)
Definition object.hpp:563
bool start_map_key()
Definition object.hpp:588
bool start_map_value()
Definition object.hpp:594
bool visit_bin(const char *, uint32_t size)
Definition object.hpp:559
bool visit_float32(float)
Definition object.hpp:549
bool end_array()
Definition object.hpp:579
aligned_zone_size_visitor(std::size_t &s)
Definition object.hpp:535
bool start_array(uint32_t num_elements)
Definition object.hpp:567
bool visit_boolean(bool)
Definition object.hpp:540
bool start_array_item()
Definition object.hpp:573
bool visit_negative_integer(int64_t)
Definition object.hpp:546
bool visit_str(const char *, uint32_t size)
Definition object.hpp:555
bool end_array_item()
Definition object.hpp:576
bool end_map_key()
Definition object.hpp:591
bool end_map_value()
Definition object.hpp:597
bool visit_float64(double)
Definition object.hpp:552
bool visit_positive_integer(uint64_t)
Definition object.hpp:543
Definition object_fwd.hpp:233
Definition object.hpp:35
with_zone(msgpack::zone &z)
Definition object.hpp:36
msgpack::zone & zone
Definition object.hpp:37
uint32_t size
Definition object_fwd.hpp:23
msgpack::object * ptr
Definition object_fwd.hpp:24
uint32_t size
Definition object_fwd.hpp:38
const char * ptr
Definition object_fwd.hpp:39
Definition object.hpp:881
bool start_map_key()
Definition object.hpp:983
bool visit_ext(const char *v, uint32_t size)
Definition object.hpp:944
bool end_array_item()
Definition object.hpp:966
bool visit_str(const char *v, uint32_t size)
Definition object.hpp:926
bool visit_boolean(bool v)
Definition object.hpp:891
bool visit_bin(const char *v, uint32_t size)
Definition object.hpp:935
bool start_map_value()
Definition object.hpp:990
bool start_array_item()
Definition object.hpp:962
bool visit_nil()
Definition object.hpp:884
bool visit_negative_integer(int64_t v)
Definition object.hpp:905
bool visit_positive_integer(uint64_t v)
Definition object.hpp:898
bool end_map_value()
Definition object.hpp:994
bool visit_float64(double v)
Definition object.hpp:919
bool start_map(uint32_t num_kv_pairs)
Definition object.hpp:974
bool start_array(uint32_t num_elements)
Definition object.hpp:953
bool visit_float32(float v)
Definition object.hpp:912
object_equal_visitor(msgpack::object const &obj, bool &result)
Definition object.hpp:882
bool end_map_key()
Definition object.hpp:987
bool end_array()
Definition object.hpp:970
bool end_map()
Definition object.hpp:998
const char * ptr
Definition object_fwd.hpp:46
uint32_t size
Definition object_fwd.hpp:45
Definition object.hpp:30
msgpack::object val
Definition object.hpp:32
msgpack::object key
Definition object.hpp:31
uint32_t size
Definition object_fwd.hpp:28
msgpack::object_kv * ptr
Definition object_fwd.hpp:29
Definition object.hpp:316
bool start_map_value()
Definition object.hpp:382
object_pack_visitor(msgpack::packer< Stream > &pk)
Definition object.hpp:317
bool visit_float32(float v)
Definition object.hpp:336
bool start_array_item()
Definition object.hpp:363
bool visit_float64(double v)
Definition object.hpp:340
bool end_map_key()
Definition object.hpp:379
bool end_map()
Definition object.hpp:388
bool end_map_value()
Definition object.hpp:385
bool visit_boolean(bool v)
Definition object.hpp:323
bool end_array()
Definition object.hpp:369
bool visit_negative_integer(int64_t v)
Definition object.hpp:332
bool start_map(uint32_t num_kv_pairs)
Definition object.hpp:372
bool start_map_key()
Definition object.hpp:376
bool end_array_item()
Definition object.hpp:366
bool visit_bin(const char *v, uint32_t size)
Definition object.hpp:349
bool start_array(uint32_t num_elements)
Definition object.hpp:359
bool visit_positive_integer(uint64_t v)
Definition object.hpp:328
bool visit_ext(const char *v, uint32_t size)
Definition object.hpp:354
bool visit_nil()
Definition object.hpp:319
bool visit_str(const char *v, uint32_t size)
Definition object.hpp:344
const char * ptr
Definition object_fwd.hpp:34
uint32_t size
Definition object_fwd.hpp:33
Definition object.hpp:396
bool end_map_value()
Definition object.hpp:517
bool start_array(uint32_t num_elements)
Definition object.hpp:482
bool start_map_value()
Definition object.hpp:514
bool visit_bin(const char *, uint32_t size)
Definition object.hpp:469
bool visit_str(const char *v, uint32_t size)
Definition object.hpp:424
bool end_array()
Definition object.hpp:497
bool start_map(uint32_t num_kv_pairs)
Definition object.hpp:502
bool visit_boolean(bool v)
Definition object.hpp:403
bool visit_negative_integer(int64_t v)
Definition object.hpp:412
bool visit_float32(float v)
Definition object.hpp:416
object_stringize_visitor(std::ostream &os)
Definition object.hpp:397
bool end_array_item()
Definition object.hpp:490
bool start_map_key()
Definition object.hpp:507
bool end_map()
Definition object.hpp:524
bool visit_float64(double v)
Definition object.hpp:420
bool visit_ext(const char *v, uint32_t size)
Definition object.hpp:473
bool end_map_key()
Definition object.hpp:510
bool visit_positive_integer(uint64_t v)
Definition object.hpp:408
bool start_array_item()
Definition object.hpp:487
bool visit_nil()
Definition object.hpp:399
Object class that corresponding to MessagePack format object.
Definition object_fwd.hpp:75
msgpack::enable_if<!msgpack::is_array< T >::value &&!msgpack::is_pointer< T >::value, T & >::type convert(T &v) const
Convert the object.
Definition object.hpp:1076
object()
Default constructor. The object is set to nil.
Definition object.hpp:1139
std::enable_if< msgpack::has_as< T >::value, T >::type as() const
Get value as T.
Definition object.hpp:1126
implicit_type convert() const
Definition object.hpp:1065
union_type via
Definition object_fwd.hpp:93
bool convert_if_not_nil(T &v) const
Convert the object if not nil.
Definition object.hpp:1104
msgpack::type::object_type type
Definition object_fwd.hpp:92
bool is_nil() const
Cheking nil.
Definition object_fwd.hpp:99
object & operator=(const T &v)
Definition object.hpp:1151
bool boolean
Definition object_fwd.hpp:77
msgpack::object_array array
Definition object_fwd.hpp:85
msgpack::object_ext ext
Definition object_fwd.hpp:89
msgpack::object_str str
Definition object_fwd.hpp:87
uint64_t u64
Definition object_fwd.hpp:78
int64_t i64
Definition object_fwd.hpp:79
msgpack::object_bin bin
Definition object_fwd.hpp:88
double f64
Definition object_fwd.hpp:84
msgpack::object_map map
Definition object_fwd.hpp:86
#define MSGPACK_NULLPTR
Definition cpp_config_decl.hpp:85
#define MSGPACK_ZONE_ALIGNOF(type)
Definition cpp03_zone_decl.hpp:30
#define MSGPACK_API_VERSION_NAMESPACE(ns)
Definition versioning.hpp:66