diff options
Diffstat (limited to '3rdparty/asio/include/asio/read.hpp')
-rw-r--r-- | 3rdparty/asio/include/asio/read.hpp | 851 |
1 files changed, 676 insertions, 175 deletions
diff --git a/3rdparty/asio/include/asio/read.hpp b/3rdparty/asio/include/asio/read.hpp index 4839934dbab..0eb966af36f 100644 --- a/3rdparty/asio/include/asio/read.hpp +++ b/3rdparty/asio/include/asio/read.hpp @@ -2,7 +2,7 @@ // read.hpp // ~~~~~~~~ // -// Copyright (c) 2003-2016 Christopher M. Kohlhoff (chris at kohlhoff dot com) +// Copyright (c) 2003-2024 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) @@ -19,6 +19,7 @@ #include <cstddef> #include "asio/async_result.hpp" #include "asio/buffer.hpp" +#include "asio/completion_condition.hpp" #include "asio/error.hpp" #if !defined(ASIO_NO_EXTENSIONS) @@ -28,12 +29,21 @@ #include "asio/detail/push_options.hpp" namespace asio { +namespace detail { + +template <typename> class initiate_async_read; +#if !defined(ASIO_NO_DYNAMIC_BUFFER_V1) +template <typename> class initiate_async_read_dynbuf_v1; +#endif // !defined(ASIO_NO_DYNAMIC_BUFFER_V1) +template <typename> class initiate_async_read_dynbuf_v2; + +} // namespace detail /** * @defgroup read asio::read * - * @brief Attempt to read a certain amount of data from a stream before - * returning. + * @brief The @c read function is a composed operation that reads a certain + * amount of data from a stream before returning. */ /*@{*/ @@ -75,9 +85,9 @@ namespace asio { */ template <typename SyncReadStream, typename MutableBufferSequence> std::size_t read(SyncReadStream& s, const MutableBufferSequence& buffers, - typename enable_if< + constraint_t< is_mutable_buffer_sequence<MutableBufferSequence>::value - >::type* = 0); + > = 0); /// Attempt to read a certain amount of data from a stream before returning. /** @@ -118,9 +128,9 @@ std::size_t read(SyncReadStream& s, const MutableBufferSequence& buffers, template <typename SyncReadStream, typename MutableBufferSequence> std::size_t read(SyncReadStream& s, const MutableBufferSequence& buffers, asio::error_code& ec, - typename enable_if< + constraint_t< is_mutable_buffer_sequence<MutableBufferSequence>::value - >::type* = 0); + > = 0); /// Attempt to read a certain amount of data from a stream before returning. /** @@ -172,9 +182,9 @@ template <typename SyncReadStream, typename MutableBufferSequence, typename CompletionCondition> std::size_t read(SyncReadStream& s, const MutableBufferSequence& buffers, CompletionCondition completion_condition, - typename enable_if< + constraint_t< is_mutable_buffer_sequence<MutableBufferSequence>::value - >::type* = 0); + > = 0); /// Attempt to read a certain amount of data from a stream before returning. /** @@ -219,9 +229,11 @@ template <typename SyncReadStream, typename MutableBufferSequence, typename CompletionCondition> std::size_t read(SyncReadStream& s, const MutableBufferSequence& buffers, CompletionCondition completion_condition, asio::error_code& ec, - typename enable_if< + constraint_t< is_mutable_buffer_sequence<MutableBufferSequence>::value - >::type* = 0); + > = 0); + +#if !defined(ASIO_NO_DYNAMIC_BUFFER_V1) /// Attempt to read a certain amount of data from a stream before returning. /** @@ -250,12 +262,15 @@ std::size_t read(SyncReadStream& s, const MutableBufferSequence& buffers, * s, buffers, * asio::transfer_all()); @endcode */ -template <typename SyncReadStream, typename DynamicBuffer> +template <typename SyncReadStream, typename DynamicBuffer_v1> std::size_t read(SyncReadStream& s, - ASIO_MOVE_ARG(DynamicBuffer) buffers, - typename enable_if< - is_dynamic_buffer<DynamicBuffer>::value - >::type* = 0); + DynamicBuffer_v1&& buffers, + constraint_t< + is_dynamic_buffer_v1<decay_t<DynamicBuffer_v1>>::value + > = 0, + constraint_t< + !is_dynamic_buffer_v2<decay_t<DynamicBuffer_v1>>::value + > = 0); /// Attempt to read a certain amount of data from a stream before returning. /** @@ -283,13 +298,16 @@ std::size_t read(SyncReadStream& s, * s, buffers, * asio::transfer_all(), ec); @endcode */ -template <typename SyncReadStream, typename DynamicBuffer> +template <typename SyncReadStream, typename DynamicBuffer_v1> std::size_t read(SyncReadStream& s, - ASIO_MOVE_ARG(DynamicBuffer) buffers, + DynamicBuffer_v1&& buffers, asio::error_code& ec, - typename enable_if< - is_dynamic_buffer<DynamicBuffer>::value - >::type* = 0); + constraint_t< + is_dynamic_buffer_v1<decay_t<DynamicBuffer_v1>>::value + > = 0, + constraint_t< + !is_dynamic_buffer_v2<decay_t<DynamicBuffer_v1>>::value + > = 0); /// Attempt to read a certain amount of data from a stream before returning. /** @@ -327,14 +345,17 @@ std::size_t read(SyncReadStream& s, * * @throws asio::system_error Thrown on failure. */ -template <typename SyncReadStream, typename DynamicBuffer, +template <typename SyncReadStream, typename DynamicBuffer_v1, typename CompletionCondition> std::size_t read(SyncReadStream& s, - ASIO_MOVE_ARG(DynamicBuffer) buffers, + DynamicBuffer_v1&& buffers, CompletionCondition completion_condition, - typename enable_if< - is_dynamic_buffer<DynamicBuffer>::value - >::type* = 0); + constraint_t< + is_dynamic_buffer_v1<decay_t<DynamicBuffer_v1>>::value + > = 0, + constraint_t< + !is_dynamic_buffer_v2<decay_t<DynamicBuffer_v1>>::value + > = 0); /// Attempt to read a certain amount of data from a stream before returning. /** @@ -373,14 +394,17 @@ std::size_t read(SyncReadStream& s, * @returns The number of bytes read. If an error occurs, returns the total * number of bytes successfully transferred prior to the error. */ -template <typename SyncReadStream, typename DynamicBuffer, +template <typename SyncReadStream, typename DynamicBuffer_v1, typename CompletionCondition> std::size_t read(SyncReadStream& s, - ASIO_MOVE_ARG(DynamicBuffer) buffers, + DynamicBuffer_v1&& buffers, CompletionCondition completion_condition, asio::error_code& ec, - typename enable_if< - is_dynamic_buffer<DynamicBuffer>::value - >::type* = 0); + constraint_t< + is_dynamic_buffer_v1<decay_t<DynamicBuffer_v1>>::value + > = 0, + constraint_t< + !is_dynamic_buffer_v2<decay_t<DynamicBuffer_v1>>::value + > = 0); #if !defined(ASIO_NO_EXTENSIONS) #if !defined(ASIO_NO_IOSTREAM) @@ -527,13 +551,169 @@ std::size_t read(SyncReadStream& s, basic_streambuf<Allocator>& b, #endif // !defined(ASIO_NO_IOSTREAM) #endif // !defined(ASIO_NO_EXTENSIONS) +#endif // !defined(ASIO_NO_DYNAMIC_BUFFER_V1) + +/// Attempt to read a certain amount of data from a stream before returning. +/** + * This function is used to read a certain number of bytes of data from a + * stream. The call will block until one of the following conditions is true: + * + * @li The specified dynamic buffer sequence is full (that is, it has reached + * maximum size). + * + * @li An error occurred. + * + * This operation is implemented in terms of zero or more calls to the stream's + * read_some function. + * + * @param s The stream from which the data is to be read. The type must support + * the SyncReadStream concept. + * + * @param buffers The dynamic buffer sequence into which the data will be read. + * + * @returns The number of bytes transferred. + * + * @throws asio::system_error Thrown on failure. + * + * @note This overload is equivalent to calling: + * @code asio::read( + * s, buffers, + * asio::transfer_all()); @endcode + */ +template <typename SyncReadStream, typename DynamicBuffer_v2> +std::size_t read(SyncReadStream& s, DynamicBuffer_v2 buffers, + constraint_t< + is_dynamic_buffer_v2<DynamicBuffer_v2>::value + > = 0); + +/// Attempt to read a certain amount of data from a stream before returning. +/** + * This function is used to read a certain number of bytes of data from a + * stream. The call will block until one of the following conditions is true: + * + * @li The supplied buffer is full (that is, it has reached maximum size). + * + * @li An error occurred. + * + * This operation is implemented in terms of zero or more calls to the stream's + * read_some function. + * + * @param s The stream from which the data is to be read. The type must support + * the SyncReadStream concept. + * + * @param buffers The dynamic buffer sequence into which the data will be read. + * + * @param ec Set to indicate what error occurred, if any. + * + * @returns The number of bytes transferred. + * + * @note This overload is equivalent to calling: + * @code asio::read( + * s, buffers, + * asio::transfer_all(), ec); @endcode + */ +template <typename SyncReadStream, typename DynamicBuffer_v2> +std::size_t read(SyncReadStream& s, DynamicBuffer_v2 buffers, + asio::error_code& ec, + constraint_t< + is_dynamic_buffer_v2<DynamicBuffer_v2>::value + > = 0); + +/// Attempt to read a certain amount of data from a stream before returning. +/** + * This function is used to read a certain number of bytes of data from a + * stream. The call will block until one of the following conditions is true: + * + * @li The specified dynamic buffer sequence is full (that is, it has reached + * maximum size). + * + * @li The completion_condition function object returns 0. + * + * This operation is implemented in terms of zero or more calls to the stream's + * read_some function. + * + * @param s The stream from which the data is to be read. The type must support + * the SyncReadStream concept. + * + * @param buffers The dynamic buffer sequence into which the data will be read. + * + * @param completion_condition The function object to be called to determine + * whether the read operation is complete. The signature of the function object + * must be: + * @code std::size_t completion_condition( + * // Result of latest read_some operation. + * const asio::error_code& error, + * + * // Number of bytes transferred so far. + * std::size_t bytes_transferred + * ); @endcode + * A return value of 0 indicates that the read operation is complete. A non-zero + * return value indicates the maximum number of bytes to be read on the next + * call to the stream's read_some function. + * + * @returns The number of bytes transferred. + * + * @throws asio::system_error Thrown on failure. + */ +template <typename SyncReadStream, typename DynamicBuffer_v2, + typename CompletionCondition> +std::size_t read(SyncReadStream& s, DynamicBuffer_v2 buffers, + CompletionCondition completion_condition, + constraint_t< + is_dynamic_buffer_v2<DynamicBuffer_v2>::value + > = 0); + +/// Attempt to read a certain amount of data from a stream before returning. +/** + * This function is used to read a certain number of bytes of data from a + * stream. The call will block until one of the following conditions is true: + * + * @li The specified dynamic buffer sequence is full (that is, it has reached + * maximum size). + * + * @li The completion_condition function object returns 0. + * + * This operation is implemented in terms of zero or more calls to the stream's + * read_some function. + * + * @param s The stream from which the data is to be read. The type must support + * the SyncReadStream concept. + * + * @param buffers The dynamic buffer sequence into which the data will be read. + * + * @param completion_condition The function object to be called to determine + * whether the read operation is complete. The signature of the function object + * must be: + * @code std::size_t completion_condition( + * // Result of latest read_some operation. + * const asio::error_code& error, + * + * // Number of bytes transferred so far. + * std::size_t bytes_transferred + * ); @endcode + * A return value of 0 indicates that the read operation is complete. A non-zero + * return value indicates the maximum number of bytes to be read on the next + * call to the stream's read_some function. + * + * @param ec Set to indicate what error occurred, if any. + * + * @returns The number of bytes read. If an error occurs, returns the total + * number of bytes successfully transferred prior to the error. + */ +template <typename SyncReadStream, typename DynamicBuffer_v2, + typename CompletionCondition> +std::size_t read(SyncReadStream& s, DynamicBuffer_v2 buffers, + CompletionCondition completion_condition, asio::error_code& ec, + constraint_t< + is_dynamic_buffer_v2<DynamicBuffer_v2>::value + > = 0); /*@}*/ /** * @defgroup async_read asio::async_read * - * @brief Start an asynchronous operation to read a certain amount of data from - * a stream. + * @brief The @c async_read function is a composed asynchronous operation that + * reads a certain amount of data from a stream before completion. */ /*@{*/ @@ -541,9 +721,9 @@ std::size_t read(SyncReadStream& s, basic_streambuf<Allocator>& b, /// stream. /** * This function is used to asynchronously read a certain number of bytes of - * data from a stream. The function call always returns immediately. The - * asynchronous operation will continue until one of the following conditions is - * true: + * data from a stream. It is an initiating function for an @ref + * asynchronous_operation, and always returns immediately. The asynchronous + * operation will continue until one of the following conditions is true: * * @li The supplied buffers are full. That is, the bytes transferred is equal to * the sum of the buffer sizes. @@ -563,24 +743,29 @@ std::size_t read(SyncReadStream& s, basic_streambuf<Allocator>& b, * of the buffer sizes indicates the maximum number of bytes to read from the * stream. Although the buffers object may be copied as necessary, ownership of * the underlying memory blocks is retained by the caller, which must guarantee - * that they remain valid until the handler is called. + * that they remain valid until the completion handler is called. * - * @param handler The handler to be called when the read operation completes. - * Copies will be made of the handler as required. The function signature of the - * handler must be: + * @param token The @ref completion_token that will be used to produce a + * completion handler, which will be called when the read completes. + * Potential completion tokens include @ref use_future, @ref use_awaitable, + * @ref yield_context, or a function object with the correct completion + * signature. The function signature of the completion handler must be: * @code void handler( - * const asio::error_code& error, // Result of operation. + * // Result of operation. + * const asio::error_code& error, * - * std::size_t bytes_transferred // Number of bytes copied into the - * // buffers. If an error occurred, - * // this will be the number of - * // bytes successfully transferred - * // prior to the error. + * // Number of bytes copied into the buffers. If an error + * // occurred, this will be the number of bytes successfully + * // transferred prior to the error. + * std::size_t bytes_transferred * ); @endcode * Regardless of whether the asynchronous operation completes immediately or - * not, the handler will not be invoked from within this function. Invocation of - * the handler will be performed in a manner equivalent to using - * asio::io_context::post(). + * not, the completion handler will not be invoked from within this function. + * On immediate completion, invocation of the handler will be performed in a + * manner equivalent to using asio::post(). + * + * @par Completion Signature + * @code void(asio::error_code, std::size_t) @endcode * * @par Example * To read into a single data buffer use the @ref buffer function as follows: @@ -596,24 +781,41 @@ std::size_t read(SyncReadStream& s, basic_streambuf<Allocator>& b, * s, buffers, * asio::transfer_all(), * handler); @endcode + * + * @par Per-Operation Cancellation + * This asynchronous operation supports cancellation for the following + * asio::cancellation_type values: + * + * @li @c cancellation_type::terminal + * + * @li @c cancellation_type::partial + * + * if they are also supported by the @c AsyncReadStream type's + * @c async_read_some operation. */ template <typename AsyncReadStream, typename MutableBufferSequence, - typename ReadHandler> -ASIO_INITFN_RESULT_TYPE(ReadHandler, - void (asio::error_code, std::size_t)) -async_read(AsyncReadStream& s, const MutableBufferSequence& buffers, - ASIO_MOVE_ARG(ReadHandler) handler, - typename enable_if< + ASIO_COMPLETION_TOKEN_FOR(void (asio::error_code, + std::size_t)) ReadToken = default_completion_token_t< + typename AsyncReadStream::executor_type>> +auto async_read(AsyncReadStream& s, const MutableBufferSequence& buffers, + ReadToken&& token = default_completion_token_t< + typename AsyncReadStream::executor_type>(), + constraint_t< is_mutable_buffer_sequence<MutableBufferSequence>::value - >::type* = 0); + > = 0) + -> decltype( + async_initiate<ReadToken, + void (asio::error_code, std::size_t)>( + declval<detail::initiate_async_read<AsyncReadStream>>(), + token, buffers, transfer_all())); /// Start an asynchronous operation to read a certain amount of data from a /// stream. /** * This function is used to asynchronously read a certain number of bytes of - * data from a stream. The function call always returns immediately. The - * asynchronous operation will continue until one of the following conditions is - * true: + * data from a stream. It is an initiating function for an @ref + * asynchronous_operation, and always returns immediately. The asynchronous + * operation will continue until one of the following conditions is true: * * @li The supplied buffers are full. That is, the bytes transferred is equal to * the sum of the buffer sizes. @@ -627,7 +829,7 @@ async_read(AsyncReadStream& s, const MutableBufferSequence& buffers, * of the buffer sizes indicates the maximum number of bytes to read from the * stream. Although the buffers object may be copied as necessary, ownership of * the underlying memory blocks is retained by the caller, which must guarantee - * that they remain valid until the handler is called. + * that they remain valid until the completion handler is called. * * @param completion_condition The function object to be called to determine * whether the read operation is complete. The signature of the function object @@ -643,22 +845,27 @@ async_read(AsyncReadStream& s, const MutableBufferSequence& buffers, * return value indicates the maximum number of bytes to be read on the next * call to the stream's async_read_some function. * - * @param handler The handler to be called when the read operation completes. - * Copies will be made of the handler as required. The function signature of the - * handler must be: + * @param token The @ref completion_token that will be used to produce a + * completion handler, which will be called when the read completes. + * Potential completion tokens include @ref use_future, @ref use_awaitable, + * @ref yield_context, or a function object with the correct completion + * signature. The function signature of the completion handler must be: * @code void handler( - * const asio::error_code& error, // Result of operation. + * // Result of operation. + * const asio::error_code& error, * - * std::size_t bytes_transferred // Number of bytes copied into the - * // buffers. If an error occurred, - * // this will be the number of - * // bytes successfully transferred - * // prior to the error. + * // Number of bytes copied into the buffers. If an error + * // occurred, this will be the number of bytes successfully + * // transferred prior to the error. + * std::size_t bytes_transferred * ); @endcode * Regardless of whether the asynchronous operation completes immediately or - * not, the handler will not be invoked from within this function. Invocation of - * the handler will be performed in a manner equivalent to using - * asio::io_context::post(). + * not, the completion handler will not be invoked from within this function. + * On immediate completion, invocation of the handler will be performed in a + * manner equivalent to using asio::post(). + * + * @par Completion Signature + * @code void(asio::error_code, std::size_t) @endcode * * @par Example * To read into a single data buffer use the @ref buffer function as follows: @@ -669,25 +876,46 @@ async_read(AsyncReadStream& s, const MutableBufferSequence& buffers, * See the @ref buffer documentation for information on reading into multiple * buffers in one go, and how to use it with arrays, boost::array or * std::vector. + * + * @par Per-Operation Cancellation + * This asynchronous operation supports cancellation for the following + * asio::cancellation_type values: + * + * @li @c cancellation_type::terminal + * + * @li @c cancellation_type::partial + * + * if they are also supported by the @c AsyncReadStream type's + * @c async_read_some operation. */ -template <typename AsyncReadStream, typename MutableBufferSequence, - typename CompletionCondition, typename ReadHandler> -ASIO_INITFN_RESULT_TYPE(ReadHandler, - void (asio::error_code, std::size_t)) -async_read(AsyncReadStream& s, const MutableBufferSequence& buffers, +template <typename AsyncReadStream, + typename MutableBufferSequence, typename CompletionCondition, + ASIO_COMPLETION_TOKEN_FOR(void (asio::error_code, + std::size_t)) ReadToken = default_completion_token_t< + typename AsyncReadStream::executor_type>> +auto async_read(AsyncReadStream& s, const MutableBufferSequence& buffers, CompletionCondition completion_condition, - ASIO_MOVE_ARG(ReadHandler) handler, - typename enable_if< + ReadToken&& token = default_completion_token_t< + typename AsyncReadStream::executor_type>(), + constraint_t< is_mutable_buffer_sequence<MutableBufferSequence>::value - >::type* = 0); + > = 0) + -> decltype( + async_initiate<ReadToken, + void (asio::error_code, std::size_t)>( + declval<detail::initiate_async_read<AsyncReadStream>>(), + token, buffers, + static_cast<CompletionCondition&&>(completion_condition))); + +#if !defined(ASIO_NO_DYNAMIC_BUFFER_V1) /// Start an asynchronous operation to read a certain amount of data from a /// stream. /** * This function is used to asynchronously read a certain number of bytes of - * data from a stream. The function call always returns immediately. The - * asynchronous operation will continue until one of the following conditions is - * true: + * data from a stream. It is an initiating function for an @ref + * asynchronous_operation, and always returns immediately. The asynchronous + * operation will continue until one of the following conditions is true: * * @li The specified dynamic buffer sequence is full (that is, it has reached * maximum size). @@ -706,49 +934,73 @@ async_read(AsyncReadStream& s, const MutableBufferSequence& buffers, * @param buffers The dynamic buffer sequence into which the data will be read. * Although the buffers object may be copied as necessary, ownership of the * underlying memory blocks is retained by the caller, which must guarantee - * that they remain valid until the handler is called. + * that they remain valid until the completion handler is called. * - * @param handler The handler to be called when the read operation completes. - * Copies will be made of the handler as required. The function signature of the - * handler must be: + * @param token The @ref completion_token that will be used to produce a + * completion handler, which will be called when the read completes. + * Potential completion tokens include @ref use_future, @ref use_awaitable, + * @ref yield_context, or a function object with the correct completion + * signature. The function signature of the completion handler must be: * @code void handler( - * const asio::error_code& error, // Result of operation. + * // Result of operation. + * const asio::error_code& error, * - * std::size_t bytes_transferred // Number of bytes copied into the - * // buffers. If an error occurred, - * // this will be the number of - * // bytes successfully transferred - * // prior to the error. + * // Number of bytes copied into the buffers. If an error + * // occurred, this will be the number of bytes successfully + * // transferred prior to the error. + * std::size_t bytes_transferred * ); @endcode * Regardless of whether the asynchronous operation completes immediately or - * not, the handler will not be invoked from within this function. Invocation of - * the handler will be performed in a manner equivalent to using - * asio::io_context::post(). + * not, the completion handler will not be invoked from within this function. + * On immediate completion, invocation of the handler will be performed in a + * manner equivalent to using asio::post(). + * + * @par Completion Signature + * @code void(asio::error_code, std::size_t) @endcode * * @note This overload is equivalent to calling: * @code asio::async_read( * s, buffers, * asio::transfer_all(), * handler); @endcode + * + * @par Per-Operation Cancellation + * This asynchronous operation supports cancellation for the following + * asio::cancellation_type values: + * + * @li @c cancellation_type::terminal + * + * @li @c cancellation_type::partial + * + * if they are also supported by the @c AsyncReadStream type's + * @c async_read_some operation. */ -template <typename AsyncReadStream, - typename DynamicBuffer, typename ReadHandler> -ASIO_INITFN_RESULT_TYPE(ReadHandler, - void (asio::error_code, std::size_t)) -async_read(AsyncReadStream& s, - ASIO_MOVE_ARG(DynamicBuffer) buffers, - ASIO_MOVE_ARG(ReadHandler) handler, - typename enable_if< - is_dynamic_buffer<DynamicBuffer>::value - >::type* = 0); +template <typename AsyncReadStream, typename DynamicBuffer_v1, + ASIO_COMPLETION_TOKEN_FOR(void (asio::error_code, + std::size_t)) ReadToken = default_completion_token_t< + typename AsyncReadStream::executor_type>> +auto async_read(AsyncReadStream& s, DynamicBuffer_v1&& buffers, + ReadToken&& token = default_completion_token_t< + typename AsyncReadStream::executor_type>(), + constraint_t< + is_dynamic_buffer_v1<decay_t<DynamicBuffer_v1>>::value + > = 0, + constraint_t< + !is_dynamic_buffer_v2<decay_t<DynamicBuffer_v1>>::value + > = 0) + -> decltype( + async_initiate<ReadToken, + void (asio::error_code, std::size_t)>( + declval<detail::initiate_async_read_dynbuf_v1<AsyncReadStream>>(), + token, static_cast<DynamicBuffer_v1&&>(buffers), transfer_all())); /// Start an asynchronous operation to read a certain amount of data from a /// stream. /** * This function is used to asynchronously read a certain number of bytes of - * data from a stream. The function call always returns immediately. The - * asynchronous operation will continue until one of the following conditions is - * true: + * data from a stream. It is an initiating function for an @ref + * asynchronous_operation, and always returns immediately. The asynchronous + * operation will continue until one of the following conditions is true: * * @li The specified dynamic buffer sequence is full (that is, it has reached * maximum size). @@ -767,7 +1019,7 @@ async_read(AsyncReadStream& s, * @param buffers The dynamic buffer sequence into which the data will be read. * Although the buffers object may be copied as necessary, ownership of the * underlying memory blocks is retained by the caller, which must guarantee - * that they remain valid until the handler is called. + * that they remain valid until the completion handler is called. * * @param completion_condition The function object to be called to determine * whether the read operation is complete. The signature of the function object @@ -783,34 +1035,60 @@ async_read(AsyncReadStream& s, * return value indicates the maximum number of bytes to be read on the next * call to the stream's async_read_some function. * - * @param handler The handler to be called when the read operation completes. - * Copies will be made of the handler as required. The function signature of the - * handler must be: + * @param token The @ref completion_token that will be used to produce a + * completion handler, which will be called when the read completes. + * Potential completion tokens include @ref use_future, @ref use_awaitable, + * @ref yield_context, or a function object with the correct completion + * signature. The function signature of the completion handler must be: * @code void handler( - * const asio::error_code& error, // Result of operation. + * // Result of operation. + * const asio::error_code& error, * - * std::size_t bytes_transferred // Number of bytes copied into the - * // buffers. If an error occurred, - * // this will be the number of - * // bytes successfully transferred - * // prior to the error. + * // Number of bytes copied into the buffers. If an error + * // occurred, this will be the number of bytes successfully + * // transferred prior to the error. + * std::size_t bytes_transferred * ); @endcode * Regardless of whether the asynchronous operation completes immediately or - * not, the handler will not be invoked from within this function. Invocation of - * the handler will be performed in a manner equivalent to using - * asio::io_context::post(). + * not, the completion handler will not be invoked from within this function. + * On immediate completion, invocation of the handler will be performed in a + * manner equivalent to using asio::post(). + * + * @par Completion Signature + * @code void(asio::error_code, std::size_t) @endcode + * + * @par Per-Operation Cancellation + * This asynchronous operation supports cancellation for the following + * asio::cancellation_type values: + * + * @li @c cancellation_type::terminal + * + * @li @c cancellation_type::partial + * + * if they are also supported by the @c AsyncReadStream type's + * @c async_read_some operation. */ -template <typename AsyncReadStream, typename DynamicBuffer, - typename CompletionCondition, typename ReadHandler> -ASIO_INITFN_RESULT_TYPE(ReadHandler, - void (asio::error_code, std::size_t)) -async_read(AsyncReadStream& s, - ASIO_MOVE_ARG(DynamicBuffer) buffers, +template <typename AsyncReadStream, + typename DynamicBuffer_v1, typename CompletionCondition, + ASIO_COMPLETION_TOKEN_FOR(void (asio::error_code, + std::size_t)) ReadToken = default_completion_token_t< + typename AsyncReadStream::executor_type>> +auto async_read(AsyncReadStream& s, DynamicBuffer_v1&& buffers, CompletionCondition completion_condition, - ASIO_MOVE_ARG(ReadHandler) handler, - typename enable_if< - is_dynamic_buffer<DynamicBuffer>::value - >::type* = 0); + ReadToken&& token = default_completion_token_t< + typename AsyncReadStream::executor_type>(), + constraint_t< + is_dynamic_buffer_v1<decay_t<DynamicBuffer_v1>>::value + > = 0, + constraint_t< + !is_dynamic_buffer_v2<decay_t<DynamicBuffer_v1>>::value + > = 0) + -> decltype( + async_initiate<ReadToken, + void (asio::error_code, std::size_t)>( + declval<detail::initiate_async_read_dynbuf_v1<AsyncReadStream>>(), + token, static_cast<DynamicBuffer_v1&&>(buffers), + static_cast<CompletionCondition&&>(completion_condition))); #if !defined(ASIO_NO_EXTENSIONS) #if !defined(ASIO_NO_IOSTREAM) @@ -819,9 +1097,9 @@ async_read(AsyncReadStream& s, /// stream. /** * This function is used to asynchronously read a certain number of bytes of - * data from a stream. The function call always returns immediately. The - * asynchronous operation will continue until one of the following conditions is - * true: + * data from a stream. It is an initiating function for an @ref + * asynchronous_operation, and always returns immediately. The asynchronous + * operation will continue until one of the following conditions is true: * * @li The supplied buffer is full (that is, it has reached maximum size). * @@ -838,44 +1116,67 @@ async_read(AsyncReadStream& s, * * @param b A basic_streambuf object into which the data will be read. Ownership * of the streambuf is retained by the caller, which must guarantee that it - * remains valid until the handler is called. + * remains valid until the completion handler is called. * - * @param handler The handler to be called when the read operation completes. - * Copies will be made of the handler as required. The function signature of the - * handler must be: + * @param token The @ref completion_token that will be used to produce a + * completion handler, which will be called when the read completes. + * Potential completion tokens include @ref use_future, @ref use_awaitable, + * @ref yield_context, or a function object with the correct completion + * signature. The function signature of the completion handler must be: * @code void handler( - * const asio::error_code& error, // Result of operation. + * // Result of operation. + * const asio::error_code& error, * - * std::size_t bytes_transferred // Number of bytes copied into the - * // buffers. If an error occurred, - * // this will be the number of - * // bytes successfully transferred - * // prior to the error. + * // Number of bytes copied into the buffers. If an error + * // occurred, this will be the number of bytes successfully + * // transferred prior to the error. + * std::size_t bytes_transferred * ); @endcode * Regardless of whether the asynchronous operation completes immediately or - * not, the handler will not be invoked from within this function. Invocation of - * the handler will be performed in a manner equivalent to using - * asio::io_context::post(). + * not, the completion handler will not be invoked from within this function. + * On immediate completion, invocation of the handler will be performed in a + * manner equivalent to using asio::post(). + * + * @par Completion Signature + * @code void(asio::error_code, std::size_t) @endcode * * @note This overload is equivalent to calling: * @code asio::async_read( * s, b, * asio::transfer_all(), * handler); @endcode + * + * @par Per-Operation Cancellation + * This asynchronous operation supports cancellation for the following + * asio::cancellation_type values: + * + * @li @c cancellation_type::terminal + * + * @li @c cancellation_type::partial + * + * if they are also supported by the @c AsyncReadStream type's + * @c async_read_some operation. */ -template <typename AsyncReadStream, typename Allocator, typename ReadHandler> -ASIO_INITFN_RESULT_TYPE(ReadHandler, - void (asio::error_code, std::size_t)) -async_read(AsyncReadStream& s, basic_streambuf<Allocator>& b, - ASIO_MOVE_ARG(ReadHandler) handler); +template <typename AsyncReadStream, typename Allocator, + ASIO_COMPLETION_TOKEN_FOR(void (asio::error_code, + std::size_t)) ReadToken = default_completion_token_t< + typename AsyncReadStream::executor_type>> +auto async_read(AsyncReadStream& s, basic_streambuf<Allocator>& b, + ReadToken&& token = default_completion_token_t< + typename AsyncReadStream::executor_type>()) + -> decltype( + async_initiate<ReadToken, + void (asio::error_code, std::size_t)>( + declval<detail::initiate_async_read_dynbuf_v1<AsyncReadStream>>(), + token, basic_streambuf_ref<Allocator>(b), transfer_all())); /// Start an asynchronous operation to read a certain amount of data from a /// stream. /** * This function is used to asynchronously read a certain number of bytes of - * data from a stream. The function call always returns immediately. The - * asynchronous operation will continue until one of the following conditions is - * true: + * data from a stream. It is an initiating function for an @ref + * asynchronous_operation, and always returns immediately. The asynchronous + * operation will continue until one of the following conditions is true: * * @li The supplied buffer is full (that is, it has reached maximum size). * @@ -892,7 +1193,7 @@ async_read(AsyncReadStream& s, basic_streambuf<Allocator>& b, * * @param b A basic_streambuf object into which the data will be read. Ownership * of the streambuf is retained by the caller, which must guarantee that it - * remains valid until the handler is called. + * remains valid until the completion handler is called. * * @param completion_condition The function object to be called to determine * whether the read operation is complete. The signature of the function object @@ -908,33 +1209,233 @@ async_read(AsyncReadStream& s, basic_streambuf<Allocator>& b, * return value indicates the maximum number of bytes to be read on the next * call to the stream's async_read_some function. * - * @param handler The handler to be called when the read operation completes. - * Copies will be made of the handler as required. The function signature of the - * handler must be: + * @param token The @ref completion_token that will be used to produce a + * completion handler, which will be called when the read completes. + * Potential completion tokens include @ref use_future, @ref use_awaitable, + * @ref yield_context, or a function object with the correct completion + * signature. The function signature of the completion handler must be: * @code void handler( - * const asio::error_code& error, // Result of operation. + * // Result of operation. + * const asio::error_code& error, * - * std::size_t bytes_transferred // Number of bytes copied into the - * // buffers. If an error occurred, - * // this will be the number of - * // bytes successfully transferred - * // prior to the error. + * // Number of bytes copied into the buffers. If an error + * // occurred, this will be the number of bytes successfully + * // transferred prior to the error. + * std::size_t bytes_transferred * ); @endcode * Regardless of whether the asynchronous operation completes immediately or - * not, the handler will not be invoked from within this function. Invocation of - * the handler will be performed in a manner equivalent to using - * asio::io_context::post(). + * not, the completion handler will not be invoked from within this function. + * On immediate completion, invocation of the handler will be performed in a + * manner equivalent to using asio::post(). + * + * @par Completion Signature + * @code void(asio::error_code, std::size_t) @endcode + * + * @par Per-Operation Cancellation + * This asynchronous operation supports cancellation for the following + * asio::cancellation_type values: + * + * @li @c cancellation_type::terminal + * + * @li @c cancellation_type::partial + * + * if they are also supported by the @c AsyncReadStream type's + * @c async_read_some operation. */ -template <typename AsyncReadStream, typename Allocator, - typename CompletionCondition, typename ReadHandler> -ASIO_INITFN_RESULT_TYPE(ReadHandler, - void (asio::error_code, std::size_t)) -async_read(AsyncReadStream& s, basic_streambuf<Allocator>& b, +template <typename AsyncReadStream, + typename Allocator, typename CompletionCondition, + ASIO_COMPLETION_TOKEN_FOR(void (asio::error_code, + std::size_t)) ReadToken = default_completion_token_t< + typename AsyncReadStream::executor_type>> +auto async_read(AsyncReadStream& s, basic_streambuf<Allocator>& b, CompletionCondition completion_condition, - ASIO_MOVE_ARG(ReadHandler) handler); + ReadToken&& token = default_completion_token_t< + typename AsyncReadStream::executor_type>()) + -> decltype( + async_initiate<ReadToken, + void (asio::error_code, std::size_t)>( + declval<detail::initiate_async_read_dynbuf_v1<AsyncReadStream>>(), + token, basic_streambuf_ref<Allocator>(b), + static_cast<CompletionCondition&&>(completion_condition))); #endif // !defined(ASIO_NO_IOSTREAM) #endif // !defined(ASIO_NO_EXTENSIONS) +#endif // !defined(ASIO_NO_DYNAMIC_BUFFER_V1) + +/// Start an asynchronous operation to read a certain amount of data from a +/// stream. +/** + * This function is used to asynchronously read a certain number of bytes of + * data from a stream. It is an initiating function for an @ref + * asynchronous_operation, and always returns immediately. The asynchronous + * operation will continue until one of the following conditions is true: + * + * @li The specified dynamic buffer sequence is full (that is, it has reached + * maximum size). + * + * @li An error occurred. + * + * This operation is implemented in terms of zero or more calls to the stream's + * async_read_some function, and is known as a <em>composed operation</em>. The + * program must ensure that the stream performs no other read operations (such + * as async_read, the stream's async_read_some function, or any other composed + * operations that perform reads) until this operation completes. + * + * @param s The stream from which the data is to be read. The type must support + * the AsyncReadStream concept. + * + * @param buffers The dynamic buffer sequence into which the data will be read. + * Although the buffers object may be copied as necessary, ownership of the + * underlying memory blocks is retained by the caller, which must guarantee + * that they remain valid until the completion handler is called. + * + * @param token The @ref completion_token that will be used to produce a + * completion handler, which will be called when the read completes. + * Potential completion tokens include @ref use_future, @ref use_awaitable, + * @ref yield_context, or a function object with the correct completion + * signature. The function signature of the completion handler must be: + * @code void handler( + * // Result of operation. + * const asio::error_code& error, + * + * // Number of bytes copied into the buffers. If an error + * // occurred, this will be the number of bytes successfully + * // transferred prior to the error. + * std::size_t bytes_transferred + * ); @endcode + * Regardless of whether the asynchronous operation completes immediately or + * not, the completion handler will not be invoked from within this function. + * On immediate completion, invocation of the handler will be performed in a + * manner equivalent to using asio::post(). + * + * @par Completion Signature + * @code void(asio::error_code, std::size_t) @endcode + * + * @note This overload is equivalent to calling: + * @code asio::async_read( + * s, buffers, + * asio::transfer_all(), + * handler); @endcode + * + * @par Per-Operation Cancellation + * This asynchronous operation supports cancellation for the following + * asio::cancellation_type values: + * + * @li @c cancellation_type::terminal + * + * @li @c cancellation_type::partial + * + * if they are also supported by the @c AsyncReadStream type's + * @c async_read_some operation. + */ +template <typename AsyncReadStream, typename DynamicBuffer_v2, + ASIO_COMPLETION_TOKEN_FOR(void (asio::error_code, + std::size_t)) ReadToken = default_completion_token_t< + typename AsyncReadStream::executor_type>> +auto async_read(AsyncReadStream& s, DynamicBuffer_v2 buffers, + ReadToken&& token = default_completion_token_t< + typename AsyncReadStream::executor_type>(), + constraint_t< + is_dynamic_buffer_v2<DynamicBuffer_v2>::value + > = 0) + -> decltype( + async_initiate<ReadToken, + void (asio::error_code, std::size_t)>( + declval<detail::initiate_async_read_dynbuf_v2<AsyncReadStream>>(), + token, static_cast<DynamicBuffer_v2&&>(buffers), transfer_all())); + +/// Start an asynchronous operation to read a certain amount of data from a +/// stream. +/** + * This function is used to asynchronously read a certain number of bytes of + * data from a stream. It is an initiating function for an @ref + * asynchronous_operation, and always returns immediately. The asynchronous + * operation will continue until one of the following conditions is true: + * + * @li The specified dynamic buffer sequence is full (that is, it has reached + * maximum size). + * + * @li The completion_condition function object returns 0. + * + * This operation is implemented in terms of zero or more calls to the stream's + * async_read_some function, and is known as a <em>composed operation</em>. The + * program must ensure that the stream performs no other read operations (such + * as async_read, the stream's async_read_some function, or any other composed + * operations that perform reads) until this operation completes. + * + * @param s The stream from which the data is to be read. The type must support + * the AsyncReadStream concept. + * + * @param buffers The dynamic buffer sequence into which the data will be read. + * Although the buffers object may be copied as necessary, ownership of the + * underlying memory blocks is retained by the caller, which must guarantee + * that they remain valid until the completion handler is called. + * + * @param completion_condition The function object to be called to determine + * whether the read operation is complete. The signature of the function object + * must be: + * @code std::size_t completion_condition( + * // Result of latest async_read_some operation. + * const asio::error_code& error, + * + * // Number of bytes transferred so far. + * std::size_t bytes_transferred + * ); @endcode + * A return value of 0 indicates that the read operation is complete. A non-zero + * return value indicates the maximum number of bytes to be read on the next + * call to the stream's async_read_some function. + * + * @param token The @ref completion_token that will be used to produce a + * completion handler, which will be called when the read completes. + * Potential completion tokens include @ref use_future, @ref use_awaitable, + * @ref yield_context, or a function object with the correct completion + * signature. The function signature of the completion handler must be: + * @code void handler( + * // Result of operation. + * const asio::error_code& error, + * + * // Number of bytes copied into the buffers. If an error + * // occurred, this will be the number of bytes successfully + * // transferred prior to the error. + * std::size_t bytes_transferred + * ); @endcode + * Regardless of whether the asynchronous operation completes immediately or + * not, the completion handler will not be invoked from within this function. + * On immediate completion, invocation of the handler will be performed in a + * manner equivalent to using asio::post(). + * + * @par Completion Signature + * @code void(asio::error_code, std::size_t) @endcode + * + * @par Per-Operation Cancellation + * This asynchronous operation supports cancellation for the following + * asio::cancellation_type values: + * + * @li @c cancellation_type::terminal + * + * @li @c cancellation_type::partial + * + * if they are also supported by the @c AsyncReadStream type's + * @c async_read_some operation. + */ +template <typename AsyncReadStream, + typename DynamicBuffer_v2, typename CompletionCondition, + ASIO_COMPLETION_TOKEN_FOR(void (asio::error_code, + std::size_t)) ReadToken = default_completion_token_t< + typename AsyncReadStream::executor_type>> +auto async_read(AsyncReadStream& s, DynamicBuffer_v2 buffers, + CompletionCondition completion_condition, + ReadToken&& token = default_completion_token_t< + typename AsyncReadStream::executor_type>(), + constraint_t< + is_dynamic_buffer_v2<DynamicBuffer_v2>::value + > = 0) + -> decltype( + async_initiate<ReadToken, + void (asio::error_code, std::size_t)>( + declval<detail::initiate_async_read_dynbuf_v2<AsyncReadStream>>(), + token, static_cast<DynamicBuffer_v2&&>(buffers), + static_cast<CompletionCondition&&>(completion_condition))); /*@}*/ |