// // registered_buffer.hpp // ~~~~~~~~~~~~~~~~~~~~~ // // Copyright (c) 2003-2023 Christopher M. Kohlhoff (chris at kohlhoff dot com) // // 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 ASIO_REGISTERED_BUFFER_HPP #define ASIO_REGISTERED_BUFFER_HPP #if defined(_MSC_VER) && (_MSC_VER >= 1200) # pragma once #endif // defined(_MSC_VER) && (_MSC_VER >= 1200) #include "asio/detail/config.hpp" #include "asio/buffer.hpp" #include "asio/detail/push_options.hpp" namespace asio { namespace detail { class buffer_registration_base; } // namespace detail class const_registered_buffer; /// Type used to identify a registered buffer. class registered_buffer_id { public: /// The native buffer identifier type. typedef int native_handle_type; /// Default constructor creates an invalid registered buffer identifier. registered_buffer_id() ASIO_NOEXCEPT : scope_(0), index_(-1) { } /// Get the native buffer identifier type. native_handle_type native_handle() const ASIO_NOEXCEPT { return index_; } /// Compare two IDs for equality. friend bool operator==(const registered_buffer_id& lhs, const registered_buffer_id& rhs) ASIO_NOEXCEPT { return lhs.scope_ == rhs.scope_ && lhs.index_ == rhs.index_; } /// Compare two IDs for equality. friend bool operator!=(const registered_buffer_id& lhs, const registered_buffer_id& rhs) ASIO_NOEXCEPT { return lhs.scope_ != rhs.scope_ || lhs.index_ != rhs.index_; } private: friend class detail::buffer_registration_base; // Hidden constructor used by buffer registration. registered_buffer_id(const void* scope, int index) ASIO_NOEXCEPT : scope_(scope), index_(index) { } const void* scope_; int index_; }; /// Holds a registered buffer over modifiable data. /** * Satisfies the @c MutableBufferSequence type requirements. */ class mutable_registered_buffer { public: #if !defined(ASIO_HAS_DECLTYPE) \ && !defined(GENERATING_DOCUMENTATION) typedef mutable_buffer value_type; #endif // !defined(ASIO_HAS_DECLTYPE) // && !defined(GENERATING_DOCUMENTATION) /// Default constructor creates an invalid registered buffer. mutable_registered_buffer() ASIO_NOEXCEPT : buffer_(), id_() { } /// Get the underlying mutable buffer. const mutable_buffer& buffer() const ASIO_NOEXCEPT { return buffer_; } /// Get a pointer to the beginning of the memory range. /** * @returns buffer().data(). */ void* data() const ASIO_NOEXCEPT { return buffer_.data(); } /// Get the size of the memory range. /** * @returns buffer().size(). */ std::size_t size() const ASIO_NOEXCEPT { return buffer_.size(); } /// Get the registered buffer identifier. const registered_buffer_id& id() const ASIO_NOEXCEPT { return id_; } /// Move the start of the buffer by the specified number of bytes. mutable_registered_buffer& operator+=(std::size_t n) ASIO_NOEXCEPT { buffer_ += n; return *this; } private: friend class detail::buffer_registration_base; // Hidden constructor used by buffer registration and operators. mutable_registered_buffer(const mutable_buffer& b, const registered_buffer_id& i) ASIO_NOEXCEPT : buffer_(b), id_(i) { } #if !defined(GENERATING_DOCUMENTATION) friend mutable_registered_buffer buffer( const mutable_registered_buffer& b, std::size_t n) ASIO_NOEXCEPT; #endif // !defined(GENERATING_DOCUMENTATION) mutable_buffer buffer_; registered_buffer_id id_; }; /// Holds a registered buffer over non-modifiable data. /** * Satisfies the @c ConstBufferSequence type requirements. */ class const_registered_buffer { public: #if !defined(ASIO_HAS_DECLTYPE) \ && !defined(GENERATING_DOCUMENTATION) typedef const_buffer value_type; #endif // !defined(ASIO_HAS_DECLTYPE) // && !defined(GENERATING_DOCUMENTATION) /// Default constructor creates an invalid registered buffer. const_registered_buffer() ASIO_NOEXCEPT : buffer_(), id_() { } /// Construct a non-modifiable buffer from a modifiable one. const_registered_buffer( const mutable_registered_buffer& b) ASIO_NOEXCEPT : buffer_(b.buffer()), id_(b.id()) { } /// Get the underlying constant buffer. const const_buffer& buffer() const ASIO_NOEXCEPT { return buffer_; } /// Get a pointer to the beginning of the memory range. /** * @returns buffer().data(). */ const void* data() const ASIO_NOEXCEPT { return buffer_.data(); } /// Get the size of the memory range. /** * @returns buffer().size(). */ std::size_t size() const ASIO_NOEXCEPT { return buffer_.size(); } /// Get the registered buffer identifier. const registered_buffer_id& id() const ASIO_NOEXCEPT { return id_; } /// Move the start of the buffer by the specified number of bytes. const_registered_buffer& operator+=(std::size_t n) ASIO_NOEXCEPT { buffer_ += n; return *this; } private: // Hidden constructor used by operators. const_registered_buffer(const const_buffer& b, const registered_buffer_id& i) ASIO_NOEXCEPT : buffer_(b), id_(i) { } #if !defined(GENERATING_DOCUMENTATION) friend const_registered_buffer buffer( const const_registered_buffer& b, std::size_t n) ASIO_NOEXCEPT; #endif // !defined(GENERATING_DOCUMENTATION) const_buffer buffer_; registered_buffer_id id_; }; /** @addtogroup buffer_sequence_begin */ /// Get an iterator to the first element in a buffer sequence. inline const mutable_buffer* buffer_sequence_begin( const mutable_registered_buffer& b) ASIO_NOEXCEPT { return &b.buffer(); } /// Get an iterator to the first element in a buffer sequence. inline const const_buffer* buffer_sequence_begin( const const_registered_buffer& b) ASIO_NOEXCEPT { return &b.buffer(); } /** @} */ /** @addtogroup buffer_sequence_end */ /// Get an iterator to one past the end element in a buffer sequence. inline const mutable_buffer* buffer_sequence_end( const mutable_registered_buffer& b) ASIO_NOEXCEPT { return &b.buffer() + 1; } /// Get an iterator to one past the end element in a buffer sequence. inline const const_buffer* buffer_sequence_end( const const_registered_buffer& b) ASIO_NOEXCEPT { return &b.buffer() + 1; } /** @} */ /** @addtogroup buffer */ /// Obtain a buffer representing the entire registered buffer. inline mutable_registered_buffer buffer( const mutable_registered_buffer& b) ASIO_NOEXCEPT { return b; } /// Obtain a buffer representing the entire registered buffer. inline const_registered_buffer buffer( const const_registered_buffer& b) ASIO_NOEXCEPT { return b; } /// Obtain a buffer representing part of a registered buffer. inline mutable_registered_buffer buffer( const mutable_registered_buffer& b, std::size_t n) ASIO_NOEXCEPT { return mutable_registered_buffer(buffer(b.buffer_, n), b.id_); } /// Obtain a buffer representing part of a registered buffer. inline const_registered_buffer buffer( const const_registered_buffer& b, std::size_t n) ASIO_NOEXCEPT { return const_registered_buffer(buffer(b.buffer_, n), b.id_); } /** @} */ /// Create a new modifiable registered buffer that is offset from the start of /// another. /** * @relates mutable_registered_buffer */ inline mutable_registered_buffer operator+( const mutable_registered_buffer& b, std::size_t n) ASIO_NOEXCEPT { mutable_registered_buffer tmp(b); tmp += n; return tmp; } /// Create a new modifiable buffer that is offset from the start of another. /** * @relates mutable_registered_buffer */ inline mutable_registered_buffer operator+(std::size_t n, const mutable_registered_buffer& b) ASIO_NOEXCEPT { return b + n; } /// Create a new non-modifiable registered buffer that is offset from the start /// of another. /** * @relates const_registered_buffer */ inline const_registered_buffer operator+(const const_registered_buffer& b, std::size_t n) ASIO_NOEXCEPT { const_registered_buffer tmp(b); tmp += n; return tmp; } /// Create a new non-modifiable buffer that is offset from the start of another. /** * @relates const_registered_buffer */ inline const_registered_buffer operator+(std::size_t n, const const_registered_buffer& b) ASIO_NOEXCEPT { return b + n; } } // namespace asio #include "asio/detail/pop_options.hpp" #endif // ASIO_REGISTERED_BUFFER_HPP