ext.hpp
Go to the documentation of this file.
//
// MessagePack for C++ static resolution routine
//
// Copyright (C) 2015-2016 KONDO Takatoshi
//
// Distributed under the Boost Software License, Version 1.0.
// (See accompanying file LICENSE_1_0.txt or copy at
// http://www.boost.org/LICENSE_1_0.txt)
//
#ifndef MSGPACK_V1_TYPE_EXT_HPP
#define MSGPACK_V1_TYPE_EXT_HPP
#include "msgpack/v1/adaptor/ext_decl.hpp"
#include "msgpack/adaptor/check_container_size.hpp"
#include <cstring>
#include <string>
#include <cassert>
namespace msgpack {
MSGPACK_API_VERSION_NAMESPACE(v1) {
namespace type {
class ext {
public:
ext() : m_data(1, 0) {}
ext(int8_t t, const char* p, uint32_t s) {
msgpack::detail::check_container_size_for_ext<sizeof(std::size_t)>(s);
m_data.reserve(static_cast<std::size_t>(s) + 1);
m_data.push_back(static_cast<char>(t));
m_data.insert(m_data.end(), p, p + s);
}
ext(int8_t t, uint32_t s) {
msgpack::detail::check_container_size_for_ext<sizeof(std::size_t)>(s);
m_data.resize(static_cast<std::size_t>(s) + 1);
m_data[0] = static_cast<char>(t);
}
ext(ext_ref const&);
int8_t type() const {
return static_cast<int8_t>(m_data[0]);
}
const char* data() const {
return &m_data[1];
}
char* data() {
return &m_data[1];
}
uint32_t size() const {
return static_cast<uint32_t>(m_data.size()) - 1;
}
bool operator== (const ext& x) const {
return m_data == x.m_data;
}
bool operator!= (const ext& x) const {
return !(*this == x);
}
bool operator< (const ext& x) const {
return m_data < x.m_data;
}
bool operator> (const ext& x) const {
return m_data > x.m_data;
}
private:
std::vector<char> m_data;
friend class ext_ref;
};
} // namespace type
namespace adaptor {
template <>
struct convert<msgpack::type::ext> {
msgpack::object const& operator()(msgpack::object const& o, msgpack::type::ext& v) const {
if(o.type != msgpack::type::EXT) {
throw msgpack::type_error();
}
v = msgpack::type::ext(o.via.ext.type(), o.via.ext.data(), o.via.ext.size);
return o;
}
};
template <>
struct pack<msgpack::type::ext> {
template <typename Stream>
msgpack::packer<Stream>& operator()(msgpack::packer<Stream>& o, const msgpack::type::ext& v) const {
// size limit has already been checked at ext's constructor
uint32_t size = v.size();
o.pack_ext(size, v.type());
o.pack_ext_body(v.data(), size);
return o;
}
};
template <>
struct object_with_zone<msgpack::type::ext> {
void operator()(msgpack::object::with_zone& o, const msgpack::type::ext& v) const {
// size limit has already been checked at ext's constructor
uint32_t size = v.size();
o.type = msgpack::type::EXT;
char* ptr = static_cast<char*>(o.zone.allocate_align(size + 1, MSGPACK_ZONE_ALIGNOF(char)));
o.via.ext.ptr = ptr;
o.via.ext.size = size;
ptr[0] = static_cast<char>(v.type());
std::memcpy(ptr + 1, v.data(), size);
}
};
} // namespace adaptor
namespace type {
class ext_ref {
public:
// ext_ref should be default constructible to support 'convert'.
// A default constructed ext_ref object::m_ptr doesn't have the buffer to point to.
// In order to avoid nullptr checking branches, m_ptr points to m_size.
// So type() returns unspecified but valid value. It might be a zero because m_size
// is initialized as zero, but shouldn't assume that.
ext_ref() : m_ptr(static_cast<char*>(static_cast<void*>(&m_size))), m_size(0) {}
ext_ref(const char* p, uint32_t s) :
m_ptr(s == 0 ? static_cast<char*>(static_cast<void*>(&m_size)) : p),
m_size(s == 0 ? 0 : s - 1) {
msgpack::detail::check_container_size_for_ext<sizeof(std::size_t)>(s);
}
// size limit has already been checked at ext's constructor
ext_ref(ext const& x) : m_ptr(&x.m_data[0]), m_size(x.size()) {}
const char* data() const {
return m_ptr + 1;
}
uint32_t size() const {
return m_size;
}
int8_t type() const {
return static_cast<int8_t>(m_ptr[0]);
}
std::string str() const {
return std::string(m_ptr + 1, m_size);
}
bool operator== (const ext_ref& x) const {
return m_size == x.m_size && std::memcmp(m_ptr, x.m_ptr, m_size) == 0;
}
bool operator!= (const ext_ref& x) const {
return !(*this == x);
}
bool operator< (const ext_ref& x) const {
if (m_size < x.m_size) return true;
if (m_size > x.m_size) return false;
return std::memcmp(m_ptr, x.m_ptr, m_size) < 0;
}
bool operator> (const ext_ref& x) const {
if (m_size > x.m_size) return true;
if (m_size < x.m_size) return false;
return std::memcmp(m_ptr, x.m_ptr, m_size) > 0;
}
private:
const char* m_ptr;
uint32_t m_size;
friend struct adaptor::object<msgpack::type::ext_ref>;
};
inline ext::ext(ext_ref const& x) {
// size limit has already been checked at ext_ref's constructor
m_data.reserve(x.size() + 1);
m_data.push_back(x.type());
m_data.insert(m_data.end(), x.data(), x.data() + x.size());
}
} // namespace type
namespace adaptor {
template <>
struct convert<msgpack::type::ext_ref> {
msgpack::object const& operator()(msgpack::object const& o, msgpack::type::ext_ref& v) const {
if(o.type != msgpack::type::EXT) { throw msgpack::type_error(); }
v = msgpack::type::ext_ref(o.via.ext.ptr, o.via.ext.size + 1);
return o;
}
};
template <>
struct pack<msgpack::type::ext_ref> {
template <typename Stream>
msgpack::packer<Stream>& operator()(msgpack::packer<Stream>& o, const msgpack::type::ext_ref& v) const {
// size limit has already been checked at ext_ref's constructor
uint32_t size = v.size();
o.pack_ext(size, v.type());
o.pack_ext_body(v.data(), size);
return o;
}
};
template <>
struct object<msgpack::type::ext_ref> {
void operator()(msgpack::object& o, const msgpack::type::ext_ref& v) const {
// size limit has already been checked at ext_ref's constructor
uint32_t size = v.size();
o.type = msgpack::type::EXT;
o.via.ext.ptr = v.m_ptr;
o.via.ext.size = size;
}
};
template <>
struct object_with_zone<msgpack::type::ext_ref> {
void operator()(msgpack::object::with_zone& o, const msgpack::type::ext_ref& v) const {
static_cast<msgpack::object&>(o) << v;
}
};
} // namespace adaptor
} // MSGPACK_API_VERSION_NAMESPACE(v1)
} // namespace msgpack
#endif // MSGPACK_V1_TYPE_EXT_HPP
msgpack::type::ext_ref::size
uint32_t size() const
Definition: ext.hpp:140
msgpack::type::ext::size
uint32_t size() const
Definition: ext.hpp:51
msgpack::type::ext::operator>
bool operator>(const ext &x) const
Definition: ext.hpp:66
msgpack::object_ext::data
const char * data() const
Definition: object_fwd.hpp:44
ext_decl.hpp
msgpack::packer::pack_ext
packer< Stream > & pack_ext(size_t l, int8_t type)
Packing ext header, type, and length.
Definition: pack.hpp:1281
msgpack::type::ext::data
char * data()
Definition: ext.hpp:48
msgpack::zone::allocate_align
void * allocate_align(size_t size, size_t align=MSGPACK_ZONE_ALIGN)
Definition: cpp03_zone.hpp:246
msgpack::adaptor::convert< msgpack::type::ext >::operator()
msgpack::object const & operator()(msgpack::object const &o, msgpack::type::ext &v) const
Definition: ext.hpp:80
msgpack::type::ext_ref::type
int8_t type() const
Definition: ext.hpp:144
msgpack::object::via
union_type via
Definition: object_fwd.hpp:93
msgpack::object_ext::ptr
const char * ptr
Definition: object_fwd.hpp:46
msgpack::type::ext::ext
ext(int8_t t, const char *p, uint32_t s)
Definition: ext.hpp:30
msgpack::type::ext
Definition: ext.hpp:27
msgpack
Definition: adaptor_base.hpp:15
msgpack::type::ext_ref::ext_ref
ext_ref(ext const &x)
Definition: ext.hpp:134
msgpack::adaptor::pack< msgpack::type::ext_ref >::operator()
msgpack::packer< Stream > & operator()(msgpack::packer< Stream > &o, const msgpack::type::ext_ref &v) const
Definition: ext.hpp:201
v2::object::with_zone
Definition: object.hpp:35
msgpack::type::ext_ref::str
std::string str() const
Definition: ext.hpp:148
msgpack::adaptor::object_with_zone
Definition: adaptor_base.hpp:43
msgpack::object_ext::size
uint32_t size
Definition: object_fwd.hpp:45
msgpack::adaptor::object_with_zone< msgpack::type::ext_ref >::operator()
void operator()(msgpack::object::with_zone &o, const msgpack::type::ext_ref &v) const
Definition: ext.hpp:223
msgpack::type_error
Definition: object_fwd.hpp:236
msgpack::type::ext::ext
ext(int8_t t, uint32_t s)
Definition: ext.hpp:36
msgpack::adaptor::pack
Definition: adaptor_base.hpp:32
msgpack::type::EXT
Definition: object_fwd_decl.hpp:43
msgpack::type::ext::operator<
bool operator<(const ext &x) const
Definition: ext.hpp:62
msgpack::type::ext_ref::ext_ref
ext_ref(const char *p, uint32_t s)
Definition: ext.hpp:127
msgpack::adaptor::convert< msgpack::type::ext_ref >::operator()
msgpack::object const & operator()(msgpack::object const &o, msgpack::type::ext_ref &v) const
Definition: ext.hpp:191
msgpack::object
Object class that corresponding to MessagePack format object.
Definition: object_fwd.hpp:75
msgpack::type::ext_ref::ext_ref
ext_ref()
Definition: ext.hpp:126
msgpack::type::ext_ref::data
const char * data() const
Definition: ext.hpp:136
msgpack::packer::pack_ext_body
packer< Stream > & pack_ext_body(const char *b, uint32_t l)
Packing ext body.
Definition: pack.hpp:1340
msgpack::object::type
msgpack::type::object_type type
Definition: object_fwd.hpp:92
MSGPACK_API_VERSION_NAMESPACE
#define MSGPACK_API_VERSION_NAMESPACE(ns)
Definition: versioning.hpp:58
msgpack::type::ext::ext
ext()
Definition: ext.hpp:29
msgpack::type::ext_ref
Definition: ext.hpp:119
msgpack::adaptor::object< msgpack::type::ext_ref >::operator()
void operator()(msgpack::object &o, const msgpack::type::ext_ref &v) const
Definition: ext.hpp:212
MSGPACK_ZONE_ALIGNOF
#define MSGPACK_ZONE_ALIGNOF(type)
Definition: cpp03_zone_decl.hpp:30
check_container_size.hpp
msgpack::adaptor::pack< msgpack::type::ext >::operator()
msgpack::packer< Stream > & operator()(msgpack::packer< Stream > &o, const msgpack::type::ext &v) const
Definition: ext.hpp:92
msgpack::object_ext::type
int8_t type() const
Definition: object_fwd.hpp:43
msgpack::adaptor::object
Definition: adaptor_base.hpp:38
msgpack::packer
The class template that supports continuous packing.
Definition: adaptor_base_decl.hpp:24
msgpack::type::ext::type
int8_t type() const
Definition: ext.hpp:42
msgpack::object::union_type::ext
msgpack::object_ext ext
Definition: object_fwd.hpp:89
v2::object::with_zone::zone
msgpack::zone & zone
Definition: object.hpp:37
msgpack::adaptor::convert
Definition: adaptor_base.hpp:27
msgpack::type::ext::operator!=
bool operator!=(const ext &x) const
Definition: ext.hpp:58
msgpack::adaptor::object_with_zone< msgpack::type::ext >::operator()
void operator()(msgpack::object::with_zone &o, const msgpack::type::ext &v) const
Definition: ext.hpp:103
msgpack::type::ext::data
const char * data() const
Definition: ext.hpp:45
msgpack::type::ext::operator==
bool operator==(const ext &x) const
Definition: ext.hpp:54