mirror of
https://github.com/boostorg/beast.git
synced 2025-07-31 05:17:26 +02:00
Decay bound arguments in handler wrapper parameters:
fix #1365 To reduce instantiations, the list of template parameters to the bind and bind_front handler wrappers are decayed before naming the class template.
This commit is contained in:
@ -1,3 +1,9 @@
|
|||||||
|
Version 201
|
||||||
|
|
||||||
|
* Decay bound arguments in handler wrapper parameters
|
||||||
|
|
||||||
|
--------------------------------------------------------------------------------
|
||||||
|
|
||||||
Version 200
|
Version 200
|
||||||
|
|
||||||
* Don't include OpenSSL for core snippets
|
* Don't include OpenSSL for core snippets
|
||||||
|
@ -31,16 +31,19 @@ namespace beast {
|
|||||||
handler, whose associated allocator and associated executor will
|
handler, whose associated allocator and associated executor will
|
||||||
will be the same as those of the original handler.
|
will be the same as those of the original handler.
|
||||||
|
|
||||||
Example:
|
@par Example
|
||||||
|
|
||||||
|
This function posts the invocation of the specified completion
|
||||||
|
handler with bound arguments:
|
||||||
|
|
||||||
@code
|
@code
|
||||||
template<class AsyncReadStream, class ReadHandler>
|
template <class AsyncReadStream, class ReadHandler>
|
||||||
void
|
void
|
||||||
signal_aborted(AsyncReadStream& stream, ReadHandler&& handler)
|
signal_aborted (AsyncReadStream& stream, ReadHandler&& handler)
|
||||||
{
|
{
|
||||||
net::post(
|
net::post(
|
||||||
stream.get_executor(),
|
stream.get_executor(),
|
||||||
bind_handler(std::forward<ReadHandler>(handler),
|
bind_handler (std::forward <ReadHandler> (handler),
|
||||||
net::error::operation_aborted, 0));
|
net::error::operation_aborted, 0));
|
||||||
}
|
}
|
||||||
@endcode
|
@endcode
|
||||||
@ -57,7 +60,8 @@ template<class Handler, class... Args>
|
|||||||
__implementation_defined__
|
__implementation_defined__
|
||||||
#else
|
#else
|
||||||
detail::bind_wrapper<
|
detail::bind_wrapper<
|
||||||
typename std::decay<Handler>::type, Args...>
|
typename std::decay<Handler>::type,
|
||||||
|
typename std::decay<Args>::type...>
|
||||||
#endif
|
#endif
|
||||||
bind_handler(Handler&& handler, Args&&... args)
|
bind_handler(Handler&& handler, Args&&... args)
|
||||||
{
|
{
|
||||||
@ -67,9 +71,11 @@ bind_handler(Handler&& handler, Args&&... args)
|
|||||||
Handler, void(Args...)>::value,
|
Handler, void(Args...)>::value,
|
||||||
"Handler requirements not met");
|
"Handler requirements not met");
|
||||||
#endif
|
#endif
|
||||||
return detail::bind_wrapper<typename std::decay<
|
return detail::bind_wrapper<
|
||||||
Handler>::type, Args...>(std::forward<
|
typename std::decay<Handler>::type,
|
||||||
Handler>(handler), std::forward<Args>(args)...);
|
typename std::decay<Args>::type...>(
|
||||||
|
std::forward<Handler>(handler),
|
||||||
|
std::forward<Args>(args)...);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Bind parameters to a completion handler, creating a new handler.
|
/** Bind parameters to a completion handler, creating a new handler.
|
||||||
@ -83,17 +89,20 @@ bind_handler(Handler&& handler, Args&&... args)
|
|||||||
handler, whose associated allocator and associated executor will
|
handler, whose associated allocator and associated executor will
|
||||||
will be the same as those of the original handler.
|
will be the same as those of the original handler.
|
||||||
|
|
||||||
Example:
|
@par Example
|
||||||
|
|
||||||
|
This function posts the invocation of the specified completion
|
||||||
|
handler with bound arguments:
|
||||||
|
|
||||||
@code
|
@code
|
||||||
template<class AsyncReadStream, class ReadHandler>
|
template <class AsyncReadStream, class ReadHandler>
|
||||||
void
|
void
|
||||||
signal_aborted(AsyncReadStream& stream, ReadHandler&& handler)
|
signal_eof (AsyncReadStream& stream, ReadHandler&& handler)
|
||||||
{
|
{
|
||||||
net::post(
|
net::post(
|
||||||
stream.get_executor(),
|
stream.get_executor(),
|
||||||
bind_front_handler(std::forward<ReadHandler>(handler),
|
bind_front_handler (std::forward<ReadHandler> (handler),
|
||||||
net::error::operation_aborted, 0));
|
net::error::eof, 0));
|
||||||
}
|
}
|
||||||
@endcode
|
@endcode
|
||||||
|
|
||||||
|
@ -31,8 +31,7 @@ namespace detail {
|
|||||||
template<class Handler, class... Args>
|
template<class Handler, class... Args>
|
||||||
class bind_wrapper
|
class bind_wrapper
|
||||||
{
|
{
|
||||||
using args_type = detail::tuple<
|
using args_type = detail::tuple<Args...>;
|
||||||
typename std::decay<Args>::type...>;
|
|
||||||
|
|
||||||
Handler h_;
|
Handler h_;
|
||||||
args_type args_;
|
args_type args_;
|
||||||
@ -84,9 +83,7 @@ class bind_wrapper
|
|||||||
std::forward<Vals>(vals));
|
std::forward<Vals>(vals));
|
||||||
}
|
}
|
||||||
|
|
||||||
template<
|
template<class ArgsTuple, std::size_t... S>
|
||||||
class ArgsTuple,
|
|
||||||
std::size_t... S>
|
|
||||||
static
|
static
|
||||||
void
|
void
|
||||||
invoke(
|
invoke(
|
||||||
@ -123,12 +120,15 @@ public:
|
|||||||
bind_wrapper(bind_wrapper&&) = default;
|
bind_wrapper(bind_wrapper&&) = default;
|
||||||
bind_wrapper(bind_wrapper const&) = default;
|
bind_wrapper(bind_wrapper const&) = default;
|
||||||
|
|
||||||
template<class DeducedHandler>
|
template<
|
||||||
|
class DeducedHandler,
|
||||||
|
class... Args_>
|
||||||
explicit
|
explicit
|
||||||
bind_wrapper(
|
bind_wrapper(
|
||||||
DeducedHandler&& handler, Args&&... args)
|
DeducedHandler&& handler,
|
||||||
|
Args_&&... args)
|
||||||
: h_(std::forward<DeducedHandler>(handler))
|
: h_(std::forward<DeducedHandler>(handler))
|
||||||
, args_(std::forward<Args>(args)...)
|
, args_(std::forward<Args_>(args)...)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -12,6 +12,7 @@
|
|||||||
|
|
||||||
#include <boost/beast/core/detail/type_traits.hpp>
|
#include <boost/beast/core/detail/type_traits.hpp>
|
||||||
#include <boost/beast/_experimental/unit_test/suite.hpp>
|
#include <boost/beast/_experimental/unit_test/suite.hpp>
|
||||||
|
#include <boost/beast/_experimental/test/stream.hpp>
|
||||||
#include <boost/asio/io_context.hpp>
|
#include <boost/asio/io_context.hpp>
|
||||||
#include <boost/asio/bind_executor.hpp>
|
#include <boost/asio/bind_executor.hpp>
|
||||||
#include <boost/asio/executor_work_guard.hpp>
|
#include <boost/asio/executor_work_guard.hpp>
|
||||||
@ -41,6 +42,40 @@ public:
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
template <class AsyncReadStream, class ReadHandler>
|
||||||
|
void
|
||||||
|
signal_aborted (AsyncReadStream& stream, ReadHandler&& handler)
|
||||||
|
{
|
||||||
|
net::post(
|
||||||
|
stream.get_executor(),
|
||||||
|
bind_handler (std::forward <ReadHandler> (handler),
|
||||||
|
net::error::operation_aborted, 0));
|
||||||
|
}
|
||||||
|
|
||||||
|
template <class AsyncReadStream, class ReadHandler>
|
||||||
|
void
|
||||||
|
signal_eof (AsyncReadStream& stream, ReadHandler&& handler)
|
||||||
|
{
|
||||||
|
net::post(
|
||||||
|
stream.get_executor(),
|
||||||
|
bind_front_handler (std::forward<ReadHandler> (handler),
|
||||||
|
net::error::eof, 0));
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
testJavadocs()
|
||||||
|
{
|
||||||
|
BEAST_EXPECT((
|
||||||
|
&bind_handler_test::signal_aborted<
|
||||||
|
test::stream, handler<error_code, std::size_t>>));
|
||||||
|
|
||||||
|
BEAST_EXPECT((
|
||||||
|
&bind_handler_test::signal_eof<
|
||||||
|
test::stream, handler<error_code, std::size_t>>));
|
||||||
|
}
|
||||||
|
|
||||||
|
//--------------------------------------------------------------------------
|
||||||
|
|
||||||
struct copyable
|
struct copyable
|
||||||
{
|
{
|
||||||
template<class... Args>
|
template<class... Args>
|
||||||
@ -469,6 +504,7 @@ public:
|
|||||||
void
|
void
|
||||||
run() override
|
run() override
|
||||||
{
|
{
|
||||||
|
testJavadocs();
|
||||||
testBindHandler();
|
testBindHandler();
|
||||||
testBindFrontHandler();
|
testBindFrontHandler();
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user