Use new buffer traits, remove old unused traits

This commit is contained in:
Vinnie Falco
2018-12-15 12:04:39 -08:00
parent 8f1faababd
commit fa14af2696
15 changed files with 148 additions and 199 deletions

View File

@@ -9,6 +9,7 @@ Version 200
* Refactor buffers_prefix * Refactor buffers_prefix
* Add const and mutable buffer sequence traits * Add const and mutable buffer sequence traits
* Add buffers_iterator_type trait * Add buffers_iterator_type trait
* Use new buffer traits, remove old unused traits
API Changes: API Changes:

View File

@@ -22,7 +22,7 @@ namespace beast {
/** Determine if a list of types satisfy the <em>ConstBufferSequence</em> requirements. /** Determine if a list of types satisfy the <em>ConstBufferSequence</em> requirements.
This metafunction is used to determine if all of the specified types This metafunction is used to determine if all of the specified types
meet the requirements for const buffer sequences. This type alias meet the requirements for constant buffer sequences. This type alias
will be `std::true_type` if each specified type meets the requirements, will be `std::true_type` if each specified type meets the requirements,
otherwise, this type alias will be `std::false_type`. otherwise, this type alias will be `std::false_type`.
@@ -36,7 +36,8 @@ struct is_const_buffer_sequence : __see_below__ {};
#else #else
template<class... TN> template<class... TN>
using is_const_buffer_sequence = mp11::mp_all< using is_const_buffer_sequence = mp11::mp_all<
net::is_const_buffer_sequence<TN>...>; net::is_const_buffer_sequence<
typename std::decay<TN>::type>...>;
#endif #endif
/** Determine if a list of types satisfy the <em>MutableBufferSequence</em> requirements. /** Determine if a list of types satisfy the <em>MutableBufferSequence</em> requirements.
@@ -56,7 +57,8 @@ struct is_mutable_buffer_sequence : __see_below__ {};
#else #else
template<class... TN> template<class... TN>
using is_mutable_buffer_sequence = mp11::mp_all< using is_mutable_buffer_sequence = mp11::mp_all<
net::is_mutable_buffer_sequence<TN>...>; net::is_mutable_buffer_sequence<
typename std::decay<TN>::type>...>;
#endif #endif
/** Type alias for the underlying buffer type of a list of buffer sequence types. /** Type alias for the underlying buffer type of a list of buffer sequence types.
@@ -97,16 +99,14 @@ template<class... TN>
struct buffers_type : __see_below__ {}; struct buffers_type : __see_below__ {};
//using buffers_type = __see_below__; //using buffers_type = __see_below__;
#else #else
using buffers_type = typename using buffers_type = typename std::conditional<
std::conditional< is_mutable_buffer_sequence<TN...>::value,
is_mutable_buffer_sequence<TN...>::value, net::mutable_buffer, net::const_buffer>::type;
net::mutable_buffer,
net::const_buffer>::type;
#endif #endif
namespace detail { #if BOOST_WORKAROUND(BOOST_MSVC, < 1910)
// VFALCO This is a workaround for MSVC.v140 namespace detail {
template<class T> template<class T>
struct buffers_iterator_type_helper struct buffers_iterator_type_helper
{ {
@@ -131,6 +131,8 @@ struct buffers_iterator_type_helper<
} // detail } // detail
#endif
/** Type alias for the iterator type of a buffer sequence type. /** Type alias for the iterator type of a buffer sequence type.
This metafunction is used to determine the type of iterator This metafunction is used to determine the type of iterator
@@ -144,15 +146,14 @@ template <class T>
#if BOOST_BEAST_DOXYGEN #if BOOST_BEAST_DOXYGEN
struct buffers_iterator_type : __see_below__ {}; struct buffers_iterator_type : __see_below__ {};
//using buffers_iterator_type = __see_below__; //using buffers_iterator_type = __see_below__;
#else #elif BOOST_WORKAROUND(BOOST_MSVC, < 1910)
# if BOOST_WORKAROUND(BOOST_MSVC, < 1910)
using buffers_iterator_type = typename using buffers_iterator_type = typename
detail::buffers_iterator_type_helper<T>::type; detail::buffers_iterator_type_helper<
# else typename std::decay<T>::type>::type;
#else
using buffers_iterator_type = using buffers_iterator_type =
decltype(net::buffer_sequence_begin( decltype(net::buffer_sequence_begin(
std::declval<T const&>())); std::declval<T const&>()));
# endif
#endif #endif
} // beast } // beast

View File

@@ -11,8 +11,7 @@
#define BOOST_BEAST_BUFFERS_ADAPTOR_HPP #define BOOST_BEAST_BUFFERS_ADAPTOR_HPP
#include <boost/beast/core/detail/config.hpp> #include <boost/beast/core/detail/config.hpp>
#include <boost/beast/core/type_traits.hpp> #include <boost/beast/core/buffer_traits.hpp>
#include <boost/asio/buffer.hpp>
#include <boost/optional.hpp> #include <boost/optional.hpp>
#include <type_traits> #include <type_traits>
@@ -40,9 +39,8 @@ class buffers_adaptor
MutableBufferSequence>::value, MutableBufferSequence>::value,
"MutableBufferSequence requirements not met"); "MutableBufferSequence requirements not met");
using iter_type = typename using iter_type =
detail::buffer_sequence_iterator< buffers_iterator_type<MutableBufferSequence>;
MutableBufferSequence>::type;
template<bool> template<bool>
class readable_bytes; class readable_bytes;

View File

@@ -11,6 +11,7 @@
#define BOOST_BEAST_BUFFERS_CAT_HPP #define BOOST_BEAST_BUFFERS_CAT_HPP
#include <boost/beast/core/detail/config.hpp> #include <boost/beast/core/detail/config.hpp>
#include <boost/beast/core/buffer_traits.hpp>
#include <boost/beast/core/detail/tuple.hpp> #include <boost/beast/core/detail/tuple.hpp>
#include <boost/beast/core/detail/type_traits.hpp> #include <boost/beast/core/detail/type_traits.hpp>
@@ -34,10 +35,9 @@ public:
Otherwise, `value_type` will be `net::const_buffer`. Otherwise, `value_type` will be `net::const_buffer`.
*/ */
#if BOOST_BEAST_DOXYGEN #if BOOST_BEAST_DOXYGEN
using value_type = __implementation_defined__; using value_type = __see_below__;
#else #else
using value_type = typename using value_type = buffers_type<Buffers...>;
detail::common_buffers_type<Buffers...>::type;
#endif #endif
/// The type of iterator used by the concatenated sequence /// The type of iterator used by the concatenated sequence
@@ -53,8 +53,8 @@ public:
@param buffers The list of buffer sequences to concatenate. @param buffers The list of buffer sequences to concatenate.
Copies of the arguments will be maintained for the lifetime Copies of the arguments will be maintained for the lifetime
of the concatenated sequence; however, the ownership of memory of the concatenated sequence; however, the ownership of the
is not transferred. memory buffers themselves is not transferred.
*/ */
explicit explicit
buffers_cat_view(Buffers const&... buffers); buffers_cat_view(Buffers const&... buffers);
@@ -98,8 +98,8 @@ buffers_cat(B1 const& b1, B2 const& b2, Bn const&... bn)
#endif #endif
{ {
static_assert( static_assert(
detail::is_all_const_buffer_sequence<B1, B2, Bn...>::value, is_const_buffer_sequence<B1, B2, Bn...>::value,
"BufferSequence requirements not met"); "BufferSequence requirements not met");
return buffers_cat_view<B1, B2, Bn...>{b1, b2, bn...}; return buffers_cat_view<B1, B2, Bn...>{b1, b2, bn...};
} }

View File

@@ -12,12 +12,15 @@
#include <boost/beast/core/detail/config.hpp> #include <boost/beast/core/detail/config.hpp>
#include <boost/beast/core/buffer_traits.hpp> #include <boost/beast/core/buffer_traits.hpp>
#include <boost/beast/core/type_traits.hpp>
#include <boost/optional/optional.hpp> // for in_place_init_t #include <boost/optional/optional.hpp> // for in_place_init_t
#include <algorithm> #include <algorithm>
#include <cstdint> #include <cstdint>
#include <type_traits> #include <type_traits>
#if BOOST_WORKAROUND(BOOST_MSVC, < 1910)
#include <boost/type_traits.hpp>
#endif
namespace boost { namespace boost {
namespace beast { namespace beast {
@@ -27,16 +30,15 @@ namespace beast {
a shorter subset of the original list of buffers starting a shorter subset of the original list of buffers starting
with the first byte of the original sequence. with the first byte of the original sequence.
@tparam ConstBufferSequence The buffer sequence to adapt. @tparam BufferSequence The buffer sequence to adapt.
*/ */
template<class ConstBufferSequence> template<class BufferSequence>
class buffers_prefix_view class buffers_prefix_view
{ {
using iter_type = typename using iter_type =
detail::buffer_sequence_iterator< buffers_iterator_type<BufferSequence>;
ConstBufferSequence>::type;
ConstBufferSequence bs_; BufferSequence bs_;
std::size_t size_; std::size_t size_;
std::size_t remain_; std::size_t remain_;
iter_type end_; iter_type end_;
@@ -51,16 +53,24 @@ class buffers_prefix_view
public: public:
/** The type for each element in the list of buffers. /** The type for each element in the list of buffers.
If the type of the underlying sequence is a mutable buffer If the type `BufferSequence` meets the requirements of
sequence, then `value_type` is `net::mutable_buffer`. Otherwise, <em>MutableBufferSequence</em>, then `value_type` is
`value_type` is `net::const_buffer`. `net::mutable_buffer`. Otherwise, `value_type` is
`net::const_buffer`.
@see buffers_type @see buffers_type
*/ */
#if BOOST_BEAST_DOXYGEN #if BOOST_BEAST_DOXYGEN
using value_type = __see_below__; using value_type = __see_below__;
#elif BOOST_WORKAROUND(BOOST_MSVC, < 1910)
using value_type = typename std::conditional<
boost::is_convertible<typename
std::iterator_traits<iter_type>::value_type,
net::mutable_buffer>::value,
net::mutable_buffer,
net::const_buffer>::type;
#else #else
using value_type = buffers_type<ConstBufferSequence>; using value_type = buffers_type<BufferSequence>;
#endif #endif
#if BOOST_BEAST_DOXYGEN #if BOOST_BEAST_DOXYGEN
@@ -92,7 +102,7 @@ public:
*/ */
buffers_prefix_view( buffers_prefix_view(
std::size_t size, std::size_t size,
ConstBufferSequence const& buffers); BufferSequence const& buffers);
/** Construct a buffer sequence prefix in-place. /** Construct a buffer sequence prefix in-place.
@@ -152,25 +162,25 @@ buffer_size(buffers_prefix_view<
size as the original buffer sequence. size as the original buffer sequence.
@param buffers An object whose type meets the requirements @param buffers An object whose type meets the requirements
of <em>ConstBufferSequence</em>. The returned value will of <em>BufferSequence</em>. The returned value will
maintain a copy of the passed buffers for its lifetime; maintain a copy of the passed buffers for its lifetime;
however, ownership of the underlying memory is not however, ownership of the underlying memory is not
transferred. transferred.
@return A constant buffer sequence that represents the prefix @return A constant buffer sequence that represents the prefix
of the original buffer sequence. If the original buffer sequence of the original buffer sequence. If the original buffer sequence
also meets the requirements of <em>MutableConstBufferSequence</em>, also meets the requirements of <em>MutableBufferSequence</em>,
then the returned value will also be a mutable buffer sequence. then the returned value will also be a mutable buffer sequence.
*/ */
template<class ConstBufferSequence> template<class BufferSequence>
buffers_prefix_view<ConstBufferSequence> buffers_prefix_view<BufferSequence>
buffers_prefix( buffers_prefix(
std::size_t size, ConstBufferSequence const& buffers) std::size_t size, BufferSequence const& buffers)
{ {
static_assert( static_assert(
net::is_const_buffer_sequence<ConstBufferSequence>::value, net::is_const_buffer_sequence<BufferSequence>::value,
"ConstBufferSequence requirements not met"); "BufferSequence requirements not met");
return buffers_prefix_view<ConstBufferSequence>(size, buffers); return buffers_prefix_view<BufferSequence>(size, buffers);
} }
/** Returns the first buffer in a buffer sequence /** Returns the first buffer in a buffer sequence
@@ -183,12 +193,9 @@ buffers_prefix(
mutable, the returned buffer sequence will also be mutable. mutable, the returned buffer sequence will also be mutable.
Otherwise, the returned buffer sequence will be constant. Otherwise, the returned buffer sequence will be constant.
*/ */
template<class ConstBufferSequence> template<class BufferSequence>
typename std::conditional< buffers_type<BufferSequence>
net::is_mutable_buffer_sequence<ConstBufferSequence>::value, buffers_front(BufferSequence const& buffers)
net::mutable_buffer,
net::const_buffer>::type
buffers_front(ConstBufferSequence const& buffers)
{ {
auto const first = auto const first =
net::buffer_sequence_begin(buffers); net::buffer_sequence_begin(buffers);

View File

@@ -11,7 +11,7 @@
#define BOOST_BEAST_BUFFERS_RANGE_HPP #define BOOST_BEAST_BUFFERS_RANGE_HPP
#include <boost/beast/core/detail/config.hpp> #include <boost/beast/core/detail/config.hpp>
#include <boost/beast/core/detail/buffers_range.hpp> #include <boost/beast/core/detail/buffers_range_adaptor.hpp>
#include <boost/asio/buffer.hpp> #include <boost/asio/buffer.hpp>
#include <functional> #include <functional>

View File

@@ -11,8 +11,7 @@
#define BOOST_BEAST_BUFFERS_SUFFIX_HPP #define BOOST_BEAST_BUFFERS_SUFFIX_HPP
#include <boost/beast/core/detail/config.hpp> #include <boost/beast/core/detail/config.hpp>
#include <boost/beast/core/detail/type_traits.hpp> #include <boost/beast/core/buffer_traits.hpp>
#include <boost/asio/buffer.hpp>
#include <boost/optional.hpp> #include <boost/optional.hpp>
#include <cstdint> #include <cstdint>
#include <iterator> #include <iterator>
@@ -53,11 +52,8 @@ namespace beast {
template<class BufferSequence> template<class BufferSequence>
class buffers_suffix class buffers_suffix
{ {
using buffers_type = using iter_type =
typename std::decay<BufferSequence>::type; buffers_iterator_type<BufferSequence>;
using iter_type = typename
detail::buffer_sequence_iterator<buffers_type>::type;
BufferSequence bs_; BufferSequence bs_;
iter_type begin_; iter_type begin_;
@@ -76,20 +72,22 @@ class buffers_suffix
public: public:
/** The type for each element in the list of buffers. /** The type for each element in the list of buffers.
If the buffers in the underlying sequence are convertible to If <em>BufferSequence</em> meets the requirements of
`net::mutable_buffer`, then this type will be <em>MutableBufferSequence</em>, then this type will be
`net::mutable_buffer`, else this type will be `net::mutable_buffer`, otherwise this type will be
`net::const_buffer`. `net::const_buffer`.
*/ */
#if BOOST_BEAST_DOXYGEN #if BOOST_BEAST_DOXYGEN
using value_type = __implementation_defined__; using value_type = __implementation_defined__;
#else #elif 0
using value_type = typename std::conditional< using value_type = typename std::conditional<
std::is_convertible<typename std::is_convertible<typename
std::iterator_traits<iter_type>::value_type, std::iterator_traits<iter_type>::value_type,
net::mutable_buffer>::value, net::mutable_buffer>::value,
net::mutable_buffer, net::mutable_buffer,
net::const_buffer>::type; net::const_buffer>::type;
#else
using value_type = buffers_type<BufferSequence>;
#endif #endif
#if BOOST_BEAST_DOXYGEN #if BOOST_BEAST_DOXYGEN

View File

@@ -39,7 +39,8 @@ public:
using const_iterator = value_type const*; using const_iterator = value_type const*;
buffers_pair() = default; buffers_pair() = default;
#if defined(BOOST_MSVC) && BOOST_MSVC < 1910
#if BOOST_WORKAROUND(BOOST_MSVC, < 1910)
buffers_pair(buffers_pair const& other) buffers_pair(buffers_pair const& other)
: buffers_pair( : buffers_pair(
*other.begin(), *(other.begin() + 1)) *other.begin(), *(other.begin() + 1))

View File

@@ -7,11 +7,10 @@
// Official repository: https://github.com/boostorg/beast // Official repository: https://github.com/boostorg/beast
// //
#ifndef BOOST_BEAST_DETAIL_BUFFERS_RANGE_HPP #ifndef BOOST_BEAST_DETAIL_BUFFERS_RANGE_ADAPTOR_HPP
#define BOOST_BEAST_DETAIL_BUFFERS_RANGE_HPP #define BOOST_BEAST_DETAIL_BUFFERS_RANGE_ADAPTOR_HPP
#include <boost/beast/core/detail/type_traits.hpp> #include <boost/beast/core/buffer_traits.hpp>
#include <boost/asio/buffer.hpp>
#include <iterator> #include <iterator>
#include <type_traits> #include <type_traits>
@@ -28,22 +27,15 @@ public:
#if BOOST_BEAST_DOXYGEN #if BOOST_BEAST_DOXYGEN
using value_type = __see_below__; using value_type = __see_below__;
#else #else
using value_type = typename std::conditional< using value_type = buffers_type<BufferSequence>;
boost::is_convertible<
typename std::iterator_traits<
typename detail::buffer_sequence_iterator<
BufferSequence>::type>::value_type,
net::mutable_buffer>::value,
net::mutable_buffer,
net::const_buffer>::type;
#endif #endif
class const_iterator class const_iterator
{ {
friend class buffers_range_adaptor; friend class buffers_range_adaptor;
using iter_type = typename using iter_type =
buffer_sequence_iterator<BufferSequence>::type; buffers_iterator_type<BufferSequence>;
iter_type it_; iter_type it_;
buffers_range_adaptor const* b_ = nullptr; buffers_range_adaptor const* b_ = nullptr;
@@ -119,17 +111,17 @@ public:
} }
}; };
buffers_range_adaptor(
buffers_range_adaptor const&) = default;
buffers_range_adaptor& operator=(
buffers_range_adaptor const&) = default;
explicit explicit
buffers_range_adaptor(BufferSequence const& b) buffers_range_adaptor(BufferSequence const& b)
: b_(b) : b_(b)
{ {
} }
buffers_range_adaptor(
buffers_range_adaptor const&) = default;
buffers_range_adaptor& operator=(
buffers_range_adaptor const&) = default;
const_iterator const_iterator
begin() const noexcept begin() const noexcept
{ {

View File

@@ -10,8 +10,9 @@
#ifndef BOOST_BEAST_DETAIL_BUFFERS_REF_HPP #ifndef BOOST_BEAST_DETAIL_BUFFERS_REF_HPP
#define BOOST_BEAST_DETAIL_BUFFERS_REF_HPP #define BOOST_BEAST_DETAIL_BUFFERS_REF_HPP
#include <boost/beast/core/type_traits.hpp> #include <boost/beast/core/buffer_traits.hpp>
#include <iterator> #include <iterator>
#include <memory>
namespace boost { namespace boost {
namespace beast { namespace beast {
@@ -24,11 +25,11 @@ class buffers_ref
BufferSequence const* buffers_; BufferSequence const* buffers_;
public: public:
using const_iterator = typename using const_iterator =
buffer_sequence_iterator<BufferSequence>::type; buffers_iterator_type<BufferSequence>;
using value_type = typename std::iterator_traits< using value_type = typename
const_iterator>::value_type; std::iterator_traits<const_iterator>::value_type;
buffers_ref(buffers_ref const&) = default; buffers_ref(buffers_ref const&) = default;
buffers_ref& operator=(buffers_ref const&) = default; buffers_ref& operator=(buffers_ref const&) = default;
@@ -57,6 +58,9 @@ template<class BufferSequence>
buffers_ref<BufferSequence> buffers_ref<BufferSequence>
make_buffers_ref(BufferSequence const& buffers) make_buffers_ref(BufferSequence const& buffers)
{ {
static_assert(
is_const_buffer_sequence<BufferSequence>::value,
"BufferSequence requirements not met");
return buffers_ref<BufferSequence>(buffers); return buffers_ref<BufferSequence>(buffers);
} }

View File

@@ -197,85 +197,7 @@ using ConstBufferSequence =
using MutableBufferSequence = using MutableBufferSequence =
BufferSequence<net::mutable_buffer>; BufferSequence<net::mutable_buffer>;
template<class B1, class... Bn>
struct is_all_const_buffer_sequence
: std::integral_constant<bool,
net::is_const_buffer_sequence<B1>::value &&
is_all_const_buffer_sequence<Bn...>::value>
{
};
template<class B>
struct is_all_const_buffer_sequence<B>
: net::is_const_buffer_sequence<B>
{
};
// //
// Returns the iterator type of a buffer sequence
//
template<class B>
struct buffer_sequence_iterator
{
using type = decltype(
net::buffer_sequence_begin(
std::declval<B const&>()));
};
template<>
struct buffer_sequence_iterator<
net::const_buffer>
{
using type = net::const_buffer const*;
};
template<>
struct buffer_sequence_iterator<
net::mutable_buffer>
{
using type = net::mutable_buffer const*;
};
//
// Returns the value type of the iterator of a buffer sequence
//
template<class B>
struct buffer_sequence_value_type
{
using type = typename std::iterator_traits<
typename buffer_sequence_iterator<B>::type
>::value_type;
};
template<>
struct buffer_sequence_value_type<
net::const_buffer const*>
{
using type = net::const_buffer;
};
template<>
struct buffer_sequence_value_type<
net::mutable_buffer const*>
{
using type = net::mutable_buffer;
};
//
template<class... Bn>
struct common_buffers_type
{
using type = typename std::conditional<
mp11::mp_and<
boost::is_convertible<
typename buffer_sequence_value_type<Bn>::type,
net::mutable_buffer>...>::value,
net::mutable_buffer,
net::const_buffer>::type;
};
// Types that meet the requirements, // Types that meet the requirements,
// for use with std::declval only. // for use with std::declval only.

View File

@@ -59,9 +59,8 @@ class buffers_cat_view<Bn...>::const_iterator
"A minimum of two sequences are required"); "A minimum of two sequences are required");
detail::tuple<Bn...> const* bn_ = nullptr; detail::tuple<Bn...> const* bn_ = nullptr;
detail::variant<typename detail::variant<
detail::buffer_sequence_iterator<Bn>::type..., buffers_iterator_type<Bn>..., past_end> it_;
past_end> it_;
friend class buffers_cat_view<Bn...>; friend class buffers_cat_view<Bn...>;
@@ -69,8 +68,8 @@ class buffers_cat_view<Bn...>::const_iterator
using C = std::integral_constant<std::size_t, I>; using C = std::integral_constant<std::size_t, I>;
public: public:
using value_type = typename using value_type =
detail::common_buffers_type<Bn...>::type; typename buffers_cat_view<Bn...>::value_type;
using pointer = value_type const*; using pointer = value_type const*;
using reference = value_type; using reference = value_type;
using difference_type = std::ptrdiff_t; using difference_type = std::ptrdiff_t;

View File

@@ -10,6 +10,7 @@
#ifndef BOOST_BEAST_IMPL_BUFFERS_PREFIX_HPP #ifndef BOOST_BEAST_IMPL_BUFFERS_PREFIX_HPP
#define BOOST_BEAST_IMPL_BUFFERS_PREFIX_HPP #define BOOST_BEAST_IMPL_BUFFERS_PREFIX_HPP
#include <boost/config/workaround.hpp>
#include <algorithm> #include <algorithm>
#include <cstdint> #include <cstdint>
#include <iterator> #include <iterator>
@@ -30,12 +31,21 @@ class buffers_prefix_view<Buffers>::const_iterator
iter_type it_; iter_type it_;
public: public:
#if BOOST_WORKAROUND(BOOST_MSVC, < 1910)
using value_type = typename std::conditional< using value_type = typename std::conditional<
boost::is_convertible<typename boost::is_convertible<typename
std::iterator_traits<iter_type>::value_type, std::iterator_traits<iter_type>::value_type,
net::mutable_buffer>::value, net::mutable_buffer>::value,
net::mutable_buffer, net::mutable_buffer,
net::const_buffer>::type; net::const_buffer>::type;
#else
using value_type = buffers_type<Buffers>;
#endif
BOOST_STATIC_ASSERT(std::is_same<
typename const_iterator::value_type,
typename buffers_prefix_view::value_type>::value);
using pointer = value_type const*; using pointer = value_type const*;
using reference = value_type; using reference = value_type;
using difference_type = std::ptrdiff_t; using difference_type = std::ptrdiff_t;
@@ -61,7 +71,9 @@ public:
reference reference
operator*() const operator*() const
{ {
return beast::buffers_prefix(remain_, *it_); value_type v(*it_);
return { v.data(),
remain_ < v.size() ? remain_ : v.size()};
} }
pointer pointer
@@ -70,7 +82,8 @@ public:
const_iterator& const_iterator&
operator++() operator++()
{ {
remain_ -= net::buffer_size(*it_++); value_type const v = *it_++;
remain_ -= v.size();
return *this; return *this;
} }
@@ -78,14 +91,16 @@ public:
operator++(int) operator++(int)
{ {
auto temp = *this; auto temp = *this;
remain_ -= net::buffer_size(*it_++); value_type const v = *it_++;
remain_ -= v.size();
return temp; return temp;
} }
const_iterator& const_iterator&
operator--() operator--()
{ {
remain_ += net::buffer_size(*--it_); value_type const v = *--it_;
remain_ += v.size();
return *this; return *this;
} }
@@ -93,7 +108,8 @@ public:
operator--(int) operator--(int)
{ {
auto temp = *this; auto temp = *this;
remain_ += net::buffer_size(*--it_); value_type const v = *--it_;
remain_ += v.size();
return temp; return temp;
} }
@@ -130,8 +146,7 @@ setup(std::size_t size)
auto const last = bs_.end(); auto const last = bs_.end();
while(end_ != last) while(end_ != last)
{ {
auto const len = auto const len = net::buffer_size(*end_++);
net::const_buffer(*end_++).size();
if(len >= size) if(len >= size)
{ {
size_ += size; size_ += size;

View File

@@ -10,7 +10,7 @@
#ifndef BOOST_BEAST_IMPL_BUFFERS_SUFFIX_HPP #ifndef BOOST_BEAST_IMPL_BUFFERS_SUFFIX_HPP
#define BOOST_BEAST_IMPL_BUFFERS_SUFFIX_HPP #define BOOST_BEAST_IMPL_BUFFERS_SUFFIX_HPP
#include <boost/beast/core/type_traits.hpp> #include <boost/beast/core/buffer_traits.hpp>
#include <boost/type_traits.hpp> #include <boost/type_traits.hpp>
#include <algorithm> #include <algorithm>
#include <cstdint> #include <cstdint>
@@ -26,19 +26,22 @@ class buffers_suffix<Buffers>::const_iterator
{ {
friend class buffers_suffix<Buffers>; friend class buffers_suffix<Buffers>;
using iter_type = typename using iter_type = buffers_iterator_type<Buffers>;
detail::buffer_sequence_iterator<Buffers>::type;
iter_type it_; iter_type it_;
buffers_suffix const* b_ = nullptr; buffers_suffix const* b_ = nullptr;
public: public:
#if BOOST_WORKAROUND(BOOST_MSVC, < 1910)
using value_type = typename std::conditional< using value_type = typename std::conditional<
boost::is_convertible<typename boost::is_convertible<typename
std::iterator_traits<iter_type>::value_type, std::iterator_traits<iter_type>::value_type,
net::mutable_buffer>::value, net::mutable_buffer>::value,
net::mutable_buffer, net::mutable_buffer,
net::const_buffer>::type; net::const_buffer>::type;
#else
using value_type = buffers_type<Buffers>;
#endif
using pointer = value_type const*; using pointer = value_type const*;
using reference = value_type; using reference = value_type;
using difference_type = std::ptrdiff_t; using difference_type = std::ptrdiff_t;
@@ -54,20 +57,7 @@ public:
bool bool
operator==(const_iterator const& other) const operator==(const_iterator const& other) const
{ {
return return b_ == other.b_ && it_ == other.it_;
(b_ == nullptr) ?
(
other.b_ == nullptr ||
other.it_ == net::buffer_sequence_end(other.b_->bs_)
):(
(other.b_ == nullptr) ?
(
it_ == net::buffer_sequence_end(b_->bs_)
): (
b_ == other.b_ &&
it_ == other.it_
)
);
} }
bool bool
@@ -118,8 +108,9 @@ public:
} }
private: private:
const_iterator(buffers_suffix const& b, const_iterator(
iter_type it) buffers_suffix const& b,
iter_type it)
: it_(it) : it_(it)
, b_(&b) , b_(&b)
{ {

View File

@@ -40,6 +40,18 @@ public:
net::mutable_buffer, net::mutable_buffer net::mutable_buffer, net::mutable_buffer
>::value); >::value);
BOOST_STATIC_ASSERT(is_const_buffer_sequence<
net::const_buffer const&
>::value);
BOOST_STATIC_ASSERT(is_const_buffer_sequence<
net::const_buffer const&, net::const_buffer const&
>::value);
BOOST_STATIC_ASSERT(is_const_buffer_sequence<
net::const_buffer const&, net::mutable_buffer const&
>::value);
// is_mutable_buffer_sequence // is_mutable_buffer_sequence
BOOST_STATIC_ASSERT(is_mutable_buffer_sequence< BOOST_STATIC_ASSERT(is_mutable_buffer_sequence<
@@ -61,6 +73,14 @@ public:
net::const_buffer, net::mutable_buffer net::const_buffer, net::mutable_buffer
>::value); >::value);
BOOST_STATIC_ASSERT(is_mutable_buffer_sequence<
net::mutable_buffer const&
>::value);
BOOST_STATIC_ASSERT(is_mutable_buffer_sequence<
net::mutable_buffer const&, net::mutable_buffer const&
>::value);
// buffers_type // buffers_type
BOOST_STATIC_ASSERT( BOOST_STATIC_ASSERT(